Страницы

Поиск по вопросам

Показаны сообщения с ярлыком docker. Показать все сообщения
Показаны сообщения с ярлыком docker. Показать все сообщения

четверг, 9 апреля 2020 г.

Docker ENOTFOUND при npm install?

#nodejs #npm #docker

                    
Почему при выполнении npm i я начинаю получать сообщения вида:

npm info attempt registry request try #2 at 11:45:00 PM
npm http request GET https://registry.npmjs.org/redis
npm info attempt registry request try #2 at 11:45:00 PM
npm http request GET https://registry.npmjs.org/hiredis
npm info attempt registry request try #2 at 11:45:00 PM
npm http request GET https://registry.npmjs.org/express
npm info retry will retry, error on last attempt: Error: getaddrinfo ENOTFOUND registry.npmjs.org
registry.npmjs.org:443
npm info retry will retry, error on last attempt: Error: getaddrinfo ENOTFOUND registry.npmjs.org
registry.npmjs.org:443
npm info retry will retry, error on last attempt: Error: getaddrinfo ENOTFOUND registry.npmjs.org
registry.npmjs.org:443

    


Ответы

Ответ 1



Помог перезапуск службы docker sudo service docker restart Видимо DNS нужно было обновить

суббота, 4 апреля 2020 г.

Вопросы по docker'у

#linux #docker

                    
Зашел сегодня на vps и увидел загрузку cpu под 100%, потом посмотрел статистику по
контейнерам и заметил такую занимательную вещь:

CONTAINER           CPU %               MEM USAGE / LIMIT     MEM %             
 NET I/O               BLOCK I/O
kibana              96.45%              536.8 MB / 536.9 MB   99.99%            
 884.5 MB / 306.2 MB   2.682 TB / 5.369 GB


Отсюда несколько вопросов:


Как ограничить использование cpu докером или может есть софт, который сам прибивает
процессы, если они выходят за определенные рамки?
Что значат 2 последних столбца и откуда терабайты в последнем?

    


Ответы

Ответ 1



Документация, сэр. Можно настроить пропорцию выделяемого контейнеру (конкретному!) процессорного времени с помощью параметра cpu-shares (по умолчанию "всем поровну", по 1024); а можно задать параметры для CFS: cpu-quota процессорного времени за cpu-period реального: настраиваются оба, целыми числами в микросекундах (1000..1 000 000). Все параметры задаются при docker run. Shares мягче, с ними контейнеру позволяется забирать почти весь процессор, если больше им никто особо не пользуется; когда CFS ставит "жёсткий потолок на все времена". Общий объём операций ввода/вывода над "блочными устройствами", например дисками. Чтение одних и тех же данных, при условии отсутствия кэширования, будет каждый раз увеличивать этот счётчик, поэтому это число вполне себе может превышать общий объём всех подключенных устройств. То же самое с записью: перезапись данных счётчиком учитывается, как обычная запись.

понедельник, 30 марта 2020 г.

Неявное поведение spring при работе с дженериками

#java #spring #docker #spring_boot


Есть некая сущность Report и одна из ее реализаций:

public class CCReport extends AbstractReport {

    public CCReport(List rows, LocalDate from, LocalDate to) {
        super(rows, from, to);
    }

    @Override
    public Class getRowClass() {
        return CCReportRow.class;
    }
}


Есть некий интерфейс сервиса: 

public interface ReportService {
    T createReport(LocalDate from, LocalDate to);
}


У него есть несколько реализаций в зависимости от типа Report:

@Service
@RequiredArgsConstructor
public class CCReportService implements ReportService {

    private final CCReportsExportRepository repository;

    @Override
    public CCReport createReport(LocalDate from, LocalDate to) {
        return repository.generateReport(from, to);
    }
}


Далее есть абстрактная реализация слушателя RabbitMq:

@Slf4j
@RequiredArgsConstructor
public abstract class AbstractReportTaskListener implements ReportTaskListener {

    protected final ReportService reportService;
    //-------------------//    

    @Override
    public void processReportTask(SingleReportRequest reportRequest) {
        Report report = reportService.createReport(reportRequest.getFrom(), reportRequest.getTo());
        //-------------------//
    }
}


И непосредственно сама реализация этого слушателя:

@Component
public class RabbitCCReportTaskListener extends AbstractReportTaskListener {

    public RabbitCCReportTaskListener(
            ReportService reportService,
            ReportMailService mailService,
            ReportToExcelService excelService,
            ReportsNameGenerator nameGenerator,
            WebDavStorageService webDavStorageService) {
        super(reportService, mailService, excelService, nameGenerator, webDavStorageService);
    }

    @RabbitListener(queues = RabbitConfig.CC_QUEUE, concurrency = "2-2", autoStartup
= "true")
    @Override
    public void processReportTask(SingleReportRequest reportRequest) {
        super.processReportTask(reportRequest);
    }
}


При запуске всего этого добра через gradle bootRun все запускается без проблем, однако,
если создаю docker-образ вылетает ошибка:


  *********************** APPLICATION FAILED TO START
  
  
  
  Description:
  
  Parameter 0 of constructor in
  com.reports.service.RabbitCCReportTaskListener required a single bean,
  but 2 were found:
   - CCReportService: defined in URL [jar:file:/app/reports.jar!/BOOT-INF/classes!/reports/service/CCReportService.class]
   - SRReportService: defined in URL [jar:file:/app/reports.jar!/BOOT-INF/classes!/reports/service/SRReportService.class]
  
  Action:
  
  Consider marking one of the beans as @Primary, updating the consumer
  to accept multiple beans, or using @Qualifier to identify the bean
  that should be consumed


В конце концов приходится явно описывать бины через @Qualifier и тогда начинает работать.
Подскажите, с чем может быть связано такое поведение?

UPD:
Вот ссылка на SO, где уже описывали подобный вопрос. Плюс есть несколько статей по
запросу "spring generic bean autowire"
    


Ответы

Ответ 1



Это случается из-за Type Erasure: при компиляции ReportService вырождается в ReportService, и здесь возникает неоднозначность в рантайме, т.к. таких бинов уже 2. Чтобы избежать ситуации используйте либо конкретный наследник ReportService либо @Qualifier в конструкторе конкретного наследника AbstractReportTaskListener. В докер упакованы все jar-файлы проекта и все зависимости. Локально, вероятно, не все скомпилировано, попробуйте пересобрать проект начисто.

