如果 HQL 中不存在则插入
insert if not exists in HQL
我正在尝试在 HQL 中编写一个查询,如果记录不存在(具有相同的名称),它可以插入一条记录,这样当从多个线程完成时就不会重复插入。
String hql = "INSERT INTO employee(emp_id, emp_name)"
+ " SELECT '100001' , 'John' " FROM employee
+ " WHERE NOT EXISTS (SELECT 1 from employee WHERE emp_name = 'John')";
但是,没有插入记录。我怀疑这是因为 table 是空的,尽管有 NOT EXISTS 子句,子查询 returns 0 条记录。
注意 - '100001','John' & 将在实际查询字符串中以编程方式替换。
你可以加“!”像这样的运算符:
String hql = "INSERT INTO employee(emp_id, emp_name)"
+ " SELECT '100001' , 'John' FROM employee "
+ " WHERE !EXISTS (SELECT 1 from employee WHERE emp_name = 'John')";
原因是您 select 从空 table 中获取常量值。因此,您正在 selecting 并插入零行。请注意,如果 table 有两行,但它们都没有 emp_name = 'John'
,您将插入两行。所以你应该 select 从 table 正好一行:
INSERT INTO employee(emp_id, emp_name)
SELECT '100001' , 'John'
FROM (select 1) as dummy -- derived table with one row
WHERE NOT EXISTS (SELECT 1 from employee WHERE emp_name = 'John')
您也可以使用 dual
im MySQL.
而不是 (select 1) as dummy
正如我在评论中所写,您还可以将 emp_name
列定义为 UNIQUE,然后只需使用 INSERT IGNORE
.
任务:我们需要添加唯一的行someId
。
但如果 someId
不是唯一的,请忽略。
存在数据 (postgresql):
+------------------------------+
| table_a |
+------+--------------+--------|
| id | some_id | data |
+------+--------------+--------|
| 1 | 111111 | a |
| 2 | 111111 | a |
| 3 | 222222 | b |
| 4 | 333333 | c |
| 5 | 333333 | c |
+------------------------------+
解决 (spring hibernate jpa hql):
@Repository
public interface TableARepository extends PagingAndSortingRepository<TableA, String>, JpaSpecificationExecutor<TableA> {
@Transactional
@Modifying
@Query("INSERT INTO TableA (someId, data) " +
"SELECT :someId, :data " + //SELECT - is alias for INSERT ... VALUES
"FROM TableA " + // just rudiment HQL for INSERT
"WHERE NOT EXISTS " +
" (SELECT 1 " +
" FROM TableA " +
" WHERE someId = :someId) " +
" GROUP BY someId" //derived table with one row
)
void saveIfNotExists(@Param("someId") Long someId,
@Param("data") String data);
}
我正在尝试在 HQL 中编写一个查询,如果记录不存在(具有相同的名称),它可以插入一条记录,这样当从多个线程完成时就不会重复插入。
String hql = "INSERT INTO employee(emp_id, emp_name)"
+ " SELECT '100001' , 'John' " FROM employee
+ " WHERE NOT EXISTS (SELECT 1 from employee WHERE emp_name = 'John')";
但是,没有插入记录。我怀疑这是因为 table 是空的,尽管有 NOT EXISTS 子句,子查询 returns 0 条记录。
注意 - '100001','John' & 将在实际查询字符串中以编程方式替换。
你可以加“!”像这样的运算符:
String hql = "INSERT INTO employee(emp_id, emp_name)"
+ " SELECT '100001' , 'John' FROM employee "
+ " WHERE !EXISTS (SELECT 1 from employee WHERE emp_name = 'John')";
原因是您 select 从空 table 中获取常量值。因此,您正在 selecting 并插入零行。请注意,如果 table 有两行,但它们都没有 emp_name = 'John'
,您将插入两行。所以你应该 select 从 table 正好一行:
INSERT INTO employee(emp_id, emp_name)
SELECT '100001' , 'John'
FROM (select 1) as dummy -- derived table with one row
WHERE NOT EXISTS (SELECT 1 from employee WHERE emp_name = 'John')
您也可以使用 dual
im MySQL.
(select 1) as dummy
正如我在评论中所写,您还可以将 emp_name
列定义为 UNIQUE,然后只需使用 INSERT IGNORE
.
任务:我们需要添加唯一的行someId
。
但如果 someId
不是唯一的,请忽略。
存在数据 (postgresql):
+------------------------------+
| table_a |
+------+--------------+--------|
| id | some_id | data |
+------+--------------+--------|
| 1 | 111111 | a |
| 2 | 111111 | a |
| 3 | 222222 | b |
| 4 | 333333 | c |
| 5 | 333333 | c |
+------------------------------+
解决 (spring hibernate jpa hql):
@Repository
public interface TableARepository extends PagingAndSortingRepository<TableA, String>, JpaSpecificationExecutor<TableA> {
@Transactional
@Modifying
@Query("INSERT INTO TableA (someId, data) " +
"SELECT :someId, :data " + //SELECT - is alias for INSERT ... VALUES
"FROM TableA " + // just rudiment HQL for INSERT
"WHERE NOT EXISTS " +
" (SELECT 1 " +
" FROM TableA " +
" WHERE someId = :someId) " +
" GROUP BY someId" //derived table with one row
)
void saveIfNotExists(@Param("someId") Long someId,
@Param("data") String data);
}