DIAL App Controller API
This reference covers App Controller 0.5.1 lifecycle endpoints for platform engineers integrating the controller with Core. The API is internal to the control plane. Application authors normally use DIAL Core and the Code Apps interface.
Endpoints
Paths are relative to the controller URL, such as http://dial-app-controller:8080.
| Method | Path | Request | Result |
|---|---|---|---|
GET | /health | None | Empty successful HTTP response |
POST | /v1/image/{name} | Source folder and optional runtime | SSE result containing image |
DELETE | /v1/image/{name} | None | SSE result containing deleted |
POST | /v1/deployment/{name} | Optional image, environment, and scale overrides | SSE result containing url |
DELETE | /v1/deployment/{name} | None | SSE result containing deleted |
GET | /v1/deployment/{name}/logs | None | JSON logs array |
POST | /v1/session/{name} | Image and optional environment | SSE result containing the pod's url |
DELETE | /v1/session/{name} | None | SSE result containing deleted |
The released handlers are ImageController, DeploymentController, SessionController, and HealthController.
{name} identifies the operation's image or workload. Generated Kubernetes names use app-ctrl-build-, app-ctrl-app-, app-ctrl-session-, or app-ctrl-dial-auth- prefixes. See NamingUtils.
Image build
POST /v1/image/{name} accepts JSON:
| Field | Required | Default | Description |
|---|---|---|---|
sources | Yes | — | DIAL file-storage folder containing the project, such as files/<BUCKET>/sources/. The builder requires a folder. |
runtime | No | APP_DEFAULT_RUNTIME | Key in the controller's app.runtimes map. The bundled default is python3.11. |
Optional api-key and Authorization: Bearer <TOKEN> headers are passed to the source preparation container as DIAL credentials. Core supplies its per-request key when requesting a Code App build. These credentials authorize source downloads; they do not configure access control for the controller API.
Example build request:
curl --no-buffer --request POST \
http://0.0.0.0:8080/v1/image/example-app \
--header 'Content-Type: application/json' \
--header 'api-key: <DIAL_API_KEY>' \
--data '{"sources":"files/<BUCKET>/sources/","runtime":"python3.11"}'
An example result with default image naming is:
event:result
data:{"image":"<REGISTRY>/app-example-app:latest"}
Source: request handling and Core's build request.
Knative deployment
POST /v1/deployment/{name} accepts the following optional JSON fields:
| Field | Default | Description |
|---|---|---|
env | Empty map | Environment variables placed on the application container. |
image | Image derived from {name} and registry settings | Existing image to deploy instead of the generated application image. |
initialScale | Service template value | Overrides autoscaling.knative.dev/initial-scale. The bundled template uses 0. |
minScale | Service template value, unset in the bundled template | Overrides autoscaling.knative.dev/min-scale. |
maxScale | Service template value | Overrides autoscaling.knative.dev/max-scale. The bundled template uses 3. |
An empty JSON object deploys the image associated with the name. The result contains the URL returned by Knative. Scale overrides and image selection are implemented in ConfigService.
GET /v1/deployment/{name}/logs returns:
{
"logs": [
{"instance": "<POD_NAME>", "content": "<CONTAINER_LOG>"}
]
}
Logs come from the configured application container in service pods whose container state is not waiting. This endpoint does not return build Job logs. See DeployService.
Session pod
POST /v1/session/{name} accepts:
| Field | Required | Default | Description |
|---|---|---|---|
image | Yes | — | Container image to run. |
env | No | Empty map | Environment variables passed to the session container. Core supplies SESSION_ID for its pod-backed interpreter mode. |
Example body:
{
"image": "epam/ai-dial-code-interpreter:0.2.0",
"env": {"SESSION_ID": "<DEPLOYMENT_ID>"}
}
The result contains http://<POD_IP>:8080. Pod creation and deletion use APP_DEPLOY_NAMESPACE. These operations do not build an image or create a Knative service. See SessionService.
Streamed results and failures
Lifecycle operations use text/event-stream. The controller emits heartbeat comments while work is pending, then a result or error event:
:heartbeat
event:error
data:{"message":"<ERROR_MESSAGE>"}
An HTTP connection succeeding does not mean the lifecycle operation succeeded. The caller must inspect the terminal SSE event. Malformed request binding can also fail before an operation stream is created. See SseUtils.
| Failure | Meaning |
|---|---|
| Unsupported runtime | The requested runtime has no entry in app.runtimes. |
| Source validation failure | The builder rejected the source folder, entrypoint, or requirements. |
| Image build failure | The Kubernetes Job failed or exceeded its wait time; a log excerpt can accompany the error. |
| Deployment or session failure | Kubernetes or Knative did not provide the required workload result within the configured wait. |
| Registry failure during cleanup | The controller could not retrieve or delete the image manifest. Registry deletion must be supported and authorized. |
Deletion results contain {"deleted":true} or {"deleted":false}. Image deletion also attempts build Job and credential Secret cleanup; it does not undeploy a running Knative service. Knative undeployment deletes the service and explicitly deletes its remaining pods. See BuildService and DeployService.
Successful builds remove their build Job and credential Secret. A failed build can leave those resources behind because its error ends the success cleanup chain. The image-delete operation provides cleanup for the same name; see build completion and cleanup.
Further reading
- Controller configuration — image names, templates, namespaces, and timeouts
- App Builder Python — the source preparation phase behind image creation
- Code Interpreter API — Core's public session API and the private interpreter endpoints
- Code Apps overview — how Code Apps are hosted, secured, and shared