优雅!Spring Boot 3.3 搭配 JSON Schema 实现灵活的 JSON 数据定义与验证

科技   2024-10-21 07:30   河北  


优雅!Spring Boot 3.3 搭配 JSON Schema 实现灵活的 JSON 数据定义与验证

在现代互联网应用中,数据验证在提高数据质量和保证系统稳定性方面扮演着至关重要的角色。随着微服务架构的广泛应用,各个服务之间的通信和交互往往依赖 JSON 格式的数据。在这种场景下,确保接收到的 JSON 数据满足某些特定的格式和规则显得尤为重要。JSON Schema 是一种定义 JSON 数据结构的标准,能够有效帮助开发者验证传输数据的正确性。

运行效果:

若想获取项目完整代码以及其他文章的项目源码,且在代码编写时遇到问题需要咨询交流,欢迎加入下方的知识星球。

本篇文章将结合 Spring Boot 3.3 框架,介绍如何使用 JSON Schema Validator 进行灵活且强大的 JSON 数据定义与验证。我们将通过创建一个完整的前后端示例,展示如何优雅地管理和验证 JSON 数据。

项目结构

我们将创建一个简单的用户验证示例,包括后端的 JSON Schema 验证和前端的用户输入数据校验。项目结构如下:

json-schema-validator
├── pom.xml
├── src
│ ├── main
│ │ ├── java
│ │ │ └── com
│ │ │ └── icoderoad
│ │ │ └── jsonvalidator
│ │ │ ├── controller
│ │ │ │ └── JsonValidatorController.java
│ │ │ ├── service
│ │ │ │ └── JsonSchemaValidatorService.java
│ │ │ └── entity
│ │ │ └── User.java
│ │ ├── resources
│ │ │ ├── application.yml
│ │ │ ├── templates
│ │ │ │ └── index.html
│ │ │ └── schemas
│ │ │ └── user-schema.json

pom.xml 配置

首先在 pom.xml 中引入所需依赖,包括 Spring Boot Web、Lombok 和 JSON Schema Validator。

<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd">

<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>3.3.4</version>
<relativePath/> <!-- lookup parent from repository -->
</parent>
<groupId>com.icoderoad</groupId>
<artifactId>json-schema-validator</artifactId>
<version>0.0.1-SNAPSHOT</version>
<name>json-schema-validator</name>
<description>Demo project for Spring Boot</description>

<properties>
<java.version>17</java.version>
</properties>
<dependencies>
<!-- Spring Boot Web -->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>

<!-- Lombok -->
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
<scope>provided</scope>
</dependency>

<!-- JSON Schema Validator -->
<dependency>
<groupId>com.github.java-json-tools</groupId>
<artifactId>json-schema-validator</artifactId>
<version>2.2.14</version>
</dependency>

<!-- Thymeleaf 模板引擎 -->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-thymeleaf</artifactId>
</dependency>

<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
</dependencies>

<build>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
</plugin>
</plugins>
</build>

</project>

application.yml 配置

在 application.yml 文件中定义 JSON Schema 文件的路径,这里将其保存在 schemas/ 目录下。

server:
port: 8080

json:
schema-path: /schemas/user-schema.json

JSON Schema 文件

在 resources/schemas/ 目录下创建 user-schema.json 文件,定义用户 JSON 数据的规则:

{
"$schema": "http://json-schema.org/draft-07/schema#",
"title": "User",
"type": "object",
"properties": {
"name": {
"type": "string",
"minLength": 2,
"maxLength": 100
},
"age": {
"type": "integer",
"minimum": 0
},
"email": {
"type": "string",
"format": "email"
}
},
"required": ["name", "age", "email"]
}

该 schema 定义了 name(字符串类型,长度为 2-100 个字符)、age(整数类型,最小值为 0)、email(必须是有效的邮箱格式),并要求所有字段为必填。

配置类

通过 @ConfigurationProperties 读取 application.yml 中的 json.schema-path 配置。

package com.icoderoad.jsonvalidator.config;

import lombok.Data;
import org.springframework.boot.context.properties.ConfigurationProperties;
import org.springframework.context.annotation.Configuration;

@Data
@Configuration
@ConfigurationProperties(prefix = "json")
public class JsonSchemaProperties {
private String schemaPath;
}

实体类

创建用户实体类 User,使用 Lombok 简化代码:

package com.icoderoad.jsonvalidator.entity;

import lombok.Data;

@Data
public class User {
private String name;
private Integer age;
private String email;
}

服务类

实现 JSON Schema 验证逻辑,使用 json-schema-validator 库来解析和验证 JSON 数据。

package com.icoderoad.jsonvalidator.service;

import java.io.IOException;
import java.io.InputStream;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import com.fasterxml.jackson.databind.JsonNode;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.github.fge.jsonschema.core.exceptions.ProcessingException;
import com.github.fge.jsonschema.core.report.ProcessingReport;
import com.github.fge.jsonschema.main.JsonSchema;
import com.github.fge.jsonschema.main.JsonSchemaFactory;
import com.icoderoad.jsonvalidator.config.JsonSchemaProperties;

