Solanaアカウントモデル:テクニカルガイド
Learn how Solana's account model works: data storage, ownership rules, rent exemption, PDAs, and how it enables parallel execution.
この「Solanaアカウントモデル:テクニカルガイド」では、所有権、実行可能アカウント、トークンアカウント、レンタル免除、プログラム派生アドレス(PDA)、関連トークンアカウント(ATA)、およびプログラム間呼出し(CPI)を含む、プログラムが依存するランタイムフィールドとアクセスルールについて解説します。
レンタルの取り扱い、アカウントサイズの制限、クライアントAPIなどの実装の詳細は変更される可能性があります。開発者はデプロイ前に現在のSolanaドキュメントを確認し、最新のネットワークパラメータを照会する必要があります。
Solana上のすべてのトランザクションはアカウントに関わります。保持しているすべてのトークン、デプロイしたすべてのプログラム、ミントしたすべてのNFT、そのすべてがアカウントの中に存在します。Solanaのコードを一行でも書く前に、アカウントがどのように機能するかを理解することは、単なる背景知識ではなく、他のすべてを行うための必須条件です。
Solanaをファイリングキャビネットとして考えてみてください。各引き出しにはフォルダが入っており、すべてのフォルダにはラベル(アドレス)、内容物(データ)、残高の印、そして表紙には中身を編集する権限を持つプログラムを示す部署名が書かれています。Ethereumから移行する開発者であっても、Solanaのアーキテクチャを評価する研究者であっても、オンチェーンのステート管理に関する最初のメンタルモデルを形成している学生であっても、このガイドは、アカウントの構造、アカウントの種類、所有権のルール、レンタルの仕組み、プログラム派生アドレス(PDA)、Ethereumとの比較、そして実践で構築するための注釈付きコードまで、全体像を網羅しています。
Solanaアカウントモデル:テクニカルガイドの概要
Solanaアカウントモデルは、Solanaブロックチェーンのデータストレージおよびステート管理アーキテクチャです。トークン残高、プログラムロジック、ユーザーデータ、システム設定を含む、Solana上のすべてのステートは、一意の256ビットのパブリックキーで識別される個別の残高に保存されます。標準仕様については、Solanaの公式アカウントドキュメント)を参照してください。
Solana上のすべてのステートはアカウント内に存在します。プログラムは自身のデータを保存しません。プログラムは実行中に渡されたアカウントの読み書きを行います。この単一のアーキテクチャ上の決定が、Solanaの設計を他のほとんどのブロックチェーンと分かつ点です。
ファイリングキャビネットの例えは、データ構造に直接当てはまります。キャビネットはSolanaブロックチェーン、フォルダはアカウント、各フォルダのラベルはパブリックキー(オンチェーンアドレス)、フォルダの中身はデータフィールド、残高の印はlamportsフィールド、そして表紙にある部署の印はどのプログラムが書込み権限を持っているかを記録する所有者(owner)フィールドです。その印にある部署名のみが、中身を変更することができます。
Ethereumの経験がある方にとって、この違いは重要です。Ethereumのスマートコントラクトは自身のステート(状態)を内部に保存しますが、Solanaプログラムはステートレスです。完全な比較は、以下の専用セクションで行います。
Solanaアカウントの構造
SOL、プログラムコード、またはアプリケーションのステートを保存するかどうかにかかわらず、すべてのSolanaアカウントは同じ5つのフィールドで構成されています。
すべてのSolanaアカウントが持つ5つのフィールド
Solana上のすべてのアカウントは、それぞれ異なる機能を持つ正確に5つのフィールドを保持しています。コードを確認する前に、これらのフィールドを平易な言葉で理解しておくことで、技術的な詳細がはるかに吸収しやすくなります。
lamports: このアカウントのSOL残高で、Lamports(Solanaの最小単位、次のセクションで説明)で表されます。ファイリングキャビネットの例えでは、これはフォルダの表紙に刻印された金銭的価値にあたります。
data: 所有プログラムが必要とするあらゆるステートを保存する生のバイト配列(Vec<u8>)です。プログラムアカウントの場合、このフィールドにはコンパイルされたBPFバイトコードが保持されます。データアカウントの場合、シリアル化されたアプリケーションのステートが保持されます。プログラムは独自のシリアル化形式(一般的にはBorsh)を定義して、このフィールドに対して構造化されたデータの読み書きを行います。ファイリングキャビネットの例えでは、フォルダの中にある物理的な内容物にあたります。
owner: このアカウントのデータフィールドを変更することを許可されたプログラムのパブリックキーです。他のプログラムは書き込むことができません。これはフォルダの表紙にある部署の印です。
executable: ブーリアンフラグです。trueに設定されている場合、アカウントはプログラムコードを保存し、実行可能です。falseの場合、アカウントはデータコンテナです。
rent_epoch: かつてレンタルの回収タイミングを追跡していたレガシーフィールドです。このフィールドは非推奨となっており、本番環境の標準であるレンタル免除アカウントにとっては運用上の重要性はありません。
各Solanaアカウントは、ed25519キーペアから派生した一意の256ビットのパブリックキーによって識別され、これがアドレスとオンチェーン識別子の両方の役割を果たします。単一アカウントの最大データフィールドサイズは、最近のプロトコルアップグレード時点で10MBです。この値はSolanaの歴史の中で変更されてきたため、現在の制限についてはSolanaのアカウントドキュメント,)で確認してください。
Lamports:Solanaの最小単位
LamportはSOLの最小単位です。1 SOLは1,000,000,000 Lamports(10⁹)に相当します。このユニット名は、現代の分散コンピューティング理論の基礎となる分散システムとフォールトトレランスの研究を行ったコンピュータ科学者レスリー・ランポートにちなんで名付けられました。Lamportsが存在するのは、レンタルの計算、取引手数料、アカウント残高を含むすべてのオンチェーン算術演算において、浮動小数点精度のエラーを避けるために整数演算を使用する必要があるためです。値をLamportsで表現することで、すべての計算が正確になります。
Solanaアカウントはウォレットと同じか?
Solanaアカウントとウォレットは同じものではありません。あなたがウォレットだと思っているもの(スマートフォンのPhantomやSolflareアプリなど)は、プライベートキーを管理するオフチェーンのソフトウェアです。オンチェーンの実体は、SOL残高を保持するシステムアカウントです。ウォレットはシステムアカウントを制御するのであって、ウォレット自体がアカウントなのではありません。トークンアカウント、プログラムアカウント、データアカウントにはウォレットに相当するものはなく、それらは純粋なオンチェーンのデータコンテナであり、コンシューマー向けのウォレットアプリケーションが直接表現するものではありません。
Solanaアカウントの種類
Solanaアカウントは4つのカテゴリに分類され、それぞれ所有プログラムと実行可能フラグによって定義されます。
- システムアカウント: システムプログラムによって所有され、SOLの保管やユーザーウォレットに使用されます。
- プログラムアカウント: コンパイルされたBPFバイトコードを保存する実行可能アカウントです。
- データ/ステートアカウント: プログラムによって所有され、アプリケーション固有のステートを保存します。
- トークンアカウント: SPLトークンプログラムによって所有される特殊なデータアカウントです(関連トークンアカウントが標準的なサブセットです)。
システムアカウント
システムアカウントはシステムプログラムによって所有されており、ユーザーウォレットはシステムアカウントです。システムプログラムは、新しいアカウントの作成(オンチェーンデータスペースの割り当て)、アカウント所有権の割り当て(ownerフィールドを指定されたプログラムに設定)、アカウント間のSOLの転送という3つのコアオペレーションを担当するSolanaのネイティブプログラムです。Solana上のすべての新しいアカウントは、システムプログラムが所有するシステムアカウントとして始まります。
システムプログラムは、よく知られたアドレス 11111111111111111111111111111111(base58で32個の1)を持っています。全インストラクションセットについてはシステムプログラムのドキュメント)を参照してください。開発者が自身のプログラム用にデータアカウントを作成する場合、システムプログラムの「Create Account」インストラクションを呼び出し、データサイズ、レンタル免除のためのLamport入金額、および新しい所有プログラムのパブリックキーを指定します。
プログラムアカウント
プログラムアカウントは、状態ではなく、コンパイル済みのBPFバイトコードを格納します。これらのアカウントの実行可能フラグはtrueに設定されています。プログラムはステートレスです。プログラムが実行されると、トランザクション命令を介して読み書きするためのアカウントのリストを受け取ります。呼び出し間で内部状態を維持しません。Ethereumから来た場合、オンチェーン実行可能コードをスマートコントラクトとして知っているかもしれませんが、Solanaプログラムは独自のステートを持たないため、根本的に異なる方法で動作します。プログラムアカウントは、BPFローダープログラムによって所有されます。デプロイ後、アップグレード権限キーペアがデプロイ中に指定されていない限り、プログラムアカウントは不変です。
データアカウントとステートアカウント
データアカウントは、プログラムが実行中に読み書きするアプリケーションの状態を保持します。これらのアカウントの実行可能フラグはfalseです。データフィールドには、Borshでシリアライズされたプログラム定義の状態が格納されます。例としては、DeFiプロトコルでのユーザーの貸付ポジション、NFTメタデータ、またはアプリケーションカウンターなどがあります。オーナープログラムは、このアカウントのデータフィールドに書き込むことができる唯一のエンティティであり、このルールは所有権セクションで詳細に説明されています。
トークンアカウントと連動トークンアカウント
トークンアカウントはSPLトークンプログラムが所有するデータアカウントであり、それぞれが1つの特定のウォレットに対して1つの特定のトークンの残高を保持します。単一のウォレットアドレスは、保有するトークンの種類ごとに、複数のトークンアカウントを持つことができます。
連動トークンアカウント(ATA)は、特定の[ウォレットアドレス、ミントアドレス]ペアの正規のトークンアカウントです。ATAは、ウォレットアドレスとトークンミントアドレスをシードとして使用して、プログラム導出アドレス(PDA)として決定論的に導出されます。これにより、各ウォレットはトークンタイプごとに正確に1つの「公式」アカウントを持つことが保証されます。ATAは、PhantomやSolflareなどのウォレット、取引所、およびプロトコルで使用されている標準です。ウォレットUIでトークンを受信すると、それはそのトークンのATAに送信されます。
指定された[ウォレット、ミント]ペアに対してATAが存在しない場合、トークンを受信する前に作成する必要があります。作成には、レント免除のLamport入金が必要です。このため、一部のトランザクションでは、ウォレットUIに少額の「アカウント作成手数料」が含まれています。ATAの完全な仕様については、SPL連動トークンアカウントドキュメント. を参照してください。ATAはトークンアカウントですが、すべてのトークンアカウントがATAであるわけではなく、トークン関連プログラムのデバッグ時にはこの区別が重要になります。
アカウント所有権:Solanaはデータアクセスをどのように制御するか
Solanaにおけるアカウント所有権は、資産所有権の概念ではなく、書き込み権限のメカニズムです。
所有権ルール
アカウントのオーナープログラムのみがそのデータフィールドを変更できます。ユーザーがトランザクションレベルで何を承認したかにかかわらず、他のプログラムがそれに書き込むことはできません。AccountInfoのオーナーフィールドには、この権限を持つプログラムの公開鍵が格納されます。非オーナープログラムはデータフィールドを自由に読み取れますが、書き込みには指定されたオーナーであることが必要です。
システムプログラムは、アカウント作成時に所有権を割り当てます。開発者がプログラムのためにデータアカウントを作成すると、Create Account命令はそのオーナーフィールドをプログラムの公開鍵に設定します。所有権は再割り当てできますが、Assign命令を使用する現在のオーナープログラムのみが可能です。外部の当事者が一方的に所有権を譲渡することはできません。
オーナーと権限:重要な区別
オーナーと権限は、Solanaアカウント管理における2つの異なる概念です。オーナーとは、アカウントのオーナーフィールドに記録されているプログラムであり、データフィールドに書き込みができるプログラムを意味します。権限(または署名者)とは、アカウントのトランザクションに署名できるキーペアです。
トークンアカウントを例として考えてみましょう。あなたのウォレットのプライベートキーがトランザクションに署名します(あなたが権限者です)。しかし、SPLトークンプログラムがあなたのトークンアカウントのオーナーであり、データフィールドにあるあなたのトークン残高を修正できる唯一のエンティティです。トークンを移動するトランザクションを承認することはできますが、データフィールドへの実際の書き込みは、あなた自身ではなく、トークンプログラムによって実行されます。これらの2つの概念を混同すると、Solanaに慣れていない開発者のほとんどのアカウント所有権デバッグエラーが発生します。
実践における所有権:DEX の例
あるDEXプログラムは、直接所有するアカウントにのみ書き込むことができます。ユーザーのトークンアカウント(SPLトークンプログラムが所有しており、DEXではありません)からトークンを転送するために、DEXは直接そのアカウントに書き込むことができません。プログラムは、同じトランザクション内で他のプログラムを呼び出すことができます。これはクロスプログラム呼び出し(CPI)と呼ばれるパターンで、DEXがトークンプログラムにユーザーの代わりにトークンを移動するように指示することを可能にします。DEXは、ユーザーの署名された承認を提供してトークンプログラムにCPIを送信し、トークンプログラムがユーザーのトークンアカウントのデータフィールドへの書き込みを実行します。これは、プログラム所有権モデルがプログラム間インタラクションにどのように拡張されるかです。完全なウォークスルーについては、Solana開発者向けのクロスプログラム呼び出し(CPI)ガイドを参照してください。
アカウントレントとレント免除
Solanaのレントは、ストレージコストのメカニズムであり、定期的な手数料ではありません。
レントとは
レントは、オンチェーンストレージの価格設定におけるSolanaのメカニズムです。すべてのアカウントは、オンチェーンでアクティブであるために、データサイズに比例した最低限のSOL残高を維持する必要があります。競合他社のコンテンツがほとんど見逃している点:レントは実際には定期的な手数料ではありません。本番環境の標準はレント免除であり、約2年間のストレージ費用をカバーするのに十分なSOLを前払いして入金すると、アカウントはレント控除から永久に免除されます。デプロイされているアカウントの圧倒的多数がレント免除の下で運用されています。
レント免除:実用的な標準
レント免除は、すべてのデプロイされたSolanaアカウントの本番環境の標準です。レント免除の最低残高は、アカウントのデータサイズ(バイト単位)に約6,960 Lamportを乗算したものに、ゼロバイトアカウントの約890,880 Lamportの基本金額が加算されたものになります。
実例:100バイトのデータアカウントには、約890,880 + (6,960 × 100) = 1,586,880 Lamport、または約0.00159 SOLが必要です。これらの数値は概算であり、変更される可能性があります。現在の値は、Solana CLIコマンド solana rent <bytes> または Solanaレントドキュメント. で確認してください。レントをトランザクション手数料モデルに変換する提案された変更は、本稿執筆時点では有効になっていません。最新のプロトコル状況については、現在のドキュメントを参照してください。
アカウントがSOLを使い果たした場合、どうなるか
現在、アカウント作成は通常レント免除の資金調達を必要とします。開発者は、古いレント徴収動作に頼るのではなく、現在のRPC要件をクエリする必要があります。これが、アカウントが「削除」されるという懸念を引き起こす動作です。
レント免除アカウントは、ランタイムによって自動的に閉じられることはありません。本番環境のアカウントは常にレント免除しきい値まで資金が供給されているため、ガベージコレクションは影響しません。アカウントを意図的に閉じることは、別個の、意図的なパターンです。プログラムは、データアカウントを閉じてLamport入金を回収できます。例えば、DeFiプロトコルでは、貸付ポジションを閉じることで、そのポジションのデータアカウントに資金を提供したSOLがユーザーに返還されます。これは、非自発的な削除ではなく、一般的なプロトコル設計パターンです。
プログラム導出アドレス(PDA)の説明
プログラム導出アドレスは、特定の課題を解決します。それは、プログラムが対応するプライベートキーを持たない誰かによってアカウントを制御できるようにする方法です。
プログラム導出アドレスとは
**プログラム導出アドレス(PDA)**とは、SHA-256ハッシュを使用して、プログラムIDと1つ以上のシード値から導出された、決定論的に生成されたアカウントアドレスです。PDAは、意図的にed25519楕円曲線から外れた位置に配置されており、対応するプライベートキーが存在しないことを意味します。所有プログラムのみがPDAアドレスのアカウントのトランザクションに署名できます。完全な仕様については、SolanaのPDAドキュメント を参照してください。
Solanaの通常のすべてのアカウントアドレスはed25519楕円曲線上にあります。PDAは意図的にその曲線から外れています。オフカーブプロパティはバグではなく、数学的に秘密鍵の生成を不可能にする設計メカニズムです。人間、ハードウェアウォレット、キー管理システムであっても、PDAの秘密鍵を生成することはできません。なぜなら、曲線上にそのような鍵は存在しないからです。
PDAが重要な理由:プログラム制御の管理
秘密鍵が存在しないという結果として、所有するプログラムだけがPDAのトランザクションを承認できます。これにより、トラストレスなプログラム制御の管理が可能になります。プログラムは、秘密鍵を保護する人間を頼ることなく、アカウントに対する権限を保持します。プログラムのロジックが管理元であり、人間ではなく監査可能なコードです。
秘密鍵を保持する人がアカウントを制御する通常のキーペアアカウントと比較してください。鍵を紛失すると、アクセスは失われます。鍵が盗まれると、アカウントは侵害されます。PDAは、この依存関係を完全に排除します。プログラムのロジックが管理元となり、人間ではなく監査可能なコードとなります。
3つの実世界におけるPDAのユースケース
PDAは、Solanaプログラム全体で3つの繰り返しパターンで現れます。
DEX エスクローアカウント:分散型取引所プログラムは、スワップの両側が必要な条件を満たすまで、PDAでトークンを保持します。信頼できる仲介者がエスクローの秘密鍵を保持することはありません。プログラムのロジックがリリースを制御し、参加者はプロトコルのルール外で資金を引き出すことはできません。
個人がNFTコレクションのミント権限を「ラグプル」することはできません。NFTミント権限は、Metaplexプログラムがミントアドレスから派生したPDAを介してミントを制御することによって機能します。このPDAには秘密鍵が存在しないため、デプロイ後、コレクションのミントルールはプログラムコードのみによって強制されます。
プログラムは、集権型インデックスを維持することなく、ユーザーごとのデータをどのように保存するのでしょうか?ユーザーごとの状態ストレージは、[program_id, user_pubkey]から派生した一意のPDAを使用します。これにより、そのユーザーのゲームスコア、貸付ポジション、またはステーキング記録を保存するための、決定論的でユーザー固有のアカウントアドレスが生成されます。プログラムは、各ユーザーのデータがどこにあるかを常に把握しています。
findProgramAddress()およびcreateProgramAddressSync()関数は、候補アドレスをインクリメントするバンプシードでテストし、曲線から外れるまでチェックすることで、有効なオフカーブアドレスを見つけます。
PDAはいつ使用すべきか?
プログラムが人間の秘密鍵に依存することなくアカウントを制御する必要がある場合は、PDAを使用してください。アカウントの権限が人間ではなくプログラムロジックであるべき場合は、PDAを使用してください。このルールは、エスクローアカウント、プロトコルのボールト、ミント権限、およびプログラム自体が複数のユーザーにわたって所有および管理する必要があるすべての状態をカバーします。
Solana vs. Ethereum:アカウントモデルの比較
SolanaとEthereumのアカウントモデルの主な違いは、状態がどこに存在するかにあります。
Ethereumでは、スマートコントラクトはステートフルであり、コードと並んで内部に自身の状態を保存します。Solidityコントラクトは、Ethereum仮想マシン(EVM)によって管理されるコントラクトストレージ内に独自のマッピングと状態変数を保持します。Solanaでは、プログラムはステートレスです。すべての状態は、プログラムが実行中に読み書きする外部アカウントに存在します。EthereumがEVMでプログラムを実行するのに対し、SolanaはBPFベースのランタイムを使用し、トランザクションであらかじめ宣言されたアカウントに対してプログラムを実行します。
| 次元 | Solana | Ethereum |
|---|---|---|
| 状態ストレージの場所 | 外部データアカウント | 内部コントラクトストレージ |
| コード/データ分離 | 強制:プログラムはステートレス | 強制なし:コントラクトは自身の状態を保存 |
| アカウント作成 | 明示的:開発者がサイズ、lamports、オーナーを指定 | 暗黙的:EVMが内部でストレージを管理 |
| ストレージコストモデル | 借料免除:データサイズに比例したSOLの預け入れ | ガス料金:SSTORE操作あたりのコスト |
| 実行モデル | 並列(Sealevel):重複しないアカウントは同時に実行 | 逐次(EVM):一度に1つのトランザクション |
| 開発者の複雑さ | 高い:アカウント、所有権、借料を明示的に管理 | 低い:状態管理はEVMが処理 |
トレードオフは両方向に働きます。Ethereumのステートフルモデルは、開発者体験における真の利点をもたらします。つまり、よりシンプルなメンタルモデル、明示的なアカウント管理の不要さ、多くのユースケースでの認知負荷の低下です。開発者は、データアカウントのサイズ、借料免除の預け入れ、またはPDAの導出を考慮することなく、ERC-20コントラクトを記述してデプロイできます。
Solanaのステートレスモデルは、そのシンプルさと引き換えに、実行の並列性と関心の分離を実現します。すべてのトランザクションで必要とされるアカウント宣言は、Sealevelのスケジューリングアルゴリズムへの入力となり、このアルゴリズムは、競合しないトランザクションを同時に実行します。AptosやSuiのような他のレイヤー1ブロックチェーンは、リソースベースの状態分離の独自のバリアントを採用しており、それぞれ異なるトレードオフプロファイルを持っています。EthereumのアプローチもSolanaのアプローチも、どちらかが絶対的に優れているわけではありません。それらは、異なるワークロードに対して異なる設計優先順位を反映しています。
このアーキテクチャが重要な理由:Sealevelと並列実行
ステートレスプログラムは設計上の制約ではなく、並列実行を可能にするメカニズムです。
アカウントモデルの設計からパフォーマンスへの因果関係は以下のようになります。まず、Solanaプログラムはステートレスです。次に、プログラムは状態を持たないため、すべてのトランザクションは、実行が開始される前に、アクセスするすべてのアカウント(読み取りと書き込みの両方)を宣言する必要があります。第三に、Solanaの並列実行エンジンであるSealevelは、スケジューリングの前にこれらのアカウントアクセスリストを分析します。第四に、重複しないアカウントセットにアクセスするトランザクションは、互いにデータ依存関係を持たず、複数のプロセッサコアで同時に実行できます。第五に、その結果、毎秒数万件のトランザクションを処理できるネットワークが実現します。
Anatoly Yakovenkoは、並列トランザクション処理を明示的な目標としてSolanaのアーキテクチャを設計しました。プログラムロジックをアカウント状態から分離することが、それを可能にしています。アカウントモデルは、Proof of History(PoH)など、Solanaの他のアーキテクチャ上のイノベーションと連携して機能します。PoHがこのスループットにどのように貢献するかを理解するには、Solanaのアーキテクチャ解説におけるProof of Historyの仕組みを参照してください。
アカウントを使った構築:開発者実装
Solanaプログラムが操作するすべてのアカウントは、プログラムがそれに読み書きする前に、作成、資金調達、およびオーナーへの割り当てが必要です。
システムプログラムを使用したアカウントの作成
Solanaプログラムはシステムプログラミング言語であるRustで記述され、デプロイ前にBPFバイトコードにコンパイルされます。Solanaでアカウントを作成する手順は次のとおりです。各手順は、システムプログラムのCreate Account命令のパラメータに対応します。
from_pubkey: 作成を資金提供するアカウント(支払者)を識別します。new_account_pubkey: 新しいアカウントのアドレスを指定します。lamports: データサイズに基づいて借料免除残高を計算します。space: アカウントデータ用に割り当てるバイト単位のデータサイズを設定します。owner: このアカウントを所有および書き込みするプログラムの公開鍵を指定します。
// システムプログラムを使用して新しいデータアカウントを作成する
let create_account_ix = system_instruction::create_account(
&payer.pubkey(), // from_pubkey: このアカウントの資金提供者
&new_account.pubkey(), // new_account_pubkey: アカウントのアドレス
rent_exempt_balance, // lamports: 借料免除に十分な量
data_size as u64, // space: アカウントデータ用に割り当てられたバイト数
&program_id, // owner: このアカウントを制御するプログラム
);この命令はアカウントの所有権を確立します。実行後、program_idにあるプログラムのみがこのアカウントのデータフィールドに書き込むことができます。
Anchorフレームワークの使用
多くのSolanaプログラムはAnchorフレームワークで構築されており、アカウントの制約とプログラム命令を定義するための構造化されたマクロを提供します。フレームワークの完全なリファレンスについては、Anchorドキュメント)を参照してください。
// Anchor: #[derive(Accounts)] マクロを使用してアカウント制約を定義します
#[derive(Accounts)]
pub struct Initialize<'info> {
#[account(
init, // 存在しない場合はこのアカウントを作成します
payer = user, // ユーザーがレント免除デポジットを支払います
space = 8 + MyData::LEN, // 8バイトのディスクリミネーター + データサイズ
)]
pub my_account: Account<'info, MyData>, // 新しいデータアカウント
#[account(mut)]
pub user: Signer<'info>, // トランザクションの署名者および支払者
pub system_program: Program<'info, System>, // アカウント作成に必要
}Anchorはアカウント検証の定型処理を自動的に行い、命令ロジックの実行前に所有権と署名者ステータスを確認します。Anchorのマクロは、この記事全体で説明されているのと同じメカニズムの抽象化であるため、所有権エラーのデバッグやPDA構造の設計時には、基盤となるアカウントモデルを理解しておくことが引き続き必要です。
関連するSolanaアーキテクチャリソース
より短い実装パスを探している開発者は、開発者向けアカウントモデルガイドを使用できます。トークンプログラムの規約については、Solana Program Libraryの概要で説明されています。SOL価格ページ)とSOL/USDT現物市場)は、アカウントの所有権やプログラムの権限ではなく、市場へのアクセスに関連しています。
FAQ: Solanaアカウントモデル:技術ガイド
Solanaにおけるアカウントとは何ですか?
Solanaのアカウントは、一意の256ビットパブリックキーによって識別されるオンチェーンデータコンテナです。すべてのアカウントは、LamportsのSOL残高、データフィールド(プログラム状態またはバイトコードを保持するバイト配列)、オーナーフィールド(データを変更する権限を持つプログラムのパブリックキー)、およびアカウントがプログラムコードを格納しているかどうかを示す実行可能フラグを格納します。
Ethereumでは、スマートコントラクトはコードと並行して独自のステートを内部に格納します。Solanaでは、プログラムはステートレスであり、すべてのステートはプログラムが実行中に読み書きする外部アカウントに格納されます。この分離により、SolanaのSealevelランタイムは、重複しないアカウントアクセスパターンを検出し、複数のトランザクションを同時に実行できるようになり、大規模な並列処理が可能になります。
すべての本番Solanaアカウントはレント免除の閾値まで資金が供給されており、ストレージ料金が永続的に免除されます。レントは基盤となるメカニズムです。アカウントは、オンチェーンでアクティブであり続けるために、データサイズに比例した最小SOL残高を維持する必要があります。閾値を超えて資金が供給されているレント免除アカウントは、ランタイムによって自動的に閉じられることはありません。
プログラム派生アドレス(PDA)は、プログラムIDとシード値からSHA-256ハッシュを使用して決定論的に生成されたアカウントアドレスです。PDAはed25519楕円曲線から外れるため、対応するプライベートキーを持ちません。PDAアドレスのアカウントに署名できるのは、所有するプログラムのみであり、エスクローアカウント、ミント権限、ユーザーごとのステートストレージのための信頼性のないプログラム制御の管理を可能にします。
現在のアカウント作成は、一般的にレント免除の資金提供が必要です。開発者は、レガシーなレント収集の動作に依存するのではなく、現在のRPC要件をクエリする必要があります。適切にデプロイされた本番アカウントは、常にレント免除の閾値まで資金が供給されており、ランタイムによって自動的に削除されることはありません。プログラムは、DeFiプロトコルで一般的なパターンである、SOLデポジットを回収するためにアカウントを意図的に閉じることもできます。
LamportはSolanaブロックチェーン上のSOLの最小単位です。1 SOLは1,000,000,000 Lamports(10⁹)に相当します。分散コンピューティングのパイオニアであるレスリー・ラマポートにちなんで名付けられたLamportは、オンチェーンでのすべてのSOL残高、トランザクション手数料、およびレント計算に使用されます。Lamport単位で金額を表記することで、オンチェーンの算術演算でSOLの小数値を扱う場合に発生する浮動小数点精度エラーを回避できます。
System Programは、3つのコア操作を担当するSolanaのネイティブプログラムです。新しいアカウントの作成(オンチェーンデータスペースの割り当て)、アカウントの所有権の割り当て(オーナーフィールドを指定されたプログラムに設定)、およびシステムアカウント間のSOLの転送です。すべての新しいSolanaアカウントは、システムアカウントとして開始されます。開発者は、プログラムのデータアカウントをプロビジョニングするために、System ProgramのCreate Account命令を呼び出します。
Solanaには3つの主要なタイプのアカウントがあります。(1) System Accounts:System Programが所有し、SOL残高およびユーザーウォレットに使用されます。(2) Program Accounts:コンパイルされたBPFバイトコードを格納する実行可能アカウント。(3) Data/State Accounts:プログラムが所有し、アプリケーション固有のステートを格納します。Token Accountsは、SPL Token Programが所有するデータアカウントの特殊なサブセットです。
Solanaのアカウントモデルは、Ethereumの状態を持つモデルよりも事前の検討が必要ですが、その思考投資が並列実行を可能にしています。
- Solana上のすべてのステートはアカウント内に存在します。プログラムは、実行中に渡されたアカウントを読み書きし、内部ストレージではありません。
- すべてのアカウントには5つのフィールドがあります:lamports、data、owner、executable、およびレガシーなrent_epoch。
- オーナープログラムのみがアカウントのdataフィールドを変更できます。これがSolanaの主要なアクセス制御メカニズムです。
- 本番アカウントはレント免除の閾値まで資金が供給されており、ランタイムによって自動的にガベージコレクションされることはありません。
- プログラム派生アドレスは、プライベートキーを持たないオフカーブアドレスを使用することにより、信頼性のないプログラム制御の管理を可能にします。
- SolanaのSealevelランタイムは、非競合トランザクション間で宣言されたアカウントアクセスリストを分析することにより、トランザクション実行を並列化します。
この基盤上で構築する準備はできましたか?以下に進んでください:
- Solanaプログラムの仕組み:ステートレス実行の開発者ガイド
- Solanaプログラム構築のためのAnchorフレームワークガイド
- クロスプログラム呼び出し(CPI)の説明:Solanaプログラムがお互いを呼び出す方法
- SolanaアーキテクチャにおけるProof of Historyの仕組み
アカウントサイズ、レント計算、ランタイムの動作に関する最新のプロトコル仕様については、Solana公式アカウントドキュメントを直接参照してください。