Habrokatの下の詳細。
与えられた:
Backbone.js、アンダースコア、jQuery、jQueryUIが使用されるUI部分の大規模なWebプロジェクト。
プロジェクトの仕様により、タイプ(int、float、price、phone、text、combobox)に応じて、マスクの使用と入力フィールド(input、textareaなど)の検証が必要です。 一見すると、このタスクに古風なものは何もありません。jQueryが親切に提供してくれるプラグインの海から何かを得ることができます。 ただし、後の日付タイプ(jQuery DatePickerに基づく)とテキストエディター(tinyMCE)がこれらのタイプに追加されました。 途中でさらにいくつかのタイプがあり、仕様が作成されたばかりであり、既成のソリューションを見つけることができるという事実からはほど遠いものでした。
ここで、検証の問題がより急激に発生しました。 使用されるプラグインの数は飛躍的に増加し、警告を発し始めました。 一般的に、「このようにできなかったため、このようにできました。これはプラグインの標準的な動作です」という絶え間ない前進にうんざりして、独自の検証システムを作成することが決定されました。
見つける:
プロジェクトで使用されているテクノロジーに基づいて、独自の検証モジュールを作成します。
解決策:
モジュールは、すでにデータ検証チェックが組み込まれているため、backbone.jsモデルに基づいていました。そのような機会を拒否するのは愚かなことです。
プロジェクトの構造全体については説明しません。backbone.jsを使用した人は、誰が簡単に見つけられないか、Habréの紹介記事を簡単に見つけることができます。
そのため、共通のビューでvalidation()メソッドが作成されました。このメソッドは特定の検証パラメーターを受け取り、カスタムValidation.jsモジュールに渡します(別のUtilsフォルダーが作成され、他の共通要素と共に配置されます)。それに基づいてモデルオブジェクトを作成します:
validate: function (params) { if (_.isArray(params.items) && params.type === 'form') { _.each(params.items, function (item) { new core.utils.Validation(item); }, this); new core.utils.Validation(params); } else { new core.utils.Validation(params); } }
プロジェクト内のすべてのカスタムビューは、共通ビューから継承されるため、validation()メソッドが含まれます。 検証は次のように呼び出されます。コントローラーでは、特定のビューをレンダリングした後、カスタムのvalidationFieldsメソッドがすぐに呼び出されます。これは、たとえば、すべてのビューで異なります。
this.getView('SomeView').render({ 'someParams': someValue, … }).validateFields();
validationFieldsメソッド自体は次のようになります。
validateFields: function () { this.validate({ id: "description", type: "text", required: false, maxLength: 500, separate: true }); }
プラグインに通知します
id: "description"-id = "description"のフィールドを検証する必要があります。
タイプ:「テキスト」-入力データのタイプ-テキスト(文字、数字、句読点などが許可されます);
必須:false-フィールドは入力に必須ではなく、入力されたデータに関するエラーメッセージは表示されませんが、テキストタイプに定義されているもののみを駆動できます(つまり、マスクは機能し続けます)。
maxLength:500-最大テキスト長は500文字です。
separate:true-500分の1後に各文字をトリミングします。
モジュール自体には何がありますか:
text : function() { $("#"+this.id).live("paste", $.proxy(this.maskPasteText, this)); $("#"+this.id).live("keyup", $.proxy(this.validateText, this)); $("#"+this.id).live("blur", $.proxy(this.finishText, this)); },
ここで、検証メソッドとマスクを貼り付け、キーアップ、ぼかしイベントに添付します。
maskPasteText: function(event) { var context = this; setTimeout(function() { context.validateText(event); }, 0); },
データを挿入するとき、タイムアウトを切り、検証関数を呼び出します。これはbluetoothと同じです。
finishText: function(event) { this.validateText(event); },
実際には、テキスト検証関数自体は次のとおりです。
validateText: function(event) { var value = $("#"+this.id).val(), selectionStart = event.target.selectionStart, selectionEnd = event.target.selectionEnd; if (this.maxLength && this.separate) { value = value.slice(0, this.maxLength); $("#"+this.id).val(value); event.target.selectionStart = selectionStart, event.target.selectionEnd = selectionEnd; } this.bind("error", $.proxy(this.showError, this)); this.validate = this.validations()[this.type]; this.hideError(); this.set({ currentValue: value, required: this.required, errorMessage: this.errorMessage, minLength: this.minLength, maxLength: this.maxLength }); },
他のデータ型(たとえば、int、float)には入力マスクも追加する必要があることは明らかです;このために、keypressイベントの関数をハングさせます:
maskTypeInt : function (event) { if ( !(event.charCode >= 48 && event.charCode <= 57 || event.charCode === 0) ) { event.preventDefault(); } }, maskTypeFloat : function (event) { var value = $("#"+this.id).val(), dots = value.search(/\./ig), commas = value.search(/,/ig); if ( !( event.charCode >= 48 && event.charCode <= 57 || (event.charCode === 46 && dots === -1) || (event.charCode === 44 && dots === -1 && commas === -1) || event.charCode === 0) ) { event.preventDefault(); } }
現在、検証は次のデータ型に対して実装されています。
int
浮く
価格
電話、
テキスト
wordProcessor(tinyMCE検証用)、
コンボボックス、
フォーム(ここでは、複数のフィールドで検証が行われ、そのオプションはitems配列に渡され、ボタンがクリックされると起動され、ボタンIDが渡されます)。
ここで現在準備ができているモジュール機能を見ることができます 。
モジュール自体はまだ最終段階にあるため、コードは完全には削除されませんが、非常に読みやすくなっています。