LINE Blockchain Developers APIをつかってみた

本投稿は TECOTEC Advent Calendar 2021 の1日目の記事です。

どうも、次世代デジタル基盤開発事業部(旧ブロックチェーン事業部)の土田です。

アドベントカレンダー1日目はLINE Blockchainについてのハンズオン的な記事にしてみます。お手柔らかに。

概要

ローカルPC上にLINE Blockchain Developers SDKを利用したAPIを作り、LINE Blockchain Developers APIの使い方を学びつつ、ブラウザ上でLINE BITMAX WALLETにアクセスして操作したNFTを確認していきます。

環境

著者環境は下記の通りです。

Windows10
WSL2(Windows Subsystem for Linux)
Ubuntu 20.04
Node.js v16.4.2

package.json抜粋

"dependencies": {
    "@line/lbd-sdk-js": "^1.0.2",
    "body-parser": "^1.19.0",
    "express": "^4.17.1"
  },
"devDependencies": {
    "@types/express": "^4.17.13",
    "@types/node": "^16.11.9",
    "ts-node": "^10.4.0",
    "typescript": "^4.5.2"
 }

APIについては、LINE公式のSDKを使います。

github.com

1.LINE Developersの準備

LINE Developersにアクセスし、プロバイダー、チャンネルを作成しましょう。公式ドキュメントに従えば特に困らないはずです。

https://docs-blockchain.line.biz/ja/service-tutorial/Step1?id=step1-0docs-blockchain.line.biz

登録後、「LINE Blockchain Developersに移動」ボタンがあると思いますので、押下してそのままLINE Blockchain Developersコンソールに移動します。

2.LINE Blockchain Developersの準備

プロバイダー、チャンネルが登録できたら、サービスを登録します。こちらも公式ドキュメントが充実していますので、そのまま進めば問題ないと思います。

https://docs-blockchain.line.biz/ja/service-tutorial/Step1?id=step1-1docs-blockchain.line.biz

公式ドキュメントのNoteに重要なことが書いてありますので、そこだけ気をつけて下さい!

例えば、

  • API SecretWallet secretは一度発行すると再確認できません。(リセットは可能です)
  • owner walletは変更できません。

3.テストユーザーの登録

公式ドキュメントは下記ですが、基本的にテストユーザーは初回登録になると思いますので、UserIDを確認する必要があります。今回はLINE Developersコンソールに登録したUserIDを使ったので、コンソール上で確認できます。

https://docs-blockchain.line.biz/ja/how-to/add-test-users?id=テストユーザーの登録方法docs-blockchain.line.biz

一般ユーザーの場合

実はドキュメントをよく読まずに、LINE Developers APIでUserIDを取得する方法も確認したので、備忘のため残します。

①.LINEプラットフォームから認可コードを取得

developers.line.biz

②.アクセストークンを発行

リクエストボディに①で取得した認可コードが必要です。

developers.line.biz

③.ユーザープロフィールを取得

リクエストヘッダに②で取得したアクセストークンが必要です。

developers.line.biz

4.ウォレットをテストネットに接続

ウォレットのテストネットへの接続はLINE BITMAX WALLETにブラウザからアクセスして設定します。

wallet.bitmax.me

テストネットへの接続方法はドキュメントが分かりづらく、サービスチュートリアルの途中にあります。

https://docs-blockchain.line.biz/ja/service-tutorial/Step4?id=step4-2docs-blockchain.line.biz

ブラウザからアクセスするとこのような画面になると思います。

f:id:teco_tsuchida:20211130093434p:plain

「その他」タブを押下し、

f:id:teco_tsuchida:20211130093437p:plain

「設定」を押下し、

f:id:teco_tsuchida:20211130093439p:plain

「Realnetモード」をオフにします。

f:id:teco_tsuchida:20211130093447p:plain

ロゴの横にtestnetと付けばOKです。(TestCoinを送った後のスクリーンショットなので、TestCoinも確認できています。)

f:id:teco_tsuchida:20211130093450p:plain

5.アイテムトークン(NFT)を登録する

NFTの登録はAPIからも可能ですが、今回はコンソールから登録します。公式ドキュメントに従って進めて下さい。

