ShapeTrees maps resource hierarchies to shape constraints. This is a Solid work product -- https://github.com/solid/data-interoperability-panel
This contains:
- two express servers:
- a simple static server to provide test documents:
- AppStore Server - serves static content and directories.
- solidApps/staticRoot - AppStore server's static content.
- a minimal LDP with support for shape trees
- LDP server - conforms to a subset of the Linked Data Platform.
- config.json - configuration for the servers
- a simple static server to provide test documents:
- mocha tests
- test - tests for several sample applications:
- bad.test.js - error conditions for LDP operations involving shape trees.
- local.test.js - tests specific to this implementation of LDP (depends on Slug: behavior, collision algorithms, etc)
- test - tests for several example applications:
- cal.test.js - calendar app that works with two calendar formats
- photo.test.js - very simple photo storage
- photoAlbum-shallow.test.js - a photo album that can use images from photo.test.js.
- gh-deep.test.js - an LDP emulation of the GitHub API.
- test-harness.js - support functions to minimize the ceremony in the above tests.
- */… - subdirectories with content POSTed in the above tests.
- test - tests for several sample applications:
git clone --recursive https://github.com/shapetrees/test-suite
cd test-suite/shapetree.js/
npm install
cd ..
npm install
npm run genkeys
The last step requires openssl to be installed. It generates two files:
- servers/ssl.key - private key file
- servers/ssl.cert - fullchain certificate
You can install your own key pair, such as what you might get from letsencrypt. You can override the location by editing the
"LDP"
entry inservers/config.json
:
"LDP": {
...
"keyFilePath": "servers/ssl.key",
"certFilePath": "servers/ssl.cert",
...
}
npm test
* npm run serve
* browse to http://localhost:12340/playground/index.html?manifest=../console/manifest.json
- remove or disable slug to reinforce lack of semantics in Container labels.
test-suite
├── shapetree.js (subrepo) - general ShapeTree Javascript library
│      ├── dist
│      │      └── shape-tree.js
│      ├── ecosystems
│      │      └── simple-apps.js
│      ├── lib
│      │      ├── prefixes.js
│      │      ├── rdf-errors.js
│      │      ├── rdf-serialization.js
│      │      └── shape-tree.js
│      ├── storage - drivers for the shapetree.js library to talk to the server's resource hierarchy
│      │      ├── fetch-self-signed.js
│      │      └── fs-promises.js
│      ├── README.md
│      ├── webapp
│      │      └── index.js
│      └── webpack.config.js
├── test ... see test below - ShapeTree tests
├── www ... (subrepo) see shapetree-tests-output - result of running tests; a sample ShapeTree ecosystem.
├── playground ... (subrepo) see playground below - intaractive WebApp for exploring/exercising ShapeTrees
├── console - configuration for the playground to use test-suite test data
│      └── manifest.json
├── servers
│      ├── ldpServer.js ⎱__ two servers used in testing
│      ├── AppStore.js  ⎰
│      ├── run - run the two servers used in testing
│      ├── config.json - server configuration
│      ├── server.cert  ⎱__ generated SSL key pair
│      ├── server.key  ⎰
│      └── favicon.ico
├── solidApps ... see solidAps below - static content for the app store server
├── README.md
├── TODO.txt
└── update-www-repo.sh
data used in tests:
└── test
        ├── bad.test.js - general ShapeTree tests
        ├── bad - files for general ShapeTree tests
        │      ├── malformed-ref-1.ttl
        │      ├── ref-1.ttl
        │      ├── ref-invalid-2.ttl
        │      └── ref-valid-3.ttl
        ├── local.test.js - tests specific to the servers/LDP.js implementation
        └── apps - tests for example applications
            ├── album
            │      └── ref-1.ttl
            ├── cal
            │      ├── 09abcdefghijklmnopqrstuvwx_20200107T140000Z.jsonld
            │      ├── 09abcdefghijklmnopqrstuvwx_20200107T140000Z.ttl
            │      ├── 19abcdefghijklmnopqrstuvwx_20200107T140000Z.jsonld
            │      ├── 19abcdefghijklmnopqrstuvwx_20200107T140000Z.ttl
            │      ├── commonAppointment1.ttl
            │      └── manifest.json
            ├── cal.test.js
            ├── gh
            │      ├── alice.json
            │      ├── alice-subscr1.ttl
            │      ├── alice.ttl
            │      ├── ericprud.ttl
            │      ├── jsg-issue1.ttl
            │      └── jsg.ttl
            ├── gh-deep.test.js
            ├── nevernote
            │      ├── img-M33_IR.jpg
            │      ├── inc-M33_IR.ttl
            │      └── note1.ttl
            ├── nevernote.test.js
            ├── photo
            │      └── 320px-Infrared_Triangulum_Galaxy_(M33).jpg
            ├── photoAlbum-shallow.test.js
            ├── photo.test.js
            └── test-harness.js
