当前位置: 首页 > news >正文

Spring Boot + MyBatis + MySQL:快速搭建CRUD应用

一、引言

1. 项目背景与目标

在现代Web开发中,CRUD(创建、读取、更新、删除)操作是几乎所有应用程序的核心功能。本项目旨在通过Spring Boot、MyBatis和MySQL技术栈,快速搭建一个高效、简洁的CRUD应用。我们将从零开始,逐步实现一个用户管理系统的增删改查功能。

2. 技术选型与适用场景

  • Spring Boot:简化了基于Spring的应用开发,提供了自动配置、嵌入式服务器等特性。
  • MyBatis:作为持久层框架,支持自定义SQL、存储过程和高级映射,灵活性高。
  • MySQL:广泛使用的开源关系型数据库,性能稳定,社区活跃。

二、开发环境准备

1. 开发工具与依赖安装

  • JDK:确保已安装Java Development Kit(建议版本8及以上)。
  • Maven/Gradle:用于项目构建和依赖管理。
  • IDE:推荐使用IntelliJ IDEA或Eclipse。
  • MySQL:下载并安装MySQL数据库,配置好数据库连接信息。

2. Spring Boot项目初始化

  • 使用 Spring Initializr 创建项目:
    • Project: Maven Project
    • Language: Java
    • Spring Boot: 最新稳定版本
    • Dependencies: Spring Web, MyBatis Framework, MySQL Driver

三、数据库设计与初始化

1. MySQL数据库表设计

创建一个简单的用户表user,包含以下字段:

CREATE TABLE user (id INT AUTO_INCREMENT PRIMARY KEY,username VARCHAR(50) NOT NULL UNIQUE,password VARCHAR(100) NOT NULL,email VARCHAR(100),created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP
);

2. 数据初始化脚本

src/main/resources目录下创建data.sql文件,插入一些测试数据:

INSERT INTO user (username, password, email) VALUES 
('admin', 'password123', 'admin@example.com'),
('user1', 'password123', 'user1@example.com');

配置application.yml中的数据库连接信息:

spring:datasource:url: jdbc:mysql://localhost:3306/mydb?useSSL=false&serverTimezone=UTCusername: rootpassword: rootdriver-class-name: com.mysql.cj.jdbc.Driver

四、Spring Boot与MyBatis集成

1. MyBatis基础配置

application.yml中添加MyBatis配置:

mybatis:mapper-locations: classpath:mapper/*.xmltype-aliases-package: com.example.demo.entity

2. 实体类与Mapper接口开发

  • 实体类:创建User类表示用户信息。

    package com.example.demo.entity;public class User {private Integer id;private String username;private String password;private String email;private Timestamp createdAt;// Getters and Setters
    }
    
  • Mapper接口:创建UserMapper接口及对应的XML映射文件。

    package com.example.demo.mapper;import org.apache.ibatis.annotations.Mapper;
    import org.apache.ibatis.annotations.Select;@Mapper
    public interface UserMapper {@Select("SELECT * FROM user WHERE id = #{id}")User findById(Integer id);
    }
    

    src/main/resources/mapper目录下创建UserMapper.xml

    <?xml version="1.0" encoding="UTF-8" ?>
    <!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN""http://mybatis.org/dtd/mybatis-3-mapper.dtd">
    <mapper namespace="com.example.demo.mapper.UserMapper"><select id="findById" resultType="com.example.demo.entity.User">SELECT * FROM user WHERE id = #{id}</select>
    </mapper>
    

3. Service层与Controller层实现

  • Service层:封装业务逻辑。

    package com.example.demo.service;import com.example.demo.entity.User;
    import com.example.demo.mapper.UserMapper;
    import org.springframework.beans.factory.annotation.Autowired;
    import org.springframework.stereotype.Service;@Service
    public class UserService {@Autowiredprivate UserMapper userMapper;public User getUserById(Integer id) {return userMapper.findById(id);}
    }
    
  • Controller层:提供RESTful API接口。

    package com.example.demo.controller;import com.example.demo.entity.User;
    import com.example.demo.service.UserService;
    import org.springframework.beans.factory.annotation.Autowired;
    import org.springframework.web.bind.annotation.GetMapping;
    import org.springframework.web.bind.annotation.PathVariable;
    import org.springframework.web.bind.annotation.RestController;@RestController
    public class UserController {@Autowiredprivate UserService userService;@GetMapping("/users/{id}")public User getUser(@PathVariable Integer id) {return userService.getUserById(id);}
    }
    

五、CRUD功能实现

1. 创建(Create)功能

  • Mapper接口:添加插入数据的方法。

    @Insert("INSERT INTO user (username, password, email) VALUES (#{username}, #{password}, #{email})")
    void insertUser(User user);
    
  • Service层:实现新增用户逻辑。

    public void createUser(User user) {userMapper.insertUser(user);
    }
    
  • Controller层:提供新增用户的API接口。

    @PostMapping("/users")
    public void createUser(@RequestBody User user) {userService.createUser(user);
    }
    

2. 读取(Read)功能

  • 分页查询:使用MyBatis分页插件PageHelper。
    <select id="findAllUsers" resultType="com.example.demo.entity.User">SELECT * FROM user
    </select>
    
  PageHelper.startPage(pageNum, pageSize);List<User> users = userMapper.findAllUsers();PageInfo<User> pageInfo = new PageInfo<>(users);
  • 动态条件查询:按用户名模糊搜索。
    <select id="findUsersByUsername" resultType="com.example.demo.entity.User">SELECT * FROM user WHERE username LIKE CONCAT('%', #{username}, '%')
    </select>
    

3. 更新(Update)功能

  • Mapper接口:添加更新数据的方法。

    @Update("UPDATE user SET username=#{username}, password=#{password}, email=#{email} WHERE id=#{id}")
    void updateUser(User user);
    
  • Service层:实现更新用户逻辑。

    public void updateUser(User user) {userMapper.updateUser(user);
    }
    
  • Controller层:提供更新用户的API接口。

    @PutMapping("/users/{id}")
    public void updateUser(@PathVariable Integer id, @RequestBody User user) {user.setId(id);userService.updateUser(user);
    }
    

4. 删除(Delete)功能

  • 硬删除:直接从数据库中删除记录。

    @Delete("DELETE FROM user WHERE id=#{id}")
    void deleteUserById(Integer id);
    
  • 软删除:添加is_deleted字段标记删除状态。

    ALTER TABLE user ADD COLUMN is_deleted TINYINT DEFAULT 0;
    
  @Update("UPDATE user SET is_deleted=1 WHERE id=#{id}")void softDeleteUserById(Integer id);

六、功能扩展与优化

1. 事务管理

  • @Transactional注解:确保多个操作在同一事务中执行。
    @Service
    @Transactional
    public class UserService {// CRUD方法
    }
    

2. 分页与排序

  • PageHelper分页插件:实现分页查询。

    <dependency><groupId>com.github.pagehelper</groupId><artifactId>pagehelper-spring-boot-starter</artifactId><version>1.4.0</version>
    </dependency>
    
  • 排序参数动态传入:根据请求参数进行排序。

    PageHelper.startPage(pageNum, pageSize).setOrderBy(orderBy);
    

3. 异常处理

  • 全局异常捕获:使用@ControllerAdvice处理全局异常。
    @ControllerAdvice
    public class GlobalExceptionHandler {@ExceptionHandler(Exception.class)public ResponseEntity<String> handleException(Exception e) {return ResponseEntity.status(HttpStatus.INTERNAL_SERVER_ERROR).body(e.getMessage());}
    }
    

七、测试与部署

1. 单元测试与集成测试

  • 单元测试:编写Mapper接口测试用例。

    @RunWith(SpringRunner.class)
    @SpringBootTest
    public class UserMapperTest {@Autowiredprivate UserMapper userMapper;@Testpublic void testFindById() {User user = userMapper.findById(1);assertNotNull(user);}
    }
    
  • 集成测试:验证CRUD功能完整性。

    @RunWith(SpringRunner.class)
    @SpringBootTest(webEnvironment = SpringBootTest.WebEnvironment.RANDOM_PORT)
    public class UserControllerIT {@Autowiredprivate TestRestTemplate restTemplate;@Testpublic void testGetUser() {ResponseEntity<User> response = restTemplate.getForEntity("/users/1", User.class);assertEquals(HttpStatus.OK, response.getStatusCode());}
    }
    

2. 项目打包与部署

  • 打包为可执行JAR文件

    mvn clean package
    
  • 部署到本地Tomcat或云服务器

    • 将生成的JAR文件上传至服务器,并通过命令启动:
      java -jar myapp.jar
      

相关文章:

Spring Boot + MyBatis + MySQL:快速搭建CRUD应用

一、引言 1. 项目背景与目标 在现代Web开发中&#xff0c;CRUD&#xff08;创建、读取、更新、删除&#xff09;操作是几乎所有应用程序的核心功能。本项目旨在通过Spring Boot、MyBatis和MySQL技术栈&#xff0c;快速搭建一个高效、简洁的CRUD应用。我们将从零开始&#xff…...

python中os库的常用举例

os 库是Python中用于与操作系统进行交互的标准库&#xff0c;以下是一些 os 库的常用示例&#xff1a; 获取当前工作目录 python import os current_dir os.getcwd() print(current_dir) os.getcwd() 函数用于获取当前工作目录的路径。 列出目录内容 python import os …...

Unity 通用UI界面逻辑总结

概述 在游戏开发中&#xff0c;常常会遇到一些通用的界面逻辑&#xff0c;它不论在什么类型的游戏中都会出现。为了避免重复造轮子&#xff0c;本文总结并提供了一些常用UI界面的实现逻辑。希望可以帮助大家快速开发通用界面模块&#xff0c;也可以在次基础上进行扩展修改&…...

Python3 与 VSCode:深度对比分析

Python3 与 VSCode:深度对比分析 引言 Python3 和 Visual Studio Code(VSCode)在软件开发领域扮演着举足轻重的角色。Python3 作为一门强大的编程语言,拥有丰富的库和框架,广泛应用于数据科学、人工智能、网络开发等多个领域。而 VSCode 作为一款轻量级且功能强大的代码…...

第五课:Express框架与RESTful API设计:技术实践与探索

在使用Node.js进行企业应用开发&#xff0c;常用的开发框架Express&#xff0c;其中的中间件、路由配置与参数解析、RESTful API核心技术尤为重要&#xff0c;本文将深入探讨它们在应用开发中的具体使用方法&#xff0c;最后通过Postman来对开发的接口进行测试。 一、Express中…...

Linux 内核自定义协议族开发:从 “No buffer space available“ 错误到解决方案

引言 在 Linux 内核网络协议栈开发中,自定义协议族(Address Family, AF)是实现新型通信协议或扩展内核功能的关键步骤。然而,开发者常因对内核地址族管理机制理解不足,遇到如 insmod: No buffer space available 的错误。本文将以实际案例为基础,深入分析错误根源,并提…...

html-列表标签和表单标签

一、列表标签 表格是用来显示数据的,那么列表就是用来布局的 列表最大的特点就是整齐&#xff64;整洁&#xff64;有序,它作为布局会更加自由和方便&#xff61; 根据使用情景不同,列表可以分为三大类:无序列表&#xff64;有序列表和自定义列表&#xff61; 1.无序列表(重…...

HTML-网页介绍

一、网页 1.什么是网页&#xff1a; 网站是指在因特网上根据一定的规则&#xff0c;使用 HTML 等制作的用于展示特定内容相关的网页集合。 网页是网站中的一“页”&#xff0c;通常是 HTML 格式的文件&#xff0c;它要通过浏览器来阅读。 网页是构成网站的基本元素&#xf…...

动态ip和静态ip适用于哪个场景?有何区别

在数字化浪潮席卷全球的今天&#xff0c;IP地址作为网络世界的“门牌号”&#xff0c;其重要性不言而喻。然而&#xff0c;面对动态IP与静态IP这两种截然不同的IP分配方式&#xff0c;许多用户往往感到困惑&#xff1a;它们究竟有何区别&#xff1f;又分别适用于哪些场景呢&…...

android13打基础: 保存用户免得下次重新登录逻辑

使用SP来做 创建LoginUser.kt // 登录用户需要Email data class LoginUser(val email: String,val password: String, )创建假数据FakeLoginUser.kt object FakeLoginUser {val fake_login_user_items arrayListOf(LoginUser(email "1690544550qq.com",password …...

Linux 4.4 内核源码的目录结构及其主要内容的介绍

以下是 Linux 4.4 内核源码的目录结构及其主要内容的介绍,适用于理解内核模块和驱动开发的基本框架: Linux 4.4 内核源码目录结构 目录作用与内容arch/平台架构相关代码每个子目录对应一种 CPU 架构(如 x86/、arm/、arm64/),包含硬件相关的启动逻辑、中断处理、内存管理等…...

手脑革命:拆解Manus AI如何用“执行智能体”重构生产力——中国团队突破硅谷未竟的技术深水区

第一章&#xff1a;Manus AI 的技术演进与行业背景 1.1 从工具到智能体&#xff1a;AI 技术的范式跃迁 人工智能的发展经历了从规则驱动&#xff08;Rule-based&#xff09;到统计学习&#xff08;Statistical Learning&#xff09;&#xff0c;再到深度学习&#xff08;Deep…...

Android 调用c++报错 exception of type std::bad_alloc: std::bad_alloc

一、报错信息 terminating with uncaught exception of type std::bad_alloc: std::bad_alloc 查了那部分报错c++代码 szGridSize因为文件太大,初始化溢出了 pEGM->pData = new float[szGridSize]; 解决办法 直接抛出异常,文件太大就失败吧 最后还增加一个日志输出,给…...

匿名GitHub链接使用教程(Anonymous GitHub)2025

Anonymous GitHub 1. 引言2. 准备3. 进入Anonymous GitHub官网4. 用GitHub登录匿名GitHub并授权5. 进入个人中心&#xff0c;然后点击• Anonymize Repo实例化6. 输入你的GitHub链接7. 填写匿名链接的基础信息8. 提交9. 实例化对应匿名GitHub链接10. 进入个人中心管理项目11. 查…...

【0基础跟AI学软考高项】成本管理

&#x1f4b0;「成本管理」是什么&#xff1f;‌ ‌一句话解释‌&#xff1a;像家庭装修控制预算&#xff0c;既要买得起好材料&#xff0c;又要避免超支吃泡面——成本管理就是精准算钱、合理花钱、动态盯钱&#xff0c;保证项目不破产&#xff01; &#x1f30b; ‌真实案例…...

模型的原始输出为什么叫 logits

模型的原始输出为什么叫 logits flyfish 一、Logarithm&#xff08;对数 log&#xff09; 定义&#xff1a;对数是指数运算的逆运算&#xff0c;表示某个数在某个底数下的指数。 公式&#xff1a;若 b x a b^x a bxa&#xff0c;则 log ⁡ b ( a ) x \log_b(a) x logb…...

[SAP MM] 查看物料主数据的物料类型

创建物料主数据时&#xff0c;必须为物料分配物料类型&#xff0c;如原材料或半成品 在标准系统中&#xff0c;物料类型ROH(原材料)的所有物料都要从外部采购&#xff0c;而类型为NLAG(非库存物料)的物料则可从外部采购也可在内部生产 ① 特殊物料类型&#xff1a;NLAG 该物料…...

风控模型算法面试题集结

特征处理 1. 特征工程的一般步骤什么?什么是特征迭代 特征工程一般包含: 数据获取,分析数据的可用性(覆盖率,准确率,获取容易程度)数据探索,分析数据业务含义,对特征有一个大致了解,同时进行数据质量校验,包含缺失值、异常值和一致性等;特征处理,包含数据处理和…...

PX4中的DroneCAN的实现库Libuavcan及基础功能示例

简介 Libuavcan是一个用C编写的可移植的跨平台库&#xff0c;对C标准库的依赖小。它可以由几乎任何符合标准的C编译器编译&#xff0c;并且可以在几乎任何体系结构/OS上使用。 在 DroneCAN 中&#xff0c;Libuavcan 有一个 DSDL 编译器&#xff0c;将 DSDL 文件转换为 hpp 头…...

Hot 3D 人体姿态估计 HPE Demo复现过程

视频讲解 Hot 3D 人体姿态估计 HPE Demo复现过程 标题&#xff1a;Hourglass Tokenizer for Efficient Transformer-Based 3D Human Pose Estimation论文地址&#xff1a;https://arxiv.org/abs/2311.12028代码地址&#xff1a;https://github.com/NationalGAILab/HoT 使用con…...

rknn优化教程(二)

文章目录 1. 前述2. 三方库的封装2.1 xrepo中的库2.2 xrepo之外的库2.2.1 opencv2.2.2 rknnrt2.2.3 spdlog 3. rknn_engine库 1. 前述 OK&#xff0c;开始写第二篇的内容了。这篇博客主要能写一下&#xff1a; 如何给一些三方库按照xmake方式进行封装&#xff0c;供调用如何按…...

【力扣数据库知识手册笔记】索引

索引 索引的优缺点 优点1. 通过创建唯一性索引&#xff0c;可以保证数据库表中每一行数据的唯一性。2. 可以加快数据的检索速度&#xff08;创建索引的主要原因&#xff09;。3. 可以加速表和表之间的连接&#xff0c;实现数据的参考完整性。4. 可以在查询过程中&#xff0c;…...

Vue3 + Element Plus + TypeScript中el-transfer穿梭框组件使用详解及示例

使用详解 Element Plus 的 el-transfer 组件是一个强大的穿梭框组件&#xff0c;常用于在两个集合之间进行数据转移&#xff0c;如权限分配、数据选择等场景。下面我将详细介绍其用法并提供一个完整示例。 核心特性与用法 基本属性 v-model&#xff1a;绑定右侧列表的值&…...

【决胜公务员考试】求职OMG——见面课测验1

2025最新版&#xff01;&#xff01;&#xff01;6.8截至答题&#xff0c;大家注意呀&#xff01; 博主码字不易点个关注吧,祝期末顺利~~ 1.单选题(2分) 下列说法错误的是:&#xff08; B &#xff09; A.选调生属于公务员系统 B.公务员属于事业编 C.选调生有基层锻炼的要求 D…...

Kafka入门-生产者

生产者 生产者发送流程&#xff1a; 延迟时间为0ms时&#xff0c;也就意味着每当有数据就会直接发送 异步发送API 异步发送和同步发送的不同在于&#xff1a;异步发送不需要等待结果&#xff0c;同步发送必须等待结果才能进行下一步发送。 普通异步发送 首先导入所需的k…...

uniapp手机号一键登录保姆级教程(包含前端和后端)

目录 前置条件创建uniapp项目并关联uniClound云空间开启一键登录模块并开通一键登录服务编写云函数并上传部署获取手机号流程(第一种) 前端直接调用云函数获取手机号&#xff08;第三种&#xff09;后台调用云函数获取手机号 错误码常见问题 前置条件 手机安装有sim卡手机开启…...

群晖NAS如何在虚拟机创建飞牛NAS

套件中心下载安装Virtual Machine Manager 创建虚拟机 配置虚拟机 飞牛官网下载 https://iso.liveupdate.fnnas.com/x86_64/trim/fnos-0.9.2-863.iso 群晖NAS如何在虚拟机创建飞牛NAS - 个人信息分享...

深入理解Optional:处理空指针异常

1. 使用Optional处理可能为空的集合 在Java开发中&#xff0c;集合判空是一个常见但容易出错的场景。传统方式虽然可行&#xff0c;但存在一些潜在问题&#xff1a; // 传统判空方式 if (!CollectionUtils.isEmpty(userInfoList)) {for (UserInfo userInfo : userInfoList) {…...

【安全篇】金刚不坏之身:整合 Spring Security + JWT 实现无状态认证与授权

摘要 本文是《Spring Boot 实战派》系列的第四篇。我们将直面所有 Web 应用都无法回避的核心问题&#xff1a;安全。文章将详细阐述认证&#xff08;Authentication) 与授权&#xff08;Authorization的核心概念&#xff0c;对比传统 Session-Cookie 与现代 JWT&#xff08;JS…...

算法打卡第18天

从中序与后序遍历序列构造二叉树 (力扣106题) 给定两个整数数组 inorder 和 postorder &#xff0c;其中 inorder 是二叉树的中序遍历&#xff0c; postorder 是同一棵树的后序遍历&#xff0c;请你构造并返回这颗 二叉树 。 示例 1: 输入&#xff1a;inorder [9,3,15,20,7…...