2015-04-30 6 views
14

Я пытаюсь определить хорошую практику для процесса сборки приложения nodejs, используя grunt/gulp для развертывания внутри контейнера докера.Запуск Grunt/Gulp внутри контейнера докеров или снаружи?

Я очень счастлив со следующей последовательностью:

  • сборка с помощью хрюканья (или глотки) снаружи контейнера
  • добавить ./dist папки в контейнер
  • запустить НПЕ установки (с --production флаг) внутри контейнера

Но в каждом примере я нахожу, я вижу другой подход:

  • добавить ./src папку в контейнер
  • запустить НПЕ установки (с зависимостями Дев) внутри контейнера
  • запустить становую установку (если требуется) внутри контейнера
  • запустить пехотинец (или глоток) внутри контейнера

IMO, первый подход создает более легкий и эффективный контейнер, но во всех примерах используется второй подход. Я что-то упускаю?

+0

Не могли бы вы указать на несколько примеров? –

+0

Что значит Адриан? Примеры файла Docker? – scarmuega

+0

Да. дополнительные символы, поэтому я могу сказать «да». –

ответ

2

Единственная разница, которую я вижу, заключается в том, что вы можете воспроизвести полную установку grunt во втором подходе.

С первым вы зависите от локального действия, которое может быть выполнено по-разному, в разных средах.

Контейнер должен быть основан на изображении, который может быть воспроизведен легко вместо зависимости от папки хоста, который содержит «то, что нужно» (не зная, как эта часть была сделана)


Если строить среды накладных расходов, которая поставляется с установкой слишком много для пехотинца изображения, вы можете:

  • создать образ «app.tar» предназначен для установки (I did that for Apache, that I had to recompile, создавая deb package in a shared volume).
    В вашем случае вы можете создать архив («tar») установленного приложения.
  • создания контейнера из базового изображения, используя объем из этого первого контейнера

    docker run --it --name=app.inst --volumes-from=app.tar ubuntu untar /shared/path/app.tar 
    docker commit app.inst app 
    

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

Это соединение между вашим подходом 1 и 2.

+0

Я вижу вашу точку зрения, но это означает, что вы должны превратить каждый контейнер в среду сборки, которая, наконец, будет развернута для производства. Это слишком тяжело, не так ли? Что вы думаете о добавлении какой-либо процедуры очистки после процесса сборки? Будет ли это эффективным докеров? – scarmuega

+0

@scarmuega Согласен. Я отредактировал свой ответ, чтобы решить вашу проблему. – VonC

+0

Почему вы создаете приложение.tar и сделать это требование вашего docker, а не создавать развернутое изображение докеров, которое вы можете поместить в репозиторий докеров? Создание разворачиваемого изображения докеров позволяет просто вытащить и запустить изображение из любого места, где оно вам нужно, и оно стабильно. Ваш контейнер также начнет в течение секунды или около того с помощью этого подхода. – Darryl

4

я хотел бы предложить третий подход, который я сделал для статического созданного сайта, отдельной сборка изображения.

В этом подходе ваш основной Dockerfile (тот, что в корне проекта) становится образцом построения и разработки, в основном делая все во втором подходе.Тем не менее, вы переопределяете CMD во время выполнения, которое должно деформировать встроенную папку dist в dist.tar или аналогично.

Затем у вас есть другая папка (что-то вроде image), которая имеет Dockerfile. Роль этого изображения заключается только в том, чтобы обслуживать содержимое dist.tar. Итак, мы делаем docker cp <container_id_from_tar_run> /dist. Затем Dockerfile просто устанавливает наш веб-сервер и имеет ADD dist.tar /var/www.

Абстрактный что-то вроде:

  • Построить builder Docker образ (который получает Вас рабочую среду без веб-сервера). В данный момент приложение построено. Мы могли бы запустить контейнер в разработке с помощью grunt serve или любой другой команды, чтобы запустить наш встроенный сервер разработки.
  • Вместо запуска сервера мы переопределяем команду по умолчанию, чтобы разгрузить нашу папку dist. Что-то вроде tar -cf /dist.tar /myapp/dist.
  • Теперь у нас есть временный контейнер с артефактом /dist.tar. Скопируйте его в папку фактического развертывания Docker, которую мы назвали image, используя docker cp <container_id_from_tar_run> /dist.tar ./image/.
  • Теперь мы можем создать небольшое изображение Docker без всех наших зависимостей разработки с docker build ./image.

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

Если вы хотите проверить изображение с помощью этого подхода в действии, ознакомьтесь с https://github.com/gliderlabs/docker-alpine, который использует изображение строителя (в папке-компоновщике) для создания файлов tar.gz, которые затем копируются в соответствующую папку Dockerfile.

+0

Этот пример gliderlabs настолько продвинут, я не могу выбрать соответствующие части, связанные с вышеуказанным вопросом. Мне нравится концепция, но пример настолько усложнен. – Scotty

1

Вариант решения 1 состоит в том, чтобы иметь «родительский -> ребенок», который делает сборку проекта очень быстрым. я бы dockerfile как:

FROM node 
RUN mkdir app 
COPY dist/package.json app/package.json 
WORKDIR app 
RUN npm install 

Это будет обрабатывать установку зависимостей узлов, и есть еще один dockerfile, который будет обрабатывать приложения «установки», как:

FROM image-with-dependencies:v1 
ENV NODE_ENV=prod 
EXPOSE 9001 
COPY dist . 
ENTRYPOINT ["npm", "start"] 

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

Надеюсь, это поможет кому-то.

С уважением

Смежные вопросы