I have a SpecFlow test definition set up where I want to assert that the response have a specific collection of fields in its response. For example I have this particular expected response from the API:
{
isActive: false,
lastProcessed: "2020-11-03T19:03:16.537"
}
What I want to verify is that the response contains those two fields, not necessarily the value those fields contain. I tried the following method:
Assert.NotNull(response.Model.isActive);
Assert.NotNull(response.Model.lastProcessed);
But I'm getting an error using this method:
Do not use Assert.NotNull() on value type 'bool'
How else can I make sure the response structure is as expected other than using "NotNull()"?
The Solution: Following the accepted answer, I serialized the model returned from the API call into JSON and parsed it into a JObject. Then I used the ContainsKey() method to assert it.
JObject jObject = JObject.Parse(JsonConvert.SerializeObject(response.Model));
Assert.True(jObject.ContainsKey("isActive"));
I don't know what packages you use for sending requests and deserialization but if you could get the response content as a raw json string you could then use Newtonsoft.JSON to parse the response into a JObject
with JObject.Parse(responseContent)
. JObject
has a method called ContainsKey(propertyName)
which determines whether there is a field of a specified name in the object. You could assert if it returns true for the desired property names.
Edit
Regarding Greg's answer below. The original error is in fact caused by bool
not being a nullable type and making it nullable in the model would fix the error. However, this solution is not ideal. In some cases null
can be a valid value returned by the API and this would generate false negatives. e.g. if we recieved:
{
isActive: null,
lastProcessed: "2020-11-03T19:03:16.537"
}
then Assert.NotNull(response.Model.isActive)
would yield a negative test result even though the field is present in the json, and that's what we wanted to check.
So theoretically if we are 100% sure that null
will never be returned by the API itself, then we could do it that way, but it won't be a universal method. Also not very descriptive of what we are trying to achieve ;)