https://docs-blockchain.line.biz/ja/service-tutorial/Step2?id=step-2.non-fungibleアイテムトークンを作成するdocs-blockchain.line.biz

こんな感じで登録しました。

f:id:teco_tsuchida:20211130093904p:plain

6.NFTをmint(鋳造)する

mintはAPIで行う必要があります。今回は直接ユーザーウォレットにmintしてみます。設定値はそれぞれの環境で置き換えて下さい。

import express from 'express'
import bodyParser from 'body-parser'
import * as devSdk from '@line/lbd-sdk-js';

const app: express.Express = express()
app.use(bodyParser.urlencoded({
    extended: true
}));
app.use(bodyParser.json());

app.listen(3000, () => {
    console.log("Start on port 3000.")
})

const BASE_URL = "https://test-api.blockchain.line.me"
const SERVICE_API_KEY = ""
const SERVICE_API_SECRET = ""
const httpClient = new devSdk.HttpClient(BASE_URL, SERVICE_API_KEY, SERVICE_API_SECRET)

const OWNER_WALLET_ADDRESS = ""
const OWNER_WALLET_SECRET = ""
const CONTRACT_ID = ""

app.post('/api/line/mintNonFungibleToken', async (req: express.Request, res: express.Response) => {
    const name = req.body.name
    const meta = req.body.meta
    const toUserId = req.body.toUserId
    const tokenType = req.body.tokenType
    const request = new devSdk.NonFungibleTokenMintRequest(OWNER_WALLET_ADDRESS, OWNER_WALLET_SECRET, name, meta, undefined, toUserId);
    const response = await httpClient.mintNonFungibleToken(CONTRACT_ID, tokenType, request);
    if (response && response.responseData) {
        res.send(JSON.stringify(response.responseData));
    }
})

結果

POST /api/line/mintNonFungibleToken HTTP/1.1
Content-Length: 125
Content-Type: application/json
Host: localhost:3000
{
  "name":"OreOreMintedToken",
  "meta":"Meta",
  "toUserId":"指定したユーザーID",
  "tokenType":"指定したトークンタイプ"
}

HTTP/1.1 200 OK
x-powered-by: Express
{"txHash":"トランザクションハッシュ"}

応答されたtxHashを使ってエクスプローラーで確認すると、Successになっているはずです。

explorer.blockchain.line.me

先程テストネットに接続したウォレットにも届いています。

f:id:teco_tsuchida:20211130094231p:plain

7.NFTをtransfer(転送)する

次はmint済みのNFTをオーナーウォレットからユーザーウォレットへ転送してみます。NFTは先程mintした手順でオーナーウォレットにmintしておいて下さい。

app.post('/api/line/transferNonFungibleTokenOfWallet', async (req: express.Request, res: express.Response) => {
    const toUserId = req.body.toUserId
    const tokenType = req.body.tokenType
    const tokenIndex = req.body.tokenIndex

    const request = new devSdk.TransferNonFungibleTokenRequest(OWNER_WALLET_SECRET, undefined, toUserId);

    const response = await httpClient.transferNonFungibleTokenOfWallet(OWNER_WALLET_ADDRESS, CONTRACT_ID, tokenType, tokenIndex, request);
    if (response && response.responseData) {
        res.send(JSON.stringify(response.responseData));
    }
})

結果

POST /api/line/transferNonFungibleTokenOfWallet HTTP/1.1
Content-Length: 105
Content-Type: application/json
Host: localhost:3000
{
  "toUserId":"指定したユーザーID",
  "tokenType":"指定したトークンタイプ",
  "tokenIndex":"指定したトークンインデックス"
}

HTTP/1.1 200 OK
x-powered-by: Express
{"txHash":"トランザクションハッシュ"}

オーナーウォレットからユーザーウォレットへmint済みのNFTを送ることができました。

f:id:teco_tsuchida:20211130094457p:plain

出来ればユーザーウォレット間のNFT転送も試したかったのですが、テストユーザーの準備が間に合わなかったので割愛します。

8.NFTをburn(焼却)する

最後にburnも試します。ユーザーウォレットのNFTを操作する(transferやburnする)には管理権限の委任(プロキシ設定)が必要です。

