Node.js + Express + Angular + MongoDB堆栈

The MEAN (MongoDB, Express, Angular, Node.js) stack is a popular one. It represents the opportunity to work with JavaScript on both sides of the application (Backend & Frontend).

MEAN(MongoDB,Express,Angular,Node.js)堆栈是一种流行的堆栈。 它代表了在应用程序的两侧(后端和前端)使用JavaScript的机会。

During this lecture I’ll show you how to add a MongoDB database to the project created previously (Node.js + Express + Angular stack).

在本讲座中,我将向您展示如何向以前创建的项目( Node.js + Express + Angular stack )中添加MongoDB数据库。

Image for post
MEAN stack
平均堆栈

1.一些定义: (1. Some definitions:)

MongoDB: is a cross-platform document-oriented database. Defined as a NoSQL and uses JSON-like documents with optional schemas.

MongoDB 是一个跨平台的面向文档的数据库。 定义为NoSQL,并使用具有可选模式的类似JSON的文档。

Image for post
That’s clear !
很清楚!

Anyway the MongoBD definition, the functionalities and why you should use it rather than other databases are not the purpose of this lecture (maybe another time, or never 🙄).

无论如何,MongoBD的定义,功能以及为什么要使用它而不是其他数据库都不是本讲座的目的(也许是另一回事,或从不🙄)。

2.将MongoDB添加到我们的堆栈中: (2. Adding MongoDB to our stack:)

Let’s take a look to our server file from the previous lecture:

让我们来看看上一堂课的服务器文件:

// Use Express
var express = require("express");
// Use body-parser
var bodyParser = require("body-parser");


// Create new instance of the express server
var app = express();


// Define the JSON parser as a default way 
// to consume and produce data through the 
// exposed APIs
app.use(bodyParser.json());


// Create link to Angular build directory
// The `ng build` command will save the result
// under the `dist` folder.
var distDir = __dirname + "/dist/";
app.use(express.static(distDir));


// Init the server
var server = app.listen(process.env.PORT || 8080, function () {
    var port = server.address().port;
    console.log("App now running on port", port);
});


/*  "/api/status"
 *   GET: Get server status
 *   PS: it's just an example, not mandatory
 */
app.get("/api/status", function (req, res) {
    res.status(200).json({ status: "UP" });
});

This server provides only one REST service /api/status returning a static value "UP”.

该服务器仅提供一个REST服务/api/status返回静态值"UP”

The idea will be to manage resource(s) using the CRUD (Create, Read, Update and Delete) functions of the persistence strategy.

这个想法将使用CRUD(C reate,R EAD,U PDATE和d elete)的持久性策略的函数来管理资源(多个)。

To add MongoDB to our server:

要将MongoDB添加到我们的服务器:

The following server.js file version contains the MongoDB connection:

下面的server.js 文件版本包含MongoDB连接:

// Use Express
var express = require("express");
// Use body-parser
var bodyParser = require("body-parser");
// Use MongoDB
var mongodb = require("mongodb");
var ObjectID = mongodb.ObjectID;
// The database variable
var database;
// The products collection
var PRODUCTS_COLLECTION = "products";


// Create new instance of the express server
var app = express();


// Define the JSON parser as a default way 
// to consume and produce data through the 
// exposed APIs
app.use(bodyParser.json());


// Create link to Angular build directory
// The `ng build` command will save the result
// under the `dist` folder.
var distDir = __dirname + "/dist/";
app.use(express.static(distDir));
// Local database URI.
const LOCAL_DATABASE = "mongodb://localhost:27017/app";
// Local port.
const LOCAL_PORT = 8080;


// Init the server
mongodb.MongoClient.connect(process.env.MONGODB_URI || LOCAL_DATABASE,
    {
        useUnifiedTopology: true,
        useNewUrlParser: true,
    }, function (error, client) {


        // Check if there are any problems with the connection to MongoDB database.
        if (error) {
            console.log(error);
            process.exit(1);
        }


        // Save database object from the callback for reuse.
        database = client.db();
        console.log("Database connection done.");


        // Initialize the app.
        var server = app.listen(process.env.PORT || LOCAL_PORT, function () {
            var port = server.address().port;
            console.log("App now running on port", port);
        });
    });


