複数行に対応したjQuery validatorを書く場合 + 小ネタ

マネーフォワードではjQuery validation pluginを利用しています。

client sideでの簡易なvalidateを行う上で非常に便利なのですが、少し変わった事をやろうと思った場合にはまった点などをまとめてみます。

同一nameの複数行validate

たとえば、
attributes[hoge][][item]

のように、同じnameの要素が複数存在するformをvalidateする場合。

Hoge.setValidator = function () {
  var validationOption = {
    onkeyup: false,
    rules : {
      'attributes[hoge][][item]': {
        required: true,
      },
    },
  };
  $('#form').validate(validationOption);
}

上記でも一見動くように見えますが、エラー制御やエラー存在時にsubmitを中止する制御など、細かい箇所で意図しない動きをする場合があります。

こういう場合は、下記のように、要素毎に個別にruleを追加してあげる必要があります。

Hoge.setItemAllValidator = function () {
  $('.item').each(function() {
    $(this).rules('add', {
      required: true,
      messages: {
        required: 'itemを入力してください'
      }
    });
  });
};

複数要素がある場合のエラーメッセージの表示制御

複数要素のvalidateを行うと、エラー表示も意図しない挙動をする場合があります。
具体的には、3行の同名nameの入力フォームがあり、2行目でエラーが存在した場合、
errorPlacement でエラー表示位置を制御しない場合、フォームの直後に

 <label for="attributes_hoge__item" class="validate-error">itemを入力してください</label>

という要素がappendされます。

この要素は一度レンダリングされると要素自体が消えないため、2行目のエラーを修正して、3行目にもエラーが存在するような場合では、3行目のエラーが2行目のフォームの直後に表示されてしまいます。

これらは、valid() を呼び出す前に、エラーをremoveするなどの制御を入れる事で回避できます。

Hoge.isValid = function () {
  $('label.validate-error').remove();//エラーを一度clearする
  return ($('#form').valid() &&
          $('.itemAll').valid());
}

hidden要素 もvalidateしたい場合

jQuery validationには、ignoreオプションが用意されており、デフォルトで”hidden”がセットされています。

そのため、ignoreオプションに空要素を渡す事で、hiddenもチェック対象にすることが可能です。

Hoge.setValidator = function () {
  var validationOption = {
    ignore: [],
    onkeyup: false,
    ...
    ...
  };
  $('#form').validate(validationOption);
}

最後に

マネーフォワードではJavaScriptも大好きなRailsエンジニア・フロントエンドエンジニアを募集しています!
みなさまのご応募お待ちしております!

マネーフォワード採用サイト
https://recruit.moneyforward.com/

日本No.1お金のサービスを創り上げるRailsエンジニアWanted!
https://www.wantedly.com/projects/9979

「金融×IT」UI・UXを支える”フロントエンドエンジニア”!
https://www.wantedly.com/projects/9977

Pocket