data.go (2510B)
1 package dati 2 3 /* 4 Copyright (C) 2021 gearsix <gearsix@tuta.io> 5 6 This program is free software: you can redistribute it and/or modify 7 it under the terms of the GNU General Public License as published by 8 the Free Software Foundation, either version 3 of the License, or 9 at your option) any later version. 10 11 This program is distributed in the hope that it will be useful, 12 but WITHOUT ANY WARRANTY; without even the implied warranty of 13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 GNU General Public License for more details. 15 16 You should have received a copy of the GNU General Public License 17 along with this program. If not, see <https://www.gnu.org/licenses/>. 18 */ 19 20 import ( 21 "encoding/json" 22 "fmt" 23 "github.com/pelletier/go-toml" 24 "gopkg.in/yaml.v3" 25 "io" 26 "io/ioutil" 27 "os" 28 "path/filepath" 29 "strings" 30 ) 31 32 // SupportedDataLangs provides a list of supported languages for data files (lower-case) 33 var SupportedDataLangs = []string{"json", "yaml", "toml"} 34 35 // IsSupportedDataLang provides the index of `SupportedLangs` that `lang` is at. 36 // If `lang` is not in `SupportedDataLangs`, `-1` will be returned. 37 // File extensions can be passed in `lang`, the prefixed `.` will be trimmed. 38 func IsSupportedDataLang(lang string) int { 39 lang = strings.ToLower(lang) 40 if len(lang) > 0 && lang[0] == '.' { 41 lang = lang[1:] 42 } 43 for i, l := range SupportedDataLangs { 44 if lang == l { 45 return i 46 } 47 } 48 return -1 49 } 50 51 // LoadData attempts to load all data from `in` as the data language `lang` 52 // and writes the result in the pointer `outp`. 53 func LoadData(lang string, in io.Reader, outp interface{}) error { 54 inbuf, e := ioutil.ReadAll(in) 55 if e != nil { 56 return e 57 } else if len(inbuf) == 0 { 58 return nil 59 } 60 61 switch IsSupportedDataLang(lang) { 62 case 0: 63 e = json.Unmarshal(inbuf, outp) 64 case 1: 65 e = yaml.Unmarshal(inbuf, outp) 66 case 2: 67 e = toml.Unmarshal(inbuf, outp) 68 case -1: 69 fallthrough 70 default: 71 e = fmt.Errorf("'%s' is not a supported data language", lang) 72 } 73 74 return e 75 } 76 77 // LoadDataFile loads all the data from the file found at `path` into the the 78 // format of that files extension (e.g. "x.json" will be loaded as a json). 79 // The result is written to the value pointed at by `outp`. 80 func LoadDataFilepath(path string, outp interface{}) error { 81 f, e := os.Open(path) 82 defer f.Close() 83 84 if e == nil { 85 lang := filepath.Ext(path)[1:] // don't include '.' 86 if e = LoadData(lang, f, outp); e != nil { 87 e = fmt.Errorf("failed to load data '%s': %s", path, e.Error()) 88 } 89 } 90 91 return e 92 }