Skip to content

Cron Scheduling

Use ostwin cron when an OSTwin plan should keep moving without an open terminal, TUI, or tmux session. Cron stores one plan/run id with its working directory, then lets the operating system scheduler call OSTwin later.

Key features

Background plan resume

When the scheduler fires, it runs:

Terminal window
ostwin cron run

cron run reads the stored cron record and expands it to:

Terminal window
ostwin run <plan_id> --resume --working-dir <working_dir> --non-interactive

This keeps scheduled execution aligned with the normal OSTwin run lifecycle, including war-room state, progress files, memory writes, and dashboard/TUI visibility.

Singleton registration

OSTwin cron stores one active record at a time:

FieldPurpose
idPlan/run id to resume.
working_dirAbsolute project directory used when the OS scheduler starts OSTwin.
argsResume arguments, currently --resume.
scheduleOptional recurring or one-time metadata.

Scheduling a new plan replaces the current registration. Keep one plan in the cron slot unless you intentionally build separate OS-level wrappers.

Three scheduling workflows

Use a recurring schedule when the same plan should resume repeatedly.

Terminal window
ostwin cron schedule dbe382fa0c3a --every 12h --working-dir /Users/paulaan/PycharmProjects/flowgpt

OS-native scheduling

OSTwin delegates timing to the platform scheduler:

PlatformRecurring scheduleOne-time schedule
macOSlaunchd LaunchAgentone-shot launchd LaunchAgent
Linuxsystemd --user timer, with crontab fallbacksystemd-run --user, with Unix nohup/sleep fallback
WindowsTask Schedulerone-time Task Scheduler task

Dry-run and observability

Cron supports dry-run checks before work is scheduled or executed:

Terminal window
ostwin cron run --dry-run
ostwin cron once dbe382fa0c3a --after 12h --working-dir /Users/paulaan/PycharmProjects/flowgpt --dry-run
ostwin cron run-once --dry-run

Use ostwin cron status to inspect the stored record and use the cron log for scheduled output.

When to use each command

GoalCommandNotes
Store the plan id and project path onlyostwin cron register <id> --working-dir <path>No OS schedule is installed.
Execute the stored record nowostwin cron runUseful for smoke-testing cron behavior.
Resume repeatedlyostwin cron schedule <id> --every 12h --working-dir <path>Installs a recurring OS scheduler entry.
Resume once after a delayostwin cron once <id> --after 12h --working-dir <path>Installs a one-shot scheduler and uses run-once.
Inspect current cron stateostwin cron statusShows id, working directory, and schedule mode.
Remove only the OS schedulerostwin cron unscheduleKeeps the stored registration.
Remove the stored registrationostwin cron unregisterClears cron.json.

Operator guideline

Follow these rules before handing execution to the OS scheduler.

  1. Use cron for resumable work only. If the plan has never started, run it once manually so OSTwin creates runtime state and war-room files.
  2. Always pass an absolute --working-dir. Native schedulers may start from $HOME, /, or C:\Windows\System32 instead of your interactive shell.
  3. Pick one scheduling intent. Use schedule --every for repeated resumes, once --after for a single delayed resume, and register + run for manual verification.
  4. Remember the singleton slot. A new register, schedule, or once command replaces the active OSTwin cron record.
  5. Do not depend on temporary shell exports. Put required variables in ~/.ostwin/.env, <project>/.env, or <project>/.agents/.env.
  6. Dry-run first. Use dry-run commands to verify plan resolution and scheduler command construction before installing background jobs.
  7. Monitor both layers. Check ostwin cron status, the OSTwin cron log, and the platform scheduler when diagnosing behavior.
  8. Clean up intentionally. Use unschedule for OS jobs and unregister for the stored OSTwin record.

Setup walkthrough

  1. Choose the plan and project path.

    Terminal window
    PLAN_ID="dbe382fa0c3a"
    PROJECT_DIR="/Users/paulaan/PycharmProjects/flowgpt"
  2. Start from a clean cron state.

    Terminal window
    ostwin cron unschedule
    ostwin cron unregister
  3. Verify that OSTwin can resolve the plan id.

    Terminal window
    cd "$PROJECT_DIR"
    ostwin run "$PLAN_ID" --dry-run --working-dir "$PROJECT_DIR" --non-interactive

    If the plan exists only in the dashboard, sync it first:

    Terminal window
    ostwin run "$PLAN_ID" --sync --dry-run --working-dir "$PROJECT_DIR" --non-interactive
  4. Create runtime state if the plan has never run.

    Terminal window
    ostwin run "$PLAN_ID" --working-dir "$PROJECT_DIR" --non-interactive
  5. Install the desired schedule.

    Terminal window
    ostwin cron schedule "$PLAN_ID" --every 12h --working-dir "$PROJECT_DIR"
  6. Verify and monitor.

    Terminal window
    ostwin cron status
    tail -f ~/.local/state/ostwin/cron.log

Storage and logs

FilemacOS/LinuxWindows
Cron registration~/.config/ostwin/cron.json%APPDATA%\Ostwin\cron.json
Cron log~/.local/state/ostwin/cron.log%LOCALAPPDATA%\Ostwin\cron.log

Platform verification

Terminal window
launchctl list com.ostwin.cron
launchctl list com.ostwin.cron.once

Stop or reset cron

Remove the OS scheduler but keep the stored record:

Terminal window
ostwin cron unschedule

Remove the stored record:

Terminal window
ostwin cron unregister

Full reset:

Terminal window
ostwin cron unschedule
ostwin cron unregister

Troubleshooting

SymptomWhat to check
No Ostwin cron run registeredRun ostwin cron register, ostwin cron schedule, or ostwin cron once first.
Plan ... not foundRun the plan dry-run from the project directory. If needed, use ostwin run <id> --sync --dry-run.
Scheduler runs from the wrong projectRe-register with an absolute --working-dir.
Nothing appears to happenCheck ostwin cron status, the cron log, and the OS scheduler entry.
Environment variables are missingMove them into ~/.ostwin/.env, <project>/.env, or <project>/.agents/.env.
PowerShell reports the expression after & is invalidUpdate to a build that resolves the OSTwin CLI script path explicitly, then verify with ostwin cron run --dry-run.