公式ドキュメントは下記になります。

https://docs-blockchain.line.biz/ja/sample-services/Link-cinema?id=_3-プロキシを設定するdocs-blockchain.line.biz

流れは下記のようになります。

Tip

プロキシは、以下の3段階をすべて完了すると設定されます。
① プロキシ設定APIを呼び出し、LINE BITMAX Walletにリクエスト(サービス側で実行)
② 1のレスポンスとして受け取ったリダイレクトURIにより、LINE BITMAX Walletに移動した後、プロキシ設定を受け入れて認証(ユーザーが実行)
③ プロキシコミット(commit)APIを呼び出し、トランザクションをコミットし、txHashを受け取って確認の受け取りおよび確認(サービス側で実行)

また、アイテムトークンのプロキシ設定ですが、コントラクトID単位の認証になります。プロキシ設定は解除不可な為、一度実行すると以降はこの手順は不要になるようです。

https://docs-blockchain.line.biz/ja/api-guide/category-users?id=v1-users-userid-item-tokens-contractid-request-proxy-postdocs-blockchain.line.biz

①と③については下記で対応します。(一度プロキシ設定をした後なので、結果は取得していませんでした・・・。公式ドキュメントをチェックして下さい!)

// プロキシ設定APIを呼び出し、LINE BITMAX Walletにリクエスト
app.post('/api/line/issueItemTokenProxyRequest', async (req: express.Request, res: express.Response) => {
    const landingUrl = "http://localhost:8080"
    const userId = req.body.userId
    const requestType = devSdk.RequestType.AOA
    const proxyRequest = new devSdk.UserProxyRequest(OWNER_WALLET_ADDRESS, landingUrl)

    const response = await httpClient.issueItemTokenProxyRequest(userId, CONTRACT_ID, requestType, proxyRequest)
    if (response && response.responseData) {
        res.send(JSON.stringify(response.responseData));
    }
})

// プロキシコミット(commit)APIを呼び出し、プロキシ設定完了
app.post('/api/line/commitProxyRequest', async (req: express.Request, res: express.Response) => {
    const requestSessionToken = req.body.requestSessionToken
    const response = await httpClient.commitProxyRequest(requestSessionToken)
    if (response && response.responseData) {
        res.send(JSON.stringify(response.responseData));
    }
})

AOAからはこのように通知がきます。認証しておいて下さい。

f:id:teco_tsuchida:20211130101053p:plain

いよいよburnです。APIは下記です。

// 要プロキシ設定
app.post('/api/line/burnNonFungibleToken', async (req: express.Request, res: express.Response) => {
    const fromUserId = req.body.fromUserId
    const tokenType = req.body.tokenType
    const tokenIndex = req.body.tokenIndex

    const request = new devSdk.NonFungibleTokenBurnRequest(OWNER_WALLET_ADDRESS, OWNER_WALLET_SECRET, fromUserId);
    const response = await httpClient.burnNonFungibleToken(CONTRACT_ID, tokenType, tokenIndex, request);
    if (response && response.responseData) {
        res.send(JSON.stringify(response.responseData));
    }
})

結果

POST /api/line/burnNonFungibleToken HTTP/1.1
Content-Length: 107
Content-Type: application/json
Host: localhost:3000
{
  "fromUserId":"指定したユーザーID",
  "tokenType":"指定したトークンタイプ",
  "tokenIndex":"指定したトークンインデックス"
}

HTTP/1.1 200 OK
x-powered-by: Express
{"txHash":"トランザクションハッシュ"}

先程mint、transferしたNFTをburnしてみました。ウォレットから無くなったことが確認できます。

f:id:teco_tsuchida:20211130101331p:plain

おわり

いかがでしたか?!

公式ドキュメントも充実していて、さらにはサービスチュートリアルまであるので敷居が低くて良いですね。今後LINE Blockchainも様々なNFTやそれらを活用したサービスが出てくると思いますので、是非一度触ってみては!

アドカレ1日目でした。ここまでご覧いただき、ありがとうございました!

明日は弊社の偉い人が書くみたいです👀

www.tecotec.co.jp

その他参考

developers.line.biz docs-blockchain.line.biz