files served by the app store server:
└── solidApps
        └── staticRoot
               ├── album
               │      ├── PhotoAlbumShapeTree.jsonld
               │      ├── PhotoAlbumShapeTree.ttl
               │      ├── PhotoAlbumShapeTree.txt
               │      └── PhotoAlbum.shex
               ├── bad
               │      ├── PhotoAlbumShapeTree.jsonld
               │      ├── PhotoAlbumShapeTree.ttl
               │      ├── PhotoAlbum.shex
               │      ├── ShapeTreeMissingSchema.jsonld
               │      ├── ShapeTreeMissingSchema.ttl
               │      ├── ShapeTreeMissingShape.jsonld
               │      ├── ShapeTreeMissingShape.ttl
               │      ├── ShapeTreeNestedTwoStaticNames.jsonld
               │      ├── ShapeTreeNoShapeProperty.jsonld
               │      ├── ShapeTreeNoShapeProperty.ttl
               │      └── ShapeTreeTwoStaticNames.jsonld
               ├── cal
               │      ├── CalendarShapeTree.jsonld
               │      ├── CalendarShapeTree.ttl
               │      ├── Calendar.shex
               │      ├── GoogleCalendar.shex
               │      ├── GoogleShapeTree.jsonld
               │      ├── GoogleShapeTree.ttl
               │      ├── ical-owl-annot.shex
               │      ├── ical-owl.shex
               │      ├── MultiCalApp.ttl
               │      └── MultiCal.shex
               ├── contacts
               │      ├── ContactShapeTree.jsonld
               │      ├── ContactShapeTree.ttl
               │      └── Contact.shex
               ├── gh
               │      ├── gh-deep-Schema.shex
               │      ├── gh-deep-ShapeTree.jsonld
               │      ├── gh-deep-ShapeTree.ttl
               │      ├── gh-deep-ShapeTree.txt
               │      └── ghSkos.en.ttl
               ├── nevernote
               │      ├── NeverNoteBookShapeTree.jsonld
               │      ├── NeverNoteBookShapeTree.ttl
               │      ├── NeverNoteShapeTree.jsonld
               │      ├── NeverNoteShapeTree.ttl
               │      ├── NeverNote.shex
               │      ├── NN.js
               │      └── NN.shex
               ├── ns
               │      └── shapeTreeContext.jsonld
               └── photo
                        ├── PhotoShapeTree.jsonld
                        └── Photo.shex
an interactive tool for playing with ShapeTrees
└── playground
        ├── index.html
        ├── LICENSE
        ├── popup.html
        ├── README.md
        ├── scripts
        │      ├── jquery.js
        │      ├── main.js
        │      ├── rdflib.min.js
        │      ├── rdflib.min.js.map
        │      ├── shapetree.js
        │      └── solid-auth-client.bundle.js
        └── styles
                └── main.css
