github.com/choria-io/go-choria@v0.28.1-0.20240416190746-b3bf9c7d5a45/providers/discovery/inventory/datafile.go (about) 1 // Copyright (c) 2021, R.I. Pienaar and the Choria Project contributors 2 // 3 // SPDX-License-Identifier: Apache-2.0 4 5 package inventory 6 7 import ( 8 "encoding/json" 9 10 "github.com/choria-io/go-choria/filter/facts" 11 "github.com/choria-io/go-choria/protocol" 12 ) 13 14 // DataSchema the schema of supported inventory files 15 const DataSchema = "https://choria.io/schemas/choria/discovery/v1/inventory_file.json" 16 17 // DataFile is a source for discovery information that describes a fleet 18 type DataFile struct { 19 Schema string `json:"$schema" yaml:"$schema"` 20 Groups []Group `json:"groups,omitempty" yaml:"groups,omitempty"` 21 Nodes []Node `json:"nodes" yaml:"nodes"` 22 } 23 24 type GroupFilter struct { 25 Agents []string `json:"agents,omitempty" yaml:"agents,omitempty"` 26 Classes []string `json:"classes,omitempty" yaml:"classes,omitempty"` 27 Facts []string `json:"facts,omitempty" yaml:"facts,omitempty"` 28 Identities []string `json:"identities,omitempty" yaml:"identities,omitempty"` 29 Compound string `json:"compound,omitempty" yaml:"compound,omitempty"` 30 } 31 32 func (f *GroupFilter) ToProtocolFilter() (*protocol.Filter, error) { 33 filter := protocol.NewFilter() 34 35 if f == nil { 36 return filter, nil 37 } 38 39 for _, fact := range f.Facts { 40 ff, err := facts.ParseFactFilterString(fact) 41 if err != nil { 42 return nil, err 43 } 44 45 err = filter.AddFactFilter(ff[0], ff[1], ff[2]) 46 if err != nil { 47 return nil, err 48 } 49 } 50 51 for _, agent := range f.Agents { 52 filter.AddAgentFilter(agent) 53 } 54 55 for _, id := range f.Identities { 56 filter.AddIdentityFilter(id) 57 } 58 59 for _, c := range f.Classes { 60 filter.AddClassFilter(c) 61 } 62 63 if f.Compound != "" { 64 err := filter.AddCompoundFilter(f.Compound) 65 if err != nil { 66 return nil, err 67 } 68 } 69 70 return filter, nil 71 } 72 73 // Group is a view over the inventory expressed as a filter saved by name 74 type Group struct { 75 Name string `json:"name" yaml:"name"` 76 Filter *GroupFilter `json:"filter,omitempty" yaml:"filter,omitempty"` 77 } 78 79 // Node describes a single node on the network 80 type Node struct { 81 Name string `json:"name" yaml:"name"` 82 Collectives []string `json:"collectives" yaml:"collectives"` 83 Facts json.RawMessage `json:"facts" yaml:"facts"` 84 Classes []string `json:"classes" yaml:"classes"` 85 Agents []string `json:"agents" yaml:"agents"` 86 } 87 88 // LookupGroup finds a group by name 89 func (d *DataFile) LookupGroup(name string) (*Group, bool) { 90 for _, g := range d.Groups { 91 if g.Name == name { 92 return &g, true 93 } 94 } 95 96 return nil, false 97 }