воскресенье, 8 марта 2020 г.

большой образ Docker

#docker


При создании Docker образа приходится тянуть 8GB пакетов с хост системы.

Методом COPY, потом удалять. Но вывод docker images показывает размер контейнера
с учетом скопированных в слое ранее пакетов. И при каждом следующем релизе образ растет
все больше.

Какой механизм можно использовать для доставки пакетов на время генерации образа?
    


Ответы

Ответ 1



После создания окончательного образа вы можете сжать все слои в один. Это позволит сократить образ, так как из него будут удалены удаленные файлы. Сейчас эти файлы по прежнему хранятся в образе в других слоях. Самый простой способ. Запустить ваш образ, что бы получить контейнер и потом выполнить вот такую команду docker export | docker import - <новое имя образа>:<новая метка образа> Это приведет к потере всей истории образа Второй способ это использовать утилиту docker-squash docker save > image.tar sudo docker-squash -i image.tar -o squashed.tar cat squashed.tar | docker load

Ответ 2



Самый оптимальный вариант, использовать статик сервер. И Wgetom тянуть установочные пакеты.

Ответ 3



Что бы уменьшить конечный размер имижда в конце каждой команде добавь "&& yum clean all" вот так: yun install httpd && yum clean all это очистит загруженные файлы и уменьшит размер слоя в файловой системе и тем самым уменьшит размер итогового имиджа. Для Ubuntu можно стирать /var/cache/apt/*

Ответ 4



Тут был кейс, что я юзал CentOS docker в CentOS по умолчанию поставлялся с aufs, с которым он некорректно работает. Требуется сменить на devicemapper и все будет ок.

Что включать в Docker-образ

#администрирование #веб_сервер #docker #сборка


Имеется веб-сайт на Django, на боевом сервере для запуска использую связку uWSGI/Nginx,
локальная разработка - virtualenv/dev-сервер Django

Из некоторых вопросов, которые задал на SO:


Распространение Docker-образов 
Запуск Docker-образов на боевом сервере
Запуск сайта из Docker-образа VS запуск c традиционными средствами (uWSGI, Nginx, Apache)


появилось еще пара.

Что включать в образ Docker?

Мы имеем production-версию и developer-версию. Как понимаю, в репозиториях распространяют
production. 

Имеет ли смысл создавать docker-образ для developer-версии (применительно ко мне,
код проекта и виртуальное окружение virtualenv)? Или разработчику достаточно только
кода из репозитория, чтобы начать разработку?

Где создают docker-образ production-версии?

На боевом сервере имеется проект, который работает на указанной связке - uwsgi/nginx/упаковщик
с production-настройками. Собирать образ я должен на боевом сервере?
    


Ответы

Ответ 1



Не должно быть понятия production и non-production версия образа. Разработчики, тестировщики, эксплуатационники и все остальные должны использовать одну и туже версию образа. Процесс разработки может быть устроен совершенно по разному, но если используется docker-образ (например, сервер разрабатываемый другой группой) в качестве внешней зависимости, то он должен браться из того же источника, что и для других нужд - тестирование, эксплуатация и т.п. Как, где и чем создают docker-образы? Процесс изготовления образа должен быть полностью автоматизирован, что бы избежать ошибок и сделать процесс повторяемым. Приблизительно процесс изготовления образа выглядит так (я опускаю некоторые шаги): Разработчик дописал код и протестировал его локально, в том числе и сборку образа. Разработчик заливает код в систему контроля версий. Робот собирает проект и создает артефакты для развертывания (мнифицирует все, объединяет в общий пакет и т.п.). Необязательный шаг - артефакты помещаются в хранилище. Робот собирает docker-образ. Необязательный шаг - робот подписывает образ. Робот заливает образ в реестр. Если нет специфических требовани, то для управления процессом создания можно использовать любой Continuous Integration сервер - Jenkins, TeamCity, Bamboo и т.д. У них у всех есть соответсвующие плагины или можно написать простые шел-скрипты и создавать образы стандартной командой docker build. Что включать в docker-образ? Сложно дать однозначный ответ на этот вопрос, так как многое зависит от типа образа и личных предпочтений. Я напишу как бы я поступил с сервером на Django. Я мало работал с Django, так что поправьте меня, если я говорю что-то несоответствующее действительности. Если проект только начинается и нагрузка на сервис будет маленькая, то я бы поместил все (кроме БД) в один образ. Т.е. образ будет содержать: Python фиксированной версии установленный как системный (без virtualenv и пр) nginx/Apache фиксированных версий с нужными настройками собственно ваше приложение, взятое как артефакт для развертывания и развернутое внутри образа БД либо в отдельный образ, либо на отдельный сервер без использования контейнерезации. Если БД идёт отдельным образом, то важно позаботится о сохранении данных на внешний (по отношению к контейнеру) раздел диска. В противном случае данные будут утеряны при перезапуске контейнера. Если нагрузка будет значительная и есть много статических страниц, то я бы сделал несколько образов: Образ со статическими страницами nginx/Apache статическая часть вашего приложения Образ с динамической частью Python часть вашего приложения (Django) Образ балансировщиком (необязательный) nginx/HAProxy/Varnish/etc Если проект очень большой, то возможно статическую и динамическую часть делают разные команды и в этом случае они и буду отвечать за подготовку Dockerfile к своей части проекта.

четверг, 5 марта 2020 г.

Как правильно деплоить проект?

#golang #docker #развертывание #bitbucket


Здравствуйте, есть restful сервис написанный на golang.
Раньше работал на локальном хосте, сейчас же появилась потребность деплоить все на
сервер.
Не могу понять как лучше осуществить деплой.
Создал репозиторий на бакете, а от дальше туплю.
Каждое изменение(А их будет много) копировать, билдить, потом закрывать процесс с
активным приложением go и запускать новый. Так как изменения будут очень частые и очень
интересует как можно автоматизировать этот процесс.
    


Ответы

Ответ 1



Есть такой подход, под названием Continuous Delivery (Непрерывное развертывание), который предлагает решение описанной вами проблемы. Что это за зверь и с чем его едят, описано в книге Continuous Delivery: Reliable Software Releases through Build, Test, and Deployment Automation / Непрерывное развертывание ПО. Автоматизация процессов сборки, тестирования и внедрения новых версий программ Небольшая выжимка о CD (цитата отсюда): Основная идея CD в том, чтобы построить конвейер (Deployment Pipeline), позволяющий каждому изменению в системе контроля версий попасть в боевое окружения стандартным и полностью автоматизированным способом. Приблизительно это может выглядеть следующим образом: Изменения вносятся в систему контроля версий (СКВ). Запускается система непрерывной интеграции (Continuous Integration, CI), собирается билд (если это компилируемый язык), прогоняются все необходимые тесты. В случае успешности предыдущего шага, билд выкатывается на окружение тестирования (QA). После успешного тестирования билд выкатывается на stage окружение (pre-production), которое максимально приближено к боевому окружению. Если все прошло хорошо, то билд попадает в боевое окружение. Тут встает в полный рост вопрос, как сделать так, чтобы все окружения, начиная с окружения разработчиков, максимально соответствовали друг другу. Для этого существуют инструменты управления конфигурацией (Configuration management system). Самое главное, что конфигурация окружений — это такой же код, и к нему точно также применимы все вышеперечисленные подходы: хранение в СКВ, CI, тестирование. Так вот, если этот процесс отлажен, все изменения проходят по нему, и, потенциально, каждое изменение может быть выкачено в продакшен, то это и называется процессом непрерывной поставки ПО.

Ответ 2



Вам в любом случае нужны решения для CI (Continuous Integration) и CD (Continuous Deployment). Вот список, из которого вы можете выбрать(ссылка). Например, как это работает с Drone: Через веб морду Drone, вы настраиваете Drone для получения проекта с репозитория Git и выполнение "запуска". Что конкретно происходит при запуске описано в следующем шаге. Вместе с кодом приложения в репозитории должен лежать .drone.yml файл, который говорит Drone как устанавливать и запускать ваше приложение. Далее вы делаете git push в ваш репозиторий, Drone проверяет репозиторий на недавно залитый Docker образ (по вашему выбору), а затем стартует его. На основе вашей конфигурации результатом успешного запуска может быть уведомление («Сборка выполнена успешно!»), создание бинарной версии или даже развертывание. Наконец, Drone удаляет Docker контейнер и переустанавливает его так, чтобы он был в исходном и известном состоянии для следующей сборки. P.S. по связке Drone + Docker есть неплохая статья на Хабре.

среда, 26 февраля 2020 г.

Для чего нужна “@” в location'е (NGINX)?

#nginx #docker #microservices


Объясните пожалуйста, для чего применяется символ @ внутри конфигурационного файла
nginx при указании пути и о чем говорит данный кусок кода:

location @web {
  proxy_pass http://web:3000;
}

    


Ответы

Ответ 1



Префикс “@” задаёт именованный location. Такой location не используется при обычной обработке запросов, а предназначен только для перенаправления в него запросов. Такие location’ы не могут быть вложенными и не могут содержать вложенные location’ы. Документация

Как победить искажение текста кирилицы в bash, запущенном в Docker-контейнере?

#docker #кириллица #locale


Настроил локаль для контейнера:

# Set the russian locale
RUN apt-get clean && apt-get update && apt-get install -y locales
RUN locale-gen ru_RU.UTF-8
ENV LANG ru_RU.UTF-8
ENV LANGUAGE ru_RU.UTF-8
ENV LC_ALL ru_RU.UTF-8


При этом русский текст в bash терминале все-равно работает неправильно: ввод начинается
с символа ":�", вставка текста на русском выгляди точно также (начало строки искажается
при вставке). Как бы справиться с этой проблемой?
    


Ответы

Ответ 1



Пример из рабочего Dockerfile, проверено и работает. FROM php:7.2-apache RUN apt-get update && apt-get install -y locales # Locale RUN sed -i -e \ 's/# ru_RU.UTF-8 UTF-8/ru_RU.UTF-8 UTF-8/' /etc/locale.gen \ && locale-gen ENV LANG ru_RU.UTF-8 ENV LANGUAGE ru_RU:ru ENV LC_LANG ru_RU.UTF-8 ENV LC_ALL ru_RU.UTF-8 # +Timezone (если надо на этапе сборки) ENV TZ Europe/Moscow RUN ln -snf /usr/share/zoneinfo/$TZ /etc/localtime && echo $TZ > /etc/timezone

Ответ 2



вероятно, в образе, используемом вами, не сгенерирована такая локаль (ru_RU.UTF-8). посмотрите список командой locale -a (приведён пример вывода): $ docker run --rm -ti имя-образа locale -a C C.UTF-8 POSIX для нормальной работы с кириллицей вполне подойдёт имеющаяся локаль C.UTF-8: $ docker run --rm -ti -e LC_ALL=C.UTF-8 ubuntu:16.04 bash если же необходима именно русскоязычная локаль, то её надо сгенерировать. наиболее, пожалуй, универсальный способ — использовать скрипт locale-gen: $ locale-gen ru_RU.UTF-8 Generating locales (this might take a while)... ru_RU.UTF-8... done Generation complete. скрипт этот присутствует (в debian-основных дистрибутивах) в пакет locales, который в вашем образе, скорее всего, тоже отсутствует, и его надо установить. демо-пример для проверки: $ docker run --rm -ti -e LC_ALL=ru_RU.UTF-8 ubuntu:16.04 bash -c 'apt update && apt install -y locales && locale-gen ru_RU.UTF-8; bash'

понедельник, 24 февраля 2020 г.

Как исполнить скрипт при запуске docker-контейнера?

#bash #docker


Здравствуйте!

Вопрос, возможно, несколько избит, но ответа на него я не нашел. А похожие вопросы
на тостере, как в и гугле не помогли. 
Я буду премного благодарен тем людям, что уделят немного своего времени и дадут развернутый
ответ!

И так, задача минимум - запустить apache при старте контейнера

Задача максимум - выполнить bash скрипт при старте контейнера

Я опишу варианты которые я пробовал.

1. Сборка простейшего образа и запуск контейнера из консоли

Dockerfile
    FROM ubuntu:14.04

RUN apt-get update && \
    apt-get install -y apache2


В консоли:
    sudo docker build -t apache .
    sudo docker run -dit --name cont_apache apache /bin/bash service   apache2 start

В ответ код контейнера, docker ps чист. docker logs cont_apache сообщает о запуске
апача - Starting web server apache2 ...
Но сам контейнер почему-то умирает. хотя флаг -d установлен. 

Попытался:
    sudo docker run -dit --name cont_apache apache service apache2 start

Результат точно такой же.

2. Сборка образа и запуск апача при помощи CMD

Dockerfile:
    FROM ubuntu:14.04

RUN apt-get update && \
    apt-get install -y apache2

CMD ["service" "apache2", "start"]


В консоли:
    sudo docker build -t apache .
    sudo docker run -dit --name cont_apache apache /bin/bash service apache2 start 

Контейнер запущем, висит как демон, перехожу в контейнер:
root@2a97628fd78b:/# service apache2 status
* apache2 is not running
Апач не запустился.
Почему?

3. Сборка образа с проброской bash скрипта и его выполнение

Dockerfile:
    FROM ubuntu:14.04

RUN apt-get update && \
    apt-get install -y apache2 

COPY ./apache2_start.sh /root/apache2_start.sh

CMD ["chmod", "777", "/root/apache2_start.sh"]

CMD ["/root/apache2_start.sh"]


Script apache2_start.sh:
    #!/bin/bash

service apache2 start
echo "127.0.0.1"


В консоли:
    sudo docker build -t apache .
    sudo docker run -dit --name cont_apache apache 

В docker ps контейнера нет. В логах docker logs cont_apache:
     * Starting web server apache2                                              
   AH00558: apache2: Could not reliably determine the server's fully qualified domain
name, using 172.17.0.3. Set the 'ServerName' directive globally to suppress this message
     * 
    127.0.0.1

Пробовал также с запуском bash из консоли:
    sudo docker run -dit --name cont_apache apache /bin/bash

В результате контейнер висит в docker ps. Docker logs conf_apache чист.

А в самом контейнере:
    root@d2c9831773a9:/# service apache2 status
    * apache2 is not running

Итог.

Я попытался добиться нужного результата разными способами, но ни одним у меня не вышло. 

Очевидно, что я допускаю ошибки в работе с докером.

Я буду очень! благодарен за конструктивную помощь в данном вопросе как в целом, так
и что в каком конкретном случае я делал не так.

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


Ответы

Ответ 1



Докер-контейнер - это один процесс, обернутый в изолированную среду. Этот процесс может порождать дочерние процессы, но основной постулат остается одинаковым: время жизни контейнера - это время жизни процесса, указанного в ENTRYPOINT/CMD. Насколько понимаю, команда apache2 service start попытается запустить апач в фоновом режиме и тут же закончит свое выполнение; как только докер увидит, что процесс закончился, он прибьет контейнер. Таким образом, ваша конечная цель - выполнить в начале скрипта требуемые действия, а потом сделать так, чтобы он выполнялся все время жизни приложения (в случае с апачем - условно бесконечно). Проще всего это сделать следующим образом: выполнить требуемые действия последней командой в шелл-скрипте запустить апач с отключенным фоновым режимом (-DFOREGROUND), предварив команду инструкцией exec. Эта инструкция позволит текущему процессу (выполняющемуся шелл-скрипту) стать процессом, вызванным exec. После этого ctrl-c и прочие плюшки будут отправляться на обработку напрямую апачу. пример такой работы можно увидеть прямо в официальном изображении library

Ответ 2



Если уже есть подходящий официальный image, то лучше использовать его, а не брать ubuntu и туда делать apt-get install. Для Apache: https://hub.docker.com/_/httpd/ Можно сделать свой image, который наследуется от него, а можно запускать его напрямую. Вероятно, нужен ещё php. Для этого можно взять image php:apache https://hub.docker.com/_/php/ Если нужны ещё другие приложения, например, MySQL, то по идеологии Docker надо запускать их в отдельном контейнере.

Ответ 3



По идеологии docker запустить bash скрипт при старте контейнера не получится, т.к. в нем не обрабатывается init как в хостовой машине. Для автозапуска процессов нужно использовать DockerFile с указанными в директиве CMD процессами. Или можно сделать следующим образом: run контейнера делать с ключом --restart unless-stopped, тогда контейнер будет стартовать при запуске системы. А для запуска процессов в контейнере написать простой баш скрипт на хостовой машине вроде этого: #!/bin/bash sudo docker exec service nginx start sudo docker exec service php7.2-fpm start sudo docker exec service mysql start Стартует nginx, php-fpm и mysql в указанном контейнере. Можно добавить своего пользователя в группу docker для исключения "sudo" и поставить скрипт в автозапуск init хостовой машины

Как правильно устанавливать Docker?

#docker


На оф сайте не нашёл нормального вменяемого объяснения , не ужели он устанавливается
через Командную строку ?
    


Ответы

Ответ 1



Цитирую документацию Docker: Installation If you have VirtualBox running, you must shut it down before running the installer. Go to the Docker Toolbox page. Click the installer link to download. Install Docker Toolbox by double-clicking the installer. Перед этим вам необходимо убедиться, что виртуализация поддерживается вашим CPU и разрешена в настройках BIOS и вашей ОС.

Ответ 2



Сейчас в публичную бету вышел Docker for Windows, он поднимает виртуалку в Hyper-V. Правда он ограничен версией винды, только Windows 10 начиная с определенного билда

пятница, 14 февраля 2020 г.

В чем разница между версиями Docker, и какую мне ставить?

#docker


Начал изучать docker и уже не могу понять, почему есть три разные версии:


docker-ce 
docker-engine
docker.io


В чём между ними разница? Какую мне лучше установить?
    


Ответы

Ответ 1



docker-engine и docker.io это устаревшие версии. На данный момент актуальные версии это платная корпоративная версия (EE - Enterprise Edition) и бесплатная комьюнити-версия (CE - Сommunity Edition). Собственно docker-ce это бесплатная актуальная версия и устанавливать следует ее. Если уже были установлены старые пакеты, то желательно удалить их перед установкой. Удаление старых версий и установка новой: Ubuntu/Debian Centos/RHL

grep в конструкции if

#linux #bash #docker #grep


Разбираюсь с bash'ем
Хочу написать скрипт для работы с докером, столкнулся с непониманием работы синтаксиса
bash.
Пример скрипта такой:

#!/bin/bash
result=$(docker ps)
container=container_name
if $result | grep $container
then
echo "$container is work"
fi


Если контейнер с именем container_name запущен то по идее мы должны пройти условие,
но получается такая ошибка:

./mscript.sh: line 4: CONTAINER: command not found

    


Ответы

Ответ 1



Все штатно. просто сделайте подстановку всех переменных и посмотрите что получается. bash пытается выполнить $result как команду. Скорее всего Вы имели ввиду такое echo $result | grep $container

Ответ 2



Дружище, изучите docker, то что вы делаете через if, grep и т.д. делается внутри команды docker ps: $ docker ps --no-trunc -af name="^*$" -f status="running" --format "{{.ID}}: {{.Status}}" 0c9b82211c4da46d2af47f30fd1f90150173b70d29574030e6eadc399c9f58a8: Up 3 days 32b8a98772a4b0520252aba1eee944251c72c404d5ddef0a71f59f82d385926f: Up 2 weeks f394c4b1dbec886c75880ae217a6243dde44ed4dc81d7c0cea533339140c5d01: Up 3 days 2e02efb775c34b945e97dbdea41da9776aa05c83789520eaf32544dad8980db1: Up 2 weeks 451524ce8dc85a63d60f561b436c646ba8f2141346a14a21d1c16709cbed6441: Up 2 weeks e0aa486fa921109c512640a49d07aa1b33a72ab9d64446614cbc44e475f26848: Up 2 weeks

среда, 5 февраля 2020 г.

Зависимости в docker и место на диске

#docker


Правильно ли я понимаю, что каждый образ тащит в зависимостях свою собственную ОС
(дебианы всех версий, убунты всех версий, alpin'ы всех версий, что там ещё есть), из-за
чего куча разных образов очень быстро сожрут свободное место на диске? 
    


Ответы

Ответ 1



Да, вы получите образы всех (почти-)ОС Из зависимостей всех ваших образов. Нет, это не съест весь ваш диск в один момент. Во-первых, Docker старается избегать дублирования данных с помощью драйверов хранения (storage drivers). Большинство образов Docker основано на каких-то других образах (директива FROM в Dockerfile). И как правило, файлы, которые из одного образа унаследовались другими без изменений, будут размещены на диске всего раз. Как именно и как будет организована работа с такими файлами — зависит от драйвера. На странице о драйверах можно почитать о технических подробностях каждого из них, для примера: Aufs представляет файловую систему контейнера в виде объединения слоёв, начиная с базового (только для чтения), через промежуточные (только для чтения) и заканчивая собственным слоем контейнера (доступным для записи). ZFS размещает базовую файловую систему прямо на устройстве хранения, а каждый очередной слой (включая собственный слой контейнера) накладывается в виде клона (clone) из снимка (snapshot) предыдущего слоя. История файлов хранится лишь по одной версии для слоя. То есть, если при сборке слоя файл был изменён дважды, сохранится лишь последняя версия. Если был создан и удалён, то в слое не будет упоминаний о нём вовсе. Удаление файлов из исходного образа реализуется путём "замазывания" (whiteout) файлов специальными записями. Во-вторых, в образах ОС для Docker, по сравнению с серверными ОС (чтобы сразу исключить из рассмотрения GUI и связанные вещи), многих вещей нет за ненадобностью: Инит-процесса и его аксессуаров. Docker стартует сразу процесс с "полезной нагрузкой", бывает что через оболочку, занимающую PID 1. Собственное ядро и утилиты для его обслуживания. Всё равно используется ядро хост-машины. Поэтому контейнеры так привязаны к ОС, на которой построены. Демонов. Хорошей практикой считается держать в каждом контейнере ровно один процесс, поэтому файлы, связанные с демонами (почтовый агент, базы данных, системы автоообновления, и т. п.), можно выбросить. Кому надо будет — поставит самостоятельно, но это редко нужно. Устаревающих файлов, вроде списков пакетов из репозиториев. Их всё равно надо будет заменить свежими версиями при наследовании образа, поэтому включать их в образ бесполезно. Популярная проблема при формировании контейнеров: пакеты не устанавливаются, если в докерфайле явно не потребовать обновить списки пакетов из репозиториев. Достаточно часто в контейнерах используется Alpine Linux, контейнерная версия которого занимает чуть больше 4 мегабайт (но при наследовании она чуть прибавляет в весе за счёт временных файлов). Для сравнения, его же самостоятельный установочный образ для полноценных систем занимает чуть больше 100 мегабайт. Другие контейнерные дистрибутивы потолще будут, но и они по сравнению со своими полновесными собратьями гораздо компактнее.

Ответ 2



Да, верно. Против этого работает дедупликация образов и использование более компактных базовых образов вроде alpine. Плюс из образов стараются выкидывать всё лишнее: к примеру, ядро и связанные с его обслуживанием утилиты, т. к. используется в итоге ядро хоста. Так что место на диске сжирается не шибко быстро, но безусловно быстрее, чем при ручной настройке продуктов из образов без докера на одной системе. Дополнительно об освобождении места можно прочитать здесь.

пятница, 24 января 2020 г.

Docker: сеть, интерфейсы и контейнеры

#linux #сеть #docker


У меня есть два сетевых интерфейса: eth0 - локальная сеть, tun0 - через него я хожу
в интернет(поднимается и тушится с помощью самописного скрипта). На этой же машине
стоит docker, у него есть свое собственное окружение для контейнеров. Из этого окружения
наружу торчит интерфейс docker0, все контейнеры связываются с внешним миром через него. 
Тут возникает проблема: при поднятом tun0(при этом он становится дефолтным) контейнеры
не хотят через него связываться. Как я понял надо как то перенаправить docker0 на tun0?
Как это сделать? 
    


Ответы

Ответ 1



Отвечаю на собственный вопрос: Проблема заключалась в том, что у меня не был указан dns сервер моей сети и по умолчанию был отключен ip_forwarding. Для начала его нужно включить, раскомметнировав строчку: net.ipv4.ip_forward=1 в файле /etc/sysctl.conf и перезагрузив машину. Далее в файле /etc/defaut/docker редактируем строку: DOCKER_OPTS="-dns <ваш_адрес_dns>" После редактирования перезапустите докер.

Выполнение задач в Docker-контейнере в Jenkins

#docker #jenkins #непрерывная_интеграция


Может ли Jenkins работать так же, как GitLab Runner + Docker executor:


Из образа развернуть контейнер.
Внутрь контейнера клонировать репозиторий git, выполнить произвольные команды.
Выделить артефакты и сохранить их вне контейнера, свернуть контейнер (завершить его
работу).



  Вопрос: нужна пошаговая инструкция по настройке Jenkins для выполнения трех вышеуказанных
шагов.


Нашел Docker Plugin. Вроде бы он умеет разворачивать Jenkins slave в докере, подключать
его к мастеру и утилизировать после использования. Этот вариант мне точно не подходит,
потому что нужно тащить в сборочное окружение Java и прочие не нужные там вещи. Базовый
образ jenkins-slave весит в 100 раз больше alpine, это вообще за гранью разумного.

docker images                                                                   
                                          
REPOSITORY              ...     SIZE
alpine                  ...     3.97 MB
evarga/jenkins-slave    ...     368 MB


Еще нашел плагин Docker build step. Одна из фич — "create new container from image".
Возможно, мне нужно именно это, но я не понимаю, как выполнить пункты 2 и 3.
    


Ответы

Ответ 1



В Jenkins можно выполнить bash/batch команду, для bash это будет примерно так: docker run -it -d my_image # запускам image в detached моде docker exec $(docker ps -a -q --filter ancestor=my_image) bash -c "cd your_path; your_command" # запускаем Вашу команду в контейнере. list=$(docker exec $(docker ps -a -q --filter ancestor=my_image) bash -c 'ls /path/to/artifacts/inside/container') # создаем список артефактов, которые мы будем вытаскивать из контенера for i in $list; do docker cp $(docker ps -a -q --filter ancestor=my_image):$i ./path/to/outside container ; done # вытаскиваем артефакты согласно списку for i in $(docker ps -a -q --filter ancestor=my_image); do docker rm $(docker stop $i); done # удалям контейнеры, если они работают

Как разрабатывать через связку PhpStorm + Docker?

#php #windows #phpstorm #docker


В интернете куча информации о докере по базовым вещам, таких как "как скачать образ",
"как запустить контейнер", но почти ничего нет о том, что дальше с этим делать. Как,
собственно, разрабатывать-то?

К примеру, сделал я pull дистрибутива  linode/lamp, у него в папке /var/www/example.com/public_html/
лежит проект. 
Запускаю: docker run -p 80:80 -t -i linode/lamp /bin/bash, service apache2 start.
Теперь в браузере по адресу http://localhost вижу индексную страницу того проекта. 

Окей. Теперь я хочу редактировать/добавлять/удалять файлы в этом проекте. Делать
это через bash и редактор nano - не совсем здравая идея, очевидно. Поэтому я хочу это
делать в PhpStorm. И тут я уже не понимаю, что делать.
Какой пункт выбирать при создании проекта?


Web server is installed locally, source files are located under its document root.
Web server is installed locally, source files are located elsewhere locally.
Web server is on a remote host, files are accessible via network share or mounted drive.
Web server is on a remote host, files are accessible via FTP/SFTP/FTPS.
Source files are in a local directory, no Web server is yet configured.


Если первый, то где брать файлы, если через FTP/SFTP/FTPS, то как настраивать? Я
не понимаю.

Я знаю, что в PhpStorm можно настроить Deployment - Docker и его конфигурацию. Вот
как у меня выглядит:





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



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

P.S. Я использую Docker на Windows - в настройках переключенный на Linux (Switched
to linux)
    


Ответы

Ответ 1



Все манипуляции надо производить через сам docker. 1 Найдите подходящий вам образ для работы с PHP 2 При запуске контейнера примонтируйте папку с вашим проектом в /var/www/ docker run -v /path/to/project/:/var/www -td IMAGE_NAME (Все параметры на ваше усмотрение, можете запускать -it если нужно работать в контейнере) -v: Монтирование volume с хоста в контейнер. -d: Запуск в бэкграду -t: Что бы при запуске он не выключался. IMAGE_NAME: Имя образа Открываете ваш проект который находиться в /path/to/project/ через PhpStorm и можете свободно работать.

суббота, 11 января 2020 г.

Docker: можно ли контейнер, созданный из Windows разместить на Linux?

#c_sharp #администрирование #docker #aspnet_core #docker_compose


У нас стартап и мы все еще активно пополняемся единомышленниками, но наш продукт
уже в скором времени близится к пилотному запуску. ПО наше состоит из следующих модулей:


API — проект ASP.NET Core Web API 2 
MySQL
Web-клиент — приложение на Angular 5. Мы не скрестили ASP.NET Core и
Angular, а разрабатываем веб-клиент Angular отдельно с Node.js на борту.


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

Операционная система, которая будет крутиться на сервере клиента неизвестна и хотелось
сделать некий универсальный процесс инсталяции который подходил бы как на Windows так
и для Linux. Понятное дело, что за универсальность надо платить.

Как писал выше, мы только развивающийся отряд, и мы не имеем пока еще в арсенале
хорошего специалиста-администратора с большим опытом решения подобных задач по развертыванию.

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

Прокси-сервер. И как не крути, но плюс к Kestrel/HTTP.sys какой-то из серверов Apache,
IIS, nginx и т.д. все же нужен на сколько понял я. Даже если клиент планирует работать
с нашим продуктом только внутри корпоративной сети. 
Дела с HTTP.sys конечно лучше: он не такой голый как Kestrel, но у нас то речь об
универсальности, а HTTP.sys только для Windows.
Пытался к примеру установить nginx на Windows Server в качестве эксперимента: мама
родная, со стороны казалось, что я в первый раз вижу компьютер).



И если можно я задал бы два вопроса:

1) Первый вопрос он более общий, вы наверное догадались: что посоветуете?

2) А теперь, чтобы конкретизироваться: я сейчас работаю на Windows 10 и если я задумал
использовать Docker, то я ведь правильно понимаю, что мне надо создать четыре контейнера


Контейнер с прокси-сервером (Apache, nginx или IIS)
Контейнер с СУБД MySQL
Контейнер с Angular-приложением
Контейнер с проектом ASP.NET Core 2 Web API


Можно ли это сделать прямо из Windows? То есть будет ли работать контейнер созданный
на Windows-машине на Linux?
    


Ответы

Ответ 1



Docker под Windows может работать в двух режимах - Windows Containers и Linux Containers. Режимы переключаются через иконку в трее: В режиме Windows Containers он собирает и хостит контейнеры прямо в текущей операционке. Собранные в этом режиме контейнеры нельзя разместить под Linux. В режиме Linux Containers он на самом деле собирает и запускает контейнеры на линуксовой виртуалке - она видна в Hyper-V Manager. Собранные в этом режиме контейнеры можно разместить под Linux. Под каждый рантайм есть свой набор тэгов - все доступные можно посмотреть на https://hub.docker.com/r/microsoft/aspnetcore/ Т.е. да, вы можете включить режим Linux Containers, собрать набор из 4-х контейнеров (взяв nginx в качестве прокси), и потом запустить все это под Linux.

пятница, 10 января 2020 г.

Docker растет директория

#docker


Столкнулся с проблемой, при каждой сборке проекта постоянно растет директория /var/lib/docker/vfs/dir/

Как можно ее почистить?

При этом docker volume ls ничего не выдает
    


Ответы

Ответ 1



Почему, собирая образ с помощью Dockerfile, я получаю толстый слоеный пирог? Это связано c внутренней архитектурой Docker. Docker-образ представляет собой просто набор слоев, каждый из которых представляет собой слепок файловый системы (точнее, слепок отличий от нижележащей файловой системы) - по факту это файловая система на основе принципа copy-on-write, у которой каждый слой создается отдельной строчкой в Dockerfile. В тот момент, когда Docker необходимо собрать финальную файловую систему, он просто собирает композицию из этих слоев, и когда выполняющемуся в контейнере процессу необходимо получить содержимое файла X, собранная файловая система выдает содержимое файла в верхнем из слоев, содержащих этот файл; в случае, если нужно записать файл, он пишется в новом слое (слое контейнера). Это ключевой момент в инфраструктуре, который убивает сразу множество зайцев: Мгновенный запуск в новой файловой системе - несмотря на то что контейнер явялется почти полностью изолированной средой, для него не нужно копировать отдельную файловую систему. Файловая система собирается мгновенно, а все изменения записываются в новый слой, принадлежащий контейнеру, а сам контейнер ничего не может сделать с вышележащими слоями. Непосредственно сборка Docker-образа ведется ровно по такому же принципу: каждая строчка Dockerfile выполняется в новом слое (в новом контейнере, ФС которого собрана из предыдущих слоев), после чего этот слой коммитится (сохраняется), и следующая инструкция Dockerfile будет выполнена уже в новом контейнере, в который будет включен и текущий слой. Возможность собирать разные изображения из одних и тех же слоев: условная java:8 весит порядка 800 мб. Если бы каждый образ, который желает отнаследовать от нее, вбирал по 800 мб, то место бы выжиралось просто с невероятной скоростью. Однако система слоев позволяет один раз скачать java:8 и использовать ее во всех производных, не скачивая заново, поэтому непосредственно приложения на java:8 будут занимать всего 50-100 мегабайт места. Каждый из вышеописанных слоев имеет собственный идентификатор - такого же формата, как и контейнеры. Это, конечно, не очень human-friendly, поэтому и были придуманы реестры (серверы с изображениями), репозитории (название конкретного изображения, например ubuntu) и теги (версия изображения, например 14.04). Все это вместе (реестр-репозиторий-тег) может использоваться, чтобы отметить определенный слой в human-friendly стиле, в то время как внутренности остаются теми же самыми. И когда вы билдите новое изображение с определенным тегом, вы, де-факто, создаете еще слои файловой системы, последний из которых и отмечается заданным тегом. Со старыми слоями при этом ничего не происходит - они остаются там же, где и были, потому что команда создания нового изображения не может подразумевать удаление старых (т.к. они могут быть еще нужны) - оттуда и утечки дискового пространства. При определенных условиях (например, ADD и http-адрес архива) инструкция, несмотря на идентичность, будет каждый раз порождать новый слой, возможно, немалого объема - за этим, конечно, нужно следить и подчищать устаревшие изображения. Чтобы удалить все изображения без тега, можно воспользоваться следующим шорткатом: docker rmi $(docker images -qf "dangling=true") Последнее, о чем хочется сказать - кроме изображений, место могут жрать и т.н. volume, причина появления которых мне не очень понятна (но, тем не менее, они есть и могут "зависать" внутри хоста даже при удалении изображений). Их тоже надо время от времени чистить, для этого существует специальный скрипт.

Ответ 2



Спасибо за помощь! Вот решение: docker rmi image id можно узнать выполнив команду docker images Оказывается при сборке команда RUN добавляет новый слой к существующему образу, т.е. в Dockerfile встречается 2-е RUN команды, то образ будет с 2-я слоями и объемом равен первый слой + первый слой и незначительные изменения от 2-ой команды RUN https://xakep.ru/2015/06/04/docker-faq/ Раздел -- Почему, собирая образ с помощью Dockerfile, я получаю толстый слоеный пирог?

Ответ 3



В docker engine 1.13 можно использовать docker system prune. Смотри документацию. $ docker system prune WARNING! This will remove: - all stopped containers - all networks not used by at least one container - all dangling images - all build cache Are you sure you want to continue? [y/N]

понедельник, 6 января 2020 г.

Как работать с docker на windows?

#windows_10 #docker


Что нужно: linux среда для комфортного создания контейнеров для своих проектов. Хотелось
бы это делать максимально просто.

Теперь достаточно просто скачать установщик( у меня Win 10), Docker Toolbox  использовать
не нужно ?

Есть несколько вопросов (возможно они немного банальные):
Т.к. работа происходит на виндовс, то нужна linux система, поверх которой уже будут
установлены все нужные приложения - php, mysql, nginx etc.
Все это добро пакуется в image к которому дальше будут обращаться контейнеры.
Если что-то неверно - просьба поправить.

Где-то можно подсмотреть готовую конфигурацию или все нужно установить с нуля ? 
    


Ответы

Ответ 1



Я работаю с docker на Windows 8. У нас много проектов с использованием Vagrant и VirtualBox, а недавно мы перешли на docker. Я где-то читал, что VirtualBox не живёт вместе с Hyper-V, поэтому мы используем Docker Toolbox и VirtualBox Чтобы начать работать после установки Docker Toolbox и VirtualBox, нужно выполнить несколько шагов Создать Docker Machine docker-machine create --driver virtualbox default docker-machine start default Настроить Docker Machine Содержимое результата выполнения команды docker-machine env default записать в переменные среды (в свойстваъх компьютера) C:\>docker-machine env default You can further specify your shell with either 'cmd' or 'powershell' with the --shell flag. SET DOCKER_TLS_VERIFY=1 SET DOCKER_HOST=tcp://192.168.99.100:2376 SET DOCKER_CERT_PATH=C:\Users\Пользователь\.docker\machine\machines\default SET DOCKER_MACHINE_NAME=default SET COMPOSE_CONVERT_WINDOWS_PATHS=true REM Run this command to configure your shell: REM @FOR /f "tokens=*" %i IN ('"C:\Program Files\Docker Toolbox\docker-machine.EXE" env default') DO @%i Например, здесь - 5 переменных от DOCKER_TLS_VERIFY до COMPOSE_CONVERT_WINDOWS_PATHS Опционально: добавить запись в файл C:\WINDOWS\System32\Drivers\etc\hosts (192.168.99.100 - это IP адрес из переменной DOCKER_HOST) 192.168.99.100 docker.local Всё. Можно начинать работать =) И linux система не нужна, тут у вас небольшое недопонимание возникло: система будет крутиться внутри docker Начать можно с простого файла docker-compose.yml version: "2.1" services: nginx: image: nginx:latest ports: - "80:80" Создать его нужно обязательно в папке пользователя, например, в C:\Users\Пользователь\Docker\Qwerty. Точнее, это нужно делать в проектах, где файлы с хоста должны быть доступны внутри контейнера, в данном примере это требование не обязательное. В папке с файлом docker-compose.yml запускаем команду docker-compose up -d и заходим в http://docker.local/. Там будет дефолтная страница Nginx Tips & Tricks: Иногда случается так, что внутри контейнера как будто нет интернета. Тогда нужно сначала остановить docker-machine stop, а затем запустить заново docker-machine start Дальше можно гуглить по слову docker-compose nginx php mysql

Ответ 2



Docker toolbox качать не нужно. Сам сталкиваться с этим, когда была 8-ка, искренне не мог понять в чем же дело Десятка тоже нужна Windows 10 Pro. Иначе докер не будет работать. Но, я думаю, вы уже поняли это :) Можете пройти туториалы на докере. Там эти моменты рассматриваются. Вот тут И еще, когда у меня были проблемы с докером, я тоже задавал тут вопрос, но ответ не получал...не берусь говорить, что на стэке этого не знают, но лучше идти на Stack на английском или искать ответ самому..

воскресенье, 29 декабря 2019 г.

Что такое Docker

#docker


Что такое докер и для чего он нужен? Во всех статьях про докер встречаются термины
"имейдж" и "контейнер", что эти термины означают?

UPDATE
В скриншоте ниже я подключился получается к какому-то контейнеру? Я сейчас нахожусь
в том контейнере? Как мне из него выйти? И можно ли выйти не останавливая его и как
потом обратно туда попасть? 


    


Ответы

Ответ 1



docker - это такая упрощенная виртуалка. Виртуалка для одной-двух программ. Виртуалка, которая стартует в доли секунды. Виртуалка, которая обещает, что если Вы предоставите специальный маленький (текстовый) докер-файл (файл конфига), то любой админ, который знает докер, сможет приготовить правильное окружение и запустить софт. Зачем все это нужно. Вспомнить классическую ситуацию - программист написал софт и говорит "у меня на ноуте работает". А админы (сисопсы/девопсы) не могут развернуть на прод сервере и заставить работать, так как нет хорошего описания как это сделать. И на это обычно говорят так - давай твой ноут поставим в стойку. А вот если программист предоставил докер файл... то все сильно упрощается. Также докер предоставляет "из коробки" всякие разные вкусности. Например, можно приложению выделить определенные ресурсы процессора/памяти, открыть порты, поставить специфическую версию какой-то библиотеки - программисты любят говорить, что их софт работает только с ограниченным набором версий библиотек. Также можно переносить запущенные в докере приложения с машины на машину без особых проблем. Что такое имедж - это подготовленный кем-то набор файлов, готовый к использованию в докере. Это может быть целый линукс, а может быть специально собранный питон, который можно "наложить" на нужный образ линукса. То есть, если админу нужно обновить ядро, он берет нужный имедж с ядном, добавляет уже готовый имедж с программами и вуаля, все работает (если только не испортили совместимость). контейнер - а это уже готовый к употреблению продукт. Его можно запустить/остановить. (А вот образ не запустишь, его нужно поместить для начала в контейнер). На самом деле, докер - это не вируталка, это инструмент управления различными средствами виртуализациями. А управляет он к примеру lxc (linux container) - почти встроенное ядро средство виртуализации). UPD виртуалка - как virtual box или vmware. Но теже "виртуалные сервера" можно сделать на базе докера. изолированное окружение - это возможность сделать так, что приложение будет думать, что оно работает на сервере само. Допустим, хочется запустить десять веб серверов, а у них у всех прибит 80 порт и изменить нельзя. А докер позволит их всех запустить, каждый в своем контейнере, а наружу выпустит под разными портами. А ещё в одном докере запустить балансер, который будет с 80 порта разбрасывать запросы. А ещё к этому можно прикрутить docker-composer, который может управлять пачкой докер контейнеров. А вот винду - да, пока не запустить в докере, но это дело наживное. Если майкрософт захочет, то сделать образ и тогда все будет буквально в пару кликов (ой, не кликов, а строк в докер файлов). Более того, поговаривают, что Майкрософт к этому готовиться - выпустили виндовс сервер без gui, интегрируют линукс внутрь... посмотрим.