Docker Compose представляет собой инструмент для определения и управления многоконтейнерными приложениями. В контексте разработки с использованием фреймворка Fresh он позволяет создавать изолированные среды для приложения, баз данных и вспомогательных сервисов, обеспечивая воспроизводимость и удобство развертывания.
Обычно проект Fresh имеет следующую структуру:
project/
├─ app/
│ ├─ components/
│ ├─ routes/
│ └─ main.ts
├─ static/
├─ Dockerfile
├─ docker-compose.yml
└─ deno.json
Файл Dockerfile должен обеспечивать установку Deno и
подготовку приложения к запуску:
# Использование официального Deno образа
FROM denoland/deno:alpine-1.42.3
# Создание рабочей директории
WORKDIR /app
# Копирование файлов проекта
COPY . .
# Разрешение необходимых прав
RUN deno cache main.ts
# Определение порта и команды запуска
EXPOSE 8000
CMD ["run", "--allow-net", "--allow-read", "main.ts"]
Ключевые моменты:
--allow-net нужен для сетевых операций, а
--allow-read — для доступа к файловой системе.8000 является стандартным для приложений
Fresh.Файл docker-compose.yml описывает несколько сервисов.
Пример с приложением Fresh и базой данных PostgreSQL:
version: '3.9'
services:
app:
build: .
ports:
- "8000:8000"
volumes:
- .:/app
depends_on:
- db
db:
image: postgres:15-alpine
environment:
POSTGRES_USER: user
POSTGRES_PASSWORD: password
POSTGRES_DB: fresh_db
ports:
- "5432:5432"
volumes:
- db_data:/var/lib/postgresql/data
volumes:
db_data:
Особенности конфигурации:
volumes позволяет синхронизировать локальный код с
контейнером, что упрощает разработку.depends_on гарантирует, что база данных будет запущена
перед приложением.Для работы с базой данных необходимо использовать правильный хост и
порт. Внутри Docker Compose сервисы общаются через имена сервисов,
указанные в docker-compose.yml. В примере выше приложение
Fresh может подключаться к PostgreSQL по адресу
db:5432.
Пример подключения с использованием Deno и Postgres драйвера:
import { Client } from "https://deno.land/x/postgres/mod.ts";
const client = new Client({
user: "user",
database: "fresh_db",
hostname: "db",
password: "password",
port: 5432,
});
await client.connect();
// выполнение запроса
const result = await client.queryObject("SELECT NOW()");
console.log(result);
await client.end();
Использование томов позволяет изменять код локально и сразу видеть результат в контейнере без пересборки образа:
volumes:
- .:/app
При этом Deno в режиме разработки (deno run --watch)
автоматически отслеживает изменения файлов.
В крупных проектах Docker Compose может содержать несколько файлов для разных сред:
docker-compose.yml — базовая конфигурация.docker-compose.override.yml — локальные настройки для
разработки.docker-compose.prod.yml — оптимизированная для продакшн
конфигурация.Это позволяет запускать приложение с разными параметрами, например:
docker-compose -f docker-compose.yml -f docker-compose.override.yml up
Для продакшн-сборки рекомендуется использовать многоэтапные Dockerfile:
FROM denoland/deno:alpine-1.42.3 AS builder
WORKDIR /app
COPY . .
RUN deno cache main.ts
FROM denoland/deno:alpine-1.42.3
WORKDIR /app
COPY --from=builder /app /app
EXPOSE 8000
CMD ["run", "--allow-net", "--allow-read", "main.ts"]
Преимущества:
Docker Compose упрощает просмотр логов:
docker-compose logs -f app
Для отдельного сервиса можно ограничить поток:
docker-compose logs -f db
Compose создает собственную сеть, что позволяет сервисам общаться без внешнего IP. Для дополнительной изоляции можно задавать пользовательские сети:
networks:
fresh_network:
driver: bridge
services:
app:
networks:
- fresh_network
db:
networks:
- fresh_network
Это предотвращает случайный доступ из других контейнеров.
Для приложений Fresh возможен горизонтальный масштаб через Compose:
docker-compose up --scale app=3
Каждый экземпляр приложения получает отдельный контейнер, что полезно при нагрузочном тестировании.
Такой подход к Docker Compose обеспечивает воспроизводимую среду разработки и продакшн-развертывания, позволяя эффективно управлять сервисами и интеграциями внутри проекта Fresh.