5 // Created by Hori,Masaki on 2017/02/05.
6 // Copyright © 2017年 Hori,Masaki. All rights reserved.
12 private struct LFSeparateLine {
14 static let empty = LFSeparateLine(line: "", empty: true)
18 private let isEmpty: Bool
20 init(line: String, empty: Bool = false) {
26 func append(_ column: String) -> LFSeparateLine {
28 if isEmpty { return LFSeparateLine(line: column) }
30 let newLine = line + "\t" + column
32 return LFSeparateLine(line: newLine)
35 func append(_ dateCol: Date) -> LFSeparateLine {
37 return append("\(dateCol)")
40 func append(_ intCol: Int) -> LFSeparateLine {
42 return append("\(intCol)")
45 func append(_ boolCol: Bool) -> LFSeparateLine {
47 return append("\(boolCol)")
51 final class TSVSupport {
53 private let store = LocalDataStore.oneTimeEditor()
55 private var dateFomatter: DateFormatter = {
57 let formatter = DateFormatter()
58 formatter.dateFormat = "yyyy'-'MM'-'dd' 'HH':'mm':'ss' 'Z"
64 let panel = NSOpenPanel()
65 panel.allowedFileTypes = ["kcdlocaldata"]
68 guard $0 == .OK else { return }
70 panel.urls.forEach { url in
72 guard let fileW = try? FileWrapper(url: url) else { return }
74 fileW.fileWrappers?.forEach {
76 guard let data = $0.value.regularFileContents else { return }
79 case "kaihatu.tsv": self.registerKaihatuHistory(data)
80 case "kenzo.tsv": self.registerKenzoHistory(data)
81 case "kenzoMark.tsv": self.registerKenzoMark(data)
82 case "dropShip.tsv": self.registerDropShipHistory(data)
93 let panel = NSSavePanel()
94 panel.allowedFileTypes = ["kcdlocaldata"]
97 guard $0 == .OK else { return }
98 guard let url = panel.url else { return }
100 let data = self.store.sync { () -> (Data, Data, Data, Data)? in
102 guard let kaihatuHistory = self.dataOfKaihatuHistory() else { return nil }
103 guard let kenzoHistory = self.dataOfKenzoHistory() else { return nil }
104 guard let kenzoMark = self.dataOfKenzoMark() else { return nil }
105 guard let dropShipHistory = self.dataOfDropShipHistory() else { return nil }
107 return (kaihatuHistory, kenzoHistory, kenzoMark, dropShipHistory)
109 guard let (kaihatuHistory, kenzoHistory, kenzoMark, dropShipHistory) = data else { return }
111 let fileW = FileWrapper(directoryWithFileWrappers: [:])
112 fileW.addRegularFile(withContents: kaihatuHistory, preferredFilename: "kaihatu.tsv")
113 fileW.addRegularFile(withContents: kenzoHistory, preferredFilename: "kenzo.tsv")
114 fileW.addRegularFile(withContents: kenzoMark, preferredFilename: "kenzoMark.tsv")
115 fileW.addRegularFile(withContents: dropShipHistory, preferredFilename: "dropShip.tsv")
118 try fileW.write(to: url, originalContentsURL: nil)
122 print("Error to write")
127 private func localData<T, Value>(_ entity: Entity<T>, sortBy: KeyPath<T, Value>) -> [T] {
129 let sortDesc = SortDescriptors(keyPath: sortBy, ascending: true)
131 guard let array = try? store.objects(of: entity, sortDescriptors: sortDesc) else {
133 print("Can not get \(entity)")
140 private func dataOfKaihatuHistory() -> Data? {
142 return localData(KaihatuHistory.entity, sortBy: \KaihatuHistory.date)
150 .append($0.kaihatusizai)
152 .append($0.flagShipName)
153 .append($0.flagShipLv)
154 .append($0.commanderLv)
157 .joined(separator: "\n")
161 private func dataOfKenzoHistory() -> Data? {
163 return localData(KenzoHistory.entity, sortBy: \KenzoHistory.date)
171 .append($0.kaihatusizai)
174 .append($0.flagShipName)
175 .append($0.flagShipLv)
176 .append($0.commanderLv)
179 .joined(separator: "\n")
183 private func dataOfKenzoMark() -> Data? {
185 return localData(KenzoMark.entity, sortBy: \KenzoMark.kDockId)
193 .append($0.kaihatusizai)
194 .append($0.created_ship_id)
196 .append($0.flagShipName)
197 .append($0.flagShipLv)
198 .append($0.commanderLv)
201 .joined(separator: "\n")
205 private func dataOfDropShipHistory() -> Data? {
207 return localData(DropShipHistory.entity, sortBy: \DropShipHistory.date)
215 .append($0.mapAreaName)
216 .append($0.mapInfoName)
221 .joined(separator: "\n")
225 private func registerKaihatuHistory(_ data: Data) {
227 let array = String(data: data, encoding: .utf8)?.components(separatedBy: "\n")
230 let attr = $0.components(separatedBy: "\t")
232 guard attr.count == 10 else { return }
233 guard let date = dateFomatter.date(from: attr[0]) else { return }
234 guard let fuel = Int(attr[1]) else { return }
235 guard let bull = Int(attr[2]) else { return }
236 guard let steel = Int(attr[3]) else { return }
237 guard let bauxite = Int(attr[4]) else { return }
238 guard let kaihatu = Int(attr[5]) else { return }
239 guard let flagLv = Int(attr[8]) else { return }
240 guard let commandLv = Int(attr[9]) else { return }
242 let predicate = Predicate(\KaihatuHistory.date, equalTo: date)
244 guard let oo = try? store.objects(of: KaihatuHistory.entity, predicate: predicate) else { return }
245 guard oo.count != 0 else { return }
246 guard let obj = store.insertNewObject(for: KaihatuHistory.entity) else { return }
252 obj.bauxite = bauxite
253 obj.kaihatusizai = kaihatu
255 obj.flagShipName = attr[7]
256 obj.flagShipLv = flagLv
257 obj.commanderLv = commandLv
261 private func registerKenzoHistory(_ data: Data) {
263 let array = String(data: data, encoding: .utf8)?.components(separatedBy: "\n")
267 let attr = $0.components(separatedBy: "\t")
269 guard attr.count == 11 else { return }
270 guard let date = dateFomatter.date(from: attr[0]) else { return }
271 guard let fuel = Int(attr[1]) else { return }
272 guard let bull = Int(attr[2]) else { return }
273 guard let steel = Int(attr[3]) else { return }
274 guard let bauxite = Int(attr[4]) else { return }
275 guard let kaihatu = Int(attr[5]) else { return }
276 guard let sType = Int(attr[7]) else { return }
277 guard let flagLv = Int(attr[9]) else { return }
278 guard let commandLv = Int(attr[10]) else { return }
280 let predicate = Predicate(\KenzoHistory.date, equalTo: date)
282 guard let oo = try? store.objects(of: KenzoHistory.entity, predicate: predicate) else { return }
283 guard oo.count != 0 else { return }
284 guard let obj = store.insertNewObject(for: KenzoHistory.entity) else { return }
290 obj.bauxite = bauxite
291 obj.kaihatusizai = kaihatu
294 obj.flagShipName = attr[8]
295 obj.flagShipLv = flagLv
296 obj.commanderLv = commandLv
300 private func registerKenzoMark( _ data: Data) {
302 let array = String(data: data, encoding: .utf8)?.components(separatedBy: "\n")
306 let attr = $0.components(separatedBy: "\t")
308 guard attr.count == 11 else { return }
309 guard let date = dateFomatter.date(from: attr[0]) else { return }
310 guard let fuel = Int(attr[1]) else { return }
311 guard let bull = Int(attr[2]) else { return }
312 guard let steel = Int(attr[3]) else { return }
313 guard let bauxite = Int(attr[4]) else { return }
314 guard let kaihatu = Int(attr[5]) else { return }
315 guard let shiId = Int(attr[6]) else { return }
316 guard let kDock = Int(attr[7]) else { return }
317 guard let flagLv = Int(attr[9]) else { return }
318 guard let commandLv = Int(attr[10]) else { return }
320 let predicate = Predicate(\KenzoMark.date, equalTo: date)
322 guard let oo = try? store.objects(of: KenzoMark.entity, predicate: predicate) else { return }
323 guard oo.count != 0 else { return }
324 guard let obj = store.insertNewObject(for: KenzoMark.entity) else { return }
330 obj.bauxite = bauxite
331 obj.kaihatusizai = kaihatu
332 obj.created_ship_id = shiId
334 obj.flagShipName = attr[8]
335 obj.flagShipLv = flagLv
336 obj.commanderLv = commandLv
340 private func registerDropShipHistory( _ data: Data) {
342 let array = String(data: data, encoding: .utf8)?.components(separatedBy: "\n")
346 let attr = $0.components(separatedBy: "\t")
348 guard attr.count == 9 else { return }
349 guard let date = dateFomatter.date(from: attr[0]) else { return }
350 guard let mapInfo = Int(attr[3]) else { return }
351 guard let mapCell = Int(attr[4]) else { return }
352 guard let mark = Int(attr[7]) else { return }
354 let predicate = Predicate(\DropShipHistory.date, equalTo: date)
356 guard let oo = try? store.objects(of: DropShipHistory.entity, predicate: predicate) else { return }
357 guard oo.count != 0 else { return }
358 guard let obj = store.insertNewObject(for: DropShipHistory.entity) else { return }
361 obj.shipName = attr[1]
362 obj.mapArea = attr[2]
363 obj.mapInfo = mapInfo
364 obj.mapCell = mapCell
365 obj.mapAreaName = attr[5]
366 obj.mapInfoName = attr[6]
368 obj.winRank = attr[8]