Spotify iOS 框架允许您的应用程序与用户设备后台运行的 Spotify 应用程序进行交互。功能包括授权、获取当前播放曲目和上下文的元数据,以及发出播放命令。
请注意: 通过使用 Spotify 开发者工具,您即表示接受我们的 开发者使用条款。
Spotify iOS SDK 是一组轻量级对象,它们与 Spotify 应用程序连接,让您在将所有繁重的播放工作卸载到 Spotify 应用程序本身的同时控制它。Spotify 应用程序负责处理播放、网络、离线缓存和操作系统音乐集成,让您专注于用户体验。从您的应用程序移动到 Spotify 应用程序以及反之亦然是一个简化的体验,其中播放和元数据始终保持同步。
我们欢迎来自开发者社区的反馈,所以请随时在我们的 问题跟踪器 上提交缺失的功能或错误。在创建新问题之前,请务必搜索现有问题。
Spotify iOS 框架需要 iOS 12 或更高的部署目标。SDK 中支持以下架构
SPTAppRemoteAlbumSPTAppRemoteArtistSPTAppRemoteLibraryStateSPTAppRemotePlaybackRestrictionsSPTAppRemotePlaybackOptionsSPTAppRemotePlayerStateSPTAppRemoteTrackSPTAppRemoteContentItemSPTAppRemoteUserCapabilitiesSPTAppRemoteImageRepresentableSPTConfiguration连接到 Spotify 应用程序并检索 API 组件的主要入口点。使用它来建立、监控和终止连接。
发送与播放相关的命令,例如
为 SPTAppRemoteImageRepresentable 获取图像
获取/订阅/设置用户相关数据,例如
SPTAppRemoteUserCapabilities为用户获取推荐内容。
当您与任何 App Remote API 交互时,您传入一个 SPTAppRemoteCallback 代码块,该代码块将在 Spotify 应用程序收到命令后(或者如果无法建立连接)使用预期的结果项或 NSError 调用。
这是一个使用 SPTRemotePlayerAPI 跳过歌曲的示例
[appRemote.playerAPI skipToNext:^(id _Nullable result, NSError * _Nullable error) {
if (error) {
// Operation failed
} else {
// Operation succeeded
}
}];
我们提供了一些示例项目,以帮助您开始使用 DemoProjects 文件夹中的 iOS 框架。有关每个示例作用的更多信息,请参阅 DemoProjects 文件夹中的 Readme。
为了与 Spotify 应用程序通信,您的应用程序需要先获得用户的许可才能使用 App Remote 的内置授权来控制播放。为此,您需要在连接到 Spotify 时请求授权视图。如果用户尚未同意,该框架将自动请求 app-remote-control 范围并显示授权视图。
请注意,通过使用 Spotify 开发者工具,您即表示接受我们的 开发者使用条款。
本教程将引导您逐步创建一个简单的应用程序,该应用程序使用 Spotify iOS SDK 播放音轨并订阅播放器状态。它将引导您完成授权流程。
按照以下步骤确保您已准备好开始编码。
将 SpotifyiOS 包添加到您的项目。您可以通过 Swift Package Manager (SPM) 执行此操作,或者直接将 SpotifyiOS.xcframework 添加到您的 Xcode 项目。
在您的 info.plist 中,添加您在 My Applications 注册的重定向 URI。您需要在“URL types”和“URL Schemes”下添加您的重定向 URI。请务必也设置唯一的“URL identifier”。
将库添加到您的源文件。
Swift
import SpotifyiOS
Objective-c
#import <SpotifyiOS/SpotifyiOS.h>
为了能够使用 SDK 的播放控制部分,用户需要授权您的应用程序。如果他们没有授权,连接将失败并显示 No token provided 错误。为了允许用户授权您的应用程序,您可以使用内置的授权流程。
使用您的客户端 ID 和重定向 URI 初始化 SPTConfiguration。
Swift
let configuration = SPTConfiguration(
clientID: "YOUR_CLIENT_ID",
redirectURL: URL(string: "your_redirect_uri")!
)
Objective-c
SPTConfiguration *configuration = [[SPTConfiguration alloc] initWithClientID:@"your_client_id"
redirectURL:[NSURL URLWithString:@"your_redirect_uri"]];
使用您的 SPTConfiguration 初始化 SPTAppRemote
Swift
self.appRemote = SPTAppRemote(configuration: configuration, logLevel: .debug)
Objective-c
self.appRemote = [[SPTAppRemote alloc] initWithConfiguration:configuration logLevel:SPTAppRemoteLogLevelDebug];
启动身份验证流程(有关检测 Spotify 是否已安装以及归因安装的其他方法,请参阅我们的 内容链接指南)。
Swift
// Note: A blank string will play the user's last song or pick a random one.
self.appRemote.authorizeAndPlayURI("spotify:track:69bp2EbF7Q2rqc5N3ylezZ") { spotifyInstalled in
if !spotifyInstalled {
/*
* The Spotify app is not installed.
* Use SKStoreProductViewController with [SPTAppRemote spotifyItunesItemIdentifier] to present the user
* with a way to install the Spotify app.
*/
}
}
Objective-c
// Note: A blank string will play the user's last song or pick a random one.
[self.appRemote authorizeAndPlayURI:@"spotify:track:69bp2EbF7Q2rqc5N3ylezZ" completionHandler:^(BOOL spotifyInstalled) {
if (!spotifyInstalled) {
/*
* The Spotify app is not installed.
* Use SKStoreProductViewController with [SPTAppRemote spotifyItunesItemIdentifier] to present the user
* with a way to install the Spotify app.
*/
}
}];
配置您的 AppDelegate 以解析 application:openURL:options: 中的 accessToken,并在 SPTAppRemote connectionParameters 上设置它。
Objective-c
- (BOOL)application:(UIApplication *)app openURL:(NSURL *)url options:(NSDictionary<UIApplicationOpenURLOptionsKey,id> *)options
{
NSDictionary *params = [self.appRemote authorizationParametersFromURL:url];
NSString *token = params[SPTAppRemoteAccessTokenKey];
if (token) {
self.appRemote.connectionParameters.accessToken = token;
} else if (params[SPTAppRemoteErrorDescriptionKey]) {
NSLog(@"%@", params[SPTAppRemoteErrorDescriptionKey]);
}
return YES;
}
如果您使用 UIScene,则需要在您的场景委托中使用适当的方法。
Swift
func scene(_ scene: UIScene, openURLContexts URLContexts: Set<UIOpenURLContext>) {
guard let url = URLContexts.first?.url else {
return
}
let parameters = appRemote.authorizationParameters(from: url);
if let access_token = parameters?[SPTAppRemoteAccessTokenKey] {
appRemote.connectionParameters.accessToken = access_token
self.accessToken = access_token
} else if let error_description = parameters?[SPTAppRemoteErrorDescriptionKey] {
// Show the error
}
}
设置您的连接委托并尝试连接。
Swift
self.appRemote.delegate = self
self.appRemote.connect()
// MARK: AppRemoteDelegate
func appRemoteDidEstablishConnection(_ appRemote: SPTAppRemote) {
// Connection was successful, you can begin issuing commands
}
func appRemote(_ appRemote: SPTAppRemote, didFailConnectionAttemptWithError error: Error?) {
// Connection failed
}
func appRemote(_ appRemote: SPTAppRemote, didDisconnectWithError error: Error?) {
// Connection disconnected
}
Objective-c
self.appRemote.delegate = self;
[self.appRemote connect];
- (void)appRemoteDidEstablishConnection:(SPTAppRemote *)appRemote
{
// Connection was successful, you can begin issuing commands
}
- (void)appRemote:(SPTAppRemote *)appRemote didFailConnectionAttemptWithError:(NSError *)error
{
// Connection failed
}
- (void)appRemote:(SPTAppRemote *)appRemote didDisconnectWithError:(nullable NSError *)error
{
// Connection disconnected
}
设置委托并订阅播放器状态
Swift
self.appRemote.playerAPI?.delegate = self
appRemote.playerAPI?.subscribe(toPlayerState: { result, error in
// Handle Errors
})
// MARK: SPTAppRemotePlayerStateDelegate
func playerStateDidChange(_ playerState: SPTAppRemotePlayerState) {
print("track name \(playerState.track.name)")
}
Objective-c
appRemote.playerAPI.delegate = self;
[appRemote.playerAPI subscribeToPlayerState:^(id _Nullable result, NSError * _Nullable error) {
// Handle Errors
}];
- (void)playerStateDidChange:(id<SPTAppRemotePlayerState>)playerState
{
NSLog(@"Track name: %@", playerState.track.name);
}
作为一项礼貌措施,当您的应用程序进入后台状态时,您应始终断开 App Remote 的连接。这告诉 Spotify 可以安全地禁用活动流。如果您的应用程序未正确调用断开连接,Spotify 将无法知道它不应保持连接,这可能会导致未来的连接问题。
如果您希望您的应用程序在中断事件(如来电或 Siri 交互)后自动重新连接,您可以使用 willResignActive 和 didBecomeActive 回调安全地断开和重新连接。如果您不希望直接重新连接,通常在 didEnterBackground 回调中关闭连接就足够了。
Swift
func sceneWillResignActive(_ scene: UIScene) {
self.appRemote.disconnect()
}
func sceneDidBecomeActive(_ scene: UIScene) {
self.appRemote.connect()
}
Objective-c
- (void)applicationWillResignActive:(UIApplication *)application
{
[self.appRemote disconnect];
}
- (void)applicationDidBecomeActive:(UIApplication *)application
{
[self.appRemote connect];
}
// If you're using UIWindowSceneDelegate
- (void)sceneDidBecomeActive:(UIScene *)scene
{
[self.appRemote connect];
}
- (void)sceneWillResignActive:(UIScene *)scene
{
[self.appRemote disconnect];
}
为什么必须在音乐播放时才能连接 SPTAppRemote?
当您连接 SPTAppRemote 时,必须正在播放音乐,以确保 Spotify 应用程序不会在后台挂起。除非 iOS 应用程序正在积极执行某些操作(如导航或播放音乐),否则它们只能在后台保持活动状态几秒钟。
SpotifyiOS.framework 是线程安全的吗?
否,该框架目前希望从主线程调用。它将在内部将其大部分工作卸载到后台线程,但对您代码的回调也将在主线程上发生。
如果我需要在不启动播放的情况下进行授权怎么办?
还有另一种授权方法。您可以在 此处 找到有关该方法的更多信息。