当前位置:网站首页>[node middle layer practice (IV)] ---- logical processing of express middle layer

[node middle layer practice (IV)] ---- logical processing of express middle layer

2022-07-23 09:56:00 Lily

Preface :
     This article is about learning Node Notes on the practice of the middle tier , It is recommended that you can read Keyon Y The original text of the big man Node Middle tier practice . Before starting this article , You can also read the following first ,Node Middle tier practice ( One )—— be based on NodeJS Full plank development , It is helpful to understand the content of this article .(PS: Continue to pay debts node The small white ╮(╯▽╰)╭)
    express The logical processing of is divided into two parts : Forwarding back-end interface and middleware .

One 、 Forwarding back-end interface

The interfaces provided by the backend are divided into two categories :

  • The data interface used for rendering pages ;
  • The front-end part sends ajax Request interface of the request

Data interface

Namely url Links to pages that can be accessed .
First use router.get() Registered routing , First pass in route axios Access the backend to get page data response, adopt res.render() Return a custom object , take response Passed as an attribute of an object to pug In the template page , stay pug You can use it freely in the page response .
config/routes/default.js file :

//  home page 
router.get('/', addUser, (req, res, next) => {
    
	axios.all([
		axios.get('/Api/Carous'),
		axios.get('/Api/Cars/Top10', {
    params: {
    page: req.query.page || 1}}),
	])
		.then(axios.spread(function (res1, res2){
    
			config.throwError(next, res1, res2);
			var page = req.query.page || 1;
			res.render('Default/index', {
    
				title: config.title(' home page '),
				keywords: config.keywords,
				description: config.description,
				menuNav: 0,
				carList: res1.data.Data,
				top10: res2.data.Data.slice((page-1)*3,page*3)
			});
		})).catch(e => {
    
		config.renderError(req, res, e);
	})
});

Request interface

Is sent by the front end ajax Requested interface .
The difference with data interface is , The middle tier only does two things :

  • Use axios, Forward the request from the front end to the back end ;
  • Use res.send(), The response forwarded to the back end is sent to the front end .
// get request 
router.get('/User/Role', (req, res, next) => {
    
    axios.get(config.origin + '/Api/User/Role', config.axiosHeaders(req, {
    
        params: {
    role: req.query.role}
    }))
        .then(res1 => {
    
            res.send(res1.data);
        }).catch(e => {
    
            config.sendError(res, e);
    })
})

// post request 
router.post('/User/SendRequest', (req, res, next) => {
    
	axios.post(config.origin + '/Api/User/SendRequest', {
    
		userID: req.body.userID || null,
		requestID: JSON.parse(req.body.requestID) || null
	}, config.axiosHeaders(req))
		.then((res2) => {
    
			res.send(res2.data);
		}).catch((e) => {
    
		config.sendError(res, e);
	})
});

post The request cannot read the request body directly , Need to install body-parser rely on

npm i –save body-parser

And in app.js Mount this dependency

app.use(bodyParser.urlencoded({
    extended: false}));

Get the parameters in the front-end request

There are three situations :

  • Get the parameters in the route with parameters
router.get('/Cars/:id', (req, res, next) => {
    
    axios.get(config.origin + '/Api/Cars', {
    
        params: {
    role: req.params.id}  // req.params.id obtain url Parameters in 
    }))
    ...
})

  • obtain get Requested parameters
//  For example, such a request  /Cars/Search?q=tobi
router.get('/Cars/Search', (req, res, next) => {
    
    axios.get(config.origin + '/Api/Cars/Search', {
    
        params: {
    car: req.query.q}  // req.query.q To obtain parameters 
    }))
    ...
})

  • obtain post Requested parameters
router.post('/Cars/Search', (req, res, next) => {
    
    axios.post(config.origin + '/Api/Cars/Search', {
    
        car: req.body.name  // req.body.name Get the parameters in the request body 
    }))
    ...
})

  • post Request to forward array objects
    express post request , When getting an array in the client request , If it's direct post An array , be express Cannot get array , You need to serialize the array on the client , Deserialize in the middle tier :
//  client 
$.ajax({
    
	url: '/Api/Mas/SendInfo',
	type: 'POST',
	data: {
    userID: userId, requestID: JSON.stringify(selected)},  //  serialize 
	success: function (res) {
    
		log(res);
		if(res.Status == 0){
    
			$thisModal.hide();
			$('#modal_cds').show();
		}
	}
})
		
//  Middle layer 
axios.post(config.origin + '/Api/Mas/SendInfo', {
    
	userID: req.body.userID || null,
	requestID: JSON.parse(req.body.requestID) || null    //  Deserialization 
}, config.axiosHeaders(req))

Two 、 middleware

The middle tier should not pass attributes that may not exist

Never pass something that may not exist in the middle layer property!
Never pass something that may not exist in the middle layer property!
Never pass something that may not exist in the middle layer property!
Important things are to be repeated for 3 times , Otherwise, the following bug I don't know where to find .

(node:20352) UnhandledPromiseRejectionWarning: Unhandled promise rejection (rejection id: 1): TypeError: Cannot read property ‘data’ of undefined

middleware