- Prefixes shapetree.js/lib/prefixes
- Errors shapetree.js/lib/rdf-errors
- RdfSerialization shapetree.js/lib/rdf-serialization
- Mutex shapetree.js/lib/mutex
- Storage
- fs-promises shapetree.js/storage/fs-promises
- ld-proxy shapetree.js/storage/ldp-proxy
- FetchSelfSigned shapetree.js/storage/fetch-self-signed
- ShapeTree shapetree.js/lib/shape
- ShapeTreeFetch shapetree.js/lib/shape
- Ecosystem
- Simple Apps shapetree.js/ecosystems/simple-apps
- LdpConf servers/config.json
LDP server
Storage(LdpConf.documentRoot, LdpConf.indexFile, RdfSerialization)
CallEcosystemFetch = (url, options = {}) => Ecosystem.fetch(url, options);
ShapeTree(Storage, RdfSerialization, FetchSelfSigned(CallEcosystemFetch))
Ecosystem(Storage, ShapeTree, RdfSerialization);
NoShapeTrees = process.env.SHAPETREE === 'fetch';
ShapeTreeFetch
const fsModule = require('../shapetree.js/storage/ldp-proxy');
const fs = new fsModule(LdpBase, RdfSerialization, FetchSelfSigned);
Fetch = await require('../shapetree.js/lib/shape-tree-fetch')(fs, RdfSerialization, FetchSelfSigned, LdpBase, Confs.LDP);
RDF serialization prefixes used in LDP and ShapeTrees.
- ldp: 'http://www.w3.org/ns/ldp#',
- rdf: 'http://www.w3.org/1999/02/22-rdf-syntax-ns#',
- rdfs: 'http://www.w3.org/2000/01/rdf-schema#',
- tree: 'http://www.w3.org/ns/shapetree#',
- xsd: 'http://www.w3.org/2001/XMLSchema#',
- dc: 'http://purl.org/dc/terms/',
Internal functions to parse and serialize RDF, plus rudimentary query.
- n3
- relateurl
- jsonld
- rdf-errors
parseRdf (body, base, contentType, prefixes = {}) parseTurtleSync (text, base, prefixes) async parseTurtle (text, base, prefixes) serializeTurtleSync (graph, base, prefixes) async serializeTurtle (graph, base, prefixes) async parseJsonLd (text, base) expectOne (g, s, p, o, nullable) function zeroOrOne (g, s, p, o) function one (g, s, p, o) renderRdfTerm (t)
Internal standard errors which result from e.g. improper input.
- class ManagedError extends Error
- class ParserError extends ManagedError
- class NotFoundError extends ManagedError
- class MiscHttpError extends ManagedError
- class MissingShapeError extends ManagedError
- class ShapeTreeStructureError extends ManagedError
- class ValidationError extends ManagedError
- class UriTemplateMatchError extends ManagedError
- async makeHttpError (operation, resource, role, resp)
- async getOrThrow (fetch, url)
Perform basic CRUD operations.
operation | LDP-C | LDP-R |
---|---|---|
read existing | read(url) | readContainer(url, prefixes) |
write existing or new | write(url, body) | writeContainer(url, prefixex) |
create and name new | invent(parentUrl, requestedName, body, mediaType) | inventContainer(url, requestedName, title, prefixes) |
delete existing | remove(url) | removeContainer(url) |
ensure existence of | -- | ensureContainer(url, prefixes, title) |
get resource info of | rstat(url) | rstat(url) |
- async rstat (url)
- async read (url)
- async write (url, body)
- async invent (parentUrl, requestedName, body, mediaType)
- async remove (url)
- async readContainer (url, prefixes)
- async writeContainer (url, graph, prefixes)
- async inventContainer (url, requestedName, title, prefixes)
- async removeContainer (url)
- async ensureContainer (url, prefixes, title)
- getIndexFilePath (url)
module | use | modules | constructor arguments |
---|---|---|---|
fs-promises | convert URLs to local paths and R/W with require('fs').promises |
fs, path | docRoot, indexFile, rdfInterface, encoding='utf8' |
ldp-proxy | execute API as fetch calls to a generic LDP server |
n3 | ldpServer, rdfInterface, fetch |
constructor (storage, rdfInterface, fetch)
- debug
- path
- n3
- rdf-errors
- prefixes
- uri-template-lite
- @shexjs/core
- @shexjs/parser
Generic LDP Container.
- constructor (url, title) {
- url
- prefixes
- graph
- subdirs
- ready
- async write ()
- async remove ()
- async merge (payload, base)
- addMember (location, shapeTreeUrl)
- removeMember (location, shapeTreeUrl)
- addSubdirs (addUs)
- async asManagedContainer (shapeTreeUrl, shapeTreeInstancePath)
extends Container
Container in a ShapeTree instance.
- constructor (url, title, shapeTreeUrl, shapeTreeInstancePath)
- shapeTreeUrl
- shapeTreeInstancePath
- shapeTreeInstanceRoot
- async getRootedShapeTree ()
- async validatePayload (payload, location, mediaType, ldpType, entityUrl)
- async function loadContainer (url)
- constructor (url, path = '.')
- getRdfRoot ()
- matchingStep (shapeTreeNode, slug)
- async instantiateStatic (stepNode, rootUrl, pathWithinShapeTree, parent, container = null)
- async validate (shape, payloadGraph, node)
- fs
- node-fetch
- lib/rdf-errors
- lib/prefixes
- constructor (storage, shapeTrees, rdfInterface) {
- storage:Storage
- shapeTrees:ShapeTree
- initialize (baseUrl, LdpConf) {
- baseUrl:URL
- appsUrl:URL
- cacheUrl:URL
- indexInstalledShapeTree (parent, instanceUrl, shapeTreeUrl)
- unindexInstalledShapeTree (parent, instanceUrl, shapeTreeUrl)
- reuseShapeTree (parent, shapeTreeUrl)
- async plantShapeTreeInstance (shapeTreeUrl, postedContainer, requestedLocation, payloadGraph)
- async registerInstance(appData, shapeTreeUrl, instanceUrl)
- parseInstatiationPayload (graph)
- async fetch (url, opts = {})