Aller au contenu

Échange

Prototype d'intégration avec le SDK d'Alephium: exchange.test.ts - Github

Ce guide explique les API de base et les informations nécessaires pour intégrer Alephium avec une plateforme d'échange de cryptomonnaies.


Pour commencer

Réseau de développement local

Pour intégrer Alephium, une plateforme d'échange doit exécuter un nœud complet. De plus, l'explorateur-backend peut être exécuté pour le débogage et l'indexation supplémentaire.

Pour créer un réseau de développement local avec prise en charge de l'explorateur, suivez les instructions dans le référentiel alephium-stack Une fois lancé, l'interface API du nœud complet et de l'explorateur backend peut être consultée via Swagger UI.


APIs

Pour garder le guide concis, les requêtes API pertinentes seront fournies dans le document au lieu de captures d'écran Swagger UI.

The web3 SDK contains generated Typescript APIs for both the full node and explorer backend.


Test wallet

Avertissement

Le portefeuille de nœud est destiné à tester les API du nœud complet. Pour générer des portefeuilles actifs pour les dépôts, veuillez consulter la génération de portefeuilles.

Récupérons le portefeuille de test en exécutant l'API suivante. Le portefeuille de test contient 1 million d'ALPH pour l'adresse 1DrDyTr9RpRsQnDnXo2YRiPzPW4ooHX5LLoqXrqfMrpQH.

Bash
curl -X 'PUT' \
  'http://127.0.0.1:22973/wallets' \
  -H 'accept: application/json' \
  -H 'Content-Type: application/json' \
  -d '{
  "password": "test",
  "mnemonic": "vault alarm sad mass witness property virus style good flower rice alpha viable evidence run glare pretty scout evil judge enroll refuse another lava",
  "walletName": "test"
}'

# Réponse
# {
#   "walletName": "test"
# }

Obtenez la clé publique de l'adresse en effectuant une requête:

Bash
curl -X 'GET' \
  'http://127.0.0.1:22973/wallets/test/addresses/1DrDyTr9RpRsQnDnXo2YRiPzPW4ooHX5LLoqXrqfMrpQH' \
  -H 'accept: application/json'

# Réponse
# {
#   "address": "1DrDyTr9RpRsQnDnXo2YRiPzPW4ooHX5LLoqXrqfMrpQH",
#   "publicKey": "0381818e63bd9e35a5489b52a430accefc608fd60aa2c7c0d1b393b5239aedf6b0",
#   "group": 0,
#   "path": "m/44'/1234'/0'/0/0"
# }

API de transaction

Créer une transaction

Construisons une transaction pour envoyer 1.23 ALPH à l'adresse 1C2RAVWSuaXw8xtUxqVERR7ChKBE1XgscNFw73NSHE1v3.

Bash
# `fromPublicKey` est la clé publique de l'adresse du portefeuille.

curl -X 'POST' \
  'http://127.0.0.1:22973/transactions/build' \
  -H 'accept: application/json' \
  -H 'Content-Type: application/json' \
  -d '{
  "fromPublicKey": "0381818e63bd9e35a5489b52a430accefc608fd60aa2c7c0d1b393b5239aedf6b0",
  "destinations": [
    {
      "address": "1C2RAVWSuaXw8xtUxqVERR7ChKBE1XgscNFw73NSHE1v3",
      "attoAlphAmount": "1230000000000000000"
    }
  ]
}'

# Réponse:
# {
#   "unsignedTx": "00040080004e20c1174876e8000137a444479fa782e8b88d4f95e28b3b2417e5bc30d33a5ae8486d4a8885b82b224259c1e6000381818e63bd9e35a5489b52a430accefc608fd60aa2c7c0d1b393b5239aedf6b002c41111d67bb1bb000000a3cd757be03c7dac8d48bf79e2a7d6e735e018a9c054b99138c7b29738c437ec00000000000000000000c6d3c20ab5db74a5b8000000bee85f379545a2ed9f6cceb331288842f378cf0f04012ad4ac8824aae7d6f80a00000000000000000000",
#   "gasAmount": 20000,
#   "gasPrice": "100000000000",
#   "txId": "a6c14ad03597ce96ebf78b336aded654395f38e0274c810183c4847d9af3d617",
#   "fromGroup": 0,
#   "toGroup": 1
# }

Signer une transaction

Signons l'ID de transaction:

Bash
curl -X 'POST' \
  'http://127.0.0.1:22973/wallets/test/sign' \
  -H 'accept: application/json' \
  -H 'Content-Type: application/json' \
  -d '{
  "data": "a6c14ad03597ce96ebf78b336aded654395f38e0274c810183c4847d9af3d617"
}'

# Réponse
# {
#   "signature": "78a607ec26165b5a63d7e30a0c85657e8a0fe3b7efccdba78166e51b52c32c9020f921e0a29b6a436ec330c3b3eb2222ee851e718e3504b1a70d73ba45cd503c"
# }

Soumettre une transaction

Soumettons la transaction au réseau:

