এক্সপ্রেস.জেএস নেস্টেড রাউটার দিয়ে বিশ্রাম করুন


136

মনে করুন আমি প্রায় শেষের দিকগুলি দেখতে চাই যা মোটামুটি এরকম দেখাচ্ছে:

/user/
/user/user_id 

/user/user_id/items/
/user/user_id/items/item_id

প্রতিটি সিআরডি যদি জ্ঞান করে তোলে। উদাহরণস্বরূপ, / ব্যবহারকারী POST একটি নতুন ব্যবহারকারী তৈরি করে, GET সমস্ত ব্যবহারকারীকে আনে। / ব্যবহারকারী / ব্যবহারকারী_ আইডি জিইটি ঠিক সেই এক ব্যবহারকারীকে নিয়ে আসে।

আইটেমগুলি ব্যবহারকারী নির্দিষ্ট হয় তাই আমি এগুলিকে ইউজার_আইডের নিচে রাখি যা একটি নির্দিষ্ট ব্যবহারকারী।

এক্সপ্রেস রাউটিংকে মডুলার করার জন্য আমি কয়েকটি রাউটার উদাহরণ তৈরি করেছি। ব্যবহারকারীর জন্য একটি রাউটার এবং আইটেমটির জন্য একটি রাউটার রয়েছে।

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 টি ইউআরএল এর URL itemবংশোদ্ভূত user। এখন আমি /usersইউআরআরউটারের সাথে ইউআরএল কীভাবে পেতে পারি তবে আইটেম রাউটারের আরও নির্দিষ্ট রুট /user/*user_id*/items/? এবং এছাড়াও, আমি চাই ইউজার_আইডি যদি সম্ভব হয় তবে আইটেমরউটারেও অ্যাক্সেসযোগ্য।


এটি সমাধানের জন্য ইতিমধ্যে এক্সপ্রেস ব্যবহার করে দুর্দান্ত উত্তর। আপনি তবে ল্যাবব্যাক (এক্সপ্রেসে নির্মিত) ব্যবহার করতে পারবেন সোয়াগার-ভিত্তিক এপিআই প্রয়োগ করতে এবং আপনার অনুরোধের মতো সিআরইউডি সম্পাদনের জন্য মডেলগুলির মধ্যে সম্পর্ক যুক্ত করতে। দুর্দান্ত জিনিস প্রাথমিক শিক্ষার বক্ররেখার পরে, এটি জড়ো হওয়া খুব দ্রুত। লুপব্যাক.ও
মাইক এস।

উত্তর:


277

আপনি রাউটারগুলিকে বা অন্য কোনও রাউটারের মিডলওয়্যার হিসাবে সংযুক্ত করে বাসা বাঁধতে পারেন params

আপনি {mergeParams: true}যদি paramsপিতৃ রাউটার থেকে অ্যাক্সেস করতে চান তবে আপনাকে অবশ্যই চাইল্ড রাউটারে যেতে হবে ।

mergeParamsএক্সপ্রেসে4.5.0 চালু হয়েছিল (জুলাই 5 2014)

এই উদাহরণে 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);

3
উত্তর করার জন্য ধন্যবাদ. আপনি এখানে যে রাউটারটি ব্যবহার করছেন সেটি জর্দোনিয়াস ভাগ করেছেন তার চেয়ে আরও স্পষ্টভাবে নেস্ট করা হয়েছে। কিন্তু এটি কি ফণা নীচে একই কাজ করে? আমি আপনাকে ব্যাপকতার জন্য অনুদান দিতে চাই তবে কয়েক ঘন্টা পরে আমি এটি করতে পারি না।
হুগি

উত্তর করার জন্য ধন্যবাদ. অভিভাবক রুটের ক্যোয়ারী প্যারামগুলি চাইলট রুট থেকে পাওয়ার মতো কোনও উপায় আছে কি ?
cwarny

1
এগুলি যদি কোনও রুটে না পাওয়া যায় তবে আমার অবাক করে দেবে, কারণ ক্যোয়ারী পরম নির্দিষ্ট কোনও রুটে বাঁধা না থেকে ...
উইলিম ডি'হ্যাসিলিয়ার

