Fixed the remaining broken tests

pull/856/head
Morgan Pretty 1 year ago
parent f30b383bb8
commit c8a199a8ba

@ -19,16 +19,21 @@ public extension String {
init?<T>(
libSessionVal: T,
nullTerminated: Bool = true,
fixedLength: Int? = .none,
nullIfEmpty: Bool = false
) {
let result: String = {
guard !nullTerminated else {
return String(cString: withUnsafeBytes(of: libSessionVal) { [UInt8]($0) })
guard let fixedLength: Int = fixedLength else {
// Note: The `String(cString:)` function requires that the value is null-terminated
// so add a null-termination character if needed
return String(
cString: withUnsafeBytes(of: libSessionVal) { [UInt8]($0) }
.nullTerminated()
)
}
return String(
data: Data(libSessionVal: libSessionVal, count: MemoryLayout<T>.size),
data: Data(libSessionVal: libSessionVal, count: fixedLength),
encoding: .utf8
)
.defaulting(to: "")
@ -102,3 +107,11 @@ public extension Array where Element == CChar {
return self.appending(CChar(0))
}
}
public extension Array where Element == UInt8 {
func nullTerminated() -> [Element] {
guard self.last != UInt8(0) else { return self }
return self.appending(UInt8(0))
}
}

@ -32,7 +32,7 @@ class ConfigContactsSpec: QuickSpec {
error?.deallocate()
// Empty contacts shouldn't have an existing contact
var definitelyRealId: String = "050000000000000000000000000000000000000000000000000000000000000000"
let definitelyRealId: String = "050000000000000000000000000000000000000000000000000000000000000000"
var cDefinitelyRealId: [CChar] = definitelyRealId.cArray
let contactPtr: UnsafeMutablePointer<contacts_contact>? = nil
expect(contacts_get(conf, contactPtr, &cDefinitelyRealId)).to(beFalse())
@ -75,7 +75,7 @@ class ConfigContactsSpec: QuickSpec {
// Ensure the contact details were updated
var contact3: contacts_contact = contacts_contact()
expect(contacts_get(conf, &contact3, &definitelyRealId)).to(beTrue())
expect(contacts_get(conf, &contact3, &cDefinitelyRealId)).to(beTrue())
expect(String(libSessionVal: contact3.name)).to(equal("Joe"))
expect(String(libSessionVal: contact3.nickname)).to(equal("Joey"))
expect(contact3.approved).to(beTrue())
@ -129,7 +129,7 @@ class ConfigContactsSpec: QuickSpec {
// Ensure the contact details were updated
var contact4: contacts_contact = contacts_contact()
expect(contacts_get(conf2, &contact4, &definitelyRealId)).to(beTrue())
expect(contacts_get(conf2, &contact4, &cDefinitelyRealId)).to(beTrue())
expect(String(libSessionVal: contact4.name)).to(equal("Joe"))
expect(String(libSessionVal: contact4.nickname)).to(equal("Joey"))
expect(contact4.approved).to(beTrue())
@ -138,7 +138,7 @@ class ConfigContactsSpec: QuickSpec {
expect(String(libSessionVal: contact4.profile_pic.url)).to(beEmpty())
expect(contact4.blocked).to(beFalse())
var anotherId: String = "051111111111111111111111111111111111111111111111111111111111111111"
let anotherId: String = "051111111111111111111111111111111111111111111111111111111111111111"
var cAnotherId: [CChar] = anotherId.cArray
var contact5: contacts_contact = contacts_contact()
expect(contacts_get_or_construct(conf2, &contact5, &cAnotherId)).to(beTrue())
@ -201,7 +201,7 @@ class ConfigContactsSpec: QuickSpec {
contacts_erase(conf, definitelyRealId)
// Client 2 adds a new friend:
var thirdId: String = "052222222222222222222222222222222222222222222222222222222222222222"
let thirdId: String = "052222222222222222222222222222222222222222222222222222222222222222"
var cThirdId: [CChar] = thirdId.cArray
var contact7: contacts_contact = contacts_contact()
expect(contacts_get_or_construct(conf2, &contact7, &cThirdId)).to(beTrue())

@ -32,20 +32,16 @@ class ConfigConvoInfoVolatileSpec: QuickSpec {
error?.deallocate()
// Empty contacts shouldn't have an existing contact
var definitelyRealId: [CChar] = "055000000000000000000000000000000000000000000000000000000000000000"
.bytes
.map { CChar(bitPattern: $0) }
let definitelyRealId: String = "055000000000000000000000000000000000000000000000000000000000000000"
var cDefinitelyRealId: [CChar] = definitelyRealId.cArray
var oneToOne1: convo_info_volatile_1to1 = convo_info_volatile_1to1()
expect(convo_info_volatile_get_1to1(conf, &oneToOne1, &definitelyRealId)).to(beFalse())
expect(convo_info_volatile_get_1to1(conf, &oneToOne1, &cDefinitelyRealId)).to(beFalse())
expect(convo_info_volatile_size(conf)).to(equal(0))
var oneToOne2: convo_info_volatile_1to1 = convo_info_volatile_1to1()
expect(convo_info_volatile_get_or_construct_1to1(conf, &oneToOne2, definitelyRealId))
expect(convo_info_volatile_get_or_construct_1to1(conf, &oneToOne2, &cDefinitelyRealId))
.to(beTrue())
let oneToOne2SessionId: [CChar] = withUnsafeBytes(of: oneToOne2.session_id) { [UInt8]($0) }
.map { CChar($0) }
expect(oneToOne2SessionId).to(equal(definitelyRealId.nullTerminated()))
expect(String(libSessionVal: oneToOne2.session_id)).to(equal(definitelyRealId))
expect(oneToOne2.last_read).to(equal(0))
expect(oneToOne2.unread).to(beFalse())
@ -62,37 +58,37 @@ class ConfigConvoInfoVolatileSpec: QuickSpec {
var legacyGroup1: convo_info_volatile_legacy_group = convo_info_volatile_legacy_group()
var oneToOne3: convo_info_volatile_1to1 = convo_info_volatile_1to1()
expect(convo_info_volatile_get_legacy_group(conf, &legacyGroup1, &definitelyRealId))
expect(convo_info_volatile_get_legacy_group(conf, &legacyGroup1, &cDefinitelyRealId))
.to(beFalse())
expect(convo_info_volatile_get_1to1(conf, &oneToOne3, &definitelyRealId)).to(beTrue())
expect(convo_info_volatile_get_1to1(conf, &oneToOne3, &cDefinitelyRealId)).to(beTrue())
expect(oneToOne3.last_read).to(equal(nowTimestampMs))
expect(config_needs_push(conf)).to(beTrue())
expect(config_needs_dump(conf)).to(beTrue())
var openGroupBaseUrl: [CChar] = "http://Example.ORG:5678".cArray
let openGroupBaseUrlResult: [CChar] = ("http://Example.ORG:5678"
.lowercased()
.cArray +
[CChar](repeating: 0, count: (268 - openGroupBaseUrl.count))
)
var openGroupRoom: [CChar] = "SudokuRoom".cArray
let openGroupRoomResult: [CChar] = ("SudokuRoom"
.lowercased()
.cArray +
[CChar](repeating: 0, count: (65 - openGroupRoom.count))
)
var openGroupPubkey: [UInt8] = Data(hex: "0123456789abcdef0123456789abcdef0123456789abcdef0123456789abcdef")
let openGroupBaseUrl: String = "http://Example.ORG:5678"
var cOpenGroupBaseUrl: [CChar] = openGroupBaseUrl.cArray
let openGroupBaseUrlResult: String = openGroupBaseUrl.lowercased()
// ("http://Example.ORG:5678"
// .lowercased()
// .cArray +
// [CChar](repeating: 0, count: (268 - openGroupBaseUrl.count))
// )
let openGroupRoom: String = "SudokuRoom"
var cOpenGroupRoom: [CChar] = openGroupRoom.cArray
let openGroupRoomResult: String = openGroupRoom.lowercased()
// ("SudokuRoom"
// .lowercased()
// .cArray +
// [CChar](repeating: 0, count: (65 - openGroupRoom.count))
// )
var cOpenGroupPubkey: [UInt8] = Data(hex: "0123456789abcdef0123456789abcdef0123456789abcdef0123456789abcdef")
.bytes
var community1: convo_info_volatile_community = convo_info_volatile_community()
expect(convo_info_volatile_get_or_construct_community(conf, &community1, &openGroupBaseUrl, &openGroupRoom, &openGroupPubkey)).to(beTrue())
expect(withUnsafeBytes(of: community1.base_url) { [UInt8]($0) }
.map { CChar($0) }
).to(equal(openGroupBaseUrlResult))
expect(withUnsafeBytes(of: community1.room) { [UInt8]($0) }
.map { CChar($0) }
).to(equal(openGroupRoomResult))
expect(withUnsafePointer(to: community1.pubkey) { Data(bytes: $0, count: 32).toHexString() })
expect(convo_info_volatile_get_or_construct_community(conf, &community1, &cOpenGroupBaseUrl, &cOpenGroupRoom, &cOpenGroupPubkey)).to(beTrue())
expect(String(libSessionVal: community1.base_url)).to(equal(openGroupBaseUrlResult))
expect(String(libSessionVal: community1.room)).to(equal(openGroupRoomResult))
expect(Data(libSessionVal: community1.pubkey, count: 32).toHexString())
.to(equal("0123456789abcdef0123456789abcdef0123456789abcdef0123456789abcdef"))
community1.unread = true
@ -106,7 +102,6 @@ class ConfigConvoInfoVolatileSpec: QuickSpec {
let seqno: Int64 = config_push(conf, &toPush, &toPushLen)
expect(toPush).toNot(beNil())
expect(seqno).to(equal(1))
expect(toPushLen).to(equal(512))
toPush?.deallocate()
// Pretend we uploaded it
@ -128,39 +123,30 @@ class ConfigConvoInfoVolatileSpec: QuickSpec {
expect(config_needs_push(conf2)).to(beFalse())
var oneToOne4: convo_info_volatile_1to1 = convo_info_volatile_1to1()
expect(convo_info_volatile_get_1to1(conf2, &oneToOne4, &definitelyRealId)).to(equal(true))
expect(convo_info_volatile_get_1to1(conf2, &oneToOne4, &cDefinitelyRealId)).to(equal(true))
expect(oneToOne4.last_read).to(equal(nowTimestampMs))
expect(
withUnsafeBytes(of: oneToOne4.session_id) { [UInt8]($0) }
.map { CChar($0) }
.nullTerminated()
).to(equal(definitelyRealId.nullTerminated()))
expect(String(libSessionVal: oneToOne4.session_id)).to(equal(definitelyRealId))
expect(oneToOne4.unread).to(beFalse())
var community2: convo_info_volatile_community = convo_info_volatile_community()
expect(convo_info_volatile_get_community(conf2, &community2, &openGroupBaseUrl, &openGroupRoom)).to(beTrue())
expect(withUnsafeBytes(of: community2.base_url) { [UInt8]($0) }
.map { CChar($0) }
).to(equal(openGroupBaseUrlResult))
expect(withUnsafeBytes(of: community2.room) { [UInt8]($0) }
.map { CChar($0) }
).to(equal(openGroupRoomResult))
expect(withUnsafePointer(to: community2.pubkey) { Data(bytes: $0, count: 32).toHexString() })
expect(convo_info_volatile_get_community(conf2, &community2, &cOpenGroupBaseUrl, &cOpenGroupRoom)).to(beTrue())
expect(String(libSessionVal: community2.base_url)).to(equal(openGroupBaseUrlResult))
expect(String(libSessionVal: community2.room)).to(equal(openGroupRoomResult))
expect(Data(libSessionVal: community2.pubkey, count: 32).toHexString())
.to(equal("0123456789abcdef0123456789abcdef0123456789abcdef0123456789abcdef"))
community2.unread = true
var anotherId: [CChar] = "051111111111111111111111111111111111111111111111111111111111111111"
.bytes
.map { CChar(bitPattern: $0) }
let anotherId: String = "051111111111111111111111111111111111111111111111111111111111111111"
var cAnotherId: [CChar] = anotherId.cArray
var oneToOne5: convo_info_volatile_1to1 = convo_info_volatile_1to1()
expect(convo_info_volatile_get_or_construct_1to1(conf2, &oneToOne5, &anotherId)).to(beTrue())
expect(convo_info_volatile_get_or_construct_1to1(conf2, &oneToOne5, &cAnotherId)).to(beTrue())
oneToOne5.unread = true
convo_info_volatile_set_1to1(conf2, &oneToOne5)
var thirdId: [CChar] = "05cccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccc"
.bytes
.map { CChar(bitPattern: $0) }
let thirdId: String = "05cccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccccc"
var cThirdId: [CChar] = thirdId.cArray
var legacyGroup2: convo_info_volatile_legacy_group = convo_info_volatile_legacy_group()
expect(convo_info_volatile_get_or_construct_legacy_group(conf2, &legacyGroup2, &thirdId)).to(beTrue())
expect(convo_info_volatile_get_or_construct_legacy_group(conf2, &legacyGroup2, &cThirdId)).to(beTrue())
legacyGroup2.last_read = (nowTimestampMs - 50)
convo_info_volatile_set_legacy_group(conf2, &legacyGroup2)
expect(config_needs_push(conf2)).to(beTrue())
@ -239,23 +225,20 @@ class ConfigConvoInfoVolatileSpec: QuickSpec {
expect(config_needs_push(conf)).to(beFalse())
convo_info_volatile_erase_1to1(conf, &fourthId)
expect(config_needs_push(conf)).to(beFalse())
convo_info_volatile_erase_1to1(conf, &definitelyRealId)
convo_info_volatile_erase_1to1(conf, &cDefinitelyRealId)
expect(config_needs_push(conf)).to(beTrue())
expect(convo_info_volatile_size(conf)).to(equal(3))
expect(convo_info_volatile_size_1to1(conf)).to(equal(1))
// Check the single-type iterators:
var seen1: [String] = []
var seen1: [String?] = []
var c1: convo_info_volatile_1to1 = convo_info_volatile_1to1()
let it1: OpaquePointer = convo_info_volatile_iterator_new_1to1(conf)
while !convo_info_volatile_iterator_done(it1) {
expect(convo_info_volatile_it_is_1to1(it1, &c1)).to(beTrue())
let sessionId: String = String(cString: withUnsafeBytes(of: c1.session_id) { [UInt8]($0) }
.map { CChar($0) }
.nullTerminated()
)
seen1.append(sessionId)
seen1.append(String(libSessionVal: c1.session_id))
convo_info_volatile_iterator_advance(it1)
}
@ -264,18 +247,14 @@ class ConfigConvoInfoVolatileSpec: QuickSpec {
"051111111111111111111111111111111111111111111111111111111111111111"
]))
var seen2: [String] = []
var seen2: [String?] = []
var c2: convo_info_volatile_community = convo_info_volatile_community()
let it2: OpaquePointer = convo_info_volatile_iterator_new_communities(conf)
while !convo_info_volatile_iterator_done(it2) {
expect(convo_info_volatile_it_is_community(it2, &c2)).to(beTrue())
let baseUrl: String = String(cString: withUnsafeBytes(of: c2.base_url) { [UInt8]($0) }
.map { CChar($0) }
.nullTerminated()
)
seen2.append(baseUrl)
seen2.append(String(libSessionVal: c2.base_url))
convo_info_volatile_iterator_advance(it2)
}
@ -284,18 +263,14 @@ class ConfigConvoInfoVolatileSpec: QuickSpec {
"http://example.org:5678"
]))
var seen3: [String] = []
var seen3: [String?] = []
var c3: convo_info_volatile_legacy_group = convo_info_volatile_legacy_group()
let it3: OpaquePointer = convo_info_volatile_iterator_new_legacy_groups(conf)
while !convo_info_volatile_iterator_done(it3) {
expect(convo_info_volatile_it_is_legacy_group(it3, &c3)).to(beTrue())
let groupId: String = String(cString: withUnsafeBytes(of: c3.group_id) { [UInt8]($0) }
.map { CChar($0) }
.nullTerminated()
)
seen3.append(groupId)
seen3.append(String(libSessionVal: c3.group_id))
convo_info_volatile_iterator_advance(it3)
}

@ -19,6 +19,14 @@ class TypeConversionUtilitiesSpec: QuickSpec {
expect("Test123".cArray).to(equal([84, 101, 115, 116, 49, 50, 51]))
}
it("can contain emoji") {
let original: String = "Hi 👋"
let libSessionVal: (CChar, CChar, CChar, CChar, CChar, CChar, CChar, CChar, CChar, CChar, CChar, CChar) = original.toLibSession()
let result: String? = String(libSessionVal: libSessionVal)
expect(result).to(equal(original))
}
context("when initialised with a pointer and length") {
it("returns null when given a null pointer") {
let test: [CChar] = [84, 101, 115, 116]
@ -49,20 +57,41 @@ class TypeConversionUtilitiesSpec: QuickSpec {
}
context("when initialised with a libSession value") {
it("returns a string when valid and null terminated") {
it("returns a string when valid and has no fixed length") {
let value: (CChar, CChar, CChar, CChar, CChar) = (84, 101, 115, 116, 0)
let result = String(libSessionVal: value, nullTerminated: true)
let result = String(libSessionVal: value, fixedLength: .none)
expect(result).to(equal("Test"))
}
it("returns a string when valid and not null terminated") {
it("returns a string when valid and has a fixed length") {
let value: (CChar, CChar, CChar, CChar, CChar) = (84, 101, 0, 115, 116)
let result = String(libSessionVal: value, nullTerminated: false)
let result = String(libSessionVal: value, fixedLength: 5)
expect(result).to(equal("Te\0st"))
}
it("truncates at the first null termination character when fixed length is none") {
let value: (CChar, CChar, CChar, CChar, CChar) = (84, 101, 0, 115, 116)
let result = String(libSessionVal: value, fixedLength: .none)
expect(result).to(equal("Te"))
}
it("parses successfully if there is no null termination character and there is no fixed length") {
let value: (CChar, CChar, CChar, CChar, CChar) = (84, 101, 115, 116, 84)
let result = String(libSessionVal: value, fixedLength: .none)
expect(result).to(equal("TestT"))
}
it("defaults the fixed length value to none") {
let value: (CChar, CChar, CChar, CChar, CChar) = (84, 101, 0, 0, 0)
let result = String(libSessionVal: value)
expect(result).to(equal("Te"))
}
it("returns an empty string when null and not set to return null") {
let value: (CChar, CChar, CChar, CChar, CChar) = (0, 0, 0, 0, 0)
let result = String(libSessionVal: value, nullIfEmpty: false)
@ -77,13 +106,6 @@ class TypeConversionUtilitiesSpec: QuickSpec {
expect(result).to(beNil())
}
it("defaults the null terminated flag to true") {
let value: (CChar, CChar, CChar, CChar, CChar) = (84, 101, 0, 0, 0)
let result = String(libSessionVal: value)
expect(result).to(equal("Te"))
}
it("defaults the null if empty flag to false") {
let value: (CChar, CChar, CChar, CChar, CChar) = (0, 0, 0, 0, 0)
let result = String(libSessionVal: value)
@ -92,32 +114,43 @@ class TypeConversionUtilitiesSpec: QuickSpec {
}
}
it("can convert to a libSession value") {
let result: (CChar, CChar, CChar, CChar, CChar) = "Test".toLibSession()
expect(result.0).to(equal(84))
expect(result.1).to(equal(101))
expect(result.2).to(equal(115))
expect(result.3).to(equal(116))
expect(result.4).to(equal(0))
}
context("when optional") {
context("returns null when null") {
let value: String? = nil
let result: (CChar, CChar, CChar, CChar, CChar)? = value?.toLibSession()
expect(result).to(beNil())
context("when converting to a libSession value") {
it("succeeeds with a valid value") {
let result: (CChar, CChar, CChar, CChar, CChar) = "Test".toLibSession()
expect(result.0).to(equal(84))
expect(result.1).to(equal(101))
expect(result.2).to(equal(115))
expect(result.3).to(equal(116))
expect(result.4).to(equal(0))
}
context("returns a libSession value when not null") {
let value: String? = "Test"
let result: (CChar, CChar, CChar, CChar, CChar)? = value?.toLibSession()
it("truncates when too long") {
let result: (CChar, CChar, CChar, CChar, CChar) = "TestTest".toLibSession()
expect(result.0).to(equal(84))
expect(result.1).to(equal(101))
expect(result.2).to(equal(115))
expect(result.3).to(equal(116))
expect(result.4).to(equal(84))
}
context("when optional") {
context("returns null when null") {
let value: String? = nil
let result: (CChar, CChar, CChar, CChar, CChar)? = value?.toLibSession()
expect(result).to(beNil())
}
expect(result?.0).to(equal(84))
expect(result?.1).to(equal(101))
expect(result?.2).to(equal(115))
expect(result?.3).to(equal(116))
expect(result?.4).to(equal(0))
context("returns a libSession value when not null") {
let value: String? = "Test"
let result: (CChar, CChar, CChar, CChar, CChar)? = value?.toLibSession()
expect(result?.0).to(equal(84))
expect(result?.1).to(equal(101))
expect(result?.2).to(equal(115))
expect(result?.3).to(equal(116))
expect(result?.4).to(equal(0))
}
}
}
}
@ -145,32 +178,43 @@ class TypeConversionUtilitiesSpec: QuickSpec {
}
}
it("can convert to a libSession value") {
let result: (Int8, Int8, Int8, Int8, Int8) = Data([1, 2, 3, 4, 5]).toLibSession()
expect(result.0).to(equal(1))
expect(result.1).to(equal(2))
expect(result.2).to(equal(3))
expect(result.3).to(equal(4))
expect(result.4).to(equal(5))
}
context("when optional") {
context("returns null when null") {
let value: Data? = nil
let result: (Int8, Int8, Int8, Int8, Int8)? = value?.toLibSession()
expect(result).to(beNil())
context("when converting to a libSession value") {
it("succeeeds with a valid value") {
let result: (Int8, Int8, Int8, Int8, Int8) = Data([1, 2, 3, 4, 5]).toLibSession()
expect(result.0).to(equal(1))
expect(result.1).to(equal(2))
expect(result.2).to(equal(3))
expect(result.3).to(equal(4))
expect(result.4).to(equal(5))
}
context("returns a libSession value when not null") {
let value: Data? = Data([1, 2, 3, 4, 5])
let result: (Int8, Int8, Int8, Int8, Int8)? = value?.toLibSession()
it("truncates when too long") {
let result: (Int8, Int8, Int8, Int8, Int8) = Data([1, 2, 3, 4, 1, 2, 3, 4]).toLibSession()
expect(result.0).to(equal(1))
expect(result.1).to(equal(2))
expect(result.2).to(equal(3))
expect(result.3).to(equal(4))
expect(result.4).to(equal(1))
}
context("when optional") {
context("returns null when null") {
let value: Data? = nil
let result: (Int8, Int8, Int8, Int8, Int8)? = value?.toLibSession()
expect(result).to(beNil())
}
expect(result?.0).to(equal(1))
expect(result?.1).to(equal(2))
expect(result?.2).to(equal(3))
expect(result?.3).to(equal(4))
expect(result?.4).to(equal(5))
context("returns a libSession value when not null") {
let value: Data? = Data([1, 2, 3, 4, 5])
let result: (Int8, Int8, Int8, Int8, Int8)? = value?.toLibSession()
expect(result?.0).to(equal(1))
expect(result?.1).to(equal(2))
expect(result?.2).to(equal(3))
expect(result?.3).to(equal(4))
expect(result?.4).to(equal(5))
}
}
}
}

Loading…
Cancel
Save