quadlet

package
v1.3.0-main Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: May 27, 2026 License: Apache-2.0 Imports: 19 Imported by: 0

Documentation

Overview

Package quadlet provides Quadlet/systemd-specific implementations of the infra providers.

Package quadlet provides Quadlet/systemd-specific implementations of the infra providers.

Package quadlet provides Quadlet/systemd-specific implementations of the infra providers.

Package quadlet provides Quadlet/systemd-specific implementations of the infra providers.

Package quadlet provides Quadlet/systemd-specific implementations of the infra providers.

Index

Constants

View Source
const (
	// RoleAdmin is the global administrator role (full access everywhere).
	RoleAdmin = "flightctl-admin"
	// RoleOrgAdmin is the organization administrator role.
	RoleOrgAdmin = "flightctl-org-admin"
	// RoleOperator can manage devices, fleets, and imagebuilds.
	RoleOperator = "flightctl-operator"
	// RoleViewer has read-only access.
	RoleViewer = "flightctl-viewer"
	// RoleInstaller can provision devices and download imageexports.
	RoleInstaller = "flightctl-installer"
)

Variables

View Source
var ServiceRegistry = map[infra.ServiceName]ServiceInfo{
	infra.ServiceRedis:              {ContainerName: "flightctl-kv", SystemdUnit: "flightctl-kv.service", Port: 6379},
	infra.ServiceAPI:                {ContainerName: "flightctl-api", SystemdUnit: "flightctl-api.service", Port: 3443},
	infra.ServiceWorker:             {ContainerName: "flightctl-worker", SystemdUnit: "flightctl-worker.service", Port: 7443},
	infra.ServicePeriodic:           {ContainerName: "flightctl-periodic", SystemdUnit: "flightctl-periodic.service", Port: 0},
	infra.ServiceTelemetryGateway:   {ContainerName: "flightctl-telemetry-gateway", SystemdUnit: "flightctl-telemetry-gateway.service", Port: 9464},
	infra.ServiceDB:                 {ContainerName: "flightctl-db", SystemdUnit: "flightctl-db.service", Port: 5432},
	infra.ServiceUI:                 {ContainerName: "flightctl-ui", SystemdUnit: "flightctl-ui.service", Port: 9001},
	infra.ServiceAlertmanager:       {ContainerName: "flightctl-alertmanager", SystemdUnit: "flightctl-alertmanager.service", Port: 9093},
	infra.ServiceAlertmanagerProxy:  {ContainerName: "flightctl-alertmanager-proxy", SystemdUnit: "flightctl-alertmanager-proxy.service", Port: 8443},
	infra.ServiceImageBuilderAPI:    {ContainerName: "flightctl-imagebuilder-api", SystemdUnit: "flightctl-imagebuilder-api.service", Port: 8445},
	infra.ServiceImageBuilderWorker: {ContainerName: "flightctl-imagebuilder-worker", SystemdUnit: "flightctl-imagebuilder-worker.service", Port: 8080},
	infra.ServiceAlertExporter:      {ContainerName: "flightctl-alert-exporter", SystemdUnit: "flightctl-alert-exporter.service", Port: 0},
}

ServiceRegistry maps service names to their Quadlet-specific metadata.

Functions

func NewSecretsProvider

func NewSecretsProvider(infraP *InfraProvider) infra.SecretsProvider

NewSecretsProvider creates a new Quadlet SecretsProvider. Pass the Quadlet InfraProvider so it can run podman commands (with sudo/SSH if configured).

func OrgGroupName

func OrgGroupName(organization string) string

OrgGroupName returns the group name for an organization (e.g., "org-engineering").

func ServicesWithServiceConfigMappings

func ServicesWithServiceConfigMappings() []infra.ServiceName

ServicesWithServiceConfigMappings returns service names that have a section mapping (SetServiceConfig writes to service-config.yaml for these).

Types

type InfraProvider

type InfraProvider struct {
	// contains filtered or unexported fields
}

InfraProvider implements infra.InfraProvider for Quadlet environments. Supports both local and remote Quadlet deployments via SSH.

func NewInfraProvider

func NewInfraProvider(configDir, secretDir string, useSudo bool) *InfraProvider

NewInfraProvider creates a new Quadlet InfraProvider. For remote hosts, set QUADLET_HOST and E2E_SSH_USER env vars. Auth: set E2E_SSH_KEY_PATH for key-based auth, or E2E_SSH_PASSWORD for password auth (requires sshpass). Registry comes from auxiliary; use auxiliary.Get(ctx).Registry.Host/Registry.Port and Registry.Authenticated for credential-required OCI pulls.

func (*InfraProvider) BuiltinDatabaseWorkloadAvailable

func (p *InfraProvider) BuiltinDatabaseWorkloadAvailable() bool

BuiltinDatabaseWorkloadAvailable reports whether service-config uses the built-in DB container. When db.type is external (see deploy/podman/service-config.yaml), there is no local flightctl-db workload to exec pg_dump into, matching Helm external DB behavior.

func (*InfraProvider) ExecInService

func (p *InfraProvider) ExecInService(service infra.ServiceName, command []string) (string, error)

ExecInService executes a command in the context of a service container. For Quadlet, this uses podman exec on the target host (local or remote via SSH).

func (*InfraProvider) ExecInServiceWithStdin

func (p *InfraProvider) ExecInServiceWithStdin(service infra.ServiceName, command []string, stdin io.Reader) (string, error)

ExecInServiceWithStdin executes a command in the context of a service container with stdin attached. For Quadlet: podman exec -i (stdin piped through SSH when remote).

func (*InfraProvider) ExposeService

func (p *InfraProvider) ExposeService(service infra.ServiceName, protocol string) (string, func(), error)

ExposeService makes an internal service accessible from the test host. If the container already publishes the port (e.g. flightctl-api), returns that URL and a no-op cleanup. Otherwise (e.g. Redis) starts a TCP forwarder from a local port to the container. Repeated calls for the same (service, protocol) return the same URL so polling (e.g. WaitForQueueAccessible) does not spawn a new forward every time. For remote Quadlet, returns host:port and the deployment must expose the service.

func (*InfraProvider) GetAPILoginToken

func (p *InfraProvider) GetAPILoginToken() (string, error)

GetAPILoginToken returns a token for flightctl login. Quadlet: read from env or file.

func (*InfraProvider) GetConfigValue

func (p *InfraProvider) GetConfigValue(name, key string) (string, error)

GetConfigValue retrieves a configuration value from config files or environment.

func (*InfraProvider) GetEnvironmentType

func (p *InfraProvider) GetEnvironmentType() string

GetEnvironmentType returns "quadlet".

func (*InfraProvider) GetExternalNamespace

func (p *InfraProvider) GetExternalNamespace() string

GetExternalNamespace returns empty for Quadlet (no K8s release namespace).

func (*InfraProvider) GetHost

func (p *InfraProvider) GetHost() string

GetHost returns the host where Quadlet services are running.

func (*InfraProvider) GetInternalNamespace

func (p *InfraProvider) GetInternalNamespace() string

GetInternalNamespace returns empty for Quadlet (no split namespaces).

func (*InfraProvider) GetSecretValue

func (p *InfraProvider) GetSecretValue(name, key string) (string, error)

GetSecretValue retrieves a secret value from secret files or environment.

func (*InfraProvider) GetServiceConfig

func (p *InfraProvider) GetServiceConfig(service infra.ServiceName) (string, error)

GetServiceConfig retrieves the full configuration content for a service. For Quadlet, configs are on the target host at /etc/flightctl/<container-name>/config.yaml.

func (*InfraProvider) GetServiceEndpoint

func (p *InfraProvider) GetServiceEndpoint(service infra.ServiceName) (string, int, error)

GetServiceEndpoint returns the host and port for a named service. For Quadlet, services run on the configured host with well-known ports.

func (*InfraProvider) InvalidateExposeCache

func (p *InfraProvider) InvalidateExposeCache(service infra.ServiceName)

InvalidateExposeCache stops any cached port-forward for the service and removes it from the cache. Call after restarting a service so the next ExposeService creates a new forward to the new container IP.

func (*InfraProvider) RunCommand

func (p *InfraProvider) RunCommand(command ...string) (string, error)

RunCommand runs a command on the Quadlet host (with SSH/sudo if configured). Used by SecretsProvider to read Podman secrets via container env.

func (*InfraProvider) SetServiceConfig

func (p *InfraProvider) SetServiceConfig(service infra.ServiceName, configKey, content string) error

SetServiceConfig writes the config content to the service's config file on the host. Quadlet has a single config file per service; configKey is ignored (callers may pass "" or "config.yaml" for API compatibility). For services with a section mapping (see service_config_mapping.go), the content is transformed and merged into /etc/flightctl/service-config.yaml so it persists across restarts when the template re-renders. For other services, the content is written to the per-service config file at /etc/flightctl/<container-name>/config.yaml.

type PAMRBACProvider

type PAMRBACProvider struct {
	// contains filtered or unexported fields
}

PAMRBACProvider implements infra.RBACProvider for Quadlet environments using PAM-based RBAC.

In Quadlet deployments, Flight Control uses PAM (Pluggable Authentication Modules) for authentication and Linux groups for authorization. This maps to the K8s RBAC model as follows:

Role/ClusterRole → Linux group:

  • Namespaced role: group named "<namespace>.<role>" (e.g., "myorg.admin")
  • Cluster role: group named "<role>" (e.g., "admin")

RoleBinding/ClusterRoleBinding → User added to group:

  • usermod -aG <group> <user>

The PAM provider in internal/auth/oidc/pam/provider.go interprets these groups:

  • "namespace.role" → org-scoped role (namespace:role)
  • "role" (no dot) → cluster-scoped role

func NewPAMRBACProvider

func NewPAMRBACProvider(useSudo bool) *PAMRBACProvider

NewPAMRBACProvider creates a new PAMRBACProvider.

func (*PAMRBACProvider) AddUserToOrg

func (p *PAMRBACProvider) AddUserToOrg(_ context.Context, orgName, userName string) error

AddUserToOrg adds the user to the organization's group (org-<orgName>).

func (*PAMRBACProvider) BindUserToRole

func (p *PAMRBACProvider) BindUserToRole(username, namespace, roleName string) error

BindUserToRole is a convenience method to bind a user to a role. For namespaced roles, provide namespace. For cluster roles, leave namespace empty.

func (*PAMRBACProvider) CleanupTestUser

func (p *PAMRBACProvider) CleanupTestUser(username string) error

CleanupTestUser removes a test user and associated resources.

func (*PAMRBACProvider) CreateClusterRole

func (p *PAMRBACProvider) CreateClusterRole(_ context.Context, spec *infra.RoleSpec) error

CreateClusterRole creates a Linux group for the cluster role (no namespace prefix).

func (*PAMRBACProvider) CreateClusterRoleBinding

func (p *PAMRBACProvider) CreateClusterRoleBinding(_ context.Context, spec *infra.RoleBindingSpec) error

CreateClusterRoleBinding adds the user to the cluster role's group.

func (*PAMRBACProvider) CreateOrganization

func (p *PAMRBACProvider) CreateOrganization(_ context.Context, name string) error

CreateOrganization creates an organization (org-<name> group).

func (*PAMRBACProvider) CreateRole

func (p *PAMRBACProvider) CreateRole(_ context.Context, spec *infra.RoleSpec) error

CreateRole creates a Linux group for the role. Namespaced roles become groups named "<namespace>.<name>".

func (*PAMRBACProvider) CreateRoleBinding

func (p *PAMRBACProvider) CreateRoleBinding(_ context.Context, spec *infra.RoleBindingSpec) error

CreateRoleBinding adds the user to the role's group. For namespaced roles (namespace != "*"), also adds the user to the org-<namespace> group. ServiceAccount subjects are not supported (no-op).

