1

I have a node server that's trying to connect to a postgres database using knex. Both are in docker containers with the same custom network. I keep getting ECONNREFUSED errors. I've poked around in the database container and I see that my DB (test_db) has been created by psql but it has no permissions. After giving root permissions, I'm still getting the same issues. I've tried removing the volumes with docker-compose down -v but still no luck. I've also tried removing knex and just using node-postgres but same errors. I'm also unable to connect to the Db from the host using pgadmin. Would appreciate any help!

Here's my docker-compose.yml

version: "3"

services:
  server:
    build:
      context: .
      dockerfile: development.Dockerfile
    ports:
      - "8081:8081"
    volumes:
      - .:/src
      - /src/node_modules
    networks:
      - dev-network
    environment:
      DB_HOSTNAME: pg-development
      DB_USER: root
      DB_PASSWORD: helloworld
      DB_PORT: 3306
      DB_NAME: test_dev
    depends_on:
      - pg-development
  pg-development:
    image: postgres
    environment:
      POSTGRES_USER: root
      POSTGRES_PASSWORD: helloworld
      POSTGRES_DB: test_dev
    ports:
      - "3308:3306"
    volumes:
      - dbdata:/data/db
    networks:
      - dev-network
    healthcheck:
      test: ["CMD-SHELL", "pg_isready -U root -d test_dev"]
      interval: 10s
      timeout: 2s
      retries: 10
networks:
  dev-network:
    driver: bridge

volumes:
  dbdata:

Here's my db connection

import knex from "knex";

const connection = {
  host: process.env.DB_HOSTNAME,
  user: process.env.DB_USER,
  password: process.env.DB_PASSWORD,
  port: Number(process.env.DB_PORT),
  database: process.env.DB_USER,
};

const db = knex({
  client: "pg",
  connection,
  debug: true,
  pool: {
    min: 0,
    max: 50,
    afterCreate: function (conn, done) {
      conn.query('SET timezone="UTC";', function (err) {
        if (err) {
          done(err, conn);
        }
      });
    },
  },
});

2
  • what the value of process.env.DB_HOSTNAME? localhost or docker ip? Commented Apr 20, 2020 at 1:38
  • Are you sure the database container is fully started when you connect (it can take a minute or so)? Commented Apr 20, 2020 at 2:05

3 Answers 3

2

The reason this wasn't working is because the DB was actually being started on the default postgres port which is 5432. Turns out in docker-compose.yml you need to add a command to change the default port.

pg-development:
    image: postgres
    environment:
      POSTGRES_USER: root
      POSTGRES_PASSWORD: helloworld
      POSTGRES_DB: test_dev
    ports:
      - "3308:3306"
    volumes:
      - dbdata:/data/db
    networks:
      - dev-network
    healthcheck:
      test: ["CMD-SHELL", "pg_isready -U root -d test_dev"]
      interval: 10s
      timeout: 2s
      retries: 10
    command: -p 3306 // this fixes the issue
Sign up to request clarification or add additional context in comments.

Comments

0

I'ts because you are exposing the wrong port in the pg-development container:

https://docs.docker.com/compose/reference/port/

port [options] SERVICE PRIVATE_PORT

The port you are exposing in the database is the port 3308, the correct configuration sould be:

...
ports:
      - "3306:3306"
...

2 Comments

Connections between container's don't use (or need) ports:. You'd connect to the "normal" PostgreSQL port 3306 regardless of what port (if any) was published.
You're right because they are running in the same internal network. Anyways, if docker-compose.yml, try to bind the container's port 3308 with the port in the physical host, and that port is bussy, that may cause that the db container crash. Also this is weird "I'm also unable to connect to the Db from the host using pgadmin."
0

This is worked for me in docker-compose, one of the container is postgresqldb another one is .net core 3.1 container.

#docker-compose.yml
version: '3.4'

services:

    customerdb:
        image: postgres

    customer.api:
        image: ${DOCKER_REGISTRY-}customerapi
        build:
            context: .
            dockerfile: Customer/Customer.API/Dockerfile

docker-compose.override.yml

customerdb:
    container_name: customerdb
    image: postgres
    restart: always
    environment:
        POSTGRES_PASSWORD: postgres
        POSTGRES_DB: postgres
        POSTGRES_USER: postgres
    ports:
        - 5100:5432
    volumes:
        - ./postgres-data1:/var/lib/postgresql/data 

customer.api:
    container_name: customerapi
    environment:
        - ASPNETCORE_ENVIRONMENT=Development
        - "ConnectionStrings:CustomerConnection=host=host.docker.internal;port=5100;database=CustomerDB;username=postgres;password=postgres"
    depends_on:
        - customerdb
    volumes:
        - ${HOME}/.microsoft/usersecrets/:/root/.microsoft/usersecrets
        - ${HOME}/.aspnet/https:/root/.aspnet/https
    ports:
        - "8000:80"

I used ConnectionStrings:CustomerConnection=host=... because I used to app.config for connection string.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.