diff --git a/docs/classes/_category_.yml b/docs/classes/_category_.yml deleted file mode 100644 index cb44a08e..00000000 --- a/docs/classes/_category_.yml +++ /dev/null @@ -1,3 +0,0 @@ -label: 'Classes' -collapsed: true -position: 5 diff --git a/docs/classes/ERC725.md b/docs/methods.md similarity index 70% rename from docs/classes/ERC725.md rename to docs/methods.md index 13115ba5..a33d6efe 100644 --- a/docs/classes/ERC725.md +++ b/docs/methods.md @@ -1,984 +1,969 @@ --- sidebar_position: 1 +title: 'Methods' --- -# ERC725 +## Encoding -## checkPermissions +### encodeData ```js -myErc725.checkPermissions(requiredPermissions, grantedPermissions); +myErc725.encodeData(data [, schemas]); ``` ```js -ERC725.checkPermissions(requiredPermissions, grantedPermissions); +ERC725.encodeData(data, schemas); ``` -Check if the required permissions are included in the granted permissions as defined by the [LSP6 KeyManager Standard](https://docs.lukso.tech/standards/universal-profile/lsp6-key-manager). +Encode the data of a smart contract according to your `ERC725JSONSchema` so that you can store the information in smart contracts. -:::info +:::tip -`checkPermissions` is available as either a static or non-static method, so it can be called without instantiating an ERC725 object. +When encoding JSON, it is possible to pass in the JSON object and the URL where it is available publicly. The JSON will be hashed with `keccak256`. ::: -#### Parameters - -##### 1. `requiredPermissions` - String[] | String - -An array of required permissions or a single required permission. (32bytes hex or the official name of the permission). - -##### 2. `grantedPermissions` - String +:::info -The granted permissions. (32bytes hex). +When encoding some values using specific `string` or `bytesN` as `valueType`, if the data passed is a non-hex value, _erc725.js_ will convert the value +to its utf8-hex representation for you. For instance: -#### Returns +- If `valueType` is `string` and you provide a `number` as input. -| Type | Description | -| :------ | :----------------------------------------------------------------------------------------------------------------------------------------------- | -| boolean | A boolean value indicating whether the required permissions are included in the granted permissions as defined by the [LSP6 KeyManager Standard] | +_Example: input `42` --> will encode as `0x3432` (utf-8 hex code for `4` = `0x34`, for `2` = `0x32`)._ -#### Permission-Name Example +- If `valueType` is `bytes32` or `bytes4`, it will convert as follow: -```javascript title="Checking permissions by name" -const requiredPermissions = 'CHANGEOWNER'; -const grantedPermissions = - '0x000000000000000000000000000000000000000000000000000000000000ff51'; -ERC725.checkPermissions(requiredPermissions, grantedPermissions); -// true +_Example 1: input `week` encoded as `bytes4` --> will encode as `0x7765656b`._ -// This method is also available on the instance: +_Example 2: input `1122334455` encoded as `bytes4` --> will encode as `0x42e576f7`._ -const requiredPermissions = ['CHANGEOWNER', 'CALL']; -const grantedPermissions = - '0x0000000000000000000000000000000000000000000000000000000000000051'; -myErc725.checkPermissions(requiredPermissions, grantedPermissions); -// false -``` +::: -#### 32bytes hex Example +#### Parameters -```javascript title="Checking permissions by 32bytes hex" -const requiredPermissions = [ - '0x0000000000000000000000000000000000000000000000000000000000000001', - '0x0000000000000000000000000000000000000000000000000000000000000800', -]; -const grantedPermissions = - '0x0000000000000000000000000000000000000000000000000000000000000051'; +##### 1. `data` - Array of Objects -ERC725.checkPermissions(requiredPermissions, grantedPermissions); -// false +An array of objects containing the following properties: -// This method is also available on the instance: +| Name | Type | Description | +| :---------------------------- | :---------------------------------------- | :--------------------------------------------------------------------------------------------------------------------------------------------------------------- | +| `keyName` | string | Can be either the named key (i.e. `LSP3Profile`, `LSP12IssuedAssetsMap:
`) or the hashed key (with or without `0x` prefix, i.e. `0x5ef...` or `5ef...`). | +| `dynamicKeyParts` (optional) | string or
string[ ] | The dynamic parts of the `keyName` that will be used for encoding the key. | +| `value` | string or
string[ ]
JSON | The value that should be encoded. Can be a string, an array of string or a JSON... | +| `startingIndex` (optional) | number | Starting index for `Array` types to encode a subset of elements. Defaults to `0`. | +| `totalArrayLength` (optional) | number | Parameter for `Array` types, specifying the total length when encoding a subset of elements. Defaults to the number of elements in the `value` field. | -const requiredPermissions = - '0x0000000000000000000000000000000000000000000000000000000000000001'; -const grantedPermissions = - '0x0000000000000000000000000000000000000000000000000000000000000051'; +The `keyName` also supports dynamic keys for [`Mapping`](https://github.com/lukso-network/LIPs/blob/main/LSPs/LSP-2-ERC725YJSONSchema.md#mapping) and [`MappingWithGrouping`](https://github.com/lukso-network/LIPs/blob/main/LSPs/LSP-2-ERC725YJSONSchema.md#mapping). Therefore, you can use variables in the key name such as `LSP12IssuedAssetsMap:
`. In that case, the value should also set the `dynamicKeyParts` property: -myErc725.checkPermissions(requiredPermissions, grantedPermissions); -// true -``` +- `dynamicKeyParts`: string or string[ ] which holds the variables that needs to be encoded. ---- +:::info Handling keyType `Array`. -## decodeData +If the keyType is Array and you pass an integer as a value it will encode only the data key for the Array length. See the example below. -```js -myErc725.decodeData(data [, schemas]); -``` +Additionally, the `totalArrayLength` parameter must be explicitly provided to ensure integrity when encoding subsets or modifying existing array elements. Its value specifies the total length of the array **after the operation is completed**, not just the size of the encoded subset. -```js -ERC725.decodeData(data, schemas); -``` +**When to use `totalArrayLength`** -If you are reading the key-value store from an ERC725 smart contract you can use the `decodeData` function to do the decoding for you. +- **Adding Elements:** When adding new elements to an array, `totalArrayLength` should equal the sum of the current array's length plus the number of new elements added. +- **Modifying Elements:** If modifying elements within an existing array without changing the total number of elements, `totalArrayLength` should match the previous length of the array. +- **Removing Elements:** In cases where elements are removed, `totalArrayLength` should reflect the number of elements left. -:::tip -If you want total convenience, it is recommended to use the [`fetchData`](ERC725.md#fetchdata) function, which automatically `decodes` and `fetches` external references. ::: -#### Parameters - -##### 1. `data` - Object or array of Objects - -An object or array of objects containing the following properties: - -| Name | Type | Description | -| :--------------------------- | :----------------------------- | :--------------------------------------------------------------------------------------------------------------------------------------------------------------- | -| `keyName` | string | Can be either the named key (i.e. `LSP3Profile`, `LSP12IssuedAssetsMap:
`) or the hashed key (with or without `0x` prefix, i.e. `0x5ef...` or `5ef...`). | -| `dynamicKeyParts` (optional) | string or
string[ ] | If `keyName` is a dynamic key, the dynamic parts of the `keyName` that will be used for encoding the key. | -| `value` | string or
string[ ] | The value that should be decoded. Can be a string, an array of string, or a JSON. | +:::caution Encoding array lengths -The `keyName` also supports dynamic keys for [`Mapping`](https://github.com/lukso-network/LIPs/blob/main/LSPs/LSP-2-ERC725YJSONSchema.md#mapping) and [`MappingWithGrouping`](https://github.com/lukso-network/LIPs/blob/main/LSPs/LSP-2-ERC725YJSONSchema.md#mapping). Therefore, you can use variables in the key name such as `LSP12IssuedAssetsMap:
`. In that case, the value should also set the `dynamicKeyParts` property: +Please be careful when updating existing contract data. Incorrect usage of `startingIndex` and `totalArrayLength` can lead to improperly encoded data that changes the intended structure of the data field. -- `dynamicKeyParts`: string or string[ ] which holds the variables that needs to be encoded. +::: ##### 2. `schemas` - Array of Objects (optional) -An array of extra [LSP-2 ERC725YJSONSchema] objects that can be used to find the schema. If called on an instance, the parameter is optional and will be concatenated with the schema provided on instantiation. +An array of extra [LSP-2 ERC725YJSONSchema] objects that can be used to find the schema. If called on an instance, it is optional and it will be concatenated with the schema provided on instantiation. #### Returns -| Name | Type | Description | -| :------------ | :-------------- | :----------------------------------------------------------------- | -| `decodedData` | Object or Array | The decoded data as defined and expected in the following schemas. | +| Name | Type | Description | +| :------------ | :----- | :--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | +| `encodedData` | Object | An object containing the encoded keys and values according to the [LSP2 ERC725Y JSON Schema](https://github.com/lukso-network/LIPs/blob/main/LSPs/LSP-2-ERC725YJSONSchema.md) of the data which was passed | -:::info +After the `data` is encoded, the object is ready to be stored in smart contracts. -- If the input is an array of objects, the values will be returned in an array. -- If the input is a single object, the output will be the decodedData object directly. +#### Examples -::: +
+ Encode a VerifiableURI with JSON and uploaded URL -### Single-Key Example +```javascript title="Encode a VerifiableURI with JSON and uploaded URL" +import ERC725 from '@erc725/erc725.js'; -```javascript title="Decoding an object with one key" -myErc725.decodeData([ +const schemas = [ + { + name: 'LSP3Profile', + key: '0x5ef83ad9559033e6e941db7d7c495acdce616347d28e90c7ce47cbfcfcad3bc5', + keyType: 'Singleton', + valueType: 'bytes', + valueContent: 'VerifiableURI', + }, +]; + +const myErc725 = new ERC725(schemas); + +myErc725.encodeData([ { keyName: 'LSP3Profile', - value: - '0x6f357c6a820464ddfac1bec070cc14a8daf04129871d458f2ca94368aae8391311af6361696670733a2f2f516d597231564a4c776572673670456f73636468564775676f3339706136727963455a4c6a7452504466573834554178', + value: { + json: profileJson, + url: 'ipfs://QmQTqheBLZFnQUxu5RDs8tA9JtkxfZqMBcmGd9sukXxwRm', + }, }, ]); /** -[ +{ + keys: ['0x5ef83ad9559033e6e941db7d7c495acdce616347d28e90c7ce47cbfcfcad3bc5'], + values: ['0x6f357c6a2404a2866f05e53e141eb61382a045e53c2fc54831daca9d9e1e039a11f739e1696670733a2f2f516d5154716865424c5a466e5155787535524473387441394a746b78665a714d42636d47643973756b587877526d'], +} +*/ + +// You can also use the hashed key (with or without 0x prefix) +myErc725.encodeData([ { - name: 'LSP3Profile', - key: '0x5ef83ad9559033e6e941db7d7c495acdce616347d28e90c7ce47cbfcfcad3bc5', + keyName: + '0x5ef83ad9559033e6e941db7d7c495acdce616347d28e90c7ce47cbfcfcad3bc5', value: { - verification: { - method: 'keccak256(utf8)', - data: '0x820464ddfac1bec070cc14a8daf04129871d458f2ca94368aae8391311af6361' - }, - url: 'ipfs://QmYr1VJLwerg6pEoscdhVGugo39pa6rycEZLjtRPDfW84UAx', + json: profileJson, + url: 'ipfs://QmQTqheBLZFnQUxu5RDs8tA9JtkxfZqMBcmGd9sukXxwRm', }, }, -] -*/ - -myErc725.decodeData({ - keyName: 'LSP3Profile', - value: - '0x6f357c6a820464ddfac1bec070cc14a8daf04129871d458f2ca94368aae8391311af6361696670733a2f2f516d597231564a4c776572673670456f73636468564775676f3339706136727963455a4c6a7452504466573834554178', -}); +]); /** { - name: 'LSP3Profile', - key: '0x5ef83ad9559033e6e941db7d7c495acdce616347d28e90c7ce47cbfcfcad3bc5', - value: { - verification: { - method: 'keccak256(utf8)', - data: '0x820464ddfac1bec070cc14a8daf04129871d458f2ca94368aae8391311af6361' + keys: ['0x5ef83ad9559033e6e941db7d7c495acdce616347d28e90c7ce47cbfcfcad3bc5'], + values: ['0x6f357c6a2404a2866f05e53e141eb61382a045e53c2fc54831daca9d9e1e039a11f739e1696670733a2f2f516d5154716865424c5a466e5155787535524473387441394a746b78665a714d42636d47643973756b587877526d'], +} +*/ + +myErc725.encodeData([ + { + keyName: + '0x5ef83ad9559033e6e941db7d7c495acdce616347d28e90c7ce47cbfcfcad3bc5', + value: { + json: profileJson, + url: 'ipfs://QmQTqheBLZFnQUxu5RDs8tA9JtkxfZqMBcmGd9sukXxwRm', }, - url: 'ipfs://QmYr1VJLwerg6pEoscdhVGugo39pa6rycEZLjtRPDfW84UAx', }, +]); +/** +{ + keys: ['0x5ef83ad9559033e6e941db7d7c495acdce616347d28e90c7ce47cbfcfcad3bc5'], + values: ['0x6f357c6a2404a2866f05e53e141eb61382a045e53c2fc54831daca9d9e1e039a11f739e1696670733a2f2f516d5154716865424c5a466e5155787535524473387441394a746b78665a714d42636d47643973756b587877526d'], } */ ``` -### Multi-Key Example +```javascript title="encode a Singleton data key of valueContent Address" +import ERC725 from '@erc725/erc725.js'; -```javascript title="Decoding an object with multiple keys" -myErc725.decodeData([ +const schemas = [ { - keyName: 'LSP3Profile', - value: - '0x6f357c6a820464ddfac1bec070cc14a8daf04129871d458f2ca94368aae8391311af6361696670733a2f2f516d597231564a4c776572673670456f73636468564775676f3339706136727963455a4c6a7452504466573834554178', + name: 'LSP1UniversalReceiverDelegate', + key: '0x0cfc51aec37c55a4d0b1a65c6255c4bf2fbdf6277f3cc0730c45b828b6db8b47', + keyType: 'Singleton', + valueType: 'address', + valueContent: 'Address', }, +]; + +const myErc725 = new ERC725(schemas); + +myErc725.encodeData([ { - keyName: 'LSP12IssuedAssets[]', - value: [ - { - key: '0x7c8c3416d6cda87cd42c71ea1843df28ac4850354f988d55ee2eaa47b6dc05cd', - value: '0x00000000000000000000000000000002', - }, - { - key: '0x7c8c3416d6cda87cd42c71ea1843df2800000000000000000000000000000000', - value: '0xd94353d9b005b3c0a9da169b768a31c57844e490', - }, - { - key: '0x7c8c3416d6cda87cd42c71ea1843df2800000000000000000000000000000001', - value: '0xdaea594e385fc724449e3118b2db7e86dfba1826', - }, - ], + keyName: 'LSP1UniversalReceiverDelegate', + value: '0x1183790f29BE3cDfD0A102862fEA1a4a30b3AdAb', }, ]); /** -[ +{ + keys: ['0x0cfc51aec37c55a4d0b1a65c6255c4bf2fbdf6277f3cc0730c45b828b6db8b47'], + values: ['0x1183790f29be3cdfd0a102862fea1a4a30b3adab'], +} +*/ +``` + +
+ +
+ Encode a VerifiableURI with hash function, hash and uploaded URL + +```javascript title="Encode a VerifiableURI with hash function, hash and uploaded URL" +import ERC725 from '@erc725/erc725.js'; + +const schemas = [ { name: 'LSP3Profile', key: '0x5ef83ad9559033e6e941db7d7c495acdce616347d28e90c7ce47cbfcfcad3bc5', + keyType: 'Singleton', + valueType: 'bytes', + valueContent: 'VerifiableURI', + }, +]; + +const myErc725 = new ERC725(schemas); + +myErc725.encodeData([ + { + keyName: 'LSP3Profile', value: { verification: { + method: 'keccak256(utf8)', data: '0x820464ddfac1bec070cc14a8daf04129871d458f2ca94368aae8391311af6361', - method: 'keccak256(utf8)' }, url: 'ipfs://QmYr1VJLwerg6pEoscdhVGugo39pa6rycEZLjtRPDfW84UAx', }, }, - { - name: 'LSP12IssuedAssets[]', - key: '0x7c8c3416d6cda87cd42c71ea1843df28ac4850354f988d55ee2eaa47b6dc05cd', - value: [ - '0xD94353D9B005B3c0A9Da169b768a31C57844e490', - '0xDaea594E385Fc724449E3118B2Db7E86dFBa1826', - ], - }, -]; +]); +/** +{ + keys: ['0x5ef83ad9559033e6e941db7d7c495acdce616347d28e90c7ce47cbfcfcad3bc5'], + values: ['0x6f357c6a820464ddfac1bec070cc14a8daf04129871d458f2ca94368aae8391311af6361696670733a2f2f516d597231564a4c776572673670456f73636468564775676f3339706136727963455a4c6a7452504466573834554178'], +} */ ``` -### Dynamic-Key Example +
+ +
+ Encode dynamic keys + +```javascript title="Encode dynamic keys" +import ERC725 from '@erc725/erc725.js'; -```javascript title="Decoding an object with dynamic key and a custom schema" const schemas = [ { - name: 'MyKeyName::', - key: '0x...', - keyType: 'Singleton', + name: 'DynamicKey:
', + key: '0x0fb367364e1852abc5f20000
', + keyType: 'Mapping', valueType: 'bytes', - valueContent: 'VerifiableURI', + valueContent: 'Address', }, ]; -myErc725.decodeData( +myErc725.encodeData( [ { - keyName: 'MyKeyName::', - dynamicKeyParts: [ - '0xaaaabbbbccccddddeeeeffff111122223333444455556666777788889999aaaa', - 'true', - ], - value: - '0x00006f357c6a0020820464ddfac1bec070cc14a8daf04129871d458f2ca94368aae8391311af6361696670733a2f2f516d597231564a4c776572673670456f73636468564775676f3339706136727963455a4c6a7452504466573834554178', + keyName: 'DynamicKey:
', + dynamicKeyParts: ['0xbedbedbedbedbedbedbedbedbedbedbedbedbedb'], + value: '0xcafecafecafecafecafecafecafecafecafecafe', }, ], schemas, ); /** -[ +{ + keys: ['0x0fb367364e1852abc5f20000bedbedbedbedbedbedbedbedbedbedbedbedbedb'], + values: ['0xcafecafecafecafecafecafecafecafecafecafe] +} +*/ + +const schemas = [ { - name: 'MyKeyName:aaaabbbbccccddddeeeeffff111122223333444455556666777788889999aaaa:true', - key: '0x35e6950bc8d2aaaabbbb00000000000000000000000000000000000000000001', - value: { - verification: { - method: 'keccak256(utf8)', - data: '0x820464ddfac1bec070cc14a8daf04129871d458f2ca94368aae8391311af6361' - }, - url: 'ifps://QmYr1VJLwerg6pEoscdhVGugo39pa6rycEZLjtRPDfW84UAx', - }, + name: 'DynamicKey::', + key: '0xForDynamicKeysThisFieldIsIrrelevantAndWillBeOverwriten', + keyType: 'Mapping', + valueType: 'bytes', + valueContent: 'Address', }, ]; + +myErc725.encodeData( + [ + { + keyName: 'DynamicKey::', + dynamicKeyParts: ['0x11223344', 'Summer'], + value: '0xcafecafecafecafecafecafecafecafecafecafe', + }, + ], + schemas, +); +/** +{ + keys: ['0x0fb367364e1852abc5f2000078c964cd805233eb39f2db152340079088809725'], + values: ['0xcafecafecafecafecafecafecafecafecafecafe'] +} */ ``` ---- - -## decodePermissions - -```js -ERC725.decodePermissions(permission); -``` +
-Decodes permissions from hexadecimal defined by the [LSP6 KeyManager Standard](https://docs.lukso.tech/standards/universal-profile/lsp6-key-manager). +
+ Encode multiple data keys at once -:::info +```javascript title="Encode multiple keys at once" +import ERC725 from '@erc725/erc725.js'; -`decodePermissions` is available as either a static or non-static method, so it can be called without instantiating an ERC725 object. +const schemas = [ + { + name: 'LSP3Profile', + key: '0x5ef83ad9559033e6e941db7d7c495acdce616347d28e90c7ce47cbfcfcad3bc5', + keyType: 'Singleton', + valueType: 'bytes', + valueContent: 'VerifiableURI', + }, + { + name: 'LSP1UniversalReceiverDelegate', + key: '0x0cfc51aec37c55a4d0b1a65c6255c4bf2fbdf6277f3cc0730c45b828b6db8b47', + keyType: 'Singleton', + valueType: 'address', + valueContent: 'Address', + }, + { + name: 'LSP12IssuedAssets[]', + key: '0x7c8c3416d6cda87cd42c71ea1843df28ac4850354f988d55ee2eaa47b6dc05cd', + keyType: 'Array', + valueType: 'address', + valueContent: 'Address', + }, +]; -::: +const myErc725 = new ERC725(schemas); -#### Parameters +myErc725.encodeData([ + { + keyName: 'LSP3Profile', + value: { + verification: { + method: 'keccak256(utf8)', + data: '0x820464ddfac1bec070cc14a8daf04129871d458f2ca94368aae8391311af6361', + }, + url: 'ipfs://QmYr1VJLwerg6pEoscdhVGugo39pa6rycEZLjtRPDfW84UAx', + }, + }, + { + keyName: 'LSP1UniversalReceiverDelegate', + value: '0x1183790f29BE3cDfD0A102862fEA1a4a30b3AdAb', + }, + { + keyName: 'LSP12IssuedAssets[]', + value: [ + '0xD94353D9B005B3c0A9Da169b768a31C57844e490', + '0xDaea594E385Fc724449E3118B2Db7E86dFBa1826', + ], + }, +]); +/** +{ + keys: [ + '0x5ef83ad9559033e6e941db7d7c495acdce616347d28e90c7ce47cbfcfcad3bc5', // LSP3Profile -> data key + '0x0cfc51aec37c55a4d0b1a65c6255c4bf2fbdf6277f3cc0730c45b828b6db8b47', // LSP1UniversalReceiverDelegate -> data key + '0x7c8c3416d6cda87cd42c71ea1843df28ac4850354f988d55ee2eaa47b6dc05cd', // LSP12IssuedAssets[] -> data key for `LSP12IssuedAssets[].length` + '0x7c8c3416d6cda87cd42c71ea1843df2800000000000000000000000000000000', // LSP12IssuedAssets[0] -> data key for index 0 + '0x7c8c3416d6cda87cd42c71ea1843df2800000000000000000000000000000001', // LSP12IssuedAssets[1] -> data key for index 1 + ], + values: [ + '0x6f357c6a820464ddfac1bec070cc14a8daf04129871d458f2ca94368aae8391311af6361696670733a2f2f516d597231564a4c776572673670456f73636468564775676f3339706136727963455 a4c6a7452504466573834554178', // LSP3Profile -> value as VerifiableURI + '0x1183790f29be3cdfd0a102862fea1a4a30b3adab', // LSP1UniversalReceiverDelegate -> value as Address + '0x00000000000000000000000000000002', // LSP12IssuedAssets[].length = 2 + '0xd94353d9b005b3c0a9da169b768a31c57844e490', // LSP12IssuedAssets[0] -> Address stored at index 0 + '0xdaea594e385fc724449e3118b2db7e86dfba1826', // LSP12IssuedAssets[1] -> Address stored at index 1 + ], +} +*/ +``` -##### 1. `permission` - String +
-The encoded permission (32bytes hex). +
+ Encode array length only -#### Returns +```javascript title="Encode the length of an array" +import ERC725 from '@erc725/erc725.js'; -| Name | Type | Description | -| :------------------- | :----- | :------------------------------------------------------------------------------------------------- | -| `decodedPermissions` | Object | An object specifying whether default LSP6 permissions are included in provided hexademical string. | +const schemas = [ + { + name: 'LSP12IssuedAssets[]', + key: '0x7c8c3416d6cda87cd42c71ea1843df28ac4850354f988d55ee2eaa47b6dc05cd', + keyType: 'Array', + valueType: 'address', + valueContent: 'Address', + }, +]; -#### Example +const myErc725 = new ERC725(schemas); -```javascript title="Decoding permissions" -ERC725.decodePermissions('0x0000000000000000000000000000000000000000000000000000000000000110'), +myErc725.encodeData([ + { + keyName: 'LSP12IssuedAssets[]', + value: 5, + }, +]); /** { - CHANGEOWNER: false, - EDITPERMISSIONS: false, - ADDCONTROLLER: false, - SETDATA: false, - CALL: true, - STATICCALL: false, - DELEGATECALL: false, - DEPLOY: false, - TRANSFERVALUE: true, - SIGN: false, + keys: [ + '0x7c8c3416d6cda87cd42c71ea1843df28ac4850354f988d55ee2eaa47b6dc05cd', + ], + values: ['0x00000000000000000000000000000005'], } */ +``` -ERC725.decodePermissions('0x000000000000000000000000000000000000000000000000000000000000000a'), +
+ +
+ Encode a subset of array elements + +```javascript title="Encode a subset of array elements" +import ERC725 from '@erc725/erc725.js'; + +const schemas = [ + { + name: 'AddressPermissions[]', + key: '0xdf30dba06db6a30e65354d9a64c609861f089545ca58c6b4dbe31a5f338cb0e3', + keyType: 'Array', + valueType: 'address', + valueContent: 'Address', + }, +]; + +const myErc725 = new ERC725(schemas); + +myErc725.encodeData( + [ + { + keyName: 'AddressPermissions[]', + value: [ + '0x983abc616f2442bab7a917e6bb8660df8b01f3bf', + '0x56ecbc104136d00eb37aa0dce60e075f10292d81', + ], + totalArrayLength: 23, + startingIndex: 21, + }, + ], + schemas, +); /** { - CHANGEOWNER: false, - EDITPERMISSIONS: true, - ADDCONTROLLER: false, - SETDATA: true, - CALL: false, - STATICCALL: false, - DELEGATECALL: false, - DEPLOY: false, - TRANSFERVALUE: false, - SIGN: false, + keys: [ + '0xdf30dba06db6a30e65354d9a64c609861f089545ca58c6b4dbe31a5f338cb0e3', // LSP12IssuedAssets[] -> data key for `LSP12IssuedAssets[].length` + '0xdf30dba06db6a30e65354d9a64c6098600000000000000000000000000000015', // LSP12IssuedAssets[21] -> data key for index 21 + '0xdf30dba06db6a30e65354d9a64c6098600000000000000000000000000000016', // LSP12IssuedAssets[22] -> data key for index 22 + ], + values: [ + '0x00000000000000000000000000000017', // LSP12IssuedAssets[].length = 23 + '0x983abc616f2442bab7a917e6bb8660df8b01f3bf', // LSP12IssuedAssets[21] -> Address stored at index 21 + '0x56ecbc104136d00eb37aa0dce60e075f10292d81', // LSP12IssuedAssets[22] -> Address stored at index 22 + ], } */ - -// This method is also available on the instance: -myErc725.decodePermissions('0x0000000000000000000000000000000000000000000000000000000000000110'), ``` +
+ --- -## decodeValueType +### encodeKeyName ```js -myErc725.decodeValueType(type, data); +ERC725.encodeKeyName(keyName [, dynamicKeyParts]); ``` -```js -ERC725.decodeValueType(type, data); -``` +Hashes a key name for use on an [ERC725Y contract](https://github.com/ethereum/EIPs/blob/master/EIPS/eip-725.md#erc725y) according to the [LSP2 ERC725Y JSON Schema Standard](https://github.com/lukso-network/LIPs/blob/main/LSPs/LSP-2-ERC725YJSONSchema.md). -Decode some data according to a provided value type. +:::info -#### Parameters +`encodeKeyName` is available as either a static or non-static method so can be called without instantiating an ERC725 object. -| Name | Type | Description | -| :----- | :----- | :---------------------------------------------------------------------------- | -| `type` | string | The value type to decode the data (i.e. `uint256`, `bool`, `bytes4`, etc...). | -| `data` | string | A hex encoded string starting with `0x` to decode | +::: -#### Returns +#### Parameters -| Name | Type | Description | -| :------------- | :--------------------- | :----------------------------------- | -| `decodedValue` | string or
number | A value decoded according to `type`. | +##### 1. `keyName` - String -#### Examples +The key name you want to encode, for instance: `LSP3Profile`. -```javascript -myErc725.decodeValueType('uint128', '0x0000000000000000000000000000000a'); -// 10 +##### 2. `dynamicKeyParts` - String or array of Strings (optional) -myErc725.decodeValueType('bool', '0x01'); -// true +The variables used to encode the key name, if the key name is a dynamic (i.e.: `MyKey:
`...) -myErc725.decodeValueType('string', '0x48656c6c6f21'); -// 'Hello!'; +#### Returns -// also available for ABI encoded array + CompactBytesArray -myErc725.decodeValueType( - 'uint256[]', - '0x00000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000003000000000000000000000000000000000000000000000000000000000000000a0000000000000000000000000000000000000000000000000000000000000014000000000000000000000000000000000000000000000000000000000000001e', -); -// [ 10, 20, 30 ] +| Name | Type | Description | +| :--------------- | :----- | :------------------------------------------- | +| `encodedKeyName` | string | The keccak256 hash of the provided key name. | -myErc725.decodeValueType( - 'uint256[CompactBytesArray]'', - '0x0020000000000000000000000000000000000000000000000000000000000000000500200000000000000000000000000000000000000000000000000000000000000008' -) -// [ 5, 8 ] -``` +The hash must be retrievable from the ERC725Y contract via the [getData](#getdata) function. -This method is also available as a static method: +#### Example -```js -ERC725.decodeValueType( - 'uint256', - '0x000000000000000000000000000000000000000000000000000000000000002a', +```javascript title="Encode the key name" +import ERC725 from '@erc725/erc725.js'; + +ERC725.encodeKeyName('LSP3Profile'); +// '0x5ef83ad9559033e6e941db7d7c495acdce616347d28e90c7ce47cbfcfcad3bc5' + +ERC725.encodeKeyName('SupportedStandards:LSP3Profile'); +// '0xeafec4d89fa9619884b600005ef83ad9559033e6e941db7d7c495acdce616347' + +ERC725.encodeKeyName( + 'AddressPermissions:Permissions:cafecafecafecafecafecafecafecafecafecafe', ); -// 42 +// '0x4b80742de2bf82acb3630000cafecafecafecafecafecafecafecafecafecafe' + +ERC725.encodeKeyName('MyKeyName:', 'true'); +// '0x35e6950bc8d21a1699e500000000000000000000000000000000000000000001' + +ERC725.encodeKeyName('MyKeyName::', ['ffff', '4081242941']); +// 0x35e6950bc8d20000ffff000000000000000000000000000000000000f342d33d + +ERC725.encodeKeyName('MyKeyName:', ['4081242941']); +// 0x35e6950bc8d21a1699e5000000000000000000000000000000000000f342d33d + +// This method is also available on the instance: +myErc725.encodeKeyName('LSP3Profile'); ``` -## encodeData +--- + +### encodeArrayKey (TBD) + +### encodeValueType ```js -myErc725.encodeData(data [, schemas]); +myErc725.encodeValueType(type, value); ``` ```js -ERC725.encodeData(data, schemas); +ERC725.encodeValueType(type, value); ``` -Encode the data of a smart contract according to your `ERC725JSONSchema` so that you can store the information in smart contracts. +#### Parameters -:::tip +| Name | Type | Description | +| :------ | :--------------------------------------------------------------------------------------------------------- | :----------------------------------------------------------------------------- | +| `type` | string | The value type to encode the value (i.e. `uint256`, `bool`, `bytes4`, etc...). | +| `value` | string or
string[ ] or
number or
number[ ] or
boolean or
boolean[] | The value that should be encoded as `type` | -When encoding JSON, it is possible to pass in the JSON object and the URL where it is available publicly. The JSON will be hashed with `keccak256`. +#### Returns -::: +| Name | Type | Description | +| :----------------- | :----- | :------------------------------------------------------- | +| `encodedValueType` | string | A hex string representing the `value` encoded as `type`. | -:::info +After the `value` is encoded, the hex string can be used to be stored inside the ERC725Y smart contract. -When encoding some values using specific `string` or `bytesN` as `valueType`, if the data passed is a non-hex value, _erc725.js_ will convert the value -to its utf8-hex representation for you. For instance: +#### Examples -- If `valueType` is `string` and you provide a `number` as input. +```javascript +import ERC725 from '@erc725/erc725.js'; -_Example: input `42` --> will encode as `0x3432` (utf-8 hex code for `4` = `0x34`, for `2` = `0x32`)._ +const myErc725 = new ERC725(); -- If `valueType` is `bytes32` or `bytes4`, it will convert as follow: +myErc725.encodeValueType('uint256', 5); +// '0x0000000000000000000000000000000000000000000000000000000000000005' -_Example 1: input `week` encoded as `bytes4` --> will encode as `0x7765656b`._ +myErc725.encodeValueType('bool', true); +// '0x01' -_Example 2: input `1122334455` encoded as `bytes4` --> will encode as `0x42e576f7`._ +// the word `boolean` (Name of the Typescript type) is also available +myErc725.encodeValueType('boolean', true); +// '0x01' -::: +// `bytesN` type will pad on the right if the value contains less than N bytes +myErc725.encodeValueType('bytes4', '0xcafe'); +// '0xcafe0000' +myErc725.encodeValueType('bytes32', '0xcafe'); +// '0xcafe000000000000000000000000000000000000000000000000000000000000' -#### Parameters +// `bytesN` type will throw an error if the value contains more than N bytes +myERC725.encodeValueType('bytes4', '0xcafecafebeef'); +// Error: Can't convert 0xcafecafebeef to bytes4. Too many bytes, expected at most 4 bytes, received 6. -##### 1. `data` - Array of Objects +// Can also be used to encode arrays as `CompactBytesArray` +myERC725.encodeValueType('uint256[CompactBytesArray]', [1, 2, 3]); +// '0x002000000000000000000000000000000000000000000000000000000000000000010020000000000000000000000000000000000000000000000000000000000000000200200000000000000000000000000000000000000000000000000000000000000003' -An array of objects containing the following properties: +myERC725.encodeValueType('bytes[CompactBytesArray]', [ + '0xaaaaaaaa', + '0xbbbbbbbbbbbbbbbbbb', +]); +// '0x0004aaaaaaaa0009bbbbbbbbbbbbbbbbbb' +``` -| Name | Type | Description | -| :---------------------------- | :---------------------------------------- | :--------------------------------------------------------------------------------------------------------------------------------------------------------------- | -| `keyName` | string | Can be either the named key (i.e. `LSP3Profile`, `LSP12IssuedAssetsMap:
`) or the hashed key (with or without `0x` prefix, i.e. `0x5ef...` or `5ef...`). | -| `dynamicKeyParts` (optional) | string or
string[ ] | The dynamic parts of the `keyName` that will be used for encoding the key. | -| `value` | string or
string[ ]
JSON | The value that should be encoded. Can be a string, an array of string, or a JSON. | -| `startingIndex` (optional) | number | Starting index for `Array` types to encode a subset of elements. Defaults to `0`. | -| `totalArrayLength` (optional) | number | Parameter for `Array` types, specifying the total length when encoding a subset of elements. Defaults to the number of elements in the `value` field. | +This method is also available as a static method. -The `keyName` also supports dynamic keys for [`Mapping`](https://github.com/lukso-network/LIPs/blob/main/LSPs/LSP-2-ERC725YJSONSchema.md#mapping) and [`MappingWithGrouping`](https://github.com/lukso-network/LIPs/blob/main/LSPs/LSP-2-ERC725YJSONSchema.md#mapping). Therefore, you can use variables in the key name such as `LSP12IssuedAssetsMap:
`. In that case, the value should also set the `dynamicKeyParts` property: +```javascript +import ERC725 from '@erc725/erc725.js'; -- `dynamicKeyParts`: string or string[ ] which holds the variables that needs to be encoded. +ERC725.encodeValueType('string', 'Hello'); +// '0x48656c6c6f' +``` -:::info Handling array subsets +--- -The `totalArrayLength` parameter must be explicitly provided to ensure integrity when encoding subsets or modifying existing array elements. Its value specifies the total length of the array **after the operation is completed**, not just the size of the encoded subset. +### encodeValueContent (TBD) -**When to Use `totalArrayLength`** +--- -- **Adding Elements:** When adding new elements to an array, `totalArrayLength` should equal the sum of the current array's length plus the number of new elements added. -- **Modifying Elements:** If modifying elements within an existing array without changing the total number of elements, `totalArrayLength` should match the previous length of the array. -- **Removing Elements:** In cases where elements are removed, `totalArrayLength` should reflect the number of elements left. +## Decoding -::: +### decodeData -:::caution Encoding array lengths +```js +myErc725.decodeData(data [, schemas]); +``` -Please be careful when updating existing contract data. Incorrect usage of `startingIndex` and `totalArrayLength` can lead to improperly encoded data that changes the intended structure of the data field. +```js +ERC725.decodeData(data, schemas); +``` +If you are reading the key-value store from an ERC725 smart contract you can use the `decodeData` function to do the decoding for you. + +:::tip +If you want total convenience, it is recommended to use the [`fetchData`](ERC725.md#fetchdata) function, which automatically `decodes` and `fetches` external references. ::: +#### Parameters + +##### 1. `data` - Object or array of Objects + +An object or array of objects containing the following properties: + +| Name | Type | Description | +| :--------------------------- | :----------------------------- | :--------------------------------------------------------------------------------------------------------------------------------------------------------------- | +| `keyName` | string | Can be either the named key (i.e. `LSP3Profile`, `LSP12IssuedAssetsMap:
`) or the hashed key (with or without `0x` prefix, i.e. `0x5ef...` or `5ef...`). | +| `dynamicKeyParts` (optional) | string or
string[ ] | If `keyName` is a dynamic key, the dynamic parts of the `keyName` that will be used for encoding the key. | +| `value` | string or
string[ ] | The value that should be decoded. Can be a string, an array of string, or a JSON. | + +The `keyName` also supports dynamic keys for [`Mapping`](https://github.com/lukso-network/LIPs/blob/main/LSPs/LSP-2-ERC725YJSONSchema.md#mapping) and [`MappingWithGrouping`](https://github.com/lukso-network/LIPs/blob/main/LSPs/LSP-2-ERC725YJSONSchema.md#mapping). Therefore, you can use variables in the key name such as `LSP12IssuedAssetsMap:
`. In that case, the value should also set the `dynamicKeyParts` property: + +- `dynamicKeyParts`: string or string[ ] which holds the variables that needs to be encoded. + ##### 2. `schemas` - Array of Objects (optional) -An array of extra [LSP-2 ERC725YJSONSchema] objects that can be used to find the schema. If called on an instance, it is optional and it will be concatenated with the schema provided on instantiation. +An array of extra [LSP-2 ERC725YJSONSchema] objects that can be used to find the schema. If called on an instance, the parameter is optional and will be concatenated with the schema provided on instantiation. #### Returns -| Name | Type | Description | -| :------------ | :----- | :--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | -| `encodedData` | Object | An object containing the encoded keys and values according to the [LSP2 ERC725Y JSON Schema](https://github.com/lukso-network/LIPs/blob/main/LSPs/LSP-2-ERC725YJSONSchema.md) of the data which was passed | +| Name | Type | Description | +| :------------ | :-------------- | :----------------------------------------------------------------- | +| `decodedData` | Object or Array | The decoded data as defined and expected in the following schemas. | -After the `data` is encoded, the object is ready to be stored in smart contracts. +:::info -#### Examples +- If the input is an array of objects, the values will be returned in an array. +- If the input is a single object, the output will be the decodedData object directly. -
- Encode a VerifiableURI with JSON and uploaded URL +::: -```javascript title="Encode a VerifiableURI with JSON and uploaded URL" -myErc725.encodeData([ +#### Single-Key Example + +```javascript title="Decoding an object with one key" +myErc725.decodeData([ { keyName: 'LSP3Profile', - value: { - json: profileJson, - url: 'ipfs://QmQTqheBLZFnQUxu5RDs8tA9JtkxfZqMBcmGd9sukXxwRm', - }, + value: + '0x6f357c6a820464ddfac1bec070cc14a8daf04129871d458f2ca94368aae8391311af6361696670733a2f2f516d597231564a4c776572673670456f73636468564775676f3339706136727963455a4c6a7452504466573834554178', }, ]); /** -{ - keys: ['0x5ef83ad9559033e6e941db7d7c495acdce616347d28e90c7ce47cbfcfcad3bc5'], - values: ['0x6f357c6a2404a2866f05e53e141eb61382a045e53c2fc54831daca9d9e1e039a11f739e1696670733a2f2f516d5154716865424c5a466e5155787535524473387441394a746b78665a714d42636d47643973756b587877526d'], -} -*/ - -// You can also use the hashed key (with or without 0x prefix) -myErc725.encodeData([ +[ { - keyName: - '0x5ef83ad9559033e6e941db7d7c495acdce616347d28e90c7ce47cbfcfcad3bc5', + name: 'LSP3Profile', + key: '0x5ef83ad9559033e6e941db7d7c495acdce616347d28e90c7ce47cbfcfcad3bc5', value: { - json: profileJson, - url: 'ipfs://QmQTqheBLZFnQUxu5RDs8tA9JtkxfZqMBcmGd9sukXxwRm', + verification: { + method: 'keccak256(utf8)', + data: '0x820464ddfac1bec070cc14a8daf04129871d458f2ca94368aae8391311af6361' + }, + url: 'ipfs://QmYr1VJLwerg6pEoscdhVGugo39pa6rycEZLjtRPDfW84UAx', }, }, -]); -/** -{ - keys: ['0x5ef83ad9559033e6e941db7d7c495acdce616347d28e90c7ce47cbfcfcad3bc5'], - values: ['0x6f357c6a2404a2866f05e53e141eb61382a045e53c2fc54831daca9d9e1e039a11f739e1696670733a2f2f516d5154716865424c5a466e5155787535524473387441394a746b78665a714d42636d47643973756b587877526d'], -} +] */ -myErc725.encodeData([ - { - keyName: '5ef83ad9559033e6e941db7d7c495acdce616347d28e90c7ce47cbfcfcad3bc5', - value: { - json: profileJson, - url: 'ipfs://QmQTqheBLZFnQUxu5RDs8tA9JtkxfZqMBcmGd9sukXxwRm', - }, - }, -]); +myErc725.decodeData({ + keyName: 'LSP3Profile', + value: + '0x6f357c6a820464ddfac1bec070cc14a8daf04129871d458f2ca94368aae8391311af6361696670733a2f2f516d597231564a4c776572673670456f73636468564775676f3339706136727963455a4c6a7452504466573834554178', +}); /** { - keys: ['0x5ef83ad9559033e6e941db7d7c495acdce616347d28e90c7ce47cbfcfcad3bc5'], - values: ['0x6f357c6a2404a2866f05e53e141eb61382a045e53c2fc54831daca9d9e1e039a11f739e1696670733a2f2f516d5154716865424c5a466e5155787535524473387441394a746b78665a714d42636d47643973756b587877526d'], + name: 'LSP3Profile', + key: '0x5ef83ad9559033e6e941db7d7c495acdce616347d28e90c7ce47cbfcfcad3bc5', + value: { + verification: { + method: 'keccak256(utf8)', + data: '0x820464ddfac1bec070cc14a8daf04129871d458f2ca94368aae8391311af6361' + }, + url: 'ipfs://QmYr1VJLwerg6pEoscdhVGugo39pa6rycEZLjtRPDfW84UAx', + }, } */ ``` -```javascript -myErc725.encodeData([ +#### Multi-Key Example + +```javascript title="Decoding an object with multiple keys" +myErc725.decodeData([ { - keyName: 'LSP1UniversalReceiverDelegate', - value: '0x1183790f29BE3cDfD0A102862fEA1a4a30b3AdAb', + keyName: 'LSP3Profile', + value: + '0x6f357c6a820464ddfac1bec070cc14a8daf04129871d458f2ca94368aae8391311af6361696670733a2f2f516d597231564a4c776572673670456f73636468564775676f3339706136727963455a4c6a7452504466573834554178', + }, + { + keyName: 'LSP12IssuedAssets[]', + value: [ + { + key: '0x7c8c3416d6cda87cd42c71ea1843df28ac4850354f988d55ee2eaa47b6dc05cd', + value: '0x00000000000000000000000000000002', + }, + { + key: '0x7c8c3416d6cda87cd42c71ea1843df2800000000000000000000000000000000', + value: '0xd94353d9b005b3c0a9da169b768a31c57844e490', + }, + { + key: '0x7c8c3416d6cda87cd42c71ea1843df2800000000000000000000000000000001', + value: '0xdaea594e385fc724449e3118b2db7e86dfba1826', + }, + ], }, ]); /** -{ - keys: ['0x0cfc51aec37c55a4d0b1a65c6255c4bf2fbdf6277f3cc0730c45b828b6db8b47'], - values: ['0x1183790f29be3cdfd0a102862fea1a4a30b3adab'], -} -*/ -``` - -
- -
- Encode a VerifiableURI with hash function, hash and uploaded URL - -```javascript title="Encode a VerifiableURI with hash function, hash and uploaded URL" -myErc725.encodeData([ +[ { - keyName: 'LSP3Profile', + name: 'LSP3Profile', + key: '0x5ef83ad9559033e6e941db7d7c495acdce616347d28e90c7ce47cbfcfcad3bc5', value: { verification: { - method: 'keccak256(utf8)', data: '0x820464ddfac1bec070cc14a8daf04129871d458f2ca94368aae8391311af6361', + method: 'keccak256(utf8)' }, url: 'ipfs://QmYr1VJLwerg6pEoscdhVGugo39pa6rycEZLjtRPDfW84UAx', }, }, -]); -/** -{ - keys: ['0x5ef83ad9559033e6e941db7d7c495acdce616347d28e90c7ce47cbfcfcad3bc5'], - values: ['0x6f357c6a820464ddfac1bec070cc14a8daf04129871d458f2ca94368aae8391311af6361696670733a2f2f516d597231564a4c776572673670456f73636468564775676f3339706136727963455a4c6a7452504466573834554178'], -} -*/ -``` - -
- -
- Encode dynamic keys - -```javascript title="Encode dynamic keys" -const schemas = [ { - name: 'DynamicKey:
', - key: '0x0fb367364e1852abc5f20000
', - keyType: 'Mapping', - valueType: 'bytes', - valueContent: 'Address', + name: 'LSP12IssuedAssets[]', + key: '0x7c8c3416d6cda87cd42c71ea1843df28ac4850354f988d55ee2eaa47b6dc05cd', + value: [ + '0xD94353D9B005B3c0A9Da169b768a31C57844e490', + '0xDaea594E385Fc724449E3118B2Db7E86dFBa1826', + ], }, ]; - -myErc725.encodeData( - [ - { - keyName: 'DynamicKey:
', - dynamicKeyParts: ['0xbedbedbedbedbedbedbedbedbedbedbedbedbedb'], - value: '0xcafecafecafecafecafecafecafecafecafecafe', - }, - ], - schemas, -); -/** -{ - keys: ['0x0fb367364e1852abc5f20000bedbedbedbedbedbedbedbedbedbedbedbedbedb'], - values: ['0xcafecafecafecafecafecafecafecafecafecafe] -} */ +``` + +#### Dynamic-Key Example +```javascript title="Decoding an object with dynamic key and a custom schema" const schemas = [ { - name: 'DynamicKey::', - key: '0xForDynamicKeysThisFieldIsIrrelevantAndWillBeOverwriten', - keyType: 'Mapping', + name: 'MyKeyName::', + key: '0x...', + keyType: 'Singleton', valueType: 'bytes', - valueContent: 'Address', + valueContent: 'VerifiableURI', }, ]; -myErc725.encodeData( +myErc725.decodeData( [ { - keyName: 'DynamicKey::', - dynamicKeyParts: ['0x11223344', 'Summer'], - value: '0xcafecafecafecafecafecafecafecafecafecafe', + keyName: 'MyKeyName::', + dynamicKeyParts: [ + '0xaaaabbbbccccddddeeeeffff111122223333444455556666777788889999aaaa', + 'true', + ], + value: + '0x00006f357c6a0020820464ddfac1bec070cc14a8daf04129871d458f2ca94368aae8391311af6361696670733a2f2f516d597231564a4c776572673670456f73636468564775676f3339706136727963455a4c6a7452504466573834554178', }, ], schemas, ); /** -{ - keys: ['0x0fb367364e1852abc5f2000078c964cd805233eb39f2db152340079088809725'], - values: ['0xcafecafecafecafecafecafecafecafecafecafe'] -} -*/ -``` - -
- -
- Encode multiple keys at once - -```javascript title="Encode multiple keys at once" -myErc725.encodeData([ +[ { - keyName: 'LSP3Profile', + name: 'MyKeyName:aaaabbbbccccddddeeeeffff111122223333444455556666777788889999aaaa:true', + key: '0x35e6950bc8d2aaaabbbb00000000000000000000000000000000000000000001', value: { verification: { method: 'keccak256(utf8)', - data: '0x820464ddfac1bec070cc14a8daf04129871d458f2ca94368aae8391311af6361', + data: '0x820464ddfac1bec070cc14a8daf04129871d458f2ca94368aae8391311af6361' }, - url: 'ipfs://QmYr1VJLwerg6pEoscdhVGugo39pa6rycEZLjtRPDfW84UAx', + url: 'ifps://QmYr1VJLwerg6pEoscdhVGugo39pa6rycEZLjtRPDfW84UAx', }, }, - { - keyName: 'LSP12IssuedAssets[]', - value: [ - '0xD94353D9B005B3c0A9Da169b768a31C57844e490', - '0xDaea594E385Fc724449E3118B2Db7E86dFBa1826', - ], - }, - { - keyName: 'LSP1UniversalReceiverDelegate', - value: '0x1183790f29BE3cDfD0A102862fEA1a4a30b3AdAb', - }, -]); -/** -{ - keys: [ - '0x5ef83ad9559033e6e941db7d7c495acdce616347d28e90c7ce47cbfcfcad3bc5', - '0x7c8c3416d6cda87cd42c71ea1843df28ac4850354f988d55ee2eaa47b6dc05cd', - '0x7c8c3416d6cda87cd42c71ea1843df2800000000000000000000000000000000', - '0x7c8c3416d6cda87cd42c71ea1843df2800000000000000000000000000000001', - '0x0cfc51aec37c55a4d0b1a65c6255c4bf2fbdf6277f3cc0730c45b828b6db8b47', - ], - values: [ - '0x6f357c6a820464ddfac1bec070cc14a8daf04129871d458f2ca94368aae8391311af6361696670733a2f2f516d597231564a4c776572673670456f73636468564775676f3339706136727963455a4c6a7452504466573834554178', - '0x00000000000000000000000000000002', - '0xd94353d9b005b3c0a9da169b768a31c57844e490', - '0xdaea594e385fc724449e3118b2db7e86dfba1826', - '0x1183790f29be3cdfd0a102862fea1a4a30b3adab', - ], -} +]; */ ``` -
+--- -
- Encode array length +### decodeValueType -If the key is of type Array and you pass an integer as a value (for instance, the array length), it will be encoded accordingly. +```js +myErc725.decodeValueType(type, data); +``` -```javascript title="Encode the length of an array" -myErc725.encodeData([ - { - keyName: 'LSP3IssuedAssets[]', - value: 5, - }, -]); -/** -{ - keys: [ - '0x3a47ab5bd3a594c3a8995f8fa58d0876c96819ca4516bd76100c92462f2f9dc0', - ], - values: ['0x00000000000000000000000000000005'], -} -*/ +```js +ERC725.decodeValueType(type, data); ``` -
+Decode some data according to a provided value type. -
- Encode a subset of array elements +#### Parameters -```javascript title="Encode a subset of array elements" -const schemas = [ - { - name: 'AddressPermissions[]', - key: '0xdf30dba06db6a30e65354d9a64c609861f089545ca58c6b4dbe31a5f338cb0e3', - keyType: 'Array', - valueType: 'address', - valueContent: 'Address', - }, -]; +| Name | Type | Description | +| :----- | :----- | :---------------------------------------------------------------------------- | +| `type` | string | The value type to decode the data (i.e. `uint256`, `bool`, `bytes4`, etc...). | +| `data` | string | A hex encoded string starting with `0x` to decode | -myErc725.encodeData( - [ - { - keyName: 'AddressPermissions[]', - value: [ - '0x983abc616f2442bab7a917e6bb8660df8b01f3bf', - '0x56ecbc104136d00eb37aa0dce60e075f10292d81', - ], - totalArrayLength: 23, - startingIndex: 21, - }, - ], - schemas, +#### Returns + +| Name | Type | Description | +| :------------- | :--------------------- | :----------------------------------- | +| `decodedValue` | string or
number | A value decoded according to `type`. | + +#### Examples + +```javascript +myErc725.decodeValueType('uint128', '0x0000000000000000000000000000000a'); +// 10 + +myErc725.decodeValueType('bool', '0x01'); +// true + +myErc725.decodeValueType('string', '0x48656c6c6f21'); +// 'Hello!'; + +// also available for ABI encoded array + CompactBytesArray +myErc725.decodeValueType( + 'uint256[]', + '0x00000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000003000000000000000000000000000000000000000000000000000000000000000a0000000000000000000000000000000000000000000000000000000000000014000000000000000000000000000000000000000000000000000000000000001e', ); -/** -{ - keys: [ - '0xdf30dba06db6a30e65354d9a64c609861f089545ca58c6b4dbe31a5f338cb0e3', - '0xdf30dba06db6a30e65354d9a64c6098600000000000000000000000000000015', - '0xdf30dba06db6a30e65354d9a64c6098600000000000000000000000000000016', - ], - values: [ - '0x00000000000000000000000000000017', - '0x983abc616f2442bab7a917e6bb8660df8b01f3bf', - '0x56ecbc104136d00eb37aa0dce60e075f10292d81', - ], -} -*/ +// [ 10, 20, 30 ] + +myErc725.decodeValueType( + 'uint256[CompactBytesArray]'', + '0x0020000000000000000000000000000000000000000000000000000000000000000500200000000000000000000000000000000000000000000000000000000000000008' +) +// [ 5, 8 ] ``` -
+This method is also available as a static method: + +```js +ERC725.decodeValueType( + 'uint256', + '0x000000000000000000000000000000000000000000000000000000000000002a', +); +// 42 +``` --- -## encodePermissions +### decodeValueContent ```js -ERC725.encodePermissions(permissions); +const erc725js = new ERC725(); + +erc725js.decodeValueContent(valueContent, value); ``` -Encodes permissions into a hexadecimal string as defined by the [LSP6 KeyManager Standard](https://docs.lukso.tech/standards/universal-profile/lsp6-key-manager). +OR -:::info +```js +ERC725.decodeValueContent(valueContent, value); +``` -`encodePermissions` is available as either a static or non-static method, so it can be called without instantiating an ERC725 object. +OR -::: +```js +import { decodeValueContent } from '@erc725/erc725.js'; -#### Parameters - -##### 1. `permissions` - Object - -An object with [LSP6 KeyManager Permissions] as keys and a `boolean` as value. Any omitted permissions will default to `false`. - -#### Returns - -| Type | Description | -| :----- | :---------------------------------------------------------------------------------------- | -| string | The permissions encoded as a hexadecimal string defined by the [LSP6 KeyManager Standard] | - -#### Example - -```javascript title="Encoding permissions" -ERC725.encodePermissions({ - CHANGEOWNER: false, - ADDCONTROLLER: false, - EDITPERMISSIONS: false, - ADDEXTENSIONS: false, - CHANGEEXTENSIONS: true, - ADDUNIVERSALRECEIVERDELEGATE: false, - CHANGEUNIVERSALRECEIVERDELEGATE: false, - REENTRANCY: false, - SUPER_TRANSFERVALUE: true, - TRANSFERVALUE: true, - SUPER_CALL: false, - CALL: true, - SUPER_STATICCALL: false, - STATICCALL: false, - SUPER_DELEGATECALL: false, - DELEGATECALL: false, - DEPLOY: false, - SUPER_SETDATA: false, - SETDATA: false, - ENCRYPT: false, - DECRYPT: false, - SIGN: false, - EXECUTE_RELAY_CALL: false, - ERC4337_PERMISSION: false -}), -// '0x0000000000000000000000000000000000000000000000000000000000000110' - -// Any omitted Permissions will default to false -ERC725.encodePermissions({ - ADDCONTROLLER: true, - ADDEXTENSIONS: true, -}), -// '0x000000000000000000000000000000000000000000000000000000000000000a' -ERC725.encodePermissions({ - EDITPERMISSIONS: true, - CHANGEEXTENSIONS: true, - CHANGEUNIVERSALRECEIVERDELEGATE: true, - SETDATA: true, -}), -// '0x0000000000000000000000000000000000000000000000000000000000040054' - - -// This method is also available on the instance: -myErc725.encodePermissions({ - EDITPERMISSIONS: true, - SETDATA: true, -}), -``` - ---- - -## encodeValueType - -```js -myErc725.encodeValueType(type, value); -``` - -```js -ERC725.encodeValueType(type, value); -``` - -#### Parameters - -| Name | Type | Description | -| :------ | :--------------------------------------------------------------------------------------------------------- | :----------------------------------------------------------------------------- | -| `type` | string | The value type to encode the value (i.e. `uint256`, `bool`, `bytes4`, etc...). | -| `value` | string or
string[ ] or
number or
number[ ] or
boolean or
boolean[] | The value that should be encoded as `type` | - -#### Returns - -| Name | Type | Description | -| :----------------- | :----- | :------------------------------------------------------- | -| `encodedValueType` | string | A hex string representing the `value` encoded as `type`. | - -After the `value` is encoded, the hex string can be used to be stored inside the ERC725Y smart contract. - -#### Examples - -```javascript -myErc725.encodeValueType('uint256', 5); -// '0x0000000000000000000000000000000000000000000000000000000000000005' - -myErc725.encodeValueType('bool', true); -// '0x01' - -// the word `boolean` (Name of the Typescript type) is also available -myErc725.encodeValueType('boolean', true); -// '0x01' - -// `bytesN` type will pad on the right if the value contains less than N bytes -myErc725.encodeValueType('bytes4', '0xcafe'); -// '0xcafe0000' -myErc725.encodeValueType('bytes32', '0xcafe'); -// '0xcafe000000000000000000000000000000000000000000000000000000000000' - -// `bytesN` type will throw an error if the value contains more than N bytes -myERC725.encodeValueType('bytes4', '0xcafecafebeef'); -// Error: Can't convert 0xcafecafebeef to bytes4. Too many bytes, expected at most 4 bytes, received 6. - -// Can also be used to encode arrays as `CompactBytesArray` -myERC725.encodeValueType('uint256[CompactBytesArray]', [1, 2, 3]); -// '0x002000000000000000000000000000000000000000000000000000000000000000010020000000000000000000000000000000000000000000000000000000000000000200200000000000000000000000000000000000000000000000000000000000000003' - -myERC725.encodeValueType('bytes[CompactBytesArray]', [ - '0xaaaaaaaa', - '0xbbbbbbbbbbbbbbbbbb', -]); -// '0x0004aaaaaaaa0009bbbbbbbbbbbbbbbbbb' -``` - -This method is also available as a static method. - -```javascript -ERC725.encodeValueType('string', 'Hello'); -// '0x48656c6c6f' -``` - ---- - -## encodeKeyName - -```js -ERC725.encodeKeyName(keyName [, dynamicKeyParts]); +decodeValueContent(valueContent, value); ``` -Hashes a key name for use on an [ERC725Y contract](https://github.com/ethereum/EIPs/blob/master/EIPS/eip-725.md#erc725y) according to the [LSP2 ERC725Y JSON Schema Standard](https://github.com/lukso-network/LIPs/blob/main/LSPs/LSP-2-ERC725YJSONSchema.md). - -:::info +Decode a hex encoded value and return it as if it was interpreted as a `valueContent`. -`encodeKeyName` is available as either a static or non-static method, so it can be called without instantiating an ERC725 object. +Available `valueContent` are: -::: +- `Address` (checksummed) +- `AssetURL` (deprecated) +- `Boolean` +- `BytesN` +- `JSONURL` (deprecated) +- `Keccak256` +- `Markdown` (similar to `String`) +- `Number` +- `String` +- `URL` +- `VerifiableURI` +- Any Hex `Literal` (e.g.: 0x1345ABCD...) #### Parameters -##### 1. `keyName` - String - -The key name you want to encode, for instance: `LSP3Profile`. - -##### 2. `dynamicKeyParts` - String or array of Strings (optional) - -The variables used to encode the key name, if the key name is a dynamic (i.e.: `MyKey:
`...) +| Name | Type | Description | +| :------------- | :------- | :----------------------------------------------------------------- | +| `valueContent` | `string` | One of the value content options defined by the LSP2 standard. | +| `value` | `string` | A hex encoded string starting with `0x` to decode as `valueContent | #### Returns -| Name | Type | Description | -| :--------------- | :----- | :------------------------------------------- | -| `encodedKeyName` | string | The keccak256 hash of the provided key name. | - -The hash must be retrievable from the ERC725Y contract via the [getData](#getdata) function. - -#### Example - -```javascript title="Encode the key name" -ERC725.encodeKeyName('LSP3Profile'); -// '0x5ef83ad9559033e6e941db7d7c495acdce616347d28e90c7ce47cbfcfcad3bc5' +| Name | Type | Description | +| :------------- | :--------------------------------------------------------------------------------------- | :------------------------------------------- | +| `decodedValue` | `string` or
`URLDataWithHash` or
`number` or
`boolean` or
`null` | A value decoded according to `valueContent`. | -ERC725.encodeKeyName('SupportedStandards:LSP3Profile'); -// '0xeafec4d89fa9619884b600005ef83ad9559033e6e941db7d7c495acdce616347' +### Examples -ERC725.encodeKeyName( - 'AddressPermissions:Permissions:cafecafecafecafecafecafecafecafecafecafe', +```javascript title="decodeValueContent example" +erc725js.decodeValueContent( + 'VerifiableURI', + '0x00006f357c6a0020027547537d35728a741470df1ccf65de10b454ca0def7c5c20b257b7b8d16168687474703a2f2f746573742e636f6d2f61737365742e676c62', ); -// '0x4b80742de2bf82acb3630000cafecafecafecafecafecafecafecafecafecafe' +// { +// verification: { +// method: SUPPORTED_VERIFICATION_METHOD_STRINGS.KECCAK256_UTF8, +// data: '0x027547537d35728a741470df1ccf65de10b454ca0def7c5c20b257b7b8d16168', +// }, +// url: 'http://test.com/asset.glb', +// } + +erc725js.decodeValueContent('String', '0x232068656c6c6f'); +// # hello + +erc725js.decodeValueContent('String', '0x68656c6c6f'); +// hello + +// `Address` will be checksummed +erc725js.decodeValueContent( + 'Address', + '0xa29afb8f3cce086b3992621324e9d7c104f03d1b', +); +// 0xa29Afb8F3ccE086B3992621324E9d7c104F03D1B -ERC725.encodeKeyName('MyKeyName:', 'true'); -// '0x35e6950bc8d21a1699e500000000000000000000000000000000000000000001' +erc725js.decodeValueContent( + 'Number', + '0x000000000000000000000000000000000000000000000000000000000000000a', +); +// 10 -ERC725.encodeKeyName('MyKeyName::', ['ffff', '4081242941']); -// 0x35e6950bc8d20000ffff000000000000000000000000000000000000f342d33d +erc725js.decodeValueContent( + 'Number', + '0x000000000000000000000000000000000000000000000000000000000000036c', +); +// 876 -ERC725.encodeKeyName('MyKeyName:', ['4081242941']); -// 0x35e6950bc8d21a1699e5000000000000000000000000000000000000f342d33d +erc725js.decodeValueContent('Boolean', '0x01'); +// true -// This method is also available on the instance: -myErc725.encodeKeyName('LSP3Profile'); +erc725js.decodeValueContent('Boolean', '0x00'); +// false ``` --- -## decodeMappingKey +### decodeMappingKey ```js ERC725.decodeMappingKey(keyNameOrSchema, keyHash); @@ -1066,7 +1051,9 @@ myErc725.decodeMappingKey( --- -## fetchData +## Fetching Data + +### fetchData ```js myErc725.fetchData([keys]); @@ -1113,6 +1100,11 @@ The name(s) (or the encoded name(s) as schema key) of the element(s) in the smar ### All-Keys Example ```javascript title="Receiving all keys from the schema" +import ERC725 from '@erc725/erc725.js'; +import LSP3Schemas from '@erc725/erc725.js/schemas/LSP3ProfileMetadata.sjon'; +const universalProfileAddress = '0x0F4180da178ed1C71398a57ca8Cb177F69591f1f'; + +const myErc725 = new ERC725(LSP3Schemas, universalProfileAddress); await myErc725.fetchData(); /** [ @@ -1151,9 +1143,15 @@ await myErc725.fetchData(); */ ``` -### Single-Key Example +#### Single-Key Example ```javascript title="Receiving one key from the schema" +import ERC725 from '@erc725/erc725.js'; +import LSP3Schemas from '@erc725/erc725.js/schemas/LSP3ProfileMetadata.sjon'; +const universalProfileAddress = '0x0F4180da178ed1C71398a57ca8Cb177F69591f1f'; + +const myErc725 = new ERC725(LSP3Schemas, universalProfileAddress); + await myErc725.fetchData('LSP3Profile'); /** { @@ -1174,9 +1172,15 @@ await myErc725.fetchData(['LSP1UniversalReceiverDelegate']); */ ``` -### Multi-Keys / Dynamic-Keys Example +#### Multi-Keys / Dynamic-Keys Example ```javascript title="Receiving multiple keys from the schema" +import ERC725 from '@erc725/erc725.js'; +import LSP3Schemas from '@erc725/erc725.js/schemas/LSP3ProfileMetadata.sjon'; +const universalProfileAddress = '0x0F4180da178ed1C71398a57ca8Cb177F69591f1f'; + +const myErc725 = new ERC725(LSP3Schemas, universalProfileAddress); + await myErc725.fetchData(['LSP3Profile', 'LSP1UniversalReceiverDelegate']); /** [ @@ -1218,7 +1222,7 @@ await myErc725.fetchData([ --- -## getData +### getData ```js myErc725.getData([keys]); @@ -1258,9 +1262,15 @@ The name(s) (or the encoded name(s) as schema key) of the element(s) in the smar ::: -### All-Keys Example +#### All-Keys Example ```javascript title="Receiving all keys from the schema" +import ERC725 from '@erc725/erc725.js'; +import LSP3Schemas from '@erc725/erc725.js/schemas/LSP3ProfileMetadata.sjon'; +const universalProfileAddress = '0x0F4180da178ed1C71398a57ca8Cb177F69591f1f'; + +const myErc725 = new ERC725(LSP3Schemas, universalProfileAddress); + await myErc725.getData(); /** [ @@ -1305,9 +1315,15 @@ await myErc725.getData(); */ ``` -### Single-Key Example +#### Single-Key Example ```javascript title="Receiving one key from the schema" +import ERC725 from '@erc725/erc725.js'; +import LSP3Schemas from '@erc725/erc725.js/schemas/LSP3ProfileMetadata.sjon'; +const universalProfileAddress = '0x0F4180da178ed1C71398a57ca8Cb177F69591f1f'; + +const myErc725 = new ERC725(LSP3Schemas, universalProfileAddress); + await myErc725.getData('LSP3Profile'); /** { @@ -1350,9 +1366,15 @@ await myErc725.getData('LSP1UniversalReceiverDelegate'); */ ``` -### Multi-Key Example +#### Multi-Key Example ```javascript title="Receiving multiple keys from the schema" +import ERC725 from '@erc725/erc725.js'; +import LSP3Schemas from '@erc725/erc725.js/schemas/LSP3ProfileMetadata.sjon'; +const universalProfileAddress = '0x0F4180da178ed1C71398a57ca8Cb177F69591f1f'; + +const myErc725 = new ERC725(LSP3Schemas, universalProfileAddress); + await myErc725.getData(['LSP3Profile', 'LSP1UniversalReceiverDelegate']); /** [ @@ -1376,17 +1398,23 @@ await myErc725.getData(['LSP3Profile', 'LSP1UniversalReceiverDelegate']); */ ``` -### Dynamic-Key Example +#### Dynamic-Key Example ```javascript title="Receiving dynamic keys from the schema" +import ERC725 from '@erc725/erc725.js'; +import LSP3Schemas from '@erc725/erc725.js/schemas/LSP3ProfileMetadata.sjon'; +const luksoUniversalProfile = '0x8363Cfe6c787218f0ADA0A4aBC289A8d9dfc2453'; + +const myErc725 = new ERC725(LSP3Schemas, luksoUniversalProfile); + await myErc725.getData({ keyName: 'LSP12IssuedAssetsMap:
', - dynamicKeyParts: '0xcafecafecafecafecafecafecafecafecafecafe', + dynamicKeyParts: '0x592dCACb0A0d4b85eea0975992E42Bc543207F74', // asset address (KidSuper World Arts Path) }); /** { - name: 'LSP12IssuedAssetsMap:cafecafecafecafecafecafecafecafecafecafe', - key: '0x74ac2555c10b9349e78f0000cafecafecafecafecafecafecafecafecafecafe', + name: 'LSP12IssuedAssetsMap:592dCACb0A0d4b85eea0975992E42Bc543207F74', + key: '0x74ac2555c10b9349e78f0000592dCACb0A0d4b85eea0975992E42Bc543207F74', value: '0x6b175474e89094c44da98b954eedeac495271d0f', } */ @@ -1440,7 +1468,7 @@ await myErc725.getData([ --- -## getOwner +### getOwner ```js myErc725.getOwner([address]); @@ -1466,256 +1494,822 @@ The address of the contract owner as stored in the contract. ::: -#### Example +#### Example + +```javascript title="Receiving the owner address" +// If no address is set, it will return the owner of the contract used to initialize the ERC725() class. +await myErc725.getOwner(); +// '0x94933413384997F9402cc07a650e8A34d60F437A' + +// You can also get the owner of a specific contract by setting the address parameter +await myErc725.getOwner('0x3000783905Cc7170cCCe49a4112Deda952DDBe24'); +// '0x7f1b797b2Ba023Da2482654b50724e92EB5a7091' +``` + +--- + +### isValidSignature + +```js +myErc725.isValidSignature(messageOrHash, signature); +``` + +Checks if a signature was signed by the `owner` of the ERC725 Account contract, according to [EIP-1271](https://eips.ethereum.org/EIPS/eip-1271). If the `owner` is a contract itself, it will delegate the `isValidsignature()` call to the owner contract if it supports [EIP-1271](https://eips.ethereum.org/EIPS/eip-1271). Otherwise, it will fail. + +#### Parameters + +##### 1. `messageOrHash` - String + +Value of a message or hash that needs to be verified. + +##### 2. `signature` - String + +The raw RLP encoded signature. + +:::info + +- The hash must be 66 chars long with the `0x` prefix. Otherwise, it will be interpreted as message. +- The message will be: enveloped as `"\x19Ethereum Signed Message:\n" + message.length + message` and hashed using `keccak256` function. + The signature can be generated with [`web3.eth.accounts.sign()`](https://web3js.readthedocs.io/en/v1.2.11/web3-eth-accounts.html#sign). + +::: + +#### Returns + +| Name | Type | Description | +| :-------- | :------ | :------------------------------------------------------------- | +| `Promise` | boolean | `true` if signature is valid, `false` if signature is invalid. | + +:::info + +- A valid signature means that the smart contract response IS the MAGICVALUE: `0x1626ba7e`. +- If this function is called on a contract which does not support [EIP-1271](https://eips.ethereum.org/EIPS/eip-1271), it will throw an error. + +::: + +#### Examples + +```javascript title="Checking the signature with a message" +await myErc725.isValidSignature( + 'hello', + '0xb91467e570a6466aa9e9876cbcd013baba02900b8979d43fe208a4a4f339f5fd6007e74cd82e037b800186422fc2da167c747ef045e5d18a5f5d4300f8e1a0291c', +); +// true +``` + +```javascript title="Checking the signature with a hash" +await myErc725.isValidSignature( + '0x1da44b586eb0729ff70a73c326926f6ed5a25f5b056e7f47fbc6e58d86871655', + '0xcafecafeb915466aa9e9876cbcd013baba02900b8979d43fe208a4a4f339f5fd6007e74cd82e037b800186422fc2da167c747ef045e5d18a5f5d4300f8e1a0291c', +); +// false +``` + +[lsp6 keymanager permissions]: ../../../../../standards/universal-profile/lsp6-key-manager#permissions +[lsp6 keymanager standard]: https://docs.lukso.tech/standards/universal-profile/lsp6-key-manager +[lsp-2 erc725yjsonschema]: https://github.com/lukso-network/LIPs/blob/main/LSPs/LSP-2-ERC725YJSONSchema.md + +### supportsInterface + +```js +myERC725.supportsInterface(interfaceIdOrName); +``` + +```js +ERC725.supportsInterface(interfaceIdOrName, options); +``` + +You can use this function if you need to check if the ERC725 object or a smart contract supports a specific interface (by ID or name). When you use the function on your instantiated ERC725 class, it will use the contract address and provider provided at instantiation. On a non-instantiated class, you need to specify them in the `options` parameter. + +:::caution +The `interfaceId` is not the most secure way to check for a standard, as they could be set manually. +::: + +#### Parameters + +##### 1. `interfaceIdOrName` - String + +Either a string of the hexadecimal `interfaceID` as defined by [ERC165](https://eips.ethereum.org/EIPS/eip-165) or one of the predefined interface names: + +| interfaceName | Standard | +| :------------------------------ | :------------------------------------------------------------------------------------------------------------------------- | +| `ERC1271` | [EIP-1271: Standard Signature Validation Method for Contracts](https://eips.ethereum.org/EIPS/eip-1271) | +| `ERC725X` | [EIP-725: General execution standard](https://eips.ethereum.org/EIPS/eip-725) | +| `ERC725Y` | [EIP-725: General key-value store](https://eips.ethereum.org/EIPS/eip-725) | +| `LSP0ERC725Account` | [LSP-0: ERC725 Account](https://docs.lukso.tech/standards/universal-profile/lsp0-erc725account) | +| `LSP1UniversalReceiver` | [LSP-1: Universal Receiver](https://docs.lukso.tech/standards/generic-standards/lsp1-universal-receiver) | +| `LSP1UniversalReceiverDelegate` | [LSP-1: Universal Receiver Delegate](https://docs.lukso.tech/standards/universal-profile/lsp1-universal-receiver-delegate) | +| `LSP6KeyManager` | [LSP-6: Key Manager](https://docs.lukso.tech/standards/universal-profile/lsp6-key-manager) | +| `LSP7DigitalAsset` | [LSP-7: Digital Asset](https://docs.lukso.tech/standards/nft-2.0/LSP7-Digital-Asset) | +| `LSP8IdentifiableDigitalAsset` | [LSP-8: Identifiable Digital Asset](https://docs.lukso.tech/standards/nft-2.0/LSP8-Identifiable-Digital-Asset) | +| `LSP9Vault` | [LSP-9: Vault](https://docs.lukso.tech/standards/universal-profile/lsp9-vault) | + +:::info + +The `interfaceName` will only check for the latest version of the standard's `interfaceID`, which can be found in `src/constants/interfaces`. For LSPs, the `interfaceIDs` are taken from the latest release of the [@lukso/lsp-smart-contracts](https://github.com/lukso-network/lsp-smart-contracts) library. + +::: + +##### 2. `options` - Object (optional) + +On non instantiated class, you should provide an `options` object. + +| Name | Type | Description | +| :-------- | :----- | :------------------------------------------------------------------- | +| `address` | string | Address of the smart contract to check against a certain interface. | +| `rpcUrl` | string | RPC URL to connect to the network the smart contract is deployed to. | +| `gas` | number | Optional: gas parameter to use. Default: 1_000_000. | + +#### Returns + +| Type | Description | +| :----------------- | :------------------------------------------------------------ | +| `Promise` | Returns `true` if the interface was found, otherwise `false`. | + +#### Examples + +```javascript title="By using the interface ID" +myErc725.supportsInterface('0xfd4d5c50'); +// true + +ERC725.supportsInterface('0xfd4d5c50', { + address: '0xe408BDDbBAB1985006A2c481700DD473F932e5cB', + rpcUrl: 'https://rpc.testnet.lukso.network', +}); +// false +``` + +```javascript title="By using interface name" +myErc725.supportsInterface('LSP0ERC725Account'); +// false + +ERC725.supportsInterface('LSP0ERC725Account', { + address: '0x0Dc07C77985fE31996Ed612F568eb441afe5768D', + rpcUrl: 'https://rpc.testnet.lukso.network', + gas: 20_000_000, +}); +// true +``` + +--- + +## External Data Source utilities (`VerifiableURI` and `JSONURI`) + +### encodeDataSourceWithHash + +```js +const myErc725 = new ERC725(); +myErc725.encodeDataSourceWithHash(verification, dataSource); +``` + +OR + +```js +ERC725.encodeDataSourceWithHash(verification, dataSource); +``` + +Encode a verifiableURI providing the hashing function of the json file (method), the hash of the json file (data) and the url where the json file is stored. + +#### Parameters + +| Name | Type | Description | +| :------------- | :---------------------------- | :----------------------------------------------------------------------------------------------------------------------- | +| `verification` | `undefined` or `Verification` | Verification is an object containing the hashing function of the json file (method) and the hash of the json file (data) | +| `dataSource` | `string` | The url where the json file is stored. | + +
+ Types details + +```js +interface Verification { + method: SUPPORTED_VERIFICATION_METHODS | string; + data: string; + source?: string; +} + +type SUPPORTED_VERIFICATION_METHODS = + | SUPPORTED_VERIFICATION_METHOD_STRINGS + | SUPPORTED_VERIFICATION_METHOD_HASHES; + +enum SUPPORTED_VERIFICATION_METHOD_STRINGS { + KECCAK256_UTF8 = 'keccak256(utf8)', + KECCAK256_BYTES = 'keccak256(bytes)', +} + +enum SUPPORTED_VERIFICATION_METHOD_HASHES { + HASH_KECCAK256_UTF8 = '0x6f357c6a', + HASH_KECCAK256_BYTES = '0x8019f9b1', +} +``` + +
+ +#### Returns + +| Name | Type | Description | +| :-------------- | :----- | :---------------- | +| `verifiableURI` | string | The verifiableURI | + +#### Examples + +
+ Encode a VerifiableURI providing the hashing function, the JSON hash and the uploaded URL + +```javascript title="Encode a VerifiableURI providing the hashing function, the JSON hash and the uploaded URL" +const verifiableURI = myErc725.encodeDataSourceWithHash( + { + method: 'keccak256(utf8)', + data: '0x820464ddfac1bec070cc14a8daf04129871d458f2ca94368aae8391311af6361', + }, + 'ifps://QmYr1VJLwerg6pEoscdhVGugo39pa6rycEZLjtRPDfW84UAx', +); +/** +0x00006f357c6a0020820464ddfac1bec070cc14a8daf04129871d458f2ca94368aae8391311af6361696670733a2f2f516d597231564a4c776572673670456f73636468564775676f3339706136727963455a4c6a7452504466573834554178 +*/ +``` + +
+ +### decodeDataSourceWithHash + +```js +const myErc725 = new ERC725(); +myErc725.decodeDataSourceWithHash(verifiableURI); +``` + +```js +ERC725.decodeDataSourceWithHash(verifiableURI); +``` + +Decode a verifiableURI into the hash function of the json file, the hash of the json file and the url where the json file is stored. + +#### Parameters + +| Name | Type | Description | +| :-------------- | :------- | :---------------- | +| `verifiableURI` | `string` | The verifiableURI | + +#### Returns + +| Name | Type | Description | +| :--------------------- | :---------------- | :--------------------------------------------------------------------------------------------------------- | +| `decodedVerifiableURI` | `URLDataWithHash` | Object containing the hash function, the hash of the JSON file and the link where the json file is stored. | + +
+ Types details + +```js +interface URLDataWithHash { + verification: Verification; + url: string +} + +interface Verification { +method: SUPPORTED_VERIFICATION_METHODS | string; +data: string; +source?: string; +} + +type SUPPORTED_VERIFICATION_METHODS = +| SUPPORTED_VERIFICATION_METHOD_STRINGS +| SUPPORTED_VERIFICATION_METHOD_HASHES; + +enum SUPPORTED_VERIFICATION_METHOD_STRINGS { +KECCAK256_UTF8 = 'keccak256(utf8)', +KECCAK256_BYTES = 'keccak256(bytes)', +} + +enum SUPPORTED_VERIFICATION_METHOD_HASHES { +HASH_KECCAK256_UTF8 = '0x6f357c6a', +HASH_KECCAK256_BYTES = '0x8019f9b1', +} + +``` + +
+ +#### Examples + +
+ Decode a VerifiableURI + +```javascript title="Decode a VerifiableURI" +const decodedVerifiableURI = myErc725.decodeDataSourceWithHash( + '0x00006f357c6a0020820464ddfac1bec070cc14a8daf04129871d458f2ca94368aae8391311af6361696670733a2f2f516d597231564a4c776572673670456f73636468564775676f3339706136727963455a4c6a7452504466573834554178', +); +/** +verification: { + data: '820464ddfac1bec070cc14a8daf04129871d458f2ca94368aae8391311af6361', + method: 'keccak256(utf8)', + } +url: 'ifps://QmYr1VJLwerg6pEoscdhVGugo39pa6rycEZLjtRPDfW84UAx' +*/ +``` + +
+ +### getVerificationMethod + +```js +const myErc725 = new ERC725(); +myErc725.getVerificationMethod(nameOrSig); +``` + +```js +ERC725.getVerificationMethod(nameOrSig); +``` + +```js +import { getVerificationMethod } from '@erc725/erc725.js'; +getVerificationMethod(nameOrSig); +``` + +Get the verification method definition, including the name, signature and related method. + +method: (data: string | object | Uint8Array | null) => string; +name: SUPPORTED_VERIFICATION_METHOD_STRINGS; +sig: SUPPORTED_VERIFICATION_METHODS; + +#### Parameters + +| Name | Type | Description | +| :---------- | :----- | :------------------------------------------ | +| `nameOrSig` | string | The 4 bytes hex of the verification method. | + +#### Returns + +| Name | Type | Description | +| :--- | :----- | :-------------------------------------------------------------------------------------- | +| | object | An object containing the name, signature and method related to the verification method. | + +#### Example + +```javascript title="Example of the method" +getVerificationMethod('0x6f357c6a'); +/* +{ + method: [Function: keccak256Method], + name: 'keccak256(utf8)', + sig: '0x6f357c6a' +} +*/ +``` + +### isDataAuthentic + +```js +const myErc725 = new ERC725(); +ERC725.isDataAuthentic(data, verificationOptions); +``` + +```js +ERC725.isDataAuthentic(data, verificationOptions); +``` + +```js +import { isDataAuthentic } from '@erc725/erc725.js'; + +isDataAuthentic(data, verificationOptions); +``` + +Hashes the `data` passed as parameter using the specified hashing functions (available under `method` in the `verificationOption` object) and compares the result with the provided hash. + +:::info +This method will console an error if the hash provided as `data` and the expected hash obtained using the verification method do not match. +::: + +#### Parameters + +| Name | Type | Description | +| :-------------------- | :----------------------- | :---------------------------------- | +| `data` | `string` or `Uint8Array` | The data to be hashed and verified. | +| `verificationOptions` | `Verification` | An object as defined below | + +
+ Types details + +```js + KECCAK256_UTF8 = , + KECCAK256_BYTES = , + HASH_KECCAK256_UTF8 = , + HASH_KECCAK256_BYTES = , + +export interface Verification { + data: string; + method: 'keccak256(utf8)' | 'keccak256(bytes)' | '0x6f357c6a' | '0x8019f9b1' | string; + source?: string; +} +``` + +
+ +#### Returns + +| Name | Type | Description | +| :--- | :-------- | :-------------------------------------------------------------------------------------------- | +| | `boolean` | `true` if the data is authentic according to the verification method used, `false` otherwise. | + +#### Example + +
+ JSON data to verify from data.json + +```json +[ + { + "name": "LSP3Profile", + "key": "0x5ef83ad9559033e6e941db7d7c495acdce616347d28e90c7ce47cbfcfcad3bc5", + "value": { + "LSP3Profile": { + "name": "test", + "description": "", + "tags": ["profile"], + "links": [], + "profileImage": [ + { + "width": 1024, + "height": 709, + "verification": { + "method": "keccak256(bytes)", + "data": "0x6a0a28680d65b69f5696859be7e0fcebbbcf0df47f1f767926de35402c7d525c" + }, + "url": "ipfs://QmVUYyft3j2JVrG4RzDe1Qx7K5gNtJGFhrExHQFeiRXz1C" + }, + { + "width": 640, + "height": 443, + "verification": { + "method": "keccak256(bytes)", + "data": "0x7cd399f2a2552aa5cd21b1584a98db3efa39c701c311c38a60c680343cfa6d82" + }, + "url": "ipfs://QmeU8FUZC9F1qMYmcWyBhfGqaf7g3kLzGb4xBpoCfyVLZW" + }, + { + "width": 320, + "height": 221, + "verification": { + "method": "keccak256(bytes)", + "data": "0x272d2e57ae1710ac7c5e3d1c9f9d24f48954ad43d0e821f8bd041a4734e309a5" + }, + "url": "ipfs://QmdViKPWYhZv7u86z7HBTgAkTAwEkNSRi1VkYEU8K5yUsH" + }, + { + "width": 180, + "height": 124, + "verification": { + "method": "keccak256(bytes)", + "data": "0x1a464ff7e0eff05da98ed309a25195d8666b6211a5dfa2214865c3fd50ead810" + }, + "url": "ipfs://QmXZUCW6MqCNfYJEFsi54Vkj6PRrUoiPjzTuA2mWtas3RJ" + } + ], + "backgroundImage": [ + { + "width": 1800, + "height": 1012, + "verification": { + "method": "keccak256(bytes)", + "data": "0x3f6be73b35d348fb8f0b87a47d8c8b6b9db8858ee044cb13734cdfe5d28031d8" + }, + "url": "ipfs://QmfLCPmL31f31RRB4R7yoTg3Hsk5PjrWyS3ZaaYyhRPT4n" + }, + { + "width": 1024, + "height": 576, + "verification": { + "method": "keccak256(bytes)", + "data": "0xcb57ed802bcd7dc4964395a609b3a0f557c5f46a602b28b058b9587bb77bb54f" + }, + "url": "ipfs://QmPoPEaoGNVYhiMTwBWp6XzLPRXyuLjZWnuMobdCbfqsU9" + }, + { + "width": 640, + "height": 360, + "verification": { + "method": "keccak256(bytes)", + "data": "0x57e8039288c3e1a7f891c839e03805984ab36524b710656f072492c1c8ebd967" + }, + "url": "ipfs://QmU3pDA4eDNPMeARsJXxKaZsMC5MgFLgzGQccnydbU9WLV" + }, + { + "width": 320, + "height": 180, + "verification": { + "method": "keccak256(bytes)", + "data": "0x2bebf9baac33d719bbd3b481b1af468701409ad7578f84be04e8f7563d5a1509" + }, + "url": "ipfs://QmcKtenPsRvrqZJQ1gLCdUFkex4i9DGp7RFvucb9nbkzsz" + }, + { + "width": 180, + "height": 101, + "verification": { + "method": "keccak256(bytes)", + "data": "0xe32154c03c892d7c41c91220b8757ec5b7847eb2dd91413f7238b0c25f55b475" + }, + "url": "ipfs://QmU7ueJ467E9HRahaqQmSPhvkTkMhCLXRxV45P4kmMk6vm" + } + ] + } + } + } +] +``` + +
+ +```typescript title="isDataAuthentic example" +import jsonData from './data.json'; + +isDataAuthentic(jsonData, { + data: '0xdb864ed42104cee179785036cb4ff1183ebc57e5532ae766ad8533fa48acfbb3', + method: 'keccak256(utf8)', +}); +// true + +isDataAuthentic(jsonData, { + data: '0xdeadbeef00000000000000000000000000000000000000000000000000000000', + method: 'keccak256(utf8)', +}); +// false +``` + +--- + +## Permissions + +### checkPermissions + +```js +myErc725.checkPermissions(requiredPermissions, grantedPermissions); +``` + +```js +ERC725.checkPermissions(requiredPermissions, grantedPermissions); +``` + +Check if the required permissions are included in the granted permissions as defined by the [LSP6 KeyManager Standard](https://docs.lukso.tech/standards/universal-profile/lsp6-key-manager). + +:::info + +`checkPermissions` is available as either a static or non-static method, so it can be called without instantiating an ERC725 object. + +::: + +#### Parameters + +##### 1. `requiredPermissions` - String[] | String + +An array of required permissions or a single required permission. (32bytes hex or the official name of the permission). + +##### 2. `grantedPermissions` - String + +The granted permissions. (32bytes hex). + +#### Returns + +| Type | Description | +| :------ | :----------------------------------------------------------------------------------------------------------------------------------------------- | +| boolean | A boolean value indicating whether the required permissions are included in the granted permissions as defined by the [LSP6 KeyManager Standard] | + +#### Permission-Name Example + +```javascript title="Checking permissions by name" +const requiredPermissions = 'CHANGEOWNER'; +const grantedPermissions = + '0x000000000000000000000000000000000000000000000000000000000000ff51'; +ERC725.checkPermissions(requiredPermissions, grantedPermissions); +// true + +// This method is also available on the instance: + +const requiredPermissions = ['CHANGEOWNER', 'CALL']; +const grantedPermissions = + '0x0000000000000000000000000000000000000000000000000000000000000051'; +myErc725.checkPermissions(requiredPermissions, grantedPermissions); +// false +``` + +#### 32bytes hex Example + +```javascript title="Checking permissions by 32bytes hex" +const requiredPermissions = [ + '0x0000000000000000000000000000000000000000000000000000000000000001', + '0x0000000000000000000000000000000000000000000000000000000000000800', +]; +const grantedPermissions = + '0x0000000000000000000000000000000000000000000000000000000000000051'; + +ERC725.checkPermissions(requiredPermissions, grantedPermissions); +// false + +// This method is also available on the instance: -```javascript title="Receiving the owner address" -// If no address is set, it will return the owner of the contract used to initialize the ERC725() class. -await myErc725.getOwner(); -// '0x94933413384997F9402cc07a650e8A34d60F437A' +const requiredPermissions = + '0x0000000000000000000000000000000000000000000000000000000000000001'; +const grantedPermissions = + '0x0000000000000000000000000000000000000000000000000000000000000051'; -// You can also get the owner of a specific contract by setting the address parameter -await myErc725.getOwner('0x3000783905Cc7170cCCe49a4112Deda952DDBe24'); -// '0x7f1b797b2Ba023Da2482654b50724e92EB5a7091' +myErc725.checkPermissions(requiredPermissions, grantedPermissions); +// true ``` --- -## getSchema +### encodePermissions ```js -myErc725.getSchema(keys [, providedSchemas]); +ERC725.encodePermissions(permissions); ``` -Parses a hashed key or a list of hashed keys and will attempt to return its corresponding [LSP2 ERC725YJSONSchema](https://github.com/lukso-network/LIPs/blob/main/LSPs/LSP-2-ERC725YJSONSchema.md) object. Additionally, it will look for a corresponding key within the schemas: +Encodes permissions into a hexadecimal string as defined by the [LSP6 KeyManager Standard](https://docs.lukso.tech/standards/universal-profile/lsp6-key-manager). -- in the [`schemas`](https://github.com/ERC725Alliance/myErc725.js/tree/main/schemas) folder (which includes all [LSPs](https://github.com/lukso-network/LIPs/tree/main/LSPs)), -- that were provided at ERC725 initialization, and -- that were provided in the function call (`providedSchemas`). +:::info -#### Parameters +`encodePermissions` is available as either a static or non-static method, so it can be called without instantiating an ERC725 object. -##### 1. `keys` - String or array of Strings +::: -The key(s) you are trying to get the schema for. +#### Parameters -##### 2. `providedSchemas` - Object (optional) +##### 1. `permissions` - Object -An array of extra [LSP-2 ERC725YJSONSchema] objects that can be used to find the schema. +An object with [LSP6 KeyManager Permissions] as keys and a `boolean` as value. Any omitted permissions will default to `false`. #### Returns -| Name | Type | Description | -| :------- | :--------------- | :-------------------------------------------------------------------- | -| `result` | ERC725JSONSchema | If the parameter `keys` is a string and the schema was found. | -| `result` | Record string | If the parameter `keys` is a string[ ] and the schema was found. | -| `result` | null | If the schema was not found. | +| Type | Description | +| :----- | :---------------------------------------------------------------------------------------- | +| string | The permissions encoded as a hexadecimal string defined by the [LSP6 KeyManager Standard] | -### Example using a predefined LSP3 schema +#### Example -```javascript title="Parsing the hashed key from the LSP3 schema" -myErc725.getSchema( - '0x5ef83ad9559033e6e941db7d7c495acdce616347d28e90c7ce47cbfcfcad3bc5', -); -/** -{ - name: 'LSP3Profile', - key: '0x5ef83ad9559033e6e941db7d7c495acdce616347d28e90c7ce47cbfcfcad3bc5', - keyType: 'Singleton', - valueContent: 'VerifiableURI', - valueType: 'bytes' -} -*/ -myErc725.getSchema([ - '0x5ef83ad9559033e6e941db7d7c495acdce616347d28e90c7ce47cbfcfcad3bc5', - '0x3a47ab5bd3a594c3a8995f8fa58d087600000000000000000000000000000001', -]); -/** -{ - '0x5ef83ad9559033e6e941db7d7c495acdce616347d28e90c7ce47cbfcfcad3bc5': { - name: 'LSP3Profile', - key: '0x5ef83ad9559033e6e941db7d7c495acdce616347d28e90c7ce47cbfcfcad3bc5', - keyType: 'Singleton', - valueContent: 'VerifiableURI', - valueType: 'bytes' - }, - '0x3a47ab5bd3a594c3a8995f8fa58d087600000000000000000000000000000001': { - name: 'LSP12IssuedAssets[1]', - key: '0x7c8c3416d6cda87cd42c71ea1843df28ac4850354f988d55ee2eaa47b6dc05cd', - keyType: 'Singleton', - valueContent: 'Address', - valueType: 'address' - } -} -*/ -``` +```javascript title="Encoding permissions" +ERC725.encodePermissions({ + CHANGEOWNER: false, + ADDCONTROLLER: false, + EDITPERMISSIONS: false, + ADDEXTENSIONS: false, + CHANGEEXTENSIONS: true, + ADDUNIVERSALRECEIVERDELEGATE: false, + CHANGEUNIVERSALRECEIVERDELEGATE: false, + REENTRANCY: false, + SUPER_TRANSFERVALUE: true, + TRANSFERVALUE: true, + SUPER_CALL: false, + CALL: true, + SUPER_STATICCALL: false, + STATICCALL: false, + SUPER_DELEGATECALL: false, + DELEGATECALL: false, + DEPLOY: false, + SUPER_SETDATA: false, + SETDATA: false, + ENCRYPT: false, + DECRYPT: false, + SIGN: false, + EXECUTE_RELAY_CALL: false, + ERC4337_PERMISSION: false +}), +// '0x0000000000000000000000000000000000000000000000000000000000000110' -### Example using a custom schema +// Any omitted Permissions will default to false +ERC725.encodePermissions({ + ADDCONTROLLER: true, + ADDEXTENSIONS: true, +}), +// '0x000000000000000000000000000000000000000000000000000000000000000a' +ERC725.encodePermissions({ + EDITPERMISSIONS: true, + CHANGEEXTENSIONS: true, + CHANGEUNIVERSALRECEIVERDELEGATE: true, + SETDATA: true, +}), +// '0x0000000000000000000000000000000000000000000000000000000000040054' -```javascript title="Parsing the hashed key from a custom schema" -myErc725.getSchema( - '0x777f55baf2e0c9f73d3bb456dfb8dbf6e609bf557969e3184c17ff925b3c402c', - [ - { - name: 'ParameterSchema', - key: '0x777f55baf2e0c9f73d3bb456dfb8dbf6e609bf557969e3184c17ff925b3c402c', - keyType: 'Singleton', - valueContent: 'VerifiableURI', - valueType: 'bytes', - }, - ], -); -/** -{ - name: 'ParameterSchema', - key: '0x777f55baf2e0c9f73d3bb456dfb8dbf6e609bf557969e3184c17ff925b3c402c', - keyType: 'Singleton', - valueContent: 'VerifiableURI', - valueType: 'bytes', -} -*/ + +// This method is also available on the instance: +myErc725.encodePermissions({ + EDITPERMISSIONS: true, + SETDATA: true, +}), ``` --- -## isValidSignature +### decodePermissions ```js -myErc725.isValidSignature(messageOrHash, signature); +ERC725.decodePermissions(permission); ``` -Checks if a signature was signed by the `owner` of the ERC725 Account contract, according to [EIP-1271](https://eips.ethereum.org/EIPS/eip-1271). If the `owner` is a contract itself, it will delegate the `isValidsignature()` call to the owner contract if it supports [EIP-1271](https://eips.ethereum.org/EIPS/eip-1271). Otherwise, it will fail. - -#### Parameters - -##### 1. `messageOrHash` - String - -Value of a message or hash that needs to be verified. - -##### 2. `signature` - String - -The raw RLP encoded signature. +Decodes permissions from hexadecimal defined by the [LSP6 KeyManager Standard](https://docs.lukso.tech/standards/universal-profile/lsp6-key-manager). :::info -- The hash must be 66 chars long with the `0x` prefix. Otherwise, it will be interpreted as message. -- The message will be: enveloped as `"\x19Ethereum Signed Message:\n" + message.length + message` and hashed using `keccak256` function. - The signature can be generated with [`web3.eth.accounts.sign()`](https://web3js.readthedocs.io/en/v1.2.11/web3-eth-accounts.html#sign). +`decodePermissions` is available as either a static or non-static method, so it can be called without instantiating an ERC725 object. ::: -#### Returns +#### Parameters -| Name | Type | Description | -| :-------- | :------ | :------------------------------------------------------------- | -| `Promise` | boolean | `true` if signature is valid, `false` if signature is invalid. | +##### 1. `permission` - String -:::info +The encoded permission (32bytes hex). -- A valid signature means that the smart contract response IS the MAGICVALUE: `0x1626ba7e`. -- If this function is called on a contract which does not support [EIP-1271](https://eips.ethereum.org/EIPS/eip-1271), it will throw an error. +#### Returns -::: +| Name | Type | Description | +| :------------------- | :----- | :------------------------------------------------------------------------------------------------- | +| `decodedPermissions` | Object | An object specifying whether default LSP6 permissions are included in provided hexademical string. | -#### Examples +#### Example -```javascript title="Checking the signature with a message" -await myErc725.isValidSignature( - 'hello', - '0xb91467e570a6466aa9e9876cbcd013baba02900b8979d43fe208a4a4f339f5fd6007e74cd82e037b800186422fc2da167c747ef045e5d18a5f5d4300f8e1a0291c', -); -// true -``` +```javascript title="Decoding permissions" +ERC725.decodePermissions('0x0000000000000000000000000000000000000000000000000000000000000110'), +/** +{ + CHANGEOWNER: false, + EDITPERMISSIONS: false, + ADDCONTROLLER: false, + SETDATA: false, + CALL: true, + STATICCALL: false, + DELEGATECALL: false, + DEPLOY: false, + TRANSFERVALUE: true, + SIGN: false, +} +*/ -```javascript title="Checking the signature with a hash" -await myErc725.isValidSignature( - '0x1da44b586eb0729ff70a73c326926f6ed5a25f5b056e7f47fbc6e58d86871655', - '0xcafecafeb915466aa9e9876cbcd013baba02900b8979d43fe208a4a4f339f5fd6007e74cd82e037b800186422fc2da167c747ef045e5d18a5f5d4300f8e1a0291c', -); -// false +ERC725.decodePermissions('0x000000000000000000000000000000000000000000000000000000000000000a'), +/** +{ + CHANGEOWNER: false, + EDITPERMISSIONS: true, + ADDCONTROLLER: false, + SETDATA: true, + CALL: false, + STATICCALL: false, + DELEGATECALL: false, + DEPLOY: false, + TRANSFERVALUE: false, + SIGN: false, +} +*/ + +// This method is also available on the instance: +myErc725.decodePermissions('0x0000000000000000000000000000000000000000000000000000000000000110'), ``` -[lsp6 keymanager permissions]: ../../../../../standards/universal-profile/lsp6-key-manager#permissions -[lsp6 keymanager standard]: https://docs.lukso.tech/standards/universal-profile/lsp6-key-manager -[lsp-2 erc725yjsonschema]: https://github.com/lukso-network/LIPs/blob/main/LSPs/LSP-2-ERC725YJSONSchema.md +--- -## supportsInterface +### mapPermission ```js -myERC725.supportsInterface(interfaceIdOrName); +const erc725 = new ERC725(); +erc725.mapPermission(permissionName); ``` ```js -ERC725.supportsInterface(interfaceIdOrName, options); +ERC725.mapPermission(permissionName); ``` -You can use this function if you need to check if the ERC725 object or a smart contract supports a specific interface (by ID or name). When you use the function on your instantiated ERC725 class, it will use the contract address and provider provided at instantiation. On a non-instantiated class, you need to specify them in the `options` parameter. - -:::caution -The `interfaceId` is not the most secure way to check for a standard, as they could be set manually. -::: - -#### Parameters - -##### 1. `interfaceIdOrName` - String - -Either a string of the hexadecimal `interfaceID` as defined by [ERC165](https://eips.ethereum.org/EIPS/eip-165) or one of the predefined interface names: +```js +import { mapPermission } from '@erc725/erc725.js'; -| interfaceName | Standard | -| :------------------------------ | :------------------------------------------------------------------------------------------------------------------------- | -| `ERC1271` | [EIP-1271: Standard Signature Validation Method for Contracts](https://eips.ethereum.org/EIPS/eip-1271) | -| `ERC725X` | [EIP-725: General execution standard](https://eips.ethereum.org/EIPS/eip-725) | -| `ERC725Y` | [EIP-725: General key-value store](https://eips.ethereum.org/EIPS/eip-725) | -| `LSP0ERC725Account` | [LSP-0: ERC725 Account](https://docs.lukso.tech/standards/universal-profile/lsp0-erc725account) | -| `LSP1UniversalReceiver` | [LSP-1: Universal Receiver](https://docs.lukso.tech/standards/generic-standards/lsp1-universal-receiver) | -| `LSP1UniversalReceiverDelegate` | [LSP-1: Universal Receiver Delegate](https://docs.lukso.tech/standards/universal-profile/lsp1-universal-receiver-delegate) | -| `LSP6KeyManager` | [LSP-6: Key Manager](https://docs.lukso.tech/standards/universal-profile/lsp6-key-manager) | -| `LSP7DigitalAsset` | [LSP-7: Digital Asset](https://docs.lukso.tech/standards/nft-2.0/LSP7-Digital-Asset) | -| `LSP8IdentifiableDigitalAsset` | [LSP-8: Identifiable Digital Asset](https://docs.lukso.tech/standards/nft-2.0/LSP8-Identifiable-Digital-Asset) | -| `LSP9Vault` | [LSP-9: Vault](https://docs.lukso.tech/standards/universal-profile/lsp9-vault) | +mapPermission(permissionName); +``` -:::info +/\*\* -The `interfaceName` will only check for the latest version of the standard's `interfaceID`, which can be found in `src/constants/interfaces`. For LSPs, the `interfaceIDs` are taken from the latest release of the [@lukso/lsp-smart-contracts](https://github.com/lukso-network/lsp-smart-contracts) library. +Return the bytes32 representation of an LSP6 permission from its name. +:::tip +When using the `mapPermission` method, if the permission is not known, the function will return `null`. ::: -##### 2. `options` - Object (optional) - -On non instantiated class, you should provide an `options` object. +#### Parameters -| Name | Type | Description | -| :-------- | :----- | :------------------------------------------------------------------- | -| `address` | string | Address of the smart contract to check against a certain interface. | -| `rpcUrl` | string | RPC URL to connect to the network the smart contract is deployed to. | -| `gas` | number | Optional: gas parameter to use. Default: 1_000_000. | +| Name | Type | Description | +| :--------------- | :------- | :------------------------------------------------------------------------------------------------ | +| `permissionName` | `string` | The name of the permission to return the associated `bytes32` value (\_e.g: `SETDATA`, `DEPLOY`). | #### Returns -| Type | Description | -| :----------------- | :------------------------------------------------------------ | -| `Promise` | Returns `true` if the interface was found, otherwise `false`. | - -#### Examples +| Name | Type | Description | +| :--- | :----------------- | :------------------------------------------------------------------------------------------------------------------------------------------- | +| | `string` or `null` | A bytes32 hex string representing the `permissionName`. Or `null` if the input is not a known permission name or a valid 32-byte hex string. | -```javascript title="By using the interface ID" -myErc725.supportsInterface('0xfd4d5c50'); -// true +### Example -ERC725.supportsInterface('0xfd4d5c50', { - address: '0xe408BDDbBAB1985006A2c481700DD473F932e5cB', - rpcUrl: 'https://rpc.testnet.lukso.network', -}); -// false -``` +```javascript title="mapPermission example" +erc725js.mapPermissions('CHANGEOWNER'); +// 0x0000000000000000000000000000000000000000000000000000000000000001 -```javascript title="By using interface name" -myErc725.supportsInterface('LSP0ERC725Account'); -// false +erc725js.mapPermissions('SETDATA'); +// 0x0000000000000000000000000000000000000000000000000000000000040000 -ERC725.supportsInterface('LSP0ERC725Account', { - address: '0x0Dc07C77985fE31996Ed612F568eb441afe5768D', - rpcUrl: 'https://rpc.testnet.lukso.network', - gas: 20_000_000, -}); -// true +erc725js.mapPermissions('DEPLOY'); +// 0x0000000000000000000000000000000000000000000000000000000000010000 ```