Desarrollo del sistema de billetera de la plataforma de intercambio — Integración con la cadena Solana

金色财经_
SOL0,42%
ETH0,45%

La última vez completamos el sistema de control de riesgos de la bolsa, en esta ocasión conectamos la wallet de la bolsa a la cadena Solana. El modelo de cuentas, el almacenamiento de logs y el mecanismo de confirmación de Solana son muy diferentes de las cadenas basadas en Ethereum. Si se sigue usando el esquema de Ethereum, es muy fácil cometer errores. A continuación, repasamos la lógica general para entender Solana.

Comprendiendo la singularidad de Solana

Modelo de cuentas de Solana

Solana utiliza un modelo donde programa y datos están separados; los programas son compartidos, mientras que los datos del programa se almacenan en cuentas PDA (Program Derived Address) de forma independiente. Debido a que los programas son compartidos, se necesita Token Mint para distinguir diferentes tokens. La cuenta Token Mint almacena metadatos globales del token, como permiso de acuñación (mint_authority), suministro total (supply), decimales (decimals), etc.
Cada token tiene una dirección única de cuenta Mint que lo identifica, por ejemplo, USDC en la red principal de Solana tiene la dirección de Mint EPjFWdd5AufqSSqeM2qN1xzybapC8G4wEGGkZwyTDt1v.

En Solana existen dos programas de Token: SPL Token y SPL Token-2022. Cada SPL Token tiene una ATA (Associated Token Account) independiente para guardar el saldo del usuario. Cuando se realiza una transferencia de tokens, en realidad se llama a su programa respectivo para transferir entre cuentas ATA.

Restricciones en los logs de Solana

En Ethereum, se obtiene información de transferencias analizando los logs históricos. En Solana, los logs de ejecución no se conservan permanentemente por defecto, no pertenecen al estado del libro mayor (no hay un filtro Bloom para logs), y pueden ser truncados durante la ejecución.
Por lo tanto, no podemos hacer conciliación de depósitos solo escaneando logs, sino que debemos usar getBlock o getSignaturesForAddress para analizar instrucciones.

Confirmación y reorganización en Solana

El tiempo de bloque en Solana es de aproximadamente 400ms. Con 32 confirmaciones (unos 12 segundos), se alcanza el estado finalizado (finalized). Si la precisión en tiempo real no es crítica, basta confiar en los bloques finalizados.
Para mayor precisión, hay que considerar posibles reorganizaciones de bloques, aunque son raras. La diferencia es que el consenso de Solana no depende del parentBlockHash para formar la cadena, por lo que no se puede detectar bifurcaciones comparando parentBlockHash y blockHash en la base de datos como en Ethereum. ¿Cómo detectar si un bloque ha sido reorganizado?
Al escanear localmente, debemos registrar el blockhash de cada slot. Si el blockhash de un mismo slot cambia, indica que hubo un rollback.

Entendiendo las diferencias de Solana, ahora podemos comenzar con las modificaciones en la base de datos:

Diseño de tablas en la base de datos

Dado que Solana tiene dos tipos de tokens, en la tabla tokens añadiremos un campo token_type para distinguir entre SPL Token y SPL Token-2022.

Aunque las direcciones de Solana difieren de Ethereum, ambas pueden derivarse usando BIP32 y BIP44, solo que con diferentes rutas de derivación. Por ello, podemos mantener la tabla wallets existente, pero para soportar el mapeo ATA y el seguimiento de bloques en Solana, añadiremos estas tres tablas:

Nombre de la tabla Campos clave Descripción
solana_slots slot, block_hash, status, parent_slot Información redundante de slots, para detectar bifurcaciones y gestionar reversiones
solana_transactions tx_hash, slot, to_addr, token_mint, amount, type Detalles de depósitos y retiros, tx_hash único para seguimiento de doble firma
solana_token_accounts wallet_id, wallet_address, token_mint, ata_address Registro del mapeo ATA-usuario, para que el módulo de escaneo pueda consultar por ata_address

