Tengo el siguiente archivo docker-compose.yml :
version: '3' services: postgres: image: postgres container_name: postgres ports: - "5431:5432" environment: - POSTGRES_USER=postgres - POSTGRES_PASSWORD=postgres - POSTGRES_DB=anime volumes: - ./init.sql:/docker-entrypoint-initdb.d/init.sqlEsta configuración inicia una base de datos de Postgres. En el volumen definí init.sql, que debería configurar una tabla:
CREATE TABLE anime ( anime_id INT PRIMARY KEY, title TEXT );Luego, me gustaría llenar la base de datos de Postgres con datos del archivo CSV.
Intenté agregar otro volumen a docker-compose:
- ./preload.sql:/preload/preload.sqlcon ese guion:
copy anime FROM 'docker/data/AnimeList.csv' DELIMITER ',' CSV HEADER; El archivo CSV se encuentra en la carpeta de data , en el mismo nivel que docker-compose.yml .
Pero no está funcionando. La base de datos se crea correctamente, pero no tiene la tabla y los datos. Cuando me conecto al contenedor Docker, ejecuto el comando 'psql e intento obtener la tabla de anime , aparece el siguiente error:
Did not find any relation named "anime".Mi pregunta es: ¿cómo precargar el contenedor de Postgres con el archivo de datos CSV en docker-compose?
Me las arreglé para que funcionara usando Dockerfile personalizado, aquí está mi solución:
data/ datasource.csv db/ scripts/ 1_init.sql 2_copy.sql Dockerfile docker-compose.yml El archivo CSV se encuentra en la carpeta de data dentro del proyecto.
En la carpeta del proyecto se encuentra el siguiente archivo docker-compose.yml :
version: '3.3' services: db: build: ./db container_name: postgres ports: - "5431:6666" environment: - POSTGRES_USER=postgres - POSTGRES_PASSWORD=postgres - POSTGRES_DB=db_name volumes: - ./data:/data Dockerfile contiene:
FROM postgres:alpine ADD scripts/1_init.sql /docker-entrypoint-initdb.d ADD scripts/2_copy.sql /docker-entrypoint-initdb.d RUN chmod a+r /docker-entrypoint-initdb.d/* EXPOSE 6666 1_init.sql cuerpo:
CREATE TABLE table_name ( --statement body ); Y 2_copy.sql :
COPY table_name FROM '/data/datasource.csv' DELIMITER ',' CSV HEADER; 1_init.sql crea la tabla DB, debe tener los mismos nombres de columna que en el archivo CSV . 2_copy.sql es responsable de copiar datos del CSV a postgres.
Dockerfile usa una imagen de postgres y copia todos los archivos *.sql en /docker-entrypoint-initdb.d/ . Posteriormente, todos los archivos se ejecutan en orden alfanumérico, por eso los archivos *.sql comienzan con dígitos. Finalmente, se expone el puerto 6666 .
docker-compose.yml crea el Dockerfile desde la carpeta db y lo hace accesible a través del puerto 5431 . Como propiedades ambientales se utilizan propiedades básicas de postgres. Y al final, la carpeta de data con el archivo CSV se copia en el contenedor.