Comments 45
Кстати, если вы работаете над несколькими взаимодействующими веб-приложениями, то для связки нужно будет использовать docker-compose, дам мой пример:
Заголовок спойлера
version: "2"

networks:
    lan_0:
        driver: bridge
        ipam:
            driver: default
            config:
                - subnet: 172.19.0.0/24
                  gateway: 172.19.0.21

services:
    nginx:
        build: ./nginx/
        ports:
            - 80:80
            - 443:443
        links:
            - php
        volumes:
            - ./code:/var/www/
        networks:
            lan_0:
                ipv4_address: 172.19.0.22
    php:
        build: ./php/
        expose:
            - 9000
        volumes:
            - ./code/:/var/www/
        extra_hosts:
            - "website.local:172.19.0.22"
            - "api.local:172.19.0.22"
        networks:
            lan_0:
                ipv4_address: 172.19.0.23
    mysql:
        build: ./mysql/
        environment:
            MYSQL_ROOT_PASSWORD: root
            MYSQL_DATABASE: dev
        ports:
            - 3306:3306
        volumes:
            - ./mysql/sql:/docker-entrypoint-initdb.d
            - ./mysql/data:/var/lib/mysql
        networks:
            lan_0:
                ipv4_address: 172.19.0.12

то есть, путем прокладывания сети.
Указывать явные IP необязательно, docker-compose автоматически перелинкует контейнеры и они по умолчанию будут доступны по имени своего service. В примере выше, вероятно, было важно иметь фиксированные IP.
Я бы вообще ничего без docker-compose не запускал, иначе потом черт ногу сломит с этими контейнерами, а compose делает имена вида folder_service_n, делает сам отдельную сетку с таким же названием папки.

Кстати, а зачем вообще указывать extra_hosts и IP адреса? Docker же позволяет внутри одной сети работать просто по имени сервиса, да и порты все наружу открывать не нужно, достаточно только для nginx.
Docker-compose хороший инструмент и конечно же его стоит использовать. Но все же, я бы исключил его для новичков, которые только-только начинают ознакамливаться с Docker'ом.
Ну видимо каждому своё, я наоборот несказанно счастлив, что параллельно учился пользоваться docker и docker-compose.
имена вида folder_service_n

Я даже больше скажу, я никогда не использую чистый образ (типа image: mysql:latest), а делаю примерно так:

version: '2'
services:
    myproject-db:
        build:
            context: .
            dockerfile: .docker/dev/db/Dockerfile
        image: myproject:db
        container_name: myproject_db


Таким образом я получаю фиксированные имена образа и контейнера (если использовать версионирование, то имя образа лучше писать в виде myproject-app:vesion, как принято в dockerhub).

При этом Dockerfile может содержать просто FROM mysql:latest, или же дополнительные инструкции.
Зачем в данном примере явно создавать сеть и прописывать ip?
docker-compose всё сделает за вас
я очень сомневаюсь, что вы из php-контейнера сможете достучаться до какого-нибудь из хостов.
Что вы имеете ввиду? Используя docker-compose можно обращаться к «своим» хостам по имени сервиса
Обьясняю. У вас есть nginx-контейнер и php-контейнер, они оба дают возможность работе двум web-сервисам site.local и api.local, если из nginx-контейнера вы можете получить доступ к обоим хостам, то в php-контейнере вам ни один не будет доступен, и из кода site.local нельзя будет сделать обращение к api.local.
Можете мне пояснить, как человеку незнакомому с Docker: если ли смысл использовать описанный подход вместо связки Vagrant + VirtualBox?
вагрант — очень тугой инструмент, докер же быстрее, да и удобнее, как по мне.
Если все устраивает, то переходить резко на докер я бы не стал. Для нового приложения имеет смысл попробовать.
Все от задач зависит. Лично я использую докер в нескольких виртуалках, развернутых варгантом (к слову, вагрант не показался мне удачным решением для разворачивания и уж тем более управления большим количеством виртуалок). Опять же, если требуется запустить зоопарк сервисов на одной машине, то докер отличное решение. Если же нужно давать доступ к машине 3-м лицам, то однозначно виртуалки.
Если ваша связка Vagrant + Virtualbox работает стабильно, и у вас нет необходимости периодически добавлять новые сервисы в проект, то данную связку вполне удобно использовать, особенно если у вас уже все настроено и отлажено, включая процессы.

Но если вы захотите сделать апгрейд вашей системы, то наверно уже стоит подумать об уходе от зависимости от Vagrant.

Я как раз имел такой опыт перехода с Vagrant на Docker. И при этом столкнулся с рядом трудностей. Например, Docker из коробки не предлагает никакой автоматизации. Есть конечно docker-compose, но его возможности по сравнению с Vagrant весьма скудные (YAML все-таки не сравнить с полноценным ЯП). В итоге пришлось разрабатывать свое собственное решение.

