Skip to content

Commit a1495f9

Browse files
Implement the createMap and createCounter methods
TODO test haven't done mode checking
1 parent 9b2fcc5 commit a1495f9

3 files changed

Lines changed: 103 additions & 12 deletions

File tree

Sources/AblyLiveObjects/Internal/InternalDefaultRealtimeObjects.swift

Lines changed: 75 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -164,20 +164,87 @@ internal final class InternalDefaultRealtimeObjects: Sendable, LiveMapObjectPool
164164
}
165165
}
166166

167-
internal func createMap(entries _: [String: LiveMapValue]) async throws(ARTErrorInfo) -> any LiveMap {
168-
notYetImplemented()
167+
internal func createMap(entries: [String: LiveMapValue], coreSDK: CoreSDK) async throws(ARTErrorInfo) -> any LiveMap {
168+
do {
169+
let internalEntries: [String: InternalLiveMapValue] = entries.mapValues { .init(liveMapValue: $0) }
170+
171+
// RTO11f
172+
// TODO: This is a stopgap; change to use server time per RTO11f5
173+
let timestamp = clock.now
174+
let creationOperation = ObjectCreationHelpers.creationOperationForLiveMap(
175+
entries: internalEntries,
176+
timestamp: timestamp,
177+
)
178+
179+
// RTO11g
180+
try await coreSDK.sendObject(objectMessages: [creationOperation.objectMessage])
181+
182+
// RTO11h
183+
let internalMap = mutex.withLock {
184+
mutableState.objectsPool.getOrCreateMap(
185+
creationOperation: creationOperation,
186+
logger: logger,
187+
userCallbackQueue: userCallbackQueue,
188+
clock: clock,
189+
)
190+
}
191+
192+
return PublicObjectsStore.shared.getOrCreateMap(
193+
proxying: internalMap,
194+
creationArgs: .init(
195+
coreSDK: coreSDK,
196+
delegate: self,
197+
logger: logger,
198+
),
199+
)
200+
} catch {
201+
throw error.toARTErrorInfo()
202+
}
169203
}
170204

171-
internal func createMap() async throws(ARTErrorInfo) -> any LiveMap {
172-
notYetImplemented()
205+
internal func createMap(coreSDK: CoreSDK) async throws(ARTErrorInfo) -> any LiveMap {
206+
// RTO11f4b
207+
try await createMap(entries: [:], coreSDK: coreSDK)
173208
}
174209

175-
internal func createCounter(count _: Double) async throws(ARTErrorInfo) -> any LiveCounter {
176-
notYetImplemented()
210+
internal func createCounter(count: Double, coreSDK: CoreSDK) async throws(ARTErrorInfo) -> any LiveCounter {
211+
do {
212+
// RTO12f
213+
// TODO: This is a stopgap; change to use server time per RTO12f5
214+
let timestamp = clock.now
215+
let creationOperation = ObjectCreationHelpers.creationOperationForLiveCounter(
216+
count: count,
217+
timestamp: timestamp,
218+
)
219+
220+
// RTO12g
221+
try await coreSDK.sendObject(objectMessages: [creationOperation.objectMessage])
222+
223+
// RTO12h
224+
let internalCounter = mutex.withLock {
225+
mutableState.objectsPool.getOrCreateCounter(
226+
creationOperation: creationOperation,
227+
logger: logger,
228+
userCallbackQueue: userCallbackQueue,
229+
clock: clock,
230+
)
231+
}
232+
233+
return PublicObjectsStore.shared.getOrCreateCounter(
234+
proxying: internalCounter,
235+
creationArgs: .init(
236+
coreSDK: coreSDK,
237+
logger: logger,
238+
),
239+
)
240+
} catch {
241+
throw error.toARTErrorInfo()
242+
}
177243
}
178244

179-
internal func createCounter() async throws(ARTErrorInfo) -> any LiveCounter {
180-
notYetImplemented()
245+
internal func createCounter(coreSDK: CoreSDK) async throws(ARTErrorInfo) -> any LiveCounter {
246+
// RTO12f2a
247+
try await createCounter(count: 0, coreSDK: coreSDK)
181248
}
182249

183250
internal func batch(callback _: sending BatchCallback) async throws {

Sources/AblyLiveObjects/Internal/InternalLiveMapValue.swift

Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,30 @@ internal enum InternalLiveMapValue: Sendable, Equatable {
66
case liveMap(InternalDefaultLiveMap)
77
case liveCounter(InternalDefaultLiveCounter)
88

9+
// MARK: - Creating from a public LiveMapValue
10+
11+
/// Converts a public ``LiveMapValue`` into an ``InternalLiveMapValue``.
12+
///
13+
/// Needed in order to access the internals of user-provided LiveObject-valued LiveMap entries to extract their object ID.
14+
internal init(liveMapValue: LiveMapValue) {
15+
switch liveMapValue {
16+
case let .primitive(primitiveValue):
17+
self = .primitive(primitiveValue)
18+
case let .liveMap(publicLiveMap):
19+
guard let publicDefaultLiveMap = publicLiveMap as? PublicDefaultLiveMap else {
20+
// TODO: Try and remove this runtime check and know this type statically, see https://github.com/ably/ably-cocoa-liveobjects-plugin/issues/37
21+
preconditionFailure("Expected PublicDefaultLiveMap, got \(publicLiveMap)")
22+
}
23+
self = .liveMap(publicDefaultLiveMap.proxied)
24+
case let .liveCounter(publicLiveCounter):
25+
guard let publicDefaultLiveCounter = publicLiveCounter as? PublicDefaultLiveCounter else {
26+
// TODO: Try and remove this runtime check and know this type statically, see https://github.com/ably/ably-cocoa-liveobjects-plugin/issues/37
27+
preconditionFailure("Expected PublicDefaultLiveCounter, got \(publicLiveCounter)")
28+
}
29+
self = .liveCounter(publicDefaultLiveCounter.proxied)
30+
}
31+
}
32+
933
// MARK: - Representation in the Realtime protocol
1034

1135
// TODO: document — it's RTO11f4 (for createMap) and RTLM20e4 (for set)

Sources/AblyLiveObjects/Public/Public Proxy Objects/PublicDefaultRealtimeObjects.swift

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -36,19 +36,19 @@ internal final class PublicDefaultRealtimeObjects: RealtimeObjects {
3636
}
3737

3838
internal func createMap(entries: [String: LiveMapValue]) async throws(ARTErrorInfo) -> any LiveMap {
39-
try await proxied.createMap(entries: entries)
39+
try await proxied.createMap(entries: entries, coreSDK: coreSDK)
4040
}
4141

4242
internal func createMap() async throws(ARTErrorInfo) -> any LiveMap {
43-
try await proxied.createMap()
43+
try await proxied.createMap(coreSDK: coreSDK)
4444
}
4545

4646
internal func createCounter(count: Double) async throws(ARTErrorInfo) -> any LiveCounter {
47-
try await proxied.createCounter(count: count)
47+
try await proxied.createCounter(count: count, coreSDK: coreSDK)
4848
}
4949

5050
internal func createCounter() async throws(ARTErrorInfo) -> any LiveCounter {
51-
try await proxied.createCounter()
51+
try await proxied.createCounter(coreSDK: coreSDK)
5252
}
5353

5454
internal func batch(callback: sending BatchCallback) async throws {

0 commit comments

Comments
 (0)