Appearance
Code Runner
Описание
runner-code — раннер для выполнения произвольного кода в закрытой песочнице (Docker). Тело задачи (command) — это исходный код; язык и зависимости задаются переменными задачи.
Схема выполнения:
- Код записывается в файл (
main.py,main.js, ...) во временный workspace на хосте, который монтируется в контейнер как/workspace. - Если заданы зависимости — они устанавливаются отдельным контейнером с доступом в сеть (
install_network, по умолчаниюbridge). Зависимости ставятся внутрь/workspaceи переживают контейнер. - Код запускается в контейнере без сети (
network=noneпо умолчанию) с лимитами памяти/CPU/pids,--cap-drop=ALLиno-new-privileges. - Файлы, записанные кодом в
$ARTIFACT_DIR(/workspace/artifacts), автоматически загружаются в storage платформы.
Поддерживаемые языки
| Язык | Алиасы | Образ по умолчанию | Файл кода | Зависимости |
|---|---|---|---|---|
python | py, python3 | python:3.12-slim | main.py | pip (CODE_DEPS, CODE_DEPS_FILE = requirements.txt) |
node | js, javascript, nodejs | node:22-alpine | main.js | npm (CODE_DEPS, CODE_DEPS_FILE = package.json) |
typescript | ts | node:22-alpine | main.ts | npm (как node), запуск через --experimental-strip-types |
go | golang | golang:1.24-alpine | main.go | go get + go mod tidy (CODE_DEPS_FILE = go.mod) |
ruby | rb | ruby:3.3-slim | main.rb | gem install (CODE_DEPS) |
php | — | php:8.3-cli | main.php | не поддерживаются |
bash | sh, shell | alpine:3.20 | main.sh | apk-пакеты; ставятся в том же контейнере, поэтому запуск идёт с сетью |
Конфигурация
Общие параметры runner-common
См. Общая документация.
Специфичные параметры
| Параметр (config) | Env | Флаг | По умолчанию | Описание |
|---|---|---|---|---|
docker_host | DOCKER_HOST | -docker-host | из окружения | Хост docker daemon |
pull_policy | CODE_PULL_POLICY | -pull-policy | if-not-present | always | if-not-present | never |
default_language | CODE_DEFAULT_LANGUAGE | -default-language | — | Язык, если задача не задала CODE_LANGUAGE |
network | CODE_NETWORK | -network | none | Сеть на стадии запуска кода |
install_network | CODE_INSTALL_NETWORK | -install-network | bridge | Сеть на стадии установки зависимостей |
memory | CODE_MEMORY | -memory | 512m | Лимит памяти контейнера |
cpus | CODE_CPUS | -cpus | 1.0 | Лимит CPU |
pids_limit | CODE_PIDS_LIMIT | -pids-limit | 256 | Лимит числа процессов |
user | CODE_USER | -user | из образа | Пользователь контейнера (1000:1000) |
upload_artifacts | CODE_UPLOAD_ARTIFACTS | -upload-artifacts | true | Загрузка артефактов из /workspace/artifacts |
images | — | — | см. таблицу языков | Переопределение образов по языкам |
Пример YAML
yaml
url: "https://app.com/"
token: "your-token"
concurrency: 2
tags: "code,sandbox"
description: "Sandboxed code executor"
default_language: python
network: none
install_network: bridge
memory: 512m
cpus: 1.0
pids_limit: 256
images:
python: "my-registry/python:3.12-slim"Переменные задачи
| Переменная | Описание | Пример |
|---|---|---|
CODE_LANGUAGE | Язык кода (обязательна, если нет default_language) | python |
CODE_DEPS | Список зависимостей (через запятую/пробел/перенос строки) | requests, pandas |
CODE_DEPS_FILE | Содержимое нативного файла зависимостей (requirements.txt / package.json / go.mod) | requests==2.32.0 |
CODE_IMAGE | Переопределение docker-образа | python:3.13-slim |
CODE_NETWORK | Переопределение сети стадии запуска | bridge |
CODE_UPLOAD_ARTIFACTS | Включить/выключить загрузку артефактов | false |
Все переменные задачи (включая служебные CODE_*) также передаются в контейнер запуска как переменные окружения.
Примеры задач
Python с зависимостями
command: |
import requests_mock # доступен: установлен на стадии deps
print("ok")
variables:
- { name: CODE_LANGUAGE, value: python }
- { name: CODE_DEPS, value: requests-mock }Точные версии через requirements.txt
variables:
- { name: CODE_LANGUAGE, value: python }
- name: CODE_DEPS_FILE
value: |
requests==2.32.3
pydantic>=2,<3Node/TypeScript
command: |
import { z } from "zod";
console.log(z.string().parse("hello"));
variables:
- { name: CODE_LANGUAGE, value: ts }
- { name: CODE_DEPS, value: zod }Go
command: |
package main
import (
"fmt"
"github.com/google/uuid"
)
func main() { fmt.Println(uuid.NewString()) }
variables:
- { name: CODE_LANGUAGE, value: go }
- { name: CODE_DEPS, value: github.com/google/uuid }Артефакты
Код пишет файлы в директорию из переменной окружения ARTIFACT_DIR (всегда /workspace/artifacts):
python
import os
out = os.environ["ARTIFACT_DIR"]
with open(os.path.join(out, "report.csv"), "w") as f:
f.write("a,b\n1,2\n")- Артефакты загружаются только при успешном выполнении (код возврата 0)
- Загружаются все файлы из
ARTIFACT_DIR(рекурсивно, с сохранением структуры) artifact_idвозвращается в статусе задачи
Передача переменных окружения
Переменные задачи передаются в контейнер запуска как env:
variables:
- { name: CODE_LANGUAGE, value: python }
- { name: API_MODE, value: staging }python
import os
print(os.environ["API_MODE"]) # stagingПесочница
- Сеть стадии запуска —
none(полная изоляция; переопределяетсяCODE_NETWORK/ конфигом) --cap-drop=ALL,--security-opt no-new-privileges- Лимиты: память (512m), CPU (1.0), pids (256)
- Файловая система хоста недоступна — монтируется только временный workspace
- Workspace удаляется после выполнения
- Таймаут задачи (
task_timeout) останавливает контейнер
Замечания:
- Для
bashзависимости (apk) ставятся в контейнер, поэтому при наличииCODE_DEPSзапуск идёт с сетью. - Стадия установки зависимостей имеет доступ в сеть — не передавайте секреты в задачи с недоверенными зависимостями.
Обработка ошибок
- Ненулевой код возврата → статус
failedс текстомCode failed with exit code N - Ошибка установки зависимостей →
failed(стадия запуска не выполняется) - Неизвестный язык / неподдерживаемые зависимости →
failedс пояснением - Таймаут контекста → контейнер останавливается, статус
failed
Остановка
Корректно обрабатывает SIGINT и SIGTERM. Запущенные контейнеры останавливаются и удаляются.