Documentation
¶
Overview ¶
Package fileloader defines the main function for a component loader with only a constant footprint at runtime. This package makes it easy for a provider of component subsystem packages to also provide a standalone tool that loads just those descriptors from a hard-coded footprint - usually for demonstration purposes.
For example, if github.com/example/my-system is a component package, exposing one or more component descriptors, all that is needed to define a standalone demonstration tool is a file, github.com/example/my-system/cmd/demo/main.go, containing:
// The demo command runs a demonstration deployment of the new subsystem.
Package main
import (
"github.com/example/my-system"
"github.com/danielorbach/go-component/fileloader"
"github.com/danielorbach/go-component/loader"
)
const footprint = `...`
func main() {
loader.ParseFlags(newsubsystem.ComponentA, newsubsystem.ComponentB, ...)
fileloader.Load(footprint, fileloader.FormatYAML)
}
Index ¶
Examples ¶
Constants ¶
const Stdin = "-"
Stdin is a special value for the footprint argument, indicating that the footprint should be read from stdin.
Variables ¶
This section is empty.
Functions ¶
func Load ¶
func Load(footprint []byte, format FormatFlag)
Load loads the components described by the footprint, using the specified format to decode it.
Example ¶
// Component is an imported descriptor for the purpose of this example.
var Component = &component.Descriptor{
Name: "example",
Bootstrap: func(l *component.L, _ component.Linker, _ any) error {
l.Logf("Hello world!")
return nil
},
OptionsType: nil,
}
// sometimes the footprint is embedded in the binary, and we can use the
// fileloader.Load function to load it directly from memory.
const Footprint = `{
"Name": "Example Footprint",
"Metadata": "This footprint is serialized into bytes and then unmarshalled into loader.Footprint.",
"Identifier": "00000000-abcd-0000-abcd-000000000000",
"Locations": null,
"Components": {
"example": {
"Location": "",
"Options": null,
"Aspects": null,
"Interests": null
}
}
}`
// in which case, we must parse the commandline flags ourselves before attempting
// to load the footprint. fortunately, this is easy to do:
loader.ParseFlags(Component)
// then we can call fileloader.Load with the footprint as a byte slice, and the
// format of the footprint (JSON, YAML, etc.) - in this case, JSON.
fileloader.Load([]byte(Footprint), fileloader.FormatJSON)
func Main ¶
func Main(d ...*component.Descriptor)
Main parses the commandline and loads the components described by the footprint.
Example ¶
// Component is an imported descriptor for the purpose of this example.
var Component = &component.Descriptor{
Name: "example",
Bootstrap: func(l *component.L, _ component.Linker, _ any) error {
l.Logf("Hello world!")
return nil
},
OptionsType: nil,
}
// simply call fileloader.Main with the component descriptors of choice, and it
// shall parse the commandline and load the components described by the footprint
// provided as the first positional argument.
fileloader.Main(Component)
Types ¶
type ComponentJSON ¶
type FootprintJSON ¶
type FootprintJSON struct {
Name string // human-readable name (does not need to be unique)
Metadata string // human-readable description/summary/notes/comments
Solution string // attribute this footprint to a solution
Identifier uuid.UUID
Revision int
Locations []string // IGNORED
Components map[string]ComponentJSON
}
type FootprintYAML ¶
type FootprintYAML struct {
Name string // human-readable name (does not need to be unique)
Metadata string // human-readable description/summary/notes/comments
Solution string // attribute this footprint to a solution
Identifier uuid.UUID
Revision int
Locations []string // IGNORED
Components map[string]struct {
Location string
Options yaml.Node // unmarshal into an appropriate Options type
Aspects map[string]string // map[aspect]topic
Interests map[string]string // map[interest]topic
}
}
type FormatFlag ¶
type FormatFlag string
FormatFlag is a flag.Value that specifies the format of the footprint, and thus the appropriate loader to use.
const ( // FormatAuto indicates that the footprint format should be inferred; currently // from the file extension. FormatAuto FormatFlag = "auto" // FormatYAML indicates that the footprint is in YAML format. FormatYAML FormatFlag = "yaml" // FormatJSON indicates that the footprint is in JSON format. FormatJSON FormatFlag = "json" )
func (*FormatFlag) Set ¶
func (f *FormatFlag) Set(s string) error
func (*FormatFlag) String ¶
func (f *FormatFlag) String() string
type JSONLoader ¶
type JSONLoader []byte
A JSONLoader implements component.Procedure loading its json-encoded blob of a loader.Footprint.
Example ¶
package main
import (
"github.com/MakeNowJust/heredoc"
"github.com/danielorbach/go-component/fileloader"
)
func main() {
var json = heredoc.Doc(`
{
"name": "Static ping-pong-probe",
"metadata": "This is a static footprint loading three components: ping, pong, and probe.\n",
"identifier": "0abcdef0-b00b-0000-b00b-000000000000",
"locations": null,
"components": {
"ping": {
"location": null,
"options": {
"data": "Hello, world"
},
"aspects": {
"ping": "ping-topic"
},
"interests": null
},
"pong": {
"location": "",
"aspects": {
"pong": "pong-topic"
},
"interests": {
"ping": "ping-topic"
}
},
"probe": {
"aspects": null,
"interests": {
"pong": "pong-topic"
},
"options": {
"timeout": "2100ms"
}
}
}
}
`)
fileloader.Load([]byte(json), fileloader.FormatJSON)
}
func (JSONLoader) Exec ¶
func (x JSONLoader) Exec(l *component.L)
type YAMLLoader ¶
type YAMLLoader []byte
A YAMLLoader implements component.Procedure loading its yaml-encoded blob of a loader.Footprint.
Example ¶
package main
import (
"github.com/MakeNowJust/heredoc"
"github.com/danielorbach/go-component/fileloader"
)
func main() {
var yaml = heredoc.Doc(`
name: Static ping-pong-probe
metadata: |
This is a static footprint loading three components: ping, pong, and probe.
identifier: "0abcdef0-b00b-0000-b00b-000000000000"
locations: ~ # a tilde (~) character is an alias for null
components:
ping:
location: null # null is a defined literal of YAML (https://yaml.org/type/null.html)
options:
data: !!binary "SGVsbG8sIHdvcmxkIQ=="
aspects:
ping: "ping-topic"
interests: # omitting value equals to a null value
pong:
location: "" # an empty string is the null value of a string variable in Go
# options: # we can omit fields as-well
aspects:
pong: "pong-topic"
interests:
ping: "ping-topic"
probe:
aspects:
interests:
pong: "pong-topic"
options:
timeout: 2100ms
`)
fileloader.Load([]byte(yaml), fileloader.FormatYAML)
}
func (YAMLLoader) Exec ¶
func (x YAMLLoader) Exec(l *component.L)