Reputation: 1717
Using:
import { HttpClient, HttpHeaders } from '@angular/common/http';
const httpOptions = {
headers: new HttpHeaders({
'Content-Type: ['application/json']
})
}
@Injectable()
export class MyService {
constructor (private http: HttpClient) {}
private myUrl = 'http://localhost:3000/my-service';
private postBody =
`
[
{ "a": ["complex"],
"serialized": "data",
"set": [],
},{
"in": "json",
"format": []
}
]
`;
getData(): Observable<ExpectedResponseType> {
return this.http.post<ExpectedResponseType>(this.myUrl, this.postBody, httpOptions);
}
}
When I subscribe to this service, the browser sends a preflight OPTIONS
request to localhost:3000/my-service
which returns 404. If I remove httpOptions
from the request, it successfully POSTs with the body I want but doesn't set Content-Type
to application/json
and thus the server returns 500.
How can I send a POST request in Angular 5 with a content type of json? The server provides the expected results from Postman, but I'm not sure how to convince Angular to simply send the POST with the headers I want.
Upvotes: 1
Views: 1775
Reputation: 1717
The best solution I found for development was to use an Angular proxy.
const proxy = [
{
context: '/api',
target: 'http://localhost:3000',
pathRewrite: {'^/api' : ''}
}
];
module.exports = proxy;
ng serve --proxy-config proxy.config.js --open
This reroutes all requests on the same domain under /api
back to my server so I don't need to worry about configuring my server to replace ng serve
.
Upvotes: 0
Reputation: 161
This is happening because of CORS restrictions (Cross-Origin Resource Sharing). Browsers do not allow requests to go a server with a different host/port combination unless the server allows it. This is for security reasons (to protect against XSRF attacks for instance). There are several ways to address this:
--disable-web-security --user-data-dir=SOME_FOLDER
.Upvotes: 1
Reputation: 56956
The OPTIONS request is not an Angular issue, it is a browser issue.
When a browser makes a cross domain request it will (for most requests, depending on what you are requesting and method used) first do an OPTIONS request.
The purpose of the OPTIONS request is to check that the server is allowing your client (browser) to make requests to it. This is determined by the server CORS response headers. If the OPTIONS request fails, then the browser knows it is not allowed and thus does not bother to make the actual request you wanted.
This is only enforced by browsers and thus POSTMAN will work fine.
Please add the CORS headers to your server response and ensure your server supports OPTIONS requests.
See https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/Access-Control-Allow-Origin
See https://developer.mozilla.org/en-US/docs/Web/HTTP/CORS
If you really cant be bothered with CORS then send the request to the same domain and get your webserver to rewrite the URL. Note that you will have to repeat the logic for the rewrite in your prod server also.
Upvotes: 3