Skip to main content
Existem dois métodos principais para enviar transações em Solana:
  1. Usando conexões staked (padrão)
  2. Usando serviços de landing especializados como Sender (recomendado)
Este artigo aborda as melhores práticas de otimização de transações ao usar conexões staked, que é o método padrão para todos os planos pagos da Helius. As conexões staked são mais adequadas para casos de uso em que a latência não é crítica para o seu negócio (por exemplo, pagamentos, carteiras, aplicativos sociais, etc.) Se você é um trader avançado (por exemplo, propAMM, sniper, copy trader, bot de liquidação, arbitragem) procurando um serviço de landing de transação especializado com baixa latência, leia nosso tutorial Sender.

Resumo

As conexões staked da Helius garantem 100% de entrega de transação com tempos de confirmação mínimos. Para otimizar suas taxas de landing de transação com conexões staked, recomendamos as seguintes melhores práticas:
  • Use o compromisso “confirmed” para buscar o blockhash mais recente
  • Adicione taxas de prioridade e calcule-as dinamicamente
  • Otimize o uso de unidade de computação (CU)
  • Defina maxRetries para 0 e implemente lógica de retentativa robusta
  • Envie com skipPreflight definido para true (opcional)
Quer ir mais a fundo? Cobrimos todos os fundamentos neste post do blog.

Otimizações Recomendadas para Traders

Para casos de uso de negociação sensíveis à latência, recomendamos usar o Sender. No entanto, se você estiver usando conexões staked e quiser otimizar sua configuração para as latências mais baixas possíveis, recomendamos as seguintes otimizações (além de aplicar as melhores práticas mencionadas acima):
  • Seu servidor cliente (a máquina que você usa para enviar transações) deve estar localizado no Leste dos EUA ou na Europa Ocidental.
  • Escolha FRA ou PIT se quiser co-locar com os servidores de envio de transações da Helius.
  • Evite enviar de regiões distantes da rede do validador (por exemplo, LATAM, África do Sul).
  • Aqueça os caches regionais da Helius para minimizar a latência de cauda.
  • Apenas um thread de aquecimento é necessário por região - qualquer mais não terá benefício.
  • Envie uma chamada RPC getHealth a cada segundo usando o mesmo endpoint e chave de API que você usa para enviar transações.
Esses benefícios serão notáveis apenas para traders experientes. Para desenvolvedores de aplicativos em geral, recomendamos seguir as diretrizes na seção Enviando Transações Inteligentes abaixo.
Obtenha dados de transações onchain o mais rápido possível com Raw Shreds (UDP). Inscreva-se no seu Dashboard da Helius.

Enviando Transações Inteligentes

Tanto os SDKs Helius Node.js quanto Rust podem enviar transações inteligentes. Este novo método constrói e envia uma transação otimizada enquanto gerencia seu status de confirmação. Os usuários podem configurar as opções de envio da transação, como, por exemplo, se a transação deve pular verificações preflight. No nível mais básico, os usuários devem fornecer seu par de chaves e as instruções que desejam executar, e nós cuidamos do resto. Nós:
  • Buscamos o blockhash mais recente
  • Construímos a transação inicial
  • Simulamos a transação inicial para buscar as unidades de computação (CUs) consumidas
  • Definimos o limite de CU para as CUs consumidas na etapa anterior, com alguma margem
  • Obtemos a taxa de prioridade recomendada pela Helius via nossa API de Taxa de Prioridade
  • Definimos a taxa de prioridade (microlamports por CU) como a taxa recomendada pela Helius
  • Adicionamos uma pequena taxa de buffer caso a taxa recomendada mude nos próximos segundos
  • Construímos e enviamos a transação otimizada
  • Retornamos a assinatura da transação se for bem-sucedida
Requerer o valor recomendado (ou superior) para nossas conexões staked garante que a Helius envie transações de alta qualidade e que não seremos limitados pelos validadores.
Este método é a maneira mais fácil de construir, enviar e aterrar uma transação em Solana. Ao usar a taxa recomendada pela Helius, as transações enviadas por usuários da Helius em um de nossos planos pagos padrão serão enviadas por nossas conexões staked, garantindo quase 100% de entrega de transação e latência mínima.

Node.js SDK

O método sendSmartTransaction está disponível no nosso Helius Node.js SDK para versões >= 1.3.2. Para atualizar para uma versão mais recente do SDK, execute npm update helius-sdk. Este exemplo transfere SOL para uma conta de sua escolha. Ele usa sendSmartTransaction para enviar uma transação otimizada que não pula verificações preflight:

Rust SDK

O método send_smart_transaction está disponível no nosso Rust SDK para versões >= 0.1.5. Para atualizar para uma versão mais recente do SDK, execute cargo update helius. O exemplo a seguir transfere 0,01 SOL para uma conta de sua escolha. Ele utiliza send_smart_transaction para enviar uma transação otimizada que pula verificações preflight e faz retentativas duas vezes, se necessário:

