admin管理员组

文章数量:1242839

I've got a React app that via an API pulls data from a separate database.

When I run it locally, the app is one port and the API is on another port.

Since when I make AJAX calls in the app to the API, I need to include the URL where the API can connect.

It works if I hardcode the separate port (e.g., the app is on http://localhost:3000 and the API on http://localhost:3100, making the AJAX url call to the API http://localhost:3100/api/trusts).

However, since the app and API are on different ports, I can't make the AJAX url a relative path because it erroneously sends the AJAX call to http://localhost:3000/api/trusts and not http://localhost:3100/api/trusts.

How do I get them to run on the same port?

Thanks!

Here's my server.js:

var express = require('express');
var bodyParser = require('body-parser');
var mongoose = require('mongoose');
var path = require('path');
var app = express();
var router = express.Router();
var mongoose = require('mongoose');
var Schema = mongoose.Schema;

//set our port to either a predetermined port number if you have set it up, or 3001
var port = process.env.PORT || 5656;

//db config
var mongoDB = 'mongodb://XXX:[email protected]:XXX/XXX';
mongoose.connect(mongoDB);
var db = mongoose.connection;
db.on('error', console.error.bind(console, 'MongoDB connection error:'));

//body parsing
app.use(bodyParser.json());
app.use(bodyParser.urlencoded({ extended: true }));

// allow cross-browser
app.use(function(req, res, next) {
  res.setHeader('Access-Control-Allow-Origin', '*');
  next();
});

// handling static assets
app.use(express.static(path.join(__dirname, 'build')));

// api handling
var TrustsSchema = new Schema({
  id: String,
  name: String
});

var Trust = mongoose.model('Trust', TrustsSchema);

const trustRouter = express.Router();

trustRouter
    .get('/', (req,res) => {

      Trust.find(function(err, trusts) {
        if (err) {
          res.send(err);
        }
        res.json(trusts)
      });
    });

app.use('/api/trusts', trustRouter);


//now  we can set the route path & initialize the API
router.get('/', function(req, res) {
  res.json({ message: 'API Initialized!'});
});

app.get('/*', function (req, res) {
   res.sendFile(path.join(__dirname, 'build', 'index.html'));
 });

app.listen(port, function() {
  console.log(`api running on port ${port}`);
});

Below is the AJAX call I'm trying to make that doesn't work because the relative path is appended to the app's port (i.e., http://localhost:3000/) and not the API's port (i.e., http://localhost:3100/):

axios.get("/api/trusts")
  .then(res => {
    this.setState({trusts: res.data});
  })
  .catch(console.error);

I've got a React app that via an API pulls data from a separate database.

When I run it locally, the app is one port and the API is on another port.

Since when I make AJAX calls in the app to the API, I need to include the URL where the API can connect.

It works if I hardcode the separate port (e.g., the app is on http://localhost:3000 and the API on http://localhost:3100, making the AJAX url call to the API http://localhost:3100/api/trusts).

However, since the app and API are on different ports, I can't make the AJAX url a relative path because it erroneously sends the AJAX call to http://localhost:3000/api/trusts and not http://localhost:3100/api/trusts.

How do I get them to run on the same port?

Thanks!

Here's my server.js:

var express = require('express');
var bodyParser = require('body-parser');
var mongoose = require('mongoose');
var path = require('path');
var app = express();
var router = express.Router();
var mongoose = require('mongoose');
var Schema = mongoose.Schema;

//set our port to either a predetermined port number if you have set it up, or 3001
var port = process.env.PORT || 5656;

//db config
var mongoDB = 'mongodb://XXX:[email protected]:XXX/XXX';
mongoose.connect(mongoDB);
var db = mongoose.connection;
db.on('error', console.error.bind(console, 'MongoDB connection error:'));

//body parsing
app.use(bodyParser.json());
app.use(bodyParser.urlencoded({ extended: true }));

// allow cross-browser
app.use(function(req, res, next) {
  res.setHeader('Access-Control-Allow-Origin', '*');
  next();
});

// handling static assets
app.use(express.static(path.join(__dirname, 'build')));

// api handling
var TrustsSchema = new Schema({
  id: String,
  name: String
});

var Trust = mongoose.model('Trust', TrustsSchema);

const trustRouter = express.Router();

trustRouter
    .get('/', (req,res) => {

      Trust.find(function(err, trusts) {
        if (err) {
          res.send(err);
        }
        res.json(trusts)
      });
    });

app.use('/api/trusts', trustRouter);


//now  we can set the route path & initialize the API
router.get('/', function(req, res) {
  res.json({ message: 'API Initialized!'});
});

app.get('/*', function (req, res) {
   res.sendFile(path.join(__dirname, 'build', 'index.html'));
 });

app.listen(port, function() {
  console.log(`api running on port ${port}`);
});

Below is the AJAX call I'm trying to make that doesn't work because the relative path is appended to the app's port (i.e., http://localhost:3000/) and not the API's port (i.e., http://localhost:3100/):

axios.get("/api/trusts")
  .then(res => {
    this.setState({trusts: res.data});
  })
  .catch(console.error);
Share Improve this question edited Jul 16, 2018 at 18:16 Tholle 113k22 gold badges208 silver badges196 bronze badges asked Jul 16, 2018 at 17:44 Adam WhiteAdam White 1,1363 gold badges14 silver badges29 bronze badges 5
  • You can't run both of them on the same port. Depending on your setup you can use a proxy to redirect API requests to your backend server. With that you don't need to hardcode the URL but use /api/foo to make a request. – devserkan Commented Jul 16, 2018 at 17:51
  • 3 if you're using webpack-dev-server, you can use the builtin proxy to send requests to /api/... to a different address transparently webpack.js/configuration/dev-server/#devserver-proxy – Tyler Sebastian Commented Jul 16, 2018 at 17:53
  • I've tried setting the proxy and it doesn't solve the problem I'm having. I've included the AJAX call above to give some more context as to what I'm trying to do. – Adam White Commented Jul 16, 2018 at 18:01
  • 1 You definitely want the proxy. It'll allow you to forward all requests to /api/trusts to a specific port like http://localhost:3100/api/trusts – wpercy Commented Jul 16, 2018 at 18:03
  • You are using a static handler. Can you serve the React app from a static directory, in which case it will know the right way to access the dynamic request as it'll be from the same host:port. How are you hosting the react app? – xrd Commented Jul 16, 2018 at 18:20
Add a ment  | 

1 Answer 1

Reset to default 12

To tell the development server to proxy any unknown requests to your API server in development, add a proxy field to your package.json, for example:

"proxy": "http://localhost:4000",

This way, when you fetch('/api/todos') in development, the development server will recognize that it’s not a static asset, and will proxy your request to http://localhost:4000/api/todos as a fallback. The development server will only attempt to send requests without text/html in its Accept header to the proxy.

"Keep in mind that proxy only has effect in development (with npm start), and it is up to you to ensure that URLs like /api/todos point to the right thing in production."

Note: this feature is available with [email protected] and higher.

More details here: https://github./facebook/create-react-app/blob/master/packages/react-scripts/template/README.md#proxying-api-requests-in-development

本文标签: javascriptHow to set React app and API on same portStack Overflow