Как работать с push-уведомлением Swift Onesignal, когда приложение iOS закрыто?

Я разрабатываю мобильное приложение веб-просмотра с использованием Swift на платформе iOS. В приложении я использую Universal Link и OneSignal. Когда приложение закрыто или находится в фоновом режиме и т. д. В любом случае deeplink работает отлично. Никаких проблем пока.

Проблема в натификации OneSignal. Если приложение закрыто и я отправляю push-уведомление с URL-адресом, я не могу перенаправить на соответствующий URL-адрес.

Нет проблем, если приложение открыто или работает в фоновом режиме. URL-адрес открывается в веб-просмотре. Однако, как я уже говорил, проблема возникает при закрытии приложения. Есть ли кто-нибудь, кто может мне помочь с этим?

Я думаю, что эта проблема должна быть решена в файле SceneDelegate.swift. Однако, хотя я перепробовал много вещей, я не смог найти решения. Кратко мои работы ниже:

// Файл AbcViewController.swift:

import UIKit
import WebKit
import OneSignalFramework
class AbcViewController: UIViewController {
    @IBOutlet weak var webView: WKWebView!
    var urlOneSignalNotification: URL?
    override func viewDidLoad() {
        super.viewDidLoad()
        NotificationCenter.default.addObserver(self, selector: #selector(handNotURL), name: Notification.Name(rawValue: "urlReceived"), object: nil)
        
        // Define default URL
        let defaultURL = URL(string: "example.com")!
        let url =  urlOneSignalNotification ?? defaultURL
        var request = URLRequest(url: url)
        webView.load(request)
    }
    
    // Get
    @objc func handNotURL(_ notification: Notification) {
        if let url = notification.object as? URL {
            urlOneSignalNotification = url
            // Load the URL in the web view
            let request = URLRequest(url: urlOneSignalNotification!)
            webView.load(request)
        } else {
            urlOneSignalNotification = nil 
        }
    }
}

// AppDelegate.swift

import UIKit
import OneSignalFramework
import UserNotifications
@main
class AppDelegate: UIResponder, UIApplicationDelegate {
//...
}
extension AppDelegate: UNUserNotificationCenterDelegate {
  func application(_ application: UIApplication, didReceiveRemoteNotification userInfo: [AnyHashable: Any], fetchCompletionHandler completionHandler: @escaping (UIBackgroundFetchResult) -> Void) {
        guard let data = userInfo as? [String: Any] else {
            completionHandler(.noData)
            return
        }
       
        if let customData = data["custom"] as? [String: Any], let urlString = customData["u"] as? String {
            if let url = URL(string: urlString) {
                NotificationCenter.default.post(name: Notification.Name(rawValue: "urlReceived"), object: url)
            } else {
            }
        } 
       
        completionHandler(.newData)
    }
}
Стоит ли изучать PHP в 2026-2027 годах?
Стоит ли изучать PHP в 2026-2027 годах?
Привет всем, сегодня я хочу высказать свои соображения по поводу вопроса, который я уже много раз получал в своем сообществе: "Стоит ли изучать PHP в...
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
В JavaScript одним из самых запутанных понятий является поведение ключевого слова "this" в стрелочной и обычной функциях.
Приемы CSS-макетирования - floats и Flexbox
Приемы CSS-макетирования - floats и Flexbox
Здравствуйте, друзья-студенты! Готовы совершенствовать свои навыки веб-дизайна? Сегодня в нашем путешествии мы рассмотрим приемы CSS-верстки - в...
Тестирование функциональных ngrx-эффектов в Angular 16 с помощью Jest
В системе управления состояниями ngrx, совместимой с Angular 16, появились функциональные эффекты. Это здорово и делает код определенно легче для...
Концепция локализации и ее применение в приложениях React ⚡️
Концепция локализации и ее применение в приложениях React ⚡️
Локализация - это процесс адаптации приложения к различным языкам и культурным требованиям. Это позволяет пользователям получить опыт, соответствующий...
Пользовательский скаляр GraphQL
Пользовательский скаляр GraphQL
Листовые узлы системы типов GraphQL называются скалярами. Достигнув скалярного типа, невозможно спуститься дальше по иерархии типов. Скалярный тип...
1
0
145
1
Перейти к ответу Данный вопрос помечен как решенный

Ответы 1

Ответ принят как подходящий

После холодного запуска приложениям часто требуется некоторое время, чтобы быть готовыми к использованию, от main.swift до application:(_didFinishLauchingWithOptions:).

Таким образом, вы можете либо определить класс для хранения полезных данных из уведомлений и затем использовать его позже, когда приложение загрузится, либо создать wait прямо перед NotificationCenter.default.post.

DispatchQueue.main.asyncAfter(deadline: .now() + 1.0) {
    NotificationCenter.default.post(name: Notification.Name(rawValue: "urlReceived"), object: url)
}

//Or
Task { @MainActor in
    try? await Task.sleep(nanoseconds: 1_000_000_000)
    NotificationCenter.default.post(name: Notification.Name(rawValue: "urlReceived"), object: url)
}

Другие вопросы по теме