Create an account

Very important

  • To access the important data of the forums, you must be active in each forum and especially in the leaks and database leaks section, send data and after sending the data and activity, data and important content will be opened and visible for you.
  • You will only see chat messages from people who are at or below your level.
  • More than 500,000 database leaks and millions of account leaks are waiting for you, so access and view with more activity.
  • Many important data are inactive and inaccessible for you, so open them with activity. (This will be done automatically)


Thread Rating:
  • 835 Vote(s) - 3.54 Average
  • 1
  • 2
  • 3
  • 4
  • 5
Spring Boot - Loading Initial Data

#11
I solved similar problem this way:

@Component
public class DataLoader {

@Autowired
private UserRepository userRepository;

//method invoked during the startup
@PostConstruct
public void loadData() {
userRepository.save(new User("user"));
}

//method invoked during the shutdown
@PreDestroy
public void removeData() {
userRepository.deleteAll();
}
}
Reply

#12
you can register and event listener to achieve that like below:

@EventListener
public void seed(ContextRefreshedEvent event) {
userRepository.save(new User("lala", "lala", "lala"));
}

When the ContextRefreshEvent is fired, we get access to all autowired beans in the application — including models and repositories.

Reply

#13
If you want to insert only few rows and u have JPA Setup. You can use below



@SpringBootApplication
@Slf4j
public class HospitalManagementApplication {

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

@Bean
ApplicationRunner init(PatientRepository repository) {
return (ApplicationArguments args) -> dataSetup(repository);
}

public void dataSetup(PatientRepository repository){
//inserts

}


Reply

#14
You're almost there!

@Component
public class DataLoader implements CommandLineRunner {

private UserRepository userRepository;

public DataLoader(UserRepository userRepository) {
this.userRepository = userRepository;
}

@Override
public void run(String... args) throws Exception {
LoadUsers()
}

private void LoadUsers() {
userRepository.save(new User("lala", "lala", "lala"));
}
}
Reply

#15
You can use the below code. In the following code a database insertion occurs during the startup of the spring boot application.

@SpringBootApplication
public class Application implements CommandLineRunner {

@Autowired
private IService<Car> service;

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

@Override
public void run(String... args) throws Exception {
for(int i=1; i<=1000; i++) {
Car car = new Car();
car.setName("Car Name "+i);
book.setPrice(50 + i);
service.saveOrUpdate(car);
}
}

}
Reply

#16
One possibility is using incorrect JDBC URL. make sure it is `jdbc:h2:mem:testdb`
Reply

#17
I created a library that facilitates initial/demo data loading in a Spring Boot application. You can find it at

[To see links please register here]


Once the data fixtures starter is on the classpath, it will automatically try to load `DICTIONARY` data upon application startup (this behavior can be controlled by properties) - all you need to do is to register a bean implementing `DataFixture`.

I find loading initial data by code superior to loading it using SQL scripts:

- the logic of your fixtures lives close to your application logic/domain model and it is subject to refactoring as your domain evolves
- you benefit from incremental demo data updates - imagine a QA environment with some user data (that needs not to be lost after application deploy) but at the same time you want to add data for the new features you developed

Example data fixture:

```java
/**
* You can have as many fixture classes as you want.
* @Order annotation is respected for the fixtures belonging to the same set.
* You can make your demo database to be incrementally updated with fresh data
* each time the application is redeployed - all you need to do is to write
* a good condition in `canBeLoaded()` method.
*/
@Component
public class InitialDataFixture implements DataFixture {

private final LanguageRepository languageRepository;

// ...

@Override
public DataFixtureSet getSet() {
return DataFixtureSet.DICTIONARY;
}

/**
* We want to make sure the fixture is applied once and once only.
* A more sophisticated condition can be used to create incremental demo data
* over time without the need to reset the QA database (for example).
*/
@Override
public boolean canBeLoaded() {
return languageRepository.size() == 0;
}

/**
* The actual application of the fixture.
* Assuming that data fixtures are registered as beans, this method can call
* other services and/or repositories.
*/
@Override
public void load() {
languageRepository.saveAll(Arrays.asList(
new Language("en-US"), new Language("pl-PL")));
}
}
```


The concept is inspired by the Symfony Doctrine Data Fixtures bundle.
Reply

#18
There are multiple ways how to achieve this. I prefer to use one of following options:

**Option 1:** Initializing with `CommandLineRunner` bean:

@Bean
public CommandLineRunner loadData(CustomerRepository repository) {
return (args) -> {
// save a couple of customers
repository.save(new Customer("Jack", "Bauer"));
repository.save(new Customer("Chloe", "O'Brian"));
repository.save(new Customer("Kim", "Bauer"));
repository.save(new Customer("David", "Palmer"));
repository.save(new Customer("Michelle", "Dessler"));

// fetch all customers
log.info("Customers found with findAll():");
log.info("-------------------------------");
for (Customer customer : repository.findAll()) {
log.info(customer.toString());
}
log.info("");

// fetch an individual customer by ID
Customer customer = repository.findOne(1L);
log.info("Customer found with findOne(1L):");
log.info("--------------------------------");
log.info(customer.toString());
log.info("");

// fetch customers by last name
log.info("Customer found with findByLastNameStartsWithIgnoreCase('Bauer'):");
log.info("--------------------------------------------");
for (Customer bauer : repository
.findByLastNameStartsWithIgnoreCase("Bauer")) {
log.info(bauer.toString());
}
log.info("");
}
}


**Option 2:** Initializing with schema and data SQL scripts

Prerequisites:

**application.properties**

spring.jpa.hibernate.ddl-auto=none

Explanation:
> Without `ddl-auto` SQL scripts will be ignored by
> Hibernate and trigger default behavior - scanning project for
> `@Entity` and/or `@Table` annotated classes.

Then, in your `MyApplication` class paste this:

@Bean(name = "dataSource")
public DriverManagerDataSource dataSource() {
DriverManagerDataSource dataSource = new DriverManagerDataSource();
dataSource.setDriverClassName("org.h2.Driver");
dataSource.setUrl("jdbc:h2:~/myDB;MV_STORE=false");
dataSource.setUsername("sa");
dataSource.setPassword("");

// schema init
Resource initSchema = new ClassPathResource("scripts/schema-h2.sql");
Resource initData = new ClassPathResource("scripts/data-h2.sql");
DatabasePopulator databasePopulator = new ResourceDatabasePopulator(initSchema, initData);
DatabasePopulatorUtils.execute(databasePopulator, dataSource);

return dataSource;
}

Where `scripts` folder is located under `resources` folder (IntelliJ Idea)

Hope it helps someone

Update 04-2021: Both options are great to combine with [Spring Profiles][1] as this will help you to avoid creating additional config files making your life as the developer easy.

[1]:

[To see links please register here]

Reply

#19
If you came here and **nothing seems to work for you**, then it might be the case that you are affected from some changes that were introduced with `Spring Boot 2.5` and onwards.

Here is the total set of properties which I use for postgresql.

spring:
sql.init.mode: always <-----------------
datasource:
url: jdbc:postgresql://localhost:5432/products
username:
password:
jpa:
defer-datasource-initialization: true <------------------
hibernate:
ddl-auto: create-drop <----------------
database-platform: org.hibernate.dialect.PostgreSQLDialect

I have also marked with `<---` the relevant properties for the current topic in order to achieve the following.
* ORM vendor will create database schema for you from Java Entities model.
* After database schema is created, initial data will be loaded to database from the file `data.sql`

Ps: Don't forget to add the file with initial data, `data.sql` under `src/main/resources`





Also as reference: [Spring Boot 2.5 release notes][1]


[1]:

[To see links please register here]

Reply

#20
For those using MysqlDriver, I tried using Init attribute of @bean annotation and it works.

After created the Schema and Data sql file in the path of ``resources\Scripts``

Add the line in ``application.properties``

spring.jpa.hibernate.ddl-auto=none

Edit the Application content:

package com.spring_mvaen.demo;

import org.springframework.boot.CommandLineRunner;

import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.context.annotation.Bean;
import org.springframework.core.io.ClassPathResource;
import org.springframework.core.io.Resource;
import org.springframework.jdbc.datasource.DriverManagerDataSource;
import org.springframework.jdbc.datasource.init.DatabasePopulator;
import org.springframework.jdbc.datasource.init.DatabasePopulatorUtils;
import org.springframework.jdbc.datasource.init.ResourceDatabasePopulator;

@SpringBootApplication
public class DemoApplication implements CommandLineRunner {

public static void main(String[] args) {
SpringApplication.run(DemoApplication.class, args);
}
@Override
public void run(String... arg0) throws Exception {
System.out.println("Hello world from Command Line Runner");
}

@Bean(name = "dataSource")
public DriverManagerDataSource dataSource() {
DriverManagerDataSource dataSource = new DriverManagerDataSource();
dataSource.setDriverClassName("com.mysql.cj.jdbc.Driver");
dataSource.setUrl("jdbc:mysql://localhost:3306/db_spring_rest?useUnicode=true&useLegacyDatetimeCode=fa lse&serverTimezone=UTC&createDatabaseIfNotExist=true&allowPublicKeyRetrieval=true&useSSL=false");
dataSource.setUsername("root");
dataSource.setPassword("root");

// schema init
Resource initSchema = new ClassPathResource("scripts/schema.sql");
Resource initData = new ClassPathResource("scripts/data.sql");
DatabasePopulator databasePopulator = new ResourceDatabasePopulator(initSchema, initData);
DatabasePopulatorUtils.execute(databasePopulator, dataSource);

return dataSource;
}


}
Reply



Forum Jump:


Users browsing this thread:
1 Guest(s)

©0Day  2016 - 2023 | All Rights Reserved.  Made with    for the community. Connected through