Showing posts with label @Modifiable. Show all posts
Showing posts with label @Modifiable. Show all posts

Sunday, 18 April 2021

Spring data jpa: Update an entity using repository method

Spring-data-jpa supports update operation using query method.

 

How to update entities using query method?

Define the repository method using @Query and @Modifying annotations. One more thing to note here is, all the update/delete operations should be called in a transaction scope.

 

Note

By default, CRUD methods (CrudRepository methods) are marked as transactional. If you are using custom query methods then you should explicitly mark it with @Transactional annotation.

 

Example 1: Update employee firstName and lastName using id.

@Transactional
@Modifying
@Query("update Employee e set e.firstName = ?1, e.lastName = ?2 where e.id = ?3")
int updateUserNameById(String firstname, String lastname, Integer userId);

 

Example 2: Update all the employees age by 1.

@Transactional
@Modifying
@Query("update Employee e set e.age = e.age+1")
int updateEmpsAgeBy1();

 

Find the below working application.

 

Step 1: Create new maven project ‘update-via-query-method’.

 

Step 2: Update pom.xml with maven dependencies.

 

pom.xml

<project xmlns="http://maven.apache.org/POM/4.0.0"
	xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
	xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd">
	<modelVersion>4.0.0</modelVersion>
	<groupId>com.sample.app</groupId>
	<artifactId>update-via-query-method</artifactId>
	<version>1</version>

	<parent>
		<groupId>org.springframework.boot</groupId>
		<artifactId>spring-boot-starter-parent</artifactId>
		<version>2.4.0</version>
	</parent>

	<properties>
		<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
	</properties>


	<dependencies>

		<dependency>
			<groupId>org.springframework.boot</groupId>
			<artifactId>spring-boot-starter-data-jpa</artifactId>
		</dependency>


		<dependency>
			<groupId>com.h2database</groupId>
			<artifactId>h2</artifactId>
		</dependency>


	</dependencies>
</project>

 

Step 3: Create application.properties file under src/main/resources folder.

 

application.properties

logging.level.root=WARN
logging.level.org.hibernate=ERROR

## H2 specific properties
spring.h2.console.enabled=true
spring.h2.console.path=/h2

spring.datasource.url=jdbc:h2:file:~/db/myOrg.db;DB_CLOSE_ON_EXIT=FALSE;DB_CLOSE_DELAY=-1;

spring.datasource.username=krishna
spring.datasource.password=password123

spring.datasource.driverClassName=org.h2.Driver

## JPA specific properties
# Creates the schema, destroying previous data.
spring.jpa.hibernate.ddl-auto=create

spring.jpa.database-platform=org.hibernate.dialect.H2Dialect

spring.jpa.show-sql=false
spring.jpa.properties.hibernate.format_sql=false

## Database connection pooling properties
# Number of ms to wait before throwing an exception if no connection is available.
spring.datasource.max-wait=10000

# Maximum number of active connections that can be allocated from this pool at the same time.
spring.datasource.tomcat.max-active=10
spring.datasource.tomcat.max-idle=5
spring.datasource.tomcat.min-idle=3

Step 4: Define Employee entity.

 

Employee.java

package com.sample.app.entity;

import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import javax.persistence.Table;

@Entity
@Table(name = "my_employee")
public class Employee {
	@Id
	@GeneratedValue(strategy = GenerationType.AUTO)
	private int id;

	@Column(name = "first_name")
	private String firstName;

	@Column(name = "last_name")
	private String lastName;

	@Column(name = "age")
	private int age;

	@Column(name = "salary")
	private double salary;

	public int getId() {
		return id;
	}

	public void setId(int id) {
		this.id = id;
	}

	public String getFirstName() {
		return firstName;
	}

	public void setFirstName(String firstName) {
		this.firstName = firstName;
	}

	public String getLastName() {
		return lastName;
	}

	public void setLastName(String lastName) {
		this.lastName = lastName;
	}

	public int getAge() {
		return age;
	}

	public void setAge(int age) {
		this.age = age;
	}

	public double getSalary() {
		return salary;
	}

	public void setSalary(double salary) {
		this.salary = salary;
	}

	public static EmployeeBuilder builder() {
		return new EmployeeBuilder();
	}

	public static class EmployeeBuilder {
		private Employee emp;

		public EmployeeBuilder() {
			emp = new Employee();
		}

		public EmployeeBuilder firstName(String firstName) {
			emp.setFirstName(firstName);
			return this;
		}

		public EmployeeBuilder lastName(String lastName) {
			emp.setLastName(lastName);
			return this;
		}

		public EmployeeBuilder age(int age) {
			emp.setAge(age);
			return this;
		}

		public EmployeeBuilder salary(double salary) {
			emp.setSalary(salary);
			return this;
		}

		public Employee build() {
			return emp;
		}
	}

	@Override
	public String toString() {
		StringBuilder builder = new StringBuilder();
		builder.append("Employee [id=").append(id).append(", firstName=").append(firstName).append(", lastName=")
				.append(lastName).append(", age=").append(age).append(", salary=").append(salary).append("]");
		return builder.toString();
	}

}


