Kevin Meredith
Kevin Meredith

Reputation: 41909

Enable CORS on Angular + Scala Play

Using AngularJS 1.2.16 and Scala Play 2.2.0, I'm trying to enable CORS.

Here's my request on the front-end. Basically it's a POST that sends a JSON with userName and password fields.

Request URL:http://localhost:9000/login
Request Headers CAUTION: Provisional headers are shown.
Accept:application/json, text/plain, */*
Content-Type:application/json;charset=UTF-8
Origin:http://localhost:8000
Referer:http://localhost:8000/app.html
User-Agent:Mozilla/5.0 ...
Request Payloadview source
  {userName:foo, password:bar}

And here's the back-end checkPreFlight method for allowing the headers of my POST request.

  def checkPreFlight = Action {
    Ok("...").withHeaders(
      ACCESS_CONTROL_ALLOW_ORIGIN -> "*",
      ACCESS_CONTROL_ALLOW_METHODS -> "POST",
      ACCESS_CONTROL_MAX_AGE -> "300",
      ACCESS_CONTROL_ALLOW_HEADERS -> "Origin, X-Requested-With, Content-Type, Accept,
                                         Referer, User-Agent")
  }

routes:

POST    /login                      controllers.Home.login
OPTIONS /login                      controllers.Home.checkPreFlight

My Chrome Browser's console shows:

XMLHttpRequest cannot load http://localhost:9000/login. No 'Access-Control-Allow-Origin' 
header is present on the requested resource. Origin 'http://localhost:8000' is therefore 
not allowed access. 

Note that the initial OPTIONS request returned a 200, however the POST was cancelled in the Network tab. Chrome (per this post) may be disabling CORS requests for security purposes?

When I tried on Firefox, both the OPTIONS and POST succeeded with a 200 status for each. However, Firefox still showed an error in the console:

200 OK 12ms 

Cross-Origin Request Blocked: The Same Origin Policy disallows reading the remote 
resource at http://localhost:9000/login. This can be fixed by moving the resource 
to the same domain or enabling CORS.

Additionally, my promise (which called the POST to /login) gets rejected, i.e. I added a console.log to the success and failure cases.

Upvotes: 4

Views: 1737

Answers (1)

William Billingsley
William Billingsley

Reputation: 771

You've shown that Access-Control-Allow-Origin is set in the response to the OPTIONS pre-flight request. But (at the time I wrote this) you haven't shown the header being set in the response to the POST request itself. As it's an easy mistake to make, I'd hazard a guess that's where your error is.

The header needs to be present in both responses. That means, for the code you've given, that you need to set the header in both controllers.Home.checkPreflight and controllers.Home.login

Upvotes: 5

Related Questions