/*  "/api/status"
 *   GET: Get server status
 *   PS: it's just an example, not mandatory
 */
app.get("/api/status", function (req, res) {
    res.status(200).json({ status: "UP" });
});


// Errors handler.
function manageError(res, reason, message, code) {
    console.log("Error: " + reason);
    res.status(code || 500).json({ "error": message });
}

The code is commented (don’t hesitate to tell me if I missed some information) but let’s take a look to some key points:

该代码已注释(如果我错过了一些信息,请不要犹豫告诉我),但让我们看一下一些关键点:

  • We use the new dependency integrated withvar mongodb = require("mongodb");

    我们使用与var mongodb = require("mongodb");集成在一起的新依赖项var mongodb = require("mongodb");

  • We will use the ObjectID object managing identifiers for our objects (represents a concatenation of 4-byte timestamp value + 5-byte random value + 3-byte incrementing counter, initialized to a random value) with var ObjectID = mongodb.ObjectID;

    我们将为对象使用ObjectID对象管理标识符(表示4字节时间戳值+ 5字节随机值+ 3字节递增计数器的串联,初始化为随机值),其中var ObjectID = mongodb.ObjectID;

  • We will manage some products during this lecture, so the idea with var PRODUCTS_COLLECTION = “products”; is just preparing a collection to store them

    在本讲座中,我们将管理一些产品,因此var PRODUCTS_COLLECTION = “products”; 只是准备一个收集来存储它们

Image for post
Smart !
聪明 !
  • Locally, the MongoDB database is running on port and URI represented with the two values LOCAL_PORT and LOCAL_DATABASE

    在本地,MongoDB数据库在端口和URI上运行,并用两个值LOCAL_PORTLOCAL_DATABASE

  • Then we save the database object from the callback and starts the server

    然后我们从回调中保存数据库对象并启动服务器

3.使用数据库: (3. Use the database:)

As I said, we will manage some products. Each product contains three mandatory values {_id: string, name: string, brand: string}.

正如我所说,我们将管理一些产品。 每个产品均包含三个必填值{_id: string, name: string, brand: string}.

To do that, we need to create new REST services:

为此,我们需要创建新的REST服务:

  • /api/products with the GET verb to get all products.

    /api/products 使用GET动词获取所有产品。

  • /api/products with the POST verb to create a product.

    /api/products POST动词创建产品。

  • /api/products/:id with the DELETE verb to delete a product using the identifier.

    /api/products/:id DELETE动词一起使用标识符来删除产品。

// Use Express
var express = require("express");
// Use body-parser
var bodyParser = require("body-parser");
// Use MongoDB
var mongodb = require("mongodb");
var ObjectID = mongodb.ObjectID;
// The database variable
var database;
// The products collection
var PRODUCTS_COLLECTION = "products";


// Create new instance of the express server
var app = express();


// Define the JSON parser as a default way 
// to consume and produce data through the 
// exposed APIs
app.use(bodyParser.json());


// Create link to Angular build directory
// The `ng build` command will save the result
// under the `dist` folder.
var distDir = __dirname + "/dist/";
app.use(express.static(distDir));
// Local database URI.
const LOCAL_DATABASE = "mongodb://localhost:27017/app";
// Local port.
const LOCAL_PORT = 8080;


// Init the server
mongodb.MongoClient.connect(process.env.MONGODB_URI || LOCAL_DATABASE,
    {
        useUnifiedTopology: true,
        useNewUrlParser: true,
    }, function (error, client) {


        // Check if there are any problems with the connection to MongoDB database.
        if (error) {
            console.log(error);
            process.exit(1);
        }


        // Save database object from the callback for reuse.
        database = client.db();
        console.log("Database connection done.");


        // Initialize the app.
        var server = app.listen(process.env.PORT || LOCAL_PORT, function () {
            var port = server.address().port;
            console.log("App now running on port", port);
        });
    });


/*  "/api/status"
 *   GET: Get server status
 *   PS: it's just an example, not mandatory
 */
app.get("/api/status", function (req, res) {
    res.status(200).json({ status: "UP" });
});


/*  "/api/products"
 *  GET: finds all products
 */