Step 5: Define EmployeeRepository interface.

 

EmployeeRepository.java

package com.sample.app.repository;

import javax.transaction.Transactional;

import org.springframework.data.jpa.repository.JpaRepository;
import org.springframework.data.jpa.repository.Modifying;
import org.springframework.data.jpa.repository.Query;

import com.sample.app.entity.Employee;

public interface EmployeeRepository extends JpaRepository<Employee, Integer>{
	
	@Transactional
	@Modifying
	@Query("update Employee e set e.firstName = ?1, e.lastName = ?2 where e.id = ?3")
	int updateUserNameById(String firstname, String lastname, Integer userId);
	
	@Transactional
	@Modifying
	@Query("update Employee e set e.age = e.age+1")
	int updateEmpsAgeBy1();
}


Step 6: Define main application class.

 

App.java

package com.sample.app;

import java.util.Arrays;
import java.util.List;

import org.springframework.boot.CommandLineRunner;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.context.annotation.Bean;

import com.sample.app.entity.Employee;
import com.sample.app.repository.EmployeeRepository;

@SpringBootApplication
public class App {

	public static void main(String args[]) {
		SpringApplication.run(App.class, args);
	}

	public void printEmployees(Iterable<Employee> emps, String msg) {
		System.out.println(msg);
		for (Employee emp : emps) {
			System.out.println(emp);
		}

		System.out.println();
	}

	@Bean
	public CommandLineRunner demo(EmployeeRepository employeeRepository) {
		return (args) -> {
			Employee emp1 = Employee.builder().firstName("Ram").lastName("Gurram").age(32).salary(100000.23).build();
			Employee emp2 = Employee.builder().firstName("Ram").lastName("Chelli").age(43).salary(60000).build();
			Employee emp3 = Employee.builder().firstName("Gopi").lastName("Battu").age(45).salary(1000000).build();
			Employee emp4 = Employee.builder().firstName("Ram").lastName("Srikanth").age(39).salary(60000).build();
			Employee emp5 = Employee.builder().firstName("Surendra").lastName("Sami").age(32).salary(100000.23).build();

			employeeRepository.save(emp1);
			employeeRepository.save(emp2);
			employeeRepository.save(emp3);
			employeeRepository.save(emp4);
			employeeRepository.save(emp5);

			List<Employee> emps = employeeRepository.findAll();
			printEmployees(emps, "All the employees information");

			int updatedRecords = employeeRepository.updateUserNameById("John", "Charter", 1);

			if (updatedRecords == 1) {
				Employee emp = employeeRepository.findById(1).get();

				printEmployees(Arrays.asList(emp), "Employee with id 1 details");
			} else {
				System.out.println("Failed to update");
			}

			updatedRecords = employeeRepository.updateEmpsAgeBy1();
			System.out.println("Total updated record : " + updatedRecords);

			emps = employeeRepository.findAll();
			printEmployees(emps, "All the employees information");
		};
	}

}


Total project structure looks like below.



Run App.java, you will see below messages in console.

All the employees information
Employee [id=1, firstName=Ram, lastName=Gurram, age=32, salary=100000.23]
Employee [id=2, firstName=Ram, lastName=Chelli, age=43, salary=60000.0]
Employee [id=3, firstName=Gopi, lastName=Battu, age=45, salary=1000000.0]
Employee [id=4, firstName=Ram, lastName=Srikanth, age=39, salary=60000.0]
Employee [id=5, firstName=Surendra, lastName=Sami, age=32, salary=100000.23]

Employee with id 1 details
Employee [id=1, firstName=John, lastName=Charter, age=32, salary=100000.23]

Total updated record : 5
All the employees information
Employee [id=1, firstName=John, lastName=Charter, age=33, salary=100000.23]
Employee [id=2, firstName=Ram, lastName=Chelli, age=44, salary=60000.0]
Employee [id=3, firstName=Gopi, lastName=Battu, age=46, salary=1000000.0]
Employee [id=4, firstName=Ram, lastName=Srikanth, age=40, salary=60000.0]
Employee [id=5, firstName=Surendra, lastName=Sami, age=33, salary=100000.23]


You can download complete working application from below link.

https://github.com/harikrishna553/springboot/tree/master/jpa/update-via-query-method

 




 

 

 

 

 

 

 

Previous                                                    Next                                                    Home

Monday, 30 September 2019

Spring boot: jpa: DELETE Query


We can execute queries using @Query annotation. If you are performing UPDATE/DELETE queries, you should annotate that query method with @Transactional and @Modifying annotations.
public interface EmployeeRepository extends JpaRepository<Employee, Integer> {

 @Transactional
 @Modifying
 @Query("UPDATE Employee SET firstName=UPPER(firstName) WHERE id in :ids")
 public int toUpperEmployeeFirstNames(@Param(value = "ids") List<Integer> ids);

 @Transactional
 @Modifying
 @Query("DELETE FROM Employee WHERE id in :ids")
 public int deleteEmployees(@Param(value = "ids") List<Integer> ids);

}

'toUpperEmployeeFirstNames' method convert employee first names to upper case for given employee ids.

