Skip to content

Commit

Permalink
encoding arrays in cheetah
Browse files Browse the repository at this point in the history
  • Loading branch information
Joannis committed Oct 23, 2017
1 parent c9eed91 commit bda835f
Show file tree
Hide file tree
Showing 2 changed files with 78 additions and 4 deletions.
20 changes: 16 additions & 4 deletions Sources/Cheetah/Codable.swift
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,13 @@ public class JSONEncoder {
return encoder.target.object
}

public func encodeArray(_ value: Encodable) throws -> JSONArray {
let encoder = _JSONEncoder(target: .array(JSONArray()))
try value.encode(to: encoder)

return encoder.target.array
}

public func encode(value: Encodable) throws -> Value? {
let encoder = _JSONEncoder(target: .primitive(get: { nil }, set: { _ in }))
try value.encode(to: encoder)
Expand Down Expand Up @@ -154,7 +161,7 @@ fileprivate class _JSONEncoder : Encoder, _JSONCodingPathContaining {
extension JSONArray {
fileprivate subscript(index: Int) -> Value? {
get {
if self.count > index {
guard self.count > index else {
return nil
}

Expand Down Expand Up @@ -198,12 +205,17 @@ fileprivate struct _JSONUnkeyedEncodingContainer : UnkeyedEncodingContainer {
}

private func nestedEncoder() -> _JSONEncoder {
let index = self.encoder.target.array.count

return _JSONEncoder(codingPath: codingPath, target: .primitive(get: {
let index = self.encoder.target.array.count
return self.encoder.target.array[index]
}, set: { value in
if let value = value {
self.encoder.target.array.append(value)
if self.encoder.target.array.count > index {
self.encoder.target.array[index] = value
} else {
self.encoder.target.array.append(value)
}
}
}))
}
Expand Down Expand Up @@ -774,7 +786,7 @@ fileprivate class _JSONUnkeyedDecodingContainer : UnkeyedDecodingContainer, _JSO
self.codingPath = decoder.codingPath
}

var count: Int? { return decoder.target.object.count }
var count: Int? { return decoder.target.array.count }
var currentIndex: Int = 0
var isAtEnd: Bool {
return currentIndex >= self.count!
Expand Down
62 changes: 62 additions & 0 deletions Tests/CheetahTests/ParserTests.swift
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,12 @@ struct BrokenArray: Codable {
]
}

struct User: Codable {
var id: Int
var username: String
var other: Bool
}

class ParsingTests: XCTestCase {

func testBrokenJSONArray() throws {
Expand All @@ -32,6 +38,62 @@ class ParsingTests: XCTestCase {
XCTAssertEqual(array.count, 3)
}

func testCodable() throws {
let user0 = User(id: 0, username: "test0", other: true)
let user1 = User(id: 1, username: "test1", other: false)
let user2 = User(id: 2, username: "test2", other: false)
let user3 = User(id: 3, username: "test3", other: true)

var obj0 = try JSONEncoder().encode(user0)
var obj1 = try JSONEncoder().encode(user1)
var obj2 = try JSONEncoder().encode(user2)
var obj3 = try JSONEncoder().encode(user3)

XCTAssertEqual(Int(obj0["id"]), 0)
XCTAssertEqual(Int(obj1["id"]), 1)
XCTAssertEqual(Int(obj2["id"]), 2)
XCTAssertEqual(Int(obj3["id"]), 3)

XCTAssertEqual(String(obj0["username"]), "test0")
XCTAssertEqual(String(obj1["username"]), "test1")
XCTAssertEqual(String(obj2["username"]), "test2")
XCTAssertEqual(String(obj3["username"]), "test3")

XCTAssertEqual(Bool(obj0["other"]), true)
XCTAssertEqual(Bool(obj1["other"]), false)
XCTAssertEqual(Bool(obj2["other"]), false)
XCTAssertEqual(Bool(obj3["other"]), true)

let value = try JSONEncoder().encodeArray([user0, user1, user2, user3])

guard let array0 = JSONArray(value) else {
XCTFail()
return
}

XCTAssertEqual(array0.count, 4)

obj0 = JSONObject(array0[0])!
obj1 = JSONObject(array0[1])!
obj2 = JSONObject(array0[2])!
obj3 = JSONObject(array0[3])!

XCTAssertEqual(Int(obj0["id"]), 0)
XCTAssertEqual(Int(obj1["id"]), 1)
XCTAssertEqual(Int(obj2["id"]), 2)
XCTAssertEqual(Int(obj3["id"]), 3)

XCTAssertEqual(String(obj0["username"]), "test0")
XCTAssertEqual(String(obj1["username"]), "test1")
XCTAssertEqual(String(obj2["username"]), "test2")
XCTAssertEqual(String(obj3["username"]), "test3")

XCTAssertEqual(Bool(obj0["other"]), true)
XCTAssertEqual(Bool(obj1["other"]), false)
XCTAssertEqual(Bool(obj2["other"]), false)
XCTAssertEqual(Bool(obj3["other"]), true)
}

func testEncodeArrayJSON() throws {
let tests: [Test] = [
0, 1, 2, 3, 4, 5
Expand Down

0 comments on commit bda835f

Please sign in to comment.