Editing metadata of resources¶
What is a description resource¶
Description resources contain auxiliary information about a resource. In CSS, these represent metadata corresponding to that resource. Every resource always has a corresponding description resource and therefore description resources can not be created or deleted directly.
Description resources are discoverable by interacting with their subject resource:
the response to a GET
or HEAD
request on a subject resource
will contain a describedby
Link Header with a URL that points to its description resource.
Clients should always follow this link rather than guessing its URL,
because the Solid Protocol does not mandate a specific description resource URL.
The default CSS configurations use as a convention that http://example.org/resource
has http://example.org/resource.meta
as its description resource.
How to edit the metadata of a resource¶
Editing the metadata of a resource is performed by editing the description resource directly.
This can only be done using PATCH
requests
(see example workflow).
PUT
requests on description resources are not allowed,
because they would replace the entire resource state,
whereas some metadata is protected or generated by the server.
Similarly, DELETE
on description resources is not allowed
because a resource will always have some metadata (e.g. rdf:type
).
Instead, the lifecycle of description resources is managed by the server.
Protected metadata¶
Some metadata is managed by the server and can not be modified directly, such as the last modified date.
The CSS will throw an error (409 ConflictHttpError
) when trying to change this protected metadata.
Preserving metadata¶
PUT
requests on a resource will reset the description resource.
There is however a way to keep the contents of description resource prior to the PUT
request:
adding the HTTP Link
header targeting the description resource with rel="preserve"
.
When the resource URL is http://localhost:3000/foobar
, preserving its description resource when updating its contents
can be achieved like in the following example:
curl -X PUT 'http://localhost:3000/foobar' \
-H 'Content-Type: text/turtle' \
-H 'Link: <http://localhost:3000/foobar.meta>;rel="preserve"' \
-d "<ex:s> <ex:p> <ex:o>."
Impact on creating containers¶
When creating a container the input body is ignored
and performing a PUT
request on an existing container will result in an error.
Container metadata can only be added and modified by performing a PATCH
on the description resource,
similarly to documents.
This is done to clearly differentiate between a container's representation and its metadata.
Example of a workflow for editing a description resource¶
In this example, we add an inbox description to http://localhost:3000/foo/
.
This allows discovery of the ldp:inbox
as described in the Linked Data Notifications specification.
We have started the CSS with the default configuration
and have already created an inbox at http://localhost:3000/inbox/
.
Since we don't know the location of the description resource,
we first send a HEAD
request to the resource to obtain the URL of its description resource.
curl --head 'http://localhost:3000/foo/'
which will produce a response with at least these headers:
HTTP/1.1 200 OK
Link: <http://localhost:3000/foo/.meta>; rel="describedby"
Now that we have the URL of the description resource, we create a patch for adding the inbox in the description of the resource.
curl -X PATCH 'http://localhost:3000/foo/.meta' \
-H 'Content-Type: text/n3' \
--data-raw '@prefix solid: <http://www.w3.org/ns/solid/terms#>.
<> a solid:InsertDeletePatch;
solid:inserts { <http://localhost:3000/foo/> <http://www.w3.org/ns/ldp#inbox> <http://localhost:3000/inbox/>. }.'
After this update, we can verify that the inbox is added by performing a GET request to the description resource
curl 'http://localhost:3000/foo/.meta'
With as result for the body
@prefix dc: <http://purl.org/dc/terms/>.
@prefix ldp: <http://www.w3.org/ns/ldp#>.
@prefix posix: <http://www.w3.org/ns/posix/stat#>.
@prefix xsd: <http://www.w3.org/2001/XMLSchema#>.
<http://localhost:3000/foo/> a ldp:Container, ldp:BasicContainer, ldp:Resource;
dc:modified "2022-06-09T08:17:07.000Z"^^xsd:dateTime;
ldp:inbox <http://localhost:3000/inbox/>;.
This can also be verified by sending a GET request to the subject resource itself. The inbox location can also be found in the Link headers.
curl -v 'http://localhost:3000/foo/'
HTTP/1.1 200 OK
Link: <http://localhost:3000/inbox/>; rel="http://www.w3.org/ns/ldp#inbox"