# Job Format Jobs are the fundamental unit of work in Horus. ## Structure ```rust pub struct Job { pub id: String, // Unique job identifier pub runner_id: String, // Target runner ID pub payload: String, // Job payload (script/command) pub timeout: Option, // Timeout in seconds pub env_vars: HashMap, // Environment variables pub signatures: Vec, // Cryptographic signatures pub created_at: i64, // Creation timestamp pub status: JobStatus, // Current status } ``` ## Job Status ```rust pub enum JobStatus { Pending, // Queued, not yet started Running, // Currently executing Completed, // Finished successfully Failed, // Execution failed Timeout, // Exceeded timeout Cancelled, // Manually cancelled } ``` ## Signature Format ```rust pub struct Signature { pub public_key: String, // Signer's public key pub signature: String, // Cryptographic signature pub algorithm: String, // Signature algorithm (e.g., "ed25519") } ``` ## Creating a Job ### Minimal Job ```rust use hero_job::Job; let job = Job::new( "my-runner", "print('Hello World')".to_string(), ); ``` ### With Timeout ```rust let job = Job::builder() .runner_id("my-runner") .payload("long_running_task()") .timeout(300) // 5 minutes .build(); ``` ### With Environment Variables ```rust use std::collections::HashMap; let mut env_vars = HashMap::new(); env_vars.insert("API_KEY".to_string(), "secret".to_string()); env_vars.insert("ENV".to_string(), "production".to_string()); let job = Job::builder() .runner_id("my-runner") .payload("deploy_app()") .env_vars(env_vars) .build(); ``` ### With Signature ```rust use hero_job::{Job, Signature}; let job = Job::builder() .runner_id("my-runner") .payload("important_task()") .signature(Signature { public_key: "ed25519:abc123...".to_string(), signature: "sig:xyz789...".to_string(), algorithm: "ed25519".to_string(), }) .build(); ``` ## Payload Format The payload format depends on the target runner: ### Hero Runner Heroscript content: ```heroscript !!git.list print("Repositories listed") !!docker.ps ``` ### SAL Runner Rhai script with SAL modules: ```rhai let files = os.list_dir("/tmp"); for file in files { print(file); } ``` ### Osiris Runner Rhai script with Osiris database: ```rhai let users = osiris.model("users"); let user = users.create(#{ name: "Alice", email: "alice@example.com" }); ``` ## Job Result ```rust pub struct JobResult { pub job_id: String, pub status: JobStatus, pub output: String, // Stdout pub error: Option, // Stderr or error message pub exit_code: Option, pub started_at: Option, pub completed_at: Option, } ``` ## Best Practices ### Timeouts - Always set timeouts for jobs - Default: 60 seconds - Long-running jobs: Set appropriate timeout - Infinite jobs: Use separate monitoring ### Environment Variables - Don't store secrets in env vars in production - Use vault/secret management instead - Keep env vars minimal - Document required variables ### Signatures - Always sign jobs in production - Use strong algorithms (ed25519) - Rotate keys regularly - Store private keys securely ### Payloads - Keep payloads concise - Validate input data - Handle errors gracefully - Log important operations ## Validation Jobs are validated before execution: 1. **Structure**: All required fields present 2. **Signature**: Valid cryptographic signature 3. **Runner**: Target runner exists and available 4. **Payload**: Non-empty payload 5. **Timeout**: Reasonable timeout value Invalid jobs are rejected before execution.