package unit import ( "strings" "testing" ) func TestValidName(t *testing.T) { for _, ok := range []string{"nightly-ci-check", "a", "Job_2", "x1-y2"} { if !ValidName(ok) { t.Errorf("%q should be valid", ok) } } for _, bad := range []string{"", "-leading", "has space", "slash/y", "รค", strings.Repeat("x", 65), "dot.name"} { if ValidName(bad) { t.Errorf("%q should be invalid", bad) } } } func TestScriptKeepsCommandVerbatim(t *testing.T) { cmd := `agy -p "check CI, say 'hi' & notify" | tee /tmp/x` s := Script(cmd) if !strings.HasPrefix(s, "#!/bin/sh\n") { t.Error("missing shebang") } if !strings.Contains(s, cmd) { t.Error("command was mangled") } } func TestServiceUnit(t *testing.T) { s := Service("nightly", "/home/x/.local/share/cronr/nightly.sh") for _, want := range []string{ "Type=oneshot", "ExecStart=/bin/sh /home/x/.local/share/cronr/nightly.sh", "Environment=PATH=%h/.local/bin", } { if !strings.Contains(s, want) { t.Errorf("service missing %q:\n%s", want, s) } } } func TestTimerUnit(t *testing.T) { rec := Timer("nightly", "*-*-* 07:00", false) if !strings.Contains(rec, "OnCalendar=*-*-* 07:00") || !strings.Contains(rec, "Persistent=true") { t.Errorf("recurring timer wrong:\n%s", rec) } once := Timer("boot", "2026-08-06 03:00", true) if !strings.Contains(once, "Persistent=false") { t.Errorf("one-shot timer should not be persistent:\n%s", once) } if !strings.Contains(once, "WantedBy=timers.target") { t.Error("timer missing install section") } } func TestUnitAndJobNames(t *testing.T) { svc, tmr := UnitNames("nightly") if svc != "cronr-nightly.service" || tmr != "cronr-nightly.timer" { t.Errorf("unit names: %s %s", svc, tmr) } if JobName("/home/x/.config/systemd/user/cronr-nightly.timer") != "nightly" { t.Error("JobName failed on full path") } if JobName("helmd.service") != "" { t.Error("foreign unit must not map to a job") } } func TestAtToCalendar(t *testing.T) { if _, err := AtToCalendar("2026-08-06 03:00"); err != nil { t.Errorf("valid --at rejected: %v", err) } if _, err := AtToCalendar("2026-08-06 03:00:30"); err != nil { t.Errorf("valid --at with seconds rejected: %v", err) } for _, bad := range []string{"imorgon", "03:00", "2026-8-6 03:00", "2026-08-06T03:00"} { if _, err := AtToCalendar(bad); err == nil { t.Errorf("bad --at %q accepted", bad) } } }