func (*PAMRBACProvider) CreateUser

func (p *PAMRBACProvider) CreateUser(username string) error

CreateUser creates a user in the PAM issuer container.

func (*PAMRBACProvider) DeleteClusterRole

func (p *PAMRBACProvider) DeleteClusterRole(_ context.Context, name string) error

DeleteClusterRole deletes the Linux group for the cluster role.

func (*PAMRBACProvider) DeleteClusterRoleBinding

func (p *PAMRBACProvider) DeleteClusterRoleBinding(_ context.Context, name string) error

DeleteClusterRoleBinding removes the user from the cluster role's group.

func (*PAMRBACProvider) DeleteOrganization

func (p *PAMRBACProvider) DeleteOrganization(_ context.Context, name string) error

DeleteOrganization deletes an organization (org-<name> group).

func (*PAMRBACProvider) DeleteRole

func (p *PAMRBACProvider) DeleteRole(_ context.Context, namespace, name string) error

DeleteRole deletes the Linux group for the role.

func (*PAMRBACProvider) DeleteRoleBinding

func (p *PAMRBACProvider) DeleteRoleBinding(_ context.Context, namespace, name string) error

DeleteRoleBinding removes the user from the role's group.

func (*PAMRBACProvider) DeleteUser

func (p *PAMRBACProvider) DeleteUser(username string) error

DeleteUser deletes a user from the PAM issuer container.

func (*PAMRBACProvider) GetUserGroups

func (p *PAMRBACProvider) GetUserGroups(username string) ([]string, error)

GetUserGroups returns the groups a user belongs to.

func (*PAMRBACProvider) SetUserPassword

func (p *PAMRBACProvider) SetUserPassword(username, password string) error

SetUserPassword sets the password for a user in the PAM issuer container.

func (*PAMRBACProvider) SetupTestUser

func (p *PAMRBACProvider) SetupTestUser(username, password, role string, organization string) error

SetupTestUser creates a test user with the specified role and optional organization. This is a convenience method for test setup.

func (*PAMRBACProvider) UnbindUserFromRole

func (p *PAMRBACProvider) UnbindUserFromRole(username, namespace, roleName string) error

UnbindUserFromRole is a convenience method to unbind a user from a role.

func (*PAMRBACProvider) UpdateClusterRole

func (p *PAMRBACProvider) UpdateClusterRole(_ context.Context, _ *infra.RoleSpec) error

