SpringBoot 配置文件之 EL 表达式 (@Value)

1 配置文件种类

Springboot 有两种配置文件,一种是 application.properties,一种是 application.yml,两种配置文件,如果同时存在的话,那么 application.properties 的优先级要高于 application.yml

2 application.properties 讲解

2.1 修改内嵌容器端口号和访问路径

 
  1. # 修改访问端口
  2. server.port=8888
  3. # 修改默认的访问路径 //helloboot
  4. server.context-path=/helloboot
 

2.2 自定义属性配置

配置文件中是 msg=Hello World

那么在类里面,按照下面写直接注入

 
  1. @Value("${msg}")
  2. private String msg;
 

2.3 配置变量引用

配置文件中是  

 
  1. hello=bjsxt 
  2. msg=Hello World ${hello}
 

在类中直接使用

 
  1. @Value("${msg}")
  2. private String msg;
 

2.4  随机值配置

2.4.1 配置随机值

在配置文件中:

 
  1. num=${random.int}
  2. msg=Hello World ${num}
 

在类中直接使用:

 
  1. @Value("${msg}")
  2. private String msg;
 

用处: 配置随机值, 在程序中如果有一些运算需要一个随机值, 那么可以使用该方式来生成。 注意, 只生成一次

2.4.2 配置随机端口

server.port=${random.int[1024,9999]}

用处: 在 SpringCloud 的微服务中, 我们是不需要记录 IP 与端口号的。 那么我们也就不需要去维护服务的端口号。 让他随机生成就可以了。

2.5 @@

${} 和 @@都是 springboot 引用属性变量的方式,具体区别与用法:

  • ${} 常用于 pom.xml,和 src/main/resources/application.properties 等默认配置文件的属性变量引用
  • @@方式常用于引用 springboot 非默认配置文件(即其他配置文件)中的变量,是 springboot 为替代 ${} 属性占位符产生,原因是 ${} 会被 maven 处理,所以引用非默认配置文件时起不到引用变量的作用。

语法为:field_name=@field_value@

示例:在实际项目开发中,为了在不同环境进行测试,我们会在 src/main/resources 目录下创建 config 文件夹,并在 config 中创建多个 properties 文件,例如:local.properties, development.properties, production.properties,
当我们在 src/main/resources/application.properties 文件中引用 src/main/resources/config/local.properties 的属性变量时,就要使用 @@方式

3 yml 配置文件

yml 配置文件是 SpringBoot 中新增的一种配置文件格式。 特点: 具备天然的树状结构

3.1 yml 配置文件与 properties 文件的区别

配置文件的扩展名有变化

配置文件中的语法有变化

3.2 yml 配置文件的语法

3.2.1 分隔符号不同

在 properties 文件中是以 “.” 进行分割, 在 yml 中使用 “: ” 进行分割

3.2.2 yml 赋值

yml 的数据格式和 json 的格式很像, 都是 K-V 结构的。 并且是通过 “: ” 赋值

3.2.3 尽量不用 TAB 而是 Enter

在 yml 中缩进一定不能使用 TAB 件, 否则会报错。

3.2.4 冒号后加空格

每个 K 的冒号后面一定要加一个空格,否则不能识别,因此,一定要在冒号后加空格

详细的.properties 和.yml 文件比较链接

4 Spring 中 EL 表达式讲解

4.1 EL 表达式简介

spring EL-Spring 表达式语言,支持在 xml 和注解中使用表达式,类似于 JSP 的 EL 表达式语言

了解 jsp 中的 EL 表达式

Spring 开发中经常涉及调用各种资源的情况,包括普通文件、网址、配置文件、系统环境变量等,我们可以使用 Spring 的表达式语言实现资源的注入

SpringEL 从名字来看就能看出,和 EL 是有点关系的,SpringEL 的使用和 EL 表达式的使用非常相似,EL 表达式在 JSP 页面更方便的获取后台中的值,而 SpringEL 就是为了更方便获取 Spring 容器中的 Bean 的值 ,EL 使用 ${},$ 是去找外部配置的参数,将值赋过来 , 而 SpringEL 使用 #{} 进行表达式的声明

在 @Value () 中使用 $ 用来从配置文件 (.properties 或.yml) 中获取的,使用 #是从一个定义个 bean 对象中获取对应属性

#{} 功能比 ${} 功能更强大,强调的是把内容赋值给属性,示例:

  • 表示常量: #{‘1’} ,#{’ This is a Constant Str’},直接注入不能使用 ${}EL${} 不支持直接指定常量
  • 使用 java 代码 new/instance of: 此方法只能是 java.lang 下的类才可以省略包名 #{“new Spring (‘Hello World’)”}
  • 使用 T (Type): 使用 “T (Type)” 来表示 java.lang.Class 实例,同样,只有 java.lang 下的类才可以省略包名。此方法一般用来引用常量或静态方法,#{“T (Integer).MAX_VALUE”}
  • 变量: 使用 “#bean_id” 来获取,#{“beanId.field”}
  • 方法调用: #{“#abc.substring(0,1)”}
  • 运算符表达式: 算数表达式,比较表达式,逻辑表达式,赋值表达式,三目表达式,正则表达式
  • 判断空: #{“name?:’other’”}
  • #{} 和 ${} 可以混合使用,但是必须 #{} 在外面 注意不能反过来
  • SpEL 还支持使用标准的 “.” 符号,即嵌套属性 prop1.prop2.prop3 和属性值的设置
  • 直接使用#{} 注入 bean 对象