Express It's a self function minimalism , It is completely composed of routing and middleware web Development framework : essentially , One Express Applications are just calling various middleware .
middleware (Middleware) It's a function , It can access the request object (request object (req)), The response object (response object (res)), and web Application in request – Middleware in the response loop process , It's generally named next The variable of .
Function code of middleware :

  • Execute any code ;
  • Modify request and response objects ;
  • End request – Response loop ;
  • Call the next Middleware in the stack .
    If the current middleware does not terminate the request – Response loop , Must call next() Method to give control to the next middleware , Otherwise the request will hang .
    Express The application can use the following Middleware :
  • Application level middleware
  • Routing level middleware
  • Error handling middleware
  • Built in middleware
  • Third-party middleware
    Use the optional mount path , Middleware can be loaded at the application level or routing level . in addition , You can also load a series of middleware functions at the same time , This creates a sub middleware stack on a mount point .

Use routing level middleware to handle request object

var addUser = require('../../middleware/addUser');
    ...
router.get('/Car/List', addUser, (req, res, next) => {
    
    ...
})

addUser The middleware , It's a method , Accept... In the route req,res,next Three parameters , Must be **next();** End code , In this way, the function pointer starts from addUser, hand (req,res,next)=> {…}.
Using middleware , You can get cookies, To verify user login information
obtain cookie The content of , Need to install cookie-parser rely on

npm i –save cookie-parser

stay app.js in , Mount this dependency to use .

app.use(cookieParser());

Error handling middleware –Error Handle

Be careful Error Handle The order of mounting , Generally mount to app.use() Next , And put it last .

var express = require('express');
var cookieParser = require('cookie-parser');
var path = require('path');
var localOptions = require('./build/localOptions');
var config = require('./config/config');
var bodyParser = require('body-parser');
var auth = require('./middleware/auth');
var log4js = require('./config/log4js');

process.env.NODE_ENV = process.env.NODE_ENV ? process.env.NODE_ENV : 'production';
var isDev = process.env.NODE_ENV === 'dev';
var app = express();
var port = config.port;


app.set('view engine', 'pug');
//  Set the template file path 
if (isDev){
    
	app.set('views', path.resolve(__dirname, 'src/Views'));
}else {
    
	app.set('views', path.resolve(__dirname, 'dist/Views'));
}

// app.locals The defined key value pairs can be accessed directly in the template 
app.locals.env = process.env.NODE_ENV || 'dev';
app.locals.reload = true;

app.use(cookieParser());
app.use(bodyParser.urlencoded({
    extended: false}));


if (isDev) {
    
    // app.locals.pretty = true;
	//  development environment , Static files use hot plug 
	var webpack = require('webpack');
	var webpackDevMiddleware = require('webpack-dev-middleware');
	var webpackHotMiddleware = require('webpack-hot-middleware');
	var webpackDevConfig = require('./build/webpack.dev.config.js');

	var compiler = webpack(webpackDevConfig);
	//  Hot plug 
	app.use(webpackDevMiddleware(compiler, {
    
		publicPath: webpackDevConfig.output.publicPath,
		noInfo: true,
		stats: 'errors-only'
	}))
	app.use(webpackHotMiddleware(compiler, {
    
		heartbeat: 1000,
		noInfo: true,
	}));

	//  It cannot be hot swapped down 
	var reload = require('reload');
	var http = require('http');
	var server = http.createServer(app);
	// reload(server, app);
	reload(app);
	server.listen(port, () => {
    
		console.log('App【dev】 is now running on port ' + port + '!');
	});

	//  Static directory settings must have , Read by the development environment vendor.js Not a memory file ;
    //  Static directory settings must be placed in reload Back , Avoid page introduction reload.js Report errors 
    app.use(express.static(path.join(config.root, 'src')));
    app.use('/', require(path.join(config.configRoot,'/routes')));
	
}else {
    
	//  Online environment does not need monitoring , Just turn it on node The service can be 
	//  Set up node Static file directory for 
	app.use(express.static(path.join(config.root, 'dist')));
    app.use('/',require(path.join(config.configRoot,'/routes')));
    // app.listen(process.env.PORT, () => {
    
    app.listen(port, () => {
    
		console.log('App【production】 is now running on port ' + port + '!');
    })
}

//  capture  404 error   Pass to  error route 
app.use('*', auth, (req, res, next) => {
    
	let err = new Error('Not Found');
	err.status = 404;
	next(err);
});

//  Capture  error, Jump to error page 
app.use((err, req, res, next) => {
    
	const sc = err.status || 500;
	if(err.status == 405){
    
		res.redirect(config.cndesignOrigin + '/Home/GuideAuthentication');
		return;
	}
	res.status(sc);
	//  Write the log here 
	log4js.error('\r\n Status: '+ sc + "\r\n Message: " + err.message + "\r\n Href: " + localOptions.baseUrl + req.originalUrl + "\r\n User-agent: " + req.headers['user-agent']);

	res.render('Error/404', {
    
		error: err,
		status: sc,
		message: err.message,
		userInfo: req.userInfo_ || {
     hasLogin: false }
	});
});

Reference blog

Node Middle tier practice ( 5、 ... and )——express- Logical processing of the middle layer
https://juejin.cn/post/6844904191635226632

原网站

版权声明
本文为[Lily]所创,转载请带上原文链接,感谢
https://yzsam.com/2022/204/202207230222108383.html