Skip to content

Commit 70e69fb

Browse files
committed
Fixed attribute decoding
1 parent e85e136 commit 70e69fb

2 files changed

Lines changed: 47 additions & 55 deletions

File tree

Sources/MongoDBModel/AttributeValue.swift

Lines changed: 41 additions & 48 deletions
Original file line numberDiff line numberDiff line change
@@ -9,64 +9,57 @@ import Foundation
99
import CoreModel
1010
import MongoSwift
1111

12-
public extension AttributeValue {
12+
internal extension AttributeValue {
1313

14-
init?(bson: BSON) {
15-
switch bson {
16-
case .document:
17-
return nil
18-
case .int32(let value):
14+
init?(bson: BSON, type: AttributeType) {
15+
switch (type, bson) {
16+
case (.int16, .int32(let value)):
17+
self = .int16(numericCast(value))
18+
case (.int16, .int64(let value)):
19+
self = .int16(numericCast(value))
20+
case (.int32, .int32(let value)):
1921
self = .int32(value)
20-
case .int64(let value):
22+
case (.int32, .int64(let value)):
23+
self = .int32(numericCast(value))
24+
case (.int64, .int64(let value)):
2125
self = .int64(value)
22-
case .decimal128:
23-
return nil
24-
case .array:
25-
return nil
26-
case .bool(let value):
26+
case (.int64, .int32(let value)):
27+
self = .int64(numericCast(value))
28+
case (.boolean, .bool(let value)):
2729
self = .bool(value)
28-
case .datetime(let date):
30+
case (.date, .datetime(let date)):
2931
self = .date(date)
30-
case .double(let double):
32+
case (.date, .timestamp(let timestamp)):
33+
self = .date(Date(timeIntervalSince1970: TimeInterval(timestamp.timestamp)))
34+
case (.double, .double(let double)):
3135
self = .double(double)
32-
case .string(let string):
36+
case (.float, .double(let double)):
37+
self = .float(Float(double))
38+
case (.string, .string(let string)):
3339
self = .string(string)
34-
case .symbol:
35-
return nil
36-
case .timestamp:
37-
return nil
38-
case .binary(let binary):
39-
switch binary.subtype {
40-
case .generic:
41-
let data = binary.data.withUnsafeReadableBytes { buffer in
42-
Data(buffer)
43-
}
44-
self = .data(data)
45-
case .uuid:
46-
guard let uuid = try? binary.toUUID() else {
47-
return nil
48-
}
49-
self = .uuid(uuid)
50-
default:
40+
case (.data, .binary(let binary)):
41+
let data = binary.data.withUnsafeReadableBytes { buffer in
42+
Data(buffer)
43+
}
44+
self = .data(data)
45+
case (.uuid, .binary(let binary)):
46+
guard let uuid = try? binary.toUUID() else {
5147
return nil
5248
}
53-
case .regex:
54-
return nil
55-
case .objectID:
56-
return nil
57-
case .dbPointer:
58-
return nil
59-
case .code:
60-
return nil
61-
case .codeWithScope:
62-
return nil
63-
case .null:
49+
self = .uuid(uuid)
50+
case (.uuid, .string(let string)):
51+
guard let uuid = UUID(uuidString: string) else {
52+
return nil
53+
}
54+
self = .uuid(uuid)
55+
case (.url, .string(let string)):
56+
guard let url = URL(string: string) else {
57+
return nil
58+
}
59+
self = .url(url)
60+
case (_, .null):
6461
self = .null
65-
case .undefined:
66-
return nil
67-
case .minKey:
68-
return nil
69-
case .maxKey:
62+
default:
7063
return nil
7164
}
7265
}

Sources/MongoDBModel/ModelData.swift

Lines changed: 6 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -16,18 +16,17 @@ public extension ModelData {
1616
self.init(entity: model.id, id: id)
1717
// decode attributes
1818
for attribute in model.attributes {
19-
let value = bson[attribute.id.rawValue]
20-
.map { AttributeValue(bson: $0) } ?? .null
19+
let attributeBSON = (bson[attribute.id.rawValue] ?? .null)
20+
guard let value = AttributeValue(bson: attributeBSON, type: attribute.type) else {
21+
throw DecodingError.typeMismatch(ModelData.self, DecodingError.Context(codingPath: [], debugDescription: "Unable to decode \(attribute.type) attribute \"\(attribute.id)\" from \(attributeBSON)"))
22+
}
2123
self.attributes[attribute.id] = value
2224
}
2325
// decode relationships
2426
for relationship in model.relationships {
2527
let relationshipBSON = bson[relationship.id.rawValue] ?? .null
26-
guard let value = RelationshipValue(
27-
bson: relationshipBSON,
28-
type: relationship.type
29-
) else {
30-
throw DecodingError.typeMismatch(ModelData.self, DecodingError.Context(codingPath: [], debugDescription: ""))
28+
guard let value = RelationshipValue(bson: relationshipBSON, type: relationship.type) else {
29+
throw DecodingError.typeMismatch(ModelData.self, DecodingError.Context(codingPath: [], debugDescription: "Unable to decode \(relationship.type) relationship \"\(relationship.id)\" from \(relationshipBSON)"))
3130
}
3231
self.relationships[relationship.id] = value
3332
}

0 commit comments

Comments
 (0)