Bash
# `unsignedTx` provient de la réponse à la construction de la transaction
# `signature`  provient de la réponse à la signature de la transaction

curl -X 'POST' \
  'http://127.0.0.1:22973/transactions/submit' \
  -H 'accept: application/json' \
  -H 'Content-Type: application/json' \
  -d '{
  "unsignedTx": "00040080004e20c1174876e8000137a444479fa782e8b88d4f95e28b3b2417e5bc30d33a5ae8486d4a8885b82b224259c1e6000381818e63bd9e35a5489b52a430accefc608fd60aa2c7c0d1b393b5239aedf6b002c41111d67bb1bb000000a3cd757be03c7dac8d48bf79e2a7d6e735e018a9c054b99138c7b29738c437ec00000000000000000000c6d3c20ab5db74a5b8000000bee85f379545a2ed9f6cceb331288842f378cf0f04012ad4ac8824aae7d6f80a00000000000000000000",
  "signature": "78a607ec26165b5a63d7e30a0c85657e8a0fe3b7efccdba78166e51b52c32c9020f921e0a29b6a436ec330c3b3eb2222ee851e718e3504b1a70d73ba45cd503c"
}'

# Réponse
# {
#   "txId": "a6c14ad03597ce96ebf78b336aded654395f38e0274c810183c4847d9af3d617",
#   "fromGroup": 0,
#   "toGroup": 1
# }

API de blocs

Obtenir le hachage de bloc avec l'ID de transaction

Pour obtenir le hachage de bloc d'une transaction confirmée, vous pouvez utiliser l'API du nœud complet:

Bash
curl -X 'GET' \
  'http://127.0.0.1:22973/transactions/status?txId=a6c14ad03597ce96ebf78b336aded654395f38e0274c810183c4847d9af3d617' \
  -H 'accept: application/json'

# Réponse
# {
#   "type": "Confirmed",
#   "blockHash": "1d616d33a7aadc3cf49f5db1cc484b22a642140673f66020c13dc7648b9382d1",
#   "txIndex": 0,
#   "chainConfirmations": 1,
#   "fromGroupConfirmations": 1,
#   "toGroupConfirmations": 0
# }

Obtenir le bloc avec le hachage de bloc

Bash
curl -X 'GET' \
  'http://127.0.0.1:22973/blockflow/blocks-with-events/ecbc7a3115eb0da1f82902db226b80950e861ef8cbb6623ed02fc42a6eeb69cb' \
  -H 'accept: application/json'

# Réponse
# {
#   "block": {
#     "hash": "ecbc7a3115eb0da1f82902db226b80950e861ef8cbb6623ed02fc42a6eeb69cb",
#     "timestamp": 1231006505000,
#     "chainFrom": 2,
#     "chainTo": 3,
#     "height": 0,
#     ...
#   },
#   "events": []
# }

Interrogation des blocs

Dans Alephium, vous pouvez récupérer tous les blocs de toutes les chaînes pour un intervalle de temps donné car il s'agit d'une blockchain sharded avec plusieurs chaînes opérant à différentes hauteurs simultanément.

Bash
curl -X 'GET' \
  'http://127.0.0.1:22973/blockflow/blocks?fromTs=0&toTs=30' \
  -H 'accept: application/json'

# Réponse: il y a 16 chaînes, donc 16 listes de hachages de blocs
# {
#   "blocks": [
#     [],
#     ...
#     []
#   ]
# }

Vous pouvez récupérer les blocs pour chaque chaîne individuellement en utilisant ce point de terminaison:

Bash
curl -X 'GET' \
  'http://127.0.0.1:22973/blockflow/chain-info?fromGroup=2&toGroup=3' \
  -H 'accept: application/json'

# Réponse
# {
#   "currentHeight": 0
# }

curl -X 'GET' \
  'http://127.0.0.1:22973/blockflow/hashes?fromGroup=2&toGroup=3&height=0' \
  -H 'accept: application/json'

# Réponse
# {
#   "headers": [
#     "ecbc7a3115eb0da1f82902db226b80950e861ef8cbb6623ed02fc42a6eeb69cb"
#   ]
# }


Gestion des UTXO

Pourquoi la gestion des UTXO?

En pratique, certains mineurs ont tendance à envoyer directement les récompenses minières aux adresses d'échange, ce qui entraîne un grand nombre de petites UTXO de faible valeur dans les portefeuilles actifs de l'échange. Cependant, en raison du nombre limité d'entrées pouvant être incluses dans chaque transaction, les retraits peuvent échouer si le portefeuille actif est rempli de ces petites UTXO.

Comment consolider les petites UTXO de faible valeur?

Si votre échange dispose déjà d'un cadre de gestion des UTXO approprié, vous êtes en bonne voie. Cependant, si ce n'est pas le cas, une solution simple est disponible. Vous pouvez utiliser le point de terminaison de balayage pour consolider les petites UTXO de faible valeur d'une adresse spécifique. Veuillez noter que cette fonctionnalité n'est accessible que à partir du nœud complet 2.3.0.

