Kotlin JdbcTemplate 为空
Kotlin JdbcTemplate Null
我正在尝试将我的应用程序从 java 转换为 kotlin,目前正在混合使用 Java 和 Kotlin。我正在尝试先将我的存储库 类 转换为 Kotlin。这是使用 Spring JDBC。我做错了什么吗?
package com.meteor.coral.resources.useradministration.domain
import org.springframework.beans.factory.annotation.Autowired
import org.springframework.jdbc.core.JdbcTemplate
import org.springframework.jdbc.core.RowMapper
import org.springframework.stereotype.Repository
import java.sql.ResultSet
import java.sql.SQLException
@Repository
open class AppUserJdbcRepository {
@Autowired
private var jdbcTemplate: JdbcTemplate? = null
fun findByFirstName(firstName: String): AppUser {
print("hello")
return jdbcTemplate!!.queryForObject("select firstname, lastname from m_appuser where firstname = ?", arrayOf<Any>(firstName), AppUserRowMapper())
}
internal inner class AppUserRowMapper : RowMapper<AppUser> {
@Throws(SQLException::class)
override fun mapRow(resultSet: ResultSet, i: Int): AppUser {
val appUser = AppUser(resultSet.getString("firstname"),resultSet.getString("lastName") )
return appUser
}
}
}
我的考试还在Java
package com.meteor.coral.resources.useradministration;
import com.meteor.coral.UserAdministrationServiceApplication;
import com.meteor.coral.resources.useradministration.domain.AppUser;
import com.meteor.coral.resources.useradministration.domain.AppUserJdbcRepository;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.context.SpringBootTest;
import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
@SpringBootTest(classes = {UserAdministrationServiceApplication.class})
@RunWith(SpringJUnit4ClassRunner.class)
public class AppUserJdbcRepositoryTest {
@Autowired
private AppUserJdbcRepository appUserJdbcRepository;
private static final Logger LOGGER = LoggerFactory.getLogger(AppUserJdbcRepositoryTest.class);
@Test
public void testAppFetch() {
AppUser appUser = appUserJdbcRepository.findByFirstName("CARLO");
LOGGER.info(appUser.getId() + "");
LOGGER.info(appUser.getFirstname());
LOGGER.info(appUser.getLastname());
}
}
jdbctemplate 始终为空。
hello
java.lang.NullPointerException
at com.meteor.coral.resources.useradministration.domain.AppUserJdbcRepository.findByFirstName(AppUserJdbcRepository.kt:18)
at com.meteor.coral.resources.useradministration.AppUserJdbcRepositoryTest.testAppFetch(AppUserJdbcRepositoryTest.java:25)
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.base/java.lang.reflect.Method.invoke(Method.java:566)
at org.junit.runners.model.FrameworkMethod.runReflectiveCall(FrameworkMethod.java:59)
at org.junit.internal.runners.model.ReflectiveCallable.run(ReflectiveCallable.java:12)
at org.junit.runners.model.FrameworkMethod.invokeExplosively(FrameworkMethod.java:56)
at org.junit.internal.runners.statements.InvokeMethod.evaluate(InvokeMethod.java:17)
at org.springframework.test.context.junit4.statements.RunBeforeTestExecutionCallbacks.evaluate(RunBeforeTestExecutionCallbacks.java:74)
at org.springframework.test.context.junit4.statements.RunAfterTestExecutionCallbacks.evaluate(RunAfterTestExecutionCallbacks.java:84)
at org.springframework.test.context.junit4.statements.RunBeforeTestMethodCallbacks.evaluate(RunBeforeTestMethodCallbacks.java:75)
at org.springframework.test.context.junit4.statements.RunAfterTestMethodCallbacks.evaluate(RunAfterTestMethodCallbacks.java:86)
at org.springframework.test.context.junit4.statements.SpringRepeat.evaluate(SpringRepeat.java:84)
at org.junit.runners.ParentRunner.runLeaf(ParentRunner.java:366)
at org.springframework.test.context.junit4.SpringJUnit4ClassRunner.runChild(SpringJUnit4ClassRunner.java:251)
at org.springframework.test.context.junit4.SpringJUnit4ClassRunner.runChild(SpringJUnit4ClassRunner.java:97)
at org.junit.runners.ParentRunner.run(ParentRunner.java:331)
at org.junit.runners.ParentRunner.schedule(ParentRunner.java:79)
at org.junit.runners.ParentRunner.runChildren(ParentRunner.java:329)
at org.junit.runners.ParentRunner.access0(ParentRunner.java:66)
at org.junit.runners.ParentRunner.evaluate(ParentRunner.java:293)
at org.springframework.test.context.junit4.statements.RunBeforeTestClassCallbacks.evaluate(RunBeforeTestClassCallbacks.java:61)
at org.springframework.test.context.junit4.statements.RunAfterTestClassCallbacks.evaluate(RunAfterTestClassCallbacks.java:70)
at org.junit.runners.ParentRunner.evaluate(ParentRunner.java:306)
at org.junit.runners.ParentRunner.run(ParentRunner.java:413)
at org.springframework.test.context.junit4.SpringJUnit4ClassRunner.run(SpringJUnit4ClassRunner.java:190)
at org.junit.runner.JUnitCore.run(JUnitCore.java:137)
at com.intellij.junit4.JUnit4IdeaTestRunner.startRunnerWithArgs(JUnit4IdeaTestRunner.java:69)
at com.intellij.rt.junit.IdeaTestRunner$Repeater.startRunnerWithArgs(IdeaTestRunner.java:33)
at com.intellij.rt.junit.JUnitStarter.prepareStreamsAndStart(JUnitStarter.java:220)
at com.intellij.rt.junit.JUnitStarter.main(JUnitStarter.java:53)
谢谢,
属性 在 kotlin 中使用 spring 注入需要 lateinit 关键字:
@Autowired
private lateinit var jdbcTemplate: JdbcTemplate
通常你想要进行构造函数注入,因为这允许你删除 Autowired 注释并使其成为 val:
class AppUserJdbcRepository(private val jdbcTemplate: JdbcTemplate){
为了完整起见:您不应该(忽略罕见的极端情况)使用“!!” kotlin 中的运算符,因为这基本上只是退回到 java 的可空性方法。至少根据我的经验,用 '?: throw MyCustomException("jdbcTemplate was null during initialization")' 替换它更容易调试,我经常发现考虑它也会暴露不必要的可空性。
我正在尝试将我的应用程序从 java 转换为 kotlin,目前正在混合使用 Java 和 Kotlin。我正在尝试先将我的存储库 类 转换为 Kotlin。这是使用 Spring JDBC。我做错了什么吗?
package com.meteor.coral.resources.useradministration.domain
import org.springframework.beans.factory.annotation.Autowired
import org.springframework.jdbc.core.JdbcTemplate
import org.springframework.jdbc.core.RowMapper
import org.springframework.stereotype.Repository
import java.sql.ResultSet
import java.sql.SQLException
@Repository
open class AppUserJdbcRepository {
@Autowired
private var jdbcTemplate: JdbcTemplate? = null
fun findByFirstName(firstName: String): AppUser {
print("hello")
return jdbcTemplate!!.queryForObject("select firstname, lastname from m_appuser where firstname = ?", arrayOf<Any>(firstName), AppUserRowMapper())
}
internal inner class AppUserRowMapper : RowMapper<AppUser> {
@Throws(SQLException::class)
override fun mapRow(resultSet: ResultSet, i: Int): AppUser {
val appUser = AppUser(resultSet.getString("firstname"),resultSet.getString("lastName") )
return appUser
}
}
}
我的考试还在Java
package com.meteor.coral.resources.useradministration;
import com.meteor.coral.UserAdministrationServiceApplication;
import com.meteor.coral.resources.useradministration.domain.AppUser;
import com.meteor.coral.resources.useradministration.domain.AppUserJdbcRepository;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.context.SpringBootTest;
import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
@SpringBootTest(classes = {UserAdministrationServiceApplication.class})
@RunWith(SpringJUnit4ClassRunner.class)
public class AppUserJdbcRepositoryTest {
@Autowired
private AppUserJdbcRepository appUserJdbcRepository;
private static final Logger LOGGER = LoggerFactory.getLogger(AppUserJdbcRepositoryTest.class);
@Test
public void testAppFetch() {
AppUser appUser = appUserJdbcRepository.findByFirstName("CARLO");
LOGGER.info(appUser.getId() + "");
LOGGER.info(appUser.getFirstname());
LOGGER.info(appUser.getLastname());
}
}
jdbctemplate 始终为空。
hello
java.lang.NullPointerException
at com.meteor.coral.resources.useradministration.domain.AppUserJdbcRepository.findByFirstName(AppUserJdbcRepository.kt:18)
at com.meteor.coral.resources.useradministration.AppUserJdbcRepositoryTest.testAppFetch(AppUserJdbcRepositoryTest.java:25)
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.base/java.lang.reflect.Method.invoke(Method.java:566)
at org.junit.runners.model.FrameworkMethod.runReflectiveCall(FrameworkMethod.java:59)
at org.junit.internal.runners.model.ReflectiveCallable.run(ReflectiveCallable.java:12)
at org.junit.runners.model.FrameworkMethod.invokeExplosively(FrameworkMethod.java:56)
at org.junit.internal.runners.statements.InvokeMethod.evaluate(InvokeMethod.java:17)
at org.springframework.test.context.junit4.statements.RunBeforeTestExecutionCallbacks.evaluate(RunBeforeTestExecutionCallbacks.java:74)
at org.springframework.test.context.junit4.statements.RunAfterTestExecutionCallbacks.evaluate(RunAfterTestExecutionCallbacks.java:84)
at org.springframework.test.context.junit4.statements.RunBeforeTestMethodCallbacks.evaluate(RunBeforeTestMethodCallbacks.java:75)
at org.springframework.test.context.junit4.statements.RunAfterTestMethodCallbacks.evaluate(RunAfterTestMethodCallbacks.java:86)
at org.springframework.test.context.junit4.statements.SpringRepeat.evaluate(SpringRepeat.java:84)
at org.junit.runners.ParentRunner.runLeaf(ParentRunner.java:366)
at org.springframework.test.context.junit4.SpringJUnit4ClassRunner.runChild(SpringJUnit4ClassRunner.java:251)
at org.springframework.test.context.junit4.SpringJUnit4ClassRunner.runChild(SpringJUnit4ClassRunner.java:97)
at org.junit.runners.ParentRunner.run(ParentRunner.java:331)
at org.junit.runners.ParentRunner.schedule(ParentRunner.java:79)
at org.junit.runners.ParentRunner.runChildren(ParentRunner.java:329)
at org.junit.runners.ParentRunner.access0(ParentRunner.java:66)
at org.junit.runners.ParentRunner.evaluate(ParentRunner.java:293)
at org.springframework.test.context.junit4.statements.RunBeforeTestClassCallbacks.evaluate(RunBeforeTestClassCallbacks.java:61)
at org.springframework.test.context.junit4.statements.RunAfterTestClassCallbacks.evaluate(RunAfterTestClassCallbacks.java:70)
at org.junit.runners.ParentRunner.evaluate(ParentRunner.java:306)
at org.junit.runners.ParentRunner.run(ParentRunner.java:413)
at org.springframework.test.context.junit4.SpringJUnit4ClassRunner.run(SpringJUnit4ClassRunner.java:190)
at org.junit.runner.JUnitCore.run(JUnitCore.java:137)
at com.intellij.junit4.JUnit4IdeaTestRunner.startRunnerWithArgs(JUnit4IdeaTestRunner.java:69)
at com.intellij.rt.junit.IdeaTestRunner$Repeater.startRunnerWithArgs(IdeaTestRunner.java:33)
at com.intellij.rt.junit.JUnitStarter.prepareStreamsAndStart(JUnitStarter.java:220)
at com.intellij.rt.junit.JUnitStarter.main(JUnitStarter.java:53)
谢谢,
属性 在 kotlin 中使用 spring 注入需要 lateinit 关键字:
@Autowired
private lateinit var jdbcTemplate: JdbcTemplate
通常你想要进行构造函数注入,因为这允许你删除 Autowired 注释并使其成为 val:
class AppUserJdbcRepository(private val jdbcTemplate: JdbcTemplate){
为了完整起见:您不应该(忽略罕见的极端情况)使用“!!” kotlin 中的运算符,因为这基本上只是退回到 java 的可空性方法。至少根据我的经验,用 '?: throw MyCustomException("jdbcTemplate was null during initialization")' 替换它更容易调试,我经常发现考虑它也会暴露不必要的可空性。