খুব পুঙ্খানুপুঙ্খ উত্তর! একটি প্রশ্ন: ব্যবহারকারীর রাউটার এবং আইটেম রাউটারের মধ্যে জ্ঞানের পৃথকীকরণ এবং বিচ্ছিন্নতার খাতিরে কোনও সাব্রোটারের একটি প্যারামিটারের প্রয়োজন আছে তা নির্দিষ্ট করার কোনও ঘোষণামূলক উপায় আছে? অন্য কথায়, রেজিস্ট্রেশন লিখতে বা কল অ্যাক্সেস করার জন্য স্পষ্ট উপায় আছে যে আইটেম রাউটারটি এটি আমাদের ব্যবহারকারীর আইডি পাস করার আশা করে তা জানতে দেয়? উদাহরণ অবস্থা, আইটেম রাউটার পুরাপুরি অন্য ফাইল হয়, গঠনের দিক এটা স্পষ্ট নয় যে এটি একটি ব্যবহারকারী প্রয়োজন যদি না আপনি তার কল ঢোকা এবং এটি ব্যবহারকারীর রাউটার একমাত্র পরিষ্কার যে এটি একটি ইউজার আইডি পাস হবে
yo.ian.g

রাউটারগুলির "স্ট্যান্ডার্ড" ব্যবহারের বিষয়টি আর স্পষ্ট নয়, কোডটি দেখার সময় আমি নীড়ের দৃশ্যটি দেখার উপায় খুঁজছি।
ড্রইউইনথাউন্টস 21

127

পরিচালিত নেস্টেড রুটগুলি ...

আমি 4 টি এক্সপ্রেসে খুব পরিচালনাযোগ্য উপায়ে নেস্টেড রুটগুলি করার একটি নির্দিষ্ট উদাহরণ চেয়েছিলাম এবং এটি "এক্সপ্রেসে নেস্টেড রুটগুলি" এর শীর্ষ অনুসন্ধানের ফলাফল ছিল। এখানে এমন একটি এপিআই রয়েছে যাতে অনেকগুলি রুট থাকে যা উদাহরণস্বরূপ ভাঙতে হবে।

./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.tml" কীভাবে ফোল্ডারগুলিতে "index.js" ব্যবহার করেন তবে কোডে আপনার এন্ট্রি পয়েন্টগুলি পরিবর্তন না করে আপনার সংস্থাকে পুনরাবৃত্তির ভিত্তিতে স্কেল করা সহজ হবে। ডিরেক্টরিতে প্রয়োজনীয় ব্যবহার করার সময় "index.js" হ'ল ডিফল্ট ডকুমেন্ট ।

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;

এখানে কিছু ডিআরওয়াই সমস্যা রয়েছে সম্ভবত তবে এটি উদ্বেগের সংমিশ্রণে নিজেকে ভাল ধার দেয়।

এফওয়াইআই, সম্প্রতি আমি অ্যাকশন হিরোতে এসেছি এবং এটি সম্পূর্ণ বৈশিষ্ট্যযুক্ত ডাব্লু / সকেট এবং কার্যাদি পেয়েছি, আরও সত্যিকারের কাঠামোর মতো এটির মাথার মধ্যে REST দৃষ্টান্তটি উল্টানো। নগ্ন ডাব্লু / এক্সপ্রেস যাওয়ার সময় আপনার এটি পরীক্ষা করা উচিত।


11
আমি দেখতে পাচ্ছি কীভাবে এটি রুটগুলি বিভক্ত করে, তবে কীভাবে এটি বাসা বাঁধবে?
1252748

নিখুঁত .... এবং জ্ঞান করে তোলে। এটি একটি স্কেলেবল বিকল্প।
অপটি

8
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);

আপনার প্রশ্নের দ্বিতীয় অংশের চাবি হ'ল মার্জপ্যারাম বিকল্প ব্যবহার

var itemRouter = require('express').Router({ mergeParams: true }); 

