go简单写个ini配置文件读取工具
直接上代码:
1 package main
2
3 import (
4 "fmt"
5 "io/ioutil"
6 "reflect"
7 "strconv"
8 "strings"
9 )
10
11 type MysqlConfig struct {
12 Address string `ini:"address"`
13 Port int `ini:"port"`
14 UserName string `ini:"username"`
15 PassWord string `ini:"password"`
16 }
17
18 type RedisConfig struct {
19 Host string `ini:"host"`
20 Port int `ini:"port"`
21 PassWord string `ini:"password"`
22 DataBase int `ini:"database"`
23 }
24
25 type Config struct {
26 MysqlConfig `ini:"mysql"`
27 RedisConfig `ini:"redis"`
28 }
29
30 func loadIni(fileName string, v interface{}) error {
31 // 参数校验:v需为结构体指针类型
32 t := reflect.TypeOf(v)
33 if t.Kind() != reflect.Ptr || t.Elem().Kind() != reflect.Struct {
34 return fmt.Errorf("v should be a struct ptr")
35 }
36
37 // 读取文件得到数据后立即关闭文件
38 f, err := ioutil.ReadFile(fileName)
39 if err != nil {
40 return err
41 }
42 // 逐行获取文件内容,将值赋值给对应的结构体对象
43 lineSlice := strings.Split(string(f), "\n")
44 var structName string
45 for index, line := range lineSlice {
46 line = strings.TrimSpace(line)
47 // 跳过注释和空行
48 if strings.HasPrefix(line, ";") || strings.HasPrefix(line, "#") || len(line) == 0 {
49 continue
50 }
51 // 以 [ 开头,为节点,需以 ] 结尾,且除空格外存在字符
52 if strings.HasPrefix(line, "[") {
53 if line[len(line) - 1] != ']' {
54 return fmt.Errorf("line:%d syntax error", index+1)
55 }
56 sectionName := strings.TrimSpace(line[1:len(line)-1])
57 if len(sectionName) == 0 {
58 return fmt.Errorf("line:%d syntax error", index+1)
59 }
60 // 根据字符串sectionName去v里面根据反射找到对应的结构体
61 for i :=0 ; i < t.Elem().NumField(); i ++ {
62 field := t.Elem().Field(i)
63 if sectionName == field.Tag.Get("ini") {
64 structName = field.Name
65 //fmt.Println(structName)
66 break
67 }
68 }
69 } else {
70 // 不以 [ 开头,为以=分割的键值对
71 if strings.Index(line, "=") == -1 || strings.HasPrefix(line, "=") {
72 return fmt.Errorf("line:%d syntax error", index+1)
73 }
74 // 根据struct名称找到对应结构体
75 data := reflect.ValueOf(v)
76 structValue := data.Elem().FieldByName(structName) // 拿到嵌套结构体的值信息
77 structType := structValue.Type() // 拿到嵌套结构体的类型信息
78 if structType.Kind() != reflect.Struct {
79 return fmt.Errorf("config struct field %s must be a struct", structName)
80 }
81 // 拆分键值对并赋值
82 paramSlice := strings.Split(line, "=")
83 key, value := strings.TrimSpace(paramSlice[0]), strings.TrimSpace(paramSlice[1])
84 for x := 0; x < structType.NumField(); x ++ {
85 // 先拿到fieldType,fieldType中可以拿到field的值类型
86 fieldType := structType.Field(x)
87 if fieldType.Tag.Get("ini") == key {
88 // 根据field名称拿到field字段
89 fieldV := structValue.FieldByName(fieldType.Name)
90 // 给字段赋值
91 switch fieldType.Type.Kind() {
92 case reflect.String:
93 fieldV.SetString(value)
94 case reflect.Int,reflect.Int8,reflect.Int16,reflect.Int32,reflect.Int64:
95 valueInt, err := strconv.ParseInt(value, 10, 64)
96 if err != nil {
97 return fmt.Errorf("parseInt error, err:%v", err)
98 }
99 fieldV.SetInt(valueInt)
100 case reflect.Float32:
101 valueFloat, err := strconv.ParseFloat(value, 32)
102 if err != nil {
103 return fmt.Errorf("parseFloat error, err:%v", err)
104 }
105 fieldV.SetFloat(valueFloat)
106 case reflect.Float64:
107 valueFloat, err := strconv.ParseFloat(value, 64)
108 if err != nil {
109 return fmt.Errorf("parseFloat error, err:%v", err)
110 }
111 fieldV.SetFloat(valueFloat)
112 case reflect.Bool:
113 valueBool, err := strconv.ParseBool(value)
114 if err != nil {
115 return fmt.Errorf("parseBool error, err:%v", err)
116 }
117 fieldV.SetBool(valueBool)
118 }
119 break
120 }
121 }
122 }
123 }
124 return nil
125 }
126
127 func main() {
128 var config Config
129 fileName := "/home/xxx/data/demo_config/config.ini"
130 err := loadIni(fileName, &config)
131 if err != nil {
132 fmt.Printf("load ini failed, err:%v", err)
133 }
134 fmt.Println("mysql config:")
135 fmt.Printf("address:%s\tport:%d\tusername:%s\tpassword:%s\n", config.MysqlConfig.Address, config.MysqlConfig.Port, config.MysqlConfig.UserName, config.MysqlConfig.PassWord)
136
137 fmt.Println("redis config:")
138 fmt.Printf("host:%s\tport:%d\tpassword:%s\tdatabase:%d\n", config.RedisConfig.Host, config.RedisConfig.Port, config.RedisConfig.PassWord, config.RedisConfig.DataBase)
139 }
go简单写个ini配置文件读取工具的更多相关文章
- (转载)将DELPHI数据库连接写进INI配置文件中
将DELPHI数据库连接写进INI配置文件中 procedure TDM.DataModuleCreate(Sender: TObject); var piececonfg:Tinifile; pat ...
- 【代码】ini 文件读取工具类
using System; using System.Runtime.InteropServices; using System.Text; namespace hrattendance.Common ...
- 配置文件读取工具类--PropertiesUtil
/** * 属性工具类 * @author admin * 参考:https://www.cnblogs.com/doudouxiaoye/p/5693454.html */ public class ...
- Java读取Maven工程下的配置文件,工具类
Java开发中,经常需要在maven工程中读取src/main/resources下的配置文件: 思路如下: Class.getClassLoader() 返回类加载器ClassLoader,进而可以 ...
- python 提供INI配置文件的操作 ConfigParser
原文地址:http://www.cnblogs.com/pumaboyd/archive/2008/08/11/1265416.html 红色的为标注信息 +++++++++++++++++引用+++ ...
- C 构造一个 简单配置文件读取库
前言 最近看到这篇文章, json引擎性能对比报告 http://www.oschina.net/news/61942/cpp-json-compare?utm_source=tuicool 感觉技术 ...
- 用C读取INI配置文件
http://blog.csdn.net/chexlong/article/details/6818017 #define CONF_FILE_PATH "Config.ini" ...
- 转 python3 读取 ini配置文件
在代码中经常会通过ini文件来配置一些常修改的配置.下面通过一个实例来看下如何写入.读取ini配置文件. 需要的配置文件是: 1 [path] 2 back_dir = /Users/abc/Pych ...
- 【Selenium05篇】python+selenium实现Web自动化:读取ini配置文件,元素封装,代码封装,异常处理,兼容多浏览器执行
一.前言 最近问我自动化的人确实有点多,个人突发奇想:想从0开始讲解python+selenium实现Web自动化测试,请关注博客持续更新! 这是python+selenium实现Web自动化第五篇博 ...
- Python读取ini配置文件的方式
python configparser模块 ConfigParser模块在python中用来读取配置文件,配置文件的格式跟windows下的ini配置文件相似,可以包含一个或多个节(section ...
随机推荐
- Axure 列表左右滑动交互-删除、置顶
Axure 列表左右滑动交互 左滑:删除.标记 右滑:置顶.回复 拖一个动态面板,命名为[滑动面板],添加三个状态,并分别命名为:正常状态.向左状态.向右状态 添加元件 正常状态 向左状态 将[正常状 ...
- DJI Flight Simulator 无人机模拟器 功能介绍与使用说明
0 前言 无人机是当前非常火热的"相机设备",而大疆又是其中翘楚,功能丰富,可以说是一个将带着云台的智能手机放到了天空中.如果你有自己玩过旋翼无人机航模的话,可能会体会到大疆的另一 ...
- KingbaseES数据库备份初始化错误处理
KingbaseES使用sys_backup.sh脚本init初始化配置文件常见错误处理: sys_backup.sh脚本按照如下顺序寻找初始化配置文件: [kingbase@postgres ~]$ ...
- bind使用场景之一
- Grafana 系列文章(十四):Helm 安装Loki
前言 写或者翻译这么多篇 Loki 相关的文章了, 发现还没写怎么安装 现在开始介绍如何使用 Helm 安装 Loki. 前提 有 Helm, 并且添加 Grafana 的官方源: helm repo ...
- spring-cloud06---Hystrix01简介
转:https://segmentfault.com/a/1190000005988895 # 1.服务雪崩介绍## 1.1基本概念分布式系统中经常会出现某个基础服务不可用造成整个系统不可用的情况, ...
- boot-repair
sudo add-apt-repository ppa:yannubuntu/boot-repair && sudo apt-get update sudo apt-get insta ...
- Stable Diffusion魔法入门
写在前面 本文为资料整合,没有原创内容,方便自己查找和学习, 花费了一晚上把sd安装好,又花了大半天了解sd周边的知识,终于体会到为啥这些生成式AI被称为魔法了,魔法使用前要吟唱类比到AI上不就是那些 ...
- JZOJ 1078. 【GDOI2006】The Kth Element
\(\text{Problem}\) 给定一个整数序列 \(a[1..N]\),定义 \(sum[i][j]=a[i]+a[i+1]+...+a[j]\),将所有的 \(sum[i][j]\) 从小到 ...
- JZOJ 2020.08.03【NOIP提高组】模拟 &&【NOIP2015模拟11.5】
总结 又是一日爆炸 \(T1\) 不出所料报 \(0\) 了?! 题目 \(T1\) JZOJ 4315. Prime 暴力就好了?! 考场根本没想暴力 赛后发现暴力跑得贼快 只需二分一下组数的上界 ...