O framework Anchor é o framework rust mais popular para o desenvolvimento de contratos inteligentes Solana on-chain chamada programs.
Instale os CLIs Solana e Anchor
Se você ainda não configurou seu ambiente de desenvolvimento Solana, poderá visualizar nossos outros artigos que aprofundam a configuração e todas as ferramentas instaladas para o desenvolvimento do programa Anchor e Solana.
Windows (em breve!)
Mac OS (chegando eventualmente?...)
Crie um novo projeto Anchor
De dentro do seu terminal, você pode criar um novo projeto usando o CLI Anchor:
anchor init project_name
Isso cria um novo diretório chamado project_name
no seu diretório de trabalho atual, estruturando um espaço de trabalho Anchor para você. O comando init
também inicializará um novo repositório git e um NPM (usando o Yarn ) para você. Que gentil da parte deles : )
Você deveria então usar o cd
para chegar a raiz do seu novo projeto e poder começar a trabalhar! PS: Se você estiver usando o VS Code, abra seu novo projeto no espaço de trabalho do seu editor.
Estrutura do projeto Anchor
Seu novo projeto Anchor possui alguns arquivos e pastas muito importantes criados durante o processo do init
.
Nota: Você pode mudar os nomes de algumas dessas pastas, mas eu não faria. Apenas mantenha-os iguais a estrutura e siga em frente :)
DIRETÓRIOS IMPORTANTES
app
- a futura casa do código front-end do seu projeto (ou seja, o JavaScript)programs
- o lar de todos os programas Solana/Anchor do seu projeto (também conhecido como código rust), mas mais sobre isso mais tardetests
- lar dos seus testes de ponta a ponta baseados em JavaScript (usando a estrutura de testes Mocha)target
- lar do seu programa Solana compilado e do arquivo Anchor IDL (mais sobre isso mais tarde também! )
ARQUIVOS IMPORTANTES
Anchor.toml
- arquivo manifesto contendo informações e configurações para o seu espaço de trabalho AnchorCargo.toml
- contém as configurações de Carga do gerenciador de pacotes (mesma ideia do arquivopackage.json
para projetos Node / NPM)package.json
- o arquivo de pacote JavaScript padrão que será usado pelo seu front-end
Crie seu programa Anchor
Ao contrário do rust vanilla , baseado no desenvolvimento do programa Solana on-chain, os projetos Anchor são construídos usando a CLI Anchor. O que faz a mesma compilação BPF que o comando nativo cargo-build-bpf
, mas adicionando a magia do Anchor de gerar o arquivo IDL (prometo que vou chegar lá, só que agora não... )
Para construir seu projeto Anchor:
anchor build
Construção inicial da Anchor
A cada novo projeto, recomendo executar o comando build
logo após o seu init
porque pode levar algum tempo para o compilador rust compilar todas as várias bibliotecas usadas. Então vá tomar um café.
Após a conclusão da compilação inicial, vá em frente e execute novamente comando anchor build
. Eu espero....
Agora deve ser muito mais rápido. Isso ocorre porque nem todos os códigos e pacotes rust compilados anteriormente precisam ser recompilados do zero. Cada vez que você reconstruir seu projeto, efetivamente apenas os arquivos alterados precisarão ser recompilados. Tornando cada compilação subsequente muito mais rápida que a inicial.
Arquivos principais gerados a partir da compilação
O comando Anchor build não apenas compilará seu código rust em um programa Solana implantável, mas também gerará alguns outros arquivos.
Nota: Por simplicidade, cobrirei apenas os arquivos / pastas diretamente importantes gerados pelo comando build.
Dentro do seu diretório target
, os seguintes arquivos importantes são gerados:
deploy/project_name.so
- o binário do programa Solana pronto para ser implantado na blockchaindeploy/project_name-keypair.json
- um novo arquivo de par de chaves do sistema de arquivos que será usado para o seu programaidl/project_name.json
- um arquivo JSON que será usado pelo seu front-end para facilitar ainda mais a interação com o seu programa on-chaintypes / project_name.ts
- definições em typescript geradas automaticamente que serão usadas pelo seu frontend
Anchor.toml file
O arquivo manifesto Anchor.toml
é onde determinadas configurações dos seus programas Solana e da área de trabalho do Anchor serão ativadas.
Por simplicidade, focalizarei apenas 2 seções principais para esta introdução ao Anchor:
[programs.cluster]
, e[provider]
Você pode ler mais sobre o arquivo Anchor.toml
na documentação Anchor lang docs.
Anchor.toml [programs.cluster]
A configuração "programs" permitirá salvar o program_id
em sequência de cada um dos seus programas Solana dentro do seu projeto. Incluindo a capacidade de definir um diferente program_id
para cada cluster, conforme desejado.
Por exemplo, o código abaixo armazena o program_id
para o localnet
cluster:
[programs.localnet]
demo = "Fg6PaFpoGXkYsidMpWTK6W2BeZ7FEfcYkg476zPFsLnS"
Para armazenar um diferente program_id
para diferentes clusters, você pode usar algo assim:
[programs.localnet]
demo = "Fg6PaFpoGXkYsidMpWTK6W2BeZ7FEfcYkg476zPFsLnS"
[programs.testnet]
demo = "3ze6Z4rR8r8PkYAYYV5yZTRLKAHQMBcJj4AZMg4MS1fG"
Anchor.toml [provider]
Você pode especificar um provider
para armazenar o cluster
Solana desejado e o arquivo de par de chaves local (aka wallet
) do seu programa implantado ao qual você deseja ter a propriedade.
[provider]
cluster = "localnet"
wallet = "~/.config/solana/id.json"
Seu verdadeiro código de programa Solana
Os programas Solana são diferentes dos programas comuns baseados em rust. Os programas Solana são criados como "bibliotecas" rust que podem ser carregados em tempo de execução do Sealevel da blockchain Solana.
Por convenção, estas bibliotecas normalmente terão seus arquivos de código principal de src / lib.rs
dentro do diretório programs / program_name
do seu espaço de trabalho Anchor( por exemplo. No caso do nosso projeto, "project_name", este arquivo será exibido em programs / project_name / src / lib.rs
)
A estrutura Anchor padrão para lib.rs
deve ficar assim:
use anchor_lang::prelude::*;
declare_id!("Fg6PaFpoGXkYsidMpWTK6W2BeZ7FEfcYkg476zPFsLnS");
#[program]
pub mod demo {
use super::*;
pub fn initialize(_ctx: Context<Initialize>) -> Result<()> {
Ok(())
}
}
#[derive(Accounts)]
pub struct Initialize {}
Este código é essencialmente o programa Solana Anchor mais básico que você pode criar. Sério, isso não faz nada, exceto criar-se. Este código é equivalente a return true
na maioria dos idiomas. Vamos dividir a estrutura do programa e o que está acontecendo.
Importar bibliotecas
Como a maioria dos outros idiomas, também é convenção "importar" todos os itens / bibliotecas / blocos desejados na parte superior do seu arquivo rust. No rust o use
é a palavra-chave usada para especificar o quê importar para o arquivo rust específico.
use anchor_lang::prelude::*;
Para cada programa Solana baseado em Anchor, a mesma importação básica do anchor_lang
é usado para informar ao compilador rust a qual é estrutura Anchor dentro do nosso código. Incluindo defini-lo como parte do namespace para podermos chamar as funções Anchor no "local scope" ( Escopo Local).
declare_id
Em seguida, estamos usando o macro declare_id
para definir estaticamente o program_id
( aka endereço) do nosso programa Solana. Isso permitirá alguma segurança extra em nosso programa, uma cortesia do framework Anchor Anchor.
Essa linha de código deve estar em todos os programas Anchor (especificamente em lib.rs
) e por convenção logo abaixo das suas importações na parte superior do seu arquivo.
declare_id!("Fg6PaFpoGXkYsidMpWTK6W2BeZ7FEfcYkg476zPFsLnS");
Por padrão, a CLI Anchor (e em qualquer outro lugar que você receber exemplos de programas Anchor ) terá um program_id
definido com esta macro.
CUIDADO: Você deveria SEMPRE alterar o valor interno se o código-fonte local for o endereço do arquivo-chave usado para implantar seu programa ( mais sobre isso em um bit ).
A lógica principal do nosso programa Solana
Em seguida, estamos criando um módulo público nomeado program_name
com o program
attribute colocado nele.
Sem trocadilhos, mas vamos descompactar essa afirmação.
#[program]
pub mod program_name {
use super::*;
pub fn initialize(_ctx: Context<Initialize>) -> Result<()> {
Ok(())
}
}
Nosso "módulo" público atuará como o contêiner para a execução primária de código dentro do nosso programa. Mais ou menos como funções e métodos fazem em outras linguagens.
O atributo program
é definido especialmente por Anchor. Não apenas lidará com muitos dos boilerplates tradicionalmente escritos em Programas Solana vanilla, mas também adicionará algumas verificações básicas de segurança ao nosso programa.
Então, de certa forma, você pode pensar em definir nosso módulo com o program
attribute definindo a função main()
, mais ou menos como em outras linguagens estaticamente tipadas.
use super::*;
Em seguida, trazemos todas as bibliotecas importadas do atributo program
em nosso escopo local dentro de nosso módulo program_name
.
pub fn initialize(_ctx: Context<Initialize>) -> Result<()> {
Ok(())
}
Finalmente definimos uma muito simples função initialize
que podemos usar para realmente executar código na blockchain Solana (por meio de uma chamada RPC ).
Para programas Anchor, todas as funções de endpoint terão um ou mais parâmetros. O primeiro parâmetro será sempre um Context
do struct
desejado e definido no seu programa Solana. Você pode adicionar mais parâmetros para as suas funções conforme necessário para o seu programa.
Você pode ler mais sobre o context Anchor na documentação da linguagem Anchor. Mas a essência é que esse context nos dará uma maneira muito conveniente de ler as contas enviadas para nossas funções.
Também estamos afirmando que nossa função sempre retornará um tipo Result
quando estiver completo (ou seja, apenas 2 resultados possíveis). Isso permitirá nossa função initialize
retornar um Ok (( ))
quando for bem-sucedido e um Err( )
quando ocorrer um erro.
Todas as funções do programa Solana são necessárias para retornar um Result
de algum tipo. O resultado Ok
é tipicamente um valor em branco de ()
, enquanto o Err()
pode ter qualquer erro que você como desenvolvedor decidir retornar. Muitas vezes, os desenvolvedores definem um struct
específico para criar erros padrão / reutilizáveis. Eu recomendo fortemente fazer o mesmo, especialmente se você quiser tornar público seu código fonte. Pense nos outros, seja atencioso!
Defina nosso básico Struct
Como apontei anteriormente, precisamos definir um struct
para ser usado por nossos Context
. Essa estrutura informará ao Anchor as contas esperadas que serão fornecidas para sua função. E como o tempo de execução do Solana requer uma lista completa de todas as contas, uma execução do programa vai interagir com o Anchor, podendo fazer algumas coisas úteis.
#[derive(Accounts)]
pub struct Initialize {}
Neste exemplo específico, nossa função initialize
não interage com nenhuma outra conta Solana, portanto nosso Initialize
e struct
podem permanecer efetivamente vazios.
Também estamos usando o macro derive(Accounts)
Anchor para adicionar alguns auxiliares de desserialização em nossa estrutura Initialize
.
Discutirei mais sobre esses tutoriais posteriores quando realmente os usarmos, mas você pode ler sobre isso de macros Accounts
no Anchor na documentação da linguagem rust
Este artigo foi escrito por Nick Frostbutter e traduzido por Adriano P. de Araujo. O original em inglês pode ser encontrado aqui.
Oldest comments (0)