Spotify SessionManager 不断失败并出现错误“invalid_grant”

Posted

技术标签:

【中文标题】Spotify SessionManager 不断失败并出现错误“invalid_grant”【英文标题】:Spotify SessionManager continually failing with error "invalid_grant" 【发布时间】:2019-12-11 10:43:04 【问题描述】:

我正在尝试做的事情: 我正在将 Spotify SDK 实施到我的 ios 项目中。我已成功接收 Spotify API 的访问令牌,因为我能够使用所述 API 执行搜索艺术家、搜索歌曲和查看播放列表等操作。

我正在努力做的一件事是使用 SDK 播放音乐。我有一个按钮,点击后,我希望发生以下流程:

我通过执行以下功能并使用以下会话管理器请求 Spotify 访问:

let SpotifyClientID = "###"
let SpotifyRedirectURL = URL(string: "bandmate://")!

lazy var configuration = SPTConfiguration(
    clientID: SpotifyClientID,
    redirectURL: SpotifyRedirectURL
)

lazy var sessionManager: SPTSessionManager = 
    if let tokenSwapURL = URL(string: "https://bandmateallcaps.herokuapp.com/api/token"),
        let tokenRefreshURL = URL(string: "https://bandmateallcaps.herokuapp.com/api/refresh_token") 
        configuration.tokenSwapURL = tokenSwapURL
        configuration.tokenRefreshURL = tokenRefreshURL
        configuration.playURI = ""
    
    let manager = SPTSessionManager(configuration: configuration, delegate: self)
    return manager
()

func requestSpotifyAccess() 
    let requestedScopes: SPTScope = [.appRemoteControl, .userReadPrivate]
    self.sessionManager.initiateSession(with: requestedScopes, options: .default)

启动 SPTSession 后,我想连接我的遥控器:

lazy var appRemote: SPTAppRemote = 
    let appRemote = SPTAppRemote(configuration: configuration, logLevel: .debug)
    appRemote.delegate = self
    return appRemote
()

func sessionManager(manager: SPTSessionManager, didInitiate session: SPTSession) 
    self.appRemote.connectionParameters.accessToken = session.accessToken
    self.appRemote.connect()

应用连接后,我想播放全局声明的 Spotify 曲目的 ID:

var pendingSpotifyId: String!

func appRemoteDidEstablishConnection(_ appRemote: SPTAppRemote) 
    print("connected")

    self.appRemote.playerAPI!.delegate = self
    self.appRemote.playerAPI!.subscribe(toPlayerState:  (result, error) in

        if let error = error 
            debugPrint(error.localizedDescription)
         else if self.pendingSpotifyId != nil 
            self.appRemote.playerAPI!.play(self.pendingSpotifyId, callback:  (any, err) in
                self.pendingSpotifyId = nil
            )
        
    )

我的问题: 每当我尝试启动会话时,此流程都会中断,sessionManager(manager: SPTSessionManager, didFailWith error: Error) 总是被称为返回以下错误: Error Domain=com.spotify.sdk.login Code=1 "invalid_grant" UserInfo=NSLocalizedDescription=invalid_grant

我需要会话成功启动,以便可以调用 sessionManager(manager: SPTSessionManager, didInitiate session: SPTSession),我可以连接我的遥控器并最终播放我的 Spotify 曲目。

我尝试过的: 我已经确保了一些事情:

    确保用户设备上后台 Spotify 应用的状态为正在播放(根据此票证:https://github.com/spotify/ios-sdk/issues/31)

    确保在接收访问令牌时具有正确的范围。返回的 JSON 类似于:

    "access_token":"###","token_type":"Bearer","expires_in":3600,"refresh_token":"###","scope":"app-remote-control user-read-private"

我怀疑的事情: 我不知道我通过 Heroku 的令牌交换是否正确完成。这是我能想到的唯一原因,为什么我会遇到这个问题。如果我能够使用 Spotify API,这是否足以证明我的令牌交换正确完成? (我怀疑是)

【问题讨论】:

您是否尝试在 Mac 上本地运行令牌交换脚本?我遇到了问题,我无法通过 Heroku 交换有效的令牌,但在本地它可以工作。如果它在本地工作,你至少可以确保你的 xcode 项目和 Spotify 开发者仪表板中的设置是匹配的。 【参考方案1】:

以下是我们的发现,希望对您有所帮助:

    SpotifySDK 教程没有提到 Bundle IDApp Callback URL 必须在 App Info.plist、源代码、Spotify App Dashboard 和 Heroku Env Vars 之间精确匹配。使用的 Bundle ID 必须与您的应用程序 Bundle ID 匹配。 App Callback URL 不能有空路径,即:my-callback-scheme://spotify-login-callback 在应用程序中同时使用 Web Spotify SDK 和 iOS Framework Spotify SDK 时,请注意只有其中一个执行身份验证。否则App Callback URL 将被调用两次导致错误。 可能需要将 Spotify configuration.playURI 设置为空字符串而不是 nil。示例应用上有注释。 最好在应用程序中只有一个管理 Spotify 身份验证的对象实例。否则,确保从 AppDelegate open url 方法调用正确的对象可能会很棘手。

【讨论】:

以上是关于Spotify SessionManager 不断失败并出现错误“invalid_grant”的主要内容,如果未能解决你的问题,请参考以下文章

即使使用 Await,Promise 也会不断返回 Undefined

Alamofire 不断被取消

axios 在调用时不断运行

Spotify 格式错误的 Json

使用 spotify-api-server 添加曲目到 Spotify 播放列表

Axios GET 请求 Spotify API 返回 401