{ "$schema": "https://json-schema.org/draft/2020-12/schema", "$id": "https://developer.hashicorp.com/schemas/nomad/job.json", "title": "HashiCorp Nomad Job", "description": "A Nomad job specification defining the workload to be scheduled, including task groups, tasks, resources, networking, service discovery, and update strategies.", "type": "object", "required": ["ID", "Name", "Type", "TaskGroups"], "properties": { "ID": { "type": "string", "description": "The unique identifier of the job, used to reference it in API calls." }, "Name": { "type": "string", "description": "The human-readable name of the job." }, "Namespace": { "type": "string", "description": "The namespace the job is registered in. Defaults to 'default'.", "default": "default" }, "Type": { "type": "string", "description": "The scheduler type for the job.", "enum": ["service", "batch", "system", "sysbatch"] }, "Priority": { "type": "integer", "description": "The priority of the job, from 1 (lowest) to 100 (highest). Defaults to 50.", "minimum": 1, "maximum": 100, "default": 50 }, "Region": { "type": "string", "description": "The region in which the job is registered." }, "Datacenters": { "type": "array", "description": "A list of datacenters the job is allowed to run in.", "items": { "type": "string" }, "minItems": 1 }, "NodePool": { "type": "string", "description": "The node pool the job should be scheduled in." }, "Status": { "type": "string", "description": "The current status of the job. Set by Nomad, not the user.", "enum": ["pending", "running", "dead"] }, "Stable": { "type": "boolean", "description": "Whether this job version is marked as stable." }, "Version": { "type": "integer", "description": "The version number of the job, incremented on each update.", "minimum": 0 }, "SubmitTime": { "type": "integer", "description": "The time the job was submitted in nanoseconds since Unix epoch." }, "Meta": { "type": "object", "description": "User-defined metadata key-value pairs attached to the job.", "additionalProperties": { "type": "string" } }, "TaskGroups": { "type": "array", "description": "The task groups that make up the job. Each group is a set of co-located tasks.", "items": { "$ref": "#/$defs/TaskGroup" }, "minItems": 1 }, "Update": { "$ref": "#/$defs/UpdateStrategy" }, "Periodic": { "$ref": "#/$defs/PeriodicConfig" }, "Parameterized": { "$ref": "#/$defs/ParameterizedConfig" }, "Constraints": { "type": "array", "description": "Job-level constraints that apply to all task groups.", "items": { "$ref": "#/$defs/Constraint" } }, "Affinities": { "type": "array", "description": "Job-level affinities for soft scheduling preferences.", "items": { "$ref": "#/$defs/Affinity" } }, "Spreads": { "type": "array", "description": "Job-level spread targets for distributing allocations.", "items": { "$ref": "#/$defs/Spread" } } }, "$defs": { "TaskGroup": { "type": "object", "description": "A task group is a set of tasks that must be co-located on the same node.", "required": ["Name", "Tasks"], "properties": { "Name": { "type": "string", "description": "The name of the task group." }, "Count": { "type": "integer", "description": "The number of instances of this task group to run.", "minimum": 0, "default": 1 }, "Tasks": { "type": "array", "description": "The tasks that are part of this task group.", "items": { "$ref": "#/$defs/Task" }, "minItems": 1 }, "Networks": { "type": "array", "description": "Network configuration for the task group.", "items": { "$ref": "#/$defs/NetworkResource" } }, "Services": { "type": "array", "description": "Service registrations for the task group.", "items": { "$ref": "#/$defs/Service" } }, "Volumes": { "type": "object", "description": "Volume declarations for the task group.", "additionalProperties": { "$ref": "#/$defs/VolumeRequest" } }, "RestartPolicy": { "$ref": "#/$defs/RestartPolicy" }, "EphemeralDisk": { "$ref": "#/$defs/EphemeralDisk" }, "Update": { "$ref": "#/$defs/UpdateStrategy" }, "Scaling": { "$ref": "#/$defs/ScalingPolicy" }, "Constraints": { "type": "array", "items": { "$ref": "#/$defs/Constraint" } }, "Affinities": { "type": "array", "items": { "$ref": "#/$defs/Affinity" } } } }, "Task": { "type": "object", "description": "A task is the smallest unit of work in Nomad, executed within a task group.", "required": ["Name", "Driver"], "properties": { "Name": { "type": "string", "description": "The name of the task." }, "Driver": { "type": "string", "description": "The task driver to use (e.g., docker, exec, raw_exec, java, podman)." }, "Config": { "type": "object", "description": "Driver-specific configuration for the task.", "additionalProperties": true }, "Env": { "type": "object", "description": "Environment variables for the task.", "additionalProperties": { "type": "string" } }, "Resources": { "$ref": "#/$defs/Resources" }, "Meta": { "type": "object", "description": "User-defined metadata for the task.", "additionalProperties": { "type": "string" } }, "LogConfig": { "type": "object", "description": "Log configuration for the task.", "properties": { "MaxFiles": { "type": "integer", "description": "Maximum number of rotated log files to retain.", "minimum": 1, "default": 10 }, "MaxFileSizeMB": { "type": "integer", "description": "Maximum size of each log file in megabytes.", "minimum": 1, "default": 10 } } }, "Templates": { "type": "array", "description": "Template configurations for rendering dynamic files.", "items": { "$ref": "#/$defs/Template" } }, "Artifacts": { "type": "array", "description": "Artifacts to download before task execution.", "items": { "$ref": "#/$defs/TaskArtifact" } }, "Leader": { "type": "boolean", "description": "If true, this task is the leader task of the group. When it exits, all other tasks are stopped." }, "KillTimeout": { "type": "integer", "description": "Time in nanoseconds to wait for the task to exit before forcefully killing it." }, "ShutdownDelay": { "type": "integer", "description": "Duration in nanoseconds to wait before sending a kill signal, allowing for graceful shutdown." }, "Lifecycle": { "type": "object", "description": "Lifecycle configuration for sidecar and init tasks.", "properties": { "Hook": { "type": "string", "description": "When to run the task relative to the main tasks.", "enum": ["prestart", "poststart", "poststop"] }, "Sidecar": { "type": "boolean", "description": "If true, the task runs for the lifetime of the allocation." } } } } }, "Resources": { "type": "object", "description": "Resource requirements for a task.", "properties": { "CPU": { "type": "integer", "description": "CPU required in MHz.", "minimum": 1 }, "Cores": { "type": "integer", "description": "Number of dedicated CPU cores required.", "minimum": 1 }, "MemoryMB": { "type": "integer", "description": "Memory required in megabytes.", "minimum": 1 }, "MemoryMaxMB": { "type": "integer", "description": "Maximum memory in megabytes for memory oversubscription.", "minimum": 1 }, "DiskMB": { "type": "integer", "description": "Disk space required in megabytes.", "minimum": 0 } } }, "NetworkResource": { "type": "object", "description": "Network resource configuration for a task group.", "properties": { "Mode": { "type": "string", "description": "The network mode (bridge, host, cni/)." }, "DNS": { "type": "object", "description": "Custom DNS configuration.", "properties": { "Servers": { "type": "array", "items": { "type": "string" }, "description": "DNS server addresses." }, "Searches": { "type": "array", "items": { "type": "string" }, "description": "DNS search domains." }, "Options": { "type": "array", "items": { "type": "string" }, "description": "DNS options." } } }, "DynamicPorts": { "type": "array", "description": "Dynamic port allocations.", "items": { "$ref": "#/$defs/Port" } }, "ReservedPorts": { "type": "array", "description": "Reserved static port allocations.", "items": { "$ref": "#/$defs/Port" } } } }, "Port": { "type": "object", "description": "A port mapping for a network resource.", "required": ["Label"], "properties": { "Label": { "type": "string", "description": "The label for the port, used to reference it in service definitions." }, "Value": { "type": "integer", "description": "The static port value (for reserved ports).", "minimum": 0, "maximum": 65535 }, "To": { "type": "integer", "description": "The port inside the allocation to map to.", "minimum": 0, "maximum": 65535 }, "HostNetwork": { "type": "string", "description": "The host network to bind to." } } }, "Service": { "type": "object", "description": "A service registration for Consul or Nomad native service discovery.", "required": ["Name"], "properties": { "Name": { "type": "string", "description": "The name of the service." }, "Tags": { "type": "array", "description": "Tags to associate with the service registration.", "items": { "type": "string" } }, "CanaryTags": { "type": "array", "description": "Tags to set on the service when it is a canary.", "items": { "type": "string" } }, "PortLabel": { "type": "string", "description": "The port label to associate with the service." }, "Provider": { "type": "string", "description": "The service discovery provider to use.", "enum": ["consul", "nomad"], "default": "consul" }, "Checks": { "type": "array", "description": "Health checks for the service.", "items": { "$ref": "#/$defs/ServiceCheck" } } } }, "ServiceCheck": { "type": "object", "description": "A health check for a service registration.", "required": ["Type"], "properties": { "Name": { "type": "string", "description": "The name of the health check." }, "Type": { "type": "string", "description": "The type of health check.", "enum": ["http", "tcp", "script", "grpc"] }, "Path": { "type": "string", "description": "The HTTP path for HTTP checks." }, "Protocol": { "type": "string", "description": "The protocol for the check (http or https)." }, "PortLabel": { "type": "string", "description": "The port label to use for the check." }, "Interval": { "type": "integer", "description": "How often to run the check in nanoseconds." }, "Timeout": { "type": "integer", "description": "Timeout for the check in nanoseconds." }, "Command": { "type": "string", "description": "The command to run for script checks." }, "Args": { "type": "array", "description": "Arguments for script checks.", "items": { "type": "string" } } } }, "UpdateStrategy": { "type": "object", "description": "Configuration for rolling update deployments.", "properties": { "MaxParallel": { "type": "integer", "description": "Maximum number of allocations to update simultaneously.", "minimum": 0 }, "HealthCheck": { "type": "string", "description": "The health check strategy for deployed allocations.", "enum": ["checks", "task_states", "manual"] }, "MinHealthyTime": { "type": "integer", "description": "Minimum time in nanoseconds an allocation must be healthy before considered successful." }, "HealthyDeadline": { "type": "integer", "description": "Deadline in nanoseconds for a single allocation to become healthy." }, "ProgressDeadline": { "type": "integer", "description": "Deadline in nanoseconds for overall deployment progress." }, "AutoRevert": { "type": "boolean", "description": "If true, automatically reverts to the last stable version on deployment failure." }, "AutoPromote": { "type": "boolean", "description": "If true, automatically promotes canary allocations when all are healthy." }, "Canary": { "type": "integer", "description": "The number of canary allocations to create during an update.", "minimum": 0 }, "Stagger": { "type": "integer", "description": "Time in nanoseconds to wait between batches of updates." } } }, "PeriodicConfig": { "type": "object", "description": "Configuration for periodic (cron-like) jobs.", "properties": { "Enabled": { "type": "boolean", "description": "Whether the periodic job is enabled." }, "Spec": { "type": "string", "description": "The cron expression for the job schedule." }, "SpecType": { "type": "string", "description": "The type of schedule specification.", "enum": ["cron"] }, "ProhibitOverlap": { "type": "boolean", "description": "If true, prevents launching new instances while previous ones are running." }, "TimeZone": { "type": "string", "description": "The time zone for the cron expression (e.g., America/New_York)." } } }, "ParameterizedConfig": { "type": "object", "description": "Configuration for parameterized dispatch jobs.", "properties": { "Payload": { "type": "string", "description": "Whether the payload is optional, required, or forbidden.", "enum": ["optional", "required", "forbidden"] }, "MetaRequired": { "type": "array", "description": "Required metadata keys for dispatch.", "items": { "type": "string" } }, "MetaOptional": { "type": "array", "description": "Optional metadata keys for dispatch.", "items": { "type": "string" } } } }, "Constraint": { "type": "object", "description": "A scheduling constraint.", "properties": { "LTarget": { "type": "string", "description": "The left-hand side target of the constraint." }, "RTarget": { "type": "string", "description": "The right-hand side target of the constraint." }, "Operand": { "type": "string", "description": "The constraint operator.", "enum": ["=", "!=", ">", ">=", "<", "<=", "regexp", "set_contains", "set_contains_any", "version", "semver", "is_set", "is_not_set", "distinct_hosts", "distinct_property"] } } }, "Affinity": { "type": "object", "description": "A soft scheduling preference.", "properties": { "LTarget": { "type": "string", "description": "The left-hand side target of the affinity." }, "RTarget": { "type": "string", "description": "The right-hand side target of the affinity." }, "Operand": { "type": "string", "description": "The affinity operator." }, "Weight": { "type": "integer", "description": "The weight of the affinity, from -100 to 100.", "minimum": -100, "maximum": 100 } } }, "Spread": { "type": "object", "description": "A spread target for distributing allocations across attribute values.", "properties": { "Attribute": { "type": "string", "description": "The attribute to spread on." }, "Weight": { "type": "integer", "description": "The weight of the spread, from 0 to 100.", "minimum": 0, "maximum": 100 }, "SpreadTarget": { "type": "array", "description": "The target distribution of allocations.", "items": { "type": "object", "properties": { "Value": { "type": "string" }, "Percent": { "type": "integer", "minimum": 0, "maximum": 100 } } } } } }, "RestartPolicy": { "type": "object", "description": "Policy for restarting failed tasks.", "properties": { "Interval": { "type": "integer", "description": "The duration in nanoseconds for which the restart attempts are tracked." }, "Attempts": { "type": "integer", "description": "Maximum number of restart attempts within the interval.", "minimum": 0 }, "Delay": { "type": "integer", "description": "Duration in nanoseconds to wait between restart attempts." }, "Mode": { "type": "string", "description": "The restart behavior after exceeding attempts.", "enum": ["delay", "fail"] } } }, "EphemeralDisk": { "type": "object", "description": "Configuration for the ephemeral disk of a task group.", "properties": { "SizeMB": { "type": "integer", "description": "The size of the ephemeral disk in megabytes.", "minimum": 1, "default": 300 }, "Sticky": { "type": "boolean", "description": "If true, attempts to place the allocation on the same node as a previous allocation." }, "Migrate": { "type": "boolean", "description": "If true, migrates the disk data from a previous allocation." } } }, "VolumeRequest": { "type": "object", "description": "A volume request for a task group.", "properties": { "Name": { "type": "string", "description": "The name of the volume." }, "Type": { "type": "string", "description": "The type of volume.", "enum": ["host", "csi"] }, "Source": { "type": "string", "description": "The source of the volume (host volume name or CSI volume ID)." }, "ReadOnly": { "type": "boolean", "description": "If true, the volume is mounted as read-only." } } }, "Template": { "type": "object", "description": "A template for rendering dynamic configuration files.", "properties": { "SourcePath": { "type": "string", "description": "Path to the template source file." }, "DestPath": { "type": "string", "description": "Path where the rendered template will be written." }, "EmbeddedTmpl": { "type": "string", "description": "Inline template content." }, "ChangeMode": { "type": "string", "description": "Action to take when the template changes.", "enum": ["noop", "restart", "signal"], "default": "restart" }, "ChangeSignal": { "type": "string", "description": "Signal to send when ChangeMode is 'signal'." }, "Perms": { "type": "string", "description": "File permissions for the rendered template.", "pattern": "^[0-7]{3,4}$" }, "Envvars": { "type": "boolean", "description": "If true, the template is parsed as environment variables." } } }, "TaskArtifact": { "type": "object", "description": "An artifact to download before task execution.", "required": ["GetterSource"], "properties": { "GetterSource": { "type": "string", "description": "The URL to download the artifact from." }, "GetterOptions": { "type": "object", "description": "Options for the artifact getter.", "additionalProperties": { "type": "string" } }, "GetterMode": { "type": "string", "description": "The download mode.", "enum": ["any", "file", "dir"] }, "RelativeDest": { "type": "string", "description": "The destination path relative to the task directory." } } }, "ScalingPolicy": { "type": "object", "description": "A scaling policy for dynamically adjusting task group count.", "properties": { "Min": { "type": "integer", "description": "Minimum count for the task group.", "minimum": 0 }, "Max": { "type": "integer", "description": "Maximum count for the task group.", "minimum": 0 }, "Enabled": { "type": "boolean", "description": "Whether the scaling policy is enabled." }, "Policy": { "type": "object", "description": "The autoscaling policy configuration.", "additionalProperties": true } } } } }