【LINE】開発してわかったミッションスタンプの落とし穴

## はじめに

LINEのAPIには様々な種類のサービスと[そのドキュメント](https://developers.line.biz/ja/docs/)があります。
その中には申請等を行うことで法人ユーザーが利用できる、[法人ユーザー向けオプション](https://developers.line.biz/ja/docs/partner-docs/)が存在します。

今回はこのオプションの中から[ミッションスタンプAPI](https://developers.line.biz/ja/docs/partner-docs/mission-stickers/)の実装における注意事項について解説していきます。

## ミッションスタンプとは

LINEユーザーに無料または条件付きで提供しているLINEプロモーションスタンプのうち、ミッションをクリアすることで取得できるスタンプになります。
[事例一覧](https://www.linebiz.com/jp/case-study/)も様々、公開されています。

また、ミッションスタンプにはさらにミッションの有無によって区分があります。

- LINEプロモーションスタンプとは
    - https://www.linebiz.com/jp/service/line-promotion-sticker/
- プロモーションスタンプの区分
    - https://www.loopass.net/column/blog20220614#overview

本記事ではスポンサードミッションスタンプを前提として記載していきます。

### 開発にあたって

ミッションスタンプの開発にあたっては、LINEより[ミッションスタンプ ガイドライン](https://www.linebiz.com/sites/default/files/media/jp/download/%E3%83%9F%E3%83%83%E3%82%B7%E3%83%A7%E3%83%B3%E3%82%B9%E3%82%BF%E3%83%B3%E3%83%95%E3%82%9A%E3%82%AB%E3%82%99%E3%82%A4%E3%83%88%E3%82%99%E3%83%A9%E3%82%A4%E3%83%B3.pdf)が公開されています。
このガイドラインにはミッションの種類や実装における仕様、大まかな実施の流れが記載されており、実装において必要な情報を知ることができます。

また、ミッションスタンプのAPIも[リファレンス](https://developers.line.biz/ja/reference/partner-docs/#mission-stickers)があります。

用意されているAPIは1つですが、そのAPIによってスタンプショップのダウンロードリンクを有効にすることができます。

![d2e5a657-ecc5-42d6-89c1-f265f0e5ebd1.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/224198/45554a96-dba3-22f8-26fb-38e602a88710.png)
*ボタンのラベルが変わっている様子。画像はガイドラインより

## 実装の注意事項

ここからは本題の実装時の注意点に関して下記の点について記載します。

- トークンの違いに注意する
- 友だち登録が必須なのでチャンネルに注意する
- キャンセル時の動作をガイドラインに合わせる
- ちょっと驚く、LINEブラウザ独特な動き
- ミッションスタンプを有効化してしまった...

### トークンの違いに注意する

まず注意することとしては、トークンの違いです。

ミッションスタンプにおいて利用するトークンは2種類存在します。
それぞれの項目については次項に記載していきます。ここでは私が誤解した点を記載します。

- [チャネルアクセストークン](https://developers.line.biz/ja/docs/messaging-api/channel-access-tokens/)
    - 発行するチャネル： Messaging APIチャネル、LINEログインチャネルなど
- [アクセストークン](https://developers.line.biz/ja/docs/line-login/managing-access-tokens/)
    - 発行するチャネル： LINEログインチャネル

![9f4a3cea-fc85-4fb4-a41a-7ab080391775.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/224198/aa4d1ea1-a7f2-c640-5d1b-73fa63f295b6.png)

[ミッションスタンプAPI](https://developers.line.biz/ja/reference/partner-docs/#send-mission-stickers-v3)のリファレンスにあるように、AuthorizationヘッダーにBearerトークンを指定します。
このBearerトークンには`channel access token`を使用します。

このチャネルアクセストークンとアクセストークンの関係性に注意が必要です。

アクセストークンの一種にチャネルアクセストークンがあるわけではありません。
```:誤解
チャネルアクセストークン ⊂ アクセストークン
```
あくまでも、アクセストークンとチャネルアクセストークンは別物となります。
```:正解
チャネルアクセストークン ≠ アクセストークン
```

アクセストークンはチャネルアクセストークンの代替にはなりません。
そのため、ミッションスタンプAPIを叩く際にはチャネルアクセストークンが必要になります。

#### チャネルアクセストークン

チャネルアクセストークンはチャネルごとに別物のトークンになります。
開発グループや利用グループごとに発行が想定されているものになります。

LINE Developersのコンソールでもチャネルアクセストークンを確認できます。
![1730e827-58b3-4857-a748-fb815433380a.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/224198/9ec315b4-bf55-8ded-f641-e493358f7aa6.png)
*Messaging APIチャネルに記載

ただし、画像に`(長期)`とあるように、このチャネルアクセストークンは新たに発行するまで期限切れにならないトークンです。
そのため利用は控えた方がよいでしょう。その代わりに別方法でチャネルアクセストークンを用意する必要があります。

それには[チャネルアクセストークンの種類](https://developers.line.biz/ja/docs/messaging-api/channel-access-tokens/#types-of-channel-access-tokens)に記載がある、[短期のチャネルアクセストークン](https://developers.line.biz/ja/reference/messaging-api/#issue-shortlived-channel-access-token)や[JWTを使って発行するトークン](https://developers.line.biz/ja/docs/messaging-api/generate-json-web-token/)を利用します。

#### アクセストークン

アクセストークンはLINEログインでユーザが認可作業をするとLINEから返ってくるトークンになります。
このアクセストークンは[LINEログインで取得する](https://developers.line.biz/ja/docs/line-login/managing-access-tokens/#get-user-access-token)以外に[SDKを使う](https://developers.line.biz/ja/docs/liff/developing-liff-apps/)ことで取得できます。

アクセストークンは[LINEログイン](https://developers.line.biz/ja/docs/line-login/)で利用するため、LINEログインチャネルを作成することになります。
![4dac9842-af31-4a64-a70d-56fdc3b2bb3f.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/224198/2c673c62-576b-5eaa-c774-4d7421bdbc9f.png)

### 友だち登録が必須なのでチャンネルに注意する

[ミッションスタンプ ガイドライン](https://www.linebiz.com/sites/default/files/media/jp/download/%E3%83%9F%E3%83%83%E3%82%B7%E3%83%A7%E3%83%B3%E3%82%B9%E3%82%BF%E3%83%B3%E3%83%95%E3%82%9A%E3%82%AB%E3%82%99%E3%82%A4%E3%83%88%E3%82%99%E3%83%A9%E3%82%A4%E3%83%B3.pdf)に```友だちにならないとミッション画⾯には
進めないように実装してください```と記載があるように、ミッションスタンプでは友だち登録が必須です。

友だち登録の状況を確認するため、前項に記載したアクセストークンを利用し、[友だち関係を確認するAPI](https://developers.line.biz/ja/reference/line-login/#friendship-status)を叩く必要があります。

```bash
curl -v -X GET https://api.line.me/friendship/v1/status -H 'Authorization: Bearer {access token}'
```

そのため、ミッションスタンプの施策ではミッションスタンプAPIの実行に必要なチャネルアクセストークンとアクセストークンの2つトークンが存在することに注意が必要です。

ただし、2つのトークンを用意することは、Messaging APIチャネルとLINEログインチャネルの2つが必要ということではありません。

ミッションスタンプの利用申請はどちらのチャネルからもできてしまいます。
[LINEログインチャネルでもチャネルアクセストークンの発行はできる](https://developers.line.biz/ja/reference/messaging-api/#issue-channel-access-token-request-body)ため、「LINEログイン」という名を冠したチャネルですがミッションスタンプAPIを実行できます。

そのため、どのチャネルでどのトークンを使って、LINE APIを実行するのか整理をしておくことをお勧めします。

※筆者は混同した結果、実装の修正に手間取りました...

### キャンセル時の動作をガイドラインに合わせる

ミッションスタンプの申請を進めていくと、スタンプパッケージIDの発⾏とそれを設定したチャネルでの挙動のテストを行うことになります。
この際、LINEログインでユーザが認可した後にリダイレクトされるCallback先を、ミッション画面にしている場合に注意が必要となります。

実装は下記の流れでした。

1. Callback先がバックエンドではなくフロントエンドのミッション画面に設定。
2. フロントエンド側で[認可の確認](https://developers.line.biz/ja/docs/line-login/integrate-line-login/#receiving-the-authorization-code-or-error-response-with-a-web-app)。
3. バックエンドにて認可コードを使ってアクセストークンの取得、友だち状況の確認を実施するためにフロントエンドからリクエスト
    4. 認可コードに誤りがあるなど、本来のアクセスと異なる場合にはリダイレクト。

ガイドラインの確認項目として、`認証画⾯の「キャンセル」ボタンを押すとスタンプショップ詳細画⾯に戻る（または適切なLPに遷移する）`というものがあります。
上記の実装場合、LINEログインでキャンセルを押した場合でも、まずはCallback URLにリダイレクトされます。何も制御されていないとミッション画面が表示されてしまいます。

このようなミッション画面で認可の確認をする実装にしている場合には、表示制御によってLPと同等のページを表示することでガイドラインに沿う形にできます。

![LINEログインで認証しなかった時の挙動](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/224198/3fa3807e-126f-1109-d5f3-3dd646b65cff.png)

また、次項でも記載しますが、スタンプショップ詳細画⾯にリダイレクト処理をした場合にはブラウザの同じタブ上では遷移せず、別タブで表示される挙動となります。

### ちょっと驚く、LINEブラウザ独特な動き

ミッションスタンプではLINEアプリからアクセスするため、LINE内部にあるLINEアプリ内ブラウザ（以降、LINEブラウザ）が起動、ミッション画面にアクセスします。

このLINEブラウザには他のブラウザとは異なる挙動があります。
例えば、ガイドラインのFAQにはBasic認証に関して記載があります。（ミッションスタンプガイドライン 2022.09版）
```
Q5.
本番チャネルでの動作確認の際、本番環境にベーシック認証を導⼊しても問題ないでしょうか︖
A.
LINEアプリ内ブラウザではベーシック認証の動作保証していないため、別⼿段での制御をお願い致します。
```

ここでは落とし穴というわけではありませんが、そうなるの？となった動きを紹介します。

スタンプショップ詳細画⾯に遷移した場合はLINEブラウザでページの遷移をするのではなく、別の画面として被さる形で表示されます。

下記のGIF画像がその時の動きです。（わかりやすくするために被さる動きの部分のみ動画速度を下げています。）
![上に被さるタブ.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/224198/57212bda-8494-8e38-4d9e-6ebc8f8a4dd6.gif)

LINEブラウザではリンクを押せば画面が同じタブ内で遷移するとは限らないようです。
そのため、特にLINEブラウザからLINEの他サービスにリンクで遷移する場合にはスマホでの確認をおすすめします。

### ミッションスタンプを有効化してしまった...

ミッションスタンプを有効化してしまったら、どうしようもないので気をつけましょうというお話です。

[ミッションスタンプAPIのリファレンス](https://developers.line.biz/ja/reference/partner-docs/#send-mission-stickers-v3)を見るとわかりますが、ミッションスタンプの利用を許可するAPIしかありません。
一度ミッションを達成し、ミッションスタンプの有効化をすると無効にできません。

ユーザがスタンプを無効化することはないのでAPIが用意されていないのも当たり前ですが、テストの時には困ったことになります。

申請を行う際にリリース前チェックを行う必要があります。（ガイドライン参照）
リリース前チェックはOS別に4パターンのテストがあります。

もし、本番環境の動作確認のついでにミッションスタンプを有効化してしまうと、リリース前チェックにそのアカウントは利用できません。
パターン別にLINEアカウントを用意する必要があるので動作確認を先にしてしまうと、後々アカウントが足りない、なんてことが起きるかもしれません。

※筆者はやらかしてしまったので、メンバーにリリース前チェックをお願いすることになりました・・・（ごめんなさい:bow:）

## おわりに

弊社でミッションスタンプの施策を実施した際に出会った開発時の注意点に関して解説しました。

法人ユーザー向けオプションというのもあるため携わる機会が少ないかもしれませんが、実施する際の手助けになれば幸いです。