iOS13 网络监视器崩溃

Posted

技术标签:

【中文标题】iOS13 网络监视器崩溃【英文标题】:Network monitor crashing in iOS13 【发布时间】:2021-05-13 07:30:21 【问题描述】:

所以我试图在 ios 13 + 上保持最新状态,同时引入一些 iOS 14 功能。 其中一项新功能是监控用户是否失去网络连接。

但是,当我运行以下代码时,我遇到了一个奇怪的错误。

TaView.swift(默认视图)

import SwiftUI


struct TaView: View 
    @StateObject var monitor = Monitor()
    @ObservedObject var location = LocationManager()
    @State var errorDetail = false
  
    
    var lat: String
        return "\(location.lastKnownLocation?.coordinate.latitude ?? 0.0)"
    
    
    var lon: String
        return "\(location.lastKnownLocation?.coordinate.longitude ?? 0.0)"
    
    
    var state: String
        return "\(UserSettings().state)"
    
    
    init() 
//        print(self.data.connected)
        self.location.startUpdating()
    
    @ObservedObject var userSettings = UserSettings()
    
    
    var body: some View 
        if (self.lat == "0.0" && self.lon == "0.0")
            LocationDisabled()
        
        else
            if #available(iOS 14.0, *) 
                TabView 
                    ContentView()
                        
                        .tabItem 
                            Image(systemName: "dot.radiowaves.left.and.right")
                            Text("Radio")
                        
                    
                    WinView()
                        .tabItem 
                            Image(systemName: "w.circle")
                            Text("Win")
                        
                    
                    SettingsView()
                        .tabItem 
                            Image(systemName: "gear")
                            Text("Settings")
                            
                        
                .accentColor(Color.red)
                .onAppear()
                    Timer.scheduledTimer(withTimeInterval: 1, repeats: true)  (timer) in
                        if monitor.score == 0
                            DispatchQueue.main.asyncAfter(deadline: .now()) 
                                self.errorDetail = true
                            
                        
                        
                        //print("this is the score \(monitor.score)")
                    
                
                .fullScreenCover(isPresented: self.$errorDetail, content: NetworkOutageView.init)
             else 
                TabView 
                    ContentView()
                        
                        .tabItem 
                            Image(systemName: "dot.radiowaves.left.and.right")
                            Text("Radio")
                        
                    
                    WinView()
                        .tabItem 
                            Image(systemName: "w.circle")
                            Text("Win")
                        
                    
                    SettingsView()
                        .tabItem 
                            Image(systemName: "gear")
                            Text("Settings")
                            
                        
                .accentColor(Color.red)
                .onAppear()
                    Timer.scheduledTimer(withTimeInterval: 1, repeats: true)  (timer) in
                        if monitor.score == 0
                            DispatchQueue.main.asyncAfter(deadline: .now()) 
                                self.errorDetail = true
                            
                        
                        
                        //print("this is the score \(monitor.score)")
                    
                
                .sheet(isPresented: self.$errorDetail, content: NetworkOutageView.init)
            
        
    



struct LocationDisabled: View 
    @ObservedObject var location = LocationManager()

    init() 
        self.location.startUpdating()
    
    var body: some View 
        GeometryReader  geo in
        VStack
            Spacer().frame(maxHeight: 100)
            Image(systemName: "location.fill").resizable().scaledToFit().frame(width: 100).foregroundColor(Color.white)
            
            VStack
                 Text("Enable Location").font(.system(.largeTitle, design: .rounded)).bold().multilineTextAlignment(.leading).foregroundColor(Color.white)
                 Text("You'll need to enable your location.\nIn order to use access these features").fontWeight(.light).multilineTextAlignment(.center).fixedSize(horizontal: false, vertical: true).padding(.all, 8).foregroundColor(Color.white)
                 Text("\u2022 Win Prizes\n\n\u2022 Change Stations\n\n\u2022 Access Podcasts\n\n\u2022 Request Songs\n\n\u2022 And More").bold().multilineTextAlignment(.center).fixedSize(horizontal: false, vertical: true).padding(.all, 8).foregroundColor(Color.white)
                 
                
                Spacer()
                Button(action: 
                     self.location.requestLoc()
                ) 
                    Text("ALLOW LOCATION")
                        .font(.headline)
                        .bold()
                .buttonStyle(LocationGradientButtonStyle())
                .padding(.bottom, 100)
           
        
        
        
       // ImageOverlay()
    .frame(maxWidth: .infinity,maxHeight: .infinity).edgesIgnoringSafeArea(.all).background(
        Image("TooFarWallPaper").resizable().aspectRatio(contentMode: .fill).frame(maxWidth: .infinity,maxHeight: .infinity).edgesIgnoringSafeArea(.all)
        )
    
    



