Java 实现 RESTful 风格的 Web 服务详解
前言
RESTful(Representational State Transfer)风格的 API 已经成为现代 Web 服务的标准。它通过简单的 HTTP 方法和资源定位来提供了一种高度可扩展和易于维护的服务接口。Java 作为一种功能强大且广泛使用的编程语言,提供了多种框架来实现 RESTful API。本文将从设计概念、规范到实际案例,详细讲解如何在 Java 中构建 RESTful 风格的 Web 服务。
一、RESTful 的设计概念和准则
1.1 什么是 RESTful?
RESTful 是一种软件架构风格,通过 HTTP 协议来实现客户端和服务器之间的通信。它遵循以下几个核心概念:
- 无状态性(Statelessness):每个请求都包含执行请求所需的所有信息。服务器不存储客户端的上下文信息。
- 资源(Resource):每一个信息片段都是一个资源,如文档、图片、用户等。资源通过 URI(统一资源标识符)唯一标识。
- 表现(Representation):资源可以有多种表现形式,如 JSON、XML 等。客户端和服务器通过这些表现形式进行交互。
- 统一接口(Uniform Interface):采用标准的 HTTP 方法(如 GET、POST、PUT、DELETE)使得 API 的使用更加简单和一致。
- 超媒体即应用状态引擎(HATEOAS):API 应该返回超链接,使得客户端可以动态发现 API 的结构,而不需要事先了解 API 的所有细节。
1.2 RESTful 的准则
- 客户端-服务器架构:客户端和服务器是分离的,它们通过 HTTP 协议进行通信。
- 分层系统:系统可以由多个层组成,每一层只与上下层交互,增加了系统的灵活性和可扩展性。
- 可缓存性:响应可以被缓存,以提高性能和可扩展性。
二、RESTful API 设计规范
2.1 基础设计原则
- URI 设计:使用名词来表示资源,且使用复数形式,如
/users表示用户资源集合,/users/{id}表示单个用户资源。 - HTTP 方法的使用:
- GET:用于获取资源。
- POST:用于创建新的资源。
- PUT:用于更新已有资源(客户端提供完整资源数据)。
- PATCH:用于部分更新资源(客户端提供部分资源数据)。
- DELETE:用于删除资源。
- 状态码:使用标准的 HTTP 状态码来表示操作结果:
- 200 OK:请求成功。
- 201 Created:资源创建成功。
- 204 No Content:请求成功,但没有内容返回。
- 400 Bad Request:请求格式错误。
- 401 Unauthorized:未授权。
- 404 Not Found:资源未找到。
- 500 Internal Server Error:服务器内部错误。
2.2 安全性与认证
- HTTPS:使用 HTTPS 协议来保护数据传输安全。
- 认证机制:常用的认证机制包括 Basic Auth、OAuth、JWT(JSON Web Tokens)等。
- 输入验证:对客户端请求的数据进行严格的验证,防止恶意输入和数据污染。
2.3 版本控制
- URI 版本控制:在 URI 中包含版本号,如
/api/v1/users。 - Header 版本控制:使用自定义 HTTP Header 来标识版本,如
Accept: application/vnd.example.v1+json。
三、RESTful API 案例:用户管理系统
3.1 环境准备
- JDK 11+
- Maven
- Spring Boot
- IDE(如 IntelliJ IDEA 或 Eclipse)
3.2 项目结构
src
├── main
│ ├── java
│ │ └── com
│ │ └── example
│ │ └── demo
│ │ ├── DemoApplication.java
│ │ ├── controller
│ │ │ └── UserController.java
│ │ ├── model
│ │ │ └── User.java
│ │ └── service
│ │ └── UserService.java
│ └── resources
│ └── application.properties
└── test
3.3 实现步骤
3.3.1 创建实体类
创建一个 User 类来表示用户模型:
package com.example.demo.model;import lombok.Data;@Data
public class User {private Long id;private String name;private String email;
}
3.3.2 创建服务类
创建一个 UserService 类来处理用户相关的业务逻辑:
package com.example.demo.service;import com.example.demo.model.User;
import org.springframework.stereotype.Service;import java.util.ArrayList;
import java.util.List;
import java.util.concurrent.atomic.AtomicLong;@Service
public class UserService {private List<User> users = new ArrayList<>();private AtomicLong counter = new AtomicLong();public List<User> getAllUsers() {return users;}public User getUserById(Long id) {return users.stream().filter(user -> user.getId().equals(id)).findFirst().orElse(null);}public User createUser(User user) {user.setId(counter.incrementAndGet());users.add(user);return user;}public User updateUser(Long id, User updatedUser) {for (User user : users) {if (user.getId().equals(id)) {user.setName(updatedUser.getName());user.setEmail(updatedUser.getEmail());return user;}}return null;}public void deleteUser(Long id) {users.removeIf(user -> user.getId().equals(id));}
}
3.3.3 创建控制器
创建一个 UserController 类来处理 HTTP 请求:
package com.example.demo.controller;import com.example.demo.model.User;
import com.example.demo.service.UserService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.http.HttpStatus;
import org.springframework.http.ResponseEntity;
import org.springframework.web.bind.annotation.*;import java.util.List;@RestController
@RequestMapping("/api/v1/users")
public class UserController {@Autowiredprivate UserService userService;@GetMappingpublic ResponseEntity<List<User>> getAllUsers() {return new ResponseEntity<>(userService.getAllUsers(), HttpStatus.OK);}@GetMapping("/{id}")public ResponseEntity<User> getUserById(@PathVariable Long id) {User user = userService.getUserById(id);if (user != null) {return new ResponseEntity<>(user, HttpStatus.OK);} else {return new ResponseEntity<>(HttpStatus.NOT_FOUND);}}@PostMappingpublic ResponseEntity<User> createUser(@RequestBody User user) {User createdUser = userService.createUser(user);return new ResponseEntity<>(createdUser, HttpStatus.CREATED);}@PutMapping("/{id}")public ResponseEntity<User> updateUser(@PathVariable Long id, @RequestBody User updatedUser) {User user = userService.updateUser(id, updatedUser);if (user != null) {return new ResponseEntity<>(user, HttpStatus.OK);} else {return new ResponseEntity<>(HttpStatus.NOT_FOUND);}}@DeleteMapping("/{id}")public ResponseEntity<Void> deleteUser(@PathVariable Long id) {userService.deleteUser(id);return new ResponseEntity<>(HttpStatus.NO_CONTENT);}
}
3.3.4 启动应用
在 DemoApplication 类中,使用 @SpringBootApplication 注解启动 Spring Boot 应用:
package com.example.demo;import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;@SpringBootApplication
public class DemoApplication {public static void main(String[] args) {SpringApplication.run(DemoApplication.class, args);}
}
3.4 测试
运行 DemoApplication 类,应用将在默认的 8080 端口启动。可以使用 Postman 或 curl 工具测试 API。
-
获取所有用户:
GET http://localhost:8080/api/v1/users -
创建新用户:
POST http://localhost:8080/api/v1/users Content-Type: application/json{"name": "John Doe","email": "john.doe@example.com" } -
根据 ID 获取用户:
GET http://localhost:8080/api/v1/users/{id} -
更新用户:
PUT http://localhost:8080/api/v1/users/{id} Content-Type: application/json{"name": "Jane Doe","email": "jane.doe@example.com" } -
删除用户:
DELETE http://localhost:8080/api/v1/users/{id}
四、总结
通过本文的讲解,我们了解了 RESTful API 的设计概念和准则,掌握了 RESTful API 的设计规范,并通过一个实际案例展示了如何在 Java 中使用 Spring Boot 框架来构建 RESTful 风格的 Web 服务。希望通过这些内容,你能更好地理解和应用 RESTful API,从而在实际项目中构建出高效、可扩展的 Web 服务。
相关文章:
Java 实现 RESTful 风格的 Web 服务详解
前言 RESTful(Representational State Transfer)风格的 API 已经成为现代 Web 服务的标准。它通过简单的 HTTP 方法和资源定位来提供了一种高度可扩展和易于维护的服务接口。Java 作为一种功能强大且广泛使用的编程语言,提供了多种框架来实现…...
18.网工入门篇--------今天介绍下广域网技术
广域网(Wide Area Network,WAN)是一种能连接多个城市、国家甚至横跨几个洲,提供远距离通信的网络。以下是关于广域网技术的详细介绍: 广域网的组成: 结点交换机:这是广域网的核心设备࿰…...
鸿蒙原生应用开发及部署:首选华为云,开启HarmonyOS NEXT App新纪元
目录 前言 HarmonyOS NEXT:下一代操作系统的愿景 1、核心特性和优势 2、如何推动应用生态的发展 3、对开发者和用户的影响 华为云服务在鸿蒙原生应用开发中的作用 1、华为云ECS C系列实例 (1)全维度性能升级 (2ÿ…...
Spring JdbcTemplate详解
文章目录 Spring JdbcTemplate详解一、引言二、配置JdbcTemplate1、引入依赖2、配置数据库连接池3、配置JdbcTemplate 三、使用JdbcTemplate操作数据库1、添加数据2、查询数据查询某个值根据条件查询返回某个对象查询对象集合 四、总结 Spring JdbcTemplate详解 一、引言 在J…...
Docker篇(Docker安装)
目录 一、Centos7.x 1. yum 包更新到最新 2. 安装需要的软件包 3. 设置 yum 源为阿里云 4. 安装docker 5. 安装后查看docker版本 6. 设置ustc镜像源 二、CentOS安装Docker 前言 1. 卸载(可选) 2. 安装docker 3. 启动docker 4. 配置镜像加速 …...
Pytorch 实现图片分类
CNN 网络适用于图片识别,卷积神经网络主要用于图片的处理识别。卷积神经网络,包括一下几部分,输入层、卷积层、池化层、全链接层和输出层。 使用 CIFAR-10 进行训练, CIFAR-10 中图片尺寸为 32 * 32。卷积层通过卷积核移动进行计…...
得物App获评新奖项,正品保障夯实供应链创新水平
近日,得物App再度获评新奖项——“2024上海市供应链创新与应用优秀案例”。 本次奖项为上海市供应链领域最高奖项,旨在评选出在供应链创新成效上处于领先地位、拥有成功模式和经验的企业。今年以来,得物App已接连获得“上海市质量金奖”、“科…...
【数据结构-邻项消除】力扣735. 小行星碰撞
给定一个整数数组 asteroids,表示在同一行的小行星。 对于数组中的每一个元素,其绝对值表示小行星的大小,正负表示小行星的移动方向(正表示向右移动,负表示向左移动)。每一颗小行星以相同的速度移动。 找…...
002-Kotlin界面开发之Kotlin旋风之旅
Kotlin旋风之旅 Compose Desktop中哪些Kotlin知识是必须的? 在学习Compose Desktop中,以下Kotlin知识是必须的: 基础语法:包括变量声明、数据类型、条件语句、循环等。面向对象编程:类与对象、继承、接口、抽象类等。…...
VMware Workstation Pro for Personal Use (For Windows)
这是从broadcom.com网下载的个人版本的Vmware 17.6.1,存分享不要分。 VMware-workstation-full-17.6.1-24319023.exe(447.93 MB) Build Number: 24319023 Oct 08, 2024 07.33AM SHA2: f95429e395a583eb5ba91f09b040e2f8c53a5e7aa37c4c6bfcaf82115a8…...
论文 | PROMPTAGATOR : FEW-SHOT DENSE RETRIEVAL FROM 8 EXAMPLES
1. 背景信息 在信息检索领域,传统的方法往往依赖于大量的标注数据来训练模型,以便在各种任务中表现良好。然而,许多实际应用中的监督数据是有限的,尤其是在不同的检索任务中。最近的研究开始关注如何从一个拥有丰富监督数据的任务…...
使用 Github 进行项目管理
GitHub 是一个广泛使用的代码托管和协作平台,它提供了强大的工具来支持项目管理和团队协作。在项目开发和工作中,避免不了 Github 的使用,然鹅我一直没有稍微系统地学习过 github 的整个工作流程,对这些操作都是一知半解的&#x…...
企业SRC挖掘选择与信息收集指南
内容预览 ≧∀≦ゞ 企业SRC挖掘选择与信息收集指南导语1. 企业SRC的选择2. 信息收集2.1 集团与子公司2.2 小程序与APP2.3 Web端信息收集 3. 信息收集常用模板总结 企业SRC挖掘选择与信息收集指南 导语 近年来,企业的安全响应中心(SRC)已逐渐…...
Golang | Leetcode Golang题解之第524题通过删除字母匹配到字典里最长单词
题目: 题解: func findLongestWord(s string, dictionary []string) (ans string) {m : len(s)f : make([][26]int, m1)for i : range f[m] {f[m][i] m}for i : m - 1; i > 0; i-- {f[i] f[i1]f[i][s[i]-a] i}outer:for _, t : range dictionary …...
【DBeaver】连接带kerberos的hive[Apache|HDP]
目录 一、安装配置Kerberos客户端环境 1.1 安装Kerberos客户端 1.2 环境配置 二、基于Cloudera驱动创建连接 三、基于Hive原生驱动创建连接 一、安装配置Kerberos客户端环境 1.1 安装Kerberos客户端 在Kerberos官网下载,地址如下:https://web.mit.edu/kerberos…...
Unity3D 开发教程:从入门到精通
Unity3D 开发教程:从入门到精通 Unity3D 是一款强大的跨平台游戏引擎,广泛应用于游戏开发、虚拟现实、增强现实等领域。本文将详细介绍 Unity3D 的基本概念、开发流程以及一些高级技巧,帮助你从零基础到掌握 Unity3D 开发。 目录 Unity3D…...
文件操作和 IO(一):文件基础知识 文件系统操作 => File类
目录 1. 什么是文件 1.1 概念 1.2 硬盘, 内存, 寄存器之间的区别 1.3 机械硬盘和固态硬盘 2. 文件路径 2.1 绝对路径 2.2 相对路径 3. 文件分类 4. File 类 4.1 属性 4.2 构造方法 4.3 方法 1. 什么是文件 1.1 概念 狭义上的文件: 保存在硬盘上的文件广义的上的文…...
用Pyhon写一款简单的益智类小游戏——2048
文字版——代码及讲解 代码—— import random# 初始化游戏棋盘 def init_board():return [[0] * 4 for _ in range(4)]# 在棋盘上随机生成一个2或4 def add_new_tile(board):empty_cells [(i, j) for i in range(4) for j in range(4) if board[i][j] 0]if empty_cells:i,…...
akshare股票涨跌幅自定义范围查询:A股、港股、美股
参看:https://stock.hexun.com/2024-10-31/215251914.html 涨幅计算公式:(当前价格 - 上一个交易日收盘价) 上一个交易日收盘价 100% 。 跌幅计算公式:(上一个交易日收盘价 - 当前价格) 上一个…...
通过js控制修改css变量
在JavaScript中,你可以通过操作CSS变量(也称为自定义属性)来动态改变样式。CSS变量在CSS中使用 – 前缀定义,例如 --main-color: red;。在JavaScript中,你可以使用 document.documentElement.style.setProperty 方法来…...
解放知识资产:dedao-dl让你的得到课程永久保存成为可能
解放知识资产:dedao-dl让你的得到课程永久保存成为可能 【免费下载链接】dedao-dl 得到 APP 课程下载工具,可在终端查看文章内容,可生成 PDF,音频文件,markdown 文稿,可下载电子书。 项目地址: https://g…...
全介质超构透镜模型实现偏振成像:实时分离聚焦与偏振信息解码
偏振成像 超构透镜模型 超表面 FDTD仿真 复现论文:2019年 APL Midinfrared real-time polarization imaging with all-dielectric metasurfaces 论文介绍:全介质实时偏振聚焦成像超构透镜模型,可以实现X Y RCP LCP四个偏振态的实时分离和聚焦…...
[Python3高阶编程] - 高阶函数一:常见的高阶函数
一、常见的高阶函数Python 中的高阶函数(Higher-Order Function)是指接收函数作为参数或返回一个函数的函数。Python 内置了大量高阶函数,下面按来源分类尽量列全:1. 内置高阶函数函数作用map(func, *iterables)将函数逐个作用于可…...
FigmaCN终极指南:3分钟实现Figma全界面汉化,设计师效率提升50%
FigmaCN终极指南:3分钟实现Figma全界面汉化,设计师效率提升50% 【免费下载链接】figmaCN 中文 Figma 插件,设计师人工翻译校验 项目地址: https://gitcode.com/gh_mirrors/fi/figmaCN 你是否曾在使用Figma时因为英文界面而感到困扰&am…...
XCOM 2模组管理终极解决方案:Alternative Mod Launcher全攻略
XCOM 2模组管理终极解决方案:Alternative Mod Launcher全攻略 【免费下载链接】xcom2-launcher The Alternative Mod Launcher (AML) is a replacement for the default game launchers from XCOM 2 and XCOM Chimera Squad. 项目地址: https://gitcode.com/gh_mi…...
Clawdbot汉化版实测:免费、私密的AI助手如何无缝接入企业微信
Clawdbot汉化版实测:免费、私密的AI助手如何无缝接入企业微信 1. 为什么选择Clawdbot汉化版 企业微信作为国内主流办公平台,每天承载着大量沟通协作需求。传统AI助手往往面临三大痛点:数据隐私顾虑、平台切换繁琐、响应速度受限。Clawdbot汉…...
通义千问1.8B模型应用场景:智能客服搭建,简单高效
通义千问1.8B模型应用场景:智能客服搭建,简单高效 1. 为什么选择通义千问1.8B搭建智能客服 智能客服已经成为企业提升服务效率、降低运营成本的重要工具。传统智能客服系统往往面临响应速度慢、理解能力有限、部署复杂等问题。通义千问1.5-1.8B-Chat-G…...
小白必看:霜儿-汉服-造相Z-Turbo常见问题与解决技巧
小白必看:霜儿-汉服-造相Z-Turbo常见问题与解决技巧 1. 镜像部署与启动问题 1.1 如何确认服务已正常启动 首次启动镜像时,模型加载可能需要3-5分钟时间。执行以下命令查看服务状态: cat /root/workspace/xinference.log成功启动的标志是日…...
使用VSCode开发AI股票分析师daily_stock_analysis插件的实践
使用VSCode开发AI股票分析师daily_stock_analysis插件的实践 1. 引言 作为一名金融科技开发者,你是否曾经为每天需要手动分析大量股票数据而感到头疼?传统的股票分析工具往往只能提供基础的数据展示,而真正的分析决策仍需人工完成。现在&am…...
OpenClaw语音交互扩展:Qwen3-14b_int4_awq对接Whisper实现语音指令
OpenClaw语音交互扩展:Qwen3-14b_int4_awq对接Whisper实现语音指令 1. 为什么需要语音交互能力 作为一个长期依赖键盘输入的开发者,我最初对语音交互持怀疑态度——直到上个月连续加班导致手腕腱鞘炎发作。当连敲空格键都变成折磨时,才意识…...
