GuidesAPI Reference
Log In

Advanced: Structured Fetch Output in Custom Runtimes

Instead of having fetch return 0 or 2, you can have fetch instead return a structured JSON.

As the Custom Runtime owner, the reason to implement structured fetch output is to give a first-class experience to engineers.

  1. Version strings in the Prodvana UI will now represent actual running versions, not the fetch command version.
  2. External Runtime objects managed by the Custom Runtime will appear natively in the UI.

To implement structured fetch output, your Custom Runtime must have the ability to track the Prodvana Service bundle versions. For example, if your infrastructure supports tagging, you can tag running instances with the Service version.

Implementing Structured Fetch Output

  1. Install pvn-wrapper into the Docker image you will use to run fetch.
  2. Modify your fetch command in your Custom Runtime config to start with pvn-wrapper exec --. This will allow us to store stdout and stderr for your process separately, as Kubernetes combines them into one stream otherwise. For example:
runtime:
  custom:
    fetch:
      fetchMode: STRUCTURED_OUTPUT
      program:
        cmd:
        - pvn-wrapper
        - exec
        - --
        - my-fetch
        - --my-fetch-flag=value
        - my-fetch-args
        ... # rest of config here
    ... # rest of config here
  1. Modify your fetch command:
    1. Successful executions, drifted or not, should always exit 0 now. Do not exit 2 for drift.
    2. Your fetch command's stderr can contain whatever you need for debugging the fetch command itself.
    3. Your fetch command's stdout must be JSON with the schema in the next section.
    4. Note that a Service Instance using the Custom Runtime will only converge when all of the following are true for all returned Runtime objects:
      1. The Runtime object status is SUCCEEDED.
      2. One of the versions returned match the desired version, is active, and is not drifted.
      3. There is only one active version.
  2. Modify your apply command to make use of the variable PVN_SERVICE_VERSION, which is automatically injected and is the desired version. When the apply command starts workload, it should store this version string with the workload started so that fetch can later retrieve it.

📘

PVN_SERVICE_ID Variable

The environment variable PVN_SERVICE_ID is available to both the fetch and apply and can further be used to ensure that the Runtime object was really started by this Service. This can be useful, e.g., in the event the same Runtime object was moved between two different Services. Store the Service ID as part of the apply command. On fetch, check if the ID matches the desired ID, and if not, treat the version as unknown (i.e. make the version string empty).

Fetch Output Schema

// NOTE: comments are not supported. We are commenting here for documentation purposes only.
{
  "objects": [  // required, list of Runtime objects tracked by this Custom Runtime. This should be the equivalent of a Kubernetes Deployment, e.g. an ECS Service or a Google Cloud Run object
    {
      "name": "object_name",  // required
      "objectType": "object_type",  // required
      "versions": [  // optional, but required for convergence to succeed. List of versions seen by instances of this object, e.g. pods
        {
          "version": "prodvana-version-string",  // required, version string passed down from Prodvana as part of the apply command. Unknown versions not started by Prodvana should have an empty version string.
          "active": false,  // optional
          "drifted": false,  // optional
          "replicas": 0,  // optional, created/running replicas, regardless of their state
          "availableReplicas": 0,  // optional, how many replicas have passed healthchecks and are considered healthy
          "targetReplicas": 0,  // optional, how many replicas are supposed to be spun up, if known. This is purely informational and not used to compute convergence status.
        }
      ],
      "status": "PENDING" | "SUCCEEDED" | "FAILED",  // optional, status of this object, defaults to PENDING
      "externalLinks": [  // optional, useful links to surface to Service owners for this object
        {
          "type": "UNKNOWN" | "DETAIL" | "LOG",  // optional, defaults to UNKNOWN, affects how Prodvana UI renders the link.
          "url": "https://mylink/my-runtime-object",  // required
          "name": "name-of-link",  // required
        }
      ],
      "debugEvents": [  // optional, recent events associated with this Runtime object, to help explain the object status
        {
          "timestamp": "2006-01-02T15:04:05Z07:00",  // required, timestamp in RFC 3339 format
          "message": "this event details",  // required, what happened at this time
        }
      ],
      "message": "my message",  // optional, freeform message explaining the status for debug purposes
    }
  ]
}

Example Implementations