solana開発入門 備忘録 ~基本概念と開発ツールのまとめ~

# まえがき
solanaがイケてるという情報を得て飛びついて学習を始めた。
入門に際して学んだ情報を本記事でまとめます。

間違いや修正補足についてコメントや編集リクエスト大歓迎です。

# 特徴

https://solana.com/ja

- C,C++,Rustで構築可能。
- Ploof of History(PoH)というコンセンサスアルゴリズムを採用
    - ざっくりいうとノード同士が同期をしないため、通信性能がボトルネックにならず、トランザクションがめちゃくちゃ高速
    - 3,455 トランザクション/sとのこと。めちゃくちゃ早え
        - [Ethereumがだいたい10~15くらい](https://blockchair.com/ja/ethereum/charts/transactions-per-second)
    - ガス代も1トランザクションあたり$0.00025と非常に安い
      
- 最近はEthereum系のトークンと互換性を持てるようになった模様 https://defipocket.jp/index.php/defi/portal/982/

# 基本的な概念・用語

下記のドキュメントが通読をおすすめ。

https://docs.solana.com/

## Account

Linuxなどのファイルに似た、ステータスの格納やスマートコントラクトの実装を行うもので、
Solana上ではロジックやデータの状態などはすべてアカウントとして表現する。
アカウントは256ビットの公開鍵文字列を自身のアドレスとして持ち、この値を持ってアカウントを一意に特定する。

実装は下記。

https://github.com/solana-labs/solana/blob/master/sdk/src/account.rs

以下は基本的なフィールド。

| フィールド名 | 説明 |
|:-:|:-:|
| lamports | アカウントが所有するlamportsの額。rentがここから支払われる。0になったアカウントは削除される。 |
| data | 保持しているデータ  |
| owner  | このアカウントを所持するプログラムアカウントのアドレス(公開鍵) |
| executable  | trueの場合、プログラムアカウントである。 |
| rent_epoch  | rentを次に支払うまでの期間 |

c.f. epochについて
https://stackoverflow.com/questions/72952040/what-is-an-epoch-in-solana

アカウントには大まかな分類として２種類ある。

- データアカウント 
    - 文字通りデータを格納する。原則は10MBまでの制限がある。
    - solanaではProgram(スマートコントラクト)はステートレスであり、永続化するデータはデータアカウントに保存する。
    - 所有者のみ、lamportsの減額とdataの変更が可能。
- プログラムアカウント
    - 他のブロックチェーンでいうところのスマートコントラクトに当たる。Programもアカウントである。
    - 基本的にアップグレード権限のあるアカウントからしか変更できない
        - 逆に言うとEthereumと違い、デプロイ済みでも変更の手段がある(データを分離しているため？)

Solanaはデータとロジックがデータアカウントとプログラムアカウントに分離されており、
スマートコントラクトはすべてステートレスである。

## Program

プログラムアカウントは二種類に分けられる。

- ネイティブプログラム
    - [Solanaのコアに組み込まれているプログラム](https://docs.solana.com/developing/runtime-facilities/programs#system-program)
        - 新しいアカウントの生成と所有を行うシステムプログラム、プログラムのデプロイ実行などの役割を担うBPF Loaderなど
- オンチェーンプログラム
    - こちらがいわゆる「スマートコントラクト」である。
    - 誰でもプログラムを作成、デプロイが可能であるほか、Solana Labsが展開している[SPL](https://spl.solana.com/)と呼ばれるライブラリ群がある
        - 特に、FT/NFTの実装があるToken Programはネット上のサンプルでも頻出
   
C,C+,Rustで実装でき、一番よく見る例としてはRust。
基本的には下記のようなアーキテクチャを取る

| フィールド名 | 説明 |
|:-:|:-:|
| lib.rs | モジュールの登録 |
| entrypoint.rs | プログラムへのエントリポイント  |
| instruction.rs  | プログラム API、命令データのシリアライズ、デシリアライズ |
| processor.rs	  | プログラムロジック |
| state.rs  | プログラムオブジェクト、シリアライズ、デシリアライズのステータス |
| error.rs  | プログラム固有のエラー |

entrypoint.rsが最初に呼び出されその引数はprocesser.rsに渡される。
processor.rsはinstruction.rsとstate.rsを通して引数やアカウントの状態のシリアライズ、デシリアライズを行い、
処理を実行する。

## Transaction/Instruction

インストラクションは最小の命令単位でそれぞれがプログラムに紐づいて処理を実行する。
複数のインストラクションをトランザクションに含めることができ、トランザクションをクラスタに送信することでプログラムの呼び出しが行える。

各インストラクションは目的となっているprogram id、読み書きするアカウントなどを指定し、
トランザクションはそれらインストラクションと書き換えを想定したアカウントに対する署名を指定する。

lamportsの減額やdataの書き換えにはそのアカウントの所有者の署名が必要。
つまり、アカウントのアドレスとなっている公開鍵に対応する秘密鍵を持っていることを証明する必要がある。

トランザクションの実行には手数料(いわゆるガス代)が必要。
solanaではbitcoinやEthereumのように手数料の上乗せによるトランザクションの優先実行の仕組みはなく、
署名の数(とそれに設定された金額)と使用された計算資源を基に手数料が計算される。



## PDA

これ単体で重たいテーマなので、別の記事を書きました。

https://qiita.com/PoKoPoKoTa2ry/items/f27cb96082aa31655b23

# 開発ツール群

## Anchor

https://www.anchor-lang.com/

インストラクションの項で触れたが、素のsolanaプログラムではシリアライズデシリアライズなども書かなければならず、
かなりつらい。
Anchorはそうしためんどうな実装を隠蔽してくれるため、簡易かつ効率的に開発が可能。
solana開発におけるデファクトとなっており、本格的な実装となれば採用したい。


## SOLPG(Solana Playground)

solana版 Remix
ウォレットの作成や接続、先述したAnchorのインポートやDevnetへのデプロイも可能で、
写経などでは特にこだわりがなければこちらを利用するのがよいだろう。

https://beta.solpg.io/


## Metaplex

solanaでのNFT向け開発ツール

https://www.metaplex.com/

# あわせて確認したい情報&この記事の参考文献

https://github.com/solana-labs

https://docs.solana.com/

https://solanacookbook.com/

https://docs.metaplex.com/

https://paulx.dev/blog/2021/01/14/programming-on-solana-an-introduction/

https://www.alchemy.com/overviews/solana-developer-tools