UNPKG

temporibusunde

Version:

Access and interact with Aragon Organizations and their apps.

88 lines (76 loc) 2.78 kB
import { utils as ethersUtils } from 'ethers' import { AppIntent } from '../types' import App from '../entities/App' import { TransactionRequestData } from '../transactions/TransactionRequest' export const apmAppId = (appName: string): string => ethersUtils.namehash(`${appName}.aragonpm.eth`) // Is the given method a full signature, e.g. 'foo(arg1,arg2,...)' export const isFullMethodSignature = (methodSignature: string): boolean => { return ( Boolean(methodSignature) && methodSignature.includes('(') && methodSignature.includes(')') ) } export function validateMethod( destination: string, methodSignature: string, destinationApp: App ): AppIntent { const methods = destinationApp.intents if (!methods) { throw new Error(`No functions specified in artifact for ${destination}`) } // Find the relevant method information const method = methods.find((method) => isFullMethodSignature(methodSignature) ? method.sig === methodSignature : // If the full signature isn't given, just select the first overload declared method.sig.split('(')[0] === methodSignature ) if (!method) { throw new Error(`No method named ${methodSignature} on ${destination}`) } return method } /** * Find the method descriptor corresponding to the data component of a * transaction sent to `app`. * * @param {Object} app App artifact * @param {Object} data Data component of a transaction to app * @return {Object|void} Method with radspec notice and function signature, or undefined if none was found */ export function findAppMethodFromIntent( app: App, transaction: TransactionRequestData ): AppIntent | undefined { const methodId = transaction.data.substring(0, 10) const checkMethodSignature = (siganture: string): boolean => { // Hash signature with Ethereum Identity and silce bytes const sigHash = ethersUtils.hexDataSlice(ethersUtils.id(siganture), 0, 4) return sigHash === methodId } const { deprecatedIntents, intents } = app || {} let method // First try to find the method in the current functions if (Array.isArray(intents)) { method = intents.find((method) => checkMethodSignature(method.sig)) } if (!method) { // The current functions didn't have it; try with each deprecated version's functions const deprecatedFunctionsFromVersions = Object.values( deprecatedIntents || {} ) if (deprecatedFunctionsFromVersions.every(Array.isArray)) { // Flatten all the deprecated functions const allDeprecatedFunctions = ([] as AppIntent[]).concat( ...deprecatedFunctionsFromVersions ) method = allDeprecatedFunctions.find((method) => checkMethodSignature(method.sig) ) } } return method }