নেক্সট.জেএস-এ যখন পরবর্তী () ব্যবহার করবেন এবং পরবর্তী () ফিরে আসবেন


136

পরিস্থিতি : নীচের কোনও নোড ওয়েব অ্যাপ্লিকেশন থেকে কোডের অংশ বিবেচনা করুন।

app.get('/users/:id?', function(req, res, next){
    var id = req.params.id;
    if (id) {
        // do something
    } else {
        next(); //or return next();
    }
});

ইস্যু : আমি যা এক মাত্র সঙ্গে যেতে দেখছি next()বা return next()। উপরে নমুনা কোড উভয়ের জন্য ঠিক একই রকম কাজ করে এবং কার্যকর করার ক্ষেত্রে কোনও পার্থক্য দেখায় না।

প্রশ্ন : কেউ কি এ বিষয়ে আলোকপাত করতে পারেন, কখন ব্যবহার করবেন next()এবং কখন ব্যবহার করবেন return next()এবং কিছু গুরুত্বপূর্ণ পার্থক্য রয়েছে?

উত্তর:


141

কিছু লোক সর্বদা লিখেন return next()তা নিশ্চিত করার জন্য কলব্যাকটি ট্রিগার করার পরে মৃত্যুদন্ড কার্যকর হবে।

যদি আপনি এটি না করেন, আপনি দ্বিতীয়বার কলব্যাকটি ট্রিগার করার ঝুঁকি নিয়েছেন, যার ফলস্বরূপ সর্বনাশা ফলাফল রয়েছে। আপনার কোড যেমন হয় ঠিক তেমন তবে আমি এটি আবার লিখতে চাই:

app.get('/users/:id?', function(req, res, next){
    var id = req.params.id;

    if(!id)
        return next();

    // do something
});

এটি আমাকে একটি ইনডেন্টেশন স্তর বাঁচায় এবং আমি যখন আবার কোডটি পড়ি তখন আমি নিশ্চিত যে কোনও nextউপায়ই দু'বার বলা হয়নি।


2
এই জাতীয় পরিস্থিতিতে res.redirect('/')বনামের মতো একই জিনিস কি সত্য হবে return res.redirect('/')? শিরোনামগুলি প্রেরণের পরে সেটিংয়ের ত্রুটিগুলি এড়ানোর জন্য রেস স্টেটমেন্টগুলির সামনে সর্বদা রিটার্ন লিখতে আরও ভাল?
অ্যাডাম ডি

185

@ লরেন্ট পেরিনের উত্তর হিসাবে:

যদি আপনি এটি না করেন, আপনি দ্বিতীয়বার কলব্যাকটি ট্রিগার করার ঝুঁকি নিয়েছেন, যার ফলস্বরূপ সর্বনাশা ফলাফল রয়েছে

আপনি এখানে মিডওয়্যারটি লিখলে আমি এখানে একটি উদাহরণ দিচ্ছি:

app.use((req, res, next) => {
  console.log('This is a middleware')
  next()
  console.log('This is first-half middleware')
})

app.use((req, res, next) => {
  console.log('This is second middleware')
  next()
})

app.use((req, res, next) => {
  console.log('This is third middleware')
  next()
})

আপনি খুঁজে পাবেন যে কনসোলের আউটপুটটি হ'ল:

This is a middleware
This is second middleware
This is third middleware
This is first-half middleware

এটি হ'ল, সমস্ত মিডলওয়্যার ফাংশন শেষ হওয়ার পরে এটি পরবর্তী () এর নীচে কোড চালায়।

তবে, আপনি যদি ব্যবহার করেন তবে return next()তা সঙ্গে সঙ্গে কলব্যাকটি ছাড়বে এবং কলব্যাকের নীচের কোডটি return next()অ্যাক্সেসযোগ্য হবে।


29
হিসাবে একটি শিক্ষানবিস expressএই উত্তরটি অন্যান্য উত্তর চেয়ে আমার কাছে কিছু পরিষ্কার করেছেন। থাম্বস আপ!
মান্দারিন

1
এই জাতীয় পরিস্থিতিতে res.redirect('/')বনামের মতো একই জিনিস কি সত্য হবে return res.redirect('/')? সম্ভবত হেডারগুলি প্রেরণের পরে সেটিংয়ের ত্রুটিগুলি এড়াতে সর্বদা বিবৃতিগুলির returnসামনে লেখার চেয়ে আরও ভাল res?
অ্যাডাম ডি

1
আমি কেন পরের () পরে কোড লিখব? মিডওয়্যারটিতে কাজ শেষ করার পরে আমি কিছুই করি না তা কি স্পষ্ট নয়? @ পিজেএইচএনডিডার
ইমরান

1
@ ইমরানপলব কখনও কখনও ভুল হয়। আপনি যখন প্রচুর কোড লিখবেন, আইএফএস / এলেস / ইত্যাদি। আপনি ভুলে যেতে পারেন next next next পরের () `
জোন পোলভোরা

46

next()কানেক্ট মিডলওয়্যার অংশ । রাউটার প্রবাহের কলব্যাকগুলি যদি আপনি আপনার ফাংশন থেকে কোনও কিছু ফিরিয়ে দেন তবে তা যত্নশীল নয়, return next()এবং next(); return;মূলত একই।

আপনি যদি ফাংশনগুলির প্রবাহ বন্ধ করতে next(err)চান তবে নীচের মতো ব্যবহার করতে পারেন

app.get('/user/:id?', 
    function(req, res, next) { 
        console.log('function one');
        if ( !req.params.id ) 
            next('No ID'); // This will return error
        else   
            next(); // This will continue to function 2
    },
    function(req, res) { 
        console.log('function two'); 
    }
);

next()আপনার অনুরোধগুলির মিডওয়্যারটি প্রসারিত করার জন্য বেশ কিছু ব্যবহৃত হয়।


1
আমরা মত পরামিতি পাঠানো যাবে না: next('No ID')?
আমল এম কুলকার্নি

7
next('No ID')আসলে একটি ত্রুটি প্রেরণ করছে, যা প্রবাহকে ভঙ্গ করবে।
ড্রিঙ্কেভ

পরবর্তী ব্যবহার করুন (নাল, "কিছুটা"); Async. ওয়াটারফলের মতো সরঞ্জামগুলির জন্য এটি পরবর্তী ফাংশনে মানটি প্রেরণ করবে। ডেটাচালিত জটিল ক্রিয়াকলাপগুলির জন্য, আমি সাধারণত ফাংশনগুলির মধ্যে একটি প্রসঙ্গ বস্তুটি পাস করি। এইভাবে আমি জেনেরিক ফাংশন তৈরি করতে পারি যা একাধিক প্রান্ত পয়েন্টগুলিতে ভাগ করা যায় এবং প্রসঙ্গে ডেটার মাধ্যমে নিয়ন্ত্রণ প্রবাহকে ভাগ করা যায়
চাদ উইলসন

5
"সুতরাং পরবর্তী () এবং পরবর্তী () এবং ফিরে আসুন; ফিরে আসুন; মূলত একই রকম।" - আমার যা পড়ার দরকার ছিল। thx @drinchev
নিক পিনেদা

1
আমি বিপরীতটি লক্ষ্য করি (যখন গুলি চালানোর সময় ত্রুটি হয়): পরবর্তী (ত্রুটি) পরবর্তী মিডলওয়্যার ট্রিগার করে, তবে কোড চালিয়ে যেতে থাকে; পরবর্তী ফিরে (ত্রুটি) কেবলমাত্র পরের মিডলওয়্যারের কাছে মৃত্যুদন্ড কার্যকর করে। পরবর্তী (ঙ) এবং পরের দিকে ফিরে (ই) এক নয়।
নিকোলোডিওন

0

একেবারেই ব্যবহার না করাই ভাল! আমি ব্যাখ্যা করি, এবং এটি আমি এটিরও ব্যাখ্যা করি।

পরবর্তী () ফাংশন যার কোনও নাম থাকতে পারে এবং কনভেনশন অনুসারে পরবর্তীতে সেট করা হয়েছে। এটি অপ্রত্যক্ষভাবে অপারেশনগুলির সাথে সম্পর্কিত (পুট, জিইটি, ডিলেট, ...) যা সাধারণত একই ইউআরআই উত্সে সঞ্চালিত হয় উদাহরণস্বরূপ/ user /: id

app.get('/user/:id', function (req,res,next)...)
app.put('/user/:id', function (req,res,next)...)
app.delete('/user/:id', function (req,res,next)...)
app.post('/user/', function ()...)

এখন আপনি যদি app.get, app.put এবং app.delete এ একই ইউরি (/ ব্যবহারকারী /: আইডি) ব্যবহার করেন তবে তাদের বাস্তবায়ন হ'ল একমাত্র জিনিস। যখন অনুরোধটি করা হয় (পুনরায়) এক্সপ্রেসটি অ্যাপ্লিকেশনটিতে প্রথমে রেকটিকে রাখে, আপনি যে কোনও বৈধতা তৈরি করেছেন কারণ সেই অনুরোধটি যে নিয়ন্ত্রকের জন্য ব্যর্থ হয় না, এটি অ্যাপ্লিকেশনকে পুনরায় রেকর্ড করে দেয় যা পরবর্তী ফাইলের ফাইল হয় চালু. নীচের উদাহরণে দেখা যায়।

    app.get('/user/:id', function (req,res,next){

    if(req.method === 'GET')
    //whatever you are going to do
    else
      return next() //it passes the request to app.put

    //Where would GET response 404 go, here? or in the next one. 
    // Will the GET answer be handled by a PUT? Something is wrong here.

   })
    app.put('/user/:id', function (req,res,next){

    if(req.method === 'PUT')
    //whatever you are going to do
    else
      return next()

   })

সমস্যাটি মিথ্যা, শেষ পর্যন্ত আপনি সমস্ত কন্ট্রোলারের কাছে রেকটি শেষ করবেন এই আশায় যে রেকের বৈধতার মাধ্যমে আপনি যা চান তা করার একটি আছে। সবশেষে সমস্ত কন্ট্রোলার এমন কিছু পান যা তাদের পক্ষে নয় :(।

তো, কিভাবে পরবর্তী () এর সমস্যা এড়ানো যায় ?

উত্তরটি খুব সহজ।

1- একটি উত্স সনাক্ত করার জন্য কেবল একটি ইউরি থাকা উচিত

HTTP: // IpServidor / colection /: সম্পদ / colection /: রিসোর্স যদি আপনার ইউআরআই এর চেয়ে বেশি হয় তবে আপনার নতুন ইউআর তৈরির কথা বিবেচনা করা উচিত

উদাহরণ HTTP: // আইপিএস সার্ভিডর / ব্যবহারকারী / পেপ / পরিচিতি / কন্টাক্টমেন্ট 1

2-এই সংস্থার সমস্ত ক্রিয়াকলাপ HT (ক্রিয়া, পোস্ট, লাগানো, মুছুন, ...) ক্রিয়া ক্রিয়াকলাপের আদর্শের প্রতি শ্রদ্ধাশীল হতে হবে সুতরাং কোনও ইউআরআইতে কল করার জন্য কেবল কল করার এক উপায় আছে

POST http://IpServidor/users/  //create a pepe user 
GET http://IpServidor/users/pepe  //user pepe returns   
PUT http://IpServidor/users/pepe  //update the user pepe 
DELETE http://IpServidor/users/pepe  //remove the user pepe

আরও তথ্য [ https://docs.microsoft.com/es-es/azure/architecture/best-practices/api-design#organize-the-api-around-res উত্স‍ +1]

কোডটি দেখি!কংক্রিট বাস্তবায়ন যা আমাদের পরবর্তী () ব্যবহার এড়াতে দেয়!

Index.js ফাইলটিতে

//index.js the entry point to the application also caller app.js
const express = require('express');
const app = express();

const usersRoute = require('./src/route/usersRoute.js');

app.use('/users', usersRoute );

ব্যবহারকারীরাউইট.জেএস ফাইলটিতে

    //usersRoute.js
    const express = require('express');
    const router = express.Router();

    const getUsersController = require('../Controllers/getUsersController.js');
    const deleteUsersController = require('../Controllers/deleteUsersController.js');

    router.use('/:name', function (req, res) //The path is in /users/:name
    {
    switch (req.method)
    {
    case 'DELETE':
      deleteUsersController(req, res);
      break;
    case 'PUT':
     // call to putUsersController(req, res);
     break;
    case 'GET':
     getUsersController(req, res);
     break;
    default:
     res.status(400).send('Bad request');
    } });

router.post('/',function (req,res) //The path is in /users/
{
    postUsersController(req, res);
});

module.exports = router;

এখন ব্যবহারকারীরাউইট.জেএস ফাইল ব্যবহারকারীরাট নামে একটি ফাইল যা প্রত্যাশা করে তা করে যা ইউআরআই / ব্যবহারকারী /

// ফাইল getUserController.js

//getUsersController.js
    const findUser= require('../Aplication/findUser.js');
    const usersRepository = require('../Infraestructure/usersRepository.js');

    const getUsersController = async function (req, res)
    {

       try{
          const userName = req.params.name;
        //...
          res.status(200).send(user.propertys())

        }catch(findUserError){
           res.status(findUserError.code).send(findUserError.message)
        }
    }
   module.exports = getUsersController;

এইভাবে আপনি পরবর্তী ব্যবহার এড়াতে পারবেন, আপনি কোডটি দ্বিগুণ করবেন, আপনি কার্য সম্পাদন করবেন, আপনি সোলিড বিকাশ করবেন, আপনি মাইক্রোসার্ভেসিসের সম্ভাব্য মাইগ্রেশনের জন্য দরজাটি উন্মুক্ত রেখে যান এবং সর্বোপরি, একজন প্রোগ্রামার দ্বারা পড়া সহজ।


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

ভুল তথ্য, দয়া করে উপরের উত্তরগুলি দেখুন।
ডিডিমন্ড

-3

পরবর্তী() :

এই ফাংশনটি কল করা অ্যাপ্লিকেশনটিতে পরবর্তী মিডলওয়্যার ফাংশনটি আহ্বান করে। পরবর্তী () ফাংশনটি নোড.জেএস বা এক্সপ্রেস এপিআইয়ের অংশ নয়, তবে এটি তৃতীয় আর্গুমেন্ট যা মিডওয়্যার ফাংশনে পাস করা হয়েছে।

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