Expressjs проблема с сердечниками при извлечении из другого источника - PullRequest
0 голосов
/ 12 марта 2020

Так что я использую express как простой бэкэнд для моего клиентского приложения. При попытке сделать запрос к конечной точке GET / URL ниже он продолжает получать это сообщение.

Access to fetch at 'http://localhost:5000/urls' from origin 'http://localhost:3000' has been 
blocked by CORS policy: No 'Access-Control-Allow-Origin' header is present on the requested 
resource. If an opaque response serves your needs, set the request's mode to 'no-cors' to 
fetch the resource with CORS disabled.

Мой express сервер выглядит так

require("dotenv/config");
const express = require("express");
var bodyParser = require("body-parser");
const app = express();
const cors = require("cors");
const mongoose = require("mongoose");
const ShortUrl = require("./modules/shortUrl");

var whitelist = ['http://localhost:3000']
var corsOptions = {
  origin: function (origin, callback) {
    if (whitelist.indexOf(origin) !== -1) {
      callback(null, true)
    } else {
      callback(new Error('Not allowed by CORS'))
    }
  }
}
app.use(cors());
app.use(express.urlencoded({ extended: false }));
app.use(bodyParser.json());

mongoose
  .connect(process.env.MONGO_DB_CONNECTIONSTRING, {
    useNewUrlParser: true,
    useUnifiedTopology: true
  })
  .then(() => console.log("\nConnected to Mongo Database\n"));

app.get("/urls", cors(corsOptions), async (req, res) => {
  const shortUrls = await ShortUrl.find();
  res.send({ serverBaseUrl: process.env.SERVER_BASE_URL, shortUrls });
});

app.post("/url", cors(corsOptions), async (req, res) => {
  console.log(req.body);
  await ShortUrl.create({ full: req.body.fullUrl });
  res.send();
});

app.get("/:shortUrl", cors(corsOptions), async (req, res) => {
  const url = await ShortUrl.findOne({ short: req.params.shortUrl });

  if (url === null) return res.sendStatus(404);

  url.clicks++;
  await url.save();

  res.redirect(url.full);
});

app.listen(process.env.PORT || 5000);

В моем веб-приложении я Я использую сборщик, я быстро набрал, чтобы это могло быть что-то там, что не совсем правильно.

const createFetchOptions = (method, body = undefined) => {
  const options = {
    method,
    headers: {}
  };

  if (body && body instanceof FormData) {
    options.body = body;
  } else if (body) {
    options.headers["Content-type"] = "application/json";
    options.body = JSON.stringify(body);
  }

  return options;
};

const Fetcher = {
  get: async url => {
    const res = await fetch(url, createFetchOptions("GET"));
    return res;
  },

  post: async (url, body) => {
    const res = await fetch(url, createFetchOptions("POST", body));
    return res;
  }
};

export default Fetcher;

Это копия моего пакета, json включает его задачу с проблемой версии

{
  "name": "url_shortner",
  "version": "1.0.0",
  "description": "",
  "main": "index.js",
  "scripts": {
    "start": "nodemon server.js"
  },
  "author": "",
  "license": "ISC",
  "dependencies": {
    "body-parser": "^1.19.0",
    "cors": "^2.8.5",
    "dotenv": "^8.2.0",
    "ejs": "^3.0.1",
    "express": "^4.17.1",
    "mongoose": "^5.9.4",
    "shortid": "^2.2.15"
  },
  "devDependencies": {
    "nodemon": "^2.0.2"
  }
}

Буду признателен за любую помощь, Крис.

1 Ответ

0 голосов
/ 13 марта 2020

Когда вы используете app.use(cors());, он становится промежуточным ПО для всех запросов. Поэтому вам не нужно вручную добавлять его в ваши маршруты. Если вы хотите внести в белый список один конкретный домен для всех маршрутов, вы можете использовать опцию origin (я установил ее как переменную строки процесса, чтобы сделать ее более гибкой для сред development и production) :

const { CLIENT } = process.env;

app.use(
  cors({
    origin: CLIENT, // "http://localhost:3000" for dev and "https://example.com" for production
  })
);
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...