note: the examples in this post are no longer live, and the data access patterns no longer recommended. for updates on Solid development, check out my work at Understory
If the web is urgently in need of a revolution then it's important to understand what we can do today to work toward a better world. Let's get the bad news out of the way first: in February 2020, Solid isn't ready for prime time. The specification isn't finished, the tools are a minefield of footguns, and the community - while active, smart, and kind - is still fairly small.
The good news is that what's there is already very powerful, and for simple use cases, already a delight:
import React from 'react';
import { Value } from '@solid/react';
export default () => (
<Value src="[https://tvachon.inrupt.net/profile/card#me].name"/>
)
This tiny component uses the @solid/react library to execute a query against my pod using the LDflex DSL. It's really running live above, which is why you may have seen a brief flicker before my name popped up. LDflex was designed to make it easy for JavaScript developers to start building Solid applications. If you think of a Solid Pod as an entrypoint to the worldwide graph of data that is the Semantic Web, you can think of LDflex as a way to navigate that graph. You can also render lists of things - here's a list of Ruben Verborgh's friends:
<List src="[https://ruben.verborgh.org/profile/#me].friends.firstName"/>
In theory, you should be able to point LDflex at any Linked Data server but at the moment most Linked Data servers in the wild do not use CORS in a way that makes this possible.
a graph navigation dsl
At a conceptual level, the Semantic Web is a graph where both the
nodes and edges are identified by globally unique URIs. My profile
page https://tvachon.inrupt.net/profile/card#me
is a node that
represents me, which when resolved results in a
Turtle file that
describes a graph of information about me:
<https://tvachon.inrupt.net/profile/card#me> <http://xmlns.com/foaf/0.1/knows> <https://tobytoberson.inrupt.net/profile/card#me>;
<https://tvachon.inrupt.net/profile/card#me> <http://www.w3.org/2006/vcard/ns#fn> "Travis";
The first of these two sets of "triples" can be read as "the entity
represented by the URI https://tvachon.inrupt.net/profile/card#me
has a relationship described by the URI
http://xmlns.com/foaf/0.1/knows
with the entity represented by the
URI https://tobytoberson.inrupt.net/profile/card#me
" - in other
words, "Travis knows Toby."
The second set of triples says "the entity represented by
https://tvachon.inrupt.net/profile/card#me
has a relationship
described by http://www.w3.org/2006/vcard/ns#fn
with the string
'Travis'" - in other words, "https://tvachon.inrupt.net/profile/card#me
's 'formatted name' is Travis."
In its most basic form, LDflex just lets you follow the links in this graph. Taking a modified version of the expression used by the react component above:
<Value src="[https://tvachon.inrupt.net/profile/card#me][http://www.w3.org/2006/vcard/ns#fn]"/>
we can now see that this can be read "display the value that has a
http://www.w3.org/2006/vcard/ns#fn
relationship with the entity
https://tvachon.inrupt.net/profile/card#me
." An LDflex interpreter
can be given a set of mappings from short strings to full URIs - in
the example above, http://www.w3.org/2006/vcard/ns#fn
has been
mapped to name
so we can shorten this to:
<Value src="[https://tvachon.inrupt.net/profile/card#me].name"/>
In the second example above, the LDflex interpreter will assume that
friends
is mapped to http://xmlns.com/foaf/0.1/knows
and
firstName
is mapped to http://xmlns.com/foaf/0.1/firstName
, so
<List src="[https://ruben.verborgh.org/profile/#me].friends.firstName"/>
will render a list of the http://xmlns.com/foaf/0.1/firstName
values
of each of the entities that has a http://xmlns.com/foaf/0.1/knows
relationship with https://ruben.verborgh.org/profile/#me
.
For a full list of the mappings that ship with the @solid/react
library, check out the @solid/context
project on
GitHub.
the future today
One of the most exciting things about @solid/react
is that it's
ready for use within the React-centric frameworks you're already
using. I'm writing this post using Gatsby
and the examples in the first section are live examples, embedded
within this post thanks to the magic of
MDX
. @solid/react
(and, I've found, most
existing Solid JavaScript libraries) doesn't currently behave well in
a Server Side Rendering (SSR) context, so to get it working in
SSR-forward frameworks like Gatsby and
next.js
you'll need to leverage React's
lazy
and Suspense
tools to ensure they only render on the client
side:
// components/LazyLoad.js
import React, {lazy, Suspense} from 'react';
export default ({path, ...args}) => {
if (typeof window === "undefined") {
return (<div>a lazy component will slouch into place here at runtime</div>)
} else {
const LazyComponent = lazy(() => import(`./${path}`))
return (
<Suspense fallback={<div>Loading..</div>}>
<LazyComponent {...args}/>
</Suspense>
)
}
}
With this in place, however, you'll be able to write MDX
that puts
code examples and their instantiations right next to each other in a
fluid manner:
simple use cases, already a delight:
```jsx
import React from 'react';
import { Value } from '@solid/react';
export default () => (
<Value src="[https://tvachon.inrupt.net/profile/card#me].name"/>
)
```
<LazyLoad path="solid-ground/Travis"/>
This tiny component uses the
I can tell you with certainty that this is a very satisfying writing experience.
In future posts I'll be writing more about the Solid frontend web development experience as it exists in early 2020 and what I'm hoping to see in the coming year. If you'd like to hear more, follow me on GitHub, Mastodon, or Twitter. If you're in the Bay Area, join me at the inaugural meetup of the Bay Area Solid Interest Club on February 20th, 2020 in downtown San Francisco.