| ページ一覧 | ブログ | twitter |  書式 | 書式(表) |

MyMemoWiki

「Swift Sample」の版間の差分

提供: MyMemoWiki
ナビゲーションに移動 検索に移動
40行目: 40行目:
 
}
 
}
 
</pre>
 
</pre>
*書き出し処理
+
*読み込み、コレクションに追加、書き出し処理
 
<pre>
 
<pre>
 +
    func addHostListDocument(host: WoL.Host) {
 
         let docPath = FileManager.default.urls(for: .documentDirectory, in: .userDomainMask)[0]
 
         let docPath = FileManager.default.urls(for: .documentDirectory, in: .userDomainMask)[0]
 
         let filePath = URL(fileURLWithPath: "hosts.json", relativeTo:docPath)
 
         let filePath = URL(fileURLWithPath: "hosts.json", relativeTo:docPath)
 +
       
 +
        var hostList: [WoL.Host] = []
 +
       
 +
        let decoder = JSONDecoder()
 +
        do {
 +
            let rawData = try Data(contentsOf: filePath)
 +
            print(rawData)
 +
            let tmpHostList = try decoder.decode([WoL.Host].self, from: rawData)
 +
            for tmpHost in tmpHostList {
 +
                hostList.append(tmpHost)
 +
            }
 +
        } catch {
 +
            print(error)
 +
        }
 +
       
 +
        hostList.append(host)
 
         let encoder = JSONEncoder()
 
         let encoder = JSONEncoder()
 
         do {
 
         do {
             let line = try encoder.encode(host)
+
             let line = try encoder.encode(hostList)
 
             try line.write(to: filePath)
 
             try line.write(to: filePath)
 
         } catch {
 
         } catch {
 
             print(error)
 
             print(error)
 
         }
 
         }
 +
    }
 
</pre>
 
</pre>
 
[[File:swift_json_encode.png|300px]]
 
[[File:swift_json_encode.png|300px]]

2021年4月27日 (火) 13:24時点における版

| Swift | SwiftUI |Xcode | Mac |

Swift Sample

Network

データ取得


        let url = URL(string: "https://www.typea.info/blog/")!
        let task = URLSession.shared.dataTask(with: url) { data, response, error in
            if let error = error {
                print("\(error)\n")
                return
            }
            guard let data = data, let response = response as? HTTPURLResponse else {
                print("no data or no response.")
                return
            }
            if response.statusCode == 200 {
                if let text = String(bytes: data, encoding: .utf8) {
                    print(text)
                }
            }
        }
        task.resume()

MacOSでエラーの場合

Error Domain=NSURLErrorDomain Code=-1003

Swift macos net error.png

File

JSONにシリアライズしてドキュメントディレクトリへ書き出し

  • データ(Codableを適用する)
struct Host : Codable {
    var host: String = ""
    var ip: String = ""
    var macaddr: String = ""
}
  • 読み込み、コレクションに追加、書き出し処理
    func addHostListDocument(host: WoL.Host) {
        let docPath = FileManager.default.urls(for: .documentDirectory, in: .userDomainMask)[0]
        let filePath = URL(fileURLWithPath: "hosts.json", relativeTo:docPath)
        
        var hostList: [WoL.Host] = []
        
        let decoder = JSONDecoder()
        do {
            let rawData = try Data(contentsOf: filePath)
            print(rawData)
            let tmpHostList = try decoder.decode([WoL.Host].self, from: rawData)
            for tmpHost in tmpHostList {
                hostList.append(tmpHost)
            }
        } catch {
            print(error)
        }
        
        hostList.append(host)
        let encoder = JSONEncoder()
        do {
            let line = try encoder.encode(hostList)
            try line.write(to: filePath)
        } catch {
            print(error)
        }
    }

Swift json encode.png

UI

バックグラウンドからUIを操作する


  • observableobj が、ObservableObject の派生クラス
  • contentフィールドに、@Published アノテーション
  • Viewで、@ObservedObjectを付与しインスタンスを生成
  • 上記で、バックグラウンドから、observableobj.contentを操作すると、UIはメインスレッドから触るように怒られる。

Publishing changes from background threads is not allowed; make sure to publish values from the main thread (via operators like receive(on:)) on model updates.

  • DispatchQueue.main.syncで囲む
DispatchQueue.main.sync {
    observableobj.content = text
}

処理

サブプロセスを起動

  • プロセスを起動し、arp -a を呼び出し、出力
    func arp() {
        let outputPipe = Pipe()

        func shell(path:String ,args: String...) -> Int32 {
            let task = Process()
            task.launchPath = path
            task.arguments = args
            task.standardOutput = outputPipe
            task.standardError = outputPipe
            
            task.launch()
            task.waitUntilExit()
            
            return task.terminationStatus
        }
        let _ = shell(path:"/usr/sbin/arp",args: "-a")
        let theTaskData = outputPipe.fileHandleForReading.readDataToEndOfFile()
        let stringResult = String(data: theTaskData, encoding: .utf8)
        
        print(stringResult!)
    }

正規表現

arp -a の結果からIPアドレスを抜きだす


    func parseArp(arpResult: String?) {
        if let input = arpResult {
            do {
                let pattern = #"[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}"#
                let regex = try NSRegularExpression(pattern: pattern, options:[])
                
                for subinput in input.split(separator: "\r\n") {
                    let line = String(subinput)
                    let maches = regex.matches(in: line, options: [], range: _NSRange(0..<line.count))
                    
                    print(line)
                    
                    for mach in maches {
                        for i in 0 ..< mach.numberOfRanges {
                            let start = line.index(line.startIndex, offsetBy: mach.range(at: i).location)
                            let end = line.index(start, offsetBy: mach.range(at: i).length)
                            let text = String(line[start..<end])
                            print(text)
                        }
                    }
                }
            } catch {
                print("RegEx fail.")
            }
        } else {
            print("arp -a result : error")
    }

名前を付与してキャプチャ


func parseArp(arpResult: String?) {
	if let input = arpResult {
		do {
			let pattern = #".*?(?<ip>[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}).*(?<mac>[0-9a-z]{1,2}:[0-9a-z]{1,2}:[0-9a-z]{1,2}:[0-9a-z]{1,2}:[0-9a-z]{1,2}:[0-9a-z]{1,2})"#
			let regex = try NSRegularExpression(pattern: pattern, options:[])
			
			for subinput in input.split(separator: "\r\n") {
				let line = String(subinput)
				let matches = regex.matches(in: line, options: [], range: _NSRange(0..<line.count))
				
				print(line)
				
				for match in matches {
					for name in ["ip", "mac"] {
						let matchRange = match.range(withName: name)
						if let substrRanget = Range(matchRange, in:line) {
							let ip = String(line[substrRanget])
							print("\(name):\(ip)")
						}
					}
				}
			}
		} catch {
			print("RegEx fail.")
		}
	} else {
		print("arp -a result : error")
	}
}