Open6

spotify連携メモ

さしもんさしもん

spotify iOS SDKについてメモをしていく

さしもんさしもん
  1. ダッシュボードでアプリを登録、設定
    https://developer.spotify.com/dashboard
    設定項目はApp Name/Redirect URIs/Bundle IDs/API Used

  2. ダッシュボードで設定した内容をプロジェクトへ反映
    App Name
    Bundle IDs
    info.plist系
    URL Types>URL Schems, URL Identifier
    Build Settings系
    Other Linker FlagsのValueに-ObjC
    Objective-C Bridging Header

この後から実際にコードを書いていく

  1. Set Up User Authorization
    3.1 Instantiate SPTConfiguration

A configuration class, holding the credentials provided for your app on the Spotify Developer Website

   3.2 Configure Auth Callback
       Spotifyへの認証が成功してURLスキームを使ってアプリに戻ってくることに成功するとappRemote.connectionParameters.accessTokenに取得したアクセストークンを設定する必要がある。

デバッグした感じだとアクセストークンが設定されるとデリゲートメソッドであるappRemoteDidEstablishConnectionが呼び出されている
Here we'll need to invoke a request to subscribe to player state update

  1. Set up App Remote
    4.1 Implement Remote Delegates
    4.2 Initialize App Remote
    App Remote is main entry point to interact with the spotify app. App Remote needs SPTConfiguration, initialized above, to instantiate.
    4.3 Configure Initial Music
    4.4 Authorizing and Connecting to Spotify

    We need to initiate authorization and connect to Spotify:

    Open Spotify app to obtain access token and start playback. The passed URI will start playing unless Spotify is already playing.
    YES if the Spotify app is installed and an authorization attempt can be made, otherwise NO. Note: The return BOOL here is not a measure of whether or not authentication succeeded, only a check if the Spotify app is installed and can attempt to handle the authorization request.

    Note

    /**
    * Attempts to connect to the Spotify application.
    *
    * @discussion If the Spotify app is not running you will need to use authorizeAndPlayURI: to 
       wake it up
    */
    - (void)connect;
    

    4.5 Subscribing to state changes
    we'll need to invoke the request to subsribe to the state changes in func appRemoteDidEstablishConnection(_ appRemote: SPTAppRemote).
    Inside playerStateDidChange, we can begin logging the output:

さしもんさしもん

認証

公式ドキュメントやらissueを読んでみた感じ
~認証は2種類あるみたい~

  • ~built-inされた認証機能を使う~
  • ~サーバーを用意して認証機能を自分で実装する~
    ~*参考~
    ~https://github.com/spotify/ios-sdk/issues/229~
    ~https://github.com/spotify/ios-sdk/issues/138~
    ~https://github.com/spotify/ios-sdk/issues/237~

違った

サーバーを用意して認証を行う場合のフロー(Swap)

  1. ユーザー認証の開始:
    アプリはSpotifyの認証画面を表示するためのリクエストを行う
    必要なスコープ(アクセス権限)を指定して、Spotifyにユーザー認証を求める

  2. Spotifyのログイン画面:
    ユーザーはSpotifyのログイン画面で認証を行う

  3. 認証コールバック:
    ログインが成功すると、Spotifyは設定されたRedirect URIを介してアプリにリダイレクトする
    この時、一時的な認証コードが付与される

  4. 認証コードの交換:
    アプリはこの認証コードをサーバーに送信します。
    サーバーは、この認証コードと、クライアントID、クライアントシークレット、そしてリダイレクトURIを使ってSpotifyにアクセストークンを要求
    Spotifyはアクセストークンとリフレッシュトークンをサーバーに返す

  5. アクセストークンの取得:
    サーバーはリフレッシュトークンを暗号化、その後アクセストークンとリフレッシュトークンをアプリに返す
    アプリはこのアクセストークンを使用して、SpotifyのAPIを呼び出し、音楽の操作などのアクションを行う

    参照: https://developer.spotify.com/documentation/ios/concepts/token-swap-and-refresh

アクセストークンの更新フロー(リフレッシュトークン)

アクセストークンは期限がある
期限が切れると、リフレッシュトークンを使って新しいアクセストークンを取得する
アプリはリフレッシュトークンをバックエンドサーバーに送信
サーバーはSpotifyに新しいアクセストークンを要求します。
新しいアクセストークンを取得したら、それをアプリに送り返す

さしもんさしもん

まとめ

Scopes let you specify exactly what types of data your application wants to
access, and the set of scopes you pass in your call determines what access
permissions the user is asked to grant.
For more information, see https://developer.spotify.com/web-api/using-scopes/.

  • Spotifyでの認証でどういった認証を行うのかクライアントアプリで定義する必要がありそう。
    ex).appRemoteControl, .playlistReadPrivateなど

  • プロダクトとして利用するならサーバー用意してRefreshTokenを使ってAccessTokenの更新を行うやり方の方が良さそう
    これはセキュリティの観点でもそうだし、あとはアクセストークンの有効期限が1時間ってことはRefreshTokenを使わない方法の場合、アクセストークンの有効期限が切れるたびにspotifyから一時的に得られる認証コードを取得する必要がありそう。そうなると毎回URLスキームが実行されそうで体験が悪そう
    そもそもリフレッシュトークンはアクセストークンを再発行してログイン状態を保持するためのものなんだろうか..

  • AccessTokenの有効期限は1時間だけど、RefreshTokenの有効期限については特に書かれてなさそう
    リフレッシュトークンの有効期限は数日とか?

  • ログインだけのサンプルアプリを試してみたけど結局認証を通せず
    *原因は俺のpcにありそう。以下が想定理由

アプリの動作: 実機上のアプリがSpotifyとの認証を行う。その際、認証コードとトークンの交換を行う必要がある
サーバーの役割: この認証コードとトークンの交換をサーバーで行う。今回はローカルにRubyサーバーを立ち上げてる

ネットワークの接続: iOS実機上のアプリがPC上のRubyのサーバーと通信するためには、両者の間のネットワーク接続が確立されている必要があるけど、pingコマンドで接続を確認したところ接続できてなさそうだった
だからアプリがPC上のサーバーと通信できず、認証フローが完了できないみたい
  • 認証通してそのまま自動で再生されてもいい場合はbuilt-inの認証機能でもいいけど
    認証を通したいだけならサーバーを建てる必要があるみたい

  • SDKが提供されてるからバックグラウンド再生時のコントロールパネルとかは自分で実装しなくてよくて楽