Detalles:

  • solana_slots registra estados como confirmed, finalized, skipped; el escáner decide si guardar o revertir según el estado.
  • solana_transactions almacena en lamports o unidades mínimas del token, con un campo type para distinguir depósitos, retiros, etc. La escritura sensible requiere firma de control de riesgos.
  • solana_token_accounts mantiene la relación con wallets/usuarios, garantizando la unicidad de ATA (wallet_address + token_mint), que es clave para la lógica de escaneo.

Para más detalles, consultar db_gateway/database.md

Procesamiento de depósitos de usuarios

Para gestionar depósitos, se deben escanear continuamente los datos en la cadena Solana, con dos métodos principales:

  1. Escaneo de firmas: getSignaturesForAddress
  2. Escaneo de bloques: getBlock

Método 1: Escanear firmas del address. Se llama a getSignaturesForAddress con la dirección (que puede ser la ATA generada para el usuario o el programID). Se pasa como parámetros before, until, limit para obtener firmas incrementales. Luego, se obtiene la transacción con getTransaction usando la firma.
Este método funciona bien con pocos usuarios o cuentas, pero si hay muchas, es mejor usar el método de escaneo de bloques, que es el que implementamos aquí.

Método 2: Escanear bloques. Se obtiene el slot más reciente, se llama a getBlock para obtener detalles completos, incluyendo transacciones y cuentas, filtrando por instrucciones y cuentas relevantes.

Nota: Debido al alto volumen de transacciones y TPS en Solana, en producción puede que el análisis y filtrado no puedan seguir el ritmo de los bloques. En ese caso, se recomienda usar colas de mensajes (Kafka, RabbitMQ) para filtrar las transferencias de tokens y detectar potenciales eventos de depósito, enviándolos a los consumidores para su procesamiento y almacenamiento. Para acelerar el filtrado, algunos datos calientes se almacenan en Redis. Si hay muchos usuarios, se puede dividir por ATA para mejorar la eficiencia con múltiples consumidores.

Otra opción es usar servicios de indexadores de terceros, que ofrecen Webhook, monitoreo de cuentas y filtrado avanzado, soportando cargas de datos elevadas.

Proceso de escaneo de bloques

Utilizamos el método 2, con código en los módulos scan/solana-scan (blockScanner.ts y txParser.ts). El flujo principal:

1. Sincronización inicial y recuperación histórica (performInitialSync)

  • Desde el último slot escaneado, se recorre hasta el más reciente.
  • Cada 100 slots, se verifica si hay nuevos slots.
  • Se obtiene el bloque con confirmación “confirmed” para balance entre rapidez y precisión.

2. Escaneo en tiempo real (scanNewSlots)

  • Se comprueba continuamente si hay nuevos slots.
  • Se revalida el slot confirmado más reciente para detectar reversiones.

3. Análisis de bloques (txParser.parseBlock)

  • Se llama a getBlock con commitment “confirmed” y encoding “jsonParsed”.
  • Se recorren las transacciones, instrucciones y metadatos internos.
  • Solo se procesan transacciones exitosas (tx.meta.err === null).

4. Análisis de instrucciones (txParser.parseInstruction)

  • Transferencias SOL: coinciden con System Program y tipo ‘transfer’, verificando si la dirección destino está en la lista monitoreada.
  • Transferencias SPL Token: coinciden con Token Program o Token-2022, verificando si la dirección destino es una ATA, y mapeando a la wallet y token mint en la base de datos.

Gestión de reversiones:
El programa obtiene continuamente el slot finalizado (finalizedSlot). Cuando un slot es menor o igual, se marca como finalizado. Para los que aún están en confirmed, se comprueba si el blockhash ha cambiado para detectar reversiones.

Ejemplo de código clave:

