Examples demonstrating transfers between various address types
In Tezos, a transfer operation transfers tokens between two addresses.
When the Babylon/proto005
protocol amendment came into effect, it changed how token transfer involving KT1 addresses work. The transfer of tokens from a KT1 account is completed by calling the KT1's smart contract do
method. The do
method takes a lambda function, and it is the logic of this function that causes the desired transfer of tokens to happen.
The Taquito integration tests can be useful to see how this works.
Transfer from an implicit mv1 address to a mv1 addressโ
This is the simplest token transfer scenario
await Tezos.contract.transfer({ to: contract.address, amount: 1 });
In the following example, we transfer 0.5แน from a mv1PYMQXgRiJBMsrEaM9Yre4JyvcLVbUr8pv
address that signs the operation to mv1UrqbBFBXnEdHnvSrMpt2BQnZzFMA9HQnc
.
Transfers involving "originated" KT1 addressesโ
Pre-Babylon/proto005
"script-less" KT1 addresses were common. This situation changed when the Tezos blockchain migrated to the new Babylon/proto005
protocol.
During the migration from proto004
to proto005
, all KT1 addresses migrated so that they got a contract called manager.tz. This change meant that there are no longer any "script-less" KT1 addresses in Tezos.
A call to the KT1's smart contracts' do
method is required to transfer tokens from KT1 addresses with the new manager.tz
contract. The do
method takes a lambda function, and it is this lambda function that causes changes to occur in the KT1 address.
The examples following apply only to KT1 addresses migrated as part of the
Babylon/proto005
upgrade. Transfers involving other types of smart-contracts depend on those contracts specifically.
Transfer 0.00005 (50 mumav) tokens from a KT1 address to a mv1 addressโ
Sending 50 mumav from kt1...
to mv1UE4jMeeBM49FjNmyvtE19aBKT73HDvM2m
.
Example transfer from a KT1 to a mv1 address on Carthage/Proto006โ
const contract = await Tezos.contract.at('kt1...');await contract.methodsObject.do(transferImplicit('mv1UE4jMeeBM49FjNmyvtE19aBKT73HDvM2m', 50)).send({ amount: 0 });
Where transferImplicit
is a function that returns the necessary Michelson lambda. It looks like this:
export const transferImplicit = (key: string, mumav: number) => {return [{ prim: 'DROP' },{ prim: 'NIL', args: [{ prim: 'operation' }] },{prim: 'PUSH',args: [{ prim: 'key_hash' }, { string: key }],},{ prim: 'IMPLICIT_ACCOUNT' },{prim: 'PUSH',args: [{ prim: 'mumav' }, { int: `${mumav}` }],},{ prim: 'UNIT' },{ prim: 'TRANSFER_TOKENS' },{ prim: 'CONS' },];};
Transfer 0.000001 (1 mumav) tokens from a KT1 address to a KT1 addressโ
Sending 1 mumav to KT1KLbEeEgW5h1QLkPuPvqdgurHx6v4hGyic
from KT1...
Example for Babylon/Proto005 or higherโ
const contract = await Tezos.contract.at('KT1...');await contract.methodsObject.do(transferToContract('KT1KLbEeEgW5h1QLkPuPvqdgurHx6v4hGyic', 1)).send({ amount: 0 });
Where transferToContract
is a function that looks like this:
export const transferToContract = (key: string, amount: number) => {return [{ prim: 'DROP' },{ prim: 'NIL', args: [{ prim: 'operation' }] },{prim: 'PUSH',args: [{ prim: 'address' }, { string: key }],},{ prim: 'CONTRACT', args: [{ prim: 'unit' }] },[{prim: 'IF_NONE',args: [[[{ prim: 'UNIT' }, { prim: 'FAILWITH' }]], []],},],{prim: 'PUSH',args: [{ prim: 'mumav' }, { int: `${amount}` }],},{ prim: 'UNIT' },{ prim: 'TRANSFER_TOKENS' },{ prim: 'CONS' },];};