如何将节点Docker容器与Postgres Docker容器连接

时间:2019-11-12 19:33:19

标签: node.js postgresql docker docker-compose

我在本地计算机上的节点上有一个CRUD应用程序。它在以postgres为数据库,使用knex.js作为查询构建器等的节点上运行。

我已经创建了一个docker文件和一个docker-compose文件,并且容器启动了,但是节点容器无法到达postgres容器。我怀疑这与环境变量有关,但我不确定。这是我的docker文件:

FROM node:12
# Create app directory
WORKDIR /usr/src/app

# Install app dependencies
# A wildcard is used to ensure both package.json AND package-lock.json are copied
# where available (npm@5+)
COPY package*.json ./

RUN npm ci --only=production

# Bundle app source
COPY . .

ENV PORT=8080
EXPOSE 8080

CMD [ "npm", "start" ]

这是docker-compose文件:

version: '2'
services:
  postgres:
    image: postgres:alpine
    environment:
      POSTGRES_PASSWORD: password
      POSTGRES_USER: app
      POSTGRES_DB: db

  app:
    build: .
    depends_on:
      - "postgres"
    links:
      - "postgres"
    environment:
      DB_PASSWORD: 'password'
      DB_USER: 'app'
      DB_NAME: 'db'
      DB_HOST: 'postgres'
      PORT: 8080
    ports:
      - '8080:8080'
    command: npm start

另外,这是根目录上的knex.js文件,用于根据环境处理数据库连接:

// Update with your config settings.

module.exports = {

  development: {
    client: 'pg',
    connection: 'postgres://localhost/db'
  },
  test: {
    client: 'pg',
    connection: 'postgres://localhost/test-db'
  }
};

另外,当我检查docker内节点应用程序上的hosts文件时,我没有看到任何提及postgres容器的链接。任何帮助将不胜感激,谢谢。

2 个答案:

答案 0 :(得分:1)

您的节点应用程序未连接的原因是,它在引用localhost时试图与其自身连接。您的数据库位于另一个不在本地的容器中,因此您需要通过服务名称postgres来引用它。

因此,假设您的应用程序以其他方式处理身份验证,则您的配置将如下所示:

// Update with your config settings.

module.exports = {

  development: {
    client: 'pg',
    connection: 'postgres://postgres/db'
  },
  test: {
    client: 'pg',
    connection: 'postgres://postgres/test-db'
  }
};

如果可以的话,应该使用分配给app容器的环境变量。

答案 1 :(得分:0)

Docker-compose创建一个由其启动的不同容器共享的内部网络。
由于apppostgres是2个单独的容器,因此它们被视为2个主机。当您将其指向localhost而不是postgres容器时,这会导致应用程序在同一容器上查找postgres。

您可以通过在localhost文件中将postgres更改为knex.js来解决此问题。