質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

新規登録して質問してみよう
ただいま回答率
85.47%
Node.js

Node.jsとはGoogleのV8 JavaScriptエンジンを使用しているサーバーサイドのイベント駆動型プログラムです。

Express

ExpressはNode.jsのWebアプリケーションフレームワークです。 マルチページを構築するための機能セットおよびハイブリッドのWebアプリケーションを提供します。

Q&A

解決済

1回答

1240閲覧

node.jsのexpress-validatorで検証が出来ない。

hokosugi

総合スコア63

Node.js

Node.jsとはGoogleのV8 JavaScriptエンジンを使用しているサーバーサイドのイベント駆動型プログラムです。

Express

ExpressはNode.jsのWebアプリケーションフレームワークです。 マルチページを構築するための機能セットおよびハイブリッドのWebアプリケーションを提供します。

0グッド

1クリップ

投稿2021/02/13 21:24

編集2021/02/14 00:34

expressでexpress-validatorモジュールを使ってパスワードとパスワード(確認)の検証しようとしていますが、下記コードが効かず、model.save以下に移ってログインしてしまいます。(コードはドキュメントを参考して書いています)

body('passwordConfirmation').custom((value, req) => { if (value !== req.body.password) { throw new Error('パスワード確認がパスワードと一致しません'); } return true; }), model.save(function(err){ if (err) { res.status(403).send('error:'+err); } else { res.render('home', {title: 'Laravel', user: req.body.name}); } });

body('passwordConfirmation')をconsole.logで出力しましたが、html側のformタグname属性の入力値が入っているようではないようです。(よく分かっていないのでformのname名とmodel側のkey名をpasswordConfirmationに統一しています)
他にbody('password')を出力しても同じような内容で、このbodyは何を表しているのか分かりません。
しかしbody('password').isLength({ min: 7 })はしっかり効いてくれてます。
なのに上記のコードが効かないのはなぜなのか?
どうやってデバッグ&検証すればよいのか教えて下さい。

宜しくおねがいします。
【修正後】
上記のコードの全文(controller.js)とview/login.ejsを追加します。

const mongoose = require('mongoose'); const { body, validationResult } = require('express-validator'); const schema = require('../models/model'); const Model = mongoose.model('Model', schema); exports.login = function(req, res){ res.render('login', {title: 'Laravel'}); }; exports.loginPost = function(req, res){ const errors = validationResult(req); const model = new Model(); console.log(body); if (!errors.isEmpty()) { return res.status(400).json({ errors: errors.array() }); }; body('passwordConfirmation').custom((value, req) => { //console.log(req.body.password); console.log(body.passwordConfirmation); if (value !== req.body.password) { throw new Error('パスワード確認がパスワードと一致しません'); } return true; }), model.save(function(err){ if (err) { res.status(403).send('error:'+err); } else { res.render('home', {title: 'Laravel', user: req.body.name}); } }); }

login.ejs

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

suama

2021/02/14 00:13

一部だけだと思いますが、できるだけ全部は載せていたくのは可能でしょうか? あと、送信するデータはPOSTメソッドだと思いますが、フォーム側のHTMLもあると良さそうな気がします。
hokosugi

2021/02/14 00:27

了解しました。修正します。
suama

2021/02/14 00:29

ありがとうございます! 先に思いついたところを書いてみますので、よかったら確認してみてくださいね!
guest

回答1

0

ベストアンサー

こんにちは。
わたしもちょっとしか使っていないので詳しくないのですが、body('passwordConfirmation').custom() でまず先にバリデーションを済ませたあと、(req, res) => {...}の処理をするので、modal.saveもこの部分で差し込まないといけないのではと思います。

通常のリクエスト処理は (req, res) => ... のところで行いますが、express-validatorはその前にチェーンの形でバリデーション処理を挟みます。

JavaScript

1 2const { body } = require('express-validator'); 3 4app.post( 5 # エンドポイントはソースコードが一部だけだったので適当です。 6 '/user', 7 body('passwordConfirmation').custom((value, { req }) => { 8 if (value !== req.body.password) { 9 throw new Error('Password confirmation does not match password'); 10 } 11 12 // Indicates the success of this synchronous custom validator 13 return true; 14 }), 15 (req, res) => { 16 // バリデーション処理をして、結果を判定 17  const errors = validationResult(req); 18 // バリデーションエラーがあれば先に4xxを返す 19  if (!errors.isEmpty()) { 20 res.status(403).send(`error: $errors`); 21 } 22 23 // modal.save はこの後に続ける 24 model.save(function(err){ ..... }) 25 }, 26);

body('password').isLength({ min: 7 }) はしっかり効いてくれてます。

ここは、Getting Startedのところの例でしょうか?
https://express-validator.github.io/docs/index.html

上記に添えた通り、まず先にバリデーション(複数OK) を済ませたあと、(req, res) => {...}の処理をするので、この例の通りに書かれていましたら、確かにちゃんと処理されると思います。

投稿2021/02/14 00:29

編集2021/02/14 00:30
suama

総合スコア1997

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

hokosugi

2021/02/14 00:53

ありがとうございます!上手くいきました。`exports.loginPost`をfunctionから始めないとエラーとなるので`router`側に`body('passwordConfirmation').custom`を移してfunctionから出したら機能してエラー表示が出るようになりました。コード自体に問題はなく、router側でcontroller.jsを呼び出す際にエラーが出るのでfunction内に`body('passwordConfirmation`を格納したことが原因でした。改めてお礼申し上げます。
suama

2021/02/14 01:02

良かったです! 結果的にはご自身で解決されたのでは、と思いますので恐縮です。。。 コードの記載もありがとうございます。
hokosugi

2021/02/14 06:41

いえいえ、ご回答がなかったら出来ておりませんでした。改めてお礼申し上げます。
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.47%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問