运行多个 Sidekiq 进程

极狐GitLab 允许您启动多个 Sidekiq 进程。 这些进程可用于一组专用队列,确保某些队列始终有专用的 worker,无论要处理的作业数量如何。

note此页面中的信息仅适用于 Omnibus GitLab。

可用的 Sidekiq 队列

有关现有 Sidekiq 队列的列表,请检查以下文件:

上述文件中的每个条目代表一个可以启动 Sidekiq 进程的队列。

启动多个进程

启动多个进程时,进程数应等于(并且超过)您希望专用于 Sidekiq 的 CPU 内核数。每个 Sidekiq 进程只能使用 1 个 CPU 内核,具体取决于可用的工作负载和并发设置。

启动多个进程:

  1. 使用 sidekiq['queue_groups'] 数组设置,指定使用 sidekiq-cluster 创建多少进程以及它们应该处理哪个队列。数组中的每一项都相当于一个额外的 Sidekiq 进程,每一项中的值决定了它处理的队列。

    例如,以下设置创建三个 Sidekiq 进程,一个运行在 elastic_commit_indexer 上,一个运行在 mailers 上,一个运行在所有队列上:

    sidekiq['queue_groups'] = [
      "elastic_commit_indexer",
      "mailers",
      "*"
    ]
    

    要让额外的 Sidekiq 进程处理多个队列,请添加多个队列名称,逗号分隔。例如:

    sidekiq['queue_groups'] = [
      "elastic_commit_indexer, elastic_association_indexer",
      "mailers",
      "*"
    ]
    

    在 12.9 及更高版本中,特殊的队列名称 * 表示所有队列。以下示例将启动两个进程,每个进程处理所有队列:

    sidekiq['queue_groups'] = [
      "*",
      "*"
    ]
    

    * 匹配所有 workers。 通配符查询必须留在列表的末尾,否则忽略它之后的规则。

    * 不能与具体的队列名称组合 - *, mailers 只处理 mailers 队列。

    sidekiq-cluster 仅在单个节点上运行时,使用 * 确保至少一个进程在所有队列上运行。这可确保进程自动在将来创建的队列中提取作业,包括具有专用进程的队列。

    如果 sidekiq-cluster 在多个节点上运行,您还可以使用 --negate 并列出所有已在处理的队列。

  2. 保存文件并重新配置极狐GitLab,使更改生效:

    sudo gitlab-ctl reconfigure
    

在极狐GitLab 中查看 Sidekiq 进程:

  1. 在顶部栏上,选择 主菜单 > 管理员
  2. 在左侧边栏上,选择 监控 > 后台作业

Negate 设置

要让 Sidekiq 进程在每个队列上工作,除去您列出的队列。在此示例中,我们从 Sidekiq 节点中排除所有与导入相关的作业:

  1. 编辑 /etc/gitlab/gitlab.rb 并添加:

    sidekiq['negate'] = true
    sidekiq['queue_selector'] = true
    sidekiq['queue_groups'] = [
       "feature_category=importers"
    ]
    
  2. 保存文件并重新配置极狐GitLab,使更改生效:

    sudo gitlab-ctl reconfigure
    

队列选择器

除了按名称选择队列,如上所述,queue_selector 选项允许使用 worker 匹配查询,以更一般的方式选择队列组。设置 queue_selector 后,所有 queue_groups 必须遵循上述语法。

/etc/gitlab/gitlab.rb 中:

sidekiq['enable'] = true
sidekiq['queue_selector'] = true
sidekiq['queue_groups'] = [
  # Run all non-CPU-bound queues that are high urgency
  'resource_boundary!=cpu&urgency=high',
  # Run all continuous integration and pages queues that are not high urgency
  'feature_category=continuous_integration,pages&urgency!=high',
  # Run all queues
  '*'
]

忽略所有导入队列

从 GitHub 导入或其他来源时,Sidekiq 可能会使用其所有资源来执行这些操作。要设置两个单独的 sidekiq-cluster 进程,其中一个只处理导入,另一个处理所有其他队列:

  1. 编辑 /etc/gitlab/gitlab.rb 并添加:

    sidekiq['enable'] = true
    sidekiq['queue_selector'] = true
    sidekiq['queue_groups'] = [
      "feature_category=importers",
      "feature_category!=importers"
    ]
    
  2. 保存文件并重新配置极狐GitLab,使更改生效:

    sudo gitlab-ctl reconfigure
    

线程数

默认情况下,在 sidekiq 下定义的每个进程都以等于队列数的线程数加上一个备用线程开始。 例如,处理 process_commitpost_receive 队列的进程总共使用三个线程。

这些线程在单个 Ruby 进程中运行,每个进程只能使用单个 CPU 内核。线程的可用性取决于需要等待一些外部依赖项的工作,例如数据库查询或 HTTP 请求。大多数 Sidekiq 部署都受益于这种线程,当在一个进程中运行较少的队列时,增加线程数可能更有效地利用 CPU 资源。

管理线程数

正确的最大线程数(也称为并发)取决于工作负载。 典型值范围从高度 CPU 密集型任务的 1 到混合低优先级工作的 15 或更高。对于非专业部署,合理的起始范围是 1525

