Estou tentando criar uma forma que, ao iniciar o sistema, ele popule uma tabela e persista no SqlServer, mas tenho que garantir que, se o sistema iniciar novamente, não realize outro insert.
Verifiquei que é possível usando um arquivo com nome data.sql“How-to” Guides (spring.io), mas quando eu uso if no código, o sql retorna:
Causedby:org.h2.jdbc.JdbcSQLSyntaxErrorException:SyntaxerrorinSQLstatement"IF[*] (NOT EXISTS(SELECT * FROM USUARIO U WHERE U.NOME='Moderador'))";SQLstatement:IF(notexists(select*fromUSUARIOuwhereu.nome='Moderador'))
Aparentemente tu está usando H2!
SQL Server e H2 tem diferenças de sintaxe, por isso é acusado erro.
L
Lucas_Camara
Para isso, acho que seria melhor tu usar ferramentas como flyway ou liquibase. Qualquer uma dessas vai ser uma mão na roda pra tu! Muito bom usar elas em projetos para manter o banco de dados.
org.springframework.beans.factory.BeanCreationException: Error creating bean with name ‘dataSourceScriptDatabaseInitializer’ defined in class path resource [org/springframework/boot/autoconfigure/sql/init/DataSourceInitializationConfiguration.class]: Invocation of init method failed; nested exception is org.springframework.jdbc.datasource.init.ScriptStatementFailedException: Failed to execute SQL script statement #2 of URL [file:/C:/Users/Suporte/Documents/JEE%20WorkSpace/eaas-CLOUD/eaas-cloud-api/target/classes/data.sql]: IF (NOT EXISTS(SELECT * FROM eaas_cloud.dbo.[user] u where u.name=‘admin’)); nested exception is com.microsoft.sqlserver.jdbc.SQLServerException: Incorrect syntax near ‘)’.
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.initializeBean(AbstractAutowireCapableBeanFactory.java:1804) ~[spring-beans-5.3.14.jar:5.3.14]
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:620) ~[spring-beans-5.3.14.jar:5.3.14]
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:542) ~[spring-beans-5.3.14.jar:5.3.14]
at org.springframework.beans.factory.support.AbstractBeanFactory.lambda$doGetBean$0(AbstractBeanFactory.java:335) ~[spring-beans-5.3.14.jar:5.3.14]
at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:234) ~[spring-beans-5.3.14.jar:5.3.14]
at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:333) ~[spring-beans-5.3.14.jar:5.3.14]
at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:208) ~[spring-beans-5.3.14.jar:5.3.14]
at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:322) ~[spring-beans-5.3.14.jar:5.3.14]
at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:208) ~[spring-beans-5.3.14.jar:5.3.14]
at org.springframework.context.support.AbstractApplicationContext.getBean(AbstractApplicationContext.java:1154) ~[spring-context-5.3.14.jar:5.3.14]
at org.springframework.context.support.AbstractApplicationContext.finishBeanFactoryInitialization(AbstractApplicationContext.java:908) ~[spring-context-5.3.14.jar:5.3.14]
at org.springframework.context.support.AbstractApplicationContext.refresh(AbstractApplicationContext.java:583) ~[spring-context-5.3.14.jar:5.3.14]
at org.springframework.boot.web.servlet.context.ServletWebServerApplicationContext.refresh(ServletWebServerApplicationContext.java:145) ~[spring-boot-2.6.2.jar:2.6.2]
at org.springframework.boot.SpringApplication.refresh(SpringApplication.java:730) ~[spring-boot-2.6.2.jar:2.6.2]
at org.springframework.boot.SpringApplication.refreshContext(SpringApplication.java:412) ~[spring-boot-2.6.2.jar:2.6.2]
at org.springframework.boot.SpringApplication.run(SpringApplication.java:302) ~[spring-boot-2.6.2.jar:2.6.2]
at org.springframework.boot.SpringApplication.run(SpringApplication.java:1301) ~[spring-boot-2.6.2.jar:2.6.2]
at org.springframework.boot.SpringApplication.run(SpringApplication.java:1290) ~[spring-boot-2.6.2.jar:2.6.2]
at com.dnia.eaascloud.EaasCloudApiApplication.main(EaasCloudApiApplication.java:11) ~[classes/:na]
Caused by: org.springframework.jdbc.datasource.init.ScriptStatementFailedException: Failed to execute SQL script statement #2 of URL [file:/C:/Users/Suporte/Documents/JEE%20WorkSpace/eaas-CLOUD/cloud-api/target/classes/data.sql]: IF (NOT EXISTS(SELECT * FROM eaas_cloud.dbo.[user] u where u.name=‘admin’)); nested exception is com.microsoft.sqlserver.jdbc.SQLServerException: Incorrect syntax near ‘)’.
B
Bruno_Moreira_Reis
Vou tentar com flyway
L
Lucas_Camara
O flyway serve exatamente para controlar esse tipo de coisa (criar tabelas, executar cargas iniciais, etc). E vc mantém todos os scripts na própria aplicação. Porém, ele necessita que seja criada uma tabela no schema da aplicação para que ele guarde esse controle (o que já foi executado, o que deu certo ou não).
Se me lembro bem, há restrições no que vc pode executar no SQL. Por exemplo, no que vc precisa executar, acho que teria que ser apenas:
Isso seria executa no momento em que a aplicação fosse iniciada apenas uma única vez.
B
Bruno_Moreira_Reis
Se eu reiniciar então ele saberia que que o insert já foi realizado?
J
Solucao aceita
Jonathan_Medeiros2 likes
Sim, o controle de schema evolution dele só aplicaria a migration uma única vez no DB.
O controle pode ser observado pela tabela flyway_schema_version, que é a tabela que o flyway usa para controlar as migrations já aplicadas de não aplicadas e inclusive migrations modificadas pós execução (isso causaria um erro).