Express.js 중첩 라우터와 함께 휴식
대략 다음과 같은 REST 엔드포인트를 갖는다고 가정합니다.
/user/
/user/user_id
/user/user_id/items/
/user/user_id/items/item_id
각각의 CRUD가 말이 된다면요.예를 들어 /user POST는 새 사용자를 생성하고 GET은 모든 사용자를 가져옵니다./user/user_id GET는 한 사용자만 가져옵니다.
아이템들은 사용자에 따라 다르므로 특정 사용자인 user_id 밑에 넣었습니다.
Express routing modular를 만들기 위해 몇 가지 라우터 인스턴스를 만들었습니다.사용자를 위한 라우터와 아이템을 위한 라우터가 있습니다.
var userRouter = require('express').Router();
userRouter.route('/')
.get(function() {})
.post(function() {})
userRouter.route('/:user_id')
.get(function() {})
var itemRouter = require('express').Router();
itemRouter.route('/')
.get(function() {})
.post(function() {})
itemRouter.route('/:item_id')
.get(function() {})
app.use('/users', userRouter);
// Now how to add the next router?
// app.use('/users/', itemRouter);
URL 대상item
는 의 URL 계층의 하위 항목입니다.user
. 이제 URL을 어떻게 얻습니까?/users
userRouter에게 무엇이든 간에 보다 구체적인 경로는/user/*user_id*/items/
라우터 항목으로 이동하시겠습니까?그리고 가능하다면 user_id도 itemRouter에 접근할 수 있기를 바랍니다.
유무와 상관없이 라우터를 다른 라우터에 미들웨어로 연결하여 네스트할 수 있습니다.params
.
통과해야 합니다.{mergeParams: true}
액세스를 원하는 경우 하위 라우터로 연결합니다.params
상위 라우터에서 전송할 수 있습니다.
mergeParams
익스프레스(2014년 7월 5일)에서 선보였습니다.
이 예에서는itemRouter
에 애착을 갖습니다.userRouter
에서/:userId/items
경로
그러면 다음과 같은 경로가 발생합니다.
GET /user
->hello user
GET /user/5
->hello user 5
GET /user/5/items
->hello items from user 5
GET /user/5/items/6
->hello item 6 from user 5
var express = require('express');
var app = express();
var userRouter = express.Router();
// you need to set mergeParams: true on the router,
// if you want to access params from the parent router
var itemRouter = express.Router({mergeParams: true});
// you can nest routers by attaching them as middleware:
userRouter.use('/:userId/items', itemRouter);
userRouter.route('/')
.get(function (req, res) {
res.status(200)
.send('hello users');
});
userRouter.route('/:userId')
.get(function (req, res) {
res.status(200)
.send('hello user ' + req.params.userId);
});
itemRouter.route('/')
.get(function (req, res) {
res.status(200)
.send('hello items from user ' + req.params.userId);
});
itemRouter.route('/:itemId')
.get(function (req, res) {
res.status(200)
.send('hello item ' + req.params.itemId + ' from user ' + req.params.userId);
});
app.use('/user', userRouter);
app.listen(3003);
중첩 경로 관리 가능...
저는 express 4에서 매우 관리하기 쉬운 방법으로 중첩 경로를 수행하는 구체적인 예를 원했고 이것이 "express에서 중첩 경로"에 대한 상위 검색 결과였습니다.여기에는 예를 들어 분해해야 할 많은 경로가 있을 것으로 예상되는 API가 있습니다.
./index.js:
var app = require('express')();
// anything beginning with "/api" will go into this
app.use('/api', require('./routes/api'));
app.listen(3000);
./routes/api/index.js:
var router = require('express').Router();
// split up route handling
router.use('/products', require('./products'));
router.use('/categories', require('./categories'));
// etc.
module.exports = router;
./routes/api/products.js:
var router = require('express').Router();
// api/products
router.get('/', function(req, res) {
res.json({ products: [] });
});
// api/products/:id
router.get('/:id', function(req, res) {
res.json({ id: req.params.id });
});
module.exports = router;
폴더 구조에 내포 예제
나는 "네스팅 폴더 구조"에 대한 몇 가지 의견을 알아챘습니다.여기에 암시되어 있지만 명확하지 않아 아래 부분을 추가했습니다.다음은 경로에 대한 중첩 폴더 구조의 구체적인 예입니다.
index.js
/api
index.js
/admin
index.js
/users
index.js
list.js
/permissions
index.js
list.js
이것은 노드가 어떻게 작동하는지에 대한 더 일반적인 예입니다.디렉토리 기본값의 웹 페이지에서 "index.html"이 작동하는 방법과 유사하게 폴더에서 "index.js"를 사용하는 경우, 입력 지점을 코드로 변경하지 않고도 재귀에 기반하여 조직을 쉽게 확장할 수 있습니다."index.js"는 디렉토리에서 require를 사용할 때 액세스되는 기본 문서입니다.
index.js의 내용
const express = require('express');
const router = express.Router();
router.use('/api', require('./api'));
module.exports = router;
/api/index.js의 내용
const express = require('express');
const router = express.Router();
router.use('/admin', require('./admin'));
module.exports = router;
/api/admin/index.js의 내용
const express = require('express');
const router = express.Router();
router.use('/users', require('./users'));
router.use('/permissions', require('./permissions'));
module.exports = router;
/api/admin/users/index.js 내용
const express = require('express');
const router = express.Router();
router.get('/', require('./list'));
module.exports = router;
여기에 DRY 문제가 있을 가능성이 있지만 우려 사항을 요약하는 데 도움이 됩니다.
참고로 저는 최근에 액션 히어로를 맡게 되었고, 그것이 REST 패러다임을 뒤집는 진정한 프레임워크 올인원(All-in-One)에 더 가깝다는 것을 알게 되었습니다.속달로 벌거벗고 가는 것을 확인해 보셔야 할 것 같습니다.
var userRouter = require('express').Router();
var itemRouter = require('express').Router({ mergeParams: true });
userRouter.route('/')
.get(function(req, res) {})
.post(function(req, res) {})
userRouter.route('/:user_id')
.get(function() {})
itemRouter.route('/')
.get(function(req, res) {})
.post(function(req, res) {})
itemRouter.route('/:item_id')
.get(function(req, res) {
return res.send(req.params);
});
app.use('/user/', userRouter);
app.use('/user/:user_id/item', itemRouter);
질문의 두 번째 부분의 핵심은 mergeParams 옵션을 사용하는 것입니다.
var itemRouter = require('express').Router({ mergeParams: true });
:/user/jordan/item/cat
답변이 왔습니다.
{"user_id":"jordan","item_id":"cat"}
@Jason Sebring 솔루션을 사용하고 Typecript에 적응합니다.
server.
import Routes from './api/routes';
app.use('/api/', Routes);
/api/routes/index.ts
import { Router } from 'express';
import HomeRoutes from './home';
const router = Router();
router.use('/', HomeRoutes);
// add other routes...
export default router;
/api/routes/home.ts
import { Request, Response, Router } from 'express';
const router = Router();
router.get('/', (req: Request, res: Response) => {
res.json({
message: 'Welcome to API',
});
});
export default router;
Express 모듈러 라우터의 정신에 따라 사용자와 아이템을 위한 별도의 라우터를 보유해야 합니다.그 라우터는 우리의 최상위 애플리케이션 로직의 일부가 아닙니다.대신 사용자의 라우터에 둥지를 틀 수 있습니다.
Users 라우터
const users = require('express').Router();
const items = require('./items');
//...
// Our root route to /users
albums.get('/', function(req, res, next) {
// res.send() our response here
});
// A route to handle requests to any individual user, identified by an user id
users.get('/:userId', function(req, res, next) {
let userId = req.params.userId;
// retrieve user from database using userId
// res.send() response with user data
});
// Note, this route represents /users/:userId/items because our top-level router is already forwarding /users to our Users router!
users.use('/:userId/items', items);
//...
module.exports = users;
아이템 공유기
// We need to merge params to make userId available in our Items router
const items = require('express').Router({ mergeParams: true });
//...
// The root router for requests to our items path
items.get('/', function(req, res, next) {
let userId = req.params.userId; // Here is where mergeParams makes its magic
// retrieve user's track data and render items list page
});
// The route for handling a request to a specific item
items.get('/:itemId', function(req, res, next) {
let userId = req.params.userId; // <-- mergeParams magic
let itemId = req.params.itemId;
// retrieve individual item data and render on single item page
});
//...
module.exports = items;
덧붙이려고 애쓰다{ mergeParams: true }
.getUser
동안이나 postUser
const userRouter = require("express").Router({ mergeParams: true });
export default ()=>{
userRouter
.route("/")
.get(getUser)
.post(postUser);
userRouter.route("/:user_id").get(function () {});
}
Express 라우터(express).라우터()는 파라미터를 별도로 유지하므로 이들 파라미터를 병합하려면 express에 명시적으로 지시해야 합니다.예: express.라우터({ mergeParams: true})
//위 줄은 질문에 대한 답변입니다.
라우터가 하나만 있으면 다음과 같이 사용할 수 있습니다.
router.get('/users');
router.get('/users/:user_id');
router.get('/users/:user_id/items');
router.get('/users/:user_id/items/:item_id');
app.use('api/v1', router);
언급URL : https://stackoverflow.com/questions/25260818/rest-with-express-js-nested-router
'bestsource' 카테고리의 다른 글
Write-Host 문을 파일로 리디렉션 (0) | 2023.10.11 |
---|---|
ASM을 C로 변환(리버스 엔지니어 아님) (0) | 2023.10.11 |
ASP.NET 웹 양식 + ASP.NET Ajax 대 ASP.NET MVC 및 Ajax 프레임워크 자유도 (0) | 2023.10.11 |
워드프레스:한 페이지에 여러 페이지를 표시하려면 어떻게 해야 합니까? (0) | 2023.10.11 |
프로그래밍 방식으로 작성된 내용 보기를 사용하여 활동에 조각을 추가하는 방법 (0) | 2023.10.11 |