定义的 bean 节点

 
  1. <bean id="itemBean" class="com.lei.demo.el.Item">
  2. <property name="name" value="itemA" />
  3. <property name="total" value="10" />
  4. </bean>
  5.  
  6. <bean id="customerBean" class="com.lei.demo.el.Customer">
  7. <property name="item" value="#{itemBean}" />
  8. <property name="itemName" value="#{itemBean.name}" />
  9. </bean>
 

#{itemBean}—— 将 itemBean 注入到 customerBean 的 item 属性中

#{itemBean.name}—— 将 itemBean 的 name 属性,注入到 customerBean 的属性 itemName 中

4.2 表达式操作符

  • 关系操作符:包括:等于 (==, eq),不等于 (!=, ne),小于 (<, lt),,小于等于 (<= , le),大于 (>, gt),大于等于 (>=, ge)
  • 逻辑操作符:包括:and,or,and not (!)
  • 数学操作符:包括:加 (+),减 (-),乘 (*),除 (/),取模 (%),幂指数 (^)

 

4.3 EL 表达式示例

EL 表达式使用示例

 
  1. public class ELConfig {
  2. @Valule("test")//注入字符串
  3. private String name;
  4. @Valule("#{systemProperties['os.name']}")//注入操作系统属性
  5. private String osName;
  6. @Valule("#{T(java.lang.Math).random()*100.0}")//注入表达式结果
  7. private double randomNumber;
  8. @Valule("#{demoService.another}")//注入其他bean属性
  9. private String fromAnother;
  10.  
  11. @Valule("classpath:com/test/test.txt")//注入文件资源
  12. private Resource testFile;
  13.  
  14. @Valule("https://www.baidu.com")//注入网址资源
  15. private Resource testUrl;
  16.  
  17. @Valule("${book.name}")//注入配置文件
  18. private String bookName;
  19.  
  20.  
  21.  
  22. 使用?.符号代表若然左边的值为null,将不执行右边方法,
  23. 即,当左边不为空才执行右边的方法
  24. @Value("#{testConstant.showProperty()?.toUpperCase}")
  25. private String method4;
  26.  
  27. 判断空,当左边为空就取冒号后的值: #{“name?:'other'”}
  28. @Value("#{test?:'123456'}")
  29. private String name;
  30.  
  31. 注入字符不存在属性值并指定默认值,默认值使用冒号分隔 :
  32. 注入常量其实就可以指定一个不存在的配置然后使用默认值,此处test的值为空字符串
  33. @Value("${test:''}")
  34. private String skill;
  35.  
  36.  
  37. @@方式常用于引用springboot非默认配置文件
  38. field_name=@field_value@
  39.  
  40. }
 

spEL:如果是字面值,用spel的意义不大 动态赋值
语法:

value="#{}"

作用:

可以调用指定类的静态方法或者静态属性
可以引用其他Bean
可以引用其他Bean的属性
可以调用其他方法,还可以链式操作
还支持算术运算法  还可以作字符串连接 还可以比较运算符等

SpEL引用类的静态变量,或者静态方法,也可以引用其他Bean:

类:

static String a="静态值";
         public static String getA(){
         System.out.println("调用静态方法,返回静态值");
         return a;
         }

xml配置:

<bean id="getHello" class="hello.Hello" p:name="你好"></bean>
<!--使用SpEL引用类的静态变量,或者静态方法,也可以引用其他Bean 值是Bean的id-->
<bean id="person" class="hello.Person" p:name="#{T(hello.Hello).a}" p:hello="#{getHello}"></bean>

输出:

调用静态方法,返回静态值
Person{name='静态值', hello=Hello{name='你好', numberInt=0, numberDouble=0.0}}

总结:
调用其他类的静态变量的时候实际调用了该属性的get变量方法,
所以必须有get变量这个方法,并且是public类型的

也可以直接调用其他Bean类的静态方法,如:

p:name="#{T(hello.Hello).getA()}"

注意 那个静态属性或者静态方法所在的类要用T包裹起来。

调用其他Bean的属性:

<bean id="getHello" class="hello.Hello" p:name="你好"></bean>
<bean id="person" class="hello.Person" p:name="#{getHello.name}" p:hello="#{getHello}"></bean>

使用运算符:在SpEL中使用运算符

<bean id="getHello" class="hello.Hello" p:name="你好" p:numberInt="12"></bean>
<bean id="person" class="hello.Person" p:name="#{getHello.numberInt>12?'大于12':'小于12'}" p:hello="#{getHello}"></bean>

输出:

Person{name='小于12', hello=Hello{name='你好', numberInt=12, numberDouble=0.0}}

 

posted @ 2024-07-01 10:38  CharyGao  阅读(67)  评论(0)    收藏  举报