Enviando Transações Sem o SDK

Recomendamos enviar transações inteligentes com um de nossos SDKs, mas a mesma funcionalidade pode ser alcançada sem usar um. Tanto o Node.js SDK quanto o Rust SDK são de código aberto, então o código subjacente para a funcionalidade de enviar transação inteligente pode ser visualizado a qualquer momento.

Preparar e Construir a Transação Inicial

Primeiro, prepare e construa a transação inicial. Isso inclui criar uma nova transação com um conjunto de instruções, adicionar o blockhash recente e designar um pagador de taxas. Para transações versionadas, crie um TransactionMessage e compile-o com tabelas de consulta, se houver. Em seguida, crie uma nova transação versionada e assine-a — isso é necessário para o próximo passo, quando simulamos a transação, pois a transação deve ser assinada. Por exemplo, se quiséssemos preparar uma transação versionada:

Otimizar o Uso da Unidade de Computação (CU) da Transação

Para otimizar o uso da unidade de computação (CU) da transação, podemos usar o método RPC simulateTransaction para simular a transação. Simular a transação retornará a quantidade de CUs utilizadas, para que possamos usar esse valor para definir nosso limite de computação adequadamente. É recomendado usar uma transação de teste com as instruções desejadas primeiro, além de uma instrução que define o limite de computação para 1,4m CUs. Isso é feito para garantir que a simulação da transação tenha sucesso. Por exemplo:
Também é recomendado adicionar um pouco de margem para garantir que a transação seja executada sem problemas. Podemos fazer isso definindo o seguinte:
Em seguida, crie uma instrução que define o limite da unidade de computação para esse valor e adicione-o ao seu array de instruções:

Serializar e Codificar a Transação

Isso é relativamente simples. Primeiro, para serializar a transação, ambos os tipos Transaction e VersionedTransaction têm um método .serialize(). Em seguida, use o pacote bs58 para codificar a transação. Seu código deve ser semelhante a bs58.encode(txt.serialize());

Definindo a Taxa de Prioridade Correta

Primeiro, use a API de Taxa de Prioridade para obter a estimativa da taxa de prioridade. Queremos passar nossa transação e obter a taxa recomendada pela Helius via o parâmetro recomendado:
Em seguida, crie uma instrução que define o preço da unidade de computação para esse valor e adicione essa instrução às suas instruções anteriores:

Construir e Enviar a Transação Otimizada

Esta etapa é quase uma repetição da primeira etapa. No entanto, o array de instruções iniciais foi alterado para adicionar duas instruções para definir o limite e o preço da unidade de computação de forma otimizada. Agora, envie a transação. Não importa se você enviar com ou sem verificações preflight ou alterar qualquer outra opção de envio — a transação será encaminhada por nossas conexões staked para todos os planos pagos.

Consultar o Status da Transação e Reenviá-la

Embora as conexões staked encaminhem uma transação diretamente para o líder, ainda é possível que a transação seja descartada no Estágio Bancário. Recomenda-se que os usuários empreguem sua própria lógica de reenviamento em vez de confiar no RPC para reenviar a transação por eles.
O método RPC sendTransaction tem um parâmetro maxRetries que pode ser definido para substituir a lógica de retentativa padrão do RPC, dando aos desenvolvedores mais controle sobre o processo de retentativa. É um padrão comum buscar o blockhash atual via getLatestBlockhash, armazenar o lastValidBlockHeight, e reenviar a transação até que o blockhash expire. É crucial re-assinar uma transação apenas quando o blockhash não for mais válido, caso contrário, é possível que ambas as transações sejam aceitas pela rede. Uma vez que uma transação é enviada, é importante consultar seu status de confirmação para ver se a rede a processou e confirmou antes de reenviar. Use o método RPC getSignatureStatuses para verificar a lista de status de confirmação das transações. O SDK @solana/web3.js também tem um método getSignatureStatuses em sua classe Connection para buscar o status atual de várias assinaturas.

Como o sendSmartTransaction Lida com Consultas e Reenviamentos

O método sendSmartTransaction tem um período de tempo limite de 60 segundos. Como um blockhash é válido por 150 slots, e assumindo slots perfeitos de 400ms, podemos assumir razoavelmente que um blockhash de transação será inválido após um minuto. O método envia a transação e consulta sua assinatura usando este período de tempo limite:
txtSig é definido para a assinatura da transação que acabou de ser enviada. O método então usa o método pollTransactionConfirmation() para consultar o status de confirmação da transação. Este método verifica o status de uma transação a cada cinco segundos por um máximo de três vezes. Se a transação não for confirmada durante este tempo, um erro é retornado: