「Java开发指南」如何在MyEclipse中使用JPA和Spring管理事务?(二)

本教程中介绍一些基于JPA/ spring的特性,重点介绍JPA-Spring集成以及如何利用这些功能。您将学习如何:

  • 为JPA和Spring设置一个项目
  • 逆向工程数据库表来生成实体
  • 实现创建、检索、编辑和删除功能
  • 启用容器管理的事务

在上文中(点击这里回顾>>),我们为大家介绍了如何用JPA和Spring Facets创建一个Java项目以及逆向工程,本文将继续介绍如何创建一个应用并启用容器管理的事务等。

MyEclipse v2023.1.2离线版下载

3. 编写应用程序

现在MyEclipse已经生成了所有这些代码,您可以快速地专注于编写“业务逻辑”,或者更具体地说,“实际执行任务的代码”。

JPA教程介绍了每个实体和DAO类的功能,以及运行一个简单场景的主要方法的基本大纲,包括:

  • 创建一个新实体并将其插入数据库
  • 检索实体
  • 更新实体
  • 删除实体

类似地,在本教程中您将看到如何使用Spring获取和使用DAO以及管理事务。

这个演示的起点是RunJPA.java类,看看这个类中的main方法。

/* 1. Initialize the transactionManager and DAO */
ClassPathXmlApplicationContext ctx = new ClassPathXmlApplicationContext("/applicationContext.xml");
txManager = ((JpaTransactionManager) ctx.getBean("transactionManager"));
dao = ProductlineDAO.getFromApplicationContext(ctx);/* 2. Create a reference to our ID */
String productlineID = "Men Shoes";/* 3. Save a new productline to the DB */
saveProductline(productlineID);/* 4. Load the productline from DB to make sure it worked */
loadProductline(productlineID);/* 5. Update the productline in the DB and check it */
updateProductline(productlineID);/* 6. Delete the productline from the DB */
deleteProductline(productlineID);

用蓝色标记的代码部分是Spring调用,您可以在其中从bean配置中检索已配置的bean。请注意,由于您正在手动管理事务,因此还需要从bean配置中检索' transactionManager '。

剩下的项目,#2 - #6,简单地调用每个“做某事”的方法。

3.1 保存实体

第一个有趣的方法是“saveProductline”,此方法的目的是创建一个新实体并将其存储在DB中。

/* 1. Create a new Productline instance */
Productline newProductline = new Productline(productlineID,
"Shoes formen.", "<strong>MenShoes</strong>", null);/* 2. Store our new product line in the DB */
TransactionStatus status = txManager
.getTransaction(new DefaultTransactionDefinition());
dao.save(newProductline);
txManager.commit(status);

首先,用一些基本值创建新的Productline实例。其次使用transactionManager,事务在将实体保存到DB之前开始。在保存实体之后,事务被提交。

手动管理事务的目的是因为作为开发人员,您知道“保存”操作的范围。根据应用程序的编写方式,一些操作的作用域可能包含许多数据库修改,将所有这些都包装在一个事务中是很重要的,以防在工作进行到一半时失败。您肯定不希望让数据处于一种状态,其中一些是正确的,而另一些是过时的。

3.2 检索实体

下一个方法使用分配给实体的ID从DB中检索实体,并显示其值,这确认保存操作成功。

/* 1. Now retrieve the new product line, using the ID we created */
Productline loadedProductline = dao.findById(productlineID);/* 2. Print out the product line information */
System.out.println("*NEW* Product Line [productLine="
+ loadedProductline.getProductline() + ", textDescription="
+ loadedProductline.getTextdescription() + "]");

注意在这段代码中,没有使用任何事务。原因是这段代码只执行读操作而不执行写操作,即使操作失败,DB中的任何数据都不会受到影响。因此,不需要使用事务来保护操作。

3.3 更新实体

现在下一段代码看起来可能更长,但这是因为它输出了新值,并确认在DB中更新了记录。

/* 1. Now retrieve the new product line, using the ID we created */
Productline loadedProductline = dao.findById(productlineID);/*
* 2. Now let's change same value on the product line, and save the
* change
*/
loadedProductline.setTextdescription("Product line for men's shoes.");TransactionStatus status = txManager
.getTransaction(new DefaultTransactionDefinition());
dao.update(loadedProductline);
txManager.commit(status);/*
* 3. Now let's load the product line from the DB again, and make sure
* its text description changed
*/
Productline secondLoadedProductline = dao.findById(productlineID);System.out.println("*REVISED* Product Line [" + "productLine="
+ secondLoadedProductline.getProductline()
+ ", textDescription="
+ secondLoadedProductline.getTextdescription() + "]");

请注意更新调用被封装在事务中,因为它必须向数据库写入一些内容,并且需要防止失败。

在上面的第3节中,产品线在更新后立即从数据库加载,并通过打印从数据库返回的值来确认更新。

3.4 删除实体

删除实体几乎等同于保存和更新实体,工作被封装在另一个事务中,然后DAO被告知去做这项工作。

/* 1. Now retrieve the new product line,
using the ID we created */
TransactionStatus status = txManager
.getTransaction(new DefaultTransactionDefinition());
Productline loadedProductline = dao.findById(productlineID);/* 2. Now let's delete the product line from
the DB */
dao.delete(loadedProductline);
txManager.commit(status);/*
* 3. To confirm the deletion, try and load it again and make sure it
* fails
*/
Productline deletedProductline = dao.findById(productlineID);/*
* 4. We use a simple inline IF clause to test for null and print
* SUCCESSFUL/FAILED
*/
System.out.println("Productline deletion: "
+ (deletedProductline == null ? "SUCCESSFUL" : "FAILED"));

与上面的“updateProductline”实现类似,您会注意到一个事务用于封装“delete”调用,然后代码尝试从DB加载实体并确认操作应该失败。

注意:事务必须封装'findById '和'delete '方法调用的原因是因为JPA管理的对象必须是同一事务的一部分,要擦除已加载的对象,它必须处于加载它并尝试擦除它的同一个事务中。

3.5 运行程序

运行此命令的输出如下所示:

如何在MyEclipse中使用JPA和Spring管理事务?

输出

红色文本是可以忽略的默认日志消息(如果希望控制日志记录,您可以设置自定义log4j.properties文件),在日志警告下面,您可以看到来自TopLink (JPA实现库)的两条消息,以及来自实现的另外三条消息。

第一个消息打印出添加的新产品线信息,第二个消息更新产品线信息并打印新信息,最后一个消息从DB中删除产品线信息并打印确认消息。

4. 启用Spring容器管理的事务

除了用户管理的事务之外,Spring还通过@Transactional属性支持容器管理的事务。对于容器管理的事务支持,您必须在添加facet时启用它,这是您在本教程前面所做的。

如何在MyEclipse中使用JPA和Spring管理事务?

启用对@Transactional注释的支持

启用此功能将向bean配置文件添加以下事务元素,您还应该添加一个JPAServiceBean,它用于使用容器管理的事务删除实体。请参阅下面的实现:

如何在MyEclipse中使用JPA和Spring管理事务?

注解驱动的配置元素

JPAServiceBean实现如下所示;注意'deleteProductLine '方法上的'@Transactional '注释和没有任何用户管理的事务语句。

public class JPAServiceBean
{ private IProductlineDAO dao; @Transactional public void deleteProductLine(String productlineID){ /* 1. Now retrieve the new product line, using the ID we created */Productline loadedProductline = dao.findById(productlineID);/* 2. Now let's delete the product line from the DB */
dao.delete(loadedProductline);/*
* 3. To confirm the deletion, try and load it again and make sure it * fails
*/
Productline deletedProductline = dao.findById(productlineID);/*
* 4. We use a simple inline IF clause to test for null and print
* SUCCESSFUL/FAILED
*/
System.out.println("Productline deletion: " + (deletedProductline == null ? "SUCCESSFUL" : "FAILED"));}public void setProductLineDAO(IProductlineDAO dao) { this.dao = dao; }
}

从应用程序上下文中获取JPAServiceBean实例,并按如下方式使用它:

JPAServiceBean bean = (JPAServiceBean) ctx.getBean("JPAServiceBean");
bean.deleteProductLine(productlineID);

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.rhkb.cn/news/172700.html

