Files
podman/pkg/machine/ignition.go
baude b5f54a9b23 introduce podman machine
podman machine allows podman to create, manage, and interact with a vm
running some form of linux (default is fcos).  podman is then configured
to be able to interact with the vm automatically.

while this is usable on linux, the real push is to get this working on
both current apple architectures in macos.

Ashley Cui contributed to this PR and was a great help.

[NO TESTS NEEDED]

Signed-off-by: baude <bbaude@redhat.com>
2021-03-25 08:43:51 -05:00

152 lines
3.6 KiB
Go

package machine
import (
"encoding/json"
"io/ioutil"
)
/*
If this file gets too nuts, we can perhaps use existing go code
to create ignition files. At this point, the file is so simple
that I chose to use structs and not import any code as I was
concerned (unsubstantiated) about too much bloat coming in.
https://github.com/openshift/machine-config-operator/blob/master/pkg/server/server.go
*/
// Convenience function to convert int to ptr
func intToPtr(i int) *int {
return &i
}
// Convenience function to convert string to ptr
func strToPtr(s string) *string {
return &s
}
// Convenience function to convert bool to ptr
func boolToPtr(b bool) *bool {
return &b
}
func getNodeUsr(usrName string) NodeUser {
return NodeUser{Name: &usrName}
}
func getNodeGrp(grpName string) NodeGroup {
return NodeGroup{Name: &grpName}
}
// NewIgnitionFile
func NewIgnitionFile(name, key, writePath string) error {
if len(name) < 1 {
name = DefaultIgnitionUserName
}
ignVersion := Ignition{
Version: "3.2.0",
}
ignPassword := Passwd{
Users: []PasswdUser{{
Name: name,
SSHAuthorizedKeys: []SSHAuthorizedKey{SSHAuthorizedKey(key)},
}},
}
ignStorage := Storage{
Directories: getDirs(name),
Files: getFiles(name),
Links: getLinks(name),
}
ignSystemd := Systemd{
Units: []Unit{
{
Enabled: boolToPtr(true),
Name: "podman.socket",
}}}
ignConfig := Config{
Ignition: ignVersion,
Passwd: ignPassword,
Storage: ignStorage,
Systemd: ignSystemd,
}
b, err := json.Marshal(ignConfig)
if err != nil {
return err
}
return ioutil.WriteFile(writePath, b, 0644)
}
func getDirs(usrName string) []Directory {
// Ignition has a bug/feature? where if you make a series of dirs
// in one swoop, then the leading dirs are creates as root.
newDirs := []string{
"/home/" + usrName + "/.config",
"/home/" + usrName + "/.config/systemd",
"/home/" + usrName + "/.config/systemd/user",
"/home/" + usrName + "/.config/systemd/user/default.target.wants",
}
var (
dirs = make([]Directory, len(newDirs))
)
for i, d := range newDirs {
newDir := Directory{
Node: Node{
Group: getNodeGrp(usrName),
Path: d,
User: getNodeUsr(usrName),
},
DirectoryEmbedded1: DirectoryEmbedded1{Mode: intToPtr(493)},
}
dirs[i] = newDir
}
return dirs
}
func getFiles(usrName string) []File {
var (
files []File
)
// Add a fake systemd service to get the user socket rolling
files = append(files, File{
Node: Node{
Group: getNodeGrp(usrName),
Path: "/home/" + usrName + "/.config/systemd/user/linger-example.service",
User: getNodeUsr(usrName),
},
FileEmbedded1: FileEmbedded1{
Append: nil,
Contents: Resource{
Source: strToPtr("data:,%5BUnit%5D%0ADescription%3DA%20systemd%20user%20unit%20demo%0AAfter%3Dnetwork-online.target%0AWants%3Dnetwork-online.target%20podman.socket%0A%5BService%5D%0AExecStart%3D%2Fusr%2Fbin%2Fsleep%20infinity%0A"),
},
Mode: intToPtr(484),
},
})
// Add a file into linger
files = append(files, File{
Node: Node{
Group: getNodeGrp(usrName),
Path: "/var/lib/systemd/linger/core",
User: getNodeUsr(usrName),
},
FileEmbedded1: FileEmbedded1{Mode: intToPtr(420)},
})
return files
}
func getLinks(usrName string) []Link {
return []Link{{
Node: Node{
Group: getNodeGrp(usrName),
Path: "/home/" + usrName + "/.config/systemd/user/default.target.wants/linger-example.service",
User: getNodeUsr(usrName),
},
LinkEmbedded1: LinkEmbedded1{
Hard: boolToPtr(false),
Target: "/home/" + usrName + "/.config/systemd/user/linger-example.service",
},
}}
}