Post

Replies

Boosts

Views

Activity

Reply to How to get a catalog playlists of a curator?
I'm hopeful, that the **** may work, but I'm waiting on an iOS16 device to test on: @available(iOS 16.0, *) func getCuratorPlaylistsFromPlaylist2(playlistId: String) async throws -> String? {     do {         var request = MusicCatalogResourceRequest<MusicKit.Playlist>(matching: \.id, equalTo: MusicItemID(playlistId))         request.properties = [.curator] // adding curator to the request         let response = try await request.response()         Logger.log(.success, "Playlists Response: \(response.items)") // this is a collection of playlists, as expected.         Logger.log(.info, "Playlists Item Count: \(response.items.count)") // this is always 1, as expected         for item in response.items {             Logger.log(.info, "Item: \(item)") // shows the playlist's id, name, curatorName, and maybe more with .curator added             Logger.log(.info, "Type of Item: \(type(of: item))") // type is Playlist             if let curatorPlaylists = item.curator?.playlists {                 Logger.log(.info, "Curator Playlists: \(curatorPlaylists)") // hopeful here!             } else {                 Logger.log(.warning, "No Curator Playlists!")             }         }     } catch {         // handle error         Logger.log(.error, "Could not findCuratorOfPlaylist \(error)")     }     return nil }
Jun ’22
Reply to How to get a catalog playlists of a curator?
Can't seem to do this either, using the curatorName that can be found in either of the two above attempts. @available(iOS 15.4, *) func searchForCurator(name: String) async throws -> MusicItemCollection<Curator>? {     do {         Logger.log(.error, "Doing search for curator by name...")         let request = MusicCatalogSearchRequest(term: name, types: [Curator.self])         let response = try await request.response()         Logger.log(.info, "Response curators: \(response.curators)") // MusicItemCollection<Curator>()         Logger.log(.info, "Response curators isEmpty: \(response.curators.isEmpty)") // true     } catch {         // handle error     Logger.log(.error, "Could not searchForCurator \(error)")     }     return nil }
Jun ’22
Reply to How to get a catalog playlists of a curator?
Here's something similar to the above, but using .moreByCurator, though I'm not sure if I'm using it right, as I never get results. @available(iOS 15.4, *) func getCuratorPlaylistsFromPlaylist(playlistId: String) async throws -> String? {     do {         let request = MusicCatalogResourceRequest<MusicKit.Playlist>(matching: \.id, equalTo: MusicItemID(playlistId)) //catalogId         let response = try await request.response()         Logger.log(.success, "Playlists Response: \(response.items)") // this is a collection of playlists, as expected.         Logger.log(.info, "Playlists Item Count: \(response.items.count)") // this is always 1, as expected         for item in response.items {             Logger.log(.info, "Item: \(item)") // shows the playlist's id, name, and curatorName             Logger.log(.info, "Type of Item: \(type(of: item))") // type is Playlist             let morePlaylists = item.moreByCurator // not sure this is the right way to use .moreByCurator             Logger.log(.info, "More Playlists: \(String(describing: morePlaylists))") // This is always nil!         }     } catch {         // handle error         Logger.log(.error, "Could not findCuratorOfPlaylist \(error)")     }     return nil }
Jun ’22
Reply to How to get a catalog playlists of a curator?
Trying some more things, admittedly not knowing what I'm doing: This still requires me to know the catalogId of a playlist that exists as a catalog resource, but it get's me the curatorId, which seems hopeful. My problem is searching for the curator using a MusicCatalogResourceRequest yields no results. func findCuratorOfPlaylist(playlistId: String) async throws -> String? {     do {         var requestURLComponents = URLComponents()         requestURLComponents.scheme = "https"         requestURLComponents.host = "api.music.apple.com"         requestURLComponents.path = "/v1/catalog/us/playlists/\(playlistId)/curator" // Got this idea from @snuff4         if let url = requestURLComponents.url {             let dataRequest = MusicDataRequest(urlRequest: URLRequest(url: url))             let dataResponse = try await dataRequest.response()             let decoder = JSONDecoder()             let response = try decoder.decode(AppleMusicGetCuratorResponse.self, from: dataResponse.data)             Logger.log(.info, "Curator Response: \(response)") // this returns the id, name, and kind (.editorial)             let items = response.data             let id = items[0].id             Logger.log(.info, "Searching for Curator with ID of \(id)")             let request = MusicCatalogResourceRequest<Curator>(matching: \.id, equalTo: id)             let resp = try await request.response()             Logger.log(.info, "Find Curator Request Response Items: \(resp.items)") // MusicCatalogResourceResponse<Curator>()             Logger.log(.info, "Is Curator Request Response empty: \(resp.items.isEmpty)") // true         }     } catch {         // handle error         Logger.log(.error, "Could not findCuratorOfPlaylist \(error)")     }     return nil }
Jun ’22
Reply to Songs are not always added to Playlist when using Music iOS
This is wild. For the first time in an exceptionally long time, I actually got a response on the Feedback Assistant regarding an issue I opened (thanks @JoeKun!). They wanted me to reproduce the problem, which I had painstakingly done in text in the ticket. Regardless, I decided to make a screen cast of the issue, so as to illustrate the issue, and... The problem is magically gone! I do need to say that this WAS a problem, and I swear it was still happening within the last month (I've been busy on other stuff, so I can't be sure of when it last didn't work). That said, @dutton, can you please check on your side to see if this issue has been resolved? Much appreciated! Imma gonna keep testing, but if this keeps working, I'll close this issue once confirmed.
Jun ’22
Reply to Missing play parameters when trying to play with MusicKit - potential storefront issue
I have confirmed that the behavior is related to country/storefront by programatically saving the offending track to a playlist in Apple Music and attempting to play it there. The result of that is an alert that says, "This song is not currently available in your country or region." So my quesiton still stands: "How can I create a MusicCatalogRequest in such a way that I only get results that are playable in my country/storefront?"
Feb ’22
Reply to Run async tasks using Background Tasks
Hi @eskimo, Thanks for the pro follow up. That is correct. To clarify further, getUpdateAppData() function is run after manually invoking the objc command in Xcode. I don't actually know of another way to test this. The task is initially registered with the configureBackgroundTasks() function (see last code block in my prior post) in the init function of the app's app file (not app delegate). Kindly let me know if you have any further questions.
Dec ’21
Reply to Run async tasks using Background Tasks
HI @eskimo, Thanks for chiming in and providing insight. Using the below, I set a breakpoint right when the app is moved to the background (I'm not using appDelegate). .onReceive(NotificationCenter.default.publisher(for: UIApplication.didEnterBackgroundNotification)) { _ in       backgroundTaskManager.scheduleAppRefresh() // <= breakpoint here     } Once the app is paused, in Xcode, I run the following command in the Xcode terminal: e -l objc -- (void)[[BGTaskScheduler sharedScheduler] _simulateLaunchForTaskWithIdentifier:@"com.example.task"] That responds with: 2021-12-07 05:29:25.405222+0700 App[602:49934] Simulating launch for task with identifier com.example.task After that, I resume the app in Xcode and see (I believe "missing data" is not an error below): 2021-12-07 05:29:29.724492+0700 App[602:50205] Starting simulated task: <decode: missing data> Followed by the initial operation of the getUpdateAppData() function being called. The initial operation is a function that runs an Amplify (iOS library) graphQL query (here's an excerpt): func getMyFriends(currentUser: User) async throws -> [Friend] {     Logger.log(.fetch, "Fetching \(currentUser.username)'s friends...")     return try await withCheckedThrowingContinuation { continuation in       let friend = Friend.keys       let predicate = friend.owner == currentUser.username       Amplify.API.query(request: .list(Friend.self, where: predicate)) { event in         switch event {         case .success(let result): ... The app seems to just stop right after the logging of "Fetching (currentUser.username)'s friends..." No errors are thrown that I can see. Note this function works fine when it's called when the app is in the foreground. Also, when I return the app to the foreground, the getUpdateAppData() tries to resume, and rarely (if ever) completes as it should: 🐕 Fetching Elmer's friends... 2021-12-07 06:02:20.150514+0700 App[654:65556] Connection 1: encountered error(1:53) // <= upon return to foreground 2021-12-07 06:02:20.150650+0700 App[654:65556] Connection 1: received failure notification 2021-12-07 06:02:20.151257+0700 App[654:65556] [connection] nw_connection_copy_connected_local_endpoint [C1] Connection has no connected path 2021-12-07 06:02:20.151450+0700 App[654:65556] [connection] nw_connection_copy_connected_remote_endpoint [C1] Connection has no connected path 2021-12-07 06:02:20.153068+0700 App[654:65556] Connection 2: encountered error(1:53) 2021-12-07 06:02:20.153125+0700 App[654:65556] Connection 2: received failure notification 2021-12-07 06:02:20.153280+0700 App[654:65556] [connection] nw_connection_copy_connected_local_endpoint [C2] Connection has no connected path 2021-12-07 06:02:20.153891+0700 App[654:65556] [connection] nw_connection_copy_connected_remote_endpoint [C2] Connection has no connected path 2021-12-07 06:02:20.155082+0700 App[654:65556] Connection 3: encountered error(1:53) 2021-12-07 06:02:20.155293+0700 App[654:65556] Connection 3: received failure notification 2021-12-07 06:02:20.161795+0700 App[654:65556] [connection] nw_connection_copy_connected_local_endpoint [C3] Connection has no connected path 2021-12-07 06:02:20.161877+0700 App[654:65556] [connection] nw_connection_copy_connected_remote_endpoint [C3] Connection has no connected path 🦴 Successfully fetched Elmer's friends! ... Maybe Amplify doesn't work when in the background? I dunno. One thing that I have yet to try is testing with a simple, single API operation in lieu of the somewhat more involved getUpdateAppData() function that is currently running through completion. Any further thoughts and/or advice is appreciated. private func configureBackgroundTasks() { Logger.log(.info, "Registering background tasks...") let bgTaskIdentifier = "com.example.task" BGTaskScheduler.shared.register(forTaskWithIdentifier: bgTaskIdentifier, using: DispatchQueue.main) { (task) in Logger.log(.info, "Performing background task \(bgTaskIdentifier)") Task { if let updatedData = await appManager.getUpdateAppData() { DispatchQueue.main.async { appManager.data = updatedData task.setTaskCompleted(success: true) } } else { task.setTaskCompleted(success: false) } backgroundTaskManager.scheduleAppRefresh() } } }
Dec ’21
Reply to Run async tasks using Background Tasks
Hi @OOPer, Thanks much for taking the time to respond. I have tried several variations, in an attempt to get this working. The result from your suggested mods: using Task instead of Task.init and putting task.setTaskCompleted(success: true) in a DispatchQueue.main.async {}, results in: 2021-12-04 14:58:39.136393-0800 App[8341:2562502] [connection] nw_read_request_report [C7] Receive failed with error "Socket is not connected" 2021-12-04 14:58:39.139668-0800 App[8341:2562502] [connection] nw_read_request_report [C7] Receive failed with error "Socket is not connected" Doing the same, but using Task.init {... results in: 2021-12-04 15:03:53.128265-0800 App[8344:2563988] [Framework] Task <BGAppRefreshTask: com.example.task> dealloc'd without completing. This is a programmer error. 2021-12-04 15:03:53.128610-0800 App[8344:2563988] Marking simulated task complete: (null) I do like the very specific calling out the programmer error 😄 I've also tried using BGProcessingTaskRequest instead of BGAppRefreshTaskRequest just in case the update operation was timing out after 30 seconds, which I believe is the time window alloted for a refresh task.
Dec ’21