Каковы преимущества dockerizing nginx и php в разных контейнерах?


18

Я только начал работать с Docker и Kubernetes, и я смотрел много стеков, в которых некоторые люди собирают nginx + php в одном образе, а некоторые создают образ с помощью nginx, а другой - с php (монтируют по тому же пути и включают оба контейнера в одном и том же месте в Кубернетесе).

Каковы будут преимущества создания двух образов докеров вместо установки обоих nginx + php в один и тот же?

Ответы:


19

PHP с nginx обычно выполняется с использованием php-fpm, который представляет собой отдельный процесс.

Сохраняя основную идею докера одного процесса (подробности см. В конце ответа) для каждого контейнера, имеет смысл иметь процессы nginx и php-fpm в отдельных контейнерах.

Поскольку связь между nginx и php-fpm возникает через fastcgi, контейнер php-fpm также может находиться на отдельном хосте, что позволяет использовать кластер контейнеров php-fpm за nginx.

За стеной комментариев приведем еще немного предыстории, в документации докера есть параграф о том, что у контейнера должен быть только один интерес .

Основная идея контейнера Linux ( lxc ) состоит в том, чтобы запустить процесс в изолированном пространстве имен на уровне процессора и памяти, а Docker добавляет к этому изоляцию на уровне файловой системы.
Преимущество состоит в том, что компрометация процесса в этом пространстве имен не позволяет читать память других процессов и, следовательно, должна предотвращать другие компрометации на хосте.

Говоря о nginx и php-fpm, они работают в паре, но у каждого есть свои проблемы, nginx выполнит HTTP-часть, маршрутизацию, проверку заголовков и т. Д., А php-fpm выполнит интерпретацию кода и вернет html-часть в nginx. , Хотя обычно оба вместе подают одно приложение, это не обязательно.

В зависимости от контекста может быть проще иметь контейнер, включающий весь стек для приложения, на рабочей станции разработчика, например. Но в идеале для производственного использования старайтесь поддерживать меньшее количество взаимодействий внутри контейнера, поскольку разделение процессов в одном и том же контейнере с супервизором приносит свою долю проблем с точки зрения процесса зомби и обработки журналов (пример приведен здесь только для иллюстрации).

Итак, наконец, я процитирую страницу докера с некоторым акцентом:

Хотя «один процесс на контейнер» часто является хорошим практическим правилом, это не жесткое и быстрое правило. Делайте все возможное, чтобы контейнеры были максимально чистыми и модульными .

Не существует «правила серебряной пули», которое применимо ко всему, это всегда баланс между сложностью внутри контейнера и сложностью организации самих контейнеров.


3
Основная идея на самом деле такова: «У каждого контейнера должна быть только одна проблема», и «не обязательно верно, что в каждом контейнере должен быть только один процесс операционной системы». docs.docker.com/engine/userguide/eng-image/...
user2640621

Я признаю, что это упрощенная идея, nginx не является ни одним монолитным процессом, ни php-fpm, но в моем ответе замените процесс озабоченностью, и все в порядке. Nginx выполняет маршрутизацию, php-fpm выполняет интерпретацию
Tensibai

3
Ответ обычно один сервис один порт на контейнер, а не один процесс. С другой стороны, если у вас есть несколько запущенных процессов в контейнере, вам нужно учитывать некоторые процессы инициализации, управления службами, перезапусков, независимой регистрации, независимых зависимостей пакетов, это становится немного сложнее. И иногда отображение 1: 1 превращается в отображение 1: n при масштабировании.
Иржи Клауда

@Jiri, играющий адвоката дьявола: так, apache перед приложением rails, использующим базу данных postgres, должен находиться внутри одного контейнера? В конце концов, это всего лишь один сервис с внешней точки зрения.
Тенсибай,

1
@JiriKlouda ответ исправлен, я надеюсь, что он достаточно подробный, чтобы передать все вопросы, поднятые в комментариях.
Тенсибай

4

На самом деле, здесь не хватает одной точки - горизонтальная масштабируемость. Есть статья от Джейми Алкизы, давным-давно адресованная этому:

http://archive.is/pDzz0

Короче говоря, вы масштабируете php-fpm по горизонтали для достижения более высокой производительности. Совместное масштабирование Nginx + php-fpm не принесет вам никакой пользы. Я рекомендую вам провести некоторое стресс-тестирование (например, Tsung, Gatling и т. Д .; пожалуйста, не делайте Apache ab, это очень старая игрушка) самостоятельно, чтобы проверить, о чем говорилось в статье. У меня лично есть несколько реальных опытов, доказавших, что статья в целом верна

Но есть два недостатка (возможно, не для Kubernetes) для чистых металлических машин / виртуальных машин:

  1. Как настроить Nginx динамически обнаруживать изменения контейнера php-fpm? Это легкая часть.
  2. Как мы разделяем тот же том / файловые системы после масштабирования? Контейнеры Nginx и php-fpm должны считывать одно и то же содержимое для обеспечения согласованности. Это оставляет вам наименьшую часть головоломки (и самую забавную часть) для работы.

РЕДАКТИРОВАНИЕ: Теперь это почти половина года 2019. Старая модель, php-fpm + nginx в том же модуле, имеет другое использование. Если вы знакомы с сервисной сеткой, то nginx (или так называемая Nginmesh) служит коляской для обработки трафика, направленного с востока на запад. Трафик, привязанный к востоку и западу, в основном используется для аутентификации среди сервисов или других причудливых функций, тогда как чистый php-fpm не мог этого сделать.


3

Нет значимого преимущества, которое перевешивает необходимость управлять двумя контейнерами. Пока у вас есть отношения 1: 1 между процессами, и они служат одной цели, поместите их в один и тот же контейнер.


Вы имеете в виду разные изображения на одном контейнере?
CarlosAS

Как вы запустите nginx и php-fpm в одном контейнере? Пожалуйста, добавьте пример.
030

1
@ 030 вот пример
CarlosAS

2
@carlos Очень подходящий пример для целей разработки, я бы заблокировал подобные вещи для производственного использования (запуск супервизора в контейнере может легко превратиться в ружье)
Tensibai

Я не согласен с этим ответом, с этой аргументацией сервер apache с модовой безопасностью, разговаривающий с котом, разговаривающим с сервером postgresql, на котором размещено только одно приложение, должен помещаться в одном контейнере.
Тенсибай,

-1

Преимущество: вы можете запускать несколько контейнеров php-fpm в бэк-энде, мы называем это кластером PHP, через количество портов. Пример порта 9000, 9001, 9002 и т. Д.

Используя наш сайт, вы подтверждаете, что прочитали и поняли нашу Политику в отношении файлов cookie и Политику конфиденциальности.
Licensed under cc by-sa 3.0 with attribution required.