/user/jordan/item/catআমার কাছ থেকে একটি জবাব পাওয়া যায়:

{"user_id":"jordan","item_id":"cat"}

কুল। আপনার এবং উইলেমের পদ্ধতি উভয়ই আমি যা চাই তা জন্য কাজ করে। আমি তার ব্যাপকতার জন্য যাচাই করব তবে আমি আপনাকেও চিহ্নিত করব। অনেক ধন্যবাদ. আপনার পদ্ধতিটি ঘৃণিত দেখাচ্ছে না তবে এটি আমি যা চেয়েছিলাম তা অনেকখানি কার্যকর করে যা আমি মনে করি আমি এমনকি আপনার পছন্দ করি। ধন্যবাদ।
হুগি

মার্জপ্যারাম বিকল্পটি এখানে কী!
মিঃ ই

2

@ জেসন সেব্রিং সলিউশন ব্যবহার করে এবং টাইপস্ক্রিপ্টের জন্য অভিযোজিত।

server.ts

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;

আপনি সরবরাহ করতে পারেন ./api/routes?
জুলিয়ান

1
@ জুলিয়ান: আমি ফাইলের অবস্থান ঠিক করেছি fixed ./api/routesদুটি ফাইল আছে index.tsএবং home.ts। প্রথমটি ব্যবহার করে server.ts। আশা করি এটা তোমাকে সাহায্য করবে।
পিয়েরে আরএ

0
try to add  { mergeParams: true } look to simple example  which it middlware use it in controller file getUser at the same for  postUser
    const userRouter = require("express").Router({ mergeParams: true });
    export default ()=>{
    userRouter
      .route("/")
      .get(getUser)
      .post(postUser);
    userRouter.route("/:user_id").get(function () {});
    
    
    }

-9

আপনার কেবল একটি রাউটার দরকার এবং এটি এটির মতো ব্যবহার করুন:

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);

হ্যাঁ তবে আমি আইটেম এবং ব্যবহারকারীদের মধ্যে লজিকগুলি পৃথক করতে চাই এবং তাই আমি এগুলি যদিও আলাদা করতে পছন্দ করি। আমি জানি না এটি সম্ভব কিনা।
হুগি

@ হুগি অধিকারের itemsঅন্তর্গত, usersআপনার এটি আলাদা করার দরকার কেন? আপনি যদি চান তবে একই রাউটারটি ব্যবহার করে বিভিন্ন ফাইলগুলিতে এগুলি সংজ্ঞায়িত করতে পারেন।
উদাহরণস্বরূপ

এটি ব্যবহারকারীর অন্তর্গত তবে আমি ব্যবহারকারীকে প্রভাবিত না করে এটিকে সহজেই প্লাগ ইন বা আউট করতে সক্ষম হতে চাই। এবং বর্তমানে আমার কাছে প্রতিটি ইউআরএল শেষ পয়েন্টের জন্য রাউটার রয়েছে। শৈলীটি এক্সপ্রেস-জেনারেটর দ্বারা উত্সাহিত বলে মনে হচ্ছে। যদি এটি সম্ভব না হয়, তবে হ্যাঁ, রাউটারের উদাহরণটি আমাকে বিভিন্ন ফাইলগুলিতে প্রেরণ করা উচিত? তবে এটি মূল কাঠামোর সাথে সামঞ্জস্যপূর্ণ নয়।
হুগি

এটি কি অন্যের নীচে একটি রাউটার যুক্ত করা সম্ভব? যেহেতু এক্সপ্রেস মিডলওয়্যার আর্কিটেকচারটি নীচে রাউটার দ্বারা পরিচালিত হয়েছে বলে মনে হচ্ছে (এটি সম্পূর্ণ কিনা তা আমি নিশ্চিত নই) আমি মনে করি এটি সম্ভব হতে পারে।
হুগি

2
-1 এটি নেস্টেড রাউটারগুলি সম্পর্কে যে প্রশ্নের উত্তর দিচ্ছে না
উইলেম ডি'হেসেলির
আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.