@procivis/react-native-one-core 1.41710.0 → 1.52682.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.
Files changed (36) hide show
  1. package/android/src/main/java/ch/procivis/one/core/DeserializeSpecific.kt +4 -2
  2. package/android/src/main/java/ch/procivis/one/core/ProcivisOneCoreModule.kt +45 -12
  3. package/android/src/main/java/ch/procivis/one/core/Serialize.kt +3 -1
  4. package/android/src/main/java/ch/procivis/one/core/SerializeSpecific.kt +13 -0
  5. package/core-sdk.json +6 -6
  6. package/dist/src/config.d.ts +17 -2
  7. package/dist/src/config.js +9 -0
  8. package/dist/src/core.d.ts +15 -9
  9. package/dist/src/core.js +6 -1
  10. package/dist/src/credential.d.ts +6 -6
  11. package/dist/src/history.d.ts +6 -3
  12. package/dist/src/history.js +3 -0
  13. package/dist/src/identifier.d.ts +125 -0
  14. package/dist/src/identifier.js +29 -0
  15. package/dist/src/key.d.ts +0 -3
  16. package/dist/src/organisation.d.ts +2 -1
  17. package/dist/src/proof.d.ts +11 -9
  18. package/dist/src/trust.d.ts +44 -4
  19. package/dist/src/trust.js +5 -0
  20. package/ios/Deserialize.swift +140 -813
  21. package/ios/EventEmitter.swift +84 -72
  22. package/ios/ProcivisOneCoreModule.m +23 -6
  23. package/ios/ProcivisOneCoreModule.swift +981 -805
  24. package/ios/ProcivisRNOneCore.xcodeproj/project.pbxproj +9 -1
  25. package/ios/RNDecoder/RNDecoder.swift +191 -0
  26. package/ios/RNDecoder/RNDecodingStorage.swift +33 -0
  27. package/ios/RNDecoder/RNKeyedDecodingContainer.swift +133 -0
  28. package/ios/RNDecoder/RNUnkeyedDecodingContainer.swift +175 -0
  29. package/ios/RNEncoder/RNAnyCodingKey.swift +31 -0
  30. package/ios/RNEncoder/RNEncoder.swift +95 -0
  31. package/ios/RNEncoder/RNKeyedEncodingContainer.swift +81 -0
  32. package/ios/RNEncoder/RNSingleValueEncodingContainer.swift +78 -0
  33. package/ios/RNEncoder/RNUnkeyedEncodingContainer.swift +84 -0
  34. package/ios/Serialize.swift +46 -615
  35. package/ios/Util.swift +35 -25
  36. package/package.json +4 -2
@@ -3,7 +3,7 @@
3
3
  archiveVersion = 1;
4
4
  classes = {
5
5
  };
