
Lens Protocol クイックセットアップ|プロファイル作成からCollectNFTについて
このセクションでは、プロファイルを最初から作成し、投稿を公開し、収集した後、独自のカスタムモジュールを作成する方法について説明します。プロトコルと対話するために、 ethers、hardhat、およびtypescriptを使用します。
コアリポジトリを操作し、プロトコル全体をローカルのヘルメットネットワークにデプロイし、それと対話するためのカスタムタスクをいくつか記述します。リポジトリと環境のセットアップから始めましょう。
📘始める前にシステムにGitとDockerComposeをインストールする必要があります(これにより、開発マシン間の一貫性が維持され、OS /バージョン管理エラーが減少します!)
設定するには、最初にリポジトリのクローンを作成し、環境を設定し、最後にDockerコンテナをビルドして入力します。
前述のように、GitとDockerComposeが必要です。
1.リポジトリのクローンを作成します
$ git clone git@github.com:aave/lens-protocol.git
または、HTTPSを使用する場合:
$ git clone https://github.com/aave/lens-protocol.git
2..envファイルを作成します
(注:ローカル開発の場合は空白にすることができます!)
$ cd lens-protocol
$ touch .env
3. DockerComposeを起動します
$ docker-compose up
または、Linuxディストリビューションを使用している場合(何をしているのかを確認してください!):
$ sudo docker-compose up
4.Dockerコンテナを入力します
追加の端末を2つ開き、両方で次のコマンドを実行します。
$ docker-compose exec contracts-env bash
または、Linuxディストリビューションを使用している場合:
$ sudo docker-compose exec contracts-env bash
さて、次は、独自のローカルブロックチェーンを起動して、プロトコル全体をデプロイします。
プロトコルの展開
Hardhatを使用して独自のブロックチェーンを起動し、独自のレンズプロトコルをローカルに展開します。
独自のローカルブロックチェーンをスピンアップ
了解しました。DockerComposeで実行しているDockerコンテナで2つのターミナルを実行しています。最初のブロックチェーンを使用してローカルブロックチェーンを実行し、2番目のブロックチェーンを使用してプロトコルをデプロイします。
また、Hardhatを使用していることを思い出してください。これは、ローカルチェーンをわずか数秒で起動するための素晴らしいツールを提供し、事前に資金提供された模擬アドレスを多数備えており、楽しむことができます。
ブロックチェーンを開始します
Dockerコンテナに接続されている2つの端末のうち最初の端末:
$ npm run compile
$ npx hardhat node
これにより、すべてがコンパイルされ、Hardhatを使用してカスタムローカルブロックチェーンが起動されます。
プロトコルを展開する
Dockerコンテナに接続されている2つの端末のうちの2番目の端末:
$ npm run full-deploy-local
これにより、ローカルのハードハットネットワーク上でハードハットタスク(ディレクトリにあります)が実行されます。これが完了すると、新しくデプロイされたすべてのアドレスのリストが表示されます。リポジトリのルートディレクトリ内のファイルにもコピーされるため、書き留める必要はありません。full-deploytasksaddresses.json
舞台裏で何が起こっているかを確認したい場合は、最初の端末で実行されたすべてのトランザクションも表示されます。
その点で、これまでのところ、ローカルブロックチェーンをスピンアップし、プロトコル全体をそれにデプロイしました。プロファイルを作成して、それとの対話を開始する時が来ました!
プロトコルの一時停止を解除する
独自のカスタムHardhatタスクでプロトコルの一時停止を解除してください!
カスタムタスクの作成
リポジトリは、ディレクトリ内のすべてのタスクをインポートするように設定されています。つまり、ローカルデプロイメントとの対話を開始するために必要なのは、新しいタスクを作成することだけです。hardhat.config.tstasks/
ディレクトリにファイルを作成し、選択したエディタで開きます。最初にやりたいことは、いくつかのモジュールをインポートすることです。unpause.tstasks/
Hardhatタスクを使用しているため、Hardhatランタイム環境に注入されたインスタンスを使用できます。この特定のタスクにインポートする必要はありませんが、バックグラウンドで使用されます。また、タイプチェーンを使用します。これにより、デプロイされたコントラクトに接続できる便利なタイプスクリプトバインディングが作成されます。ethers
以下は、プロトコルの状態を設定する(つまり、一時停止を解除する)ために必要なすべてのインポートです。それぞれの使い方を説明します。
import { task } from 'hardhat/config';
import { LensHub__factory } from '../typechain-types';
import { ProtocolState, waitForTx, initEnv, getAddrs } from './helpers/utils';
📘タイプチェーンからのインポートが機能しません!これはおそらく、コントラクトをまだコンパイルしていないためです。次のコマンドでうまくいくはずです。$ npm run compile
次に、hardhatタスクを作成する必要があります(このファイルが存在する場合は、Hardhat構成ファイルに自動的にインポートされます)。実行される実際のコードは、タスクのプロパティのコールバック関数になります。customsetAction
task('unpause', 'unpauses the protocol').setAction(async ({}, hre) => {});
ローカル展開と対話する準備をする
了解しました。Hardhatタスクを作成しました。これで、署名者(トランザクションに署名して送信できるウォレット)をインスタンス化し、プロトコルとの対話を開始する必要があります。ローカルデプロイメントでは、挿入されたインスタンスに接続されたデフォルトの署名者を使用し、それらをさまざまなプロトコルロールに自動的にマップします。ethers
私たちの目的では、0インデックスのアカウントはデプロイヤー、1インデックスのアカウントはガバナンスアドレス、2インデックスのアカウントは財務省、3インデックスのアカウントは汎用ユーザーです。また、デプロイされたコントラクトのアドレスを知る必要があるため、 fsを使用してアドレスJSONファイルを読み取り、それも保存しましょう。
次の関数は同じタスクファイルにはありませんが、ファイルからインポートされます。それがどのように機能するかは注目に値します。./tasks/helpers/utils.ts
// NOTE: These functions are in tasks/helpers/utils.ts and imported into our task file!
export async function initEnv(hre: HardhatRuntimeEnvironment): Promise<SignerWithAddress[]> {
const ethers = hre.ethers; // This allows us to access the hre (Hardhat runtime environment)'s injected ethers instance easily
const accounts = await ethers.getSigners(); // This returns an array of the default signers connected to the hre's ethers instance
const governance = accounts[1]; // We'll use this signer to, for example, unpause the protocol
const treasury = accounts[2]; // This is the treasury address, which we won't use
const user = accounts[3]; // We'll use this signer as our general purpose user
return [governance, treasury, user];
}
export function getAddrs(): any {
const json = fs.readFileSync('addresses.json', 'utf8'); // Read the 'addresses.json' file
const addrs = JSON.parse(json); // Parse the JSON into an object
return addrs;
}
上記のヘルパー関数を呼び出して、タスクで必要なデータをフェッチします。ガバナンスとアドレスオブジェクトのみが必要です。
...
const [governance] = await initEnv(hre);
const addrs = getAddrs();
...
インスタンス化する必要がある最後のことは、コントラクト自体へのインターフェイスです。これを行うには多くの方法がありますが、インポートされたタイプチェーンバインディングを使用し、それをガバナンス署名者に接続することから始めます。 。
タスクのコールバック関数内に次の行を追加しましょう。
...
const lensHub = LensHub__factory.connect(addrs['lensHub proxy'], governance);
...
トランザクションの実行
これまでに、新しいHardhatタスクを作成し、署名者をインスタンス化し、契約へのインターフェイスをインスタンス化しました。トランザクションの送信を開始する準備が整いました。
プロファイルの作成を開始する前に、少しハウスキーピングを行う必要があります。これは、すべてが正しく設定されているかどうかを確認するための優れたテストとして役立ちます。
展開時に、プロトコルはデフォルトで一時停止されます。タスクのコールバック関数に次の行を追加して、一時停止を解除しましょう。
...
console.log(await lensHub.getState());
await waitForTx(lensHub.setState(ProtocolState.Unpaused));
console.log(await lensHub.getState());
...
通常、トランザクションを送信するだけでなく、ラッパーを使用していることに注意してください。これにより、トランザクションがマイニングされるのを待ってから続行することができます。
簡単な補足として、スマートコントラクトABI(Application Binary Interface)は、列挙型を通常の符号なし整数として扱います。これは、javascript / typescriptコードでも発生します。したがって、列挙型は舞台裏の整数のセットにすぎません。ProtocolState
要約
ファイルは次のようになります。unpause.ts
import { task } from 'hardhat/config';
import { LensHub__factory } from '../typechain-types';
import { ProtocolState, waitForTx, initEnv, getAddrs } from './helpers/utils';
task('unpause', 'unpauses the protocol').setAction(async ({}, hre) => {
const [governance] = await initEnv(hre);
const addrs = getAddrs();
const lensHub = LensHub__factory.connect(addrs['lensHub proxy'], governance);
console.log(await lensHub.getState());
await waitForTx(lensHub.setState(ProtocolState.Unpaused));
console.log(await lensHub.getState());
});
そして今、それは真実の瞬間です!先に進み、次のコマンドで実行します。
$ npx hardhat unpause --network localhost
うまくいけば、ターミナルに次の出力が表示されます。
2
0
これは素晴らしい!2はの値であり、0はの値です。ProtocolState.PausedProtocolState.Unpaused
次に、ユーザーをホワイトリストに登録して最初のプロファイルを作成するための新しいタスクを作成します。
プロファイルの作成
ローカルレンズ展開で本格的なプロファイルを作成してください!
カスタムタスクの作成
プロトコルの一時停止を解除するためのHardhatタスクを作成した前の手順と同様に、プロファイルを作成するための別のタスクを作成します。これにより、新しい投稿、コメント、ミラーをチェーン上で公開できるようになります。
まず、ディレクトリに新しいファイルを作成しましょう。次に、インポートするものがいくつかあります。create-profile.tstasks/
import { task } from 'hardhat/config';
import { LensHub__factory } from '../typechain-types';
import { CreateProfileDataStruct } from '../typechain-types/LensHub';
import { waitForTx, initEnv, getAddrs, ZERO_ADDRESS } from './helpers/utils';
さらに、タスクを作成し、次のように環境を初期化します。
task('create-profile', 'creates a profile').setAction(async ({}, hre) => {
const [governance, , user] = await initEnv(hre);
const addrs = getAddrs();
const lensHub = LensHub__factory.connect(addrs['lensHub proxy'], governance);
});
Lensはプロファイル作成者のホワイトリストを使用しているため、ガバナンス署名者が必要になります。先に進み、ユーザーをホワイトリストに登録しましょう。次に、楽しいものに飛び込んでプロファイルを作成できます!
...
await waitForTx(lensHub.whitelistProfileCreator(user.address, true));
...
プロファイルの作成
プロファイルを作成するためにユーザーをホワイトリストに登録しました。あとは、プロファイル自体を作成するだけです。まず、プロファイルの作成に必要な入力構造体を見てみましょう(から):contracts/libraries/Datatypes.sol
// NOTE: This struct is defined in the contracts/libraries/Datatypes.sol library
/**
* @notice A struct containing the parameters required for the `createProfile()` function.
*
* @param to The address receiving the profile.
* @param handle The handle to set for the profile, must be unique and non-empty.
* @param imageURI The URI to set for the profile image.
* @param followModule The follow module to use, can be the zero address.
* @param followModuleData The follow module initialization data, if any.
* @param followNFTURI The URI to use for the follow NFT.
*/
struct CreateProfileData {
address to;
string handle;
string imageURI;
address followModule;
bytes followModuleData;
string followNFTURI;
}
それが邪魔にならないように、先に進んで入力構造体を構築しましょう。プロファイルNFT受信者を自分自身(ユーザー)にし、ハンドルとURIをモック値にすることができます。また、誰でもフォローできるようにフォローモジュールは必要ありません。
...
const inputStruct: CreateProfileDataStruct = {
to: user.address,
handle: 'zer0dot',
imageURI:
'https://ipfs.fleek.co/ipfs/ghostplantghostplantghostplantghostplantghostplantghostplan',
followModule: ZERO_ADDRESS,
followModuleData: [],
followNFTURI:
'https://ipfs.fleek.co/ipfs/ghostplantghostplantghostplantghostplantghostplantghostplan',
};
...
最後に、トランザクションを送信する必要があります。コントラクトインスタンスをユーザーに接続し、上記の入力構造体を使用してトランザクションを送信します。いくつかのチェックも含まれるので、コンソールで機能したことがわかります。lensHub
...
await waitForTx(lensHub.connect(user).createProfile(inputStruct));
console.log(`Total supply (should be 1): ${await lensHub.totalSupply()}`);
console.log(
`Profile owner: ${await lensHub.ownerOf(1)}, user address (should be the same): ${user.address}`
);
console.log(
`Profile ID by handle: ${await lensHub.getProfileIdByHandle(
'zer0dot'
)}, user address (should be the same): ${user.address}`
);
...
要約
ファイルは次のようになります。create-profile.ts
import { task } from 'hardhat/config';
import { LensHub__factory } from '../typechain-types';
import { CreateProfileDataStruct } from '../typechain-types/LensHub';
import { waitForTx, initEnv, getAddrs, ZERO_ADDRESS } from './helpers/utils';
task('create-profile', 'creates a profile').setAction(async ({}, hre) => {
const [governance, , user] = await initEnv(hre);
const addrs = getAddrs();
const lensHub = LensHub__factory.connect(addrs['lensHub proxy'], governance);
await waitForTx(lensHub.whitelistProfileCreator(user.address, true));
const inputStruct: CreateProfileDataStruct = {
to: user.address,
handle: 'zer0dot',
imageURI:
'https://ipfs.fleek.co/ipfs/ghostplantghostplantghostplantghostplantghostplantghostplan',
followModule: ZERO_ADDRESS,
followModuleData: [],
followNFTURI:
'https://ipfs.fleek.co/ipfs/ghostplantghostplantghostplantghostplantghostplantghostplan',
};
await waitForTx(lensHub.connect(user).createProfile(inputStruct));
console.log(`Total supply (should be 1): ${await lensHub.totalSupply()}`);
console.log(
`Profile owner: ${await lensHub.ownerOf(1)}, user address (should be the same): ${user.address}`
);
console.log(`Profile ID by handle: ${await lensHub.getProfileIdByHandle('zer0dot')}`);
});
すべてが完了したら、あと1つだけ行う必要があります。次のコマンドを使用してタスクを実行しましょう。
$ npx hardhat create-profile --network localhost
すべてが順調であれば、次のような出力が得られるはずです。
Total supply (should be 1): 1
Profile owner: 0x92561F28Ec438Ee9831D00D1D59fbDC981b762b2, user address (should be the same): 0x92561F28Ec438Ee9831D00D1D59fbDC981b762b2
Profile ID by the handle: 1
おめでとう!プロファイルが正常に作成され、プロファイルNFTを受け取りました。今、可能性は無限大です。しかし、まだ終わっていません!次は、投稿の公開について掘り下げます。
投稿の公開
最初の投稿を公開し、そうすることで、好きなものを公開することを学びましょう!
カスタムタスクの作成
あなたは今ではそれに慣れていると確信しています。まず、tasks /ディレクトリにpost.tsという名前の新しいファイルを作成します。 また、通常のインポートと基本的な初期化も含まれます。また、EmptyCollectModuleを使用します。これにより、フォロワーは誰でも無料で投稿を永久に収集できます。ファイルは次のようになります。
import { task } from 'hardhat/config';
import { LensHub__factory } from '../typechain-types';
import { PostDataStruct } from '../typechain-types/LensHub';
import { getAddrs, initEnv, waitForTx, ZERO_ADDRESS } from './helpers/utils';
task('post', 'publishes a post')
.setAction(async ({}, hre) => {
const [governance, , user] = await initEnv(hre);
const addrs = getAddrs();
const emptyCollectModuleAddr = addrs['empty collect module'];
const lensHub = LensHub__factory.connect(addrs['lensHub proxy'], governance);
});
collectモジュールのホワイトリストへの登録
このプロトコルでは、ホワイトリストに登録されたcollectモジュールのみを投稿とコメントで使用できます(ミラーには収集モジュールが関連付けられていません)。そのため、空のcollectモジュールをホワイトリストに登録する必要があります。
...
await waitForTx(lensHub.whitelistCollectModule(emptyCollectModuleAddr, true));
...
投稿の作成
収集モジュールをホワイトリストに登録したので、投稿を作成する準備が整いました。プロファイルの作成と同様に、公開関数(この場合は、入力データ構造体のみを参照しています)を使用します。必要なデータ構造体は次のようになります(from ):post()contracts/libraries/Datatypes.sol
// NOTE: This struct is defined in the contracts/libraries/Datatypes.sol library
/**
* @notice A struct containing the parameters required for the `post()` function.
*
* @param profileId The token ID of the profile to publish to.
* @param contentURI The URI to set for this new publication.
* @param collectModule The collect module to set for this new publication.
* @param collectModuleData The data to pass to the collect module's initialization.
* @param referenceModule The reference module set for the given publication must be whitelisted.
* @param referenceModuleData The data to be passed to the reference module for initialization.
*/
struct PostData {
uint256 profileId;
string contentURI;
address collectModule;
bytes collectModuleData;
address referenceModule;
bytes referenceModuleData;
}
これで、入力構造体の構築に進む準備ができました。存在する唯一のプロファイルを所有しているため、プロファイルIDを1にする必要があります。コンテンツURIをモックすることができます。収集モジュールは、データを取得しない新しくホワイトリストに登録され、最後に、参照モジュールとそれに関連するデータフィールドは空になります。EmptyCollectModule,
これがどのように見えるかです:
...
const inputStruct: PostDataStruct = {
profileId: 1,
contentURI:
'https://ipfs.fleek.co/ipfs/plantghostplantghostplantghostplantghostplantghostplantghos',
collectModule: emptyCollectModuleAddr,
collectModuleData: [],
referenceModule: ZERO_ADDRESS,
referenceModuleData: [],
};
...
これで、トランザクションを実行する準備が整いました。プロファイルの作成と同様に、インスタンスを署名者に接続してトランザクションを送信します。確かに、ログを追加して、すべてが期待どおりに機能するようにします。lensHubuser
...
await waitForTx(lensHub.connect(user).post(inputStruct));
console.log(await lensHub.getPub(1, 1));
...
要約
post.tsファイルは次のようになります。
import { task } from 'hardhat/config';
import { LensHub__factory } from '../typechain-types';
import { PostDataStruct } from '../typechain-types/LensHub';
import { getAddrs, initEnv, waitForTx, ZERO_ADDRESS } from './helpers/utils';
task('post', 'publishes a post').setAction(async ({}, hre) => {
const [governance, , user] = await initEnv(hre);
const addrs = getAddrs();
const emptyCollectModuleAddr = addrs['empty collect module'];
const lensHub = LensHub__factory.connect(addrs['lensHub proxy'], governance);
await waitForTx(lensHub.whitelistCollectModule(emptyCollectModuleAddr, true));
const inputStruct: PostDataStruct = {
profileId: 1,
contentURI:
'https://ipfs.fleek.co/ipfs/plantghostplantghostplantghostplantghostplantghostplantghos',
collectModule: emptyCollectModuleAddr,
collectModuleData: [],
referenceModule: ZERO_ADDRESS,
referenceModuleData: [],
};
await waitForTx(lensHub.connect(user).post(inputStruct));
console.log(await lensHub.getPub(1, 1));
});
最後に、先に進んでタスクを実行しましょう。
$ npx hardhat post --network localhost
すべてが計画どおりに進んだ場合、コンソールは次のように出力するはずです。
[
BigNumber { _hex: '0x00', _isBigNumber: true },
BigNumber { _hex: '0x00', _isBigNumber: true },
'https://ipfs.fleek.co/ipfs/plantghostplantghostplantghostplantghostplantghostplantghos',
'0x0000000000000000000000000000000000000000',
'0x20Ce94F404343aD2752A2D01b43fa407db9E0D00',
'0x0000000000000000000000000000000000000000',
profileIdPointed: BigNumber { _hex: '0x00', _isBigNumber: true },
pubIdPointed: BigNumber { _hex: '0x00', _isBigNumber: true },
contentURI: 'https://ipfs.fleek.co/ipfs/plantghostplantghostplantghostplantghostplantghostplantghos',
referenceModule: '0x0000000000000000000000000000000000000000',
collectModule: '0x20Ce94F404343aD2752A2D01b43fa407db9E0D00',
collectNFT: '0x0000000000000000000000000000000000000000'
]
素晴らしい!これで確認できます。最初のプロファイルを作成し、最初の投稿を公開しました。さて、当然のことながら、私たちのプロフィールと投稿は少し孤独で、そこには空白があります。それでは、私たちのプロフィールをフォローして投稿を収集していきましょう!
次のプロファイル
あなたの孤独なプロフィールをフォローして、それを入手してくださいNFTをフォローしてください!
カスタムタスクの作成
あなたはドリルを知っています!まず、タスクを「」という新しいファイルに設定することから始めましょう。また、ユーザーに接続するためにをインポートして初期化することに注意してください。
follow.ts.FollowNFT__factorylensHub
import { task } from 'hardhat/config';
import { LensHub__factory, FollowNFT__factory } from '../typechain-types';
import { getAddrs, initEnv, waitForTx } from './helpers/utils';
task('follow', 'follows a profile').setAction(async ({}, hre) => {
const [, , user] = await initEnv(hre);
const addrs = getAddrs();
const lensHub = LensHub__factory.connect(addrs['lensHub proxy'], user);
});
プロファイルをフォローする
プロファイルを作成したときにフォローモジュールを使用しなかったことを思い出してください。これは、どのウォレットも心配することなくプロファイルをフォローできることを意味します。それでは、先に進んで、私たち自身のプロファイルに従ってみましょう:
...
await waitForTx(lensHub.follow([1], [[]]));
...
ここで行っていることを明確にするために、関数は2つのパラメーターを取ります。どちらも配列です。follow()
フォローするプロファイルIDの配列と...
対応するフォローモジュールに渡す任意のデータの配列。
この例では、IDが「1」のプロファイルをフォローし、フォローモジュールがないためデータを渡さないようにします。ネストされた角かっこが必要な理由(この奇妙なこと:)は[[]]、コントラクトによって両方の入力配列の長さが等しくなることが保証されるためです。配列に空のデータパラメータを1つ渡す必要があります。
最後に、ログを追加して、すべてが意図したとおりに機能したかどうかを確認しましょう。まず、次のNFTアドレスを取得します。次に、FollowNFT__factoryに接続して、関連するデータを取得します。
...
const followNFTAddr = await lensHub.getFollowNFT(1); // Retrieve the follow NFT for a given profile ID
const followNFT = FollowNFT__factory.connect(followNFTAddr, user); // Connect our typechain bindings
const totalSupply = await followNFT.totalSupply(); // Fetch the total supply
const ownerOf = await followNFT.ownerOf(1); // Fetch the owner of the follow NFT with id 1 (NFT IDs in Lens start at 1, not 0!)
console.log(`Follow NFT total supply (should be 1): ${totalSupply}`);
console.log(
`Follow NFT owner of ID 1: ${ownerOf}, user address (should be the same): ${user.address}`
);
...
要約
了解しました。もうすぐです。ファイル全体がどのように見えるかを見てみましょう。follow.ts
import { task } from 'hardhat/config';
import { LensHub__factory, FollowNFT__factory } from '../typechain-types';
import { getAddrs, initEnv, waitForTx } from './helpers/utils';
task('follow', 'follows a profile').setAction(async ({}, hre) => {
const [, , user] = await initEnv(hre);
const addrs = getAddrs();
const lensHub = LensHub__factory.connect(addrs['lensHub proxy'], user);
await waitForTx(lensHub.follow([1], [[]]));
const followNFTAddr = await lensHub.getFollowNFT(1);
const followNFT = FollowNFT__factory.connect(followNFTAddr, user);
const totalSupply = await followNFT.totalSupply();
const ownerOf = await followNFT.ownerOf(1);
console.log(`Follow NFT total supply (should be 1): ${totalSupply}`);
console.log(
`Follow NFT owner of ID 1: ${ownerOf}, user address (should be the same): ${user.address}`
);
});
ぼろぼろではないですよね?さて、私たちが待っていた瞬間...それを試してみましょう:
$ npx hardhat follow --network localhost
何も壊れていない場合(当然のことながら、プログラミングでよく起こります)、端末の出力は次のようになります。
Follow NFT total supply (should be 1): 1
Follow NFT owner of ID 1: 0x92561F28Ec438Ee9831D00D1D59fbDC981b762b2, user address (should be the same): 0x92561F28Ec438Ee9831D00D1D59fbDC981b762b2
大丈夫!プロファイルを追跡することができました。簡単にまとめると、独自のブロックチェーンを正常に起動し、プロトコルをローカルに展開し、プロファイルを作成し、投稿を公開し、プロファイルを追跡しました。かなり甘いですね 次のステップは投稿を集めることです!
Collect NFTの収集
壮大な投稿を集めて、おしゃれな新しいCollect NFTを手に入れましょう!
カスタムタスクの作成
先に進んで、collect.tsというファイルに新しいタスクを作成しましょう。このタスクでは、followタスクで行ったのと同じ初期化手順に従いますが、FollowNFT__factoryをCollectNFT__factoryに置き換えます。これは次のようになります。
import { task } from 'hardhat/config';
import { LensHub__factory, CollectNFT__factory } from '../typechain-types';
import { getAddrs, initEnv, waitForTx, } from './helpers/utils';
task('collect', 'collects a post').setAction(async ({}, hre) => {
const [, , user] = await initEnv(hre);
const addrs = getAddrs();
const lensHub = LensHub__factory.connect(addrs['lensHub proxy'], user);
});
投稿の収集
さて、最初の投稿を収集する時が来ました!ミラーを収集すると、ミラーリングされた投稿/コメントが紹介とともに収集される場合を除いて、投稿、コメント、ミラーを収集できることに注意してください。
collect関数呼び出しをタスクに追加しましょう:
...
await waitForTx(lensHub.collect(1, 1, []));
...
同じページにいるので、この関数は3つのパラメーターを取ります。
収集しているパブリケーションを作成したプロファイルのプロファイルID(この場合は1)、
収集しているパブリケーションのパブリケーションIDと...
collectモジュールに渡す任意のデータ。
この状況では、最初のプロファイルから最初のパブリケーションを収集しているため、最初の2つのパラメーターは両方とも「1」です。次に、collectモジュールに渡したいデータがあります。パブリケーションのcollectモジュールはEmptyCollectModuleであり、データを必要としません(NFTに従ってプロファイルを保持している人からの収集が可能です)。 '空のバイト配列、または「[]」を渡します。
最後に、コンソールに情報をプリントして、すべてが意図したとおりに機能することを確認します。これで、CollectNFTができました。また、CollectNFTのURIが投稿のコンテンツURIに対応していることも検証します。これは次のようになります。
...
const collectNFTAddr = await lensHub.getCollectNFT(1, 1);
const collectNFT = CollectNFT__factory.connect(collectNFTAddr, user);
const publicationContentURI = await lensHub.getContentURI(1, 1);
const totalSupply = await collectNFT.totalSupply();
const ownerOf = await collectNFT.ownerOf(1);
const collectNFTURI = await collectNFT.tokenURI(1);
console.log(`Collect NFT total supply (should be 1): ${totalSupply}`);
console.log(
`Collect NFT owner of ID 1: ${ownerOf}, user address (should be the same): ${user.address}`
);
...
要約
大丈夫!もうすぐ着きます; collect.tsファイル全体がどのように見えるかを見てみましょう。
import { task } from 'hardhat/config';
import { LensHub__factory, CollectNFT__factory } from '../typechain-types';
import { getAddrs, initEnv, waitForTx } from './helpers/utils';
task('collect', 'collects a post').setAction(async ({}, hre) => {
const [, , user] = await initEnv(hre);
const addrs = getAddrs();
const lensHub = LensHub__factory.connect(addrs['lensHub proxy'], user);
await waitForTx(lensHub.collect(1, 1, []));
const collectNFTAddr = await lensHub.getCollectNFT(1, 1);
const collectNFT = CollectNFT__factory.connect(collectNFTAddr, user);
const publicationContentURI = await lensHub.getContentURI(1, 1);
const totalSupply = await collectNFT.totalSupply();
const ownerOf = await collectNFT.ownerOf(1);
const collectNFTURI = await collectNFT.tokenURI(1);
console.log(`Collect NFT total supply (should be 1): ${totalSupply}`);
console.log(
`Collect NFT owner of ID 1: ${ownerOf}, user address (should be the same): ${user.address}`
);
});
やるべきことが1つだけ残っています。
npx hardhat collect --network localhost
すべてが計画どおりに進んだ場合、端末の出力は次のようになります。
Collect NFT total supply (should be 1): 1
Collect NFT owner of ID 1: 0x92561F28Ec438Ee9831D00D1D59fbDC981b762b2, user address (should be the same): 0x92561F28Ec438Ee9831D00D1D59fbDC981b762b2
Collect NFT URI: https://ipfs.fleek.co/ipfs/plantghostplantghostplantghostplantghostplantghostplantghos, publication content URI (should be the same): https://ipfs.fleek.co/ipfs/plantghostplantghostplantghostplantghostplantghostplantghos
おめでとう!ウォークスルーのこの時点で、レンズプロトコルとのすべての重要な相互作用を完了することができました。プロファイルを作成し、それを操作して、物事が本来あるべき姿であることを検証しました。
今度は、まったく新しいフォローモジュールを作成して、プロトコルの上に構築することに移行します。