diff options
Diffstat (limited to 'cmd/podman/registry')
-rw-r--r-- | cmd/podman/registry/config.go | 106 | ||||
-rw-r--r-- | cmd/podman/registry/registry.go | 116 | ||||
-rw-r--r-- | cmd/podman/registry/remote.go | 9 |
3 files changed, 231 insertions, 0 deletions
diff --git a/cmd/podman/registry/config.go b/cmd/podman/registry/config.go new file mode 100644 index 000000000..358f9172e --- /dev/null +++ b/cmd/podman/registry/config.go @@ -0,0 +1,106 @@ +package registry + +import ( + "fmt" + "os" + "path/filepath" + "runtime" + "strings" + + "github.com/containers/common/pkg/config" + "github.com/containers/libpod/pkg/domain/entities" + "github.com/containers/libpod/pkg/rootless" + "github.com/containers/libpod/pkg/util" + "github.com/pkg/errors" +) + +const ( + ParentNSRequired = "ParentNSRequired" +) + +var ( + PodmanOptions entities.PodmanConfig +) + +// NewPodmanConfig creates a PodmanConfig from the environment +func NewPodmanConfig() entities.PodmanConfig { + if err := setXdgDirs(); err != nil { + fmt.Fprintf(os.Stderr, err.Error()) + os.Exit(1) + } + + var mode entities.EngineMode + switch runtime.GOOS { + case "darwin": + fallthrough + case "windows": + mode = entities.TunnelMode + case "linux": + mode = entities.ABIMode + default: + fmt.Fprintf(os.Stderr, "%s is not a supported OS", runtime.GOOS) + os.Exit(1) + } + + // cobra.Execute() may not be called yet, so we peek at os.Args. + for _, v := range os.Args { + // Prefix checking works because of how default EngineMode's + // have been defined. + if strings.HasPrefix(v, "--remote") { + mode = entities.TunnelMode + } + } + + // FIXME: for rootless, add flag to get the path to override configuration + cfg, err := config.NewConfig("") + if err != nil { + fmt.Fprint(os.Stderr, "Failed to obtain podman configuration: "+err.Error()) + os.Exit(1) + } + + cfg.Network.NetworkConfigDir = cfg.Network.CNIPluginDirs[0] + if rootless.IsRootless() { + cfg.Network.NetworkConfigDir = "" + } + + return entities.PodmanConfig{Config: cfg, EngineMode: mode} +} + +// SetXdgDirs ensures the XDG_RUNTIME_DIR env and XDG_CONFIG_HOME variables are set. +// containers/image uses XDG_RUNTIME_DIR to locate the auth file, XDG_CONFIG_HOME is +// use for the libpod.conf configuration file. +func setXdgDirs() error { + if !rootless.IsRootless() { + return nil + } + + // Setup XDG_RUNTIME_DIR + if _, found := os.LookupEnv("XDG_RUNTIME_DIR"); !found { + dir, err := util.GetRuntimeDir() + if err != nil { + return err + } + if err := os.Setenv("XDG_RUNTIME_DIR", dir); err != nil { + return errors.Wrapf(err, "cannot set XDG_RUNTIME_DIR="+dir) + } + } + + if _, found := os.LookupEnv("DBUS_SESSION_BUS_ADDRESS"); !found { + sessionAddr := filepath.Join(os.Getenv("XDG_RUNTIME_DIR"), "bus") + if _, err := os.Stat(sessionAddr); err == nil { + os.Setenv("DBUS_SESSION_BUS_ADDRESS", "unix:path="+sessionAddr) + } + } + + // Setup XDG_CONFIG_HOME + if _, found := os.LookupEnv("XDG_CONFIG_HOME"); !found { + cfgHomeDir, err := util.GetRootlessConfigHomeDir() + if err != nil { + return err + } + if err := os.Setenv("XDG_CONFIG_HOME", cfgHomeDir); err != nil { + return errors.Wrapf(err, "cannot set XDG_CONFIG_HOME="+cfgHomeDir) + } + } + return nil +} diff --git a/cmd/podman/registry/registry.go b/cmd/podman/registry/registry.go new file mode 100644 index 000000000..1c5e5d21b --- /dev/null +++ b/cmd/podman/registry/registry.go @@ -0,0 +1,116 @@ +package registry + +import ( + "context" + + "github.com/containers/libpod/pkg/domain/entities" + "github.com/containers/libpod/pkg/domain/infra" + "github.com/pkg/errors" + "github.com/spf13/cobra" +) + +// DefaultAPIAddress is the default address of the REST socket +const DefaultAPIAddress = "unix:/run/podman/podman.sock" + +// DefaultVarlinkAddress is the default address of the varlink socket +const DefaultVarlinkAddress = "unix:/run/podman/io.podman" + +type CliCommand struct { + Mode []entities.EngineMode + Command *cobra.Command + Parent *cobra.Command +} + +const ExecErrorCodeGeneric = 125 + +var ( + cliCtx context.Context + containerEngine entities.ContainerEngine + exitCode = ExecErrorCodeGeneric + imageEngine entities.ImageEngine + + // Commands holds the cobra.Commands to present to the user, including + // parent if not a child of "root" + Commands []CliCommand +) + +func SetExitCode(code int) { + exitCode = code +} + +func GetExitCode() int { + return exitCode +} + +func ImageEngine() entities.ImageEngine { + return imageEngine +} + +// NewImageEngine is a wrapper for building an ImageEngine to be used for PreRunE functions +func NewImageEngine(cmd *cobra.Command, args []string) (entities.ImageEngine, error) { + if imageEngine == nil { + PodmanOptions.FlagSet = cmd.Flags() + engine, err := infra.NewImageEngine(PodmanOptions) + if err != nil { + return nil, err + } + imageEngine = engine + } + return imageEngine, nil +} + +func ContainerEngine() entities.ContainerEngine { + return containerEngine +} + +// NewContainerEngine is a wrapper for building an ContainerEngine to be used for PreRunE functions +func NewContainerEngine(cmd *cobra.Command, args []string) (entities.ContainerEngine, error) { + if containerEngine == nil { + PodmanOptions.FlagSet = cmd.Flags() + engine, err := infra.NewContainerEngine(PodmanOptions) + if err != nil { + return nil, err + } + containerEngine = engine + } + return containerEngine, nil +} + +func SubCommandExists(cmd *cobra.Command, args []string) error { + if len(args) > 0 { + return errors.Errorf("unrecognized command `%[1]s %[2]s`\nTry '%[1]s --help' for more information.", cmd.CommandPath(), args[0]) + } + return errors.Errorf("missing command '%[1]s COMMAND'\nTry '%[1]s --help' for more information.", cmd.CommandPath()) +} + +// IdOrLatestArgs used to validate a nameOrId was provided or the "--latest" flag +func IdOrLatestArgs(cmd *cobra.Command, args []string) error { + if len(args) > 1 || (len(args) == 0 && !cmd.Flag("latest").Changed) { + return errors.New(`command requires a name, id or the "--latest" flag`) + } + return nil +} + +type PodmanOptionsKey struct{} + +func Context() context.Context { + if cliCtx == nil { + cliCtx = ContextWithOptions(context.Background()) + } + return cliCtx +} + +func ContextWithOptions(ctx context.Context) context.Context { + cliCtx = context.WithValue(ctx, PodmanOptionsKey{}, PodmanOptions) + return cliCtx +} + +// GetContextWithOptions deprecated, use NewContextWithOptions() +func GetContextWithOptions() context.Context { + return ContextWithOptions(context.Background()) +} + +// GetContext deprecated, use Context() +func GetContext() context.Context { + return Context() +} diff --git a/cmd/podman/registry/remote.go b/cmd/podman/registry/remote.go new file mode 100644 index 000000000..5378701e7 --- /dev/null +++ b/cmd/podman/registry/remote.go @@ -0,0 +1,9 @@ +package registry + +import ( + "github.com/containers/libpod/pkg/domain/entities" +) + +func IsRemote() bool { + return PodmanOptions.EngineMode == entities.TunnelMode +} |