每个线程都需要一个 Redis 连接,因此添加线程可能会增加 Redis 延迟并可能导致客户端超时。有关更多信息,请参阅有关 Redis 的 Sidekiq 文档

运行 Sidekiq 集群时(默认)

运行 Sidekiq 集群是 13.0 及更高版本中的默认设置。

  1. 编辑 /etc/gitlab/gitlab.rb 并添加:

    sidekiq['min_concurrency'] = 15
    sidekiq['max_concurrency'] = 25
    
  2. 保存文件并重新配置极狐GitLab,使更改生效:

    sudo gitlab-ctl reconfigure
    

min_concurrencymax_concurrency 是独立的。将 min_concurrency 设置为 0 会禁用限制。

对于每个队列组,让 N 比队列数大 1。并发设置为:

  1. N,如果它在 min_concurrencymax_concurrency 之间。
  2. max_concurrency,如果 N 超过这个值。
  3. min_concurrency,如果 N 小于这个值。

如果 min_concurrency 等于 max_concurrency,则无论队列数量如何,都会使用此值。

min_concurrency 大于 max_concurrency 时,它被视为等于 max_concurrency

运行单个 Sidekiq 进程时

运行单个 Sidekiq 进程是 12.10 及更早版本中的默认设置。

caution14.0 版本中删除了直接运行 Sidekiq。
  1. 编辑 /etc/gitlab/gitlab.rb 并添加:

    sidekiq['cluster'] = false
    sidekiq['concurrency'] = 25
    
  2. 保存文件并重新配置极狐GitLab,使更改生效:

    sudo gitlab-ctl reconfigure
    

这将设置 Sidekiq 进程的并发性(线程数)。

修改检查间隔

为附加的 Sidekiq 进程修改 sidekiq-cluster 的健康检查间隔:

1.编辑 /etc/gitlab/gitlab.rb 并添加(值可以是任意整数秒):

   sidekiq['interval'] = 5
  1. 保存文件并重新配置极狐GitLab,使更改生效。

使用 CLI 进行故障排除

caution建议使用 /etc/gitlab/gitlab.rb 来配置 Sidekiq 进程。如果您遇到问题,建议您联系技术支持。使用命令行需要您自担风险。

出于调试目的,您可以使用命令 /opt/gitlab/embedded/service/gitlab-rails/bin/sidekiq-cluster 启动额外的 Sidekiq 进程。此命令使用以下语法接受参数:

/opt/gitlab/embedded/service/gitlab-rails/bin/sidekiq-cluster [QUEUE,QUEUE,...] [QUEUE, ...]

每个单独的参数表示一组必须由 Sidekiq 进程处理的队列。多个队列可以由同一进程处理,方法是用逗号而不是空格分隔它们。

除了队列,还可以提供队列命名空间,让进程自动侦听该命名空间中的所有队列,而无需列出所有队列名称。

例如,您要启动 2 个额外进程:一个处理 process_commit 队列,一个处理 post_receive 队列,可以按如下方式完成:

/opt/gitlab/embedded/service/gitlab-rails/bin/sidekiq-cluster process_commit post_receive

如果您想启动一个进程来处理两个队列,则可以使用以下语法:

/opt/gitlab/embedded/service/gitlab-rails/bin/sidekiq-cluster process_commit,post_receive

如果您想让一个 Sidekiq 进程处理 process_commitpost_receive 队列,以及一个处理 gitlab_shell 队列的进程,可以使用以下命令:

/opt/gitlab/embedded/service/gitlab-rails/bin/sidekiq-cluster process_commit,post_receive gitlab_shell

监控 sidekiq-cluster 命令

sidekiq-cluster 命令在启动所需数量的 Sidekiq 进程后不会终止。相反,该进程继续运行并将任何信号转发给子进程。这允许您在向 sidekiq-cluster 进程发送信号时停止所有 Sidekiq 进程,而不必将其发送到各个进程。

如果 sidekiq-cluster 进程崩溃或收到 SIGKILL,子进程会在几秒钟后自行终止。这可确保您不会遇到僵尸 Sidekiq 进程。

这允许您通过将 sidekiq-cluster 连接到您选择的 supervisor(例如,runit)来监控进程。

如果一个子进程死亡,则 sidekiq-cluster 命令会通知所有剩余的进程终止,然后自行终止。这消除了对 sidekiq-cluster 重新实现复杂进程监控/重启代码的需要。相反,您应该确保您的 supervisor 在必要时重新启动 sidekiq-cluster 进程。

PID 文件

sidekiq-cluster 命令可以将其 PID 存储在文件中。默认情况下不写入 PID 文件,但这可以通过将 --pidfile 选项传递给 sidekiq-cluster 来更改。例如:

/opt/gitlab/embedded/service/gitlab-rails/bin/sidekiq-cluster --pidfile /var/run/gitlab/sidekiq_cluster.pid process_commit

请记住,PID 文件包含 sidekiq-cluster 命令的 PID,而不是已启动的 Sidekiq 进程的 PID。

环境

Rails 环境可以通过将 --environment 标志传递给 sidekiq-cluster 命令,或将 RAILS_ENV 设置为非空值来设置。默认值可以在 /opt/gitlab/etc/gitlab-rails/env/RAILS_ENV 中找到。