#postgresql #docker
#postgresql #docker
Вопрос:
Моему приложению требуется 3 базы данных. Я использую PostgreSQL.
Как я могу запустить все 3 базы данных в одном контейнере за один раз. Все 3 имеют разные таблицы и сценарии. Для каждого из них *.sql
файлы выполняются путем копирования в Dockerfile
.
Я пытался обычным способом. Не сработало.
Dockerfile:
FROM postgres
ENV POSTGRES_USER postgres
ENV POSTGRES_PASSWORD postgres
ENV POSTGRES_DB my_db_dev
COPY /devdb.sql /docker-entrypoint-initdb.d/
ENV POSTGRES_DB my_db_test
COPY /testdb.sql /docker-entrypoint-initdb.d/
ENV POSTGRES_DB my_db_prod
COPY /proddb.sql /docker-entrypoint-initdb.d/
Здесь запускается только последняя база данных (my_db_prod).
Как я могу создать все 3 сразу?
Комментарии:
1. Когда вы перезаписываете POSTGRES_DB env, postgresql не запускается, поэтому создается только последняя БД, вы можете получить доступ к контейнеру и войти в psql для создания других баз данных;
Ответ №1:
ENV
Команда Dockerfile устанавливает переменную среды во время сборки.
COPY
Также выполняется во время сборки, в основном перезаписывая docker-entrypoint-initdb.d
Когда вы вызываете эти действия, последнее выполненное переопределяет предыдущее, таким образом, конечное состояние изображения будет иметь POSTGRES_DB=my_db_prod
и docker-entrypoint-initdb.d
будет иметь содержимое proddb.sql
.
База данных не создается во время сборки. Вместо этого он создается во время выполнения, следуя инструкциям из /docker-entrypoint-initdb.d/ (/proddb.sql )
и POSTGRES_DB my_db_prod
, следовательно, это состояние, в котором последовательность команд из времени сборки покинула образ.
Чтобы создать несколько баз данных, вы можете объединить сценарии из 3 точек входа в одну или, что еще лучше, иметь один сценарий для каждой БД и заставить сценарии читать разные среды:
COPY ./create_second_db.sql /docker-entrypoint-initdb.d/create_second_db.sql
COPY ./create_third_db.sql /docker-entrypoint-initdb.d/create_third_db.sql
Вот полный пример, который может сэкономить некоторое время.
Комментарии:
1. В этом случае мой файл Dockerfile будет содержать только нижеприведенную вещь?
2. ИЗ postgres ENV POSTGRES_USER postgres ENV POSTGRES_PASSWORD КОПИЯ postgres ./create_first_db.sql /docker-entrypoint-initdb.d/create_second_db.sqlCOPY ./create_second_db.sql /docker-entrypoint-initdb.d/create_second_db.sql КОПИЯ ./create_third_db.sql /docker-точка входа-initdb.d/create_third_db.sql
3. Должен ли я добавить запрос на СОЗДАНИЕ базы данных в сам скрипт?
4. Создание баз данных в большом
docker-entrypoint-initdb.d
будет работать, но чище иметь сценарии инициализации под/docker-entrypoint-initdb.d/
. Они должны быть обнаружены initdb и выполнены.5. @Ranjith, вот пример, который может сэкономить вам некоторое время. Однако с Docker у вас очень небольшие накладные расходы, если вы запускаете 3 разных контейнера, по одному для каждой базы данных. На самом деле, это лучшая практика, следовательно, она лучше изолирует ваши области разработки / тестирования / продукта. Представьте, что вам нужно выполнить стресс-тест в вашей базе данных тестовой среды — это также повлияет на базы данных dev и prod, следовательно, они работают в одном контейнере.
Ответ №2:
я продолжаю этот путь, и у меня это работает.
мой docker-compose.yml :
version: '3.7'
db:
image: postgres:10.5
container_name: pg
restart: always
environment:
POSTGRES_PASSWORD: postgres
volumes:
- /initdb:/docker-entrypoint-initdb.d
ports:
- "5432:5432"
я монтирую одну папку initdb с хоста docker во внутренний контейнер postgres, как указано выше.
внутри initdb есть 2 sql-файла. и он успешно запущен для обоих сценариев sql.
Комментарии:
1. Как насчет владения каждой базой данных? где мы должны указать / назначить это?
2. Уважаемый Ранджит, я выделяю это в side sql script.