convert ABIService from class to module and add typings
This commit is contained in:
parent
f049f8598d
commit
2c0bcfefe6
|
@ -1,41 +0,0 @@
|
|||
import { getWeb3 } from 'src/logic/wallets/getWeb3'
|
||||
|
||||
class ABIService {
|
||||
static extractUsefulMethods(abi) {
|
||||
return abi
|
||||
.filter(({ constant, name, type }) => type === 'function' && !!name && typeof constant === 'boolean')
|
||||
.map((method) => ({
|
||||
action: method.constant ? 'read' : 'write',
|
||||
...ABIService.getMethodSignatureAndSignatureHash(method),
|
||||
...method,
|
||||
}))
|
||||
.sort(({ name: a }, { name: b }) => (a.toLowerCase() > b.toLowerCase() ? 1 : -1))
|
||||
}
|
||||
|
||||
static getMethodHash(method) {
|
||||
const signature = ABIService.getMethodSignature(method)
|
||||
return ABIService.getSignatureHash(signature)
|
||||
}
|
||||
|
||||
static getMethodSignatureAndSignatureHash(method) {
|
||||
const methodSignature = ABIService.getMethodSignature(method)
|
||||
const signatureHash = ABIService.getSignatureHash(methodSignature)
|
||||
return { methodSignature, signatureHash }
|
||||
}
|
||||
|
||||
static getMethodSignature({ inputs, name }) {
|
||||
const params = inputs.map((x) => x.type).join(',')
|
||||
return `${name}(${params})`
|
||||
}
|
||||
|
||||
static getSignatureHash(signature) {
|
||||
const web3 = getWeb3()
|
||||
return web3.utils.keccak256(signature).toString()
|
||||
}
|
||||
|
||||
static isPayable(method) {
|
||||
return method.payable
|
||||
}
|
||||
}
|
||||
|
||||
export default ABIService
|
|
@ -0,0 +1,38 @@
|
|||
import { getWeb3 } from 'src/logic/wallets/getWeb3'
|
||||
import { ABI, ExtendedABI } from './types'
|
||||
|
||||
export const getMethodSignature = ({ inputs, name }) => {
|
||||
const params = inputs.map((x) => x.type).join(',')
|
||||
return `${name}(${params})`
|
||||
}
|
||||
|
||||
export const getSignatureHash = (signature) => {
|
||||
const web3 = getWeb3()
|
||||
return web3.utils.keccak256(signature).toString()
|
||||
}
|
||||
|
||||
export const getMethodHash = (method) => {
|
||||
const signature = getMethodSignature(method)
|
||||
return getSignatureHash(signature)
|
||||
}
|
||||
|
||||
export const getMethodSignatureAndSignatureHash = (method) => {
|
||||
const methodSignature = getMethodSignature(method)
|
||||
const signatureHash = getSignatureHash(methodSignature)
|
||||
return { methodSignature, signatureHash }
|
||||
}
|
||||
|
||||
export const extractUsefulMethods = (abi: ABI): ExtendedABI => {
|
||||
return abi
|
||||
.filter(({ constant, name, type }) => type === 'function' && !!name && typeof constant === 'boolean')
|
||||
.map((method) => ({
|
||||
action: method.constant ? 'read' : 'write',
|
||||
...getMethodSignatureAndSignatureHash(method),
|
||||
...method,
|
||||
}))
|
||||
.sort(({ name: a }, { name: b }) => (a.toLowerCase() > b.toLowerCase() ? 1 : -1))
|
||||
}
|
||||
|
||||
export const isPayable = (method) => {
|
||||
return method.payable
|
||||
}
|
|
@ -0,0 +1,25 @@
|
|||
export interface InterfaceParams {
|
||||
internalType: string
|
||||
name: string
|
||||
type: string
|
||||
}
|
||||
|
||||
export interface ContractInterface {
|
||||
constant: boolean
|
||||
inputs: InterfaceParams[]
|
||||
name: string
|
||||
outputs: InterfaceParams[]
|
||||
payable: boolean
|
||||
stateMutability: string
|
||||
type: string
|
||||
}
|
||||
|
||||
export interface ExtendedContractInterface extends ContractInterface {
|
||||
action: string
|
||||
methodSignature: string
|
||||
signatureHash: string
|
||||
}
|
||||
|
||||
export type ABI = ContractInterface[]
|
||||
|
||||
export type ExtendedABI = ExtendedContractInterface[]
|
|
@ -1,11 +1,10 @@
|
|||
import { RateLimit } from 'async-sema'
|
||||
import memoize from 'lodash.memoize'
|
||||
|
||||
import ABIService from 'src/logic/contractInteraction/sources/ABIService'
|
||||
import { ETHEREUM_NETWORK } from 'src/logic/wallets/getWeb3'
|
||||
import { ETHERSCAN_API_KEY } from 'src/utils/constants'
|
||||
|
||||
class EtherscanService extends ABIService {
|
||||
class EtherscanService {
|
||||
_rateLimit = async () => {}
|
||||
|
||||
_endpointsUrls = {
|
||||
|
@ -38,7 +37,6 @@ class EtherscanService extends ABIService {
|
|||
)
|
||||
|
||||
constructor(options) {
|
||||
super()
|
||||
this._rateLimit = RateLimit(options.rps)
|
||||
}
|
||||
|
||||
|
|
|
@ -3,13 +3,13 @@ import React from 'react'
|
|||
import TextareaField from 'src/components/forms/TextareaField'
|
||||
import Col from 'src/components/layout/Col'
|
||||
import Row from 'src/components/layout/Row'
|
||||
import EtherscanService from 'src/logic/contractInteraction/sources/EtherscanService'
|
||||
import { extractUsefulMethods } from 'src/logic/contractInteraction/sources/ABIService'
|
||||
|
||||
export const NO_DATA = 'no data'
|
||||
|
||||
const mustBeValidABI = (abi) => {
|
||||
try {
|
||||
const parsedABI = EtherscanService.extractUsefulMethods(JSON.parse(abi))
|
||||
const parsedABI = extractUsefulMethods(JSON.parse(abi))
|
||||
|
||||
if (parsedABI.length === 0) {
|
||||
return NO_DATA
|
||||
|
|
|
@ -11,7 +11,7 @@ import ButtonLink from 'src/components/layout/ButtonLink'
|
|||
import Col from 'src/components/layout/Col'
|
||||
import Paragraph from 'src/components/layout/Paragraph'
|
||||
import Row from 'src/components/layout/Row'
|
||||
import ABIService from 'src/logic/contractInteraction/sources/ABIService'
|
||||
import { isPayable } from 'src/logic/contractInteraction/sources/ABIService'
|
||||
import { styles } from 'src/routes/safe/components/Balances/SendModal/screens/ContractInteraction/style'
|
||||
import { safeSelector } from 'src/routes/safe/store/selectors'
|
||||
|
||||
|
@ -23,7 +23,7 @@ const EthValue = ({ onSetMax }) => {
|
|||
const {
|
||||
input: { value: method },
|
||||
} = useField('selectedMethod', { value: true })
|
||||
const disabled = !ABIService.isPayable(method)
|
||||
const disabled = !isPayable(method)
|
||||
|
||||
return disabled ? null : (
|
||||
<>
|
||||
|
|
|
@ -11,11 +11,11 @@ import { useField, useFormState } from 'react-final-form'
|
|||
|
||||
import Col from 'src/components/layout/Col'
|
||||
import Row from 'src/components/layout/Row'
|
||||
import EtherscanService from 'src/logic/contractInteraction/sources/EtherscanService'
|
||||
import { NO_CONTRACT } from 'src/routes/safe/components/Balances/SendModal/screens/ContractInteraction/utils'
|
||||
import CheckIcon from 'src/routes/safe/components/CurrencyDropdown/img/check.svg'
|
||||
import { useDropdownStyles } from 'src/routes/safe/components/CurrencyDropdown/style'
|
||||
import { DropdownListTheme } from 'src/theme/mui'
|
||||
import { extractUsefulMethods } from 'src/logic/contractInteraction/sources/ABIService'
|
||||
|
||||
const MENU_WIDTH = '452px'
|
||||
|
||||
|
@ -37,7 +37,7 @@ const MethodsDropdown = ({ onChange }) => {
|
|||
React.useEffect(() => {
|
||||
if (abi) {
|
||||
try {
|
||||
setMethodsList(EtherscanService.extractUsefulMethods(JSON.parse(abi)))
|
||||
setMethodsList(extractUsefulMethods(JSON.parse(abi)))
|
||||
} catch (e) {
|
||||
setMethodsList([])
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue