Go:读配置文件程序包的程序
核心任务:包必须提供一个函数 Watch(filename,listener) (configuration, error)
- 输入 filename 是配置文件名
- 输入 listener 一个特殊的接口,用来监听配置文件是否被修改,让开发者自己决定如何处理配置变化
type ListenFunc func(string)
type inteface Listener { listen(inifile string) }
ListenFunc
实现接口方法listen
直接调用函数- 优点
- 所有满足签名的函数、方法都可以作为参数
- 所有实现 Listener 接口的数据类型都可作为参数
- 输出 configuration 数据类型,可根据 key 读对应的 value。 key 和 value 都是字符串
- 输出 error 是错误数据,如配置文件不存在,无法打开等
- 可选的函数
WatchWithOption(filename,listener,...) (configuration, error
简单使用:
测试demo,包含在readme里的简单例子
测试过程gif,当处于监听过程中的时候,如果修改test.ini文件,可以监听到文件发生修改。
TestReadFile(自动测试,读取文件是否符合和储存文件是否一致)
ReadFile文件是
使用了Map
测试函数(借鉴了别的同学的测试函数,感谢!)
自定义错误类型
、
实现监听函数
判断系统类型
关于API部分生成:
例子:我想要生成某个文件夹下的go文档,假设你的gopath是D:/code 你项目目录是D:\code\src\下的test,你想生成test 项目中的testcode文件夹下的所有go的doc;那么需要执行如下步骤。
第1步、那么在命令行中进入到该文件夹下 D:\code\src\test,执行 godoc -http=:6060
第2步、打开浏览器输入http://127.0.0.1:6060/pkg/test
妥了
在ubuntu环境下还要下载一个go工具包,按照提示安装就可以了
部分截图:
watch.go完整代码:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 | package watchFile import ( "bufio" "fmt" "os" "runtime" "strings" "io" ) //创建一个自定义的错误类型 func New(text string) errorString { return errorString{text} } //错误信息的数据结构 type errorString struct { s string } //错误的方法:打印错误信息并返回错误信息 func (e *errorString) Error() string { fmt.Fprintf(os.Stdout, e.s) return e.s } //根据路径参数读取配置文件,并且返回一个储存配置文件键值对的map和自定义的错误类型 func readFile(iniFile string) ( map [string]string, errorString) { temConfig := map [string]string{} var error errorString _, err := os.Stat(iniFile) if err != nil { error = New( "error1:The configuration file is not in the current path" ) return temConfig, error } Filein, err1 := os.OpenFile(iniFile, os.O_RDONLY, 0644) if err1 != nil { error = New( "error1: Failed to open file" ) return temConfig, error } else { error = New( "" ) } buffin := bufio.NewReader(Filein) for { line, err2 := buffin.ReadString( '\n' ) if (err2 == io.EOF) { break } var i int for i = 0; i < len(line); i++ { if line[i] != ' ' && line[i] != '\t' { break } } if i == len(line) { continue } if line[i] == '#' || line[i] == ';' || line[i] == '[' { continue } keyStart := i lastBlank := i for i = 0; i < len(line); i++ { if line[i] == '=' { break } if line[i] == ' ' { lastBlank = i } } if i >= len(line)-1 { continue } if lastBlank == keyStart { lastBlank = i } keyString := line[keyStart:lastBlank] valueString := line[i+2: len(line) - 1] valueString = strings.Replace(valueString, "\n" , "" , -1) valueString = strings.Replace(valueString, "\t" , "" , -1) temConfig[keyString] = valueString if err2 != nil { break } } _ = Filein.Close(); return temConfig, error } //打印map func printConfig(conf map [string]string) { fmt.Printf( "File content : \n" ) for key, value := range conf { fmt.Printf( "%s = %s\n" , key, value) } fmt.Printf( "\nEnd ------------ : \n" ) } //比较两个map是否相同 func mapCompare(map1 map [string]string, map2 map [string]string) bool { for key1, value1 := range map1 { value2, _ := map2[key1] if value1 != value2 { return false } } if len(map2) > len(map1) { return false } return true } type ListenFunc func (string) //接口 type Listener interface { listen(inifile string) } //函数签名ListenFunc实现接口方法 func (Listen ListenFunc) listen(inifile string) { config1, _ := readFile(inifile) print( "Listening :\n" ) for { temConfig, _ := readFile(inifile) if !mapCompare(config1, temConfig) { break } } } var symbol byte //注释符 //判断系统类型,根据系统类型判断注释符 func initSys() { sysType := runtime.GOOS if sysType == "linux" { symbol = '#' } else if sysType == "window" { symbol = ';' } } //读取文件,然后监听文件,如果文件在监听期间修改,则打印返回最新文件,并结束 func Watch(filename string, Listen Listener) ( map [string]string, errorString) { initSys() config, error1 := readFile(filename) if len(error1.s) > 0 { fmt.Printf( "An error occurs in function Watch : %s" , error1.s) return config, error1 } printConfig(config) Listen.listen(filename) print( "The configuration file has changed :\n" ) config, error1 = readFile(filename) if len(error1.s) > 0 { fmt.Printf( "An error occurs in function Watch : %s" , error1.s) } printConfig(config) return config, error1 } |
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 从 HTTP 原因短语缺失研究 HTTP/2 和 HTTP/3 的设计差异
· AI与.NET技术实操系列:向量存储与相似性搜索在 .NET 中的实现
· 基于Microsoft.Extensions.AI核心库实现RAG应用
· Linux系列:如何用heaptrack跟踪.NET程序的非托管内存泄露
· 开发者必知的日志记录最佳实践
· winform 绘制太阳,地球,月球 运作规律
· TypeScript + Deepseek 打造卜卦网站:技术与玄学的结合
· Manus的开源复刻OpenManus初探
· 写一个简单的SQL生成工具
· AI 智能体引爆开源社区「GitHub 热点速览」