1

I have a contact form that the user fills out which gets posted to my Web API to be sent using nodemailer.

CORS works as expected with the when I run the client and API locally:

Client

localhost:4200 with POST request

sendEmail(queryObject: any) {
const body = JSON.stringify(queryObject);
const headers = new Headers();
headers.append('Content-Type', 'application/json');
return this.http.post('http://localhost:3000/api/sendemail', body, {headers: headers})
  .map((response: Response) => response.json());
}

API

localhost:3000

but as soon as I deploy my API to heroku and change the POST URL in the client to point to Heroku I get the preflight error:

OPTIONS https://keilcarpenter-portfolioapi.herokuapp.com/api/sendemail 503 (Service Unavailable)

XMLHttpRequest cannot load https://keilcarpenter-portfolioapi.herokuapp.com/api/sendemail. Response to preflight request doesn't pass access control check: No 'Access-Control-Allow-Origin' header is present on the requested resource. Origin 'http://localhost:4200' is therefore not allowed access. The response had HTTP status code 503.

I am sure I have CORS set up properly in server.js on my API:

    app.use(function (req, res, next) {
    res.header("Access-Control-Allow-Origin", "*");
    res.header("Access-Control-Allow-Methods", "GET, POST, PATCH, PUT, DELETE, OPTIONS");
    res.header("Access-Control-Allow-Headers", "Origin, X-Requested-With, Content-Type, Accept");
    next();
});

Why is CORS accepting the POST locally but not on Heroku?

sideshowbarker
  • 81,827
  • 26
  • 193
  • 197
ShadowCore
  • 311
  • 2
  • 5
  • 13
  • Possible duplicate of [Allow CORS REST request to a Express/Node.js application on Heroku](http://stackoverflow.com/questions/11001817/allow-cors-rest-request-to-a-express-node-js-application-on-heroku) – Tatsuyuki Ishi Mar 27 '17 at 06:18
  • Also note that stringifying to json and adding the json content-type header is unnecessary. Just post the object, and angular will do that for you. – JB Nizet Mar 27 '17 at 06:41

1 Answers1

1

Ok, when you deploy a webapp or an app from differents port will make you deal with CORS, so you will need to configurate the server to be more friendly and accept CORS(makes you acept request form different origins). In tomcat modify web.xml, firebase do another thing, on azure the same etc... every serve has his own config. But in angular is the same, you must config a proxy to bypass these port problems. So create an proxy.conf.json like this

{
  "/angular": {
     "target":  {
       "host": "github.com",
       "protocol": "https:",
       "port": 443
     },
     "secure": false,
     "changeOrigin": true,
     "logLevel": "info"
  }
}

and then create a script like this in package.json:

"scripts": {
        "start": "ng serve --proxy-config proxy.conf.json",

and then instead run ng serve run ng start or npm start

Really nice documnets about this:

https://github.com/angular/angular-cli/pull/1896/commits/a81aa3b6117848a1c9c99d3b6d0666433b5144e0

Qiqke
  • 486
  • 5
  • 19