UpdateClusterRole is a no-op for PAM (groups don't have permissions).

func (*PAMRBACProvider) UpdateRole

func (p *PAMRBACProvider) UpdateRole(_ context.Context, _ *infra.RoleSpec) error

UpdateRole is a no-op for PAM (groups don't have permissions).

type SecretsProvider

type SecretsProvider struct {
	// contains filtered or unexported fields
}

SecretsProvider implements infra.SecretsProvider for Quadlet environments. It reads secret values via `podman secret inspect --showsecret <name>`.

func (*SecretsProvider) CreateSecret

func (p *SecretsProvider) CreateSecret(ctx context.Context, namespace, name string, stringData map[string]string) error

CreateSecret is not supported for Quadlet; secrets are file-based.

func (*SecretsProvider) GetSecretData

func (p *SecretsProvider) GetSecretData(_ context.Context, _, _, _ string) ([]byte, error)

GetSecretData returns ErrSecretsNotSupported. Callers should fall back to infra or local file paths.

func (*SecretsProvider) GetSecretDataForService

func (p *SecretsProvider) GetSecretDataForService(_ context.Context, _ infra.ServiceName, secretName, key string) ([]byte, error)

GetSecretDataForService reads the secret from Podman with `podman secret inspect --showsecret <name>` and returns SecretData. Caller secretName (e.g. "flightctl-kv-secret") is mapped to Podman secret name (e.g. "flightctl-kv-password") by convention.

type SectionMapping

type SectionMapping struct {
	RenderedKey      string
	ServiceConfigKey string
	Transform        func(renderedSubtree interface{}) (interface{}, error)
}

SectionMapping describes how one top-level section in the rendered per-service config maps back to service-config.yaml. RenderedKey is the key in the per-service config (e.g. imageBuilderWorker); ServiceConfigKey is the key in service-config.yaml (e.g. imagebuilderWorker). If Transform is non-nil, it converts the rendered subtree into service-config shape; otherwise the subtree is copied as-is (use when structure is 1:1, with key normalization).

Key behavior:

  • Key missing from config: left unchanged in service-config.yaml
  • Key present with value: merged into service-config.yaml
  • Key present with null: deleted from service-config.yaml

type ServiceInfo

type ServiceInfo struct {
	ContainerName string
	SystemdUnit   string
	Port          int
}

ServiceInfo holds metadata about a Quadlet service.

func GetServiceInfo

func GetServiceInfo(service infra.ServiceName) ServiceInfo

getServiceInfo returns the service metadata from the registry. GetServiceInfo returns the service metadata from the registry.

type ServiceLifecycleProvider

type ServiceLifecycleProvider struct {
	// contains filtered or unexported fields
}

ServiceLifecycleProvider implements infra.ServiceLifecycleProvider for Quadlet environments.

func NewServiceLifecycleProvider

func NewServiceLifecycleProvider(infraP *InfraProvider, useSudo bool) *ServiceLifecycleProvider

NewServiceLifecycleProvider creates a new Quadlet ServiceLifecycleProvider.

func (*ServiceLifecycleProvider) AreServicesHealthy

func (p *ServiceLifecycleProvider) AreServicesHealthy() (bool, error)

AreServicesHealthy checks if all flightctl services are healthy by checking the flightctl.target.

func (*ServiceLifecycleProvider) IsRunning

func (p *ServiceLifecycleProvider) IsRunning(service infra.ServiceName) (bool, error)

IsRunning checks if a service is currently running.

func (*ServiceLifecycleProvider) RemoveDeploymentEnv

func (p *ServiceLifecycleProvider) RemoveDeploymentEnv(service infra.ServiceName, envName string) error

RemoveDeploymentEnv removes an environment variable from a Quadlet service's container drop-in.

func (*ServiceLifecycleProvider) Restart

func (p *ServiceLifecycleProvider) Restart(service infra.ServiceName) error

Restart restarts a service.

func (*ServiceLifecycleProvider) SetDeploymentEnv

func (p *ServiceLifecycleProvider) SetDeploymentEnv(service infra.ServiceName, envName, envValue string) error

SetDeploymentEnv sets an environment variable on a Quadlet service using a Quadlet container drop-in.

func (*ServiceLifecycleProvider) Start

func (p *ServiceLifecycleProvider) Start(service infra.ServiceName) error

Start starts a stopped service.

func (*ServiceLifecycleProvider) Stop

Stop stops a running service.

func (*ServiceLifecycleProvider) WaitForReady

func (p *ServiceLifecycleProvider) WaitForReady(service infra.ServiceName, timeout time.Duration) error

WaitForReady waits for a service to be ready.

type TPMProvider

type TPMProvider struct {
	// contains filtered or unexported fields
}

TPMProvider implements infra.TPMProvider for Quadlet environments.

func NewTPMProvider

func NewTPMProvider(infraP *InfraProvider, lifecycle *ServiceLifecycleProvider) *TPMProvider

NewTPMProvider creates a new Quadlet TPMProvider.

func (*TPMProvider) CleanupCerts

func (p *TPMProvider) CleanupCerts(ctx context.Context) error

CleanupCerts removes TPM CA certificates from the API server configuration.

func (*TPMProvider) InjectCerts

func (p *TPMProvider) InjectCerts(ctx context.Context, certs map[string][]byte) error

InjectCerts configures TPM CA certificates for the API server. For Quadlet: writes certs to /etc/flightctl/tpm-cas/, updates API config, restarts service. It skips the service restart if all certs and config are already in place.

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL