除了应用程序之外,如何在单独的不同 docker 容器中运行 sidekiq

Rpj*_*Rpj 5 ruby-on-rails whenever sidekiq docker docker-compose

除了应用程序之外,如何在单独的不同 docker 容器中运行 sidekiq。我们在任何时候使用 sidekiq 作业,但这些作业在所有 Web 容器中都被触发

  1. 我们如何设置 web 容器(rails 应用程序)和 sidekiq 工作器以水平扩展(最好作为单独的容器)。
  2. 我们应该如何管理数据库迁移,因为 sidekiq、ui 容器使用相同的图像
  3. 我正在尝试使用以下代码段,这是正确的还是应该有所不同?
version: '3.8'

services:
  foo-db:
    image: postgres:$POSTGRES_VERSION
    container_name: foo-db-container
    restart: unless-stopped
    env_file: .env
    volumes:
      - /var/lib/postgresql/data
    networks:
      - $FOO_NETWORK

  foo-redis:
    image: redis:$REDIS_VERSION
    container_name: foo-redis-container
    init: true
    sysctls:
      net.core.somaxconn: 511
    env_file: .env
    volumes:
      - /var/lib/redis/data
    networks:
      - $FOO_NETWORK

  foo-sidekiq:
    depends_on:
      - foo-db
      - foo-redis
    build: ./foo-ui
    command: bundle exec sidekiq
    env_file: .env
    volumes:
      - /var/lib/redis/data
    networks:
      - $FOO_NETWORK

  foo-service:
    build: foo-service
    # image: gcr.io/foo/foo-service:latest
    container_name: foo-service-container
    ports:
      - "$FOO_SERVICE_PORT:$FOO_SERVICE_PORT"
    env_file: .env
    networks:
      - $FOO_NETWORK

  foo-ui:
    build: ./foo-ui
    # image: gcr.io/foo/foo-ui:latest
    container_name: foo-ui-container
    depends_on:
      - foo-db
      - foo-redis
      - foo-sidekiq
      - foo-service
    ports:
      - "$FOO_UI_PORT:$FOO_UI_PORT"
    env_file: .env
    networks:
      - $FOO_NETWORK

networks:
  foo-network:
Run Code Online (Sandbox Code Playgroud)

ces*_*ves 5

以下是您应该设置的内容列表:

  • 图片

您的 sidekiq 和 Web 应用程序应该有不同的图像。这样,您可以确保whenever -w仅在背景 (sidekiq) 图像中调用,而不是在 Web 图像内调用。

示例图片:https://gist.github.com/cesartalves/69f6440b97c89e9dee6cfffbdf9b7790(适应您的需求)

要点:

  • apt-get update && apt-get install -y cron- 安装crontab
  • bundle exec whenever -w- 随时运行
  • CMD [ "bundle", "exec", "sidekiq"- 将 sidekiq 作为主进程运行
  • ENTRYPOINT [ "./docker-entrypoint.sh" ]- 在后台运行 cron 以及您可能需要执行的其他命令

要检查 crontab 是否正在运行,您可以在容器运行后执行以下操作之一https://askubuntu.com/questions/85558/verify-if-crontab-works

关于“水平缩放”,如果您有多个 sidekiq 实例使用同一个 Redis 池,这应该自动完成 - sidekiq 实例越多,您的作业运行得越快。

如果“水平”意味着能够设置 crons 将在哪些服务器上运行,那么您可以有多个 Schedule.rb 文件,并且每个后台容器应该仅将其中一个部署到 crontab,方法是执行whenever -w -f config/schedule_specific_cron1.rb. 您可以将该文件作为环境变量传递。

  1. 迁移

如果所有应用程序容器都使用相同的数据库,则仅让其中一个执行迁移。这将加快容器的启动速度并避免任何锁定错误。我建议在“web”图像中执行此操作,因为您将拥有多个 sidekiq 容器实例。

  1. 宝石

您的所有图像都将使用相同的宝石。因此,您需要创建一个卷来存储它们,以加快它们的构建过程:

foo-sidekiq:
    depends_on:
      - foo-db
      - foo-redis
    build: ./foo-ui
    command: bundle exec sidekiq
    env_file: .env
    volumes:
      - /var/lib/redis/data
      - gem_cache:/gems
    networks:
      - $FOO_NETWORK

volumes:
  gem_cache:
Run Code Online (Sandbox Code Playgroud)

在你的图像中:

ENV BUNDLE_PATH /gems

  1. 编排

您使用哪种容器编排系统?

依赖项应按以下顺序运行:

  1. 运行数据库容器
  2. 运行redis容器
  3. 运行 Web 容器和后台任务容器

理想情况下,您应该使用允许您指定所需数量的 sidekiq 容器实例的东西。

--

我认为这涵盖了要点。如果您需要更多信息,请与我们联系。