6
- objectVersion = 54;
6
+ objectVersion = 70;
7
7
  objects = {
8
8
 
9
9
  /* Begin PBXBuildFile section */
@@ -49,6 +49,10 @@
49
49
  33F2711A292F97400090E4DB /* ProcivisOneCoreModule.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = ProcivisOneCoreModule.swift; sourceTree = "<group>"; };
50
50
  /* End PBXFileReference section */
51
51
 
52
+ /* Begin PBXFileSystemSynchronizedRootGroup section */
53
+ 33CF268B2CB97A5700E95B65 /* RNEncoder */ = {isa = PBXFileSystemSynchronizedRootGroup; explicitFileTypes = {}; explicitFolders = (); path = RNEncoder; sourceTree = "<group>"; };
54
+ /* End PBXFileSystemSynchronizedRootGroup section */
55
+
52
56
  /* Begin PBXFrameworksBuildPhase section */
53
57
  58B511D81A9E6C8500147676 /* Frameworks */ = {
54
58
  isa = PBXFrameworksBuildPhase;
@@ -79,6 +83,7 @@
79
83
  15260DEB2D561D7F00797D80 /* RSEPinPadManager.m */,
80
84
  15260DE92D561D6900797D80 /* RSEKeyStorage.swift */,
81
85
  15260DE72D561D4300797D80 /* UBQKit.xcframework */,
86
+ 33CF268B2CB97A5700E95B65 /* RNEncoder */,
82
87
  33F27119292F97400090E4DB /* ProcivisOneCoreModule.m */,
83
88
  339DE1312A4EB16300F68DE2 /* ProcivisOneCore.xcframework */,
84
89
  33F2711A292F97400090E4DB /* ProcivisOneCoreModule.swift */,
@@ -105,6 +110,9 @@
105
110
  );
106
111
  dependencies = (
107
112
  );
113
+ fileSystemSynchronizedGroups = (
114
+ 33CF268B2CB97A5700E95B65 /* RNEncoder */,
115
+ );
108
116
  name = ProcivisRNOneCore;
109
117
  productName = RCTDataManager;
110
118
  productReference = 134814201AA4EA6300B7C361 /* libProcivisRNOneCore.a */;
@@ -0,0 +1,191 @@
1
+ import Foundation
2
+
3
+ public typealias CustomDecoder = (_ value: Any, _ type: Any.Type, _ codingPath: [CodingKey]) throws
4
+ -> Any?
5
+ public let customDecoderKey = CodingUserInfoKey(rawValue: "customDecoder")!
6
+
7
+ final public class RNDecoder {
8
+ public init() {}
9
+
10
+ public var userInfo: [CodingUserInfoKey: Any] = [:]
11
+
12
+ public func decode<T: Decodable>(_ value: Any) throws -> T {
13
+ return try decode(T.self, from: value)
14
+ }
15
+
16
+ public func decode<T: Decodable>(_ type: T.Type, from data: Any) throws -> T {
17
+ let decoder = RNInternalDecoder(referencing: data, userInfo: self.userInfo)
18
+
19
+ guard let value = try decoder.unbox(data, as: type) else {
20
+ throw DecodingError.valueNotFound(
21
+ type,
22
+ DecodingError.Context(
23
+ codingPath: [],
24
+ debugDescription: "The given data did not contain a top-level value."
25
+ )
26
+ )
27
+ }
28
+
29
+ return value
30
+ }
31
+ }
32
+
33
+ // MARK: - TopLevelDecoder
34
+
35
+ #if canImport(Combine)
36
+ import Combine
37
+
38
+ extension RNDecoder: TopLevelDecoder {
39
+ public typealias Input = Any
40
+ }
41
+ #endif
42
+
43
+ // MARK: -
44
+
45
+ class RNInternalDecoder {
46
+ internal var storage: RNDecodingStorage
47
+ internal let userInfo: [CodingUserInfoKey: Any]
48
+ internal(set) public var codingPath: [CodingKey]
49
+
50
+ internal init(
51
+ referencing container: Any,
52
+ at codingPath: [CodingKey] = [],
53
+ userInfo: [CodingUserInfoKey: Any]
54
+ ) {
55
+ self.storage = RNDecodingStorage()
56
+ self.storage.push(container: container)
57
+ self.codingPath = codingPath
58
+ self.userInfo = userInfo
59
+ }
60
+ }
61
+
62
+ extension RNInternalDecoder: Decoder {
63
+ func container<Key>(keyedBy type: Key.Type) throws -> KeyedDecodingContainer<Key>
64
+ where Key: CodingKey {
65
+ guard !(self.storage.topContainer is NSNull) else {
66
+ throw DecodingError.valueNotFound(
67
+ KeyedDecodingContainer<Key>.self,
68
+ DecodingError.Context(
69
+ codingPath: self.codingPath,
70
+ debugDescription: "Cannot get keyed decoding container -- found null value instead."
71
+ )
72
+ )
73
+ }
74
+
75
+ guard let topContainer = self.storage.topContainer as? [String: Any] else {
76
+ let description =
77
+ "Expected to decode \([String : Any].self) but found '\(self.storage.topContainer)' instead."
78
+ throw DecodingError.typeMismatch(
79
+ [String: Any].self,
80
+ DecodingError.Context(codingPath: self.codingPath, debugDescription: description)
81
+ )
82
+ }
83
+
84
+ let container = RNKeyedDecodingContainer<Key>(referencing: self, wrapping: topContainer)
85
+ return KeyedDecodingContainer(container)
86
+ }
87
+
88
+ func unkeyedContainer() throws -> any UnkeyedDecodingContainer {
89
+ guard !(self.storage.topContainer is NSNull) else {
90
+ throw DecodingError.valueNotFound(
91
+ UnkeyedDecodingContainer.self,
92
+ DecodingError.Context(
93
+ codingPath: self.codingPath,
94
+ debugDescription: "Cannot get unkeyed decoding container -- found null value instead."
95
+ )
96
+ )
97
+ }
98
+
99
+ let topContainer: [Any]
100
+
101
+ if let container = self.storage.topContainer as? [Any] {
102
+ topContainer = container
103
+ } else if let container = self.storage.topContainer as? [AnyHashable: Any] {
104
+ topContainer = [container]
105
+ } else {
106
+ let description =
107
+ "Expected to decode \([Any].self) but found '\(self.storage.topContainer)' instead."
108
+ throw DecodingError.typeMismatch(
109
+ [Any].self,
110
+ DecodingError.Context(codingPath: self.codingPath, debugDescription: description)
111
+ )
112
+ }
113
+
114
+ return RNUnkeyedDecodingContainer(referencing: self, wrapping: topContainer)
115
+ }
116
+
117
+ public func singleValueContainer() throws -> SingleValueDecodingContainer {
118
+ return self
119
+ }
120
+ }
121
+
122
+ extension RNInternalDecoder: SingleValueDecodingContainer {
123
+ private func expectNonNull<T>(_ type: T.Type) throws {
124
+ guard !self.decodeNil() else {
125
+ throw DecodingError.valueNotFound(
126
+ type,
127
+ DecodingError.Context(
128
+ codingPath: self.codingPath,
129
+ debugDescription: "Expected \(type) but found null value instead."
130
+ )
131
+ )
132
+ }
133
+ }
134
+
135
+ public func decodeNil() -> Bool {
136
+ return self.storage.topContainer is NSNull
137
+ }
138
+
139
+ public func decode<T: Decodable>(_ type: T.Type) throws -> T {
140
+ try expectNonNull(type)
141
+ return try self.unbox(self.storage.topContainer, as: type)!
142
+ }
143
+ }
144
+
145
+ extension RNInternalDecoder {
146
+ internal func unbox<T: Decodable>(_ value: Any, as type: T.Type) throws -> T? {
147
+ if let customDecoder = self.userInfo[customDecoderKey] {
148
+ if let result = try (customDecoder as! CustomDecoder)(value, type, self.codingPath) {
149
+ return (result as! T)
150
+ }
151
+ }
152
+
153
+ if type == String.self || type == Bool.self || type is any Numeric.Type {
154
+ guard let data = value as? T else {
155
+ let description = "Expected to decode \(type) but found '\(value)' instead."
156
+ throw DecodingError.typeMismatch(
157
+ type,
158
+ DecodingError.Context(codingPath: self.codingPath, debugDescription: description)
159
+ )
160
+ }
161
+ return data
162
+ }
163
+
164
+ if let enumType = type as? any CaseIterable.Type {
165
+ guard let data = value as? String else {
166
+ let description = "Expected to decode \(type) but found '\(value)' instead."
167
+ throw DecodingError.typeMismatch(
168
+ type,
169
+ DecodingError.Context(codingPath: self.codingPath, debugDescription: description)
170
+ )
171
+ }
172
+
173
+ let match = enumType.allCases.first {
174
+ return serializeEnumValue(value: $0) == data
175
+ }
176
+
177
+ guard let result = match as? T else {
178
+ let description = "Expected to decode \(type) but found '\(value)' instead."
179
+ throw DecodingError.typeMismatch(
180
+ type,
181
+ DecodingError.Context(codingPath: self.codingPath, debugDescription: description)
182
+ )
183
+ }
184
+ return result
185
+ }
186
+
187
+ self.storage.push(container: value)
188
+ defer { self.storage.popContainer() }
189
+ return try type.init(from: self)
190
+ }
191
+ }
@@ -0,0 +1,33 @@
1
+ import Foundation
2
+
3
+ internal struct RNDecodingStorage {
4
+ // MARK: Properties
5
+
6
+ /// The container stack.
7
+ private(set) internal var containers: [Any] = []
8
+
9
+ // MARK: - Initialization
10
+
11
+ /// Initializes `self` with no containers.
12
+ internal init() {}
13
+
14
+ // MARK: - Modifying the Stack
15
+
16
+ internal var count: Int {
17
+ return self.containers.count
18
+ }
19
+
20
+ internal var topContainer: Any {
21
+ precondition(!self.containers.isEmpty, "Empty container stack.")
22
+ return self.containers.last!
23
+ }
24
+
25
+ internal mutating func push(container: Any) {
26
+ self.containers.append(container)
27
+ }
28
+
29
+ internal mutating func popContainer() {
30
+ precondition(!self.containers.isEmpty, "Empty container stack.")
31
+ self.containers.removeLast()
32
+ }
33
+ }
@@ -0,0 +1,133 @@
1
+ import Foundation
2
+
3
+ internal class RNKeyedDecodingContainer<Key: CodingKey> {
4
+ private let decoder: RNInternalDecoder
5
+ private let container: [String: Any]
6
+ private(set) public var codingPath: [CodingKey]
7
+
8
+ internal init(referencing decoder: RNInternalDecoder, wrapping container: [String: Any]) {
9
+ self.decoder = decoder
10
+ self.container = container
11
+ self.codingPath = decoder.codingPath
12
+ }
13
+ }
14
+
15
+ extension RNKeyedDecodingContainer: KeyedDecodingContainerProtocol {
16
+ public var allKeys: [Key] {
17
+ return self.container.keys.compactMap { Key(stringValue: $0) }
18
+ }
19
+
20
+ public func contains(_ key: Key) -> Bool {
21
+ return self.container[key.stringValue] != nil
22
+ }
23
+
24
+ public func decodeNil(forKey key: Key) throws -> Bool {
25
+ return !self.contains(key)
26
+ }
27
+
28
+ private func _errorDescription(of key: CodingKey) -> String {
29
+ return "\(key) (\"\(key.stringValue)\")"
30
+ }
31
+
32
+ func decode<T: Decodable>(_ type: T.Type, forKey key: Key) throws -> T {
33
+ guard let entry = self.container[key.stringValue] else {
34
+ throw DecodingError.keyNotFound(
35
+ key,
36
+ DecodingError.Context(
37
+ codingPath: self.decoder.codingPath,
38
+ debugDescription: "No value associated with key \(_errorDescription(of: key))."
39
+ )
40
+ )
41
+ }
42
+
43
+ self.decoder.codingPath.append(key)
44
+ defer { self.decoder.codingPath.removeLast() }
45
+
46
+ guard let value = try self.decoder.unbox(entry, as: type) else {
47
+ throw DecodingError.valueNotFound(
48
+ type,
49
+ DecodingError.Context(
50
+ codingPath: self.decoder.codingPath,
51
+ debugDescription: "Expected \(type) value but found null instead."
52
+ )
53
+ )
54
+ }
55
+
56
+ return value
57
+ }
58
+
59
+ func nestedContainer<NestedKey>(keyedBy type: NestedKey.Type, forKey key: Key) throws
60
+ -> KeyedDecodingContainer<NestedKey> where NestedKey: CodingKey
61
+ {
62
+ self.decoder.codingPath.append(key)
63
+ defer { self.decoder.codingPath.removeLast() }
64
+
65
+ guard let value = self.container[key.stringValue] else {
66
+ throw DecodingError.keyNotFound(
67
+ key,
68
+ DecodingError.Context(
69
+ codingPath: self.codingPath,
70
+ debugDescription:
71
+ "Cannot get \(KeyedDecodingContainer<NestedKey>.self) -- no value found for key \"\(key.stringValue)\""
72
+ )
73
+ )
74
+ }
75
+
76
+ guard let dictionary = value as? [String: Any] else {
77
+ let description = "Expected to decode \([String : Any].self) but found '\(value)' instead."
78
+ throw DecodingError.typeMismatch(
79
+ [String: Any].self,
80
+ DecodingError.Context(codingPath: self.codingPath, debugDescription: description)
81
+ )
82
+ }
83
+
84
+ let container = RNKeyedDecodingContainer<NestedKey>(
85
+ referencing: self.decoder,
86
+ wrapping: dictionary
87
+ )
88
+ return KeyedDecodingContainer(container)
89
+ }
90
+
91
+ func nestedUnkeyedContainer(forKey key: Key) throws -> any UnkeyedDecodingContainer {
92
+ self.decoder.codingPath.append(key)
93
+ defer { self.decoder.codingPath.removeLast() }
94
+
95
+ guard let value = self.container[key.stringValue] else {
96
+ throw DecodingError.keyNotFound(
97
+ key,
98
+ DecodingError.Context(
99
+ codingPath: self.codingPath,
100
+ debugDescription:
101
+ "Cannot get UnkeyedDecodingContainer -- no value found for key \"\(key.stringValue)\""
102
+ )
103
+ )
104
+ }
105
+
106
+ guard let array = value as? [Any] else {
107
+ let description = "Expected to decode \([Any].self) but found '\(value)' instead."
108
+ throw DecodingError.typeMismatch(
109
+ [Any].self,
110
+ DecodingError.Context(codingPath: self.codingPath, debugDescription: description)
111
+ )
112
+ }
113
+
114
+ return RNUnkeyedDecodingContainer(referencing: self.decoder, wrapping: array)
115
+ }
116
+
117
+ private func _superDecoder(forKey key: CodingKey) throws -> Decoder {
118
+ let value: Any = self.container[key.stringValue] ?? NSNull()
119
+ return RNInternalDecoder(
120
+ referencing: value,
121
+ at: self.decoder.codingPath + [key],
122
+ userInfo: self.decoder.userInfo
123
+ )
124
+ }
125
+
126
+ public func superDecoder() throws -> Decoder {
127
+ fatalError("Unimplemented")
128
+ }
129
+
130
+ public func superDecoder(forKey key: Key) throws -> Decoder {
131
+ return try _superDecoder(forKey: key)
132
+ }
133
+ }
@@ -0,0 +1,175 @@
1
+ import Foundation
2
+
3
+ internal class RNUnkeyedDecodingContainer {
4
+ private let decoder: RNInternalDecoder
5
+ private let container: [Any]
6
+ private(set) public var codingPath: [CodingKey]
7
+ private(set) public var currentIndex: Int
8
+
9
+ internal init(referencing decoder: RNInternalDecoder, wrapping container: [Any]) {
10
+ self.decoder = decoder
11
+ self.container = container
12
+ self.codingPath = decoder.codingPath
13
+ self.currentIndex = 0
14
+ }
15
+ }
16
+
17
+ extension RNUnkeyedDecodingContainer: UnkeyedDecodingContainer {
18
+ var count: Int? {
19
+ return self.container.count
20
+ }
21
+
22
+ var isAtEnd: Bool {
23
+ return self.currentIndex >= self.container.count
24
+ }
25
+
26
+ func decodeNil() throws -> Bool {
27
+ guard !self.isAtEnd else {
28
+ throw DecodingError.valueNotFound(
29
+ Any?.self,
30
+ DecodingError.Context(
31
+ codingPath: self.decoder.codingPath + [RNAnyCodingKey(intValue: self.currentIndex)],
32
+ debugDescription: "Unkeyed container is at end."
33
+ )
34
+ )
35
+ }
36
+
37
+ if self.container[self.currentIndex] is NSNull {
38
+ self.currentIndex += 1
39
+ return true
40
+ } else {
41
+ return false
42
+ }
43
+ }
44
+
45
+ func decode<T: Decodable>(_ type: T.Type) throws -> T {
46
+ guard !self.isAtEnd else {
47
+ throw DecodingError.valueNotFound(
48
+ type,
49
+ DecodingError.Context(
50
+ codingPath: self.decoder.codingPath + [RNAnyCodingKey(intValue: self.currentIndex)],
51
+ debugDescription: "Unkeyed container is at end."
52
+ )
53
+ )
54
+ }
55
+
56
+ self.decoder.codingPath.append(RNAnyCodingKey(intValue: self.currentIndex))
57
+ defer { self.decoder.codingPath.removeLast() }
58
+
59
+ guard let decoded = try self.decoder.unbox(self.container[self.currentIndex], as: type) else {
60
+ throw DecodingError.valueNotFound(
61
+ type,
62
+ DecodingError.Context(
63
+ codingPath: self.decoder.codingPath + [RNAnyCodingKey(intValue: self.currentIndex)],
64
+ debugDescription: "Expected \(type) but found null instead."
65
+ )
66
+ )
67
+ }
68
+
69
+ self.currentIndex += 1
70
+ return decoded
71
+ }
72
+
73
+ func nestedContainer<NestedKey>(keyedBy type: NestedKey.Type) throws -> KeyedDecodingContainer<
74
+ NestedKey
75
+ > where NestedKey: CodingKey {
76
+ self.decoder.codingPath.append(RNAnyCodingKey(intValue: self.currentIndex))
77
+ defer { self.decoder.codingPath.removeLast() }
78
+
79
+ guard !self.isAtEnd else {
80
+ throw DecodingError.valueNotFound(
81
+ KeyedDecodingContainer<NestedKey>.self,
82
+ DecodingError.Context(
83
+ codingPath: self.codingPath,
84
+ debugDescription: "Cannot get nested keyed container -- unkeyed container is at end."
85
+ )
86
+ )
87
+ }
88
+
89
+ let value = self.container[self.currentIndex]
90
+ guard !(value is NSNull) else {
91
+ throw DecodingError.valueNotFound(
92
+ KeyedDecodingContainer<NestedKey>.self,
93
+ DecodingError.Context(
94
+ codingPath: self.codingPath,
95
+ debugDescription: "Cannot get keyed decoding container -- found null value instead."
96
+ )
97
+ )
98
+ }
99
+
100
+ guard let dictionary = value as? [String: Any] else {
101
+ let description = "Expected to decode \([String : Any].self) but found '\(value)' instead."
102
+ throw DecodingError.typeMismatch(
103
+ [String: Any].self,
104
+ DecodingError.Context(codingPath: self.codingPath, debugDescription: description)
105
+ )
106
+ }
107
+
108
+ self.currentIndex += 1
109
+ let container = RNKeyedDecodingContainer<NestedKey>(
110
+ referencing: self.decoder,
111
+ wrapping: dictionary
112
+ )
113
+ return KeyedDecodingContainer(container)
114
+ }
115
+
116
+ func nestedUnkeyedContainer() throws -> any UnkeyedDecodingContainer {
117
+ self.decoder.codingPath.append(RNAnyCodingKey(intValue: self.currentIndex))
118
+ defer { self.decoder.codingPath.removeLast() }
119
+
120
+ guard !self.isAtEnd else {
121
+ throw DecodingError.valueNotFound(
122
+ UnkeyedDecodingContainer.self,
123
+ DecodingError.Context(
124
+ codingPath: self.codingPath,
125
+ debugDescription: "Cannot get nested keyed container -- unkeyed container is at end."
126
+ )
127
+ )
128
+ }
129
+
130
+ let value = self.container[self.currentIndex]
131
+ guard !(value is NSNull) else {
132
+ throw DecodingError.valueNotFound(
133
+ UnkeyedDecodingContainer.self,
134
+ DecodingError.Context(
135
+ codingPath: self.codingPath,
136
+ debugDescription: "Cannot get keyed decoding container -- found null value instead."
137
+ )
138
+ )
139
+ }
140
+
141
+ guard let array = value as? [Any] else {
142
+ let description = "Expected to decode \([Any].self) but found '\(value)' instead."
143
+ throw DecodingError.typeMismatch(
144
+ [Any].self,
145
+ DecodingError.Context(codingPath: self.codingPath, debugDescription: description)
146
+ )
147
+ }
148
+
149
+ self.currentIndex += 1
150
+ return RNUnkeyedDecodingContainer(referencing: self.decoder, wrapping: array)
151
+ }
152
+
153
+ func superDecoder() throws -> any Decoder {
154
+ self.decoder.codingPath.append(RNAnyCodingKey(intValue: self.currentIndex))
155
+ defer { self.decoder.codingPath.removeLast() }
156
+
157
+ guard !self.isAtEnd else {
158
+ throw DecodingError.valueNotFound(
159
+ Decoder.self,
160
+ DecodingError.Context(
161
+ codingPath: self.codingPath,
162
+ debugDescription: "Cannot get superDecoder() -- unkeyed container is at end."
163
+ )
164
+ )
165
+ }
166
+
167
+ let value = self.container[self.currentIndex]
168
+ self.currentIndex += 1
169
+ return RNInternalDecoder(
170
+ referencing: value,
171
+ at: self.decoder.codingPath,
172
+ userInfo: self.decoder.userInfo
173
+ )
174
+ }
175
+ }
@@ -0,0 +1,31 @@
1
+ struct RNAnyCodingKey: CodingKey, Equatable {
2
+ var stringValue: String
3
+ var intValue: Int?
4
+
5
+ init(stringValue: String) {
6
+ self.stringValue = stringValue
7
+ self.intValue = nil
8
+ }
9
+
10
+ init(intValue: Int) {
11
+ self.stringValue = "\(intValue)"
12
+ self.intValue = intValue
13
+ }
14
+
15
+ init<Key>(_ base: Key) where Key: CodingKey {
16
+ if let intValue = base.intValue {
17
+ self.init(intValue: intValue)
18
+ } else {
19
+ self.init(stringValue: base.stringValue)
20
+ }
21
+ }
22
+ }
23
+
24
+ extension RNAnyCodingKey: Hashable {
25
+ public func hash(into hasher: inout Hasher) {
26
+ if intValue != nil {
27
+ hasher.combine(intValue)
28
+ }
29
+ hasher.combine(stringValue)
30
+ }
31
+ }
@@ -0,0 +1,95 @@
1
+ import Foundation
2
+
3
+ public typealias CustomEncoder = (_ value: Encodable) throws -> Any?
4
+ public let customEncoderKey = CodingUserInfoKey(rawValue: "customEncoder")!
5
+
6
+ final public class RNEncoder {
7
+ public init() {}
8
+
9
+ /**
10
+ A dictionary you use to customize the encoding process
11
+ by providing contextual information.
12
+ */
13
+ public var userInfo: [CodingUserInfoKey: Any] = [:]
14
+
15
+ public func encode<T>(_ value: T) throws -> Any where T: Encodable {
16
+ if let customEncoder = self.userInfo[customEncoderKey] {
17
+ if let result = try (customEncoder as! CustomEncoder)(value) {
18
+ return result
19
+ }
20
+ }
21
+
22
+ let encoder = RNObjectEncoder(userInfo: self.userInfo)
23
+ try value.encode(to: encoder)
24
+ return encoder.data
25
+ }
26
+ }
27
+
28
+ // MARK: - TopLevelEncoder
29
+
30
+ #if canImport(Combine)
31
+ import Combine
32
+
33
+ extension RNEncoder: TopLevelEncoder {}
34
+ #endif
35
+
36
+ // MARK: -
37
+
38
+ protocol RNEncodingContainer {
39
+ var data: Any? { get }
40
+ }
41
+
42
+ class RNObjectEncoder {
43
+ var codingPath: [CodingKey] = []
44
+
45
+ var userInfo: [CodingUserInfoKey: Any] = [:]
46
+
47
+ fileprivate var container: RNEncodingContainer?
48
+
49
+ var data: Any {
50
+ return container?.data ?? NSDictionary()
51
+ }
52
+
53
+ init(userInfo: [CodingUserInfoKey: Any]) {
54
+ self.userInfo = userInfo
55
+ }
56
+ }
57
+
58
+ extension RNObjectEncoder: Encoder {
59
+ fileprivate func assertCanCreateContainer() {
60
+ precondition(self.container == nil)
61
+ }
62
+
63
+ func container<Key>(keyedBy type: Key.Type) -> KeyedEncodingContainer<Key> where Key: CodingKey {
64
+ assertCanCreateContainer()
65
+
66
+ let container = RNKeyedEncodingContainer<Key>(
67
+ codingPath: self.codingPath,
68
+ userInfo: self.userInfo
69
+ )
70
+ self.container = container
71
+
72
+ return KeyedEncodingContainer(container)
73
+ }
74
+
75
+ func unkeyedContainer() -> UnkeyedEncodingContainer {
76
+ assertCanCreateContainer()
77
+
78
+ let container = RNUnkeyedEncodingContainer(codingPath: self.codingPath, userInfo: self.userInfo)
79
+ self.container = container
80
+
81
+ return container
82
+ }
83
+
84
+ func singleValueContainer() -> SingleValueEncodingContainer {
85
+ assertCanCreateContainer()
86
+
87
+ let container = RNSingleValueEncodingContainer(
88
+ codingPath: self.codingPath,
89
+ userInfo: self.userInfo
90
+ )
91
+ self.container = container
92
+
93
+ return container
94
+ }
95
+ }