JSON Schema與表單驗證

做者:神機算子,美團金融前端團隊成員。喜歡簡單,樂於編程,富有激情的前端開發者。前端

表單驗證是一個前端常聊的問題,在這個問題上實際上已經有不少種方案了,大致來講有如下兩種:node

  • 本身定義驗證原語,進行簡單封裝,按需定製。這個方案好在對於簡單的小表單上手快,幾經提煉能夠造成本身的驗證庫,也能夠代碼保持的精簡。可是出現跨項目複用的時候,容易出現須要補充大量新場景的狀況,並且穩定性也不容易保證。
  • 使用市面上已有的表單驗證庫。這個方案能秒殺大部分場景,但可定製性每每比較差,有些驗證庫方案甚至是基於某種組件庫的。另外一方面,一旦開始使用某種驗證庫,將來想要切換就很是棘手。

那麼這裏說的方案是否能超越這兩種方案呢?這要從JSON Schema自己是什麼提及。webpack

JSON Schema是一種用JSON數據來描述須要驗證的JSON的格式。利用這種格式,能夠作到:git

  • 有據可依。每一種驗證方式都有固定的寫法,即便某一天跨語言,也只需很小的遷移成本。
  • 一應俱全。JSON Schema是一個在不斷髮展的標準,基本上你想要的驗證方法都在裏面囊括了。
  • 文本爲準。JSON自己只是一段文本,所以這種驗證方法無需特別的工具便可編寫,也很利於保存和分享。

ajv是JS實現的JSON Schema庫。目前來講,它的性能和標準實現覆蓋都比較好,具體能夠看它項目主頁的自我宣傳。github

在不使用任何驗證庫、驗證工具的狀況下,要驗證表單須要逐個字段進行讀取、判斷。表單字段越多,代碼的複雜度就越高,並且若是多個表單存在必定的共性,如何複用表單驗證也是一個麻煩事。
好比:web

圖1
圖1

單從可讀性來講,這段代碼很是易讀,由於它足夠直白、簡單,但若是全部的表單驗證都這樣作,很是容易出錯,也不便於維護。編程

ajv自己只是一個驗證工具,這個工具接受一個JSON Schema和你的目標數據,而後返回驗證結果。和其餘不少驗證工具相似,ajv提供了默認的報錯文案,默認狀況下是英文的。json

不過這個沒法知足產品對錶單驗證的需求。理想的表單驗證明際上包含如下需求:數組

  • 對於每一個異常的字段,都須要指出其錯誤
  • 錯誤須要是產品本身所但願的文案,而不是某種庫的內置文案,更別說是英文或者代碼中的字段名了
  • 表單驗證須要是有序的。直覺上來講,表單驗證須要先報頁面上最頂端的字段的問題。

對於第一點,ajv完善提供了錯誤信息。但對於第二點,ajv沒有提供比較好的方式來處理,由於它的報錯信息是很是程式化的,對於某一類錯誤,它的文案都是套路。
針對這一點,引入ajv-errors就比較合理了。ajv-errors須要開發在原有的schema中增長一個自定義字段,這個字段對每一種報錯均可以定製本身的報錯文案,大體以下:瀏覽器

圖2
圖2

圖中errorMessage字段是ajv-errors須要的字段。
這樣一來,報錯文案的可定製性就很是強了。
那順序如何保證呢?
通常來講,JSON Schema中若是要驗證一個Object的屬性,是沒有顯式順序的,這個就好像Object在遍歷時自己就沒有順序同樣。在界面上每一個字段的位置,對於JSON Schema來講是透明的,無關的。

幸虧ajv的報錯是數組形式返回的。儘管數組的順序在文檔中沒有明確指出,但這個報錯的格式很是友好,它會代表本身是哪一個字段。根據這一點,開發只需對報錯數組進行一次排序便可,大體以下:

圖3
圖3

圖的頂端指定了字段的順序,而尾端則使用這個順序進行了排序。

完美,產品全部的需求都搞定了。

但做爲一個合格的前端工程師,我本身是不能就這樣收工的。實際上在引入了ajv和ajv-errors以後,前端的JS資源在minify以後膨脹了100KB左右,即便由於gzip可以作到只增長數十KB,這個結果也是不太理想的——太大了。

針對這個狀況,若是退一步做爲任意項目來對待,那可能我比較想要的作法是將這兩個庫都進行異步按需加載。這樣作的話,多出來的尺寸基本上不會對首次加載形成影響,並且也足夠靈活。

可是咱們這個項目受限於現有發佈系統,沒有辦法支持webpack的異步按需加載。這怎麼搞?

我本身的想法是,將驗證挪到node當中去作,讓服務器完成這個過程,並將結果返回。

方案是:node端當中內置若干schema,並對每一個schema命名,新加一個接口;瀏覽器端將須要驗證的數據和schema的名字發送到node端,並取回驗證結果。

從某種角度來講,這也是一種按需加載。粗略來看,這個驗證在瀏覽器端可能會被惡意用戶跳過,但只要你提交數據的接口最終沒有完善的驗證,那其餘任何地方所增長的驗證都是能夠被繞過的,放在瀏覽器仍是node,也就沒什麼區別了。

從長遠來看,這個驗證的過程也能夠再追加到業務接口上,這樣就沒法被繞過了。

最後回過頭來看,基於JSON Schema的表單驗證方案不只可以解決咱們在表單驗證上的基本需求,同時也在穩定性、可擴展性等方面有必定優點,適合於絕大部分表單驗證的場景。

最後,團隊爲了招聘方便,整了個公衆號,主要是一些招聘信息,團隊信息,全部的技術文章在公衆號裏也能夠看到,對了,若是你想去美團其餘團隊,咱們也能夠幫你內推哦 ~

二維碼
二維碼
相關文章
相關標籤/搜索