Saltar al contenido principal

Instalar código byte de WebAssembly (Wasm) usando código

Este proceso sube el código del contrato a la Stellar Testnet en una transacción, el blob Wasm subido es una fuente del contrato, que se puede considerar como la 'clase' de un contrato. Se pueden desplegar múltiples instancias de un contrato que comparten la misma fuente, pero tienen su propio estado.

Prerrequisitos

Antes de comenzar, asegúrate de tener instalado lo siguiente para compilar un contrato inteligente:

  1. Rust y Cargo (para compilar contratos inteligentes)
  2. La CLI de Stellar

Inicializar y desarrollar un contrato Rust de ejemplo

stellar contract init hello-world
cd hello-world

# use rust compiler to compile Rust project into a WebAssembly (Wasm) dynamic library (cdylib).
stellar contract build
# cargo rustc --manifest-path=contracts/hello_world/Cargo.toml --crate-type=cdylib --target=wasm32v1-none --release

Estamos inicializando el contrato hello_world por defecto en soroban_examples en el directorio hello-world. Puedes usar la opción -w para crear con otro ejemplo como account.

Después de desarrollar el contrato para producción, el archivo .wasm generado está en la ruta hello-word/target/wasm32v1-none/release/hello_world.wasm

Subir Wasm a la blockchain Stellar

Podemos usar uno de los SDKs, instala las dependencias necesarias para el lenguaje de programación que elijas:

  • SDK de JavaScript: Node.js y npm
  • SDK de Python: pip

Crea un nuevo directorio para tu proyecto y navega dentro de él:

mkdir install-wasm
cd install-wasm

Ejecutar el script de instalación

Se pueden usar diferentes lenguajes de programación para subir el archivo .wasm, su hash SHA256 se usa para desplegar el contrato.

Esta guía te llevará a través de la instalación del Wasm del contrato usando el SDK de JavaScript: js-stellar-sdk.

Crea un nuevo proyecto Node.js con un archivo JavaScript e instala las dependencias necesarias:

touch index.js
npm init es6 -y
npm install @stellar/stellar-sdk fs

Ejecuta el script con node index.js, lee el archivo Wasm, obtiene detalles de la cuenta y sube el contrato en una transacción:

// Import necessary modules in your JavaScript file:
import * as StellarSDK from "@stellar/stellar-sdk";
import fs from "fs";

async function uploadWasm(filePath) {
// reads the compiled Wasm file to buffer
const bytecode = fs.readFileSync(filePath);

// retrieves account details from the network
const account = await server.getAccount(sourceKeypair.publicKey());

// installs the bytecode with a `uploadContractWasm` Stellar operation wrapped in a transaction sent to the network
const operation = StellarSDK.Operation.uploadContractWasm({ wasm: bytecode });
return await buildAndSendTransaction(account, operation);
}

// constructs a transaction, signs it, and submits it to the network, handling any necessary retries for transaction confirmation.
async function buildAndSendTransaction(account, operations) {
const transaction = new StellarSDK.TransactionBuilder(account, {
fee: StellarSDK.BASE_FEE,
networkPassphrase: StellarSDK.Networks.TESTNET,
})
.addOperation(operations)
.setTimeout(30)
.build();

const tx = await server.prepareTransaction(transaction);
tx.sign(sourceKeypair);

console.log("Submitting transaction...");
let response = await server.sendTransaction(tx);
const hash = response.hash;
console.log(`Transaction hash: ${hash}`);
console.log("Awaiting confirmation...");

while (true) {
response = await server.getTransaction(hash);
if (response.status !== "NOT_FOUND") {
break;
}
await new Promise((resolve) => setTimeout(resolve, 1000));
}

if (response.status === "SUCCESS") {
console.log("Transaction successful.");
return response;
} else {
console.log("Transaction failed.");
throw new Error("Transaction failed");
}
}

// Upload contract to the testnet
const server = new StellarSDK.rpc.Server(
"https://soroban-testnet.stellar.org:443",
);
// Replace `Your_Secret_Key`
const sourceKeypair = StellarSDK.Keypair.fromSecret("Your_Secret_Key");
// Adjust this path as necessary
const wasmFilePath = "../target/wasm32v1-none/release/hello_world.wasm";

try {
let uploadResponse = await uploadWasm(wasmFilePath);
const byteArray = uploadResponse.returnValue.bytes();
const wasmHash = byteArray.toString("hex");
console.log(`Wasm hash: ${wasmHash}`);
} catch (error) {
console.error(error);
}

Reemplaza "Your_Secret_Key" con tu clave secreta real.

stellar keys generate --global hello --network testnet
stellar keys show hello

La CLI de Stellar se puede usar para generar identidades, por ejemplo hello, y mostrar su clave secreta.

consejo

Asegúrate de manejar las claves secretas y privadas de forma segura en entornos de producción y nunca las expongas en tus repositorios de código.

Submitting transaction...
Transaction hash: cef7a63667fe5b0ddcde5562d90e0a40bc04c69616916d1d7fa74a8571bbd82f
Awaiting confirmation...
Transaction successful.
Wasm hash: 275405755441e4be59555bb5c5fd81e84ed21659015d8f3594796c1cf3f380db

El hash de la transacción de carga devuelto puede verse con herramientas en línea: stellar.expert/explorer/testnet/tx/cef7a63667fe5b0ddcde5562d90e0a40bc04c69616916d1d7fa74a8571bbd82f

Los contratos cargados se almacenan en entradas ledger ContractCodeEntry. Estas entradas están indexadas por el hash del Wasm usado para cargarlos.

Puedes usar el hash del Wasm para desplegar con la CLI de Stellar:

stellar contract deploy \
--source-account hello \
--network testnet \
--wasm-hash 275405755441e4be59555bb5c5fd81e84ed21659015d8f3594796c1cf3f380db
# CC6NAQE3ZHRQV3NPQB3F3NYEFBAMEABA4KQTM6A2V5V7PBR5H3UEU3MW

Visualiza el contrato desplegado usando el identificador devuelto con herramientas en línea: stellar.expert/explorer/testnet/contract/CC6NAQE3ZHRQV3NPQB3F3NYEFBAMEABA4KQTM6A2V5V7PBR5H3UEU3MW

Guías en esta categoría: