Kotlin 安利贴 3. Spring with Kotlin

本文介绍了如何使用Kotlin进行Spring开发,包括安装步骤、@Autowired的字段、构造器和setter注入,以及@Value和@Controller的用法。强调了Kotlin在Spring中的优雅实现,如字段注入的简化和构造器注入的优势。同时推荐了相关阅读资源。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

本次 More Time 为观众朋友带来拿 Kotlin 写 Spring的介绍。
Spring 官方支持 Kotlin,看这篇报道 , 17年就支持了,17之前可能会有一些问题。现在19年已经完全可用了。
其实也有个 Spring Scala 项目。不过这个项目不是官方支持的。
因此,Spring 官方支持的语言就是

  1. Java
  2. Groovy
  3. Kotlin

好,接下来看怎么用。

安装

  1. 新项目

直接在 Spring Initializar 里装一个就知道了。页面上或者 IDEA 上都有。

  1. 和Java混写

请点击阅读原文看附录,用这份 pom.xml 绝对没错,时间过长,我也不记得从哪里抄来的了😈

接下来看几个关键点的用法

@Autowired

Spring的核心就是 IOC和AOP,大家都知道。不会AOP可以,不会IOC就说不过去了。
当然了,这里用IOC这个词也是和AOP对仗押韵,通常我会称之为依赖注入,DI。

@Autowired 用来注入 stereostype (controller, Component, Service这些的) 和 @Bean 修饰的对象,即 Spring Bean。
有3种方式

  1. 字段注入
  2. 构造函数注入
  3. setter 注入。

字段注入

@Component
class A { }

@Component
class B {
    @Autowired private A a;
}

构造器注入

@Component
class B {
    A a;
    B(A a) {
        this.a = a;
    }
}

setter 注入

@Component
class B {
    A a;

    @Autowired
    void setA(A a) {
        this.a = a;
    }
}

Java里面显然是字段注入看得最爽,当然爽是有代价的,就是单测的时候GG。
就是如果没有Spring环境,就不能实例化一个能用的对象。依赖的东西动无法装载进去。
有一种观点就是单测的时候别加载Spring环境,加载Spring环境的是集成测试。
setter注入代码量比构造器注入还多,不考虑。
并且如果这种情况 final A a; 那么就只能构造器注入了。对于Java来说多一个 final 看上去噪音多了,实际用处也不大。没事把 @Autowired 的字段给改掉的人还是太少了。
OK,看Kotlin怎么做的

@Component
class A {}

@Component
class B(val a: A) {}

this.a = a 不需要。
这就是 kotlin 的 主构造器语法

Java里构造器注入看上去就头大,而 Kotlin 构造器注入非常优雅。

lateint 注入

在JUnit4 里面测试类只能是空的构造函数,JUnit5不用,所以JUnit4只能这么写

@SpringBootTest
class DemoApplicationTests {

	@Autowired
	lateinit var a: A

	@Test
	fun contextLoads() {
		assertThat(a).isNotNull
	}
}

如此注入部分就讲完了。

@Value

Kotlin 支持字符串插值这一神器。

val a = 1
val b = "a"
println("$a$b")

输出 1a
但是 Spring 里面读 .properties 的也是用 $ 啊。
所以 Kotlin 里面用 \$ 表示 $

@Component
class A(@Value("\${x}") val x: String) {}

@Controller

kotlin 支持 = 的函数写法,所以一个可行的时间是吧 controller 做成很薄的一层,完全交给 service 层。更不要再 controller 写 返回 ResponseEntity.badRequest() 的逻辑。统一交给异常处理类。
即这种结构

@Service
class MyService {
    fun f() { }
}

@RestController
class IndexController(val myService: MyService) {

    @GetMapping("/")
    fun index() = myService.f()
}

@ControllerAdvice
class GlobalExceptionHandler {

    @ExceptionHandler(Exception::class)
    fun not1Error(e: Exception): ResponseEntity<String> =
            ResponseEntity.badRequest().body(e.message)
}

BTW

  1. gradle 支持 Kotlin 代替 groovy了,但我用 Maven。
  2. 有些注解的参数可能和 Java不一样,一般搞个 arrayOf 就好了

推荐阅读

  1. https://spring.io/blog/2016/02/15/developing-spring-boot-applications-with-kotlin
  2. https://spring.io/guides/tutorials/spring-boot-kotlin/

    在这里插入图片描述

附录

<project>
  
  <properties>
		<kotlin.version>1.3.50</kotlin.version>
	</properties>

	<dependencies>
		<dependency>
			<groupId>com.fasterxml.jackson.module</groupId>
			<artifactId>jackson-module-kotlin</artifactId>
		</dependency>
		<dependency>
			<groupId>org.jetbrains.kotlin</groupId>
			<artifactId>kotlin-reflect</artifactId>
		</dependency>
    <dependency>
      <groupId>org.jetbrains.kotlin</groupId>
      <artifactId>kotlin-stdlib-jdk8</artifactId>
      <version>${kotlin.version}</version>
    </dependency>
    <dependency>
       <groupId>org.jetbrains.kotlin</groupId>
       <artifactId>kotlin-test</artifactId>
       <version>${kotlin.version}</version>
       <scope>test</scope>
     </dependency>
	</dependencies>

	<build>
		<plugins>
			<plugin>
				<groupId>org.jetbrains.kotlin</groupId>
				<artifactId>kotlin-maven-plugin</artifactId>
				<version>${kotlin.version}</version>
				<executions>
					<execution>
						<id>compile</id>
						<goals> <goal>compile</goal> </goals>
						<configuration>
							<sourceDirs>
								<sourceDir>${project.basedir}/src/main/kotlin</sourceDir>
								<sourceDir>${project.basedir}/src/main/java</sourceDir>
							</sourceDirs>
						</configuration>
					</execution>
					<execution>
						<id>test-compile</id>
						<goals> <goal>test-compile</goal> </goals>
						<configuration>
							<sourceDirs>
								<sourceDir>${project.basedir}/src/test/kotlin</sourceDir>
								<sourceDir>${project.basedir}/src/test/java</sourceDir>
							</sourceDirs>
						</configuration>
					</execution>
				</executions>
			</plugin>
			<plugin>
				<groupId>org.apache.maven.plugins</groupId>
				<artifactId>maven-compiler-plugin</artifactId>
				<version>3.5.1</version>
				<executions>
					<execution>
						<id>default-compile</id>
						<phase>none</phase>
					</execution>
					<execution>
						<id>default-testCompile</id>
						<phase>none</phase>
					</execution>
					<execution>
						<id>java-compile</id>
						<phase>compile</phase>
						<goals> <goal>compile</goal> </goals>
					</execution>
					<execution>
						<id>java-test-compile</id>
						<phase>test-compile</phase>
						<goals> <goal>testCompile</goal> </goals>
					</execution>
				</executions>
			</plugin>
			<plugin>
				<groupId>org.springframework.boot</groupId>
				<artifactId>spring-boot-maven-plugin</artifactId>
				<executions>
					<execution>
						<goals>
							<goal>repackage</goal>
						</goals>
					</execution>
				</executions>
			</plugin>
			<plugin>
				<groupId>org.jetbrains.kotlin</groupId>
				<artifactId>kotlin-maven-plugin</artifactId>
				<configuration>
					<args>
						<arg>-Xjsr305=strict</arg>
					</args>
					<compilerPlugins>
						<plugin>spring</plugin>
					</compilerPlugins>
				</configuration>
				<dependencies>
					<dependency>
						<groupId>org.jetbrains.kotlin</groupId>
						<artifactId>kotlin-maven-allopen</artifactId>
						<version>${kotlin.version}</version>
					</dependency>
				</dependencies>
			</plugin>
		</plugins>
	</build>

</project>

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值