@capgo/capacitor-updater 3.1.0 → 3.3.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -22,6 +22,11 @@ public class AppVersion: NSObject {
22
22
  var message: String?
23
23
  var major: Bool?
24
24
  }
25
+ extension OperatingSystemVersion {
26
+ func getFullVersion(separator: String = ".") -> String {
27
+ return "\(majorVersion)\(separator)\(minorVersion)\(separator)\(patchVersion)"
28
+ }
29
+ }
25
30
  extension Bundle {
26
31
  var releaseVersionNumber: String? {
27
32
  return infoDictionary?["CFBundleShortVersionString"] as? String
@@ -31,15 +36,36 @@ extension Bundle {
31
36
  }
32
37
  }
33
38
 
39
+ enum CustomError: Error {
40
+ // Throw when an unzip fail
41
+ case cannotUnzip
42
+
43
+ // Throw in all other cases
44
+ case unexpected(code: Int)
45
+ }
46
+
47
+ extension CustomError: LocalizedError {
48
+ public var errorDescription: String? {
49
+ switch self {
50
+ case .cannotUnzip:
51
+ return NSLocalizedString(
52
+ "The file cannot be unzip",
53
+ comment: "Invalid zip"
54
+ )
55
+ case .unexpected(_):
56
+ return NSLocalizedString(
57
+ "An unexpected error occurred.",
58
+ comment: "Unexpected Error"
59
+ )
60
+ }
61
+ }
62
+ }
63
+
34
64
  @objc public class CapacitorUpdater: NSObject {
35
65
 
36
- public var statsUrl = ""
37
- public var appId = ""
38
- public var deviceID = UIDevice.current.identifierForVendor?.uuidString ?? ""
39
- public var notifyDownload: (Int) -> Void = { _ in }
40
- public var pluginVersion = "3.1.0"
41
66
  private var versionBuild = Bundle.main.releaseVersionNumber ?? ""
42
67
  private var versionCode = Bundle.main.buildVersionNumber ?? ""
68
+ private var versionOs = ProcessInfo().operatingSystemVersion.getFullVersion()
43
69
  private var lastPathHot = ""
44
70
  private var lastPathPersist = ""
45
71
  private let basePathHot = "versions"
@@ -47,11 +73,17 @@ extension Bundle {
47
73
  private let documentsUrl = FileManager.default.urls(for: .documentDirectory, in: .userDomainMask).first!
48
74
  private let libraryUrl = FileManager.default.urls(for: .libraryDirectory, in: .userDomainMask).first!
49
75
 
50
- @objc private func calcTotalPercent(percent: Int, min: Int, max: Int) -> Int {
76
+ public var statsUrl = ""
77
+ public var appId = ""
78
+ public var deviceID = UIDevice.current.identifierForVendor?.uuidString ?? ""
79
+ public var notifyDownload: (Int) -> Void = { _ in }
80
+ public var pluginVersion = "3.2.0"
81
+
82
+ private func calcTotalPercent(percent: Int, min: Int, max: Int) -> Int {
51
83
  return (percent * (max - min)) / 100 + min;
52
84
  }
53
85
 
54
- @objc private func randomString(length: Int) -> String {
86
+ private func randomString(length: Int) -> String {
55
87
  let letters = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789"
56
88
  return String((0..<length).map{ _ in letters.randomElement()! })
57
89
  }
@@ -95,17 +127,19 @@ extension Bundle {
95
127
  }
96
128
  }
97
129
 
98
- private func saveDownloaded(sourceZip: URL, version: String, base: URL) {
130
+ private func saveDownloaded(sourceZip: URL, version: String, base: URL) throws {
99
131
  prepareFolder(source: base)
100
132
  let destHot = base.appendingPathComponent(version)
101
133
  let destUnZip = documentsUrl.appendingPathComponent(randomString(length: 10))
102
- SSZipArchive.unzipFile(atPath: sourceZip.path, toDestination: destUnZip.path)
134
+ if (!SSZipArchive.unzipFile(atPath: sourceZip.path, toDestination: destUnZip.path)) {
135
+ throw CustomError.cannotUnzip
136
+ }
103
137
  if (unflatFolder(source: destUnZip, dest: destHot)) {
104
138
  deleteFolder(source: destUnZip)
105
139
  }
106
140
  }
107
141
 
108
- @objc public func getLatest(url: URL) -> AppVersion? {
142
+ public func getLatest(url: URL) -> AppVersion? {
109
143
  let semaphore = DispatchSemaphore(value: 0)
110
144
  let latest = AppVersion()
111
145
  let headers: HTTPHeaders = [
@@ -114,6 +148,7 @@ extension Bundle {
114
148
  "cap_app_id": self.appId,
115
149
  "cap_version_build": self.versionBuild,
116
150
  "cap_version_code": self.versionCode,
151
+ "cap_version_os": self.versionOs,
117
152
  "cap_plugin_version": self.pluginVersion,
118
153
  "cap_version_name": UserDefaults.standard.string(forKey: "versionName") ?? "builtin"
119
154
  ]
@@ -143,9 +178,10 @@ extension Bundle {
143
178
  return latest.url != "" ? latest : nil
144
179
  }
145
180
 
146
- @objc public func download(url: URL) -> String? {
181
+ public func download(url: URL) throws -> String {
147
182
  let semaphore = DispatchSemaphore(value: 0)
148
- var version: String? = nil
183
+ var version: String = ""
184
+ var mainError: NSError? = nil
149
185
  let destination: DownloadRequest.Destination = { _, _ in
150
186
  let documentsURL = FileManager.default.urls(for: .documentDirectory, in: .userDomainMask)[0]
151
187
  let fileURL = documentsURL.appendingPathComponent(self.randomString(length: 10))
@@ -164,24 +200,32 @@ extension Bundle {
164
200
  case .success:
165
201
  self.notifyDownload(71);
166
202
  version = self.randomString(length: 10)
167
- self.saveDownloaded(sourceZip: fileURL, version: version!, base: self.documentsUrl.appendingPathComponent(self.basePathHot))
168
- self.notifyDownload(85);
169
- self.saveDownloaded(sourceZip: fileURL, version: version!, base: self.libraryUrl.appendingPathComponent(self.basePathPersist))
170
- self.notifyDownload(100);
171
- self.deleteFolder(source: fileURL)
203
+ do {
204
+ try self.saveDownloaded(sourceZip: fileURL, version: version, base: self.documentsUrl.appendingPathComponent(self.basePathHot))
205
+ self.notifyDownload(85);
206
+ try self.saveDownloaded(sourceZip: fileURL, version: version, base: self.libraryUrl.appendingPathComponent(self.basePathPersist))
207
+ self.notifyDownload(100);
208
+ self.deleteFolder(source: fileURL)
209
+ } catch {
210
+ print("✨ Capacitor-updater: download unzip error", error)
211
+ mainError = error as NSError
212
+ }
172
213
  case let .failure(error):
173
214
  print("✨ Capacitor-updater: download error", error)
174
- version = nil
215
+ mainError = error as NSError
175
216
  }
176
217
  }
177
218
  semaphore.signal()
178
219
  }
179
220
  self.notifyDownload(0);
180
221
  semaphore.wait()
222
+ if (mainError != nil) {
223
+ throw mainError!
224
+ }
181
225
  return version
182
226
  }
183
227
 
184
- @objc public func list() -> [String] {
228
+ public func list() -> [String] {
185
229
  let dest = documentsUrl.appendingPathComponent(basePathHot)
186
230
  do {
187
231
  let files = try FileManager.default.contentsOfDirectory(atPath: dest.path)
@@ -192,7 +236,7 @@ extension Bundle {
192
236
  }
193
237
  }
194
238
 
195
- @objc public func delete(version: String, versionName: String) -> Bool {
239
+ public func delete(version: String, versionName: String) -> Bool {
196
240
  let destHot = documentsUrl.appendingPathComponent(basePathHot).appendingPathComponent(version)
197
241
  let destPersist = libraryUrl.appendingPathComponent(basePathPersist).appendingPathComponent(version)
198
242
  do {
@@ -210,7 +254,7 @@ extension Bundle {
210
254
  return true
211
255
  }
212
256
 
213
- @objc public func set(version: String, versionName: String) -> Bool {
257
+ public func set(version: String, versionName: String) -> Bool {
214
258
  let destHot = documentsUrl.appendingPathComponent(basePathHot).appendingPathComponent(version)
215
259
  let indexHot = destHot.appendingPathComponent("index.html")
216
260
  let destHotPersist = libraryUrl.appendingPathComponent(basePathPersist).appendingPathComponent(version)
@@ -226,19 +270,19 @@ extension Bundle {
226
270
  return false
227
271
  }
228
272
 
229
- @objc public func getLastPathHot() -> String {
273
+ public func getLastPathHot() -> String {
230
274
  return UserDefaults.standard.string(forKey: "lastPathHot") ?? ""
231
275
  }
232
276
 
233
- @objc public func getVersionName() -> String {
277
+ public func getVersionName() -> String {
234
278
  return UserDefaults.standard.string(forKey: "versionName") ?? ""
235
279
  }
236
280
 
237
- @objc public func getLastPathPersist() -> String {
281
+ public func getLastPathPersist() -> String {
238
282
  return UserDefaults.standard.string(forKey: "lastPathPersist") ?? ""
239
283
  }
240
284
 
241
- @objc public func reset() {
285
+ public func reset() {
242
286
  let version = UserDefaults.standard.string(forKey: "versionName") ?? ""
243
287
  sendStats(action: "reset", version: version)
244
288
  UserDefaults.standard.set("", forKey: "lastPathHot")
@@ -247,7 +291,7 @@ extension Bundle {
247
291
  UserDefaults.standard.synchronize()
248
292
  }
249
293
 
250
- @objc func sendStats(action: String, version: String) {
294
+ func sendStats(action: String, version: String) {
251
295
  if (statsUrl == "") { return }
252
296
  let parameters: [String: String] = [
253
297
  "platform": "ios",
@@ -256,6 +300,7 @@ extension Bundle {
256
300
  "version_name": version,
257
301
  "version_build": self.versionBuild,
258
302
  "version_code": self.versionCode,
303
+ "version_os": self.versionOs,
259
304
  "plugin_version": self.pluginVersion,
260
305
  "app_id": self.appId
261
306
  ]
@@ -65,16 +65,20 @@ public class CapacitorUpdaterPlugin: CAPPlugin {
65
65
  @objc func getId(_ call: CAPPluginCall) {
66
66
  call.resolve(["id": implementation.deviceID])
67
67
  }
68
+
69
+ @objc func getPluginVersion(_ call: CAPPluginCall) {
70
+ call.resolve(["version": implementation.pluginVersion])
71
+ }
68
72
 
69
73
  @objc func download(_ call: CAPPluginCall) {
70
74
  let url = URL(string: call.getString("url") ?? "")
71
- let res = implementation.download(url: url!)
72
- if ((res) != nil) {
75
+ do {
76
+ let res = try implementation.download(url: url!)
73
77
  call.resolve([
74
- "version": res!
78
+ "version": res
75
79
  ])
76
- } else {
77
- call.reject("download failed")
80
+ } catch {
81
+ call.reject("download failed", error.localizedDescription)
78
82
  }
79
83
  }
80
84
 
@@ -221,14 +225,14 @@ public class CapacitorUpdaterPlugin: CAPPlugin {
221
225
  print("✨ Capacitor-updater: Cannot get version \(failingVersion) \(newVersion)")
222
226
  }
223
227
  if (newVersion != "0.0.0" && newVersion != failingVersion) {
224
- let dlOp = self.implementation.download(url: downloadUrl)
225
- if let dl = dlOp {
228
+ do {
229
+ let dl = try self.implementation.download(url: downloadUrl)
226
230
  print("✨ Capacitor-updater: New version: \(newVersion) found. Current is \(currentVersion == "" ? "builtin" : currentVersion), next backgrounding will trigger update")
227
231
  UserDefaults.standard.set(dl, forKey: "nextVersion")
228
232
  UserDefaults.standard.set(newVersion.description, forKey: "nextVersionName")
229
233
  self.notifyListeners("updateAvailable", data: ["version": newVersion])
230
- } else {
231
- print("✨ Capacitor-updater: Download version \(newVersion) fail")
234
+ } catch {
235
+ print("✨ Capacitor-updater: Download version \(newVersion) fail", error.localizedDescription)
232
236
  }
233
237
  } else {
234
238
  print("✨ Capacitor-updater: No need to update, \(currentVersion) is the latest")
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@capgo/capacitor-updater",
3
- "version": "3.1.0",
3
+ "version": "3.3.0",
4
4
  "license": "AGPL-3.0-only",
5
5
  "description": "OTA update for capacitor apps",
6
6
  "main": "dist/plugin.cjs.js",