【问题标题】:How do I run Rails in Docker? PG::ConnectionBad could not translate host name "pg" to address: No address associated with hostname如何在 Docker 中运行 Rails? PG::ConnectionBad 无法将主机名“pg”转换为地址:没有与主机名关联的地址
【发布时间】:2018-04-29 18:40:12
【问题描述】:

我尝试按照此处的指南进行操作:https://docs.docker.com/compose/rails/

docker-compose.yml
version: '3'
services:
  pg:                                     ######### LOOK HERE!
    image: postgres
    volumes:
      - ./tmp/db:/var/lib/postgresql/data
  web:
    build: .
    command: bundle exec rails server -p 3000 -b '0.0.0.0'
    volumes:
      - .:/app
    ports:
      - "3000:3000"
    depends_on:
      - pg
    links:
      - pg                                     ######### LOOK HERE!
  cms:
    image: joomla
    restart: always
    links:
      - mysql:joomladb
    ports:
      - 8080:80
    environment:
      JOOMLA_DB_HOST: mysql
      JOOMLA_DB_PASSWORD: example
  mysql:
    image: mysql:5.6
    restart: always
    environment:
      MYSQL_ROOT_PASSWORD: example
config/database.yml
# SQLite version 3.x
#   gem install sqlite3
#
#   Ensure the SQLite 3 gem is defined in your Gemfile
#   gem 'sqlite3'
#
default: &default
  adapter: postgresql
  encoding: unicode
  pool: 5
  timeout: 5000
  host: pg                                     ######### LOOK HERE!
  username: postgres
  password:

development:
  <<: *default
  database: project

# Warning: The database defined as "test" will be erased and
# re-generated from your development database when you run "rake".
# Do not set this db to the same as development or production.
test:
  <<: *default
  database: project_test

production:
  <<: *default
  database: project

控制台

C:\Users\Chloe\workspace\project\src>docker-compose run web rake db:create
Starting src_pg_1 ... done
could not translate host name "pg" to address: No address associated with hostname
Couldn't create database for {"adapter"=>"postgresql", "encoding"=>"unicode", "pool"=>5, "timeout"=>5000, "host"=>"pg", "username"=>"postgres", "password"=>nil, "database"=>"project"}
rake aborted!
PG::ConnectionBad: could not translate host name "pg" to address: No address associated with hostname

docker-compose 版本 1.20.1,构建 5d8c71b2,Docker 版本 18.03.0-ce,构建 0520e24302

【问题讨论】:

  • 你解决了吗?
  • @wilgosz.pl 不!我很高兴我不是唯一一个遇到问题并意识到 Docker 是一坨屎的人。它有很大的潜力,但如果它不能解析主机名,那就没有用了,
  • 克洛伊,请检查我的回答。当我尝试运行:docker-compose up web 时,pg 问题就在那里,但是当我在没有 web 的情况下运行它时,它会尝试运行所有服务,然后 depend_on 赶上。所以要么: 1. 在一个终端会话中运行它:docker-compose up 2. 然后运行:docker-compose run web rake db:create 它会有帮助吗?

标签: ruby-on-rails docker docker-compose


【解决方案1】:

好的,我会试着回答这个问题:

通常出现此错误时,可能意味着运行db容器返回一些错误并停止。

我有同样的问题,经过一些挖掘发现我有

LANG='en_US.UTF-8'
LANGUAGE='en_US:en'
LC_ALL='en_US.UTF-8'

在我的环境变量中设置,这导致db 容器停止。因此,由于容器没有运行,我没有 db 主机。

这是我的docker-compose.yml 文件的样子:

version: '3'

services:
  db:
    image: postgres
    volumes:
      - ./tmp/db:/var/lib/postgresql/data
    env_file: .env
  app:
    build: .
    command: bundle exec puma -p 3000 -C config/puma.rb
    env_file: .env
    volumes:
      - .:/app
    ports:
      - "3031:3000"
    depends_on:
      - db

这里是config/database.yml

default: &default
  adapter: postgresql
  encoding: unicode
  host: db
  pool: 5
  username: <%= ENV['POSTGRES_USER'] %>
  password: <%= ENV['POSTGRES_PASSWORD'] %>

development:
  <<: *default
  database: driggl_dev

test:
  <<: *default
  database: driggl_test

production:
  <<: *default
  database: driggl_prod

...以及用于开发的.env 文件:

POSTGRES_USER=driggl
POSTGRES_PASSWORD=driggl