如若内容造成侵权/违法违规/事实不符,请联系长河编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

Flink将数据写入MySQL(JDBC)

一、写在前面 在实际的生产环境中&#xff0c;我们经常会把Flink处理的数据写入MySQL、Doris等数据库中&#xff0c;下面以MySQL为例&#xff0c;使用JDBC的方式将Flink的数据实时数据写入MySQL。 二、代码示例 2.1 版本说明 <flink.version>1.14.6</flink.version…

DBSCAN算法c++实现

首先计算出距离每个点e以内的点&#xff0c;如果个数>minPts,则找出它的直接密度可达和间接可达的点&#xff0c;用visited标记点是否已经在簇中&#xff0c;循环直到最后一个点。 #include <fstream> #include <vector> #include <iostream> #include &…

广州华锐互动:VR技术应用到工程项目施工安全培训的好处

随着科技的飞速发展&#xff0c;虚拟现实(VR)技术已经深入到各个领域。在建筑施工领域&#xff0c;VR技术的应用为工程项目施工安全培训带来了许多好处。本文将探讨VR技术在这方面的优势和应用。 首先&#xff0c;VR技术能够提供沉浸式的安全培训体验。通过VR设备&#xff0c;学…

x210项目重新回顾之十七升级到linux4.19.114 +buildroot2018再讨论

代码参考https://github.com/colourfate/x210_bsp/ 他的是linux_4.10(dtb为 s5pv210-x210..dtb)我打算用linux4.19.114(dtb为 s5pv210-smdkv210.dtb) &#xff0c;所以修改build.sh ------------------------------------------------------------------------------ 5 M…

【开源】基于SpringBoot的高校学院网站的设计和实现

目录 一、摘要1.1 项目介绍1.2 项目录屏 二、功能模块2.1 学院院系模块2.2 竞赛报名模块2.3 教育教学模块2.4 招生就业模块2.5 实时信息模块 三、系统设计3.1 用例设计3.2 数据库设计3.2.1 学院院系表3.2.2 竞赛报名表3.2.3 教育教学表3.2.4 招生就业表3.2.5 实时信息表 四、系…

python之计算平面点集的的面积

在当今数据驱动的世界中&#xff0c;计算平面点集的最小外接轮廓面积被广泛应用于各种实际场景中。它是一项重要而魅力十足的任务&#xff0c;旨在找到一个最小的矩形或多边形区域&#xff0c;能够完全包围给定的离散点集。这个看似简单的问题背后隐藏着许多挑战&#xff0c;需…

python爬虫之feapder.AirSpider轻量爬虫案例:豆瓣

创建feaderSpider项目&#xff1a;feapder create -p feapderSpider&#xff0c;已创建可忽略进入feapderSpider目录&#xff1a;cd .\ feapderSpider\spiders创建爬虫&#xff1a;feapder create -s airSpiderDouban&#xff0c;选择AirSpider爬虫模板&#xff0c;可跳过1、2直…

KMS在腾讯云的微服务实践助力其降本50%

背景介绍 KMS 是一家日本的游戏公司&#xff0c;主要经营游戏业务、数字漫画业务、广告业务、云解决方案业务等&#xff0c;出品了多款在日本畅销的漫画风游戏&#xff0c;同时有网络漫画专业厂牌&#xff0c;以内容创作为目标&#xff0c;拥有原创 IP 创作、游戏开发等多元化发…

bitlocker 加密锁定的固态硬盘,更换到别的电脑上,怎么把原密钥写进新电脑TPM芯片内,开启无需手动填密钥

环境: Win11 专业版 联想E14笔记本 512G ssd 问题描述: 一台笔记本因充电故障,需要拿去维修,不想重装系统,将bitlocker 加密锁定的固态硬盘拆下更换到别的笔记本电脑上,现在开机要手动填密钥,怎么把原密钥写进新电脑TPM芯片内,开启无需手动填密钥和之前那台电脑一…

DevOps与CI/CD的最佳实践

在当今的软件开发领域&#xff0c;DevOps&#xff08;开发与运维的结合&#xff09;和CI/CD&#xff08;持续集成/持续交付&#xff09;已经成为了不可或缺的一部分。它们不仅提高了软件开发的效率&#xff0c;还帮助团队更快地交付高质量的软件。本文将深入探讨DevOps文化和CI…

