【问题标题】:creating pg_cron extension within docker-entrypoint-initdb.d fails在 docker-entrypoint-initdb.d 中创建 pg_cron 扩展失败
【发布时间】:2018-06-12 16:12:50
【问题描述】:

如果我在 docker-entrypoint-initdb.d/init.sql 文件中创建 pg_cron 扩展名,docker 映像将无法运行,docker logs <id> 只会说“没有这样的容器”。这是相关的 .sql sn-p:

CREATE DATABASE my_database;
\c my_database;
CREATE EXTENSION IF NOT EXISTS postgis CASCADE;
CREATE EXTENSION IF NOT EXISTS timescaledb CASCADE;
CREATE EXTENSION IF NOT EXISTS pg_cron CASCADE;

但是,如果我在 docker run 命令完成后创建 pg_cron 扩展(即删除上面的最后一行并在 docker run 完成后使用 psql --file 单独运行它),则成功创建扩展(似乎是 postgis 和 timescaledb 扩展没关系)。

我无法从docker-entrypoint-init.d 创建 pg_cron 扩展是否有原因?有正确的地方吗?

我的docker运行命令如下:

 docker run -d \
        --name my_container --rm \
        -p 5432:5432 \
        -clog_line_prefix="%m [%p]: [%l-1] %u@%d" \
        -clog_error_verbosity=VERBOSE \
        -cshared_preload_libraries='timescaledb,pg_cron' \
        -ccron.database_name='my_database'

【问题讨论】:

    标签: postgresql docker psql timescaledb


    【解决方案1】:

    pg_cron 只能作为共享库加载。您必须在postgres.conf 文件中指定它。因为docker-entrypoint-init.d 中的所有脚本都是在postgres 服务器启动后执行的(使用pg_ctl start),所以在postgres.conf 中对shared_preload_libraries 的所有更改都可以在重新启动后(使用pg_ctl restart)变得可用。

    现实世界的例子:

    002-setup.sh

    #!/bin/sh
    
    # Remove last line "shared_preload_libraries='citus'"
    sed -i '$ d' ${PGDATA}/postgresql.conf
    
    cat <<EOT >> ${PGDATA}/postgresql.conf
    shared_preload_libraries='pg_cron,citus'
    cron.database_name='${POSTGRES_DB:-postgres}'
    EOT
    
    # Required to load pg_cron
    pg_ctl restart
    

    003-main.sql

    CREATE EXTENSION pg_cron;
    

    通知

    1. 脚本执行顺序很重要,按文件名排序
    2. pg_croncron.database_name 指定的db 中可用

    【讨论】:

    • 这还不够,您实际上需要先安装扩展,然后才能在 PostgreSQL 配置中引用它
    【解决方案2】:

    您需要安装和设置pg_cron 扩展。

    我建议您使用(或至少 fork)此存储库:ramazanpolat/postgres_cron: Dockerfile for building postgresql:11 with pg_cron extension

    【讨论】:

      【解决方案3】:

      建议的解决方案不适用于我新创建的容器。所以,我是这样做的:

      Docker 文件

      FROM postgres:13.2
      
      RUN apt-get update && apt-get -y install git build-essential postgresql-server-dev-13
      
      RUN git clone https://github.com/citusdata/pg_cron.git
      RUN cd pg_cron && make && make install
      
      RUN cd / && \
              rm -rf /pg_cron && \
              apt-get remove -y git build-essential postgresql-server-dev-13 && \
              apt-get autoremove --purge -y && \
              apt-get clean && \
              apt-get purge
      
      COPY init-db /docker-entrypoint-initdb.d
      

      init-db/002-pg-cron.sh

      #!/usr/bin/env bash
      
      # use same db as the one from env
      dbname="$POSTGRES_DB"
      
      # create custom config
      customconf=/var/lib/postgresql/data/custom-conf.conf
      echo "" > $customconf
      echo "shared_preload_libraries = 'pg_cron'" >> $customconf
      echo "cron.database_name = '$dbname'" >> $customconf
      chown postgres $customconf
      chgrp postgres $customconf
      
      # include custom config from main config
      conf=/var/lib/postgresql/data/postgresql.conf
      found=$(grep "include = '$customconf'" $conf)
      if [ -z "$found" ]; then
        echo "include = '$customconf'" >> $conf
      fi
      

      另外,您可以将其他初始化文件放入 init-db 目录。

      003-main.sql

      CREATE EXTENSION pg_cron;
      

      Docker 撰写文件

      version: '3.7'
      services:
        postgres:
          container_name: your-container
          build: .
          environment:
            POSTGRES_DB: "your_db"
            POSTGRES_USER: "your_user"
            POSTGRES_PASSWORD: "your_user"
          volumes:
            - pgdata:/var/lib/postgresql/data
          ports:
            - "5432:5432"
      volumes:
        pgdata:
          driver: local
      

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2021-01-16
        • 1970-01-01
        相关资源
        最近更新 更多