# bootc edit - Technical Guide ## Overview `bootc edit` is a declarative configuration management command that allows users to modify the host specification of a bootc-managed system. It operates similarly to `kubectl apply`, providing both interactive and programmatic interfaces for system configuration changes. ## Purpose The edit command serves several critical functions: 1. **Declarative Configuration**: Apply changes to system configuration declaratively 2. **Interactive Editing**: Use system editor for interactive configuration changes 3. **Programmatic Interface**: Apply configuration from files for automation 4. **State Management**: Maintain system state consistency across changes 5. **Validation**: Ensure configuration changes are valid and safe ## Command Syntax ```bash bootc edit [OPTIONS...] ``` ### Basic Usage ```bash # Interactive editing (opens in $EDITOR) bootc edit # Edit from file bootc edit --filename /path/to/config.yaml # Quiet mode (no progress output) bootc edit --quiet ``` ## Command Options | Option | Description | Default | Required | |--------|-------------|---------|----------| | `-f`, `--filename` | Use filename to edit system specification | `None` | No | | `--quiet` | Don't display progress | `false` | No | ## Architecture Overview ### 1. Configuration Structure The bootc edit system operates on a `Host` structure that contains: ```rust pub struct Host { pub resource: k8sapitypes::Resource, // Kubernetes-style metadata pub spec: HostSpec, // Host specification pub status: HostStatus, // Current system status } ``` ### 2. Host Specification The `HostSpec` contains the editable configuration: ```rust pub struct HostSpec { pub image: Option, // Container image reference pub boot_order: BootOrder, // Boot ordering configuration } ``` ### 3. Supported Changes Only changes to the `spec` section are honored: - **Image Reference**: Change the container image source - **Boot Order**: Modify boot ordering (rollback configuration) ## Technical Implementation ### 1. Edit Command Structure ```rust pub(crate) struct EditOpts { pub(crate) filename: Option, // Optional file input pub(crate) quiet: bool, // Progress suppression } ``` ### 2. Edit Process Flow ```rust async fn edit(opts: EditOpts) -> Result<()> { // 1. Get system storage and OSTree let sysroot = &get_storage().await?; let ostree = sysroot.get_ostree()?; let repo = &ostree.repo(); // 2. Get current system status let (booted_deployment, _deployments, host) = crate::status::get_status_require_booted(ostree)?; // 3. Load new configuration let new_host: Host = if let Some(filename) = opts.filename { // Load from file let mut r = std::io::BufReader::new(std::fs::File::open(filename)?); serde_yaml::from_reader(&mut r)? } else { // Interactive editing let tmpf = tempfile::NamedTempFile::new()?; serde_yaml::to_writer(std::io::BufWriter::new(tmpf.as_file()), &host)?; crate::utils::spawn_editor(&tmpf)?; tmpf.as_file().seek(std::io::SeekFrom::Start(0))?; serde_yaml::from_reader(&mut tmpf.as_file())? }; // 4. Validate changes if new_host.spec == host.spec { println!("Edit cancelled, no changes made."); return Ok(()); } // 5. Verify transition host.spec.verify_transition(&new_host.spec)?; let new_spec = RequiredHostSpec::from_spec(&new_host.spec)?; // 6. Apply changes if host.spec.boot_order != new_host.spec.boot_order { return crate::deploy::rollback(sysroot).await; } // 7. Pull and stage new image let fetched = crate::deploy::pull(repo, new_spec.image, None, opts.quiet, prog.clone()).await?; let stateroot = booted_deployment.osname(); crate::deploy::stage(sysroot, &stateroot, &fetched, &new_spec, prog.clone()).await?; // 8. Update system sysroot.update_mtime()?; Ok(()) } ``` ### 3. Editor Integration The system supports multiple editors through the `spawn_editor` function: ```rust pub(crate) fn spawn_editor(tmpf: &tempfile::NamedTempFile) -> Result<()> { let editor_variables = ["EDITOR"]; let backup_editors = ["nano", "vim", "vi"]; let editor = editor_variables.into_iter().find_map(std::env::var_os); let editor = if let Some(e) = editor.as_ref() { e.to_str() } else { backup_editors .into_iter() .find(|v| std::path::Path::new("/usr/bin").join(v).exists()) }; let editor = editor.ok_or_else(|| anyhow::anyhow!("$EDITOR is unset, and no backup editor found"))?; let mut editor_args = editor.split_ascii_whitespace(); let argv0 = editor_args.next().ok_or_else(|| anyhow::anyhow!("Invalid editor: {editor}"))?; Command::new(argv0) .args(editor_args) .arg(tmpf.path()) .lifecycle_bind() .run_inherited() .with_context(|| format!("Invoking editor {editor} failed")) } ``` ## Configuration Format ### 1. YAML Structure The configuration is stored in YAML format with the following structure: ```yaml apiVersion: v1 kind: Host metadata: name: localhost namespace: default spec: image: quay.io/myorg/debian-bootc:latest bootOrder: "normal" # or "rollback" status: staged: null booted: image: quay.io/myorg/debian-bootc:v1.0.0 digest: sha256:abc123... version: "1.0.0" rollback: image: quay.io/myorg/debian-bootc:v0.9.0 digest: sha256:def456... version: "0.9.0" rollbackQueued: false otherDeployments: [] ``` ### 2. Image Reference Format ```yaml spec: image: transport: "registry" name: "quay.io/myorg/debian-bootc" tag: "latest" # or digest: "sha256:abc123..." ``` ### 3. Boot Order Options ```yaml spec: bootOrder: "normal" # Normal boot order # or bootOrder: "rollback" # Rollback to previous deployment ``` ## Usage Patterns ### 1. Interactive Editing ```bash # Set editor environment variable export EDITOR=vim # Edit configuration interactively bootc edit ``` **Process**: 1. Current configuration is written to temporary file 2. System editor is launched with temporary file 3. User makes changes and saves 4. Changes are validated and applied ### 2. File-Based Editing ```bash # Create configuration file cat > config.yaml << EOF apiVersion: v1 kind: Host metadata: name: localhost spec: image: quay.io/myorg/debian-bootc:v2.0.0 bootOrder: "normal" EOF # Apply configuration bootc edit --filename config.yaml ``` **Process**: 1. Configuration is loaded from file 2. Changes are validated 3. Configuration is applied to system ### 3. Image Switching ```bash # Switch to different image bootc edit --filename - << EOF apiVersion: v1 kind: Host metadata: name: localhost spec: image: quay.io/myorg/debian-bootc:v2.0.0 EOF ``` ### 4. Rollback Configuration ```bash # Configure rollback bootc edit --filename - << EOF apiVersion: v1 kind: Host metadata: name: localhost spec: image: quay.io/myorg/debian-bootc:latest bootOrder: "rollback" EOF ``` ## State Transitions ### 1. Image Changes When the image reference changes: 1. **Validation**: Verify new image exists and is accessible 2. **Download**: Pull new container image from registry 3. **Staging**: Stage new image for next boot 4. **Status Update**: Update system status ### 2. Boot Order Changes When boot order changes: 1. **Validation**: Verify rollback deployment exists 2. **Rollback**: Execute rollback operation 3. **Status Update**: Update boot order configuration ### 3. No Changes When no changes are detected: 1. **Message**: Display "Edit cancelled, no changes made" 2. **Exit**: Return without making changes ## Error Handling ### 1. Editor Errors ```rust // Editor not found $EDITOR is unset, and no backup editor found // Editor execution failed Invoking editor vim failed ``` ### 2. Configuration Errors ```rust // Invalid YAML Error parsing YAML: invalid syntax // Invalid configuration Error: invalid host specification ``` ### 3. System Errors ```rust // System not bootc compatible Error: system is not bootc compatible // Image not found Error: image not found in registry ``` ## Integration Points ### 1. OSTree Integration - **Deployment Management**: Uses OSTree for deployment operations - **Status Queries**: Queries OSTree for current system state - **Staging**: Uses OSTree staging for new deployments ### 2. Container Registry Integration - **Image Pulling**: Uses container registry for image downloads - **Authentication**: Supports registry authentication - **Signature Verification**: Validates image signatures ### 3. Systemd Integration - **Service Management**: Coordinates with systemd services - **Status Updates**: Updates system status through systemd ## Security Considerations ### 1. Configuration Validation - **Schema Validation**: Validates configuration against schema - **Transition Validation**: Ensures safe state transitions - **Image Verification**: Verifies image signatures and authenticity ### 2. Editor Security - **Editor Selection**: Uses secure editor selection process - **Temporary Files**: Uses secure temporary file handling - **Process Isolation**: Isolates editor process execution ### 3. System Security - **Privilege Escalation**: Requires appropriate privileges - **State Consistency**: Maintains system state consistency - **Rollback Safety**: Ensures safe rollback operations ## Performance Considerations ### 1. Configuration Loading - **File I/O**: Efficient file reading and writing - **Memory Usage**: Minimal memory footprint for configuration - **Parsing**: Fast YAML parsing and validation ### 2. Editor Launch - **Process Spawning**: Efficient editor process creation - **Temporary Files**: Fast temporary file operations - **Editor Detection**: Quick editor availability checking ### 3. System Updates - **Incremental Updates**: Only updates changed components - **Status Caching**: Caches system status for performance - **Validation Caching**: Caches validation results ## Troubleshooting ### 1. Editor Issues ```bash # Check editor availability which vim nano vi # Set editor explicitly export EDITOR=/usr/bin/vim bootc edit ``` ### 2. Configuration Issues ```bash # Validate YAML syntax yaml-lint config.yaml # Check configuration schema bootc edit --filename config.yaml --dry-run ``` ### 3. System Issues ```bash # Check system status bootc status # Check system compatibility bootc status --json | jq '.status.booted' ``` ## Best Practices ### 1. Configuration Management - **Version Control**: Store configurations in version control - **Validation**: Validate configurations before applying - **Backup**: Backup current configuration before changes - **Testing**: Test configurations in staging environment ### 2. Editor Usage - **Editor Selection**: Use reliable editors (vim, nano) - **Environment Variables**: Set EDITOR environment variable - **Backup Editors**: Ensure backup editors are available - **Editor Configuration**: Configure editor for YAML editing ### 3. System Integration - **Automation**: Use file-based editing for automation - **Monitoring**: Monitor system status after changes - **Rollback**: Test rollback procedures regularly - **Documentation**: Document configuration changes ## Future Enhancements ### 1. Planned Features - **Dry Run Mode**: Preview changes without applying - **Configuration Templates**: Predefined configuration templates - **Validation Rules**: Custom validation rules - **Change Tracking**: Track configuration changes over time ### 2. Integration Improvements - **API Support**: REST API for configuration management - **Web Interface**: Web-based configuration editor - **Configuration Sync**: Synchronize configurations across systems - **Audit Logging**: Comprehensive audit logging This technical guide provides comprehensive understanding of the bootc edit system's architecture, implementation, and usage patterns.