Skip to content

Instantly share code, notes, and snippets.

@minsOne
Created September 19, 2015 09:00
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save minsOne/765aaffe565e688dd790 to your computer and use it in GitHub Desktop.
Save minsOne/765aaffe565e688dd790 to your computer and use it in GitHub Desktop.
struct PostCode {
var code: Int
}
struct Address {
var street: String
var post: PostCode
}
struct Man {
var name: String = "John"
var age: Int = 50
var dutch: Bool = false
var address: Address? = Address(street: "Market St.", post: PostCode(code: 111))
}
let john = Man()
extension Mirror {
var properties: [(String, Child)] {
return self.children.reduce([(String, Child)]()) {
guard let propertyName = $1.label else { return $0 }
return $0 + [(propertyName, $1)]
}
}
}
protocol JSON {
func toJSON() throws -> AnyObject?
}
enum CouldNotSerializeError {
case NoImplementation(source: Any, type: Mirror)
}
extension CouldNotSerializeError: ErrorType { }
extension JSON {
func toJSON() throws -> AnyObject? {
let mirror = Mirror(reflecting: self)
if !mirror.properties.isEmpty {
var result = [String:AnyObject]()
for (key, child) in mirror.properties {
guard let value = child.value as? JSON else {
throw CouldNotSerializeError.NoImplementation(source: self, type: mirror)
}
result[key] = try value.toJSON()
}
return result
}
return self as? AnyObject
}
}
extension Man: JSON { }
extension String: JSON { }
extension Int: JSON { }
extension Bool: JSON { }
extension Address: JSON { }
extension PostCode: JSON { }
extension Optional: JSON {
func toJSON() throws -> AnyObject? {
guard let x = self else { return nil }
if let value = x as? JSON {
return try value.toJSON()
}
throw CouldNotSerializeError.NoImplementation(source: x, type: Mirror(reflecting: x))
}
}
do {
if let johnDescrip = try john.toJSON() {
print(johnDescrip)
}
} catch {
print(error)
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment