Bagaimana Menangani Penolakan janji yang tidak tertangani dalam metode objek async di Node.js expressjs?

Saya menggunakan fungsi async di dalam objek untuk mengirim respons di express.js

Kode Pengontrol:

module.exports = {

    async signUpEmail(req, res) {

        /**
         * @description Parameters from body
         * @param {string} firstName - First Name
         * @inner
         */  

        const firstName = req.body.firstName;

        res.send({ success: name });
        throw new Error(); // purposely Done
    }
}

Pertanyaan:

Karena metode signUpEmail dalam kasus saya adalah async dan akan ditolak dengan metode async apa pun yang saya lempar, ini dia Error.(sengaja diletakkan di sana)

jadi login ini di konsol.

(node:13537) UnhandledPromiseRejectionWarning: Unhandled promise rejection (rejection id: 1): Error
(node:13537) DeprecationWarning: Unhandled promise rejections are deprecated. In the future, promise rejections that are not handled will terminate the Node.js process with a non-zero exit code.

Jadi saya harus menanganinya dari rute tempat saya memanggilnya.

Kode Perute

    const routes = require('express').Router();
const SignUpController = require('../controllers/signUpController')

// /signup
routes.post('/', SignUpController.signUpEmail);

module.exports = routes;

ada yang seperti ini SignUpController.signUpEmail().then(…); Tapi karena saya tidak memanggil fungsi di rute yang saya lewati saja. Bagaimana hal ini dapat dilakukan secara efektif ?

PS:Tolong jangan menyarankan solusi yang terlalu rumit. Saya pemula dengan JS dan sedang belajar.

Saya tidak menggunakan penangan rute yang dapat dirantai karena saya ingin membuat penangan rute yang modular dan dapat dipasang.

Contoh Dokumen Resmi


person Ankur Anand    schedule 22.04.2017    source sumber
comment
Lewatkan saja fungsi yang berfungsi: routes.pos('/', (...args) => SignUpController.signUpEmail().then(…))   -  person Bergi    schedule 23.04.2017
comment
@Bergi mendapatkan ini sekarang TypeError: Tidak dapat membaca properti 'tubuh' yang tidak ditentukan. sepertinya spread tidak melewati req ..mencoba console.log menjadi tidak terdefinisi   -  person Ankur Anand    schedule 23.04.2017
comment
Sepertinya Anda menginginkan …signUpEmail(...args)… atau apa pun yang diharapkan fungsi Anda   -  person Bergi    schedule 23.04.2017
comment
@Bergi ya paham.. jika Anda bisa memberikan sedikit pencerahan mengapa cara ini berhasil terutama bagaimana (...args) =› tersedia dan apa ini? Karena jika saya melakukan` rute.post('/', konsol.log(args));` saya mendapatkan ReferenceError: args is not defined ini akan sangat membantu   -  person Ankur Anand    schedule 23.04.2017
comment
Anda harus memasukkannya ke dalam fungsi panah untuk mencatatnya. Namun Anda juga dapat menulisnya tanpa parameter spread: routes.post('/', (req, res) => SignUpController.signUpEmail(req, res).then(…))   -  person Bergi    schedule 23.04.2017
comment
@Bergi Sekarang saya pikir saya mengerti (spread) membuatnya lebih jelas .. tidak mengetahui js spread masih belajar JS. jadi pada dasarnya Route.post() memerlukan panggilan balik .. dan kami melakukan hal yang sama dalam menyelesaikan atau menolak janji yang dikembalikan oleh SignUpController.signUpEmail(req, res) ini dan menjadikan hasilnya seperti yang dikembalikan oleh fungsi normal .. Koreksi saya jika saya tidak mengerti.. Terima kasih atas Anda sangat membantu :)   -  person Ankur Anand    schedule 23.04.2017
comment
FYI, async/await bukan bagian dari ES7, melainkan bagian dari ES2017.   -  person Felix Kling    schedule 23.04.2017


Jawaban (1)


Di rute Anda, Anda perlu menambahkan pembungkus untuk menangkap kesalahan yang terjadi:

let wrapper = fn => (...args) => fn(...args).catch(args[2]);

// /signup
routes.post('/', wrapper(SignUpController.signUpEmail));

Dengan metode ini Anda dapat menggunakan penangkap kesalahan tingkat atas dan tidak perlu menggunakan blok coba tangkap internal di rute Anda, kecuali Anda memerlukannya secara kontekstual.

Gunakan middleware penangkap kesalahan untuk mencapai hal ini sebagai berikut:

// last middleware in chain

app.use(function(err, req, res, next) {
    // handle your errors
});

Sekarang di rute Anda, Anda dapat melakukan kesalahan dan kesalahan tersebut akan ditangkap oleh middleware itu. Saya suka membuat kesalahan khusus dan menangani responsnya serta masuk ke middleware ini.

Selain itu: Pola menunggu async sangat bagus untuk menulis kode asinkron yang mudah dibaca manusia secara sinkron. Ingatlah bahwa setelah Anda melakukan async, Anda harus tetap async! Sangat disarankan untuk menggunakan perpustakaan promisifikasi seperti Bluebird dan menjalankan .promisifyAll di nodeback perpustakaan.

EDIT : Sumber - Penanganan Kesalahan Asinkron dalam Ekspres dengan Janji, Generator dan ES7

person Kyle Richardson    schedule 22.04.2017
comment
Yang pertama sangat membantu dan memahaminya, tetapi untuk menggunakan middleware bukankah kita harus meneruskannya ke next(err) agar bisa berfungsi di sini? - person Ankur Anand; 23.04.2017
comment
let wrapper = fn => (...args) => fn(...args).catch(args[2]); menangkap kesalahan yang muncul dari fungsi di dalam pembungkus dan mengembalikannya sebagai rute berikutnya, yang kemudian diambil oleh middleware penanganan kesalahan Anda - person Kyle Richardson; 23.04.2017
comment
Apakah ini menjawab pertanyaan Anda? - person Kyle Richardson; 23.04.2017