.. and press ENTER to ask a question on web5, how to write code and more.

Skip to main content
warning

This project is not actively being maintained. If you are interested in adopting it, please open an issue.

Create a Schema

A Credential Schema is a document that defines the structure of a Verifiable Credential (VC). It's based on JSON Schema and specifies which properties the issuer will use to create the VC. In this tutorial, you'll learn how to construct a schema and use the SSI Service to create it.

Details

Background on Schemas When creating Verifiable Credentials, it's useful to have a mechanism to define the shape the data in the credential takes, in a consistent manner.

The VC Data Model uses an open world data model, and with it, provides a mechanism to extend the core terminology to add any term with a technology known as JSON-LD.

JSON-LD is responsible for the @context property visible in VCs, DIDs, and other documents in the SSI space. However, JSON-LD is focused on semantics, answering the question "do we have a shared understanding of what this thing is?". More specifically, for a name credential, does your concept of "name" match mine?

Though the core data model is a JSON-LD data model, processing VCs as JSON-LD is not a requirement. The SSI Service chooses to take a simpler approach and processes VCs as pure JSON.

When constructing and processing VCs as pure JSON, it's useful to have a mechanism to define the data and add some light validation onto the shape that data takes.

JSON Schema is a widely used, and widely supported toolset that enables such functionality: the ability to define a schema, which provides a set of properties (both required and optional), and some light validation on top of those properties. The VC Data Model has a section on data schemas that enables this functionality.

1. Construct the JSON Schema​

Let's create a plain JSON Schema for an email address.

Keywords​

The JSON Schema Core Vocabulary is made up of keywords, which all begin with $, and are used to process schemas and guarantee interoperability.

The two keywords needed for our JSON schema are $id and $schema.

$id​

The $id keyword identifies a schema resource with its canonical URI. Note that this URI is an identifier and not necessarily a network locator. In the case of a network-addressable URL, a schema does not need to be downloadable from its canonical URI.

{
"$id": "https://example.com/schemas/email.json",
}

$schema​

For the $schema keyword, we'll use the JSON Schema Draft 2020-12

{
"$id": "https://example.com/schemas/email.json",
"$schema": "https://json-schema.org/draft/2020-12/schema",
}

Next, we'll define the data needed for our schema: an email address. This includes the name, type, and properties of the data:

{
"$id": "https://example.com/schemas/email.json",
"$schema": "https://json-schema.org/draft/2020-12/schema",
"name": "Email Address",
"type": "object",
"properties": {
"emailAddress": {
"type": "string",
"format": "email"
}
},
}

We see that the schema defines a property emailAddress of type string and format email.

The next part of the JSON specifies any required properties. We want an email address to be a required property of the schema so we indicate that as such:

{
"$id": "https://example.com/schemas/email.json",
"$schema": "https://json-schema.org/draft/2020-12/schema",
"name": "Email Address",
"type": "object",
"properties": {
"emailAddress": {
"type": "string",
"format": "email"
}
},
"required": ["emailAddress"]
}

This means that any piece of JSON we apply this schema to will pass if a valid emailAddress property is present and will fail otherwise.

2. Create Credential Schema​

Now that we have a valid JSON Schema, we'll need to transform it so that it's not just any arbitrary JSON, but can be applied to a Verifiable Credential.

info

Prerequisite​

Follow guide to Clone & Run SSI Service

Signed vs. Unsigned Schemas​

The SSI Service exposes a set of APIs for managing schemas. To create a schema you have two options: signed or unsigned. The signed version of a schema is packaged as a VC. In some cases, it's useful to package a JSON Schema as a VC to retain information about authorship (who created the schema), when it was created, and enable other features the VC Data Model offers, such as the ability to suspend the usage of a schema.

Let's look at the approach for creating both kinds of schemas.

Create Unsigned Schema​

To apply our JSON Schema to a Verifiable Credential, let's add emailAddress in the credentialSubject property then execute a PUT request to /v1/schemas:

curl -X PUT localhost:8080/v1/schemas -d '{
"name": "Email Credential",
"schema": {
"$schema": "https://json-schema.org/draft/2020-12/schema",
"type": "object",
"properties": {
"credentialSubject": {
"type": "object",
"properties": {
"emailAddress": {
"type": "string",
"format": "email"
}
},
"required": ["emailAddress"]
}
}
}
}'

Upon success, you'll see a response which includes the schema you passed in, a service-generated identifier for the schema, and a JsonSchema2023 type:

{
// Schema identifier
"id": "ebeebf7b-d452-4832-b8d3-0042ec80e108",

// Schema type
"type": "JsonSchema2023",

// Schema that was passed into request
"schema": {
"$id": "http://localhost:3000/v1/schemas/ebeebf7b-d452-4832-b8d3-0042ec80e108",
"$schema": "https://json-schema.org/draft/2020-12/schema",
"name": "Email Credential",
"properties": {
"credentialSubject": {
"properties": {
"emailAddress": {
"format": "email",
"type": "string"
}
},
"required": [
"emailAddress"
],
"type": "object"
}
},
"type": "object"
}
}

Create Signed Schema​

Signed schemas are packaged as VCs themselves, and therefore require a few additional properties. At minimum, we'd need:

  • issuer - The DID of the VC issuer
  • verificationMethodId - The ID of the verification method
curl -X PUT localhost:8080/v1/schemas -d '{
"name": "Email Credential",
"issuer": "did:key:z6MkjePG6UBCLbrgUQgURoTSuXAbRpDbCdTLEPUXDqUC4EFw",
"verificationMethodId": "did:key:z6MkjePG6UBCLbrgUQgURoTSuXAbRpDbCdTLEPUXDqUC4EFw#z6MkjePG6UBCLbrgUQgURoTSuXAbRpDbCdTLEPUXDqUC4EFw",
"schema": {
"$schema": "https://json-schema.org/draft/2020-12/schema",
"type": "object",
"properties": {
"credentialSubject": {
"type": "object",
"properties": {
"emailAddress": {
"type": "string",
"format": "email"
}
},
"required": ["emailAddress"]
}
}
}
}'

Signed VC schemas are created the same way unsigned ones are - by executing a PUT request to v1/schemas.

Connect with us on Discord

Submit feedback: Open a GitHub issue

Edit this page: GitHub Repo

Contribute: Contributing Guide