我正在使用Spring Boot并尝试在内存中使用H2数据库(在内存中)。我的Spring数据存储库实现无法正常工作,我需要对其进行调试。
我将我的项目(不使用原始项目)简化为以下示例,以隔离并演示该问题。该项目可以在GitHub中找到。
Eclipse项目结构:
pom.xml:
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>2.0.5.RELEASE</version>
</parent>
<dependencies>
<dependency>
<groupId>org.glassfish.jaxb</groupId>
<artifactId>jaxb-runtime</artifactId>
<version>2.3.0.1</version>
</dependency>
<dependency>
<groupId>javax.activation</groupId>
<artifactId>activation</artifactId>
<version>1.1.1</version>
</dependency>
<dependency>
<groupId>javax.transaction</groupId>
<artifactId>jta</artifactId>
<version>1.1</version>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<dependency>
<groupId>org.apache.maven</groupId>
<artifactId>maven-model</artifactId>
<version>3.5.4</version>
</dependency>
<dependency>
<groupId>org.modelmapper</groupId>
<artifactId>modelmapper</artifactId>
<version>2.2.0</version>
</dependency>
<dependency>
<groupId>com.h2database</groupId>
<artifactId>h2</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-jpa</artifactId>
</dependency>
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
<optional>true</optional>
</dependency>
</dependencies>
<build>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
<configuration>
<executable>true</executable>
<skipTests>true</skipTests>
</configuration>
<executions>
<execution>
<goals>
<goal>repackage</goal>
</goals>
</execution>
</executions>
</plugin>
</plugins>
</build>
<repositories>
<repository>
<id>spring-releases</id>
<url>https://repo.spring.io/libs-release</url>
</repository>
</repositories>
<pluginRepositories>
<pluginRepository>
<id>spring-releases</id>
<url>https://repo.spring.io/libs-release</url>
</pluginRepository>
</pluginRepositories>
application.properties:
debug=true
logging.level.root=WARN
logging.level.org.foo=WARN
logging.level.org.springframework=WARN
spring.datasource.driver-class-name=org.h2.Driver
spring.datasource.url=jdbc:h2:mem:test_database;DB_CLOSE_DELAY=-1
spring.datasource.username=sa
spring.datasource.password=sa
spring.jpa.database-platform=org.hibernate.dialect.H2Dialect
spring.h2.console.enabled=true
spring.h2.console.path=/h2-console
主要配置类:
@SpringBootApplication
@Configuration
@PropertySource("classpath:application.properties")
@EnableJpaRepositories(basePackages = "org.foo.repositories")
@EntityScan("org.foo.entities")
@EnableTransactionManagement
public class Application {
Logger logger = LoggerFactory.getLogger(Application.class);
public static void main(String[] args) {
Logger logger = LoggerFactory.getLogger(Application.class);
SpringApplication.run(Application.class, args);
logger.info("Application started");
}
@Bean
public CommandLineRunner commandLineRunner(ApplicationContext ctx) {
return args -> {
logger.trace("Let's inspect the beans provided by Spring Boot:");
String[] beanNames = ctx.getBeanDefinitionNames();
Arrays.sort(beanNames);
for (String beanName : beanNames) {
logger.trace(beanName);
}
};
}
}
学生实体类:
package org.foo.entities;
import javax.persistence.Entity;
import javax.persistence.Id;
import lombok.Data;
@Entity
@Data
public class Student {
@Id
private long id;
private String first_name;
private String last_name;
}
StudentRepository类:
@Repository
public interface StudentRepository extends JpaRepository<Student, Long> {
@Override
List<Student> findAll();
}
StudentRepositoryTester类:
@RunWith(SpringRunner.class)
@SpringBootTest
@Transactional
@ContextConfiguration(classes = { org.foo.Application.class }, loader = AnnotationConfigContextLoader.class)
public class StudentRepositoryTester {
Logger logger = LoggerFactory.getLogger(StudentRepositoryTester.class);
@Autowired
private StudentRepository studentRepository;
@Test
public void findAllTester() {
Iterable<Student> students = studentRepository.findAll();
for(Student student: students) {
logger.info(student.toString());
}
long size = StreamSupport.stream(students.spliterator(), false).count();
assertTrue(students != null && size == 3);
}
}
data.sql:
USE `test_database`;
INSERT INTO `students` (`id`,`first_name`,`last_name`) VALUES (1,'First1','Last1');
INSERT INTO `students` (`id`,`first_name`,`last_name`) VALUES (2,'First2','Last2');
INSERT INTO `students` (`id`,`first_name`,`last_name`) VALUES (3,'First3','Last3');
schema.sql:
DROP ALL OBJECTS;
CREATE SCHEMA `test_database`;
USE `test_database`;
CREATE TABLE `students` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`first_name` varchar(45) NOT NULL,
`last_name` varchar(45) NOT NULL,
PRIMARY KEY (`id`)
);
我可以在控制台日志中看到已填充H2,因为我可以看到data.sql中的语句已执行。我在日志中没有发现其他可疑的东西。
具体问题:
运行StudentRepositoryTester测试类,我看到(在assert语句上带有断点)没有实体返回。我不明白为什么。也许我错过了Spring Boot配置注释中的某些内容?
我试图在断点处检查数据库内容,但是找不到找到H2数据库的方法。我遵循this tutorial打开H2的Web资源管理器应用程序,但是localhost:8080没有提供任何服务。难道我做错了什么?另外,还有另一种方法可以调试H2数据库(在内存中)发生的情况吗?
请注意,相应的Eclipse项目已上传到GitHub中,以方便讨论。
答案 0 :(得分:0)
打开由Hibernate执行的SQL语句的日志记录(在application.properties中):
logging.level.org.hibernate.SQL=DEBUG
这会将所有SQL语句输出到控制台。但是没有注入变量。这应该可以帮助您进行故障排除。
答案 1 :(得分:0)
H2引导脚本由ScriptUtils
处理因此,在application.properties中增加其日志记录级别:
logging.level.org.springframework.jdbc.datasource.init.ScriptUtils=DEBUG