JobFrame platform.job-frame@1

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

Version
1.0.0
Owner
network
Visibility
public
Status
active
Compatibility
backward
Decision
ADR-034
Schema
https://openvibe.network/contracts/platform/job-frame.v1.json

platform.job-frame@1: one job lifecycle frame on the device control link (plan T14 Run; ADR-034 proposed). The link is OpenVibe.Node's WebSocket to OpenVibe.Bot (Node docs/protocol.md section 2); Fabric may terminate it later. Each frame is one JSON object in one text message, with the link's envelope at the top level: `v` (1), `seq` (per-direction counter from 1 on each connection), `ts` (sender's clock, Unix ms) and `type`. Server to device: `job`, `job_cancel`, `job_exit_ack`. Device to server: `job_started`, `job_stdout`, `job_usage`, `job_exit`. The link's existing `ack`/`nack` frames, keyed by the job id, accept or refuse a `job`; a worker that runs jobs advertises its classes in `status.capabilities`. A running `function` job is metered per wall-clock second into platform.usage-sample@1 readings: see `job_usage` and `job_exit`.

Fields

This schema has no named fields.

Examples

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

Valid: job-cancel
{
  "v": 1,
  "seq": 8,
  "ts": 1790935201150,
  "type": "job_cancel",
  "id": "job_01JAB2C3D4E5F6G7H8J9K0MNPQ"
}
Valid: job-exit-ack
{
  "v": 1,
  "seq": 9,
  "ts": 1790935202650,
  "type": "job_exit_ack",
  "id": "job_01JAB2C3D4E5F6G7H8J9K0MNPQ"
}
Valid: job-exit-never-started
{
  "v": 1,
  "seq": 9,
  "ts": 1790935260250,
  "type": "job_exit",
  "id": "job_01JAB2C3D4E5F6G7H8J9K0MNPQ",
  "reason": "ttl",
  "code": null,
  "result": null,
  "usage": {
    "wall_ms": 0
  }
}
Valid: job-exit
{
  "v": 1,
  "seq": 15,
  "ts": 1790935202600,
  "type": "job_exit",
  "id": "job_01JAB2C3D4E5F6G7H8J9K0MNPQ",
  "reason": "exited",
  "code": 0,
  "result": {
    "url": "media:object-7"
  },
  "usage": {
    "started_ms": 1790935200250,
    "wall_ms": 2350,
    "cpu_ms": 1800,
    "mem_peak_bytes": 41943040
  }
}
Valid: job-started
{
  "v": 1,
  "seq": 11,
  "ts": 1790935200255,
  "type": "job_started",
  "id": "job_01JAB2C3D4E5F6G7H8J9K0MNPQ",
  "started_ms": 1790935200250
}
Valid: job-stdout
{
  "v": 1,
  "seq": 13,
  "ts": 1790935201350,
  "type": "job_stdout",
  "id": "job_01JAB2C3D4E5F6G7H8J9K0MNPQ",
  "chunk_seq": 1,
  "chunk": "resized 1 of 1\n"
}
Valid: job-usage
{
  "v": 1,
  "seq": 12,
  "ts": 1790935201250,
  "type": "job_usage",
  "id": "job_01JAB2C3D4E5F6G7H8J9K0MNPQ",
  "started_ms": 1790935200250,
  "second": 0,
  "cpu_ms": 640
}
Valid: job
{
  "v": 1,
  "seq": 7,
  "ts": 1790935200000,
  "type": "job",
  "job": {
    "id": "job_01JAB2C3D4E5F6G7H8J9K0MNPQ",
    "class": "function",
    "artifact": {
      "name": "thumbnail",
      "version": "1.2.0"
    },
    "args": {
      "width": 320
    },
    "ttl_ms": 60000,
    "limits": {
      "wall_ms": 30000,
      "cpu_ms": 30000,
      "mem_bytes": 268435456
    }
  }
}
Rejected: envelope-v2
{
  "v": 2,
  "seq": 8,
  "ts": 1790935200250,
  "type": "job_cancel",
  "id": "job_01JAB2C3D4E5F6G7H8J9K0MNPQ"
}
Rejected: exit-ran-without-started-ms
{
  "v": 1,
  "seq": 15,
  "ts": 1790935202600,
  "type": "job_exit",
  "id": "job_01JAB2C3D4E5F6G7H8J9K0MNPQ",
  "reason": "exited",
  "code": 0,
  "result": null,
  "usage": {
    "wall_ms": 2350
  }
}
Rejected: exit-unknown-reason
{
  "v": 1,
  "seq": 15,
  "ts": 1790935202600,
  "type": "job_exit",
  "id": "job_01JAB2C3D4E5F6G7H8J9K0MNPQ",
  "reason": "oom",
  "code": null,
  "result": null,
  "usage": {
    "started_ms": 1790935200250,
    "wall_ms": 2350
  }
}
Rejected: stdout-without-chunk-seq
{
  "v": 1,
  "seq": 13,
  "ts": 1790935201350,
  "type": "job_stdout",
  "id": "job_01JAB2C3D4E5F6G7H8J9K0MNPQ",
  "chunk": "x"
}
Rejected: unknown-type
{
  "v": 1,
  "seq": 15,
  "ts": 1790935200250,
  "type": "job_pause",
  "id": "job_01JAB2C3D4E5F6G7H8J9K0MNPQ"
}
Rejected: usage-partial-second
{
  "v": 1,
  "seq": 12,
  "ts": 1790935201250,
  "type": "job_usage",
  "id": "job_01JAB2C3D4E5F6G7H8J9K0MNPQ",
  "started_ms": 1790935200250,
  "second": 2,
  "quantity": 0.35
}

Validate

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