RunJobCreateRequest run.job-create-request@1

Generated at from openvibe-contracts v0.97.0 and openvibe-sdk v0.26.0.

Version
1.0.0
Owner
run
Visibility
public
Status
planned
Compatibility
backward
Decision
ADR-034
Schema
https://openvibe.network/contracts/run/job-create-request.v1.json

run.job-create-request@1 (PLANNED; plan T14 R1, ADR-034): the body of POST /api/v1/jobs on OpenVibe.Run (capability run.job.submit). The job belongs to the project the caller's token names. CLASS is a platform.runtime-class@1 name; Run accepts any of them but places a job only on a node that advertises worker:<class> (platform.resource-offer@1), so a class no node runs today (browser, linux, desktop, gpu) ends expired with run.job.unplaceable. ARTIFACT is the pre-registered artifact to run (name and one exact version), required for function and code, as platform.job@1 carries it. ARGS is the artifact's declared input as JSON (at most 512 KiB serialized, else 413). INPUTS are files placed in the job directory before the process starts, each an OpenVibe.Media object pinned by its sha256: a size or digest mismatch fails the job (run.job.input_digest_mismatch) before the process ever runs; Run never fetches a caller-chosen URL. LIMITS are hard caps merged stricter with the node's own (platform.job@1 limits); a request over the project's tier cap is refused 422 run.limits.exceeded, never silently lowered. EGRESS is the network the job may reach, the values of OpenVibe.Node's worker.egress, carried per job as the same-named platform.job@1 net: none (default; no network), public or openvibe-only. A job asking for public or openvibe-only is placed only on a node whose worker.egress allows it; a worker whose host policy is stricter runs the stricter one. REQUIREMENTS (platform.workload-requirements@1) narrow placement; absent means { kind: run.<class>, mobility: job, latency_class: background, objective: balanced }. IDEMPOTENCY_KEY: a repeat from the same project within 24 h with an identical body answers the first job (200, created false); with a different body 409 run.idempotency.conflict.

Fields

FieldTypeRequiredDescriptionConstraints
classplatform.runtime-classyes
artifacthttps://openvibe.network/contracts/run/job-create-request.v1.json#/$defs/artifact
argsobjectThe artifact's declared input as JSON; default {}.
inputshttps://openvibe.network/contracts/run/job-create-request.v1.json#/$defs/inputFiles placed in the job directory before the process starts; names are unique (else 422).
  • maxItems 32
limitshttps://openvibe.network/contracts/run/job-create-request.v1.json#/$defs/limitsyes
ttl_msintegerLifetime from creation, covering the wait for a node and the run (platform.job@1 ttl_ms); when it runs out the job ends expired. Default: limits.wall_ms plus 600000.
  • minimum 1000
  • maximum 86400000
egresshttps://openvibe.network/contracts/run/job-create-request.v1.json#/$defs/egress
requirementsplatform.workload-requirements
idempotency_keyhttps://openvibe.network/contracts/run/job-create-request.v1.json#/$defs/idempotency_key

Examples

From the contract's own test fixtures: valid ones validate, rejected ones must fail.

