New project structure
New folder structure Changed to type:module Moved routes to separate files
This commit is contained in:
302
app.js
302
app.js
@@ -1,292 +1,20 @@
|
||||
/*
|
||||
|
||||
|
||||
CONFIGS
|
||||
|
||||
|
||||
*/
|
||||
require("dotenv").config(); //require environment variables
|
||||
const mongoose = require("mongoose");
|
||||
const express = require("express");
|
||||
const helmet = require("helmet");
|
||||
const multer = require("multer");
|
||||
const bcrypt = require("bcrypt");
|
||||
const validators = require("./validation");
|
||||
var sanitizer = require("string-sanitizer");
|
||||
import * as config from "./config/index.js";
|
||||
const { port, dbPass } = config;
|
||||
import express from "express";
|
||||
const app = express();
|
||||
app.use(helmet());
|
||||
const port = 3000;
|
||||
const rateLimit = require("express-rate-limit");
|
||||
const limiter = rateLimit({
|
||||
windowMs: 15 * 60 * 1000, //time window
|
||||
max: 100, //requests from a single IP for a time window
|
||||
});
|
||||
app.use(limiter);
|
||||
const bodyParser = require("body-parser");
|
||||
app.use(bodyParser.json({ limit: "100kb" })); // limit body payload size
|
||||
app.use(bodyParser.urlencoded({ extended: true }));
|
||||
/*
|
||||
|
||||
|
||||
Mongoose schemas
|
||||
|
||||
|
||||
*/
|
||||
const Restaurant = require("./models/restaurant");
|
||||
const Dish = require("./models/dish");
|
||||
const User = require("./models/users");
|
||||
/*
|
||||
|
||||
|
||||
Image upload config (multer)
|
||||
|
||||
|
||||
*/
|
||||
var storage = multer.diskStorage({
|
||||
destination: function (req, file, cb) {
|
||||
cb(null, "./images");
|
||||
},
|
||||
filename: function (req, file, cb) {
|
||||
cb(
|
||||
null,
|
||||
new Date()
|
||||
.toISOString()
|
||||
.trim()
|
||||
.replace(/[:_ -.]/g, "") +
|
||||
Math.floor(Math.random() * 5000 + 1) +
|
||||
file.mimetype.replace("/", ".")
|
||||
);
|
||||
},
|
||||
});
|
||||
const upload = multer({
|
||||
storage: storage,
|
||||
fileFilter: function (req, file, cb) {
|
||||
if (file.mimetype !== "image/jpg") {
|
||||
return cb(null, false);
|
||||
}
|
||||
cb(null, true);
|
||||
},
|
||||
limits: { fileSize: 4000000 },
|
||||
}); //max file size = 4Mb
|
||||
/*
|
||||
|
||||
Code
|
||||
|
||||
*/
|
||||
// Connect to DB
|
||||
mongoose.connect(
|
||||
"mongodb+srv://menui_db_user:" +
|
||||
process.env.DB_PASS +
|
||||
"@menui-database.9quwf.mongodb.net/<dbname>?retryWrites=true&w=majority",
|
||||
{ useNewUrlParser: true, useUnifiedTopology: true },
|
||||
(err) => {
|
||||
if (err) console.log("Unable to connect :(");
|
||||
else console.log("Connected To Database");
|
||||
}
|
||||
);
|
||||
|
||||
// GET RESTAURANT BY ID
|
||||
|
||||
app.get("/restaurant", function (req, res) {
|
||||
//validate restaurant
|
||||
validators.validateRestaurant(req.body.restaurantId, (result) => {
|
||||
if (!result) {
|
||||
res.sendStatus(400);
|
||||
} else {
|
||||
Restaurant.findById(req.body.restaurantId, (err, data) => {
|
||||
import loaders from "./loaders/index.js";
|
||||
//
|
||||
// Server init function
|
||||
//
|
||||
async function startServer() {
|
||||
await loaders({ expressApp: app, dbPass: dbPass });
|
||||
app.listen(port, (err) => {
|
||||
if (err) {
|
||||
res.sendStatus(404);
|
||||
} else res.send(data);
|
||||
});
|
||||
console.log("Server Startup Failed");
|
||||
return;
|
||||
}
|
||||
console.log("Server is running");
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
// GET RESTAURANTS IN A SPECIFIED CITY
|
||||
|
||||
app.get("/city", function (req, res) {
|
||||
Restaurant.find({ city: req.body.city }, (err, data) => {
|
||||
if (err) {
|
||||
res.sendStatus(404);
|
||||
} else res.send(data);
|
||||
});
|
||||
});
|
||||
|
||||
// GET DISH BY ID
|
||||
|
||||
app.get("/dish", (req, res) => {
|
||||
Dish.findById(req.body.dishId, (err, data) => {
|
||||
if (err) {
|
||||
res.sendStatus(404);
|
||||
} else res.send(data);
|
||||
});
|
||||
});
|
||||
|
||||
// ADD NEW RESTAURANT
|
||||
|
||||
app.post("/restaurant", (req, res) => {
|
||||
//validate user
|
||||
validators.validateUser(req.body.userId, (result) => {
|
||||
if (!result) res.sendStatus(401);
|
||||
//create restaurant
|
||||
const restaurant = new Restaurant({
|
||||
_id: new mongoose.Types.ObjectId(),
|
||||
name: sanitizer.sanitize.keepUnicode(req.body.name),
|
||||
city: sanitizer.sanitize.keepUnicode(req.body.city),
|
||||
imgUrl: req.body.imgUrl,
|
||||
workingHours: req.body.workingHours,
|
||||
hidden: req.body.hidden,
|
||||
});
|
||||
//add restaurant to DB
|
||||
restaurant.save((err) => {
|
||||
if (err) {
|
||||
res.sendStatus(400);
|
||||
} else {
|
||||
res.status(201);
|
||||
}
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
// ADD NEW DISH
|
||||
|
||||
app.post("/dish", (req, res) => {
|
||||
//validate restaurant
|
||||
validators.validateRestaurant(req.body.restaurantId, (result) => {
|
||||
if (!result) res.sendStatus(400);
|
||||
else {
|
||||
//validate user
|
||||
validators.validateUser(req.body.userId, (result) => {
|
||||
if (!result) {
|
||||
res.sendStatus(401);
|
||||
} else {
|
||||
//construct dish
|
||||
const dish = new Dish({
|
||||
_id: new mongoose.Types.ObjectId(),
|
||||
name: sanitizer.sanitize.keepUnicode(req.body.dish.name),
|
||||
category: req.body.dish.category,
|
||||
price: req.body.dish.price,
|
||||
notes: sanitizer.sanitize.keepUnicode(req.body.dish.notes),
|
||||
imgUrl: req.body.dish.imgUrl,
|
||||
weight: req.body.dish.weight,
|
||||
allergens: {
|
||||
gluten: req.body.dish.allergens.gluten,
|
||||
lactose: req.body.dish.allergens.lactose,
|
||||
soy: req.body.dish.allergens.soy,
|
||||
eggs: req.body.dish.allergens.eggs,
|
||||
seaFood: req.body.dish.allergens.seaFood,
|
||||
peanuts: req.body.dish.allergens.peanuts,
|
||||
sesame: req.body.dish.allergens.sesame,
|
||||
},
|
||||
vegan: req.body.dish.vegan,
|
||||
vegetarian: req.body.dish.vegetarian,
|
||||
});
|
||||
//add dish to DB
|
||||
dish.save((err) => {
|
||||
if (err) {
|
||||
res.sendStatus(400);
|
||||
} else {
|
||||
//add dish ID to restaurant
|
||||
Restaurant.updateOne(
|
||||
{ _id: req.body.restaurantId },
|
||||
{ $push: { dishes: dish._id } },
|
||||
(err) => {
|
||||
if (err) {
|
||||
res.sendStatus(400);
|
||||
} else {
|
||||
res.sendStatus(201);
|
||||
}
|
||||
}
|
||||
);
|
||||
}
|
||||
});
|
||||
}
|
||||
});
|
||||
}
|
||||
});
|
||||
});
|
||||
|
||||
// GET ALL DISHES FROM A RESTAURANT ID (All at once)
|
||||
|
||||
app.get("/dishes", (req, res) => {
|
||||
//validate restaurant
|
||||
validators.validateRestaurant(req.body.restaurantId, (result) => {
|
||||
if (!result) {
|
||||
res.sendStatus(400);
|
||||
} else {
|
||||
//get restaurant
|
||||
Restaurant.findById(req.body.restaurantId, (err, result) => {
|
||||
if (err) {
|
||||
res.sendStatus(404);
|
||||
} else {
|
||||
//prepare variables
|
||||
const dishesCount = result.dishes.length;
|
||||
let dishes = [];
|
||||
//fetch all dishes
|
||||
result.dishes.forEach((element) => {
|
||||
Dish.findById(element, (err, result) => {
|
||||
if (err) console.log("ERROR fetching dish");
|
||||
dishes.push(result);
|
||||
if (dishes.length == dishesCount) res.send(dishes);
|
||||
});
|
||||
});
|
||||
}
|
||||
});
|
||||
}
|
||||
});
|
||||
});
|
||||
|
||||
// UPDATE DISH
|
||||
|
||||
app.put("/dish", (req, res) => {
|
||||
//validate dish ID
|
||||
validators.validateDishId(req.body.dishId, (result) => {
|
||||
if (!result) {
|
||||
res.sendStatus(204);
|
||||
} else {
|
||||
//validate user
|
||||
validators.validateUser(req.body.userId, (result) => {
|
||||
if (!result) {
|
||||
res.sendStatus(401);
|
||||
} else {
|
||||
//replace dish in DB
|
||||
Dish.replaceOne(
|
||||
{ _id: req.body.dishId },
|
||||
{
|
||||
name: sanitizer.sanitize.keepUnicode(req.body.dish.name),
|
||||
category: req.body.dish.category,
|
||||
price: req.body.dish.price,
|
||||
notes: sanitizer.sanitize.keepUnicode(req.body.dish.notes),
|
||||
imgUrl: req.body.dish.imgUrl,
|
||||
weight: req.body.dish.weight,
|
||||
allergens: {
|
||||
gluten: req.body.dish.allergens.gluten,
|
||||
lactose: req.body.dish.allergens.lactose,
|
||||
soy: req.body.dish.allergens.soy,
|
||||
eggs: req.body.dish.allergens.eggs,
|
||||
seaFood: req.body.dish.allergens.seaFood,
|
||||
peanuts: req.body.dish.allergens.peanuts,
|
||||
sesame: req.body.dish.allergens.sesame,
|
||||
},
|
||||
vegan: req.body.dish.vegan,
|
||||
vegetarian: req.body.dish.vegetarian,
|
||||
},
|
||||
(err) => {
|
||||
if (err) {
|
||||
res.sendStatus(304);
|
||||
} else {
|
||||
res.sendStatus(200);
|
||||
}
|
||||
}
|
||||
);
|
||||
}
|
||||
});
|
||||
}
|
||||
});
|
||||
});
|
||||
|
||||
app.post("/img", upload.single("menuiImage"), (req, res) => {
|
||||
res.sendStatus(201);
|
||||
});
|
||||
|
||||
app.listen(port, () => console.log("Menui listening at: " + port));
|
||||
startServer();
|
||||
|
||||
5
config/index.js
Normal file
5
config/index.js
Normal file
@@ -0,0 +1,5 @@
|
||||
import dotenv from "dotenv";
|
||||
dotenv.config();
|
||||
|
||||
export const port = process.env.PORT;
|
||||
export const dbPass = process.env.DB_PASS;
|
||||
27
loaders/express.js
Normal file
27
loaders/express.js
Normal file
@@ -0,0 +1,27 @@
|
||||
import bodyParser from "body-parser";
|
||||
import cors from "cors";
|
||||
import rateLimiter from "express-rate-limit";
|
||||
import helmet from "helmet";
|
||||
import routeDish from "../routes/routeDish.js";
|
||||
import routeCity from "../routes/routeCity.js";
|
||||
import routeRestaurant from "../routes/routeRestaurant.js";
|
||||
import routeImg from "../routes/routeImg.js";
|
||||
|
||||
export default ({ app }) => {
|
||||
const limiter = rateLimiter({
|
||||
windowMs: 15 * 60 * 1000, //time window
|
||||
max: 100, //requests from a single IP for a time window
|
||||
});
|
||||
|
||||
app.use(bodyParser.json({ limit: "100kb" })); // limit JSON body payload size
|
||||
app.use(bodyParser.urlencoded({ extended: true }));
|
||||
app.use(helmet());
|
||||
app.use(limiter);
|
||||
app.use(cors());
|
||||
app.use("/dish", routeDish);
|
||||
app.use("/city", routeCity);
|
||||
app.use("/restaurant", routeRestaurant);
|
||||
app.use("/img", routeImg);
|
||||
|
||||
return app;
|
||||
};
|
||||
9
loaders/index.js
Normal file
9
loaders/index.js
Normal file
@@ -0,0 +1,9 @@
|
||||
import expressLoader from "./express.js";
|
||||
import mongooseLoader from "./mongoose.js";
|
||||
|
||||
export default async ({ expressApp, dbPass }) => {
|
||||
const mongoConnection = await mongooseLoader({ pass: dbPass });
|
||||
console.log("Mongoose Loaded");
|
||||
await expressLoader({ app: expressApp });
|
||||
console.log("Express Initialized");
|
||||
};
|
||||
14
loaders/mongoose.js
Normal file
14
loaders/mongoose.js
Normal file
@@ -0,0 +1,14 @@
|
||||
import mongoose from "mongoose";
|
||||
|
||||
export default async ({ pass }) => {
|
||||
const connection = await mongoose.connect(
|
||||
"mongodb+srv://menui_db_user:" +
|
||||
pass +
|
||||
"@menui-database.9quwf.mongodb.net/<dbname>?retryWrites=true&w=majority",
|
||||
{ useNewUrlParser: true, useUnifiedTopology: true },
|
||||
(err) => {
|
||||
if (err) console.log("Unable to connect :(");
|
||||
else console.log("Connected To Database");
|
||||
}
|
||||
);
|
||||
};
|
||||
@@ -1,4 +1,4 @@
|
||||
const mongoose = require("mongoose");
|
||||
import mongoose from "mongoose";
|
||||
|
||||
const dishSchema = mongoose.Schema({
|
||||
_id: mongoose.Types.ObjectId,
|
||||
@@ -39,4 +39,4 @@ const dishSchema = mongoose.Schema({
|
||||
vegetarian: Boolean,
|
||||
});
|
||||
|
||||
module.exports = mongoose.model("Dish", dishSchema);
|
||||
export default mongoose.model("Dish", dishSchema);
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
const mongoose = require("mongoose");
|
||||
import mongoose from "mongoose";
|
||||
|
||||
const restaurantSchema = mongoose.Schema({
|
||||
_id: mongoose.Types.ObjectId,
|
||||
@@ -24,4 +24,4 @@ const restaurantSchema = mongoose.Schema({
|
||||
dishes: [mongoose.Types.ObjectId],
|
||||
});
|
||||
|
||||
module.exports = mongoose.model("Restaurant", restaurantSchema);
|
||||
export default mongoose.model("Restaurant", restaurantSchema);
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
const mongoose = require("mongoose");
|
||||
import mongoose from "mongoose";
|
||||
|
||||
const userSchema = mongoose.Schema({
|
||||
_id: mongoose.Types.ObjectId,
|
||||
@@ -18,4 +18,4 @@ const userSchema = mongoose.Schema({
|
||||
subscriptionDue: Date,
|
||||
});
|
||||
|
||||
module.exports = mongoose.model("User", userSchema);
|
||||
export default mongoose.model("User", userSchema);
|
||||
|
||||
33
node_modules/cors/CONTRIBUTING.md
generated
vendored
Normal file
33
node_modules/cors/CONTRIBUTING.md
generated
vendored
Normal file
@@ -0,0 +1,33 @@
|
||||
# contributing to `cors`
|
||||
|
||||
CORS is a node.js package for providing a [connect](http://www.senchalabs.org/connect/)/[express](http://expressjs.com/) middleware that can be used to enable [CORS](http://en.wikipedia.org/wiki/Cross-origin_resource_sharing) with various options. Learn more about the project in [the README](README.md).
|
||||
|
||||
## The CORS Spec
|
||||
|
||||
[http://www.w3.org/TR/cors/](http://www.w3.org/TR/cors/)
|
||||
|
||||
## Pull Requests Welcome
|
||||
|
||||
* Include `'use strict';` in every javascript file.
|
||||
* 2 space indentation.
|
||||
* Please run the testing steps below before submitting.
|
||||
|
||||
## Testing
|
||||
|
||||
```bash
|
||||
$ npm install
|
||||
$ npm test
|
||||
```
|
||||
|
||||
## Interactive Testing Harness
|
||||
|
||||
[http://node-cors-client.herokuapp.com](http://node-cors-client.herokuapp.com)
|
||||
|
||||
Related git repositories:
|
||||
|
||||
* [https://github.com/TroyGoode/node-cors-server](https://github.com/TroyGoode/node-cors-server)
|
||||
* [https://github.com/TroyGoode/node-cors-client](https://github.com/TroyGoode/node-cors-client)
|
||||
|
||||
## License
|
||||
|
||||
[MIT License](http://www.opensource.org/licenses/mit-license.php)
|
||||
58
node_modules/cors/HISTORY.md
generated
vendored
Normal file
58
node_modules/cors/HISTORY.md
generated
vendored
Normal file
@@ -0,0 +1,58 @@
|
||||
2.8.5 / 2018-11-04
|
||||
==================
|
||||
|
||||
* Fix setting `maxAge` option to `0`
|
||||
|
||||
2.8.4 / 2017-07-12
|
||||
==================
|
||||
|
||||
* Work-around Safari bug in default pre-flight response
|
||||
|
||||
2.8.3 / 2017-03-29
|
||||
==================
|
||||
|
||||
* Fix error when options delegate missing `methods` option
|
||||
|
||||
2.8.2 / 2017-03-28
|
||||
==================
|
||||
|
||||
* Fix error when frozen options are passed
|
||||
* Send "Vary: Origin" when using regular expressions
|
||||
* Send "Vary: Access-Control-Request-Headers" when dynamic `allowedHeaders`
|
||||
|
||||
2.8.1 / 2016-09-08
|
||||
==================
|
||||
|
||||
This release only changed documentation.
|
||||
|
||||
2.8.0 / 2016-08-23
|
||||
==================
|
||||
|
||||
* Add `optionsSuccessStatus` option
|
||||
|
||||
2.7.2 / 2016-08-23
|
||||
==================
|
||||
|
||||
* Fix error when Node.js running in strict mode
|
||||
|
||||
2.7.1 / 2015-05-28
|
||||
==================
|
||||
|
||||
* Move module into expressjs organization
|
||||
|
||||
2.7.0 / 2015-05-28
|
||||
==================
|
||||
|
||||
* Allow array of matching condition as `origin` option
|
||||
* Allow regular expression as `origin` option
|
||||
|
||||
2.6.1 / 2015-05-28
|
||||
==================
|
||||
|
||||
* Update `license` in package.json
|
||||
|
||||
2.6.0 / 2015-04-27
|
||||
==================
|
||||
|
||||
* Add `preflightContinue` option
|
||||
* Fix "Vary: Origin" header added for "*"
|
||||
22
node_modules/cors/LICENSE
generated
vendored
Normal file
22
node_modules/cors/LICENSE
generated
vendored
Normal file
@@ -0,0 +1,22 @@
|
||||
(The MIT License)
|
||||
|
||||
Copyright (c) 2013 Troy Goode <troygoode@gmail.com>
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining
|
||||
a copy of this software and associated documentation files (the
|
||||
'Software'), to deal in the Software without restriction, including
|
||||
without limitation the rights to use, copy, modify, merge, publish,
|
||||
distribute, sublicense, and/or sell copies of the Software, and to
|
||||
permit persons to whom the Software is furnished to do so, subject to
|
||||
the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be
|
||||
included in all copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED 'AS IS', WITHOUT WARRANTY OF ANY KIND,
|
||||
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
||||
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
|
||||
IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
|
||||
CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
|
||||
TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
|
||||
SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
||||
243
node_modules/cors/README.md
generated
vendored
Normal file
243
node_modules/cors/README.md
generated
vendored
Normal file
@@ -0,0 +1,243 @@
|
||||
# cors
|
||||
|
||||
[![NPM Version][npm-image]][npm-url]
|
||||
[![NPM Downloads][downloads-image]][downloads-url]
|
||||
[![Build Status][travis-image]][travis-url]
|
||||
[![Test Coverage][coveralls-image]][coveralls-url]
|
||||
|
||||
CORS is a node.js package for providing a [Connect](http://www.senchalabs.org/connect/)/[Express](http://expressjs.com/) middleware that can be used to enable [CORS](http://en.wikipedia.org/wiki/Cross-origin_resource_sharing) with various options.
|
||||
|
||||
**[Follow me (@troygoode) on Twitter!](https://twitter.com/intent/user?screen_name=troygoode)**
|
||||
|
||||
* [Installation](#installation)
|
||||
* [Usage](#usage)
|
||||
* [Simple Usage](#simple-usage-enable-all-cors-requests)
|
||||
* [Enable CORS for a Single Route](#enable-cors-for-a-single-route)
|
||||
* [Configuring CORS](#configuring-cors)
|
||||
* [Configuring CORS Asynchronously](#configuring-cors-asynchronously)
|
||||
* [Enabling CORS Pre-Flight](#enabling-cors-pre-flight)
|
||||
* [Configuration Options](#configuration-options)
|
||||
* [Demo](#demo)
|
||||
* [License](#license)
|
||||
* [Author](#author)
|
||||
|
||||
## Installation
|
||||
|
||||
This is a [Node.js](https://nodejs.org/en/) module available through the
|
||||
[npm registry](https://www.npmjs.com/). Installation is done using the
|
||||
[`npm install` command](https://docs.npmjs.com/getting-started/installing-npm-packages-locally):
|
||||
|
||||
```sh
|
||||
$ npm install cors
|
||||
```
|
||||
|
||||
## Usage
|
||||
|
||||
### Simple Usage (Enable *All* CORS Requests)
|
||||
|
||||
```javascript
|
||||
var express = require('express')
|
||||
var cors = require('cors')
|
||||
var app = express()
|
||||
|
||||
app.use(cors())
|
||||
|
||||
app.get('/products/:id', function (req, res, next) {
|
||||
res.json({msg: 'This is CORS-enabled for all origins!'})
|
||||
})
|
||||
|
||||
app.listen(80, function () {
|
||||
console.log('CORS-enabled web server listening on port 80')
|
||||
})
|
||||
```
|
||||
|
||||
### Enable CORS for a Single Route
|
||||
|
||||
```javascript
|
||||
var express = require('express')
|
||||
var cors = require('cors')
|
||||
var app = express()
|
||||
|
||||
app.get('/products/:id', cors(), function (req, res, next) {
|
||||
res.json({msg: 'This is CORS-enabled for a Single Route'})
|
||||
})
|
||||
|
||||
app.listen(80, function () {
|
||||
console.log('CORS-enabled web server listening on port 80')
|
||||
})
|
||||
```
|
||||
|
||||
### Configuring CORS
|
||||
|
||||
```javascript
|
||||
var express = require('express')
|
||||
var cors = require('cors')
|
||||
var app = express()
|
||||
|
||||
var corsOptions = {
|
||||
origin: 'http://example.com',
|
||||
optionsSuccessStatus: 200 // some legacy browsers (IE11, various SmartTVs) choke on 204
|
||||
}
|
||||
|
||||
app.get('/products/:id', cors(corsOptions), function (req, res, next) {
|
||||
res.json({msg: 'This is CORS-enabled for only example.com.'})
|
||||
})
|
||||
|
||||
app.listen(80, function () {
|
||||
console.log('CORS-enabled web server listening on port 80')
|
||||
})
|
||||
```
|
||||
|
||||
### Configuring CORS w/ Dynamic Origin
|
||||
|
||||
```javascript
|
||||
var express = require('express')
|
||||
var cors = require('cors')
|
||||
var app = express()
|
||||
|
||||
var whitelist = ['http://example1.com', 'http://example2.com']
|
||||
var corsOptions = {
|
||||
origin: function (origin, callback) {
|
||||
if (whitelist.indexOf(origin) !== -1) {
|
||||
callback(null, true)
|
||||
} else {
|
||||
callback(new Error('Not allowed by CORS'))
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
app.get('/products/:id', cors(corsOptions), function (req, res, next) {
|
||||
res.json({msg: 'This is CORS-enabled for a whitelisted domain.'})
|
||||
})
|
||||
|
||||
app.listen(80, function () {
|
||||
console.log('CORS-enabled web server listening on port 80')
|
||||
})
|
||||
```
|
||||
|
||||
If you do not want to block REST tools or server-to-server requests,
|
||||
add a `!origin` check in the origin function like so:
|
||||
|
||||
```javascript
|
||||
var corsOptions = {
|
||||
origin: function (origin, callback) {
|
||||
if (whitelist.indexOf(origin) !== -1 || !origin) {
|
||||
callback(null, true)
|
||||
} else {
|
||||
callback(new Error('Not allowed by CORS'))
|
||||
}
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### Enabling CORS Pre-Flight
|
||||
|
||||
Certain CORS requests are considered 'complex' and require an initial
|
||||
`OPTIONS` request (called the "pre-flight request"). An example of a
|
||||
'complex' CORS request is one that uses an HTTP verb other than
|
||||
GET/HEAD/POST (such as DELETE) or that uses custom headers. To enable
|
||||
pre-flighting, you must add a new OPTIONS handler for the route you want
|
||||
to support:
|
||||
|
||||
```javascript
|
||||
var express = require('express')
|
||||
var cors = require('cors')
|
||||
var app = express()
|
||||
|
||||
app.options('/products/:id', cors()) // enable pre-flight request for DELETE request
|
||||
app.del('/products/:id', cors(), function (req, res, next) {
|
||||
res.json({msg: 'This is CORS-enabled for all origins!'})
|
||||
})
|
||||
|
||||
app.listen(80, function () {
|
||||
console.log('CORS-enabled web server listening on port 80')
|
||||
})
|
||||
```
|
||||
|
||||
You can also enable pre-flight across-the-board like so:
|
||||
|
||||
```javascript
|
||||
app.options('*', cors()) // include before other routes
|
||||
```
|
||||
|
||||
### Configuring CORS Asynchronously
|
||||
|
||||
```javascript
|
||||
var express = require('express')
|
||||
var cors = require('cors')
|
||||
var app = express()
|
||||
|
||||
var whitelist = ['http://example1.com', 'http://example2.com']
|
||||
var corsOptionsDelegate = function (req, callback) {
|
||||
var corsOptions;
|
||||
if (whitelist.indexOf(req.header('Origin')) !== -1) {
|
||||
corsOptions = { origin: true } // reflect (enable) the requested origin in the CORS response
|
||||
} else {
|
||||
corsOptions = { origin: false } // disable CORS for this request
|
||||
}
|
||||
callback(null, corsOptions) // callback expects two parameters: error and options
|
||||
}
|
||||
|
||||
app.get('/products/:id', cors(corsOptionsDelegate), function (req, res, next) {
|
||||
res.json({msg: 'This is CORS-enabled for a whitelisted domain.'})
|
||||
})
|
||||
|
||||
app.listen(80, function () {
|
||||
console.log('CORS-enabled web server listening on port 80')
|
||||
})
|
||||
```
|
||||
|
||||
## Configuration Options
|
||||
|
||||
* `origin`: Configures the **Access-Control-Allow-Origin** CORS header. Possible values:
|
||||
- `Boolean` - set `origin` to `true` to reflect the [request origin](http://tools.ietf.org/html/draft-abarth-origin-09), as defined by `req.header('Origin')`, or set it to `false` to disable CORS.
|
||||
- `String` - set `origin` to a specific origin. For example if you set it to `"http://example.com"` only requests from "http://example.com" will be allowed.
|
||||
- `RegExp` - set `origin` to a regular expression pattern which will be used to test the request origin. If it's a match, the request origin will be reflected. For example the pattern `/example\.com$/` will reflect any request that is coming from an origin ending with "example.com".
|
||||
- `Array` - set `origin` to an array of valid origins. Each origin can be a `String` or a `RegExp`. For example `["http://example1.com", /\.example2\.com$/]` will accept any request from "http://example1.com" or from a subdomain of "example2.com".
|
||||
- `Function` - set `origin` to a function implementing some custom logic. The function takes the request origin as the first parameter and a callback (which expects the signature `err [object], allow [bool]`) as the second.
|
||||
* `methods`: Configures the **Access-Control-Allow-Methods** CORS header. Expects a comma-delimited string (ex: 'GET,PUT,POST') or an array (ex: `['GET', 'PUT', 'POST']`).
|
||||
* `allowedHeaders`: Configures the **Access-Control-Allow-Headers** CORS header. Expects a comma-delimited string (ex: 'Content-Type,Authorization') or an array (ex: `['Content-Type', 'Authorization']`). If not specified, defaults to reflecting the headers specified in the request's **Access-Control-Request-Headers** header.
|
||||
* `exposedHeaders`: Configures the **Access-Control-Expose-Headers** CORS header. Expects a comma-delimited string (ex: 'Content-Range,X-Content-Range') or an array (ex: `['Content-Range', 'X-Content-Range']`). If not specified, no custom headers are exposed.
|
||||
* `credentials`: Configures the **Access-Control-Allow-Credentials** CORS header. Set to `true` to pass the header, otherwise it is omitted.
|
||||
* `maxAge`: Configures the **Access-Control-Max-Age** CORS header. Set to an integer to pass the header, otherwise it is omitted.
|
||||
* `preflightContinue`: Pass the CORS preflight response to the next handler.
|
||||
* `optionsSuccessStatus`: Provides a status code to use for successful `OPTIONS` requests, since some legacy browsers (IE11, various SmartTVs) choke on `204`.
|
||||
|
||||
The default configuration is the equivalent of:
|
||||
|
||||
```json
|
||||
{
|
||||
"origin": "*",
|
||||
"methods": "GET,HEAD,PUT,PATCH,POST,DELETE",
|
||||
"preflightContinue": false,
|
||||
"optionsSuccessStatus": 204
|
||||
}
|
||||
```
|
||||
|
||||
For details on the effect of each CORS header, read [this](http://www.html5rocks.com/en/tutorials/cors/) article on HTML5 Rocks.
|
||||
|
||||
## Demo
|
||||
|
||||
A demo that illustrates CORS working (and not working) using jQuery is available here: [http://node-cors-client.herokuapp.com/](http://node-cors-client.herokuapp.com/)
|
||||
|
||||
Code for that demo can be found here:
|
||||
|
||||
* Client: [https://github.com/TroyGoode/node-cors-client](https://github.com/TroyGoode/node-cors-client)
|
||||
* Server: [https://github.com/TroyGoode/node-cors-server](https://github.com/TroyGoode/node-cors-server)
|
||||
|
||||
## License
|
||||
|
||||
[MIT License](http://www.opensource.org/licenses/mit-license.php)
|
||||
|
||||
## Author
|
||||
|
||||
[Troy Goode](https://github.com/TroyGoode) ([troygoode@gmail.com](mailto:troygoode@gmail.com))
|
||||
|
||||
[coveralls-image]: https://img.shields.io/coveralls/expressjs/cors/master.svg
|
||||
[coveralls-url]: https://coveralls.io/r/expressjs/cors?branch=master
|
||||
[downloads-image]: https://img.shields.io/npm/dm/cors.svg
|
||||
[downloads-url]: https://npmjs.org/package/cors
|
||||
[npm-image]: https://img.shields.io/npm/v/cors.svg
|
||||
[npm-url]: https://npmjs.org/package/cors
|
||||
[travis-image]: https://img.shields.io/travis/expressjs/cors/master.svg
|
||||
[travis-url]: https://travis-ci.org/expressjs/cors
|
||||
238
node_modules/cors/lib/index.js
generated
vendored
Normal file
238
node_modules/cors/lib/index.js
generated
vendored
Normal file
@@ -0,0 +1,238 @@
|
||||
(function () {
|
||||
|
||||
'use strict';
|
||||
|
||||
var assign = require('object-assign');
|
||||
var vary = require('vary');
|
||||
|
||||
var defaults = {
|
||||
origin: '*',
|
||||
methods: 'GET,HEAD,PUT,PATCH,POST,DELETE',
|
||||
preflightContinue: false,
|
||||
optionsSuccessStatus: 204
|
||||
};
|
||||
|
||||
function isString(s) {
|
||||
return typeof s === 'string' || s instanceof String;
|
||||
}
|
||||
|
||||
function isOriginAllowed(origin, allowedOrigin) {
|
||||
if (Array.isArray(allowedOrigin)) {
|
||||
for (var i = 0; i < allowedOrigin.length; ++i) {
|
||||
if (isOriginAllowed(origin, allowedOrigin[i])) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
} else if (isString(allowedOrigin)) {
|
||||
return origin === allowedOrigin;
|
||||
} else if (allowedOrigin instanceof RegExp) {
|
||||
return allowedOrigin.test(origin);
|
||||
} else {
|
||||
return !!allowedOrigin;
|
||||
}
|
||||
}
|
||||
|
||||
function configureOrigin(options, req) {
|
||||
var requestOrigin = req.headers.origin,
|
||||
headers = [],
|
||||
isAllowed;
|
||||
|
||||
if (!options.origin || options.origin === '*') {
|
||||
// allow any origin
|
||||
headers.push([{
|
||||
key: 'Access-Control-Allow-Origin',
|
||||
value: '*'
|
||||
}]);
|
||||
} else if (isString(options.origin)) {
|
||||
// fixed origin
|
||||
headers.push([{
|
||||
key: 'Access-Control-Allow-Origin',
|
||||
value: options.origin
|
||||
}]);
|
||||
headers.push([{
|
||||
key: 'Vary',
|
||||
value: 'Origin'
|
||||
}]);
|
||||
} else {
|
||||
isAllowed = isOriginAllowed(requestOrigin, options.origin);
|
||||
// reflect origin
|
||||
headers.push([{
|
||||
key: 'Access-Control-Allow-Origin',
|
||||
value: isAllowed ? requestOrigin : false
|
||||
}]);
|
||||
headers.push([{
|
||||
key: 'Vary',
|
||||
value: 'Origin'
|
||||
}]);
|
||||
}
|
||||
|
||||
return headers;
|
||||
}
|
||||
|
||||
function configureMethods(options) {
|
||||
var methods = options.methods;
|
||||
if (methods.join) {
|
||||
methods = options.methods.join(','); // .methods is an array, so turn it into a string
|
||||
}
|
||||
return {
|
||||
key: 'Access-Control-Allow-Methods',
|
||||
value: methods
|
||||
};
|
||||
}
|
||||
|
||||
function configureCredentials(options) {
|
||||
if (options.credentials === true) {
|
||||
return {
|
||||
key: 'Access-Control-Allow-Credentials',
|
||||
value: 'true'
|
||||
};
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
function configureAllowedHeaders(options, req) {
|
||||
var allowedHeaders = options.allowedHeaders || options.headers;
|
||||
var headers = [];
|
||||
|
||||
if (!allowedHeaders) {
|
||||
allowedHeaders = req.headers['access-control-request-headers']; // .headers wasn't specified, so reflect the request headers
|
||||
headers.push([{
|
||||
key: 'Vary',
|
||||
value: 'Access-Control-Request-Headers'
|
||||
}]);
|
||||
} else if (allowedHeaders.join) {
|
||||
allowedHeaders = allowedHeaders.join(','); // .headers is an array, so turn it into a string
|
||||
}
|
||||
if (allowedHeaders && allowedHeaders.length) {
|
||||
headers.push([{
|
||||
key: 'Access-Control-Allow-Headers',
|
||||
value: allowedHeaders
|
||||
}]);
|
||||
}
|
||||
|
||||
return headers;
|
||||
}
|
||||
|
||||
function configureExposedHeaders(options) {
|
||||
var headers = options.exposedHeaders;
|
||||
if (!headers) {
|
||||
return null;
|
||||
} else if (headers.join) {
|
||||
headers = headers.join(','); // .headers is an array, so turn it into a string
|
||||
}
|
||||
if (headers && headers.length) {
|
||||
return {
|
||||
key: 'Access-Control-Expose-Headers',
|
||||
value: headers
|
||||
};
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
function configureMaxAge(options) {
|
||||
var maxAge = (typeof options.maxAge === 'number' || options.maxAge) && options.maxAge.toString()
|
||||
if (maxAge && maxAge.length) {
|
||||
return {
|
||||
key: 'Access-Control-Max-Age',
|
||||
value: maxAge
|
||||
};
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
function applyHeaders(headers, res) {
|
||||
for (var i = 0, n = headers.length; i < n; i++) {
|
||||
var header = headers[i];
|
||||
if (header) {
|
||||
if (Array.isArray(header)) {
|
||||
applyHeaders(header, res);
|
||||
} else if (header.key === 'Vary' && header.value) {
|
||||
vary(res, header.value);
|
||||
} else if (header.value) {
|
||||
res.setHeader(header.key, header.value);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
function cors(options, req, res, next) {
|
||||
var headers = [],
|
||||
method = req.method && req.method.toUpperCase && req.method.toUpperCase();
|
||||
|
||||
if (method === 'OPTIONS') {
|
||||
// preflight
|
||||
headers.push(configureOrigin(options, req));
|
||||
headers.push(configureCredentials(options, req));
|
||||
headers.push(configureMethods(options, req));
|
||||
headers.push(configureAllowedHeaders(options, req));
|
||||
headers.push(configureMaxAge(options, req));
|
||||
headers.push(configureExposedHeaders(options, req));
|
||||
applyHeaders(headers, res);
|
||||
|
||||
if (options.preflightContinue) {
|
||||
next();
|
||||
} else {
|
||||
// Safari (and potentially other browsers) need content-length 0,
|
||||
// for 204 or they just hang waiting for a body
|
||||
res.statusCode = options.optionsSuccessStatus;
|
||||
res.setHeader('Content-Length', '0');
|
||||
res.end();
|
||||
}
|
||||
} else {
|
||||
// actual response
|
||||
headers.push(configureOrigin(options, req));
|
||||
headers.push(configureCredentials(options, req));
|
||||
headers.push(configureExposedHeaders(options, req));
|
||||
applyHeaders(headers, res);
|
||||
next();
|
||||
}
|
||||
}
|
||||
|
||||
function middlewareWrapper(o) {
|
||||
// if options are static (either via defaults or custom options passed in), wrap in a function
|
||||
var optionsCallback = null;
|
||||
if (typeof o === 'function') {
|
||||
optionsCallback = o;
|
||||
} else {
|
||||
optionsCallback = function (req, cb) {
|
||||
cb(null, o);
|
||||
};
|
||||
}
|
||||
|
||||
return function corsMiddleware(req, res, next) {
|
||||
optionsCallback(req, function (err, options) {
|
||||
if (err) {
|
||||
next(err);
|
||||
} else {
|
||||
var corsOptions = assign({}, defaults, options);
|
||||
var originCallback = null;
|
||||
if (corsOptions.origin && typeof corsOptions.origin === 'function') {
|
||||
originCallback = corsOptions.origin;
|
||||
} else if (corsOptions.origin) {
|
||||
originCallback = function (origin, cb) {
|
||||
cb(null, corsOptions.origin);
|
||||
};
|
||||
}
|
||||
|
||||
if (originCallback) {
|
||||
originCallback(req.headers.origin, function (err2, origin) {
|
||||
if (err2 || !origin) {
|
||||
next(err2);
|
||||
} else {
|
||||
corsOptions.origin = origin;
|
||||
cors(corsOptions, req, res, next);
|
||||
}
|
||||
});
|
||||
} else {
|
||||
next();
|
||||
}
|
||||
}
|
||||
});
|
||||
};
|
||||
}
|
||||
|
||||
// can pass either an options hash, an options delegate, or nothing
|
||||
module.exports = middlewareWrapper;
|
||||
|
||||
}());
|
||||
78
node_modules/cors/package.json
generated
vendored
Normal file
78
node_modules/cors/package.json
generated
vendored
Normal file
@@ -0,0 +1,78 @@
|
||||
{
|
||||
"_from": "cors",
|
||||
"_id": "cors@2.8.5",
|
||||
"_inBundle": false,
|
||||
"_integrity": "sha512-KIHbLJqu73RGr/hnbrO9uBeixNGuvSQjul/jdFvS/KFSIH1hWVd1ng7zOHx+YrEfInLG7q4n6GHQ9cDtxv/P6g==",
|
||||
"_location": "/cors",
|
||||
"_phantomChildren": {},
|
||||
"_requested": {
|
||||
"type": "tag",
|
||||
"registry": true,
|
||||
"raw": "cors",
|
||||
"name": "cors",
|
||||
"escapedName": "cors",
|
||||
"rawSpec": "",
|
||||
"saveSpec": null,
|
||||
"fetchSpec": "latest"
|
||||
},
|
||||
"_requiredBy": [
|
||||
"#USER",
|
||||
"/"
|
||||
],
|
||||
"_resolved": "https://registry.npmjs.org/cors/-/cors-2.8.5.tgz",
|
||||
"_shasum": "eac11da51592dd86b9f06f6e7ac293b3df875d29",
|
||||
"_spec": "cors",
|
||||
"_where": "D:\\WORK\\Menui\\menui_backend",
|
||||
"author": {
|
||||
"name": "Troy Goode",
|
||||
"email": "troygoode@gmail.com",
|
||||
"url": "https://github.com/troygoode/"
|
||||
},
|
||||
"bugs": {
|
||||
"url": "https://github.com/expressjs/cors/issues"
|
||||
},
|
||||
"bundleDependencies": false,
|
||||
"dependencies": {
|
||||
"object-assign": "^4",
|
||||
"vary": "^1"
|
||||
},
|
||||
"deprecated": false,
|
||||
"description": "Node.js CORS middleware",
|
||||
"devDependencies": {
|
||||
"after": "0.8.2",
|
||||
"eslint": "2.13.1",
|
||||
"express": "4.16.3",
|
||||
"mocha": "5.2.0",
|
||||
"nyc": "13.1.0",
|
||||
"supertest": "3.3.0"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">= 0.10"
|
||||
},
|
||||
"files": [
|
||||
"lib/index.js",
|
||||
"CONTRIBUTING.md",
|
||||
"HISTORY.md",
|
||||
"LICENSE",
|
||||
"README.md"
|
||||
],
|
||||
"homepage": "https://github.com/expressjs/cors#readme",
|
||||
"keywords": [
|
||||
"cors",
|
||||
"express",
|
||||
"connect",
|
||||
"middleware"
|
||||
],
|
||||
"license": "MIT",
|
||||
"main": "./lib/index.js",
|
||||
"name": "cors",
|
||||
"repository": {
|
||||
"type": "git",
|
||||
"url": "git+https://github.com/expressjs/cors.git"
|
||||
},
|
||||
"scripts": {
|
||||
"lint": "eslint lib test",
|
||||
"test": "npm run lint && nyc --reporter=html --reporter=text mocha --require test/support/env"
|
||||
},
|
||||
"version": "2.8.5"
|
||||
}
|
||||
23
node_modules/esm/LICENSE
generated
vendored
Normal file
23
node_modules/esm/LICENSE
generated
vendored
Normal file
@@ -0,0 +1,23 @@
|
||||
The MIT License (MIT)
|
||||
|
||||
Copyright esm contributors
|
||||
|
||||
Based on reify, copyright Ben Newman <https://github.com/benjamn/reify>
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
of this software and associated documentation files (the "Software"), to deal
|
||||
in the Software without restriction, including without limitation the rights
|
||||
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
copies of the Software, and to permit persons to whom the Software is
|
||||
furnished to do so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in all
|
||||
copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||
SOFTWARE.
|
||||
137
node_modules/esm/README.md
generated
vendored
Normal file
137
node_modules/esm/README.md
generated
vendored
Normal file
@@ -0,0 +1,137 @@
|
||||
# esm
|
||||
|
||||
The brilliantly simple, babel-less, bundle-less ECMAScript module loader.
|
||||
|
||||
> `esm` is the world’s most advanced ECMAScript module loader.
|
||||
This fast, production ready, zero dependency loader is all you need to support
|
||||
ECMAScript modules in Node 6+. See the release [post](https://medium.com/web-on-the-edge/tomorrows-es-modules-today-c53d29ac448c)
|
||||
and [video](https://www.youtube.com/watch?v=JcZ-FzfDq8A#t=5) for details!
|
||||
|
||||
Install
|
||||
---
|
||||
|
||||
* __New projects__
|
||||
|
||||
Run `npm init esm` or `yarn create esm`.
|
||||
|
||||
:bulb: Use the `-y` flag to answer “yes” to all prompts.
|
||||
|
||||
* __Existing projects__
|
||||
|
||||
Run `npm i esm` or `yarn add esm`.
|
||||
|
||||
Getting started
|
||||
---
|
||||
|
||||
There are two ways to enable `esm`.
|
||||
|
||||
1. Enable `esm` for packages:
|
||||
|
||||
Use `esm` to load the main ES module and export it as CommonJS.
|
||||
|
||||
__index.js__
|
||||
```js
|
||||
// Set options as a parameter, environment variable, or rc file.
|
||||
require = require("esm")(module/*, options*/)
|
||||
module.exports = require("./main.js")
|
||||
```
|
||||
__main.js__
|
||||
```js
|
||||
// ESM syntax is supported.
|
||||
export {}
|
||||
```
|
||||
:bulb: These files are automagically created with `npm init esm` or `yarn create esm`.
|
||||
|
||||
2. Enable `esm` for local runs:
|
||||
|
||||
```shell
|
||||
node -r esm main.js
|
||||
```
|
||||
:bulb: Omit the filename to enable `esm` in the REPL.
|
||||
|
||||
Features
|
||||
---
|
||||
|
||||
:clap: By default, :100: percent CJS interoperability is enabled so you can get stuff done.<br>
|
||||
:lock: `.mjs` files are limited to basic functionality without support for `esm` options.
|
||||
|
||||
Out of the box `esm` just works, no configuration necessary, and supports:
|
||||
|
||||
* Passing all applicable [test262](https://github.com/tc39/test262) compliance tests
|
||||
* [`import`](https://ponyfoo.com/articles/es6-modules-in-depth#import)/[`export`](https://ponyfoo.com/articles/es6-modules-in-depth#export)
|
||||
* [`import.meta`](https://github.com/tc39/proposal-import-meta)
|
||||
* [Dynamic `import`](https://github.com/tc39/proposal-dynamic-import)
|
||||
* [Live bindings](https://ponyfoo.com/articles/es6-modules-in-depth#bindings-not-values)
|
||||
* [File URI scheme](https://en.wikipedia.org/wiki/File_URI_scheme)
|
||||
* Node `stdin`, [`--eval`](https://nodejs.org/api/cli.html#cli_e_eval_script), [`--print`](https://nodejs.org/api/cli.html#cli_p_print_script) flags
|
||||
* Node [`--check`](https://nodejs.org/api/cli.html#cli_c_check) flag _(Node 10+)_
|
||||
|
||||
Options
|
||||
---
|
||||
|
||||
Specify options with one of the following:
|
||||
|
||||
* `"esm"` field in `package.json`
|
||||
* CJS/ESM in an `.esmrc.js`, `.esmrc.cjs`, or `.esmrc.mjs` file
|
||||
* [JSON6](https://github.com/d3x0r/json6) in an `.esmrc` or `.esmrc.json` file
|
||||
* JSON6 or file path in the `ESM_OPTIONS` environment variable
|
||||
* `ESM_DISABLE_CACHE` environment variable
|
||||
|
||||
<table><tr><td colspan=2><code>{</code><tr><td valign=top><code>"cjs":true</code><td><p>A boolean or object for toggling CJS features in ESM.<details><summary>Features</summary><table><tr><td colspan=2><code>{</code><tr><td valign=top><code>"cache":true</code><td><p>A boolean for storing ES modules in <code>require.cache</code>.<tr><td valign=top><code>"esModule":true</code><td><p>A boolean for <code>__esModule</code> interoperability.<tr><td valign=top><code>"extensions":true</code><td><p>A boolean for respecting <code>require.extensions</code> in ESM.<tr><td valign=top><code>"mutableNamespace":true</code><td><p>A boolean for mutable <a href=https://ponyfoo.com/articles/es6-modules-in-depth#import-all-the-things>namespace objects</a>.<tr><td valign=top><code>"namedExports":true</code><td><p>A boolean for <a href=https://ponyfoo.com/articles/es6-modules-in-depth#importing-named-exports>importing named exports</a> of CJS modules.<tr><td valign=top><code>"paths":true</code><td><p>A boolean for following CJS <a href=https://github.com/nodejs/node-eps/blob/master/002-es-modules.md#432-removal-of-non-local-dependencies>path rules</a> in ESM.<tr><td valign=top><code>"vars":true</code><td><p>A boolean for <code>__dirname</code>, <code>__filename</code>, and <code>require</code> in ESM.<tr><td valign=top><code>"dedefault":false</code><td><p>A boolean for requiring ES modules without the dangling <code>require().default</code>.<tr><td valign=top><code>"topLevelReturn":false</code><td><p>A boolean for top-level <code>return</code> support.<tr><td colspan=2><code>}</code></table></details><tr><td valign=top><code>"mainFields":["main"]</code><td><p>An array of fields checked when importing a package.<tr><td valign=top><code>"mode":"auto"</code><td><p>A string mode:<ul><li><code>"auto"</code> detect files with <code>import</code>, <code>import.meta</code>, <code>export</code>,<br><a href=https://github.com/tc39/proposal-modules-pragma><code>"use module"</code></a>, or <code>.mjs</code> as ESM.<li><code>"all"</code> files besides those with <code>"use script"</code> or <code>.cjs</code> are treated as ESM.<li><code>"strict"</code> to treat <strong>only</strong> <code>.mjs</code> files as ESM.</ul><tr><td valign=top><code>"await":false</code><td><p>A boolean for <a href=https://github.com/tc39/proposal-top-level-await>top-level <code>await</code></a> in modules without ESM exports. <em>(Node 10+)</em><tr><td valign=top><code>"force":false</code><td><p>A boolean to apply these options to all module loads.<tr><td valign=top><code>"wasm":false</code><td><p>A boolean for <a href=https://nodejs.org/api/globals.html#globals_webassembly>WebAssembly</a> module support. <em>(Node 8+)</em><tr><td colspan=2><code>}</code></table>
|
||||
|
||||
DevOpts
|
||||
---
|
||||
|
||||
<table><tr><td colspan=2><code>{</code><tr><td valign=top><code>"cache":true</code><td><p>A boolean for toggling cache creation or a cache directory path.<tr><td valign=top><code>"sourceMap":false</code><td><p>A boolean for including inline source maps.<tr><td colspan=2><code>}</code></table>
|
||||
|
||||
Tips
|
||||
---
|
||||
|
||||
### Bundling
|
||||
|
||||
* For bundlers like [`browserify`](http://browserify.org/)+[`esmify`](https://github.com/mattdesl/esmify),
|
||||
[`parcel-bundler`](https://parceljs.org/), and [`webpack`](https://webpack.js.org/)
|
||||
add a `"module"` field to `package.json` pointing to the main ES module.
|
||||
```json
|
||||
"main": "index.js",
|
||||
"module": "main.js"
|
||||
```
|
||||
|
||||
:bulb: This is automagically done with `npm init esm` or `yarn create esm`.
|
||||
|
||||
### Extensions
|
||||
|
||||
* Enable `esm` for [`wallaby.js`](https://wallabyjs.com/) following their
|
||||
[integration example](https://wallabyjs.com/docs/integration/node.html#es-modules).
|
||||
|
||||
### Loading
|
||||
|
||||
* Load `esm` before loaders/monitors like
|
||||
[`@babel/register`](https://babeljs.io/docs/en/next/babel-register.html),
|
||||
[`newrelic`](https://github.com/newrelic/node-newrelic),
|
||||
[`sqreen`](https://docs.sqreen.io/sqreen-for-nodejs/getting-started-2/), and
|
||||
[`ts-node`](https://github.com/TypeStrong/ts-node#programmatic).
|
||||
|
||||
* Load `esm` for [`jasmine`](https://jasmine.github.io/) using the
|
||||
[`"helpers"`](https://jasmine.github.io/setup/nodejs.html#configuration)
|
||||
field in `jasmine.json`:
|
||||
```json
|
||||
"helpers": [
|
||||
"node_modules/esm"
|
||||
]
|
||||
```
|
||||
|
||||
* Load `esm` with “node-args" options of:<br>
|
||||
- [`pm2`](https://pm2.io/doc/en/runtime/reference/pm2-cli/#pm2-flags): `--node-args="-r esm"`
|
||||
|
||||
* Load `esm` with “require” options of
|
||||
[`ava`](https://github.com/avajs/ava/blob/master/docs/recipes/es-modules.md),
|
||||
[`mocha`](https://mochajs.org/#-require-module-r-module),
|
||||
[`nodemon`](https://nodemon.io/),
|
||||
[`nyc`](https://github.com/istanbuljs/nyc#require-additional-modules),
|
||||
[`qunit`](https://github.com/qunitjs/qunit/releases/tag/2.6.0),
|
||||
[`tape`](https://github.com/substack/tape#preloading-modules), and
|
||||
[`webpack`](https://webpack.js.org/api/cli/#config-options).
|
||||
|
||||
:bulb: Builtin `require` cannot sideload `.mjs` files. However, `.js` files
|
||||
can be sideloaded or `.mjs` files may be loaded with dynamic `import`.
|
||||
1
node_modules/esm/esm.js
generated
vendored
Normal file
1
node_modules/esm/esm.js
generated
vendored
Normal file
@@ -0,0 +1 @@
|
||||
const e=(function(){return this||Function("return this")()})(),{apply:t,defineProperty:n}=Reflect,{freeze:r}=Object,{hasOwnProperty:l}=Object.prototype,o=Symbol.for,{type:i,versions:u}=process,{filename:a,id:s,parent:c}=module,_=x(u,"electron"),p=_&&"renderer"===i;let d="";"string"==typeof s&&s.startsWith("internal/")&&(d=q("internal/esm/loader"));const f=require("module"),{Script:m}=require("vm"),{createCachedData:y,runInNewContext:h,runInThisContext:b}=m.prototype,{sep:g}=require("path"),{readFileSync:v}=require("fs"),w=new f(s);function q(e){let t;try{const{internalBinding:n}=require("internal/bootstrap/loaders"),r=n("natives");x(r,e)&&(t=r[e])}catch(e){}return"string"==typeof t?t:""}function x(e,n){return null!=e&&t(l,e,[n])}function D(){return M(require,w,T),w.exports}function O(e,t){return D()(e,t)}function j(e,t){try{return v(e,t)}catch(e){}return null}let C,F;w.filename=a,w.parent=c;let I="",S="";""!==d?(S=d,F={__proto__:null,filename:"esm.js"}):(I=__dirname+g+"node_modules"+g+".cache"+g+"esm",C=j(I+g+".data.blob"),S=j(__dirname+g+"esm"+g+"loader.js","utf8"),null===C&&(C=void 0),null===S&&(S=""),F={__proto__:null,cachedData:C,filename:a,produceCachedData:"function"!=typeof y});const k=new m("const __global__ = this;(function (require, module, __shared__) { "+S+"\n});",F);let M,T;if(M=p?t(b,k,[{__proto__:null,filename:a}]):t(h,k,[{__proto__:null,global:e},{__proto__:null,filename:a}]),T=D(),""!==I){const{dir:e}=T.package;let t=e.get(I);if(void 0===t){let n=C;void 0===n&&(n=null),t={buffer:C,compile:new Map([["esm",{circular:0,code:null,codeWithTDZ:null,filename:null,firstAwaitOutsideFunction:null,firstReturnOutsideFunction:null,mtime:-1,scriptData:n,sourceType:1,transforms:0,yieldIndex:-1}]]),meta:new Map},e.set(I,t)}const{pendingScripts:n}=T;let r=n.get(I);void 0===r&&(r=new Map,n.set(I,r)),r.set("esm",k)}n(O,T.symbol.package,{__proto__:null,value:!0}),n(O,T.customInspectKey,{__proto__:null,value:()=>"esm enabled"}),n(O,o("esm:package"),{__proto__:null,value:!0}),r(O),module.exports=O;
|
||||
1
node_modules/esm/esm/loader.js
generated
vendored
Normal file
1
node_modules/esm/esm/loader.js
generated
vendored
Normal file
File diff suppressed because one or more lines are too long
1
node_modules/esm/index.js
generated
vendored
Normal file
1
node_modules/esm/index.js
generated
vendored
Normal file
@@ -0,0 +1 @@
|
||||
"use strict";module.exports=require("./esm.js");
|
||||
71
node_modules/esm/package.json
generated
vendored
Normal file
71
node_modules/esm/package.json
generated
vendored
Normal file
@@ -0,0 +1,71 @@
|
||||
{
|
||||
"_from": "esm",
|
||||
"_id": "esm@3.2.25",
|
||||
"_inBundle": false,
|
||||
"_integrity": "sha512-U1suiZ2oDVWv4zPO56S0NcR5QriEahGtdN2OR6FiOG4WJvcjBVFB0qI4+eKoWFH483PKGuLuu6V8Z4T5g63UVA==",
|
||||
"_location": "/esm",
|
||||
"_phantomChildren": {},
|
||||
"_requested": {
|
||||
"type": "tag",
|
||||
"registry": true,
|
||||
"raw": "esm",
|
||||
"name": "esm",
|
||||
"escapedName": "esm",
|
||||
"rawSpec": "",
|
||||
"saveSpec": null,
|
||||
"fetchSpec": "latest"
|
||||
},
|
||||
"_requiredBy": [
|
||||
"#USER",
|
||||
"/"
|
||||
],
|
||||
"_resolved": "https://registry.npmjs.org/esm/-/esm-3.2.25.tgz",
|
||||
"_shasum": "342c18c29d56157688ba5ce31f8431fbb795cc10",
|
||||
"_spec": "esm",
|
||||
"_where": "D:\\WORK\\Menui\\menui_backend",
|
||||
"author": {
|
||||
"name": "John-David Dalton",
|
||||
"email": "john.david.dalton@gmail.com"
|
||||
},
|
||||
"bugs": {
|
||||
"url": "https://github.com/standard-things/esm/issues"
|
||||
},
|
||||
"bundleDependencies": false,
|
||||
"deprecated": false,
|
||||
"description": "Tomorrow's ECMAScript modules today!",
|
||||
"engines": {
|
||||
"node": ">=6"
|
||||
},
|
||||
"files": [
|
||||
"index.js",
|
||||
"esm.js",
|
||||
"esm/loader.js"
|
||||
],
|
||||
"homepage": "https://github.com/standard-things/esm#readme",
|
||||
"husky": {
|
||||
"hooks": {
|
||||
"precommit": "npm run lint"
|
||||
}
|
||||
},
|
||||
"keywords": [
|
||||
"commonjs",
|
||||
"ecmascript",
|
||||
"export",
|
||||
"import",
|
||||
"modules",
|
||||
"node",
|
||||
"require"
|
||||
],
|
||||
"license": "MIT",
|
||||
"main": "esm.js",
|
||||
"name": "esm",
|
||||
"repository": {
|
||||
"type": "git",
|
||||
"url": "git+https://github.com/standard-things/esm.git"
|
||||
},
|
||||
"runkitExample": "require = require(\"esm\")(module)\nrequire(\"lodash-es\")",
|
||||
"scripts": {
|
||||
"test": "echo \"Error: no test specified\" && exit 1"
|
||||
},
|
||||
"version": "3.2.25"
|
||||
}
|
||||
14
package-lock.json
generated
14
package-lock.json
generated
@@ -531,6 +531,15 @@
|
||||
"resolved": "https://registry.npmjs.org/core-util-is/-/core-util-is-1.0.2.tgz",
|
||||
"integrity": "sha1-tf1UIgqivFq1eqtxQMlAdUUDwac="
|
||||
},
|
||||
"cors": {
|
||||
"version": "2.8.5",
|
||||
"resolved": "https://registry.npmjs.org/cors/-/cors-2.8.5.tgz",
|
||||
"integrity": "sha512-KIHbLJqu73RGr/hnbrO9uBeixNGuvSQjul/jdFvS/KFSIH1hWVd1ng7zOHx+YrEfInLG7q4n6GHQ9cDtxv/P6g==",
|
||||
"requires": {
|
||||
"object-assign": "^4",
|
||||
"vary": "^1"
|
||||
}
|
||||
},
|
||||
"crypto-random-string": {
|
||||
"version": "2.0.0",
|
||||
"resolved": "https://registry.npmjs.org/crypto-random-string/-/crypto-random-string-2.0.0.tgz",
|
||||
@@ -703,6 +712,11 @@
|
||||
"resolved": "https://registry.npmjs.org/escape-html/-/escape-html-1.0.3.tgz",
|
||||
"integrity": "sha1-Aljq5NPQwJdN4cFpGI7wBR0dGYg="
|
||||
},
|
||||
"esm": {
|
||||
"version": "3.2.25",
|
||||
"resolved": "https://registry.npmjs.org/esm/-/esm-3.2.25.tgz",
|
||||
"integrity": "sha512-U1suiZ2oDVWv4zPO56S0NcR5QriEahGtdN2OR6FiOG4WJvcjBVFB0qI4+eKoWFH483PKGuLuu6V8Z4T5g63UVA=="
|
||||
},
|
||||
"etag": {
|
||||
"version": "1.8.1",
|
||||
"resolved": "https://registry.npmjs.org/etag/-/etag-1.8.1.tgz",
|
||||
|
||||
@@ -7,13 +7,16 @@
|
||||
"test": "echo \"Error: no test specified\" && exit 1"
|
||||
},
|
||||
"keywords": [],
|
||||
"type": "module",
|
||||
"author": "Jonasz Bigda",
|
||||
"license": "ISC",
|
||||
"dependencies": {
|
||||
"@material-ui/core": "^4.11.0",
|
||||
"bcrypt": "^5.0.0",
|
||||
"body-parser": "^1.19.0",
|
||||
"cors": "^2.8.5",
|
||||
"dotenv": "^8.2.0",
|
||||
"esm": "^3.2.25",
|
||||
"express": "^4.17.1",
|
||||
"express-rate-limit": "^5.1.3",
|
||||
"gitignore": "^0.6.0",
|
||||
|
||||
14
routes/routeCity.js
Normal file
14
routes/routeCity.js
Normal file
@@ -0,0 +1,14 @@
|
||||
import express from "express";
|
||||
import Restaurant from "../models/restaurant.js";
|
||||
|
||||
var router = express.Router();
|
||||
|
||||
router.get("/", (req, res) => {
|
||||
Restaurant.find({ city: req.body.city }, (err, data) => {
|
||||
if (err) {
|
||||
res.sendStatus(404);
|
||||
} else res.send(data);
|
||||
});
|
||||
});
|
||||
|
||||
export default router;
|
||||
119
routes/routeDish.js
Normal file
119
routes/routeDish.js
Normal file
@@ -0,0 +1,119 @@
|
||||
import express from "express";
|
||||
import Restaurant from "../models/restaurant.js";
|
||||
import Dish from "../models/dish.js";
|
||||
import sanitizer from "string-sanitizer";
|
||||
|
||||
var router = express.Router();
|
||||
|
||||
router.get("/", (req, res) => {
|
||||
Dish.findById(req.body.dishId, (err, data) => {
|
||||
if (err) {
|
||||
res.sendStatus(404);
|
||||
} else res.send(data);
|
||||
});
|
||||
});
|
||||
|
||||
router.post("/", (req, res) => {
|
||||
//validate restaurant
|
||||
validators.validateRestaurant(req.body.restaurantId, (result) => {
|
||||
if (!result) res.sendStatus(400);
|
||||
else {
|
||||
//validate user
|
||||
validators.validateUser(req.body.userId, (result) => {
|
||||
if (!result) {
|
||||
res.sendStatus(401);
|
||||
} else {
|
||||
//construct dish
|
||||
const dish = new Dish({
|
||||
_id: new mongoose.Types.ObjectId(),
|
||||
name: sanitizer.sanitize.keepUnicode(req.body.dish.name),
|
||||
category: req.body.dish.category,
|
||||
price: req.body.dish.price,
|
||||
notes: sanitizer.sanitize.keepUnicode(req.body.dish.notes),
|
||||
imgUrl: req.body.dish.imgUrl,
|
||||
weight: req.body.dish.weight,
|
||||
allergens: {
|
||||
gluten: req.body.dish.allergens.gluten,
|
||||
lactose: req.body.dish.allergens.lactose,
|
||||
soy: req.body.dish.allergens.soy,
|
||||
eggs: req.body.dish.allergens.eggs,
|
||||
seaFood: req.body.dish.allergens.seaFood,
|
||||
peanuts: req.body.dish.allergens.peanuts,
|
||||
sesame: req.body.dish.allergens.sesame,
|
||||
},
|
||||
vegan: req.body.dish.vegan,
|
||||
vegetarian: req.body.dish.vegetarian,
|
||||
});
|
||||
//add dish to DB
|
||||
dish.save((err) => {
|
||||
if (err) {
|
||||
res.sendStatus(400);
|
||||
} else {
|
||||
//add dish ID to restaurant
|
||||
Restaurant.updateOne(
|
||||
{ _id: req.body.restaurantId },
|
||||
{ $push: { dishes: dish._id } },
|
||||
(err) => {
|
||||
if (err) {
|
||||
res.sendStatus(400);
|
||||
} else {
|
||||
res.sendStatus(201);
|
||||
}
|
||||
}
|
||||
);
|
||||
}
|
||||
});
|
||||
}
|
||||
});
|
||||
}
|
||||
});
|
||||
});
|
||||
|
||||
router.put("/", (req, res) => {
|
||||
//validate dish ID
|
||||
validators.validateDishId(req.body.dishId, (result) => {
|
||||
if (!result) {
|
||||
res.sendStatus(204);
|
||||
} else {
|
||||
//validate user
|
||||
validators.validateUser(req.body.userId, (result) => {
|
||||
if (!result) {
|
||||
res.sendStatus(401);
|
||||
} else {
|
||||
//replace dish in DB
|
||||
Dish.replaceOne(
|
||||
{ _id: req.body.dishId },
|
||||
{
|
||||
name: sanitizer.sanitize.keepUnicode(req.body.dish.name),
|
||||
category: req.body.dish.category,
|
||||
price: req.body.dish.price,
|
||||
notes: sanitizer.sanitize.keepUnicode(req.body.dish.notes),
|
||||
imgUrl: req.body.dish.imgUrl,
|
||||
weight: req.body.dish.weight,
|
||||
allergens: {
|
||||
gluten: req.body.dish.allergens.gluten,
|
||||
lactose: req.body.dish.allergens.lactose,
|
||||
soy: req.body.dish.allergens.soy,
|
||||
eggs: req.body.dish.allergens.eggs,
|
||||
seaFood: req.body.dish.allergens.seaFood,
|
||||
peanuts: req.body.dish.allergens.peanuts,
|
||||
sesame: req.body.dish.allergens.sesame,
|
||||
},
|
||||
vegan: req.body.dish.vegan,
|
||||
vegetarian: req.body.dish.vegetarian,
|
||||
},
|
||||
(err) => {
|
||||
if (err) {
|
||||
res.sendStatus(304);
|
||||
} else {
|
||||
res.sendStatus(200);
|
||||
}
|
||||
}
|
||||
);
|
||||
}
|
||||
});
|
||||
}
|
||||
});
|
||||
});
|
||||
|
||||
export default router;
|
||||
35
routes/routeImg.js
Normal file
35
routes/routeImg.js
Normal file
@@ -0,0 +1,35 @@
|
||||
import express from "express";
|
||||
import multer from "multer";
|
||||
var router = express.Router();
|
||||
var storage = multer.diskStorage({
|
||||
destination: function (req, file, cb) {
|
||||
cb(null, "./images");
|
||||
},
|
||||
filename: function (req, file, cb) {
|
||||
cb(
|
||||
null,
|
||||
new Date() //Date.now().toString
|
||||
.toISOString()
|
||||
.trim()
|
||||
.replace(/[:_ -.]/g, "") +
|
||||
Math.floor(Math.random() * 5000 + 1) +
|
||||
file.mimetype.replace("/", ".")
|
||||
);
|
||||
},
|
||||
});
|
||||
const upload = multer({
|
||||
storage: storage,
|
||||
fileFilter: function (req, file, cb) {
|
||||
if (file.mimetype !== "image/jpg") {
|
||||
return cb(null, false);
|
||||
}
|
||||
cb(null, true);
|
||||
},
|
||||
limits: { fileSize: 4000000 },
|
||||
}); //max file size = 4Mb
|
||||
|
||||
router.post("/", upload.single("menuiImage"), (req, res) => {
|
||||
res.sendStatus(201);
|
||||
});
|
||||
|
||||
export default router;
|
||||
76
routes/routeRestaurant.js
Normal file
76
routes/routeRestaurant.js
Normal file
@@ -0,0 +1,76 @@
|
||||
import express from "express";
|
||||
import * as validators from "../services/validation.js";
|
||||
import Restaurant from "../models/restaurant.js";
|
||||
import Dish from "../models/dish.js";
|
||||
import User from "../models/users.js";
|
||||
import sanitizer from "string-sanitizer";
|
||||
|
||||
var router = express.Router();
|
||||
|
||||
router.get("/", (req, res) => {
|
||||
validators.validateRestaurant(req.body.restaurantId, (result) => {
|
||||
if (!result) {
|
||||
res.sendStatus(400);
|
||||
} else {
|
||||
Restaurant.findById(req.body.restaurantId, (err, data) => {
|
||||
if (err) {
|
||||
res.sendStatus(404);
|
||||
} else res.send(data);
|
||||
});
|
||||
}
|
||||
});
|
||||
});
|
||||
|
||||
router.post("/", (req, res) => {
|
||||
//validate user
|
||||
validators.validateUser(req.body.userId, (result) => {
|
||||
if (!result) res.sendStatus(401);
|
||||
//create restaurant
|
||||
const restaurant = new Restaurant({
|
||||
_id: new mongoose.Types.ObjectId(),
|
||||
name: sanitizer.sanitize.keepUnicode(req.body.name),
|
||||
city: sanitizer.sanitize.keepUnicode(req.body.city),
|
||||
imgUrl: req.body.imgUrl,
|
||||
workingHours: req.body.workingHours,
|
||||
hidden: req.body.hidden,
|
||||
});
|
||||
//add restaurant to DB
|
||||
restaurant.save((err) => {
|
||||
if (err) {
|
||||
res.sendStatus(400);
|
||||
} else {
|
||||
res.status(201);
|
||||
}
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
router.get("/dishes", (req, res) => {
|
||||
//validate restaurant
|
||||
validators.validateRestaurant(req.body.restaurantId, (result) => {
|
||||
if (!result) {
|
||||
res.sendStatus(400);
|
||||
} else {
|
||||
//get restaurant
|
||||
Restaurant.findById(req.body.restaurantId, (err, result) => {
|
||||
if (err) {
|
||||
res.sendStatus(404);
|
||||
} else {
|
||||
//prepare variables
|
||||
const dishesCount = result.dishes.length;
|
||||
let dishes = [];
|
||||
//fetch all dishes
|
||||
result.dishes.forEach((element) => {
|
||||
Dish.findById(element, (err, result) => {
|
||||
if (err) console.log("ERROR fetching dish");
|
||||
dishes.push(result);
|
||||
if (dishes.length == dishesCount) res.send(dishes);
|
||||
});
|
||||
});
|
||||
}
|
||||
});
|
||||
}
|
||||
});
|
||||
});
|
||||
|
||||
export default router;
|
||||
@@ -1,9 +1,9 @@
|
||||
const Restaurant = require("./models/restaurant");
|
||||
const Dish = require("./models/dish");
|
||||
const User = require("./models/users");
|
||||
const mongoose = require("mongoose");
|
||||
import Restaurant from "../models/restaurant.js";
|
||||
import Dish from "../models/dish.js";
|
||||
import User from "../models/users.js";
|
||||
import mongoose from "mongoose";
|
||||
|
||||
function validateRestaurant(id, callback) {
|
||||
export function validateRestaurant(id, callback) {
|
||||
if (mongoose.Types.ObjectId.isValid(id)) {
|
||||
Restaurant.exists({ _id: id }, (err, res) => {
|
||||
if (err) {
|
||||
@@ -15,11 +15,11 @@ function validateRestaurant(id, callback) {
|
||||
} else callback(false);
|
||||
}
|
||||
|
||||
function validateUser(id, callback) {
|
||||
export function validateUser(id, callback) {
|
||||
callback(true);
|
||||
}
|
||||
|
||||
function validateDishId(id, callback) {
|
||||
export function validateDishId(id, callback) {
|
||||
if (mongoose.Types.ObjectId.isValid(id)) {
|
||||
Dish.exists({ _id: id }, (err, res) => {
|
||||
if (err) {
|
||||
@@ -30,7 +30,3 @@ function validateDishId(id, callback) {
|
||||
});
|
||||
} else callback(false);
|
||||
}
|
||||
|
||||
exports.validateRestaurant = validateRestaurant;
|
||||
exports.validateUser = validateUser;
|
||||
exports.validateDishId = validateDishId;
|
||||
Reference in New Issue
Block a user