How to verify an image contains in the response via pact test - pact

I want to use pact test to verify if a provider could provide a image in a response. now the actual response looks like this
server response body which contains the picture
My Pact Json File looks like this
"interactions": [
{
"providerState": "there's a user has a portrait tiger.png",
"description": "Get the user's portrait",
"request": {
"method": "GET",
"path": "/api/Employees/v1/Employee/106656048406528/Attachments",
"headers": {
"Content-Type": "application/json",
"X-Employee-ID": "106656048406528",
"X-Tenant-ID": "26663977872256",
"X-User-ID": "1333"
}
},
"response": {
"status": 200,
"headers": {
"Content-Type": "image/jpeg;charset=UTF-8"
},
"body": "iVBORw0KGgoAAAANSU",
"matchingRules": {
"$.body": {
"match": "type"
}
}
}
}
],
the pact test always fails and say the body mismatch. I can understand the actual response is not a base64 format and not a string. it should some binaries file. In this case, how can I write the matching rules to valid it's a binary file?

The way to do this would be to ignore the body unless you really want to match the exact binary every time, which would be counter productive in my opinion.
When a binary file is sent, it does send the appropriate headers with it, like you already have in your contract with 'Content-Type'. You can always add a matching rule that the body has to be there, but you just don't care about the content, but I'm not positive if this is even needed since you could just look at the 'Content-Length' header and make sure it's bigger than 0.
What needs to be remembered is that Pact is not meant to be used to match everything. It's meant to match the critical parts of your system and certain expectations from your consumer, ie. as a consumer, I want to call this service which should give me an image, but I don't care what that image is since I just show it in the DOM. If you need an actual image to be given on the consumer side while testing, you can use the matcher query to resolve to anything by using regex, then as the generator, use the actual image output. I'd use something small though if I were you since Pact isn't exactly meant to be spewing out megabytes of binaries.

In my opinion, only the header check is enough. (Unless you want to verify entire binary content, which I think is not the best).

Related

Is there such a thing as an ordered pair in request parameters / query string? in GET request

I'm writing an endpoint where it logically makes sense to think of request parameters as coupled ordered pairs
(eg breed=labrador&name=fido, breed=dalmnation&name=mike etc)
Is there anything I can do to enforce this pairing from the request
(eg having a dog object such that dog1{breed=labrador&name=fido}&dog2{breed=dalmnation&name=mike} or am I to just read the parameters in order and know that given a query know that the order matters and I must trust the ordering of the parameters would follow breed,name breed,name etc?
For context my endpoint would accept [1,15] dogs in a GET request and am using Django if that makes a difference.
I'm sorry if this has been asked before or is covered elsewhere, I'm struggling to find the right words to use to find a solution on Google.
If you are using a GET request you could possibly put a json string inside one of the of the url encoded variables. Like this example with python request library:
import requests,json
dogs = [
{ "breed": "labrador", "name": "fido"},
{ "breed": "dalmnation", "name": "mike"}
]
payload = { "json": json.dumps(dogs) }
requests.get("http://endpoint", params = payload);
Then on the receiving end:
def my(request):
myDogs = json.loads(request.GET.get('json'))

Hoverfly: Custom JSON request body matcher matching specific parts

Is there a way in Hoverly-Java APIs to custom match a JSON request body?
For instance, say I have this request body that my service will use
{
"name": "Tom",
"age": 24,
"timestamp": <unix time stamp long>
}
I want to be able to skip the matching/checking for timestamp when building the stub but match other parts of the JSON body.
When I stub the relevant request for this body, none of the existing matcher types fit my need. It is not an exact match, not a partialJsonMatch etc.
Help appreciated.
You could match on any body or remove the timestamp from your json and use the PartialMatcher.
And then you could check the request afterwards by getting the journal from the hoverfly client. Each JournalEntry has a field with the request details.

Sending POST request with form-data works, but its simple raw equivalent doesn't

I am trying to send a Post request to my server, and here is the thing, when I try doing that with "form-data" everything works absolutely fine.
you can see what I wrote below:
form-data
But when I send it as a raw Json, it doesn't work at all...
below is the body that contains the json code:
{
"cookie": "test1|1521275188|udWlZft3jKw8HYBmni7F2LzctUFBCSDOzahc63Jm6Gk|2a7f91a7d68e2c10399706ba3f9e2833123ddb17e1de2f2d7a669b47ff701ab0",
"nonce": "84d874e5b7",
"title": "post Try" }
as you can see, I wrote a key and a value in both places, but one works and the other doesn't, and because I only sent 3 parameter I don't really see any place for a spelling mistake...
What do you think it might be?
Thank you!
You need to send the object too, the form wraps the form-data inside the object
something like,
"post":{
{
"cookie": "test1|1521275188|udWlZft3jKw8HYBmni7F2LzctUFBCSDOzahc63Jm6Gk|2a7f91a7d68e2c10399706ba3f9e2833123ddb17e1de2f2d7a669b47ff701ab0",
"nonce": "84d874e5b7",
"title": "post Try" }
}

How to execute ElasticSearch agg query from Apache Nifi using InvokeHTTP?

I want to execute the following query from Apache Nifi:
GET /myindex/_search
{
"size": 0,
"aggs": {
"range": {
"date_range": {
"field": "Datetime",
"ranges": [
{
"from": "2017-02-17T16:00:00Z||-1H/H",
"to": "2017-02-17T16:00:00Z||/H"
}
]
}
}
}
}
I want to get the value of doc_count.
I tried to use InvokeHTTP and directly pasted the above-defined query into the field HTTP Method. I also set Remote URL to http://localhost:9200. I connected InvokeHTTP with PutFile in order to save a response on the disk. The relationship is Response.
When I run InvokeHTTP, it does not give me any error. However, it neither outputs any result (FlowFile for Response). I am sure that the result is not an empty set, because I tested this query with curl.
What is wrong with my approach? Should I define HTTP Method in some different way?
For verbs like POST, PUT, and PATCH, you'd normally have the above JSON body as the content of a flow file and pass that to InvokeHttp, setting the correct verb and URL there. However the InvokeHttp documentation states that the message body will not be sent for a GET verb.
The good news is that the Elasticsearch REST API for the search endpoint supports both GET and POST. From their latest doc: "Both HTTP GET and HTTP POST can be used to execute search with body. Since not all clients support GET with body, POST is allowed as well."
I would set the content of a flow file to the above JSON body (perhaps using GenerateFlowFile or ReplaceText), then use POST as the verb.
There is a JsonQueryElasticsearch processor, which supports JSON elasticsearch queries.
Your query goes into the Query field.
The processor has hits and aggregations relations for you to process the result.

Returning a JSON object from a PageMethod with custom formatting

Is it possible to format how an object is returned as JSON from a PageMethod? ie. removing the first "d" element from the data, without writing the JSON from scratch.
From:
{ "d": { "name": "bob", "email": "bob#example.com" } }
To
{ "name": "bob", email: "bob#example.com" }
The extra "d" parameter is added by the .NET framework as an added security measure against XSS attacks [source]. It's included when the "Content-Type" of the request specifies "application/json".
I think you can get the framework to exclude it (ie don't wrap the result in the "d") if you simply specifying the "Content-Type" of the request as something other than "application/json". Try removing that header from the request (if you can) and seeing what .NET returns.
No. Microsoft's JSON serializer adds the d for some reason on the server side, and the client-side AJAX code that deserializes the JSON string expects it to be there.

Resources