Если вы все же захотите попробовать Docker без отказа от Vagrant, то последний предоставляет такую возможность, но разобраться в настройке не так то просто. Мне очень помогло в свое время вот это описание процесса настройки Vagrant + Docker.
Куча sed'ов выглядит ужасно. Я бы просто создал конфиг-файл и переписал бы им дефолтный файл конфига
Куча sed'ов выглядит ужасно.
Альтернативы ни чем не лучше, везде будет тот же самый PCRE (в лучшем случае)
Я бы просто создал конфиг-файл и переписал бы им дефолтный файл конфига
Простые решения увы не всегда подходят, иногда надо сохранить имеющийся конфиг. А со временем приходит понимание, что sed вовсе не ужасен, а совсем даже наоборот
Альтернативы ни чем не лучше, везде будет тот же самый PCRE (в лучшем случае)

Гораздо лучше: допишите эти измененные строки в новом ini-файле в mods-available директории.
Не надо править конфиги: либо переписываете своим, либо дополняете (самый чистый вариант).

А со временем приходит понимание, что sed вовсе не ужасен, а совсем даже наоборот

Он не просто ужасен, а отвратителен, и уровень отвратительности пропорционален величине проекта.
Например, вариант с шаблонизатором (подход популярен в средствах управления инфраструктурой) гораздо чище.
UFO landed and left these words here

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


Я например, не один раз в работе получал в наследство такие вот "однострочники", в которых сам автор через полгода после написания разобраться не мог :(


В этом плане мне нравятся шаблонизаторы, вроде встроенного в ruby ERB, с помощью которого можно генерить вполне приятные вещи, и не только конфиги

Также не вижу в PHP образе перенаправление логов в потоки вывода. Вы как логи с контейнера считываете?
Это форк официального образа для PHP. Для моего проекта там немного по-другому настраивается PHP, в этом же случае, оставил все по дефолту, но показал людям настройки, чтобы было понятно. На счет логов, действительно их нет. Не учел, добавлю как буду у компьютера. Спасибо!
Как только, появился докер я помню задавался вопросом, по поводу, контейнерезации, в том числе и бд.и ячитал, что контейнеры, придуманны не для хранения бд, это так? сейчас ситуация изменилась
Эта статья послужит новичкам в этой сфере примером, как нужно упаковывать свое приложение в Docker контейнеры.
Я — новичёк в этой сфере и раздел DockerFile из этой статьи выглядит для меня также, как нарисовать_сову.jpg
В статье написано «Docker создает образы на основе DockerFile файлов, в котором описывается функционал. Мы создадим 3 образа для наших составляющих.».
Я это сказал к тому, что если Вы позиционируете подаваемый материал как информацию для новичков, то желательно всё-таки хотя-бы маленько разжёвывать содержимое примеров. А то смотришь в этот кусок кода и медленно офигеваешь от него.

PS: Как_нарисовать_сову.jpg
image
Я правильно понимаю, что после pull'a контейнеров и их запуска, нам еще нужно запустить миграции базы?
Запуск миграций можно написать в конце DockerFile'а в команде CMD.
CMD(«php bin/console doctrine:migrations run»);
При сборке контейнера контейнер базы данных не обязательно будет запущен. Я пока этот момент путём не решил. Ниже есть комментарий про использование /docker-entrypoint-initdb.d, но это не совсем миграции. Хотя дамп туда можно загрузить, но выполняться он будет только при первом запуске контейнера сразу после его создания.
При создании контейнера из образа, вы можете поместить любое количество файлов с расширением .sql в специальную папку (смотреть в документации к образу вашей БД), которые автоматически исполнятся
Я вам предложу вместо длинной портянки chain-вызовов — сделать несколько .sh-файлов.

И я думаю не стоит делать -p на posgresql/project порты, так как они не должны быть доступны снаружи (как минимум сделать ограничение на 127.0.0.1). У вас есть expose в project, всё, что осталось — использовать link при создании контейнера
В дальнейшем советую добавить к этим командам --no-cache, чтобы каждый раз не компилировать составляющие

Если меня не подводит память, то опция --no-cache как раз наоборот будет каждый раз пересобирать все слои.
Лично я только 2 способа знаю (если кто знает ещё, поделитесь):
1) Самый простой. Вы загружаете новый образ своего приложения в docker-репозиторий. Затем на сервере в папке вашего приложения выполняете «docker-compose up -d». После чего докер сперва скачает новый образ, грохнет старый контейнер и создаст новый. В этот момент я без остановки делаю рефреш страницы в браузере. При очередном рефреше страницы вижу уже новую версию в браузере, никаких ошибок или зависания не обнаружил.
2) Более сложный. Нужно использовать прокси с несколькими бэкендами. Поднимаете новый бэкенд с новой версией приложения, если всё ок, тушите бэкенд со старой версией приложения. В этом случае можно протестировать работу на небольшом количестве пользователей как ведёт себя новая версия прежде чем полностью переключаться.
В первом варианте сперва нужно сделать docker pull образа перед вызовом «docker-compose up -d»
А как вы статику обслуживаете? Через php? Я не вижу приложения в nginx контейнере.
Статика у меня лежит в volumes, который подключается к nginx контейнеру. Думаю, следующая статья затронет больше тонкостей.
Думаю, следующая статья затронет больше тонкостей.

Не пора ли? ;)
Only those users with full accounts are able to leave comments. Log in, please.