Agent Lessons Learned
Shell Color Variables
Use $(printf '\nnn') not '\nnn' or $'...'. Test in isolation before using:
# WRONG - doesn't expand properly in heredocs
RED='\nn[0;31m'
# WRONG - $'...' not always supported
RED=$'\nn[0;31m'
# CORRECT
RED=$(printf '\nn[0;31m')
Drive Detection (OpenBSD)
- Root drive: Parse
root on sdXafromdmesg - Removable: Parse
removablefromdmesg - Softraid parents: Check disklabel for RAID partition type (
^ [a-z]:.*RAID) - Protect:
root_drive + softraid_parents - Offer for burn:
removable + internal_non_OS
Heredocs in Shell
- Closing marker must be at start of line (no indentation)
- Check for orphan closing markers after multi-edit sessions
- Run
sh -n script.shto verify syntax
packages.yaml Build Entries
ALWAYS include desc: prefix in build entries, even for heredocs:
build:
- |
desc: "Description of what this does"
cmd: |
actual shell commands here
Without desc:, the module will print blank [INFO] ...
OpenBSD Quirks
grep -Adoes NOT work - usesedorview+ offset- No
xxd- useod -corstrings - Many bash commands behave differently
Eth Network Detection
Return immediately on status: active - don’t set flag and fall through:
if isEth && strings.Contains(line, "status: active") {
return current, true // IMMEDIATELY
}
Shell Scaling Without X11
Default to 1920x1080, don’t fail:
if os.Getenv("DISPLAY") == "" {
width = 1920 // Default to 1080p
}
i3 Window Rules
- Use
pptnot%for whole-screen percentage for_window [instance="^floating_center"](instance, not class)
Porting Shell Scripts to Go
NEVER write new code that already exists in the codebase.
Before Writing Any Go Code
- Read the ENTIRE shell script and note every output line and its EXACT format
- Search the existing codebase for functions that do similar things
- Reuse existing functions - don’t rewrite them
After Writing Go Code
- grep sweep of ALL print/printf statements in the package
- Verify every output message matches the shell script character-for-character
- Check for: colors, brackets (
[INFO]notINFO), spacing, punctuation
make release Order (CRITICAL)
1. Sync packages.yaml
2. Bump VERSION
3. Build binary ← VERSION bump BEFORE build
4. Update README badge
5. Commit + tag
make-img.sh Details
Image Sizing
- Starts at 2GB fixed (handles tarball + packages)
shrink_img()truncates to actual content after injection- Calculation:
used_KB * 1.1 + 32MB buffer, aligned to 4MB
Auto-Cleanup
- Old
openriot.imgdeleted at start ofbuild_img() - Old
openriot.tgzdeleted at start ofcreate_site() - Old packages cleaned before download (not in list OR in exceptions.yaml)
Package Management
exceptions.yamllists packages to exclude from image- Old packages not in current list are auto-deleted
pkg_addhandles deps at install time, not download time
Drive Detection
[ROOT]= Boot drive (fromroot on sd1ain dmesg) + softraid parents (drives with RAID partitions)[WARN]= Removable drives (fromremovablein dmesg)[INFO]= Internal empty drives
Progress Output
- Use
printf "\r%80s\r" ""to clear progress lines between sections - Don’t use
\nin progress loops - useecho ""after loop completes set -ecauses exit on non-zero returns - use|| truefor expected failuresgrep -c .returns exit 1 on empty input - use|| 0fallback