-
Notifications
You must be signed in to change notification settings - Fork 58
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
wrapper: handle intent baskets (#286)
- Loading branch information
Showing
12 changed files
with
588 additions
and
240 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,56 @@ | ||
import abi from 'web3-eth-abi' | ||
import { soliditySha3 } from 'web3-utils' | ||
|
||
import { addressesEqual } from '../../utils' | ||
import { findAppMethodFromData } from '../../utils/apps' | ||
|
||
const SET_APP_ABI = [ | ||
{ name: 'namespace', type: 'bytes32' }, | ||
{ name: 'appId', type: 'bytes32' }, | ||
{ name: 'appAddress', type: 'address' } | ||
] | ||
|
||
const CORE_NAMESPACE = soliditySha3('core') | ||
const APP_ADDR_NAMESPACE = soliditySha3('app') | ||
const APP_BASES_NAMESPACE = soliditySha3('base') | ||
const KERNEL_NAMESPACES_NAMES = new Map([ | ||
[CORE_NAMESPACE, 'Core'], | ||
[APP_ADDR_NAMESPACE, 'Default apps'], | ||
[APP_BASES_NAMESPACE, 'App code'] | ||
]) | ||
|
||
/** | ||
* Decode `Kernel.setApp()` parameters based on transaction data. | ||
* | ||
* @param {Object} data Transaction data | ||
* @return {Object} Decoded parameters for `setApp()` (namespace, appId, appAddress) | ||
*/ | ||
export function decodeKernelSetAppParameters (data) { | ||
// Strip 0x prefix + bytes4 sig to get parameter data | ||
const paramData = data.substring(10) | ||
return abi.decodeParameters(SET_APP_ABI, paramData) | ||
} | ||
|
||
export function getKernelNamespace (hash) { | ||
return KERNEL_NAMESPACES_NAMES.has(hash) | ||
? { name: KERNEL_NAMESPACES_NAMES.get(hash), hash } | ||
: null | ||
} | ||
|
||
export function isKernelAppCodeNamespace (namespaceHash) { | ||
return namespaceHash === APP_BASES_NAMESPACE | ||
} | ||
|
||
/** | ||
* Is the transaction intent for `Kernel.setApp()`? | ||
* | ||
* @param {Object} kernelApp App artifact for Kernel | ||
* @param {Object} intent Transaction intent | ||
* @return {Boolean} Whether the intent is `Kernel.setApp()` | ||
*/ | ||
export function isKernelSetAppIntent (kernelApp, intent) { | ||
if (!addressesEqual(kernelApp.proxyAddress, intent.to)) return false | ||
|
||
const method = findAppMethodFromData(kernelApp, intent.data) | ||
return !!method && method.sig === 'setApp(bytes32,bytes32,address)' | ||
} |
105 changes: 105 additions & 0 deletions
105
packages/aragon-wrapper/src/core/aragonOS/kernel.test.js
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,105 @@ | ||
import test from 'ava' | ||
import sinon from 'sinon' | ||
import { soliditySha3 } from 'web3-utils' | ||
import * as kernel from './kernel' | ||
|
||
test.afterEach.always(() => { | ||
sinon.restore() | ||
}) | ||
|
||
// Kernel.setApp(APP_BASES_NAMESPACE, namehash('voting.aragonpm.eth'), '0x7FB5C052A391953De579b0ed7dC87aD59a9A5473') | ||
const SET_APP_TX_DATA = '0xae5b2540f1f3eb40f5bc1ad1344716ced8b8a0431d840b5783aea1fd01786bc26f35ac0f9fa3927f639745e587912d4b0fea7ef9013bf93fb907d29faeab57417ba6e1d40000000000000000000000007fb5c052a391953de579b0ed7dc87ad59a9a5473' | ||
// Kernel.initialize('0xd95677b5b3bc3c89c4c2c3ab702b0aa5d5cb28af', '0x0000000000000000000000000000000000000000') | ||
const INITIALIZE_TX_DATA = '0x485cc955000000000000000000000000d95677b5b3bc3c89c4c2c3ab702b0aa5d5cb28af0000000000000000000000000000000000000000000000000000000000000000' | ||
|
||
test('aragonOS/kernel: decodeKernelSetAppParameters', async (t) => { | ||
t.plan(4) | ||
// arrange | ||
const setAppData = SET_APP_TX_DATA | ||
const notSetAppData = INITIALIZE_TX_DATA | ||
// act | ||
const decodedData = kernel.decodeKernelSetAppParameters(setAppData) | ||
// assert | ||
t.is(decodedData.namespace, '0xf1f3eb40f5bc1ad1344716ced8b8a0431d840b5783aea1fd01786bc26f35ac0f') | ||
t.is(decodedData.appId, '0x9fa3927f639745e587912d4b0fea7ef9013bf93fb907d29faeab57417ba6e1d4') | ||
t.is(decodedData.appAddress, '0x7FB5C052A391953De579b0ed7dC87aD59a9A5473') | ||
|
||
t.throws( | ||
() => kernel.decodeKernelSetAppParameters(notSetAppData), | ||
{ | ||
instanceOf: Error | ||
} | ||
) | ||
}) | ||
|
||
test('aragonOS/kernel: getKernelNamespace', async (t) => { | ||
t.plan(3) | ||
// arrange | ||
// soliditySha3('core') | ||
const coreNamespaceHash = '0xc681a85306374a5ab27f0bbc385296a54bcd314a1948b6cf61c4ea1bc44bb9f8' | ||
// act | ||
const result = kernel.getKernelNamespace(coreNamespaceHash) | ||
const emptyResult = kernel.getKernelNamespace() | ||
// assert | ||
t.is(result.hash, coreNamespaceHash) | ||
t.is(result.name, 'Core') | ||
t.is(emptyResult, null) | ||
}) | ||
|
||
test('aragonOS/kernel: isKernelAppCodeNamespace', async (t) => { | ||
t.plan(2) | ||
// arrange | ||
const appCodeNamespace = soliditySha3('base') | ||
// act | ||
const result = kernel.isKernelAppCodeNamespace(appCodeNamespace) | ||
const emptyResult = kernel.isKernelAppCodeNamespace() | ||
// assert | ||
t.true(result) | ||
t.false(emptyResult) | ||
}) | ||
|
||
test('aragonOS/kernel: isKernelSetAppIntent', async (t) => { | ||
t.plan(3) | ||
|
||
// arrange | ||
const kernelApp = { | ||
proxyAddress: '0x123', | ||
functions: [ | ||
{ | ||
sig: 'initialize(address,address)', | ||
roles: [], | ||
notice: 'Initializes a kernel instance along with its ACL and sets `_permissionsCreator` as the entity that can create other permissions' | ||
}, | ||
{ | ||
sig: 'setApp(bytes32,bytes32,address)', | ||
roles: [ | ||
'APP_MANAGER_ROLE' | ||
], | ||
notice: 'Set the resolving address of `_appId` in namespace `_namespace` to `_app`' | ||
} | ||
] | ||
} | ||
const setAppIntent = { | ||
to: '0x123', | ||
data: SET_APP_TX_DATA | ||
} | ||
const initializeIntent = { | ||
to: '0x123', | ||
data: INITIALIZE_TX_DATA | ||
} | ||
const otherAppIntent = { | ||
to: '0x456', | ||
// vote(0, true) | ||
data: '0xc9d27afe00000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000001' | ||
} | ||
|
||
// act | ||
const setAppResult = kernel.isKernelSetAppIntent(kernelApp, setAppIntent) | ||
const initializeResult = kernel.isKernelSetAppIntent(kernelApp, initializeIntent) | ||
const otherAppResult = kernel.isKernelSetAppIntent(kernelApp, otherAppIntent) | ||
|
||
// assert | ||
t.true(setAppResult) | ||
t.false(initializeResult) | ||
t.false(otherAppResult) | ||
}) |
Oops, something went wrong.