Skip to content

Commit

Permalink
refactor(protocol-kit): Rename MasterCopy to singleton (safe-global#532)
Browse files Browse the repository at this point in the history
* isL1SafeMasterCopy - isL1SingletonCopy

* safeMasterCopyAddress - safeMasterCopyAddress
safeMasterCopyAbi - safeMasterCopyAbi
MASTER_COPY_ADDRESS - SINGLETON_ADDRESS
MASTER_COPY_ABI - SINGLETON_ABI

* type MasterCopyResponse - SafeSingletonResponse

* masterCopy - singleton

* type safeMasterCopyVersion - safeSingletonVersion
type safeMasterCopyL2Version - safeSingletonL2Version

* getServiceMasterCopiesInfo() - getServiceSingletonsInfo()

* Rename some strings

* Rename aliases in adapters folder

* Update packages/protocol-kit/README.md

Co-authored-by: Daniel <[email protected]>

* Update packages/api-kit/tests/e2e/getServiceMastercopiesInfo.test.ts

Co-authored-by: Daniel <[email protected]>

* Commit suggestion

---------

Co-authored-by: Daniel <[email protected]>
  • Loading branch information
yagopv and dasanra committed Oct 25, 2023
1 parent 50c696d commit f359f9f
Show file tree
Hide file tree
Showing 26 changed files with 155 additions and 159 deletions.
10 changes: 5 additions & 5 deletions guides/integrating-the-safe-core-sdk.md
Original file line number Diff line number Diff line change
Expand Up @@ -66,12 +66,12 @@ const safeSdk = await Safe.create({ ethAdapter, safeAddress })

There are two versions of the Safe contracts: [Safe.sol](https://github.com/safe-global/safe-contracts/blob/v1.4.1/contracts/Safe.sol) that does not trigger events in order to save gas and [SafeL2.sol](https://github.com/safe-global/safe-contracts/blob/v1.4.1/contracts/SafeL2.sol) that does, which is more appropriate for L2 networks.

By default `Safe.sol` will be only used on Ethereum Mainnet. For the rest of the networks where the Safe contracts are already deployed, the `SafeL2.sol` contract will be used unless you add the property `isL1SafeMasterCopy` to force the use of the `Safe.sol` contract.
By default `Safe.sol` will be only used on Ethereum Mainnet. For the rest of the networks where the Safe contracts are already deployed, the `SafeL2.sol` contract will be used unless you add the property `isL1SafeSingleton` to force the use of the `Safe.sol` contract.

```js
const safeFactory = await SafeFactory.create({ ethAdapter, isL1SafeMasterCopy: true })
const safeFactory = await SafeFactory.create({ ethAdapter, isL1SafeSingleton: true })

const safeSdk = await Safe.create({ ethAdapter, safeAddress, isL1SafeMasterCopy: true })
const safeSdk = await Safe.create({ ethAdapter, safeAddress, isL1SafeSingleton: true })
```

If the Safe contracts are not deployed to your current network, the property `contractNetworks` will be required to point to the addresses of the Safe contracts previously deployed by you.
Expand All @@ -82,15 +82,15 @@ import { ContractNetworksConfig } from '@safe-global/protocol-kit'
const chainId = await ethAdapter.getChainId()
const contractNetworks: ContractNetworksConfig = {
[chainId]: {
safeMasterCopyAddress: '<MASTER_COPY_ADDRESS>',
safeSingletonAddress: '<SINGLETON_ADDRESS>',
safeProxyFactoryAddress: '<PROXY_FACTORY_ADDRESS>',
multiSendAddress: '<MULTI_SEND_ADDRESS>',
multiSendCallOnlyAddress: '<MULTI_SEND_CALL_ONLY_ADDRESS>',
fallbackHandlerAddress: '<FALLBACK_HANDLER_ADDRESS>',
signMessageLibAddress: '<SIGN_MESSAGE_LIB_ADDRESS>',
createCallAddress: '<CREATE_CALL_ADDRESS>',
simulateTxAccessorAddress: '<SIMULATE_TX_ACCESSOR_ADDRESS>',
safeMasterCopyAbi: '<MASTER_COPY_ABI>', // Optional. Only needed with web3.js
safeSingletonAbi: '<SINGLETON_ABI>', // Optional. Only needed with web3.js
safeProxyFactoryAbi: '<PROXY_FACTORY_ABI>', // Optional. Only needed with web3.js
multiSendAbi: '<MULTI_SEND_ABI>', // Optional. Only needed with web3.js
multiSendCallOnlyAbi: '<MULTI_SEND_CALL_ONLY_ABI>', // Optional. Only needed with web3.js
Expand Down
6 changes: 3 additions & 3 deletions packages/api-kit/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -69,12 +69,12 @@ Returns the information and configuration of the service.
const serviceInfo: SafeServiceInfoResponse = await safeService.getServiceInfo()
```

### getServiceMasterCopiesInfo
### getServiceSingletonsInfo

Returns the list of Safe master copies.
Returns the list of Safe singleton copies.

```js
const masterCopies: MasterCopyResponse = await safeService.getServiceMasterCopiesInfo()
const singletons: SafeSingletonResponse = await safeService.getServiceSingletonsInfo()
```

### decodeData
Expand Down
8 changes: 4 additions & 4 deletions packages/api-kit/src/SafeApiKit.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@ import {
AllTransactionsOptions,
DeleteSafeDelegateProps,
GetSafeDelegateProps,
MasterCopyResponse,
SafeSingletonResponse,
ModulesResponse,
OwnerResponse,
ProposeTransactionProps,
Expand Down Expand Up @@ -76,11 +76,11 @@ class SafeApiKit {
}

/**
* Returns the list of Safe master copies.
* Returns the list of Safe singletons.
*
* @returns The list of Safe master copies
* @returns The list of Safe singletons
*/
async getServiceMasterCopiesInfo(): Promise<MasterCopyResponse[]> {
async getServiceSingletonsInfo(): Promise<SafeSingletonResponse[]> {
return sendRequest({
url: `${this.#txServiceBaseUrl}/v1/about/master-copies`,
method: HttpMethod.Get
Expand Down
6 changes: 3 additions & 3 deletions packages/api-kit/src/types/safeTransactionServiceTypes.ts
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,7 @@ export type SafeServiceInfoResponse = {
}
}

export type MasterCopyResponse = {
export type SafeSingletonResponse = {
address: string
version: string
deployer: string
Expand All @@ -35,7 +35,7 @@ export type SafeInfoResponse = {
readonly nonce: number
readonly threshold: number
readonly owners: string[]
readonly masterCopy: string
readonly singleton: string
readonly modules: string[]
readonly fallbackHandler: string
readonly guard: string
Expand All @@ -51,7 +51,7 @@ export type SafeCreationInfoResponse = {
readonly creator: string
readonly transactionHash: string
readonly factoryAddress: string
readonly masterCopy: string
readonly singleton: string
readonly setupData: string
readonly dataDecoded?: string
}
Expand Down
12 changes: 6 additions & 6 deletions packages/api-kit/tests/e2e/getServiceMastercopiesInfo.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,18 +4,18 @@ import { getServiceClient } from '../utils/setupServiceClient'

let safeApiKit: SafeApiKit

describe('getServiceMasterCopiesInfo', () => {
describe('getServiceSingletonsInfo', () => {
before(async () => {
;({ safeApiKit } = await getServiceClient(
'0x4f3edf983ac636a65a842ce7c78d9aa706d3b113bce9c46f30d7d21715b23b1d'
))
})

it('should call getServiceMasterCopiesInfo', async () => {
const masterCopiesResponse = await safeApiKit.getServiceMasterCopiesInfo()
chai.expect(masterCopiesResponse.length).to.be.greaterThan(1)
masterCopiesResponse.map((masterCopy) => {
chai.expect(masterCopy.deployer).to.be.equal('Gnosis')
it('should call getServiceSingletonsInfo', async () => {
const singletonsResponse = await safeApiKit.getServiceSingletonsInfo()
chai.expect(singletonsResponse.length).to.be.greaterThan(1)
singletonsResponse.map((singleton) => {
chai.expect(singleton.deployer).to.be.equal('Gnosis')
})
})
})
4 changes: 2 additions & 2 deletions packages/api-kit/tests/endpoint/index.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -62,9 +62,9 @@ describe('Endpoint tests', () => {
})
})

it('getServiceMasterCopiesInfo', async () => {
it('getServiceSingletonsInfo', async () => {
await chai
.expect(safeApiKit.getServiceMasterCopiesInfo())
.expect(safeApiKit.getServiceSingletonsInfo())
.to.be.eventually.deep.equals({ data: { success: true } })
chai.expect(fetchData).to.have.been.calledWith({
url: `${txServiceBaseUrl}/v1/about/master-copies`,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -33,7 +33,7 @@ function Monerium() {
const safeSdk = await Safe.create({
ethAdapter: ethAdapter,
safeAddress: selectedSafe,
isL1SafeMasterCopy: true
isL1SafeSingleton: true
})

const pack = new MoneriumPack({
Expand Down
34 changes: 17 additions & 17 deletions packages/protocol-kit/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -163,14 +163,14 @@ import { SafeFactory } from '@safe-global/protocol-kit'
const safeFactory = await SafeFactory.create({ ethAdapter })
```
- The `isL1SafeMasterCopy` flag
- The `isL1SafeSingleton` flag
There are two versions of the Safe contracts: [Safe.sol](https://github.com/safe-global/safe-contracts/blob/v1.4.1/contracts/Safe.sol) that does not trigger events in order to save gas and [SafeL2.sol](https://github.com/safe-global/safe-contracts/blob/v1.4.1/contracts/SafeL2.sol) that does, which is more appropriate for L2 networks.
By default `Safe.sol` will be only used on Ethereum Mainnet. For the rest of the networks where the Safe contracts are already deployed, the `SafeL2.sol` contract will be used unless you add the `isL1SafeMasterCopy` flag to force the use of the `Safe.sol` contract.
By default `Safe.sol` will be only used on Ethereum Mainnet. For the rest of the networks where the Safe contracts are already deployed, the `SafeL2.sol` contract will be used unless you add the `isL1SafeSingleton` flag to force the use of the `Safe.sol` contract.
```js
const safeFactory = await SafeFactory.create({ ethAdapter, isL1SafeMasterCopy: true })
const safeFactory = await SafeFactory.create({ ethAdapter, isL1SafeSingleton: true })
```
- The `contractNetworks` property
Expand All @@ -183,15 +183,15 @@ const safeFactory = await SafeFactory.create({ ethAdapter })
const chainId = await ethAdapter.getChainId()
const contractNetworks: ContractNetworksConfig = {
[chainId]: {
safeMasterCopyAddress: '<MASTER_COPY_ADDRESS>',
safeSingletonAddress: '<SINGLETON_ADDRESS>',
safeProxyFactoryAddress: '<PROXY_FACTORY_ADDRESS>',
multiSendAddress: '<MULTI_SEND_ADDRESS>',
multiSendCallOnlyAddress: '<MULTI_SEND_CALL_ONLY_ADDRESS>',
fallbackHandlerAddress: '<FALLBACK_HANDLER_ADDRESS>',
signMessageLibAddress: '<SIGN_MESSAGE_LIB_ADDRESS>',
createCallAddress: '<CREATE_CALL_ADDRESS>',
simulateTxAccessorAddress: '<SIMULATE_TX_ACCESSOR_ADDRESS>',
safeMasterCopyAbi: '<MASTER_COPY_ABI>', // Optional. Only needed with web3.js
safeSingletonAbi: '<SINGLETON_ABI>', // Optional. Only needed with web3.js
safeProxyFactoryAbi: '<PROXY_FACTORY_ABI>', // Optional. Only needed with web3.js
multiSendAbi: '<MULTI_SEND_ABI>', // Optional. Only needed with web3.js
multiSendCallOnlyAbi: '<MULTI_SEND_CALL_ONLY_ABI>', // Optional. Only needed with web3.js
Expand All @@ -216,7 +216,7 @@ const safeFactory = await SafeFactory.create({ ethAdapter })
### deploySafe
Deploys a new Safe and returns an instance of the Protocol Kit connected to the deployed Safe. The address of the Master Copy, Safe contract version and the contract (`Safe.sol` or `SafeL2.sol`) of the deployed Safe will depend on the initialization of the `safeFactory` instance.
Deploys a new Safe and returns an instance of the Protocol Kit connected to the deployed Safe. The Singleton address, contract version and layer instance (`Safe.sol` or `SafeL2.sol`) of the deployed Safe will depend on the configuration used to create the `safeFactory`.
```js
const safeAccountConfig: SafeAccountConfig = {
Expand Down Expand Up @@ -317,14 +317,14 @@ const predictedSafe: PredictedSafeProps = {
const safeSdk = await Safe.create({ ethAdapter, predictedSafe })
```
- The `isL1SafeMasterCopy` flag
- The `isL1SafeSingleton` flag
There are two versions of the Safe contracts: [Safe.sol](https://github.com/safe-global/safe-contracts/blob/v1.4.1/contracts/Safe.sol) that does not trigger events in order to save gas and [SafeL2.sol](https://github.com/safe-global/safe-contracts/blob/v1.4.1/contracts/SafeL2.sol) that does, which is more appropriate for L2 networks.
By default `Safe.sol` will be only used on Ethereum Mainnet. For the rest of the networks where the Safe contracts are already deployed, the `SafeL2.sol` contract will be used unless you add the `isL1SafeMasterCopy` flag to force the use of the `Safe.sol` contract.
By default `Safe.sol` will be only used on Ethereum Mainnet. For the rest of the networks where the Safe contracts are already deployed, the `SafeL2.sol` contract will be used unless you add the `isL1SafeSingleton` flag to force the use of the `Safe.sol` contract.
```js
const safeSdk = await Safe.create({ ethAdapter, safeAddress, isL1SafeMasterCopy: true })
const safeSdk = await Safe.create({ ethAdapter, safeAddress, isL1SafeSingleton: true })
```
- The `contractNetworks` property
Expand All @@ -337,15 +337,15 @@ const safeSdk = await Safe.create({ ethAdapter, predictedSafe })
const chainId = await ethAdapter.getChainId()
const contractNetworks: ContractNetworksConfig = {
[chainId]: {
safeMasterCopyAddress: '<MASTER_COPY_ADDRESS>',
safeSingletonAddress: '<SINGLETON_ADDRESS>',
safeProxyFactoryAddress: '<PROXY_FACTORY_ADDRESS>',
multiSendAddress: '<MULTI_SEND_ADDRESS>',
multiSendCallOnlyAddress: '<MULTI_SEND_CALL_ONLY_ADDRESS>',
fallbackHandlerAddress: '<FALLBACK_HANDLER_ADDRESS>',
signMessageLibAddress: '<SIGN_MESSAGE_LIB_ADDRESS>',
createCallAddress: '<CREATE_CALL_ADDRESS>',
simulateTxAccessorAddress: '<SIMULATE_TX_ACCESSOR_ADDRESS>',
safeMasterCopyAbi: '<MASTER_COPY_ABI>', // Optional. Only needed with web3.js
safeSingletonAbi: '<SINGLETON_ABI>', // Optional. Only needed with web3.js
safeProxyFactoryAbi: '<PROXY_FACTORY_ABI>', // Optional. Only needed with web3.js
multiSendAbi: '<MULTI_SEND_ABI>', // Optional. Only needed with web3.js
multiSendCallOnlyAbi: '<MULTI_SEND_CALL_ONLY_ABI>', // Optional. Only needed with web3.js
Expand Down Expand Up @@ -382,14 +382,14 @@ const predictedSafe: PredictedSafeProps = {
const safeSdk = await safeSdk.connect({ ethAdapter, predictedSafe })
```
- The `isL1SafeMasterCopy` flag
- The `isL1SafeSingleton` flag
There are two versions of the Safe contracts: [Safe.sol](https://github.com/safe-global/safe-contracts/blob/v1.4.1/contracts/Safe.sol) that does not trigger events in order to save gas and [SafeL2.sol](https://github.com/safe-global/safe-contracts/blob/v1.4.1/contracts/SafeL2.sol) that does, which is more appropriate for L2 networks.
By default `Safe.sol` will be only used on Ethereum Mainnet. For the rest of the networks where the Safe contracts are already deployed, the `SafeL2.sol` contract will be used unless you add the `isL1SafeMasterCopy` flag to force the use of the `Safe.sol` contract.
By default `Safe.sol` will be only used on Ethereum Mainnet. For the rest of the networks where the Safe contracts are already deployed, the `SafeL2.sol` contract will be used unless you add the `isL1SafeSingleton` flag to force the use of the `Safe.sol` contract.
```js
const safeSdk = await Safe.connect({ ethAdapter, safeAddress, isL1SafeMasterCopy: true })
const safeSdk = await Safe.connect({ ethAdapter, safeAddress, isL1SafeSingleton: true })
```
- The `contractNetworks` property
Expand All @@ -402,15 +402,15 @@ const safeSdk = await safeSdk.connect({ ethAdapter, predictedSafe })
const chainId = await ethAdapter.getChainId()
const contractNetworks: ContractNetworksConfig = {
[chainId]: {
safeMasterCopyAddress: '<MASTER_COPY_ADDRESS>',
safeSingletonAddress: '<SINGLETON_ADDRESS>',
safeProxyFactoryAddress: '<PROXY_FACTORY_ADDRESS>',
multiSendAddress: '<MULTI_SEND_ADDRESS>',
multiSendCallOnlyAddress: '<MULTI_SEND_CALL_ONLY_ADDRESS>',
fallbackHandlerAddress: '<FALLBACK_HANDLER_ADDRESS>',
signMessageLibAddress: '<SIGN_MESSAGE_LIB_ADDRESS>',
createCallAddress: '<CREATE_CALL_ADDRESS>',
simulateTxAccessorAddress: '<SIMULATE_TX_ACCESSOR_ADDRESS>',
safeMasterCopyAbi: '<MASTER_COPY_ABI>', // Optional. Only needed with web3.js
safeSingletonAbi: '<SINGLETON_ABI>', // Optional. Only needed with web3.js
safeProxyFactoryAbi: '<PROXY_FACTORY_ABI>', // Optional. Only needed with web3.js
multiSendAbi: '<MULTI_SEND_ABI>', // Optional. Only needed with web3.js
multiSendCallOnlyAbi: '<MULTI_SEND_CALL_ONLY_ABI>', // Optional. Only needed with web3.js
Expand All @@ -433,7 +433,7 @@ const safeAddress = await safeSdk.getAddress()
### getContractVersion
Returns the Safe Master Copy contract version.
Returns the Safe Singleton contract version.
```js
const contractVersion = await safeSdk.getContractVersion()
Expand Down
22 changes: 11 additions & 11 deletions packages/protocol-kit/src/Safe.ts
Original file line number Diff line number Diff line change
Expand Up @@ -94,7 +94,7 @@ class Safe {
* @throws "MultiSendCallOnly contract is not deployed on the current network"
*/
private async init(config: SafeConfig): Promise<void> {
const { ethAdapter, isL1SafeMasterCopy, contractNetworks } = config
const { ethAdapter, isL1SafeSingleton, contractNetworks } = config

this.#ethAdapter = ethAdapter

Expand All @@ -103,14 +103,14 @@ class Safe {
this.#contractManager = await ContractManager.create({
ethAdapter: this.#ethAdapter,
predictedSafe: this.#predictedSafe,
isL1SafeMasterCopy,
isL1SafeSingleton,
contractNetworks
})
} else {
this.#contractManager = await ContractManager.create({
ethAdapter: this.#ethAdapter,
safeAddress: config.safeAddress,
isL1SafeMasterCopy,
isL1SafeSingleton,
contractNetworks
})
}
Expand All @@ -133,10 +133,10 @@ class Safe {
* @throws "MultiSendCallOnly contract is not deployed on the current network"
*/
async connect(config: ConnectSafeConfig): Promise<Safe> {
const { ethAdapter, safeAddress, predictedSafe, isL1SafeMasterCopy, contractNetworks } = config
const { ethAdapter, safeAddress, predictedSafe, isL1SafeSingleton, contractNetworks } = config
const configProps: SafeConfigProps = {
ethAdapter: ethAdapter || this.#ethAdapter,
isL1SafeMasterCopy: isL1SafeMasterCopy || this.#contractManager.isL1SafeMasterCopy,
isL1SafeSingleton: isL1SafeSingleton || this.#contractManager.isL1SafeSingleton,
contractNetworks: contractNetworks || this.#contractManager.contractNetworks
}

Expand Down Expand Up @@ -248,9 +248,9 @@ class Safe {
}

/**
* Returns the Safe Master Copy contract version.
* Returns the Safe Singleton contract version.
*
* @returns The Safe Master Copy contract version
* @returns The Safe Singleton contract version
*/
async getContractVersion(): Promise<SafeVersion> {
if (this.#contractManager.safeContract) {
Expand Down Expand Up @@ -1031,12 +1031,12 @@ class Safe {
const safeVersion = await this.getContractVersion()
const chainId = await this.getChainId()
const customContracts = this.#contractManager.contractNetworks?.[chainId]
const isL1SafeMasterCopy = this.#contractManager.isL1SafeMasterCopy
const isL1SafeSingleton = this.#contractManager.isL1SafeSingleton

const safeSingletonContract = await getSafeContract({
ethAdapter: this.#ethAdapter,
safeVersion: safeVersion,
isL1SafeMasterCopy,
isL1SafeSingleton,
customContracts
})

Expand Down Expand Up @@ -1136,13 +1136,13 @@ class Safe {
const safeVersion = await this.getContractVersion()
const ethAdapter = this.#ethAdapter
const chainId = await ethAdapter.getChainId()
const isL1SafeMasterCopy = this.#contractManager.isL1SafeMasterCopy
const isL1SafeSingleton = this.#contractManager.isL1SafeSingleton
const customContracts = this.#contractManager.contractNetworks?.[chainId]

const safeSingletonContract = await getSafeContract({
ethAdapter: this.#ethAdapter,
safeVersion,
isL1SafeMasterCopy,
isL1SafeSingleton,
customContracts
})

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@ import { Safe_proxy_factory as SafeProxyFactory_V1_4_1 } from '@safe-global/prot
import { SafeProxyFactoryContract } from '@safe-global/safe-core-sdk-types'

export interface CreateProxyProps {
safeMasterCopyAddress: string
safeSingletonAddress: string
initializer: string
saltNonce: string
options?: EthersTransactionOptions
Expand All @@ -33,7 +33,7 @@ class SafeProxyFactoryEthersContract implements SafeProxyFactoryContract {
}

async createProxy({
safeMasterCopyAddress,
safeSingletonAddress,
initializer,
saltNonce,
options,
Expand All @@ -44,14 +44,14 @@ class SafeProxyFactoryEthersContract implements SafeProxyFactoryContract {
if (options && !options.gasLimit) {
options.gasLimit = await this.estimateGas(
'createProxyWithNonce',
[safeMasterCopyAddress, initializer, saltNonce],
[safeSingletonAddress, initializer, saltNonce],
{
...options
}
)
}
const proxyAddress = this.contract
.createProxyWithNonce(safeMasterCopyAddress, initializer, saltNonce, options)
.createProxyWithNonce(safeSingletonAddress, initializer, saltNonce, options)
.then(async (txResponse) => {
if (callback) {
callback(txResponse.hash)
Expand Down
Loading

0 comments on commit f359f9f

Please sign in to comment.