Bash
# `maxAttoAlphPerUTXO` fait référence au montant maximal de ALPH dans les UTXO à consolider.

curl -X 'POST' \
  'http://127.0.0.1:22973/transactions/sweep-address/build' \
  -H 'accept: application/json' \
  -H 'Content-Type: application/json' \
  -d '{
  "fromPublicKey": "0381818e63bd9e35a5489b52a430accefc608fd60aa2c7c0d1b393b5239aedf6b0",
  "toAddress": "1DrDyTr9RpRsQnDnXo2YRiPzPW4ooHX5LLoqXrqfMrpQH",
  "maxAttoAlphPerUTXO": "100 ALPH"
}'

Comment travailler avec des UTXO désignées?

Pour créer des transactions de manière plus efficace, il est recommandé à un échange de stocker l'ensemble des UTXO de leurs portefeuilles actifs, puis de fournir des UTXO spécifiques via l'API.

Bash
curl -X 'POST' \
  'http://127.0.0.1:22973/transactions/build' \
  -H 'accept: application/json' \
  -H 'Content-Type: application/json' \
  -d '{
  "fromPublicKey": "0381818e63bd9e35a5489b52a430accefc608fd60aa2c7c0d1b393b5239aedf6b0",
  "destinations": [
    {
      "address": "1C2RAVWSuaXw8xtUxqVERR7ChKBE1XgscNFw73NSHE1v3",
      "attoAlphAmount": "230000000000000000"
    }
  ]
  "utxos": [
    {
        "hint": 714242201,
        "key": "3bfdeea82a5702cdd98426546d9eeecd744cc540aaffc5ec8ea998dc105da46f"
    }
  ]
}'

hint et key pour l'UTXO sont récupérés à partir de la première sortie de la première transaction que nous avons effectuée. key est unique et peut être utilisé pour indexer l'UTXO.

Bash
curl -X 'GET' \
  'http://127.0.0.1:22973/transactions/details/a6c14ad03597ce96ebf78b336aded654395f38e0274c810183c4847d9af3d617' \
  -H 'accept: application/json'

# Réponse
# {
#   "unsigned": {
#     "txId": "a6c14ad03597ce96ebf78b336aded654395f38e0274c810183c4847d9af3d617",
#     ...
#     "fixedOutputs": [
#       {
#         "hint": 714242201,
#         "key": "3bfdeea82a5702cdd98426546d9eeecd744cc540aaffc5ec8ea998dc105da46f",
#         "attoAlphAmount": "1230000000000000000",
#         "address": "1C2RAVWSuaXw8xtUxqVERR7ChKBE1XgscNFw73NSHE1v3",
#         ...
#       },
#       {
#         "hint": 933512263,
#         "key": "087ee967733900cc7f7beada612ba514dd134ddffc2ad1b6ad8b6998915089c4",
#         "attoAlphAmount": "999998768000000000000000",
#         "address": "1DrDyTr9RpRsQnDnXo2YRiPzPW4ooHX5LLoqXrqfMrpQH",
#         ...
#       }
#     ]
#   },
#   ...
# }

Plus d'informations

Génération de portefeuilles

Pour générer plusieurs adresses pour les utilisateurs, vous pouvez utiliser le portefeuille HD dans le SDK web3.

Sharding

Alephium est une blockchain sharded et ses adresses sont divisées en 4 groupes sur le mainnet. Cependant, on peut: - Envoyer ALPH à plusieurs adresses appartenant au même groupe d'adresse dans une seule transaction. Toutes les adresses de destination doivent appartenir au même groupe. - Envoyer ALPH à partir de plusieurs adresses appartenant au même groupe d'adresse dans une seule transaction. Toutes les adresses d'envoi doivent appartenir au même groupe. - Envoyer ALPH à partir de plusieurs adresses appartenant au même groupe vers plusieurs adresses appartenant à un autre groupe. Toutes les adresses d'envoi doivent appartenir au même groupe, et toutes les adresses de destination doivent également appartenir au même groupe.

Pour obtenir le groupe d'une adresse, vous pouvez vous référer à la fonction du SDK web3 groupOfAddress(address).

Calcul des frais de transaction

Les frais de transaction d'Alephium sont déterminés par la quantité de gaz allouée et le prix du gaz. Un montant maximum de gaz de 625 000 peut être attribué à chaque transaction. Le prix du gaz par défaut est fixé à 1e11 attoALPH par unité de gaz. Lors de la réalisation d'une transaction de transfert simple, le montant de gaz peut être calculé en utilisant le pseudo-code suivant :

TypeScript
txInputBaseGas = 2000
txOutputBaseGas = 4500
inputGas = txInputBaseGas * tx.inputs.length
outputGas = txOutputBaseGas * tx.outputs.length

txBaseGas = 1000
p2pkUnlockGas = 2060 // Actuellement, il n'y a qu'une seule signature

txGas = inputGas + outputGas + txBaseGas + p2pkUnlockGas
minimalGas = 20000

gas = max(minimalGas, txGas)