Valid: code-public-egress
{
  "class": "code",
  "artifact": {
    "name": "py-runner",
    "version": "3.12.1"
  },
  "args": {
    "entry": "main.py"
  },
  "limits": {
    "wall_ms": 600000,
    "cpu_ms": 600000,
    "mem_bytes": 1073741824
  },
  "egress": "public",
  "requirements": {
    "kind": "run.code",
    "mobility": "job",
    "latency_class": "background",
    "objective": "cheapest",
    "trust": [
      "first-party",
      "user-owned"
    ]
  }
}
Valid: function-with-input
{
  "class": "function",
  "artifact": {
    "name": "thumbnail",
    "version": "1.2.0"
  },
  "args": {
    "width": 320
  },
  "inputs": [
    {
      "name": "photo.jpg",
      "media_id": "med_01JAB2C3D4E5F6G7H8J9K0MNPS",
      "sha256": "9f86d081884c7d659a2feaa0c55ad015a3bf4f1b2b0b822cd15d6c15b0f00a08",
      "size_bytes": 482113
    }
  ],
  "limits": {
    "wall_ms": 30000,
    "cpu_ms": 30000,
    "mem_bytes": 268435456
  },
  "ttl_ms": 630000,
  "egress": "none",
  "idempotency_key": "thumb:photo-7"
}
Rejected: function-without-artifact
{
  "class": "function",
  "limits": {
    "wall_ms": 30000,
    "cpu_ms": 30000,
    "mem_bytes": 268435456
  }
}
Rejected: input-url
{
  "class": "function",
  "artifact": {
    "name": "thumbnail",
    "version": "1.2.0"
  },
  "args": {
    "width": 320
  },
  "inputs": [
    {
      "name": "photo.jpg",
      "media_id": "med_01JAB2C3D4E5F6G7H8J9K0MNPS",
      "sha256": "9f86d081884c7d659a2feaa0c55ad015a3bf4f1b2b0b822cd15d6c15b0f00a08",
      "size_bytes": 482113,
      "url": "https://example.com/photo.jpg"
    }
  ],
  "limits": {
    "wall_ms": 30000,
    "cpu_ms": 30000,
    "mem_bytes": 268435456
  },
  "ttl_ms": 630000,
  "egress": "none",
  "idempotency_key": "thumb:photo-7"
}
Rejected: input-without-digest
{
  "class": "function",
  "artifact": {
    "name": "thumbnail",
    "version": "1.2.0"
  },
  "args": {
    "width": 320
  },
  "inputs": [
    {
      "name": "photo.jpg",
      "media_id": "med_01JAB2C3D4E5F6G7H8J9K0MNPS"
    }
  ],
  "limits": {
    "wall_ms": 30000,
    "cpu_ms": 30000,
    "mem_bytes": 268435456
  },
  "ttl_ms": 630000,
  "egress": "none",
  "idempotency_key": "thumb:photo-7"
}
Rejected: limits-without-memory
{
  "class": "function",
  "artifact": {
    "name": "thumbnail",
    "version": "1.2.0"
  },
  "args": {
    "width": 320
  },
  "inputs": [
    {
      "name": "photo.jpg",
      "media_id": "med_01JAB2C3D4E5F6G7H8J9K0MNPS",
      "sha256": "9f86d081884c7d659a2feaa0c55ad015a3bf4f1b2b0b822cd15d6c15b0f00a08",
      "size_bytes": 482113
    }
  ],
  "limits": {
    "wall_ms": 30000,
    "cpu_ms": 30000
  },
  "ttl_ms": 630000,
  "egress": "none",
  "idempotency_key": "thumb:photo-7"
}
Rejected: unknown-egress
{
  "class": "function",
  "artifact": {
    "name": "thumbnail",
    "version": "1.2.0"
  },
  "args": {
    "width": 320
  },
  "inputs": [
    {
      "name": "photo.jpg",
      "media_id": "med_01JAB2C3D4E5F6G7H8J9K0MNPS",
      "sha256": "9f86d081884c7d659a2feaa0c55ad015a3bf4f1b2b0b822cd15d6c15b0f00a08",
      "size_bytes": 482113
    }
  ],
  "limits": {
    "wall_ms": 30000,
    "cpu_ms": 30000,
    "mem_bytes": 268435456
  },
  "ttl_ms": 630000,
  "egress": "lan",
  "idempotency_key": "thumb:photo-7"
}
Rejected: version-range
{
  "class": "function",
  "artifact": {
    "name": "thumbnail",
    "version": "^1.2"
  },
  "args": {
    "width": 320
  },
  "inputs": [
    {
      "name": "photo.jpg",
      "media_id": "med_01JAB2C3D4E5F6G7H8J9K0MNPS",
      "sha256": "9f86d081884c7d659a2feaa0c55ad015a3bf4f1b2b0b822cd15d6c15b0f00a08",
      "size_bytes": 482113
    }
  ],
  "limits": {
    "wall_ms": 30000,
    "cpu_ms": 30000,
    "mem_bytes": 268435456
  },
  "ttl_ms": 630000,
  "egress": "none",
  "idempotency_key": "thumb:photo-7"
}

Validate

const contracts = require('openvibe-contracts');
contracts.validate('run.job-create-request@1', value);   // { valid, errors: [{ path, message }] }