哈尔滨网站建设方案服务,优秀的公司网站,网站建设对帮助信息的设置,wordpress 搜索页面讲解YML使用场景、语法和解析 1.基础知识1.1 什么是YML1.2 YML优点1.3 YML使用场景 2.YML语法2.1 基础语法2.2 字面量数据类型2.2.1 字符串2.2.2 NULL2.4.5 时间戳#xff08;timestamp#xff09; 2.3 对象\MAP类型2.4 数组/List/Set2.4.1 值为基础类型2.4.2 值为对象2.4.3 … 讲解YML使用场景、语法和解析 1.基础知识1.1 什么是YML1.2 YML优点1.3 YML使用场景 2.YML语法2.1 基础语法2.2 字面量数据类型2.2.1 字符串2.2.2 NULL2.4.5 时间戳timestamp 2.3 对象\MAP类型2.4 数组/List/Set2.4.1 值为基础类型2.4.2 值为对象2.4.3 多维数组2.4.4 复杂类型 2.5 显示类型2.6 引用和复用 3.YML解析3.1准备工作3.1 spring解析3.1.1 Environment注解3.1.2 YamlPropertiesFactoryBean 3.2 SnakeYml组件3.2.1 pom依赖3.2.2 解析yml文件到map3.2.3 解析yml到vo对象3.2.4 vo生成yml格式字符串 3.3 jackson组件3.3.1 pom依赖3.3.2 解析yml文件到map3.3.3 解析yml到vo对象 4.总结4.1 XML、JSON、YAML4.2 易错点 1.基础知识
1.1 什么是YML
YAML 是 “YAML Ain’t a Markup Language”YAML 不是一种标记语言的递归缩写。在开发的这种语言时YAML 的意思其实是”Yet Another Markup Language”仍是一种标记语言。
YAML是一个类似 XML、JSON 的标记性语言。YAML 强调以数据为中心并不是以标识语言为重点。因而 YAML 本身的定义比较简单号称“一种人性化的数据格式语言”。
1.2 YML优点
YAML是一种非常简单的基于文本的人类可读的语言用于在人和计算机之间交换数据。YAML是不是一种编程语言。它主要用于存储配置信息。YAML 的缩进就像 Python 的缩进一样优雅。YAML 还减少了 JSON 和 XML 文件中的大部分“噪音”格式例如引号、方括号和大括号
1.3 YML使用场景
yml主要用于软件配置大有替代properties、XML、JSON的趋势主要其格式简洁易懂
2.YML语法
2.1 基础语法
先看yml示例:
person:name: 蒋增奎gender: 男spring:profiles: devdatasource:url: jdbc:mysql://127.0.01/banchengbang_springbootusername: rootpassword: rootdriver-class-name: com.mysql.jdbc.Driver对比json
spring:{profiles:dev,datasource:{url:jdbc:mysql://127.0.01/banchengbang_springboot,username:root,password:root,driver-class-name:com.mysql.jdbc.Driver}
}对比java,和java对象之间的关系更接近
private String profiles;
private Datasource datasource;使用缩进表示层级关系。 | json使用花括号{}缩进时不允许使用 Tab 键只允许使用空格。缩进的空格数不重要但同级元素必须左侧对齐。大小写敏感key:value键值对模式 |和json一样内容如字符串不需要加 与json区别 大小写敏感 (json 里也是大小写敏感的)使用缩进表示层级关系 (json 中使用 {} 表示层级)#表示注释 (json 不允许写注释, yaml 写的配置文件要比 json 方便很多)key : val 值之前必须有空格多个key-val组合不需要加逗号, 总结比json少{},逗号多缩进和值前空格 YAML 支持以下三种数据结构 对象键值对的集合数组一组按次序排列的值字面量单个的、不可拆分的值 2.2 字面量数据类型
字面量是指单个的不可拆分的值例如数字、字符串、布尔值、以及日期等。在 YAML 中使用“key:[空格]value”的形式表示一对键值对空格不能省略 如 url: www.biancheng.net。字面量直接写在键值对的“value”中即可且默认情况下字符串是不需要使用单引号或双引号的。
示例
name: 蒋增奎 #姓名
isMan: true # 男士
birth: 2023-12-01 #出身日期
weight: 80.5
height: 172
parent: ~ # ~ 表示null2.2.1 字符串
字符串可以加单引号或双引号或者没有引号。
quoted: - single quoted string- double quoted strings- withoout quoted string都是合法的等价于json
{quoted: [single quoted string,double quoted strings,withoout quoted string]
}多行文本 字符串比较多的时候更好的展示选择单行/多行文本展示用| 前缀。 例如配置 GitHub Actions 时候运行一些命令
# Multiline strings start with |
execute: |npm cinpm buildnpm test等价json
{execute: npm ci\nnpm build\nnpm test\n
}2.2.2 NULL
YAML 声明空值有以下几种方法
manager: null
blank:
tilde: ~
title: null
~: null key等同json
{manager: null,blank: null,tilde: null,title: null,null: null key
}2.4.5 时间戳timestamp
时间戳表示单个时间点。它使用符号形式 ISO8601。如果未添加时区则假定该时区为 UTC。要描述日期格式可以省略时间部分。在这种情况下时间默认为00:00:00Z。请参见下面示例中的用法。
time: 2020-12-07T01:02:59:34.02Z
timestamp: 2020-12-07T01:02:59:34.02 05:30
datetime: 2020-12-07T01:02:59:34.0205:30
notimezone: 2020-12-07T01:02:59:34.02
date: 2020-12-07但实际转化有点问题
2.3 对象\MAP类型
使用缩进表示对象与属性的层级关系。 写法1推荐 key1: value1 key2: value2 写法2不推荐除非比较深的嵌套。感觉有点像json数据 key: {key1: value1, key2: value2, …} website: name: baiduurl: www.baidu.com或者
website: {name: baidu,url: www.baidu.com}2.4 数组/List/Set
2.4.1 值为基础类型
写法1推荐 YAML 使用“-”表示数组中的元素注意- 后面也要加空格
pets:- cat- dog- pig写法2这种也推荐比较简化 用[]表示 key: [value1,value2]
pets: [cat,dog,pig]2.4.2 值为对象
如果值一个对象如
# java 代码
private ListDog lists;#yml数据
lists:- name: 可乐age: 2 #注意前面没有 - 哦- name: 卷毛age: 3
或者
lists: - {name: 可乐,age: 2}- {name: 卷毛,age: 3}
或者
lists: [{name: 可乐,age: 2},{name: 卷毛,age: 3}]2.4.3 多维数组
-- A- B- C
-- D- E- F
结果[[A, B, C],[D, E, F]] 2.4.4 复杂类型
有对象有数组、基本数据类型 name: zhangsanage: 30pets:-dog-cat-pigcar:name: QQchild:name: zhangxiaosanage: 2java代码
public class Person {private String lastName;private Integer age;private Boolean boss;private Date birth;private MapString,Object maps;private ListDog lists;private Dog dog;private String[] arr;
}
public class Dog {private String name;private Integer age;
}
对应的yml填充数据
person:boss: falsemaps:k1: v1k2: 14lists:- name: d1age: 2- name: d2age: 3- {name: d3,age: 4}birth: 2017/12/15dog:name: p_dogage: 15age: 13last-name: 张三arr: [s1,s2,s3]
2.5 显示类型
默认情况下YAML 会自动推断数据类型就像 TypeScript 的类型推断一样但是当你需要你也可以使用 标签tags显示指定类型比如整数类型 两个英文感叹号 !! 再加上 int 就变成了一个整数 tag ——!!int。
# The following value should be an int, no matter what:
should-be-int: !!int 3.2# Parse any value to string:
should-be-string: !!str 30.25# I need the next value to be boolean:
should-be-boolean: !!bool yes!!com.jsoft.po.Company
address: 天府大道
boss: {birth: !!date 2023-12-13, id: 1, name: 蒋增奎, weight: 78.78}
creat_date: 2000-12-31
id: 1
name: 雪州科技
users:- {birth: !!timestamp2023-12-13T01:10:32.464Z, id: 2, name: 张三丰, weight: !!float 89}- {birth: !!timestamp 2023-12-13T01:10:32.464Z, id: 3, name: 张无忌, weight: !!float 100}2.6 引用和复用
YML值相互引用的基本语法如下 key:anchor value other_key:anchor 在上面的例子中key是一个YML键anchor是一个锚点value是一个值。 通过在其他地方使用anchor来引用这个值。
database:host: db_host localhost #给key[host]取一个别名prot: db_port 3306username: db_username rootpwd: db_pwd 11111development:database:host: *db_host # *别名引用别名对应的值 这里就是localhost prot: *db_portusername: *db_usernamepwd: *db_pwd
实际效果如下
development:database:host: localhostprot: 3306username: rootpwd: 11111development:database:host: localhostprot: 3306username: rootpwd: 11111复用大节点
basic: common #这个basic节点时可复用的sex: 男city: 女user:name: 蒋增奎: *common等价于
basic: common #这个basic节点时可复用的sex: 男city: 女user:name: 蒋增奎sex: 男city: 女用来建立锚点defaults 表示合并到当前数据* 用来引用锚点。注意只是复用这个节点的数据这个节点不会复用过来
3.YML解析
3.1准备工作
准备两个vo类
public class Company {private Long id;private String name;private String address;private User boss;private ListUser users;.......
}public class User {private Long id;private String name;private Date birth;private BigDecimal weight;
...
}3.1 spring解析
3.1.1 Environment注解
在Spring中有一个类Environment它可以被认为是当前应用程序正在运行的环境它继承了PropertyResolver接口因此可以作为一个属性解析器使用。先创建一个yml文件属性如下
person:name: hydragender: maleage: 18使用起来也非常简单直接使用Autowired就可以注入到要使用的类中然后调用它的getProperty()方法就可以根据属性名称取出对应的值了。
RestController
public class EnvironmentController {Autowiredprivate Environment environment; //注入GetMapping(envTest)private void getEnv(){System.out.println(environment.getProperty(person.name)); //通过key获取System.out.println(environment.getProperty(person.gender));Integer autoClose environment.getProperty(person.age, Integer.class); //类型转化System.out.println(autoClose);String defaultValue environment.getProperty(person.other, String.class, defaultValue);//类型转化System.out.println(defaultValue);}
}3.1.2 YamlPropertiesFactoryBean
在Spring中还可以使用YamlPropertiesFactoryBean来读取自定义配置的yml文件而不用再被拘束于application.yml及其激活的其他配置文件。
在使用过程中只需要通过setResources()方法设置自定义yml配置文件的存储路径再通过getObject()方法获取Properties对象后续就可以通过它获取具体的属性下面看一个例子
GetMapping(fcTest)
public void ymlProFctest(){YamlPropertiesFactoryBean yamlProFb new YamlPropertiesFactoryBean();yamlProFb.setResources(new ClassPathResource(application2.yml));Properties properties yamlProFb.getObject();System.out.println(properties.get(person2.name));System.out.println(properties.get(person2.gender));System.out.println(properties.toString());
}3.2 SnakeYml组件
前面介绍的几种方式在Spring环境下无需引入其他依赖就可以完成的接下来要介绍的SnakeYml在使用前需要引入依赖但是同时也可以脱离Spring环境单独使用。先引入依赖坐标
3.2.1 pom依赖
!-- https://mvnrepository.com/artifact/org.yaml/snakeyaml --
dependencygroupIdorg.yaml/groupIdartifactIdsnakeyaml/artifactIdversion1.30/version
/dependency
3.2.2 解析yml文件到map
test.yml
id: 10
title: 钢铁是怎么炼成的
price: 35
author:firstName: 蒋lastName: 增奎tel: 13688006645解析 Yaml yamlnew Yaml(); 1.返回的是一个map对象:mapkey,value MapString, Object mapyaml).load(inputStream); 2.返回的是一个VO对象 VO voyaml).load(inputStream,VO.class); Testpublic void t2() {Yaml yamlnew Yaml();MapString, Object map yaml.load(getClass().getClassLoader().getResourceAsStream(test.yml));//System.out.println(map);for (Map.EntryString, Object entry : map.entrySet()) {System.out.println(key entry.getKey() , value entry.getValue());}//获得基础类型String title(String)map.get(title);System.out.println(title-title;id-map.get(id);price-map.get(price));//获得对象MapString, Object author (Map)map.get(author);//获得对象的子属性String lastName(String) author.get(lastName);System.out.println(lastNamelastName);}效果
key id, value 10
key title, value 钢铁是怎么炼成的
key price, value 35
key author, value {firstName蒋, lastName增奎, tel13688006645}
title-钢铁是怎么炼成的;id-10;price-35
lastName增奎3.2.3 解析yml到vo对象
把上一个步骤生成字符串保存到company.yml文件放置到类的根目录下 代码
Testpublic void t2(){Yaml yamlnew Yaml();Company Company yaml.loadAs(getClass().getClassLoader().getResourceAsStream(company.yml), Company.class);System.out.println(Company.toString());}效果
Company{
id1, name雪州科技, address天府大道, bossUser{id1,
name蒋增奎, birthTue Dec 12 22:32:36 CST 2023, weight78.78},
users[User{id2, name张三丰, birthTue Dec 12 22:32:36 CST 2023, weight89},User{id3, name张无忌, birthTue Dec 12 22:32:36 CST 2023, weight100}]}
3.2.4 vo生成yml格式字符串
public class TestDemo {/*** vo生成yml格式字符串*/Testpublic void t1() {Company companygetGS();Yaml yaml new Yaml();StringWriter sw new StringWriter();yaml.dump(company, sw);System.out.println(sw.toString());}public Company getGS(){Company gsnew Company();gs.setAddress(天府大道);gs.setBoss(new User(1l,蒋增奎,new Date(), new BigDecimal(78.78)));gs.setId(1l);gs.setName(雪州科技);ListUser usersnew ArrayList();users.add(new User(2l,张三丰,new Date(), new BigDecimal(89)));users.add(new User(3l,张无忌,new Date(), new BigDecimal(100)));gs.setUsers(users);return gs;}
}执行效果
!!com.jsoft.po.Company
address: 天府大道
boss: {birth: !!timestamp 2023-12-12T23:37:08.209Z, id: 1, name: 蒋增奎, weight: 78.78}
id: 1
name: 雪州科技
users:
- {birth: !!timestamp 2023-12-12T23:37:08.211Z, id: 2, name: 张三丰, weight: !!float 89}
- {birth: !!timestamp 2023-12-12T23:37:08.211Z, id: 3, name: 张无忌, weight: !!float 100}
3.3 jackson组件
jackson不仅可以解析json,也支持yml
3.3.1 pom依赖 dependencygroupIdcom.fasterxml.jackson.dataformat/groupIdartifactIdjackson-dataformat-yaml/artifactIdversion2.12.3/version/dependency3.3.2 解析yml文件到map
test.yml
id: 10
title: 钢铁是怎么炼成的
price: 35
author:firstName: 蒋lastName: 增奎tel: 13688006645java代码 Testpublic void t4() throws IOException {ObjectMapper objectMapper new ObjectMapper(new YAMLFactory());InputStream inputthis.getClass().getClassLoader().getResourceAsStream(test.yml);MapString,Object map objectMapper.readValue(input, Map.class);for (Map.EntryString, Object entry : map.entrySet()) {System.out.println(key entry.getKey() , value entry.getValue());}//获得基础类型String title(String)map.get(title);System.out.println(title-title;id-map.get(id);price-map.get(price));//获得对象MapString, Object author (Map)map.get(author);//获得对象的子属性String lastName(String) author.get(lastName);System.out.println(lastNamelastName);}效果
key id, value 10
key title, value 钢铁是怎么炼成的
key price, value 35
key author, value {firstName蒋, lastName增奎, tel13688006645}
title-钢铁是怎么炼成的;id-10;price-35
lastName增奎3.3.3 解析yml到vo对象
把上一个步骤生成字符串保存到company.yml文件放置到类的根目录下 代码
Testpublic void t5() throws IOException {ObjectMapper objectMapper new ObjectMapper(new YAMLFactory());InputStream inputthis.getClass().getClassLoader().getResourceAsStream(company.yml);Company Company objectMapper.readValue(input, Company.class);System.out.println(Company.toString());}效果
Company{
id1, name雪州科技, address天府大道, bossUser{id1,
name蒋增奎, birthTue Dec 12 22:32:36 CST 2023, weight78.78},
users[User{id2, name张三丰, birthTue Dec 12 22:32:36 CST 2023, weight89},User{id3, name张无忌, birthTue Dec 12 22:32:36 CST 2023, weight100}]}
4.总结
4.1 XML、JSON、YAML
看下图从左往右是 XML、JSON、YAML 文件JSON 通过 {} 和 [] 等简化了 XML变得更加直观但是当嵌套过深 XML 需要找结尾标签JSON 需要找结尾的 }无论 XML 还是 JSON 都需要找结尾标记很不直观但 YAML 直接做的比 JSON 更加激进连符号都没了立体结构也变得扁平了更加符合人类阅读习惯。
4.2 易错点
Java
public class Person {private String name;private String tel;//-----}对应yml
name : jzk
tel : 13688006635错误
person:name : jzktel : 13688006635不要因为缩进把java类名也写入和json一样yml只和对象的属性值有关和类无关