// blockScanner.ts - Escaneo de un slot
async scanSingleSlot(slot: number) {
  const block = await solanaClient.getBlock(slot);
  if (!block) {
    await insertSlot({ slot, status: 'skipped' });
    return;
  }
  const finalizedSlot = await getCachedFinalizedSlot();
  const status = slot <= finalizedSlot ? 'finalized' : 'confirmed';
  await processBlock(slot, block, status);
}

// txParser.ts - Parseo de instrucciones
for (const tx of block.transactions) {
  if (tx.meta?.err) continue; // Saltar transacciones fallidas
  const instructions = [
    ...tx.transaction.message.instructions,
    ...(tx.meta.innerInstructions ?? []).flatMap(i => i.instructions)
  ];
  for (const ix of instructions) {
    // Transferencia SOL
    if (ix.programId === SYSTEM_PROGRAM_ID && ix.parsed?.type === 'transfer') {
      if (monitoredAddresses.has(ix.parsed.info.destination)) {
        // Procesar depósito
      }
    }
    // Transferencia SPL Token
    if (ix.programId === TOKEN_PROGRAM_ID || ix.programId === TOKEN_2022_PROGRAM_ID) {
      if (ix.parsed?.type === 'transfer' || ix.parsed?.type === 'transferChecked') {
        const ataAddress = ix.parsed.info.destination;
        const walletAddress = ataToWalletMap.get(ataAddress);
        if (walletAddress && monitoredAddresses.has(walletAddress)) {
          // Procesar depósito
        }
      }
    }
  }
}

Al detectar depósitos, se mantiene la seguridad con DB Gateway y firma doble del control de riesgos, y se registra en la tabla de fondos.

Retiro

El proceso de retiro en Solana es similar al de EVM, pero con diferencias en la construcción de transacciones:

  1. Hay dos tipos de tokens: SPL-Token y SPL-Token 2022, con diferentes programID. Al construir la transacción, se debe distinguir entre ellos.
  2. La transacción consta de dos partes: firmas (signatures) y mensaje (message). El message incluye header, accountKeys, recentBlockhash, instructions. El hash del mensaje se firma con las firmas.
    No hay nonce en Solana; en su lugar, se usa recentBlockhash, válido por unos 150 bloques (~1 minuto). Cada vez que se realiza un retiro, se obtiene un recentBlockhash actualizado en tiempo real. Si el retiro requiere revisión manual, se vuelve a obtener el recentBlockhash, se construye la transacción y se firma nuevamente.

Proceso de retiro

El flujo general:

![diagrama de flujo de retiro]

El código clave para firmar y enviar la transacción:

// Construcción de instrucciones
const instruction = getTransferSolInstruction({
  source: hotWalletSigner,
  destination: solanaAddressTo,
  amount: BigInt(amount)
});

// Para token
const instruction = getTransferInstruction({
  source: sourceAta,
  destination: destAta,
  authority: hotWalletSigner,
  amount: BigInt(amount)
});

// Construcción y firma del mensaje
const transactionMessage = pipe(
  createTransactionMessage({ version: 0 }),
  tx => setTransactionMessageFeePayerSigner(hotWalletSigner, tx),
  tx => setTransactionMessageLifetime({ blockhash, lastValidBlockHeight }),
  tx => appendTransactionMessageInstruction(instruction, tx)
);

// Firmar
const signedTx = await signTransactionMessageWithSigners(transactionMessage);

// Codificación para envío
const signedTransaction = getBase64EncodedWireTransaction(signedTx);

Luego, se envía usando @solana/web3.js:

const solanaRpc = chainConfigManager.getSolanaRpc();
const txSignature = await solanaRpc.sendTransaction(signedTransaction, ...);

Los archivos relevantes son:

  • Wallet: walletBusinessService.ts (405-754)
  • Signer: solanaSigner.ts (29-122)
  • Scripts de prueba: requestWithdrawOnSolana.ts

Optimización pendiente:

  • Verificación previa de ATA: asegurar que la cuenta ATA exista antes del retiro, o crearla si no.
  • Prioridad en tarifas: en congestión, ajustar computeUnitPrice para priorizar.