@Service
public class JsonSchemaValidatorService {

@Autowired
private JsonSchemaProperties jsonSchemaProperties;

private final ObjectMapper objectMapper = new ObjectMapper();

public ProcessingReport validateUserSchema(String jsonData) throws IOException {
// 读取 JSON Schema 文件
InputStream schemaStream = getClass().getResourceAsStream(jsonSchemaProperties.getSchemaPath());
JsonNode schemaNode = objectMapper.readTree(schemaStream);

// 创建 JSON Schema 对象
JsonSchemaFactory schemaFactory = JsonSchemaFactory.byDefault();
JsonSchema jsonSchema;
try {
jsonSchema = schemaFactory.getJsonSchema(schemaNode);
// 解析要验证的 JSON 数据
JsonNode jsonNode = objectMapper.readTree(jsonData);

// 执行验证
return jsonSchema.validate(jsonNode);
} catch (ProcessingException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
return null;

}
}

控制器类

优化后的控制器提供一个 POST 接口供前端验证 JSON 数据,并在返回结果时结合 Bootstrap风格进行提示展示。

package com.icoderoad.jsonvalidator.controller;

import com.github.fge.jsonschema.core.report.ProcessingReport;
import com.icoderoad.jsonvalidator.service.JsonSchemaValidatorService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.ResponseBody;

@Controller
public class JsonValidatorController {

@Autowired
private JsonSchemaValidatorService validatorService;

@GetMapping("/")
public String home() {
return "index";
}

@PostMapping("/validate")
@ResponseBody
public String validateJson(@RequestBody String userData, Model model) {
try {
ProcessingReport report = validatorService.validateUserSchema(userData);
if (report.isSuccess()) {
return "<div class='alert alert-success'>验证成功!</div>";
} else {
return "<div class='alert alert-danger'>验证失败:" + report.toString() + "</div>";
}
} catch (Exception e) {
return "<div class='alert alert-danger'>验证过程中出现错误:" + e.getMessage() + "</div>";
}
}
}

前端代码

前端使用 Thymeleaf 模板引擎,结合 jQuery 和 Bootstrap 创建表单,并调用后端接口来进行 JSON 验证。

在 src/main/resources/templates/ 目录下创建 index.html 文件。

<!DOCTYPE html>
<html xmlns:th="http://www.thymeleaf.org">
<head>
<meta charset="UTF-8">
<title>JSON Schema 验证</title>
<link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/bootstrap@5.1.3/dist/css/bootstrap.min.css">
<script src="https://code.jquery.com/jquery-3.6.0.min.js"></script>
</head>
<body>
<div class="container">
<h1>用户数据验证</h1>
<form id="userForm">
<div class="mb-3">
<label for="name" class="form-label">姓名</label>
<input type="text" class="form-control" id="name" name="name" required>
</div>
<div class="mb-3">
<label for="age" class="form-label">年龄</label>
<input type="number" class="form-control" id="age" name="age" required>
</div>
<div class="mb-3">
<label for="email" class="form-label">邮箱</label>
<input type="email" class="form-control" id="email" name="email" required>
</div>
<button type="submit" class="btn btn-primary">提交</button>
</form>
<div id="result"></div>
</div>

<script>
$('#userForm').submit(function (e) {
e.preventDefault();
var userData = {
name: $('#name').val(),
age: parseInt($('#age').val()),
email: $('#email').val()
};
$.ajax({
url: '/validate',
type: 'POST',
contentType: 'application/json',
data: JSON.stringify(userData),
success: function (response) {
$('#result').html(response);
},
error: function () {
$('#result').html("<div class='alert alert-danger'>请求失败!</div>");
}
});
});
</script>
</body>
</html>

结语

通过本文的示例,我们可以看到如何利用 Spring Boot 3.3 和 JSON Schema 有效地实现 JSON 数据的定义与验证。这种方法灵活、易于扩展,特别适合于需要动态处理和验证 JSON 数据的场景。JSON Schema 的使用不仅能确保数据的结构和完整性,还能帮助开发者在处理外部数据时提高安全性和可靠性。在未来的开发中,JSON Schema 还能与 API 文档、自动生成工具结合使用,进一步提升开发效率。


今天就讲到这里,如果有问题需要咨询,大家可以直接留言或扫下方二维码来知识星球找我,我们会尽力为你解答。


AI资源聚合站已经正式上线,该平台不仅仅是一个AI资源聚合站,更是一个为追求知识深度和广度的人们打造的智慧聚集地。通过访问 AI 资源聚合网站 https://ai-ziyuan.techwisdom.cn/,你将进入一个全方位涵盖人工智能和语言模型领域的宝藏库


作者:路条编程(转载请获本公众号授权,并注明作者与出处)

路条编程
路条编程是一个友好的社区,在这里你可以免费学习编程技能,我们旨在激励想学编程的人尝试新的想法和技术,在最短的时间学习到工作中使用到的技术!
 最新文章