1. 概述
當在 Java 中處理原始 JSON 值時,有時需要檢查其有效性。有幾個庫可以幫助我們完成此操作,包括 Gson、JSON API 和 Jackson。每種工具都有其自身的優勢和侷限性。
在本教程中,我們將使用每種工具對 JSON String 進行驗證,並深入瞭解不同方法的差異,並通過實際示例進行説明。
2. 使用 JSON API 進行驗證
最輕量級且簡單的庫是 JSON API。
檢查 String 是否為有效 JSON 的常見方法是異常處理。因此,我們委託 JSON 解析並處理因無效值而產生的特定類型錯誤,或者在未發生任何異常時假設值有效。
2.1. Maven 依賴
首先,我們需要在我們的 <em title="pom.xml">pom.xml</em > 中包含 `json 依賴:
<dependency>
<groupId>org.json</groupId>
<artifactId>json</artifactId>
<version>20211205</version>
</dependency>2.2. 使用 JSONObject 進行驗證
首先,為了檢查給定的 String 是否為有效的 JSON,我們將嘗試創建一個 JSONObject。 進一步,如果值為無效,將會拋出 JSONException 異常。
public boolean isValid(String json) {
try {
new JSONObject(json);
} catch (JSONException e) {
return false;
}
return true;
}讓我們用一個簡單的例子來試試:
String json = "{\"email\": \"example@com\", \"name\": \"John\"}";
assertTrue(validator.isValid(json));String json = "Invalid_Json";
assertFalse(validator.isValid(json));然而,這種方法的缺點是,String 只能是對象,而不能是數組,使用 JSONObject 無法實現。
例如,我們來看一下它在數組中的工作方式:
String json = "[{\"email\": \"example@com\", \"name\": \"John\"}]";
assertFalse(validator.isValid(json));2.3. 使用 JSONArray 進行驗證
為了無論 String 是否為對象或數組,都進行驗證,我們需要在 JSONObject 創建失敗時添加額外的條件。 同樣,當 JSONArray 檢測到 String 不適合作為 JSON 數組時,會拋出 JSONException 異常。
public boolean isValid(String json) {
try {
new JSONObject(json);
} catch (JSONException e) {
try {
new JSONArray(json);
} catch (JSONException ne) {
return false;
}
}
return true;
}因此,我們可以驗證任何值:
String json = "[{\"email\": \"example@com\", \"name\": \"John\"}]";
assertTrue(validator.isValid(json));3. 使用 Jackson 進行驗證
類似於 Jackson 庫,它提供了一種基於 異常處理 的方式來驗證 JSON 數據。 這是一個更復雜且具有多種解析策略的工具,但使用起來更加簡單。
3.1. Maven 依賴
讓我們添加 jackson-databind Maven 依賴:
<dependency>
<groupId>com.fasterxml.jackson.core</groupId>
<artifactId>jackson-databind</artifactId>
<version>2.13.0</version>
</dependency>3.2. 使用 ObjectMapper 進行驗證
我們使用 readTree() 方法讀取整個 JSON 並獲取如果語法不正確則返回 JacksonException。
換句話説,我們不需要提供額外的檢查。它適用於對象和數組:
ObjectMapper mapper = new ObjectMapper()
.enable(DeserializationFeature.FAIL_ON_TRAILING_TOKENS)
.build()
public boolean isValid(String json) {
try {
mapper.readTree(json);
} catch (JacksonException e) {
return false;
}
return true;
}讓我們看看如何使用以下示例:
String json = "{\"email\": \"example@com\", \"name\": \"John\"}";
assertTrue(validator.isValid(json));
String json = "[{\"email\": \"example@com\", \"name\": \"John\"}]";
assertTrue(validator.isValid(json));
String json = "Invalid_Json";
assertFalse(validator.isValid(json));請注意,我們還啓用了FAIL_ON_TRAILING_TOKENS選項,以確保驗證過程在有效JSON之後出現任何非空白文本時會失敗。
在沒有啓用此選項的情況下,格式為{"email": "example@com"}text的JSON仍然會被視為有效,儘管它實際上無效。
4. 使用 Gson 進行驗證
Gson 是另一個常用的庫,它允許我們使用相同的機制驗證原始 JSON 值。它是一個複雜的工具,用於 Java 對象映射以及不同類型的 JSON 處理。
4.1. Maven 依賴
讓我們添加 gson Maven 依賴:
<dependency>
<groupId>com.google.code.gson</groupId>
<artifactId>gson</artifactId>
<version>2.11.0</version>
</dependency>4.2. 寬鬆驗證 驗證
Gson 提供 JsonParser 用於將指定的 JSON 讀取為 JsonElement 的樹結構。因此,它保證在讀取過程中如果出現錯誤,我們會得到 JsonSyntaxException。
因此,我們可以使用 parse() 方法來計算 String 並處理在 JSON 值格式錯誤時發生的 Exception:
public boolean isValid(String json) {
try {
JsonParser.parseString(json);
} catch (JsonSyntaxException e) {
return false;
}
return true;
}讓我們編寫一些測試用例來檢查主要情況:
String json = "{\"email\": \"example@com\", \"name\": \"John\"}";
assertTrue(validator.isValid(json));
String json = "[{\"email\": \"example@com\", \"name\": \"John\"}]";
assertTrue(validator.isValid(json));這種方法的關鍵區別在於 Gson 的默認策略將單獨的字符串和數字值視為有效的 JsonElement 節點。換句話説,它將單個字符串或數字也視為有效值。
例如,我們來看一下它如何處理單個字符串:
String json = "Invalid_Json";
assertTrue(validator.isValid(json));然而,如果我們考慮這些值作為無效值,則需要對我們的 JsonParser 強制執行嚴格的類型策略。
4.3. 嚴格驗證
為了實施嚴格的類型策略,我們創建一個 TypeAdapter並定義 JsonElement類作為必需的類型匹配。 結果,JsonParser如果類型不是 JSON 對象或數組,將拋出 JsonSyntaxException。
我們可以調用 fromJson()方法來使用特定的 TypeAdapter讀取原始 JSON:
final TypeAdapter<JsonElement> strictAdapter = new Gson().getAdapter(JsonElement.class);
public boolean isValid(String json) {
try {
strictAdapter.fromJson(json);
} catch (JsonSyntaxException | IOException e) {
return false;
}
return true;
}最後,我們可以檢查 JSON 是否有效:
String json = "Invalid_Json";
assertFalse(validator.isValid(json));5. 結論
在本文中,我們探討了如何檢查字符串是否為有效的 JSON。
每種方法都有其自身的優勢和侷限性。儘管 JSON API 適用於簡單的對象驗證,Gson 則可以更靈活地用於原始值的驗證,作為 JSON 對象的一部分。然而,Jackson 更易於使用。因此,我們應該選擇最適合特定需求的方案。
此外,我們還應該檢查是否已經使用了某些庫,並將其應用於其他目標。