'deleteEmployees' method take list of employee ids as input and delete the employees that matches to given ids.

Find the below working application.

Employee.java
package com.sample.app.entity;

import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.Id;
import javax.persistence.Table;

@Entity
@Table(name = "employees")
public class Employee {

 @Id
 @GeneratedValue
 @Column(name = "EMPLOYEE_ID")
 private int id;

 @Column(name = "EMPLOYEE_FIRST_NAME")
 private String firstName;

 @Column(name = "EMPLOYEE_LAST_NAME")
 private String lastName;

 public Employee() {

 }

 public Employee(String firstName, String lastName) {
  this.firstName = firstName;
  this.lastName = lastName;
 }

 public int getId() {
  return id;
 }

 public void setId(int id) {
  this.id = id;
 }

 public String getFirstName() {
  return firstName;
 }

 public void setFirstName(String firstName) {
  this.firstName = firstName;
 }

 public String getLastName() {
  return lastName;
 }

 public void setLastName(String lastName) {
  this.lastName = lastName;
 }

 @Override
 public String toString() {
  return "Employee [id=" + id + ", firstName=" + firstName + ", lastName=" + lastName + "]";
 }

}


EmployeeRepository.java
package com.sample.app.repository;

import java.util.List;

import org.springframework.data.jpa.repository.JpaRepository;
import org.springframework.data.jpa.repository.Modifying;
import org.springframework.data.jpa.repository.Query;
import org.springframework.data.repository.query.Param;
import org.springframework.transaction.annotation.Transactional;

import com.sample.app.entity.Employee;

public interface EmployeeRepository extends JpaRepository<Employee, Integer> {

 @Transactional
 @Modifying
 @Query("UPDATE Employee SET firstName=UPPER(firstName) WHERE id in :ids")
 public int toUpperEmployeeFirstNames(@Param(value = "ids") List<Integer> ids);

 @Transactional
 @Modifying
 @Query("DELETE FROM Employee WHERE id in :ids")
 public int deleteEmployees(@Param(value = "ids") List<Integer> ids);

}


App.java
package com.sample.app;

import java.util.Arrays;

import org.springframework.boot.CommandLineRunner;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.context.annotation.Bean;

import com.sample.app.entity.Employee;
import com.sample.app.repository.EmployeeRepository;

@SpringBootApplication
public class App {

 public static void main(String args[]) {
  SpringApplication.run(App.class, args);
 }

 @Bean
 public CommandLineRunner demo(EmployeeRepository empRepo) {
  return (args) -> {

   Employee emp1 = new Employee("Naresh", "Deva");
   Employee emp2 = new Employee("Nani", "Kulkarni");
   Employee emp3 = new Employee("Ram", "Kishore");

   empRepo.saveAll(Arrays.asList(emp1, emp2, emp3));

   empRepo.findAll().forEach(System.out::println);

   int updatedRecords = empRepo.toUpperEmployeeFirstNames(Arrays.asList(1, 2));
   System.out.println("\nTotal records updated : " + updatedRecords + "\n");

   empRepo.findAll().forEach(System.out::println);

   int deletedRecords = empRepo.deleteEmployees(Arrays.asList(2, 3));
   System.out.println("\nTotal records deleted : " + deletedRecords + "\n");

   empRepo.findAll().forEach(System.out::println);
  };
 }

}


application.properties
logging.level.root=WARN
logging.level.org.hibernate=ERROR

## H2 specific properties
spring.h2.console.enabled=true
spring.h2.console.path=/h2

spring.datasource.url=jdbc:h2:file:~/db/myOrg.db;DB_CLOSE_ON_EXIT=FALSE;DB_CLOSE_DELAY=-1;

spring.datasource.username=krishna
spring.datasource.password=password123

spring.datasource.driverClassName=org.h2.Driver

## JPA specific properties
# Creates the schema, destroying previous data.
spring.jpa.hibernate.ddl-auto=create

spring.jpa.database-platform=org.hibernate.dialect.H2Dialect

spring.jpa.show-sql=false
spring.jpa.properties.hibernate.format_sql=false

## Database connection pooling properties
# Number of ms to wait before throwing an exception if no connection is available.
spring.datasource.max-wait=10000

# Maximum number of active connections that can be allocated from this pool at the same time.
spring.datasource.tomcat.max-active=10
spring.datasource.tomcat.max-idle=5
spring.datasource.tomcat.min-idle=3


Total project structure looks like below.


Run App.java, you can see below messages in console.
Employee [id=1, firstName=Naresh, lastName=Deva]
Employee [id=2, firstName=Nani, lastName=Kulkarni]
Employee [id=3, firstName=Ram, lastName=Kishore]

Total records updated : 2

Employee [id=1, firstName=NARESH, lastName=Deva]
Employee [id=2, firstName=NANI, lastName=Kulkarni]
Employee [id=3, firstName=Ram, lastName=Kishore]

Total records deleted : 2

Employee [id=1, firstName=NARESH, lastName=Deva]

You can download complete working application from this link.



Previous                                                    Next                                                    Home