Resumen

Integrar Solana en la bolsa no requiere cambios en la arquitectura general, solo adaptar su modelo de cuentas, estructura de transacciones y mecanismo de confirmación.
Para depósitos, mantener un mapeo ATA-wallet, monitorizar cambios en blockhash para detectar reorganizaciones, y actualizar dinámicamente el estado del bloque (confirmed → finalized).
Para retiros, obtener el último recentBlockhash en tiempo real, distinguir entre tokens SPL y Token-2022, y construir transacciones específicas para cada caso.

Aviso legal: La información de esta página puede proceder de terceros y no representa los puntos de vista ni las opiniones de Gate. El contenido que aparece en esta página es solo para fines informativos y no constituye ningún tipo de asesoramiento financiero, de inversión o legal. Gate no garantiza la exactitud ni la integridad de la información y no se hace responsable de ninguna pérdida derivada del uso de esta información. Las inversiones en activos virtuales conllevan riesgos elevados y están sujetas a una volatilidad significativa de los precios. Podrías perder todo el capital invertido. Asegúrate de entender completamente los riesgos asociados y toma decisiones prudentes de acuerdo con tu situación financiera y tu tolerancia al riesgo. Para obtener más información, consulta el Aviso legal.

Artículos relacionados

Solana mantiene un soporte clave mientras la subida de Bitcoin impulsa el mercado de criptomonedas

El precio de Solana se mantuvo por encima de $80 en medio del aumento de los valores de Bitcoin, contribuyendo a una recuperación más amplia del mercado cripto con una capitalización de $2.35 billones. La demanda institucional y la disminución de las tensiones geopolíticas respaldaron este crecimiento, mientras que Solana lideró en actividad de finanzas descentralizadas, registrando volúmenes significativos de DEX y de stablecoins en marzo.

CryptoNewsLandhace10h

Solana mantiene el soporte clave mientras el rango se ajusta por debajo de $90

Ideas clave Solana cotiza cerca del soporte de $80 a medida que el precio se comprime dentro de un rango estrecho, lo que refleja una volatilidad más reducida y una participación equilibrada del mercado entre los traders. Los máximos más bajos persistentes y el precio por debajo de las principales medias móviles confirman la estructura bajista en curso, limitando los intentos de recuperación

CryptoNewsLandhace11h

Implementación de firmas de seguridad cuántica en la red de pruebas de Solana; la velocidad de procesamiento de la red disminuye aproximadamente un 90%

Project Eleven y la Solana Foundation despliegan firmas de seguridad cuántica en la red de pruebas, y los resultados iniciales muestran que su tamaño es 20-40 veces mayor que el de las firmas existentes, lo que provoca una caída del 90% en la velocidad de las transacciones. El diseño de clave pública de Solana la hace enfrentar un mayor riesgo de ataques cuánticos, superando a Bitcoin y Ethereum. Aunque los últimos están buscando soluciones seguras, Solana ya va a la vanguardia en experimentos de seguridad cuántica.

GateNewshace13h

3 Altcoins prometedores para comprar antes de que se construya el impulso — SOL, DOGE y BCH

Solana impulsa el crecimiento a través de alta velocidad, escalabilidad y un ecosistema de desarrolladores en expansión. Dogecoin se beneficia del fuerte apoyo de la comunidad, del reconocimiento de marca y del uso cotidiano para pagos. Bitcoin Cash permite transacciones rápidas y de bajo costo con utilidad real para pagos y solidez

CryptoNewsLandhace18h

Circle acuña más de $10B en USDC en Solana en un mes

Circle ha aumentado significativamente la acuñación de USD Coin (USDC) en Solana, con un total de más de $10.25 mil millones recientemente. Este repunte indica una fuerte demanda vinculada al trading de criptoactivos y al crecimiento de DeFi, posicionando a Solana como un actor clave para la actividad de stablecoins.

Coinfomaniahace19h
Comentar
0/400
Sin comentarios