iOS Xcode15 适配:Other Linker Flags:-ld_classic

0x00 适配是一条没有尽头的路 Xcode 14 毛问题都没有&#xff0c;Xcode 15 崩溃 看图说话 0x01 解决方案 Other Linker Flags 添加 -ld_classic 即可 0x02 我的小作品 欢迎体验我的作品之一&#xff1a;小挑战-XGame 拼图游戏&#xff0c;渐变色游戏&#xff0c;经典24点游…

List 3.5 详解原码、反码、补码

前言 欢迎来到我的博客&#xff0c;我是雨空集&#xff08;全网同名&#xff09;&#xff0c;无论你是无意中发现我&#xff0c;还是有意搜索而来&#xff0c;我都感到荣幸。这里是一个分享知识、交流想法的平台&#xff0c;我希望我的博客能给你带来帮助和启发。如果你喜欢我…

Ubuntu ARMv8编译Qt源码以及QtCreator

最近需要在NVIDIA小盒子上面跑一个程序&#xff0c;一开始想着在Ubuntu x64下交叉编译一版&#xff0c;后来发现libqxcb.so 这个库在configure时就会一直报错&#xff0c;多方查找怀疑可能是由于硬件不支持在x64环境下编译AMR架构的xcb库。 所以最后在ARM下直接编译Qt源码了&am…

word页脚设置,页脚显示第几页共有几页设置步骤

word页脚设置&#xff0c;页脚显示第几页共有几页设置步骤&#xff1a; 具体步骤&#xff1a; 步骤1&#xff1a; 步骤1.1选择页脚---空白页脚 步骤1.2&#xff0c;在"[在此处键入]"&#xff0c;直接输入你需要的格式&#xff0c;如 “第页/共页” 步骤1.3选择第“…

数据分析和互联网医院小程序:提高医疗决策的准确性和效率

互联网医院小程序已经在医疗领域取得了显著的进展&#xff0c;为患者和医疗从业者提供了更便捷和高效的医疗服务。随着数据分析技术的快速发展&#xff0c;互联网医院小程序能够利用大数据来提高医疗决策的准确性和效率。本文将探讨数据分析在互联网医院小程序中的应用&#xf…

Vue图片路径问题(动态引入)

vue项目中我们经常会遇到动态路径的图片无法显示的问题&#xff0c;以下是静态路径和动态路径的常见使用方法。 1.静态路径 在日常的开发中&#xff0c;图片的静态路径通过相对路径和绝对路径的方式引入。 相对路径&#xff1a;以.开头的&#xff0c;例如./、../之类的。就是…

pytorch笔记:TRIPLETMARGINLOSS

1 介绍 创建一个衡量三元组损失的标准&#xff0c;给定输入张量 x1​、x2​ 和 x3​ 以及一个大于0的间距值。这用于测量样本之间的相对相似性。一个三元组由a、p和n组成&#xff08;锚点、正例和负例&#xff09;。所有输入张量的形状都应为 (N,D) 2 基本使用方法 torch.nn.…

iPhone手机屏幕分辨率

ios app测试时&#xff0c;需要测试应用在不同型号的苹果手机上的表现形式&#xff0c;可以自己在浏览器上配置。 代数设备逻辑像素尺寸缩放发布时间第一代iPhone 2G320 x 480480 x 3203.5寸1x2007年6月29日第二代iPhone 3320 x 480480 x 3203.5寸1x2008年7月11日第三代iPhone …

前端 :用HTML和css制作一个小米官网的静态页面

1.HTML&#xff1a; <body><div id "content"><div id "box"><div id "top"><div id "top-left"><span id "logo">MI</span><span id "text-logo">小米账…

机器视觉3D项目评估的基本要素及测量案例分析

目录 一. 检测需求确认 1、产品名称&#xff1a;【了解是什么产品上的零件&#xff0c;功能是什么】 2、*产品尺寸&#xff1a;【最大兼容尺寸】 3、*测量项目&#xff1a;【确认清楚测量点位】 4、*精度要求&#xff1a;【若客户提出的精度值过大或者过小&#xff0c;可以和客…