我们有一个需求,需要新增、修改用户订单。一个订单拥有多个商品,使用 JPA 保存时需要保存订单信息和订单所属的商品、价格信息。最简单的做法是逐一保存订单、订单所属商品信息,这样就会执行 n+1 次数据库操作。
从功能上说,上面的做法有问题,能够满足我们的需求。如果某一个订单拥有几十个商品,我们就会执行几十次数据库操作,这对数据库是不友好的;在 JPA 中,我们可以通过 saveAll() 方法实现批量保存,一次性保存几十个订单商品信息;这样一个订单就只需要执行两次数据库操作。
<S extends T> Iterable<S> saveAll(Iterable<S> entities);
上面方法用来保存传递给 saveAll 方法的所有实体,entities 参数是一个实体迭代器,不能为空,迭代器中每一个元素也不能为 null。
saveAll 方法返回保存实体,永远不会返回 null,返回的 Iterable 和传递的 entities 具有相同的大小。
如果给定的 Iterable 实体或 entities 参数其中一个实体是 null,则抛出 IllegalArgumentException 异常。
import com.hxstrive.jpa.springboot_jpa.dao.UserDao; import com.hxstrive.jpa.springboot_jpa.entity.User; import org.junit.jupiter.api.Test; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.boot.test.context.SpringBootTest; import java.util.ArrayList; import java.util.List; /** * 批量保存 * @author Administrator 2021/9/22 12:53 * @version 1.0 */ @SpringBootTest public class Demo2 { @Autowired private UserDao userDao; @Test public void batch1() { List<User> userList = new ArrayList<>(); userList.add(new User("用户1", 22, 7500.34f)); userList.add(new User("用户2", 23, 7350.12f)); userList.add(new User("用户3", 26, 6890.05f)); userList.add(new User("用户4", 30, 7120.5f)); // 批量保存用户实体 Iterable<User> iterable = userDao.saveAll(userList); for(User user : iterable) { System.out.println(user); } } }
上面代码中,一次性保存了4个 User 实体。