# Getting started
- Connect to the zkSync network.
- Deposit assets from Ethereum into zkSync.
- Make transfers.
- Withdraw funds back to Ethereum mainnet (or testnet).
# Adding zkSync Swift SDK as a dependency
# CocoaPods
pod 'ZKSync'
# Swift Package Manager
- In Xcode go to
File -> Swift Packages -> Add Package Dependency...
. - Insert
https://github.com/zksync-sdk/zksync-swift.git
inEnter package repository URL
field and press Enter. - In
Rules
setmaster
as a default branch.
# Creating signers
Using seed bytes (like MNEMONIC phrase). Must have length >= 32
let zkSigner = try ZkSigner(seed: seed)
Using raw private key
let privateKey = Data(hex: "0x...")
let zkSigner = try ZkSigner(rawPrivateKey: privateKey)
Using EthSigner (explained below). The private key used by ZkSigner is implicitly derived from Ethereum signature of a special message.
let ethSigner = ...
let zkSigner = try ZkSigner(ethSigner: ethSigner, chainId: .goerli)
In case of interacting with Ethereum network like Deposit
or onchain Withdraw
and for creating ZkSigner you may need
to create EthSigner
.
let ethSigner = try DefaultEthSigner(privateKey: "0x...")
// or from Mnemonic
let ethSigner = try DefaultEthSigner(mnemonic: "some mnemonic phrase")
# Connecting to zkSync network
For interact with both zkSync and Ethereum networks you need to create providers with endpoints to blockchain nodes
# zkSync provider
Library has predefined URLs for the next networks ChainId.Mainnet
,ChainId.Goerli
that
officially supports by MatterLabs. Also you can use local node for testing ChainId.Localhost
set to
http://127.0.0.1:3030
let provider = DefaultProvider(chainId: .goerli)
You can create Provider
with any custom URL, just use HTTPTransport
for DefaultProvider
let transport = HTTPTransport(networkURL: "http://127.0.0.1:3030")
let provider = DefaultProvider(transport: transport)
# Ethereum provider
For onchain operation in Ethereum network you may create EthereumProvider
using method createEthereumProvider
of
Wallet
let wallet = ...
let ethereum = try wallet.createEthereumProvider(web3: Web3.InfuraGoerliWeb3())
# Creating a Wallet
To control your account in zkSync, use the Wallet
. It can sign transactions with keys stored in ZkSigner
and
EthSigner
and send transaction to zkSync network using Provider
.
let ethSigner = ...
let zkSigner = ...
let wallet = try DefaultWallet(ethSigner: ethSigner, zkSigner: zkSigner, provider: DefaultProvider(chainId: .goerli))
For onchain operations you can create Ethereum provider from Wallet
let wallet = ...
let ethereum = try wallet.createEthereumProvider(web3: Web3.InfuraGoerliWeb3())
# Depositing assets from Ethereum into zkSync
Let's try to deposit 1.0 ETH to our zkSync account.
let ethSigner = ...
let ethereum = ...
let amount = Web3.Utils.parseToBigUInt("1", units: .eth)!
firstly {
ethereum.deposit(token: .ETH, amount: amount, userAddress: self.ethSigner.address)
}.done { result in
print("Successfully performed deposit with result: \(result)")
}.catch { error in
print("Failed with error: \(error)")
}
# Checking your zkSync balance
You should be want to check your balance in zkSync network after deposit.
firstly {
wallet.getAccountStatePromise()
}.done { (state) in
let balance = state.committed.balances["ETH"] ?? "0"
print("Balance: \(balance)")
}.catch { (error) in
print("Failed with error: \(error)")
}
# Unlocking zkSync account
To make any transaction in zkSync network, you must register your ZkSigner's public key to your account provided EthSigner.
let wallet = ...
firstly {
wallet.getAccountStatePromise()
}.then { state in
wallet.provider
.transactionFeePromise(for: .changePubKey, address: wallet.address, tokenIdentifier: Token.ETH.address)
.map { ($0, state) }
}.then { (feeDetails, state) -> Promise<String> in
let fee = TransactionFee(feeToken: Token.ETH.address,
fee: feeDetails.totalFeeInteger)
return wallet.setSigningKeyPromise(fee: fee,
nonce: state.committed.nonce,
onchainAuth: false)
}.done { hash in
print("Successfully submitted transaction with hash: \(hash)")
}.catch { error in
print("Failed to submit transaction with error: \(error)")
}
# Making transfer funds in zkSync
Now after Deposit
and Unlocking
your account you can create second account and transfer some funds to it.
Note that we can send assets to any fresh Ethereum account, without preliminary registration!
We're going to transfer 0.1 ETH
let receiver = "0x..."
let wallet = ...
let amount = Web3.Utils.parseToBigUInt("1000000", units: .Gwei)!
firstly {
wallet.getAccountStatePromise()
}.then { state in
wallet.provider.transactionFeePromise(for: .transfer,
address: receiver,
tokenIdentifier: Token.ETH.address).map { ($0, state) }
}.then { (feeDetails, state) -> Promise<String> in
let fee = TransactionFee(feeToken: Token.ETH.address,
fee: feeDetails.totalFeeInteger)
return wallet.transferPromise(to: receiver,
amount: amount,
fee: fee,
nonce: nil)
}.done { hash in
print("Successfully submitted transaction with hash: \(hash)")
}.catch { error in
print("Failed to submit transaction with error: \(error)")
}
# Withdrawing funds back to Ethereum
All (or part of) your funds can be withdrawn back to any yours account in Ethereum.
let wallet = ...
let amount = Web3.Utils.parseToBigUInt("1000", units: .Gwei)!
firstly {
wallet.getAccountStatePromise()
}.then { state in
wallet.provider.transactionFeePromise(for: .withdraw, address: wallet.address,
tokenIdentifier: Token.ETH.address).map { ($0, state) }
}.then { (feeDetails, state) -> Promise<String> in
let fee = TransactionFee(feeToken: Token.ETH.address,
fee: feeDetails.totalFeeInteger)
return wallet.withdrawPromise(ethAddress: state.address,
amount: amount,
fee: fee,
nonce: state.committed.nonce,
fastProcessing: false)
}.done { hash in
print("Successfully submitted transaction with hash: \(hash)")
}.catch { error in
print("Failed to submit transaction with error: \(error)")
}