struct LocationGradientButtonStyle: ButtonStyle 
    func makeBody(configuration: Self.Configuration) -> some SwiftUI.View 
        configuration.label
            .foregroundColor(Color.white)
            .padding()
            .background(LinearGradient(gradient: Gradient(colors: [Color.blue, Color.purple]), startPoint: .topLeading, endPoint: .bottomTrailing))
            .cornerRadius(15.0)
    


struct SaveGradientButtonStyle: ButtonStyle 
    func makeBody(configuration: Self.Configuration) -> some SwiftUI.View 
        configuration.label
            .foregroundColor(Color.black)
            .padding()
            .background(LinearGradient(gradient: Gradient(colors: [Color.green, Color.green]), startPoint: .topLeading, endPoint: .bottomTrailing))
            .cornerRadius(15.0)
    


Monitor.swift

import Network
import SwiftUI

// An enum to handle the network status
enum NetworkStatus: String 
    case connected
    case disconnected


class Monitor: ObservableObject 
    private let monitor = NWPathMonitor()
    private let queue = DispatchQueue(label: "Monitor")

    @Published var score = 0
    @Published var status: NetworkStatus = .connected
  
    init() 
        monitor.pathUpdateHandler =  [weak self] path in
            guard let self = self else  return 

            // Monitor runs on a background thread so we need to publish
            // on the main thread
            DispatchQueue.main.async 
                if path.status == .satisfied 
                    print("We're connected!")
                    self.status = .connected
                    self.score = 1
                  

                 else 
                    print("No connection.")
                    self.score = 0
                    self.status = .disconnected
                
            
        
        monitor.start(queue: queue)
    


错误是

Thread 1: signal SIGABRT

我想知道如何解决这个问题?

【问题讨论】:

我无法重现此错误,您是否在 Simulator 上运行,这对我来说工作正常,在 iOS 14.4Xcode 12.4 上进行了测试 是的,它适用于 iOS14+ 但不适用于 iOS 13.6 请注意,此代码无法在iOS 13.6 上运行,因为您使用的是@StateObject 属性包装器,该包装器可从iOS 14.0 及更高版本获得。 尝试改用@ObservedObject 那么想知道解决这个问题的解决方案是什么,使其向后兼容 【参考方案1】:

@StateObject 更改为ObservedObject 效果很好。

注意:在检查@availability(进行向后兼容时)时,您并不总是需要在ifelse 中再次编写相同的代码,您只需为View 创建一个变量即可并重用它,就像在这种情况下我们重用 tabViewContent

struct TaView: View 
    @ObservedObject var monitor = Monitor()
    
    @ObservedObject var location = LocationManager()
    @State var errorDetail = false
    
    
    var lat: String
        return "\(location.lastKnownLocation?.coordinate.latitude ?? 0.0)"
    
    
    var lon: String
        return "\(location.lastKnownLocation?.coordinate.longitude ?? 0.0)"
    
    
    var state: String
        return "\(UserSettings().state)"
    
    
    init() 
        //        print(self.data.connected)
        self.location.startUpdating()
    
    @ObservedObject var userSettings = UserSettings()
    
    var tabViewContent: some View 
        TabView 
            ContentView()
                
                .tabItem 
                    Image(systemName: "dot.radiowaves.left.and.right")
                    Text("Radio")
                
            
            WinView()
                .tabItem 
                    Image(systemName: "w.circle")
                    Text("Win")
                
            
            SettingsView()
                .tabItem 
                    Image(systemName: "gear")
                    Text("Settings")
                    
                
        .accentColor(Color.red)
        .onAppear()
            Timer.scheduledTimer(withTimeInterval: 1, repeats: true)  (timer) in
                if monitor.score == 0
                    self.errorDetail = true
                 else 
                    self.errorDetail = false
                    
                
                
                //print("this is the score \(monitor.score)")
            
        
    
    
    var body: some View 
        if (self.lat == "0.0" && self.lon == "0.0")
            LocationDisabled()
        
        else
            if #available(iOS 14.0, *) 
                tabViewContent
                    .fullScreenCover(isPresented: self.$errorDetail, content: NetworkOutageView.init)
             else 
                tabViewContent
                    .sheet(isPresented: self.$errorDetail, content: NetworkOutageView.init)
            
        
    

Xcode 12.4iOS13.3.1iOS 14.4.2 测试

【讨论】:

以上是关于iOS13 网络监视器崩溃的主要内容,如果未能解决你的问题,请参考以下文章

Android Studio:您的设备无法使用网络监控功能

监控程序崩溃

tcpdump常用方法

免费网络监视器

某网络监视器完整逆向

Firefox:网络监视器:如何调试 JSON 有效负载?