app.get("/api/products", function (req, res) {
    database.collection(PRODUCTS_COLLECTION).find({}).toArray(function (error, data) {
        if (error) {
            manageError(res, err.message, "Failed to get contacts.");
        } else {
            res.status(200).json(data);
        }
    });
});


/*  "/api/products"
 *   POST: creates a new product
 */
app.post("/api/products", function (req, res) {
    var product = req.body;


    if (!product.name) {
        manageError(res, "Invalid product input", "Name is mandatory.", 400);
    } else if (!product.brand) {
        manageError(res, "Invalid product input", "Brand is mandatory.", 400);
    } else {
        database.collection(PRODUCTS_COLLECTION).insertOne(product, function (err, doc) {
            if (err) {
                manageError(res, err.message, "Failed to create new product.");
            } else {
                res.status(201).json(doc.ops[0]);
            }
        });
    }
});


/*  "/api/products/:id"
 *   DELETE: deletes product by id
 */
app.delete("/api/products/:id", function (req, res) {
    if (req.params.id.length > 24 || req.params.id.length < 24) {
        manageError(res, "Invalid product id", "ID must be a single String of 12 bytes or a string of 24 hex characters.", 400);
    } else {
        database.collection(PRODUCTS_COLLECTION).deleteOne({ _id: new ObjectID(req.params.id) }, function (err, result) {
            if (err) {
                manageError(res, err.message, "Failed to delete product.");
            } else {
                res.status(200).json(req.params.id);
            }
        });
    }
});


// Errors handler.
function manageError(res, reason, message, code) {
    console.log("Error: " + reason);
    res.status(code || 500).json({ "error": message });
}

More information about how to make MongoDB queries here.

有关如何进行MongoDB查询的更多信息,请参见此处

Using Postman (or your favorite tool), try to send requests to test the created endpoints:

使用邮递员 (或您喜欢的工具),请尝试发送请求以测试创建的端点:

⚠️ MongoDB database must be running locally and to start your Express server use thenpm start command.

⚠️ 的MongoDB数据库必须在本地运行,并启动Express服务器使用npm start 命令。

  1. Create a product

    创建一个产品

Image for post
Create a product
创建一个产品

In the same time you can check your products collection inside the MongoDB database (I’m using Robot 3T for that):

同时,您可以在MongoDB数据库中检查产品集合(我正在使用Robot 3T ):

Image for post
Products collection
产品集合

2. Get all products

2.获取所有产品

Image for post
Get all products
获取所有产品

3. Delete a product

3.删除产品

Image for post
Delete a product
删除产品

奖金: (Bonus:)

Inside the GitHub repository, You will find a simple Angular screen using a service developed to manage the created endpoints:

在GitHub存储库中,您将找到一个简单的Angular屏幕,其中使用开发用于管理创建的端点的服务:

import { Injectable } from '@angular/core';
import { Http } from '@angular/http';
import { IProduct, Product } from './product.model';


@Injectable({
    providedIn: 'root'
})
export class ProductService {
    private productsUrl = '/api/products';


    constructor(private http: Http) { }


    // Get products
    get(): Promise<Array<IProduct>> {
        return this.http.get(this.productsUrl)
            .toPromise()
            .then(response => response.json())
            .catch(this.error);
    }


    // Create product
    create(product: Product): Promise<IProduct> {
        return this.http.post(this.productsUrl, product)
            .toPromise()
            .then(response => response.json())
            .catch(this.error);
    }


    // Delete a product
    delete(id: string): Promise<any> {
        return this.http.delete(`${this.productsUrl}/${id}`)
            .toPromise()
            .then(response => response.json())
            .catch(this.error);
    }


    // Error handling
    private error(error: any) {
        let message = (error.message) ? error.message :
            error.status ? `${error.status} - ${error.statusText}` : 'Server error';
        console.error(message);
    }
}

⚠️ To run the Angular app use the following command and check the http://localhost:4200 URL:

To️要运行Angular应用程序,请使用以下命令并检查http://localhost:4200 网址:

ng serve --proxy-config proxy.config.json
Image for post
Result !
结果!

翻译自: https://medium.com/swlh/node-js-express-angular-mongodb-stack-3dcc5087b6d4

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值