Reputation: 4239
I have a web app with a Node.js backend and Angular front end, both on the same server (Windows Server 2016), however, using different domains. So the front-end is at http://frontend.mydomain.com and the backend is at http://backend.mydomain.com.
Unfortunately I didn't write this web app, nor do I have any experience with Node.js or Angular.
The web app was working perfectly on the older server. However, we have moved both the front-end and the back-end to a new web server, and now, when trying to load it, I get this error message:
/#/login:1 Access to XMLHttpRequest at 'http://backend.mydomain/authenticate' from origin 'http://frontend.mydomain.com' has been blocked by CORS policy: No 'Access-Control-Allow-Origin' header is present on the requested resource.
Now I'm looking at the server.js file in the backend folder, and this is what it looks like:
var express = require('express');
const sql = require("mssql");
// var cors = require("cors");
var app = express();
var port = process.env.PORT || 3000;
// app.use(cors());
var config =
{
server: "**************",
database: "**************",
user: "**************",
password: "**************",
port: 1433,
connectionTimeout: 1500,
requestTimeout: 1500
};
app.use(function(req, res, next)
{
var data = '';
req.setEncoding('utf8');
req.on('data', function(chunk)
{
data += chunk;
});
req.on('end', function()
{
req.body = data;
next();
});
});
var cors = require("cors");
and app.use(cors());
where commented out, so I tried uncommenting it (and restarting the web service in IIS) but it made no difference.
I did some research, and tried adding things such as
app.use(function(req, res, next) {
res.header("Access-Control-Allow-Origin", "*");
res.header("Access-Control-Allow-Headers", "Origin, X-Requested-With, Content-Type, Accept")
next();
}
as well as a myriad of other things, always remembering to restart the web service in IIS after each change, but nothing I do seems to make a difference. Any suggestions anyone please? Thanks...
EDIT:
So the welcome/login page loads. But as soon as I type in my username and password, and hit the Submit button, I get the error described above. Looking at Developer Tools -> Network, I see that "authenticate" is in red, and when I click on it, it shows this:
Request URL: http://backend.mydomain.com/authenticate
Referrer Policy: no-referrer-when-downgrade
Content-Length: 1208
Content-Type: text/html
Date: Mon, 30 Mar 2020 10:53:26 GMT
Server: Microsoft-IIS/10.0
X-Powered-By: ASP.NET
Accept: application/json, text/plain, */*
Accept-Encoding: gzip, deflate
Accept-Language: en-US,en;q=0.9,es-AR;q=0.8,es;q=0.7
Connection: keep-alive
Content-Length: 34
content-type: text/plain
Host: backend.mydomain.com
Origin: http://frontend.mydomain.com
Referer: http://frontend.mydomain.com
User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/80.0.3987.149 Safari/537.36
myusername!@#$%&mypassword
p.s. i have changed actual domain names, usernames and passwords...
Upvotes: 1
Views: 1020
Reputation: 420
It may happen sometimes when the origin didn't implemented correctly, you can setup the back-end for this situation:
Use cors npm (in nodejs back-end) for setup the allowed origin by yourself:
const cors = require("cors");
app.use(cors({
origin: //Hardcoded string of your coming request path or regex for filter anything,
//Like this: "http://frontend.mydomain.com" or /frontend.mydomain.com/
credentials: true //Allow the server to get cookies and other auth data from other
// domains and ports to send cookies
}));
This is worked for me but in some cases you may get in trouble with preflight requests which are some kind of issue that the origin (a path which request is coming from) is not implemented correctly, You have to set a Express middleware for set some header manually (Like yourself):
app.use(function(req, res, next) {
res.header("Access-Control-Allow-Origin", "http://frontend.mydomain.com");
res.header("Access-Control-Allow-Headers", "Origin, X-Requested-With, Content-Type, Accept");
res.header('Access-Control-Allow-Methods', 'GET,PUT,POST,DELETE');
next();
});
You have to put this all together like this:
const cors = require("cors");
app.use(function(req, res, next) {
res.header("Access-Control-Allow-Origin", "http://frontend.mydomain.com");
res.header("Access-Control-Allow-Headers", "Origin, X-Requested-With, Content-Type, Accept");
res.header('Access-Control-Allow-Methods', 'GET,PUT,POST,DELETE');
next();
});
app.use(cors({
origin: //Hardcoded string of your coming request path or regex for check in string,
//Like this: "http://frontend.mydomain.com" or /frontend.mydomain.com/
credentials: true //Allow the server to get cookies and other auth data from other
// domains and ports
}));
In res.header("Access-Control-Allow-Origin", "http://frontend.mydomain.com")
it's better that you put a specific domain for the origin instead of a "*"
because it may be not secure at all. When you put "*"
CORS policy would prevent the credentials to be passed.
Hope this works.
Upvotes: 1
Reputation: 30685
I would check in your browser (use the developer tools, go to Network) and ensure you're seeing requests successfully returning allowed methods, headers etc.
You should see headers like:
Access-Control-Allow-Headers: content-type
Access-Control-Allow-Methods: GET,HEAD,PUT,PATCH,POST,DELETE
Access-Control-Allow-Origin: *
If these headers are not being send back, something is going wrong with the CORS setup.
You should at the very least receive an Access-Control-Allow-Origin header.
It may be that something is swallowing the headers you are sending back (such as a proxy). In this case the calls will fail.
Upvotes: 0
Reputation: 1522
Try adding the allowed http methods in your app.use()-
app.use(function(req, res, next) {
res.header("Access-Control-Allow-Origin", "*");
res.header("Access-Control-Allow-Methods", "GET,PUT,POST,DELETE");
res.header("Access-Control-Allow-Headers", "Origin, X-Requested-With, Content-Type, Accept")
next();
}
Upvotes: 0