Skip to content

Commit 78dfa07

Browse files
CrownedPhoenixJairon TerrerostevensJourney
authored
feat: Add PowerSyncDataConvertible protocol (#84)
* feat: Add PowerSyncDataConvertible protocol This enables downstream consumers to define how certain types should be mapped to those that are supported by the PowerSync Kotlin Multiplatform SDK. * Update Sources/PowerSync/Kotlin/db/PowerSyncDataTypeConvertible.swift --------- Co-authored-by: Jairon Terrero <jairon@passivelogic.com> Co-authored-by: stevensJourney <51082125+stevensJourney@users.noreply.github.com>
1 parent 1248391 commit 78dfa07

File tree

3 files changed

+65
-1
lines changed

3 files changed

+65
-1
lines changed

Sources/PowerSync/Kotlin/db/KotlinConnectionContext.swift

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -97,6 +97,11 @@ final class KotlinTransactionContext: Transaction, KotlinConnectionContextProtoc
9797
// Allows nil values to be passed to the Kotlin [Any] params
9898
func mapParameters(_ parameters: [Any?]?) -> [Any] {
9999
parameters?.map { item in
100-
item ?? NSNull()
100+
switch item {
101+
case .none: NSNull()
102+
case let item as PowerSyncDataTypeConvertible:
103+
item.psDataType?.unwrap() ?? NSNull()
104+
default: item
105+
}
101106
} ?? []
102107
}
Lines changed: 32 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,32 @@
1+
import struct Foundation.Data
2+
3+
/// Represents the set of types that are supported
4+
/// by the PowerSync Kotlin Multiplatform SDK
5+
public enum PowerSyncDataType {
6+
case bool(Bool)
7+
case string(String)
8+
case int64(Int64)
9+
case int32(Int32)
10+
case double(Double)
11+
case data(Data)
12+
}
13+
14+
/// Types conforming to this protocol will be
15+
/// mapped to the specified ``PowerSyncDataType``
16+
/// before use by SQLite
17+
public protocol PowerSyncDataTypeConvertible {
18+
var psDataType: PowerSyncDataType? { get }
19+
}
20+
21+
extension PowerSyncDataType {
22+
func unwrap() -> Any {
23+
switch self {
24+
case let .bool(bool): bool
25+
case let .string(string): string
26+
case let .int32(int32): int32
27+
case let .int64(int64): int64
28+
case let .double(double): double
29+
case let .data(data): data
30+
}
31+
}
32+
}

Tests/PowerSyncTests/Kotlin/KotlinPowerSyncDatabaseImplTests.swift

Lines changed: 27 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,5 @@
11
@testable import PowerSync
2+
import struct Foundation.UUID
23
import XCTest
34

45
final class KotlinPowerSyncDatabaseImplTests: XCTestCase {
@@ -156,6 +157,25 @@ final class KotlinPowerSyncDatabaseImplTests: XCTestCase {
156157
}
157158
}
158159

160+
func testCustomDataTypeConvertible() async throws {
161+
let uuid = UUID()
162+
try await database.execute(
163+
sql: "INSERT INTO users (id, name, email) VALUES (?, ?, ?)",
164+
parameters: [uuid, "Test User", "test@example.com"]
165+
)
166+
167+
let _ = try await database.getOptional(
168+
sql: "SELECT id, name, email FROM users WHERE id = ?",
169+
parameters: [uuid]
170+
) { cursor throws in
171+
try (
172+
cursor.getString(name: "id"),
173+
cursor.getString(name: "name"),
174+
cursor.getString(name: "email")
175+
)
176+
}
177+
}
178+
159179
func testGetAll() async throws {
160180
try await database.execute(
161181
sql: "INSERT INTO users (id, name, email) VALUES (?, ?, ?), (?, ?, ?)",
@@ -698,3 +718,10 @@ final class KotlinPowerSyncDatabaseImplTests: XCTestCase {
698718
try deleteSQLiteFiles(dbFilename: testDbFilename, in: databaseDirectory)
699719
}
700720
}
721+
722+
723+
extension UUID: @retroactive PowerSyncDataTypeConvertible {
724+
public var psDataType: PowerSyncDataType? {
725+
.string(uuidString)
726+
}
727+
}

0 commit comments

Comments
 (0)