由于我为 db 数据共享了卷,因此我从存储库中删除了 tmp/db 文件夹以确保安全。

rm -rf tmp/*

然后我删除了所有容器和图像

docker rm $(docker ps -q -a) -f
docker rmi $(docker images -q) -f

最后我再次启动容器:

docker-compose up --build

最后一切顺利。

总结

  1. 确保系统某处没有缓存任何内容
  2. 确保您的数据库容器在启动时不会返回错误。

我希望这对遇到这个问题的人有所帮助。

【讨论】:

  • 必须有一种方法可以做到这一点,而无需将容器合并到一个 compose 文件中,并将它们构建在一起。 Docker 有自己的网络 - 如何在 database.yml 文件中对其进行寻址?
  • 这个答案拯救了我的一天。
【解决方案2】:

此设置适用于我在 docker 上运行 rails。基本上需要指定一个 URL,因此您将使用 .env 文件来指定 postgres url,并且您将使用 config/database 文件在 _development _test 和 _production 之间进行更改,只需添加 env。文件到您的网络服务 docker-compose 文件:

/docker-compose.yml:

services:
  postgres:
    image: postgres:9.6
    restart: always
    environment:
      POSTGRES_USER: kunzig #DockerHub postgres docs state this is optional but must be used when password is set.  It will also create a db under the supplied username which you'll use to connect to in rails console such as: $docker-compose exec postgres psql -U YourUserNameHere
      POSTGRES_PASSWORD: 'whateverPWYouWant'
    ports:
      - '5432' #Was originally 5432:5432 with the Left hand side being port on host machine, right hand side is the port on the docker container.  However I let docker choose the port it will use by supplying because 5432 is running on my local for other projects.  
    volumes:
      - postgres:/var/lib/postgresql/data 



  web:
    build: . #Runs the docker build command on the current directory
    links: #Links the listed services to our application so containers can talk to eachother
      - postgres
      - redis
    restart: always
    volumes:
      - .:/kunzig #Left hand side is current directory of compose file, right hand side is container folder.  This needs to be same as Install_path folder in Dockerfile.
    ports:
      - '8000:8000' #Left is the local port and the right side is the container port
    env_file:
      - .YourProjectNameHere.env #This should be in your root project directory along side the Dockerfile and docker-compose file
    depends_on:
      - 'redis'
      - 'postgres'

/.projectname.env

DATABASE_URL=postgresql://PostgresUserNameHere:PasswordFromDockerCompose@postgres:5432/PostgresUsername?encoding=utf8&pool=5&timeout=5000

/config/database.yml

development:
  url: <%= ENV['DATABASE_URL'].gsub('?', '_development?' ) %>
test:
  url: <%= ENV['DATABASE_URL'].gsub('?', '_test?' ) %>
production:
  url: <%= ENV['DATABASE_URL'].gsub('?', '_production?' ) %>

保持您的网络服务与 pg 服务保持原样链接,您应该很好,只需注意我调用了我的服务 postgres。

【讨论】:

  • 但是您仍然使用主机名@postgres:5432,所以如果现在找不到主机名,如何使用包含主机名的URL?
【解决方案3】:

我也有同样的问题。对于我的一生,我无法弄清楚它为什么会发生。调试了很长一段时间,但无法弄清楚如何使 db 容器的 container_name 在我的 database.yml 文件中解析。更奇怪的是,在不同的计算机上,相同的配置却完全可以正常工作。

最后我发现如果你使用host.docker.internal,它本质上就相当于Docker中的localhost

所以我将我的database.yml 文件更改为:

default: &default
  adapter: postgresql
  encoding: unicode
  host: host.docker.internal
  port: 5432
  username: <%= ENV['DATABASE_USERNAME'] %>
  password: <%= ENV['DATABASE_PASSWORD'] %>

这一切都解决了。请注意,我听说这在 Unix 系统中不起作用。我正在使用 OS X,这工作正常。

【讨论】:

    【解决方案4】:

    在谷歌搜索此问题时,只需将其添加为第一个命中。

    与@swilgosz 的回答类似(但不同) - 我的数据库无法启动:

    could not write lock file "postmaster.pid": No space left on device
    

    运行后果然快了:

    docker system prune
    

    一切都恢复了。回想起来很明显,但我想我会添加这个以防它节省任何时间。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2017-12-04
      • 2018-12-04
      • 2021-10-02
      • 1970-01-01
      • 1970-01-01
      • 2022-10-04
      相关资源
      最近更新 更多