Hi,
I want to write some unit tests around processing query results. Let's say I have this query:
query userName($userID: ID!)
{
user(id: $userID)
{
firstName
lastName
}
}
In the Swift code, after I fetch the query from the client, I'll end up with GraphQLResult<UserNameQuery.Data>.
For my tests, is there a way I can start with a string representation of the result JSON, e.g.
{
"data": {
"user": {
"firstName": "John",
"lastName": "Doe"
}
}
}
and create a UserNameQuery.Data object that I can pass to my code that processes the result?
I've tried different initializers but they don't seem to fully populate the object.
Thanks,
Jeff
You should be able to use the public init(unsafeResultMap: ResultMap) initializer that's included with the Data objects. ResultMap is just a typealias to a [String: Any?] dictionary.
Thanks so much! Works like a charm. You just saved me a ton of time vs testing things manually.
Huzzah! Mind if we close this issue out then?
Not at all. I'll close it.
As an addendum, I have a query that contains an enum. Is there a way I can have the JSON text parsed from a string to the proper enum? When I init my Data object using unsafeResultMap (from my test) the string (correctly) stays as a string. e.g.
{
"user": {
"__typename": "User",
"status": "UNSELECTED",
}
}
status is an enum with cases for selected, and unselected.
When my parser test tries to parse the data, it fails because the value for the key is a string, not an enum.
Is there a mechanism I can invoke to parse any strings into enums when building up my Data object?
Thanks,
Jeff
Can you send what the generated getter for status looks like? In theory since that type should be generated as a string-based enum, you should be able to just use the failable initializer for the type to do the conversion.
Of course.
public var status: UserStatus {
get {
return resultMap["status"]! as! UserStatus
}
set {
resultMap.updateValue(newValue, forKey: "status")
}
}
PS This is how I create my Data object in my test.
let data = UserQuery.Data(unsafeResultMap: json(
"""
{
"user": {
"__typename": "User",
"status": "UNSELECTED"
}
}
"""))
json is a simple function that turns a String into a ResultMap. I'm copying the text from GrqphiQL to match what I'll receive from my backend.
You should be able to just use a dictionary since UnsafeResultMap is just a typealias to a dictionary - so something like
let data = UserQuery.Data(unsafeResultMap: [
"user": [
"__typename": "User",
"status": .unselected
]
])
Thanks. That works. Digging into it more it looks like it would be rather difficult to create the Data object from a json string. Converting the string to a Swift dictionary literal isn't that much work鈥攋ust convert {} to [] :-)
@designatednerd is there a way in which i can parse jsonstring into GraphqQLResponse object specially when you are using custom scalar type? Current parseResult function is not public.