I am testing a server implementation and need to send invalid data to the server.
When using axios post with Content-Type application/json the data gets automatically parsed as JSON.
If the data axios receives is invalid JSON it will automatically turn this into valid JSON by quoting the data as a string.
axios.post('api/paths/invalid.json', '{"invalid: ()',
{ headers: { 'Content-Type': 'application/json' } })
The above will actually send "{\"invalid: ()" to the server, which will parse as valid JSON.
Override the default request transformation to be able to send any raw unmodified data to the server with data => data (AKA the id-function).
axios.post('api/paths/invalid.json', '{"invalid: ()',
{
headers: { 'Content-Type': 'application/json' },
transformRequest: [data => data]
}
)
Related
Is there any way to send binary data of a file in body of a put request using nodejs and axios ?
you can use a FormData append your file to it , send it with axios then get it with multer in server side.
const data = new FormData()
data.append('multer_file_name', file, file.name)
axios.post("your_api", data, {
headers: {
accept: 'application/json',
'Accept-Language': 'en-US,en;q=0.8',
'Content-Type': undefined,
},
}).then((response) => {
})
you can get your file like this if you have an input :
const file = document.getElementById('your_input_id').files[0]
I have a React application where I am changing POST method to GET with the request body as it is. It works fine with POST request however when I change the method to GET, it gives me error-
message: "org.springframework.http.converter.HttpMessageNotReadableException: Required request body is missing: public
My Front End Code-
export const setData = (getData) => dispatch => {
axios({
method: 'GET',
url: 'http://localhost:8080/api',
headers: {
'Content-Type': 'application/json'
},
data: getData
})
.then (response => {
dispatch({
type: API_DATA,
payload: response.data
})
dispatch({
type: SET_SEARCH_LOADER,
payload: false
})
})
.catch(function(error) {
})
}
Can someone let me know what I am missing here. As per my understanding, http allows to have a request body for GET method.
As per my understanding, http allows to have a request body for GET method.
While this is technically true (although it may be more accurate to say that it just doesn't explicitly disallow it), it's a very odd thing to do, and most systems do not expect GET requests to have bodies.
Consequently, plenty of libraries will not handle this.
The documentation for Axois says:
// `data` is the data to be sent as the request body
// Only applicable for request methods 'PUT', 'POST', and 'PATCH'
Under the hood, if you run Axios client side in a web browser, it will use XMLHttpRequest. If you look at the specification for that it says:
client . send([body = null])
Initiates the request. The body argument provides the request body, if any, and is ignored if the request method is GET or HEAD.
If you want to send parameters with get request in axios, you should send parameters as params.
If you want to set "Content-type":"application/json" and send params with get request, you should also send an empty data object.
For example:
const AUTH_TOKEN = 'Bearer token'
const config = {
headers: {
'Content-Type': 'application/json',
'Accept': 'application/json',
'Authorization': AUTH_TOKEN,
},
data: {},
params: {
"post_id": 1
}
}
axios.get("http://localhost/api/v1/posts/", config)
This is not axios, the error origniates from the java backend you're talking to. The public field in your request body is missing.
If you just want to send the data as parameters (which would be odd), pass it using params instead of data (as shown here: https://github.com/axios/axios#example).
I personally don't think your API should support GET with a request body (talk to the devs and ask for documentation).
I am using the node-fetch library and it by-default decompresses the response. I want to make a POST request which returns gzipped content and I want to pipe the POST request response to the response.
The code I am currently using is here:
router.post('/getData', async(request, response) => {
fetch(`http://url:port/path`, { method: 'POST', headers: {'Accept-Encoding': 'gzip'}, body: ''})
.then(data=> {
return data.body.pipe(response);
}
}
}
I understand that the node-fetch library decompresses the data by default. I do not need this. I want to pass the compressed data directly using streams. (Like a proxy)
What worked for me was setting compress=false but then adding the header to accept gzip encoding:
fetch(url, {
compress: false,
headers: { "accept-encoding": "gzip" },
});
I have to implement the following workflow:
Make request no.1, get a JSON response. Manipulate this JSON object so that it can be used as payload in the second request. Make second request.
The first request is successfully implemented. I get the correct JSON object. The manipulation part is also done and tested.
I managed to create a correct postman collection for the second request. It uses the method POST, has several headers, Content-type is multipart/form-data and the payload from request no.1 is sent as Raw (in the body, options none, form-data etc ... I choose raw).
I am trying to implement this second request but get an error no matter what I try to tweak. The following is my code:
const manipulatedObject = await this._flattenPayload(payload);
const Request = require(request-promise);
const options = {
method: 'POST',
uri: 'https://second_request_url',
formData: {
file: {
value: manipulatedObject,
},
},
headers: {
Accept: 'application/json, text/plain, */*',
Connection: 'keep-alive',
'Content-Type': 'multipart/form-data; boundary=----WebKitFormBoundaryxxxxxxxxxxxxxxxx', // this is generated dynamically and matches the value in the manipulatedObject
cookie: this.cachedCookie,
'X-XSRF-TOKEN': this.cachedToken,
},
};
Request(options)
.then((body) => {
return body;
})
.catch((error) => {
return error;
});
* The parameter payload is the response from the first request.
The error I get is this:
message=source.on is not a function, stack=TypeError: source.on is not
a function
The variable manipulatedObject is a string. Currently I am copying it's value from the successful postman request to avoid errors from the manipulation process. The random token in the Content-Type header matches the ones in the manipulatedObject string. So the data are identical to the ones I use in the postman request.
I suspect the error is in the way I send the data, but I am having trouble figuring it out. I have read about this error and it seems to be generated when an object is passed to formData, but I am sending a string so I don't understand why it happens.
The values of formData accepts only three types of elements viz. string, Buffer and Stream. Refer to:request/issues/2366
U may change formData as follows:
formData: {
file: manipulatedObject,
},
or
formData: {
file: {
value: manipulatedObject,
options: {},
},
},
I want to send a get request but I need to insert my api key in to a 'x-api-key' header. I am using NodeJS + Express. Right now i'm using fetch from the "isomorphic unfetch" lib:
https://github.com/developit/unfetch/tree/master/packages/isomorphic-unfetch
I use it in order to fetch data from the get request. I use this library specially because it works well on both the server and a client.
How should I add the header to my request? Thanks!
There's an example in the unfetch repository that shows how to add headers to fetch requests.
// complex POST request with JSON, headers:
fetch('/bear', {
method: 'POST',
headers: {
'Content-Type': 'application/json',
'x-api-key': 'Bearer XYZ'
},
body: JSON.stringify({ hungry: true })
}).then( r => {
open(r.headers.get('location'));
return r.json();
})