使用docker compose在postgresql数据库中创建表

使用docker compose在postgresql数据库中创建表,postgresql,docker,docker-compose,Postgresql,Docker,Docker Compose,我正在使用docker compose部署一个多容器python Flask web应用程序。在构建过程中,我很难理解如何在postgresql数据库中创建表,因此我不必使用psql手动添加它们 我的docker-compose.yml文件是: web: restart: always build: ./web expose: - "8000" links: - postgres:postgres volumes: - /usr/src/flask-a

我正在使用docker compose部署一个多容器python Flask web应用程序。在构建过程中,我很难理解如何在postgresql数据库中创建表,因此我不必使用psql手动添加它们

我的docker-compose.yml文件是:

web:
  restart: always
  build: ./web
  expose:
    - "8000"
  links:
    - postgres:postgres
  volumes:
    - /usr/src/flask-app/static
  env_file: .env
  command: /usr/local/bin/gunicorn -w 2 -b :8000 app:app

nginx:
  restart: always
  build: ./nginx/
  ports:
    - "80:80"
  volumes:
    - /www/static
  volumes_from:
    - web
  links:
    - web:web

data:
  restart: always
  image: postgres:latest
  volumes:
    - /var/lib/postgresql
  command: "true"

postgres:
  restart: always
  image: postgres:latest
  volumes_from:
    - data
  ports:
    - "5432:5432"
我不想必须输入psql才能输入:

CREATE DATABASE my_database;
CREATE USER this_user WITH PASSWORD 'password';
GRANT ALL PRIVILEGES ON DATABASE "my_database" to this_user;
\i create_tables.sql

我希望您能指导我如何创建表格。

我会在构建过程中创建表格。在新目录
/database/

FROM postgres:latest
COPY . /fixtures
WORKDIR /fixtures
RUN /fixtures/setup.sh
/database/setup.sh
看起来像这样:

#!/bin/bash
set -e

/etc/init.d/postgresql start
psql -f create_fixtures.sql    
/etc/init.d/postgresql stop
将创建用户、创建数据库、创建表sql(以及任何其他夹具数据)放入
创建夹具.sql
文件中,该文件位于
/database/
目录下

最后,您的
postgres
服务将更改为使用
build

postgres:
    build: ./database/
    ...
注意:有时在
/etc/init.d/postgresql start
行之后,您需要一个
sleep 5
(或者更好的脚本来轮询并等待postgresql启动)。根据我的经验,无论是init脚本还是psql客户机都可以为您处理这个问题,但我知道mysql不是这样的,所以我想我应该调用它

我不想必须输入psql才能输入

您可以简单地使用容器的内置init机制:

COPY init.sql/docker entrypoint initdb.d/10 init.sql

这可以确保在DB server正确启动后执行sql

看看他们的入口点。它为正确启动psql做了一些准备,并查看
/docker entrypoint initdb.d/
目录中以
.sh
.sql
.sql.gz
结尾的文件

文件名中的
10-
是因为文件是按ASCII顺序处理的。例如,您可以将其他init文件命名为
20 create tables.sql
30 seed tables.sql.gz
,并确保按照您需要的顺序处理它们

还要注意,调用命令指定数据库。如果您正在迁移到docker compose,并且您现有的
。sql
文件也没有指定DB,请记住这一点


您的文件将在容器的第一个开始安装的
build
阶段进行处理。由于Docker Compose停止图像,然后恢复图像,所以几乎没有区别,但是,如果在
构建
阶段初始化DB对您来说至关重要,我建议您仍然使用内置的init方法,从dockerfile调用
/docker entrypoint.sh
,然后在
/docker entrypoint initdb.d/
目录中进行清理。

中的
复制
方法对我不起作用
Dockerfile
。但是我通过向docker compose.yml添加以下内容来运行我的
init.sql
文件:

    volumes:
        - ./init.sql:/docker-entrypoint-initdb.d/init.sql
init.sql
与我的
docker compose.yml
位于同一目录中。
我从gist中选择了解决方案。查看文章了解更多信息。

谢谢您的帮助。我在构建docker-compose.yml时遇到了这个错误
bin/sh:1:/fixtures/setup.sh:Permission denied Service'postgres'无法生成:命令'/bin/sh-c/fixtures/setup.sh'返回一个非零代码:126
Ok,您也可以将
set-x
添加到脚本顶部,这样它将打印出每个步骤,我添加了
runchmod+x/fixtures/setup.sh
,解决了这个问题。我现在得到
没有PostgreSQL集群存在;请参阅“man pg_createcluster”。。。(警告)。psql:无法连接到服务器:没有这样的文件或目录是在本地运行并在Unix域套接字上接受连接的服务器“/var/run/postgresql/.s.PGSQL.5432”?服务“postgres”构建失败:命令“/bin/sh-c/fixtures/setup.sh”返回了一个非零代码:2
Ok,我想你遇到了我在回答底部的“注意”中描述的情况。你解决过这个集群问题吗?这不适用于最新版本的postgres映像:(