Commit ad66b824 authored by Sean McGivern's avatar Sean McGivern

Merge branch 'include-worker-metadata-in-all-queues-yml' into 'master'

Add Rake task to generate all_queues.yml

See merge request gitlab-org/gitlab!22892
parents 22d37c56 32f0cd79
# This file is generated automatically by
# bin/rake gitlab:sidekiq:all_queues_yml:generate
#
# Do not edit it manually!
--- ---
- auto_devops:auto_devops_disable - auto_devops:auto_devops_disable
- auto_merge:auto_merge_process - auto_merge:auto_merge_process
- chaos:chaos_cpu_spin - chaos:chaos_cpu_spin
- chaos:chaos_db_spin - chaos:chaos_db_spin
- chaos:chaos_kill - chaos:chaos_kill
- chaos:chaos_leak_mem - chaos:chaos_leak_mem
- chaos:chaos_sleep - chaos:chaos_sleep
- container_repository:cleanup_container_repository
- container_repository:delete_container_repository
- cronjob:admin_email - cronjob:admin_email
- cronjob:ci_archive_traces_cron
- cronjob:container_expiration_policy - cronjob:container_expiration_policy
- cronjob:expire_build_artifacts - cronjob:expire_build_artifacts
- cronjob:gitlab_usage_ping - cronjob:gitlab_usage_ping
- cronjob:import_export_project_cleanup - cronjob:import_export_project_cleanup
- cronjob:pages_domain_verification_cron - cronjob:issue_due_scheduler
- cronjob:namespaces_prune_aggregation_schedules
- cronjob:pages_domain_removal_cron - cronjob:pages_domain_removal_cron
- cronjob:pages_domain_ssl_renewal_cron - cronjob:pages_domain_ssl_renewal_cron
- cronjob:pages_domain_verification_cron
- cronjob:personal_access_tokens_expiring - cronjob:personal_access_tokens_expiring
- cronjob:pipeline_schedule - cronjob:pipeline_schedule
- cronjob:prune_old_events - cronjob:prune_old_events
- cronjob:prune_web_hook_logs
- cronjob:remove_expired_group_links - cronjob:remove_expired_group_links
- cronjob:remove_expired_members - cronjob:remove_expired_members
- cronjob:remove_unreferenced_lfs_objects - cronjob:remove_unreferenced_lfs_objects
- cronjob:repository_archive_cache - cronjob:repository_archive_cache
- cronjob:repository_check_dispatch - cronjob:repository_check_dispatch
- cronjob:requests_profiles - cronjob:requests_profiles
- cronjob:schedule_migrate_external_diffs
- cronjob:stuck_ci_jobs - cronjob:stuck_ci_jobs
- cronjob:stuck_import_jobs - cronjob:stuck_import_jobs
- cronjob:stuck_merge_jobs - cronjob:stuck_merge_jobs
- cronjob:ci_archive_traces_cron
- cronjob:trending_projects - cronjob:trending_projects
- cronjob:issue_due_scheduler - deployment:deployments_finished
- cronjob:prune_web_hook_logs - deployment:deployments_success
- cronjob:schedule_migrate_external_diffs - gcp_cluster:cluster_configure
- cronjob:namespaces_prune_aggregation_schedules
- gcp_cluster:cluster_install_app - gcp_cluster:cluster_install_app
- gcp_cluster:cluster_patch_app - gcp_cluster:cluster_patch_app
- gcp_cluster:cluster_upgrade_app - gcp_cluster:cluster_project_configure
- gcp_cluster:cluster_provision - gcp_cluster:cluster_provision
- gcp_cluster:clusters_cleanup_app - gcp_cluster:cluster_upgrade_app
- gcp_cluster:clusters_cleanup_project_namespace
- gcp_cluster:clusters_cleanup_service_account
- gcp_cluster:cluster_wait_for_app_installation - gcp_cluster:cluster_wait_for_app_installation
- gcp_cluster:wait_for_cluster_creation
- gcp_cluster:cluster_wait_for_ingress_ip_address - gcp_cluster:cluster_wait_for_ingress_ip_address
- gcp_cluster:cluster_configure - gcp_cluster:clusters_applications_activate_service
- gcp_cluster:cluster_project_configure - gcp_cluster:clusters_applications_deactivate_service
- gcp_cluster:clusters_applications_wait_for_uninstall_app
- gcp_cluster:clusters_applications_uninstall - gcp_cluster:clusters_applications_uninstall
- gcp_cluster:clusters_applications_wait_for_uninstall_app
- gcp_cluster:clusters_cleanup_app - gcp_cluster:clusters_cleanup_app
- gcp_cluster:clusters_cleanup_project_namespace - gcp_cluster:clusters_cleanup_project_namespace
- gcp_cluster:clusters_cleanup_service_account - gcp_cluster:clusters_cleanup_service_account
- gcp_cluster:clusters_applications_activate_service - gcp_cluster:wait_for_cluster_creation
- gcp_cluster:clusters_applications_deactivate_service
- github_import_advance_stage
- github_importer:github_import_import_diff_note - github_importer:github_import_import_diff_note
- github_importer:github_import_import_issue - github_importer:github_import_import_issue
- github_importer:github_import_import_note
- github_importer:github_import_import_lfs_object - github_importer:github_import_import_lfs_object
- github_importer:github_import_import_note
- github_importer:github_import_import_pull_request - github_importer:github_import_import_pull_request
- github_importer:github_import_refresh_import_jid - github_importer:github_import_refresh_import_jid
- github_importer:github_import_stage_finish_import - github_importer:github_import_stage_finish_import
- github_importer:github_import_stage_import_base_data - github_importer:github_import_stage_import_base_data
- github_importer:github_import_stage_import_issues_and_diff_notes - github_importer:github_import_stage_import_issues_and_diff_notes
- github_importer:github_import_stage_import_notes
- github_importer:github_import_stage_import_lfs_objects - github_importer:github_import_stage_import_lfs_objects
- github_importer:github_import_stage_import_notes
- github_importer:github_import_stage_import_pull_requests - github_importer:github_import_stage_import_pull_requests
- github_importer:github_import_stage_import_repository - github_importer:github_import_stage_import_repository
- hashed_storage:hashed_storage_migrator - hashed_storage:hashed_storage_migrator
- hashed_storage:hashed_storage_rollbacker
- hashed_storage:hashed_storage_project_migrate - hashed_storage:hashed_storage_project_migrate
- hashed_storage:hashed_storage_project_rollback - hashed_storage:hashed_storage_project_rollback
- hashed_storage:hashed_storage_rollbacker
- mail_scheduler:mail_scheduler_issue_due - mail_scheduler:mail_scheduler_issue_due
- mail_scheduler:mail_scheduler_notification_service - mail_scheduler:mail_scheduler_notification_service
- notifications:new_release
- object_pool:object_pool_create
- object_pool:object_pool_destroy
- object_pool:object_pool_join
- object_pool:object_pool_schedule_join
- object_storage:object_storage_background_move - object_storage:object_storage_background_move
- object_storage:object_storage_migrate_uploads - object_storage:object_storage_migrate_uploads
- pipeline_background:archive_trace
- pipeline_background:ci_build_trace_chunk_flush
- pipeline_cache:expire_job_cache - pipeline_cache:expire_job_cache
- pipeline_cache:expire_pipeline_cache - pipeline_cache:expire_pipeline_cache
- pipeline_creation:create_pipeline - pipeline_creation:create_pipeline
- pipeline_creation:run_pipeline_schedule - pipeline_creation:run_pipeline_schedule
- pipeline_background:archive_trace
- pipeline_background:ci_build_trace_chunk_flush
- pipeline_default:build_coverage - pipeline_default:build_coverage
- pipeline_default:build_trace_sections - pipeline_default:build_trace_sections
- pipeline_default:pipeline_metrics - pipeline_default:pipeline_metrics
...@@ -95,74 +95,67 @@ ...@@ -95,74 +95,67 @@
- pipeline_hooks:build_hooks - pipeline_hooks:build_hooks
- pipeline_hooks:pipeline_hooks - pipeline_hooks:pipeline_hooks
- pipeline_processing:build_finished - pipeline_processing:build_finished
- pipeline_processing:ci_build_prepare
- pipeline_processing:build_queue - pipeline_processing:build_queue
- pipeline_processing:build_success - pipeline_processing:build_success
- pipeline_processing:ci_build_prepare
- pipeline_processing:ci_build_schedule
- pipeline_processing:ci_resource_groups_assign_resource_from_resource_group
- pipeline_processing:pipeline_process - pipeline_processing:pipeline_process
- pipeline_processing:pipeline_success - pipeline_processing:pipeline_success
- pipeline_processing:pipeline_update - pipeline_processing:pipeline_update
- pipeline_processing:stage_update - pipeline_processing:stage_update
- pipeline_processing:update_head_pipeline_for_merge_request - pipeline_processing:update_head_pipeline_for_merge_request
- pipeline_processing:ci_build_schedule
- pipeline_processing:ci_resource_groups_assign_resource_from_resource_group
- deployment:deployments_success
- deployment:deployments_finished
- repository_check:repository_check_clear
- repository_check:repository_check_batch - repository_check:repository_check_batch
- repository_check:repository_check_clear
- repository_check:repository_check_single_repository - repository_check:repository_check_single_repository
- todos_destroyer:todos_destroyer_confidential_issue - todos_destroyer:todos_destroyer_confidential_issue
- todos_destroyer:todos_destroyer_entity_leave - todos_destroyer:todos_destroyer_entity_leave
- todos_destroyer:todos_destroyer_group_private - todos_destroyer:todos_destroyer_group_private
- todos_destroyer:todos_destroyer_project_private
- todos_destroyer:todos_destroyer_private_features - todos_destroyer:todos_destroyer_private_features
- todos_destroyer:todos_destroyer_project_private
- update_namespace_statistics:namespaces_schedule_aggregation
- update_namespace_statistics:namespaces_root_statistics - update_namespace_statistics:namespaces_root_statistics
- update_namespace_statistics:namespaces_schedule_aggregation
- object_pool:object_pool_create
- object_pool:object_pool_schedule_join
- object_pool:object_pool_join
- object_pool:object_pool_destroy
- container_repository:delete_container_repository
- container_repository:cleanup_container_repository
- notifications:new_release
- default
- mailers # ActionMailer::DeliveryJob.queue_name
- authorized_projects - authorized_projects
- background_migration - background_migration
- chat_notification - chat_notification
- create_evidence
- create_gpg_signature - create_gpg_signature
- create_note_diff_file
- default
- delete_diff_files
- delete_merged_branches - delete_merged_branches
- delete_stored_files
- delete_user - delete_user
- detect_repository_languages
- email_receiver - email_receiver
- emails_on_push - emails_on_push
- error_tracking_issue_link - error_tracking_issue_link
- expire_build_instance_artifacts - expire_build_instance_artifacts
- file_hook
- git_garbage_collect - git_garbage_collect
- github_import_advance_stage
- gitlab_shell - gitlab_shell
- group_destroy - group_destroy
- group_export
- import_issues_csv
- invalid_gpg_signature_update - invalid_gpg_signature_update
- irker - irker
- mailers
- merge - merge
- merge_request_mergeability_check
- migrate_external_diffs - migrate_external_diffs
- namespaceless_project_destroy - namespaceless_project_destroy
- new_issue - new_issue
- new_merge_request - new_merge_request
- new_note - new_note
- pages - pages
- pages_domain_verification
- pages_domain_ssl_renewal - pages_domain_ssl_renewal
- file_hook - pages_domain_verification
- phabricator_import_import_tasks
- post_receive - post_receive
- process_commit - process_commit
- project_cache - project_cache
- project_daily_statistics
- project_destroy - project_destroy
- project_export - project_export
- project_service - project_service
...@@ -170,26 +163,16 @@ ...@@ -170,26 +163,16 @@
- reactive_caching - reactive_caching
- rebase - rebase
- remote_mirror_notification - remote_mirror_notification
- repository_cleanup
- repository_fork - repository_fork
- repository_import - repository_import
- repository_remove_remote - repository_remove_remote
- repository_update_remote_mirror
- self_monitoring_project_create
- self_monitoring_project_delete
- system_hook_push - system_hook_push
- update_external_pull_requests - update_external_pull_requests
- update_merge_requests - update_merge_requests
- update_project_statistics - update_project_statistics
- upload_checksum - upload_checksum
- web_hook - web_hook
- repository_update_remote_mirror
- create_note_diff_file
- delete_diff_files
- detect_repository_languages
- repository_cleanup
- delete_stored_files
- import_issues_csv
- project_daily_statistics
- create_evidence
- group_export
- self_monitoring_project_create
- self_monitoring_project_delete
- merge_request_mergeability_check
- phabricator_import_import_tasks
...@@ -268,8 +268,9 @@ default value can be found in `/opt/gitlab/etc/gitlab-rails/env/RAILS_ENV`. ...@@ -268,8 +268,9 @@ default value can be found in `/opt/gitlab/etc/gitlab-rails/env/RAILS_ENV`.
### Using negation ### Using negation
You're able to run all queues in `sidekiq_queues.yml` file on a single or You're able to run all queues in the `all_queues.yml` file (or the equivalent EE
multiple processes with exceptions using the `--negate` flag. file) on a single or multiple processes with exceptions using the `--negate`
flag.
For example, say you want to run a single process for all queues, For example, say you want to run a single process for all queues,
except `process_commit` and `post_receive`: except `process_commit` and `post_receive`:
......
...@@ -17,8 +17,11 @@ would be `process_something`. If you're not sure what queue a worker uses, ...@@ -17,8 +17,11 @@ would be `process_something`. If you're not sure what queue a worker uses,
you can find it using `SomeWorker.queue`. There is almost never a reason to you can find it using `SomeWorker.queue`. There is almost never a reason to
manually override the queue name using `sidekiq_options queue: :some_queue`. manually override the queue name using `sidekiq_options queue: :some_queue`.
You must always add any new queues to `app/workers/all_queues.yml` or `ee/app/workers/all_queues.yml` After adding a new queue, run `bin/rake
otherwise your worker will not run. gitlab:sidekiq:all_queues_yml:generate` to regenerate
`app/workers/all_queues.yml` or `ee/app/workers/all_queues.yml` so that
it can be picked up by
[`sidekiq-cluster`](../administration/operations/extra_sidekiq_processes.md).
## Queue Namespaces ## Queue Namespaces
......
# This file is generated automatically by
# bin/rake gitlab:sidekiq:all_queues_yml:generate
#
# Do not edit it manually!
--- ---
- cronjob:adjourned_group_deletion - cronjob:adjourned_group_deletion
- cronjob:adjourned_projects_deletion_cron
- cronjob:clear_shared_runners_minutes - cronjob:clear_shared_runners_minutes
- cronjob:geo_container_repository_sync_dispatch
- cronjob:geo_file_download_dispatch - cronjob:geo_file_download_dispatch
- cronjob:geo_metrics_update - cronjob:geo_metrics_update
- cronjob:geo_prune_event_log
- cronjob:geo_migrated_local_files_clean_up - cronjob:geo_migrated_local_files_clean_up
- cronjob:geo_prune_event_log
- cronjob:geo_repository_sync - cronjob:geo_repository_sync
- cronjob:geo_repository_verification_primary_batch - cronjob:geo_repository_verification_primary_batch
- cronjob:geo_repository_verification_secondary_scheduler - cronjob:geo_repository_verification_secondary_scheduler
- cronjob:geo_sidekiq_cron_config - cronjob:geo_repository_verification_secondary_shard
- cronjob:geo_scheduler_per_shard_scheduler - cronjob:geo_scheduler_per_shard_scheduler
- cronjob:geo_scheduler_primary_per_shard_scheduler - cronjob:geo_scheduler_primary_per_shard_scheduler
- cronjob:geo_scheduler_secondary_per_shard_scheduler - cronjob:geo_scheduler_secondary_per_shard_scheduler
- cronjob:geo_repository_verification_secondary_shard - cronjob:geo_sidekiq_cron_config
- cronjob:geo_container_repository_sync_dispatch
- cronjob:historical_data - cronjob:historical_data
- cronjob:import_software_licenses - cronjob:import_software_licenses
- cronjob:ldap_all_groups_sync - cronjob:ldap_all_groups_sync
- cronjob:ldap_sync - cronjob:ldap_sync
- cronjob:update_all_mirrors
- cronjob:pseudonymizer - cronjob:pseudonymizer
- cronjob:update_all_mirrors
- cronjob:update_max_seats_used_for_gitlab_com_subscriptions - cronjob:update_max_seats_used_for_gitlab_com_subscriptions
- cronjob:adjourned_projects_deletion_cron - epics:epics_update_epics_dates
- gcp_cluster:cluster_update_app - gcp_cluster:cluster_update_app
- gcp_cluster:cluster_wait_for_app_update - gcp_cluster:cluster_wait_for_app_update
- geo:geo_batch_project_registry - geo:geo_batch_project_registry
- geo:geo_batch_project_registry_scheduler - geo:geo_batch_project_registry_scheduler
- geo:geo_container_repository_sync
- geo:geo_design_repository_shard_sync
- geo:geo_design_repository_sync
- geo:geo_file_download - geo:geo_file_download
- geo:geo_file_removal
- geo:geo_file_registry_removal - geo:geo_file_registry_removal
- geo:geo_file_removal
- geo:geo_hashed_storage_attachments_migration - geo:geo_hashed_storage_attachments_migration
- geo:geo_hashed_storage_migration - geo:geo_hashed_storage_migration
- geo:geo_project_sync - geo:geo_project_sync
- geo:geo_container_repository_sync
- geo:geo_design_repository_sync
- geo:geo_rename_repository - geo:geo_rename_repository
- geo:geo_secondary_repository_backfill
- geo:geo_repositories_clean_up - geo:geo_repositories_clean_up
- geo:geo_repository_cleanup - geo:geo_repository_cleanup
- geo:geo_repository_destroy - geo:geo_repository_destroy
- geo:geo_repository_shard_sync - geo:geo_repository_shard_sync
- geo:geo_design_repository_shard_sync
- geo:geo_repository_verification_primary_shard - geo:geo_repository_verification_primary_shard
- geo:geo_repository_verification_primary_single - geo:geo_repository_verification_primary_single
- geo:geo_repository_verification_secondary_single - geo:geo_repository_verification_secondary_single
- geo:geo_scheduler_scheduler
- geo:geo_scheduler_primary_scheduler - geo:geo_scheduler_primary_scheduler
- geo:geo_scheduler_scheduler
- geo:geo_scheduler_secondary_scheduler - geo:geo_scheduler_secondary_scheduler
- geo:geo_secondary_repository_backfill
- pipeline_default:store_security_reports
- pipeline_default:sync_security_reports_to_report_approval_rules
- pipeline_default:ci_create_cross_project_pipeline
- pipeline_default:ci_pipeline_bridge_status
- incident_management:incident_management_process_alert - incident_management:incident_management_process_alert
- incident_management:incident_management_process_prometheus_alert - incident_management:incident_management_process_prometheus_alert
- jira_connect:jira_connect_sync_branch - jira_connect:jira_connect_sync_branch
- jira_connect:jira_connect_sync_merge_request - jira_connect:jira_connect_sync_merge_request
- personal_access_tokens:personal_access_tokens_policy - personal_access_tokens:personal_access_tokens_policy
- pipeline_default:ci_create_cross_project_pipeline
- pipeline_default:ci_pipeline_bridge_status
- pipeline_default:store_security_reports
- pipeline_default:sync_security_reports_to_report_approval_rules
- adjourned_project_deletion
- admin_emails - admin_emails
- create_github_webhook - create_github_webhook
- design_management_new_version - design_management_new_version
- elastic_batch_project_indexer - elastic_batch_project_indexer
- elastic_namespace_indexer
- elastic_commit_indexer - elastic_commit_indexer
- elastic_indexer
- elastic_full_index - elastic_full_index
- elastic_indexer
- elastic_namespace_indexer
- elastic_namespace_rollout - elastic_namespace_rollout
- export_csv - export_csv
- ldap_group_sync - ldap_group_sync
- new_epic - new_epic
- project_import_schedule - project_import_schedule
- project_update_repository_storage - project_update_repository_storage
- adjourned_project_deletion
- rebase
- refresh_license_compliance_checks - refresh_license_compliance_checks
- repository_update_mirror
- repository_push_audit_event - repository_push_audit_event
- epics:epics_update_epics_dates - repository_update_mirror
...@@ -5,10 +5,10 @@ require 'spec_helper' ...@@ -5,10 +5,10 @@ require 'spec_helper'
describe Gitlab::SidekiqConfig do describe Gitlab::SidekiqConfig do
describe '.workers' do describe '.workers' do
it 'includes EE workers' do it 'includes EE workers' do
workers = described_class.workers worker_classes = described_class.workers.map(&:klass)
expect(workers).to include(RepositoryUpdateMirrorWorker) expect(worker_classes).to include(RepositoryUpdateMirrorWorker)
expect(workers).to include(LdapGroupSyncWorker) expect(worker_classes).to include(LdapGroupSyncWorker)
end end
end end
...@@ -41,4 +41,42 @@ describe Gitlab::SidekiqConfig do ...@@ -41,4 +41,42 @@ describe Gitlab::SidekiqConfig do
expect(queues).to include('unknown') expect(queues).to include('unknown')
end end
end end
describe '.workers_for_all_queues_yml' do
it 'returns a tuple with EE workers second' do
expect(described_class.workers_for_all_queues_yml.second)
.to include(an_object_having_attributes(queue: 'repository_update_mirror'))
end
end
describe '.all_queues_yml_outdated?' do
before do
workers = [
LdapGroupSyncWorker,
RepositoryUpdateMirrorWorker
].map { |worker| described_class::Worker.new(worker, ee: true) }
allow(described_class).to receive(:workers).and_return(workers)
allow(File).to receive(:read)
.with(described_class::FOSS_QUEUE_CONFIG_PATH)
.and_return(YAML.dump([]))
end
it 'returns true if the YAML file does not match the application code' do
allow(File).to receive(:read)
.with(described_class::EE_QUEUE_CONFIG_PATH)
.and_return(YAML.dump(['ldap_group_sync']))
expect(described_class.all_queues_yml_outdated?).to be(true)
end
it 'returns false if the YAML file matches the application code' do
allow(File).to receive(:read)
.with(described_class::EE_QUEUE_CONFIG_PATH)
.and_return(YAML.dump(%w[ldap_group_sync repository_update_mirror]))
expect(described_class.all_queues_yml_outdated?).to be(false)
end
end
end end
...@@ -4,6 +4,22 @@ require 'yaml' ...@@ -4,6 +4,22 @@ require 'yaml'
module Gitlab module Gitlab
module SidekiqConfig module SidekiqConfig
FOSS_QUEUE_CONFIG_PATH = 'app/workers/all_queues.yml'
EE_QUEUE_CONFIG_PATH = 'ee/app/workers/all_queues.yml'
QUEUE_CONFIG_PATHS = [
FOSS_QUEUE_CONFIG_PATH,
(EE_QUEUE_CONFIG_PATH if Gitlab.ee?)
].compact.freeze
# For queues that don't have explicit workers - default and mailers
DummyWorker = Struct.new(:queue)
DEFAULT_WORKERS = [
Gitlab::SidekiqConfig::Worker.new(DummyWorker.new('default'), ee: false),
Gitlab::SidekiqConfig::Worker.new(DummyWorker.new('mailers'), ee: false)
].freeze
class << self class << self
include Gitlab::SidekiqConfig::CliMethods include Gitlab::SidekiqConfig::CliMethods
...@@ -25,29 +41,47 @@ module Gitlab ...@@ -25,29 +41,47 @@ module Gitlab
def workers def workers
@workers ||= begin @workers ||= begin
result = find_workers(Rails.root.join('app', 'workers')) result = []
result.concat(find_workers(Rails.root.join('ee', 'app', 'workers'))) if Gitlab.ee? result.concat(DEFAULT_WORKERS)
result.concat(find_workers(Rails.root.join('app', 'workers'), ee: false))
if Gitlab.ee?
result.concat(find_workers(Rails.root.join('ee', 'app', 'workers'), ee: true))
end
result result
end end
end end
def workers_for_all_queues_yml
workers.partition(&:ee?).reverse.map(&:sort)
end
def all_queues_yml_outdated?
foss_workers, ee_workers = workers_for_all_queues_yml
return true if foss_workers != YAML.safe_load(File.read(FOSS_QUEUE_CONFIG_PATH))
Gitlab.ee? && ee_workers != YAML.safe_load(File.read(EE_QUEUE_CONFIG_PATH))
end
private private
def find_workers(root) def find_workers(root, ee:)
concerns = root.join('concerns').to_s concerns = root.join('concerns').to_s
workers = Dir[root.join('**', '*.rb')] Dir[root.join('**', '*.rb')]
.reject { |path| path.start_with?(concerns) } .reject { |path| path.start_with?(concerns) }
.map { |path| worker_from_path(path, root) }
.select { |worker| worker < Sidekiq::Worker }
.map { |worker| Gitlab::SidekiqConfig::Worker.new(worker, ee: ee) }
end
workers.map! do |path| def worker_from_path(path, root)
ns = Pathname.new(path).relative_path_from(root).to_s.gsub('.rb', '') ns = Pathname.new(path).relative_path_from(root).to_s.gsub('.rb', '')
ns.camelize.constantize ns.camelize.constantize
end end
# Skip things that aren't workers
workers.select { |w| w < Sidekiq::Worker }
end
end end
end end
end end
# frozen_string_literal: true
module Gitlab
module SidekiqConfig
class Worker
include Comparable
attr_reader :klass
delegate :feature_category_not_owned?, :get_feature_category,
:get_worker_resource_boundary, :latency_sensitive_worker?,
:queue, :worker_has_external_dependencies?,
to: :klass
def initialize(klass, ee:)
@klass = klass
@ee = ee
end
def ee?
@ee
end
def ==(other)
to_yaml == case other
when self.class
other.to_yaml
else
other
end
end
def <=>(other)
to_sort <=> other.to_sort
end
# Put namespaced queues first
def to_sort
[queue.include?(':') ? 0 : 1, queue]
end
# YAML representation
def encode_with(coder)
coder.represent_scalar(nil, to_yaml)
end
def to_yaml
queue
end
end
end
end
# frozen_string_literal: true
return if Rails.env.production?
namespace :gitlab do
namespace :sidekiq do
namespace :all_queues_yml do
def write_yaml(path, object)
banner = <<~BANNER
# This file is generated automatically by
# bin/rake gitlab:sidekiq:all_queues_yml:generate
#
# Do not edit it manually!
BANNER
File.write(path, banner + YAML.dump(object))
end
desc 'GitLab | Generate all_queues.yml based on worker definitions'
task generate: :environment do
foss_workers, ee_workers = Gitlab::SidekiqConfig.workers_for_all_queues_yml
write_yaml(Gitlab::SidekiqConfig::FOSS_QUEUE_CONFIG_PATH, foss_workers)
if Gitlab.ee?
write_yaml(Gitlab::SidekiqConfig::EE_QUEUE_CONFIG_PATH, ee_workers)
end
end
desc 'GitLab | Validate that all_queues.yml matches worker definitions'
task check: :environment do
if Gitlab::SidekiqConfig.all_queues_yml_outdated?
raise <<~MSG
Changes in worker queues found, please update the metadata by running:
bin/rake gitlab:sidekiq:all_queues_yml:generate
Then commit and push the changes from:
- #{Gitlab::SidekiqConfig::FOSS_QUEUE_CONFIG_PATH}
- #{Gitlab::SidekiqConfig::EE_QUEUE_CONFIG_PATH}
MSG
end
end
end
end
end
...@@ -34,6 +34,7 @@ unless Rails.env.production? ...@@ -34,6 +34,7 @@ unless Rails.env.production?
scss_lint scss_lint
gettext:lint gettext:lint
lint:static_verification lint:static_verification
gitlab:sidekiq:all_queues_yml:check
] ]
if Gitlab.ee? if Gitlab.ee?
......
# frozen_string_literal: true
require 'fast_spec_helper'
describe Gitlab::SidekiqConfig::Worker do
def worker_with_queue(queue)
described_class.new(double(queue: queue), ee: false)
end
describe '#ee?' do
it 'returns the EE status set on creation' do
expect(described_class.new(double, ee: true)).to be_ee
expect(described_class.new(double, ee: false)).not_to be_ee
end
end
describe '#==' do
def worker_with_yaml(yaml)
described_class.new(double, ee: false).tap do |worker|
allow(worker).to receive(:to_yaml).and_return(yaml)
end
end
it 'defines two workers as equal if their YAML representations are equal' do
expect(worker_with_yaml('a')).to eq(worker_with_yaml('a'))
expect(worker_with_yaml('a')).not_to eq(worker_with_yaml('b'))
end
it 'returns true when a worker is compared with its YAML representation' do
expect(worker_with_yaml('a')).to eq('a')
expect(worker_with_yaml(a: 1, b: 2)).to eq(a: 1, b: 2)
end
end
describe 'delegations' do
[
:feature_category_not_owned?, :get_feature_category,
:get_worker_resource_boundary, :latency_sensitive_worker?, :queue,
:worker_has_external_dependencies?
].each do |meth|
it "delegates #{meth} to the worker class" do
worker = double
expect(worker).to receive(meth)
described_class.new(worker, ee: false).send(meth)
end
end
end
describe 'sorting' do
it 'sorts queues with a namespace before those without a namespace' do
namespaced_worker = worker_with_queue('namespace:queue')
plain_worker = worker_with_queue('a_queue')
expect([plain_worker, namespaced_worker].sort)
.to eq([namespaced_worker, plain_worker])
end
it 'sorts alphabetically by queue' do
workers = [
worker_with_queue('namespace:a'),
worker_with_queue('namespace:b'),
worker_with_queue('other_namespace:a'),
worker_with_queue('other_namespace:b'),
worker_with_queue('a'),
worker_with_queue('b')
]
expect(workers.shuffle.sort).to eq(workers)
end
end
describe 'YAML encoding' do
it 'encodes the worker in YAML as a string of the queue' do
worker_a = worker_with_queue('a')
worker_b = worker_with_queue('b')
expect(YAML.dump(worker_a)).to eq(YAML.dump('a'))
expect(YAML.dump([worker_a, worker_b]))
.to eq(YAML.dump(%w[a b]))
end
end
end
...@@ -5,10 +5,10 @@ require 'spec_helper' ...@@ -5,10 +5,10 @@ require 'spec_helper'
describe Gitlab::SidekiqConfig do describe Gitlab::SidekiqConfig do
describe '.workers' do describe '.workers' do
it 'includes all workers' do it 'includes all workers' do
workers = described_class.workers worker_classes = described_class.workers.map(&:klass)
expect(workers).to include(PostReceive) expect(worker_classes).to include(PostReceive)
expect(workers).to include(MergeWorker) expect(worker_classes).to include(MergeWorker)
end end
end end
...@@ -44,4 +44,40 @@ describe Gitlab::SidekiqConfig do ...@@ -44,4 +44,40 @@ describe Gitlab::SidekiqConfig do
expect(queues).to include('unknown') expect(queues).to include('unknown')
end end
end end
describe '.workers_for_all_queues_yml' do
it 'returns a tuple with FOSS workers first' do
expect(described_class.workers_for_all_queues_yml.first)
.to include(an_object_having_attributes(queue: 'post_receive'))
end
end
describe '.all_queues_yml_outdated?' do
before do
workers = [
PostReceive,
MergeWorker,
ProcessCommitWorker
].map { |worker| described_class::Worker.new(worker, ee: false) }
allow(described_class).to receive(:workers).and_return(workers)
allow(Gitlab).to receive(:ee?).and_return(false)
end
it 'returns true if the YAML file does not match the application code' do
allow(File).to receive(:read)
.with(described_class::FOSS_QUEUE_CONFIG_PATH)
.and_return(YAML.dump(%w[post_receive merge]))
expect(described_class.all_queues_yml_outdated?).to be(true)
end
it 'returns false if the YAML file matches the application code' do
allow(File).to receive(:read)
.with(described_class::FOSS_QUEUE_CONFIG_PATH)
.and_return(YAML.dump(%w[merge post_receive process_commit]))
expect(described_class.all_queues_yml_outdated?).to be(false)
end
end
end end
...@@ -3,8 +3,12 @@ ...@@ -3,8 +3,12 @@
require 'spec_helper' require 'spec_helper'
describe 'Every Sidekiq worker' do describe 'Every Sidekiq worker' do
let(:workers_without_defaults) do
Gitlab::SidekiqConfig.workers - Gitlab::SidekiqConfig::DEFAULT_WORKERS
end
it 'does not use the default queue' do it 'does not use the default queue' do
expect(Gitlab::SidekiqConfig.workers.map(&:queue)).not_to include('default') expect(workers_without_defaults.map(&:queue)).not_to include('default')
end end
it 'uses the cronjob queue when the worker runs as a cronjob' do it 'uses the cronjob queue when the worker runs as a cronjob' do
...@@ -45,7 +49,7 @@ describe 'Every Sidekiq worker' do ...@@ -45,7 +49,7 @@ describe 'Every Sidekiq worker' do
# or explicitly be excluded with the `feature_category_not_owned!` annotation. # or explicitly be excluded with the `feature_category_not_owned!` annotation.
# Please see doc/development/sidekiq_style_guide.md#Feature-Categorization for more details. # Please see doc/development/sidekiq_style_guide.md#Feature-Categorization for more details.
it 'has a feature_category or feature_category_not_owned! attribute', :aggregate_failures do it 'has a feature_category or feature_category_not_owned! attribute', :aggregate_failures do
Gitlab::SidekiqConfig.workers.each do |worker| workers_without_defaults.each do |worker|
expect(worker.get_feature_category).to be_a(Symbol), "expected #{worker.inspect} to declare a feature_category or feature_category_not_owned!" expect(worker.get_feature_category).to be_a(Symbol), "expected #{worker.inspect} to declare a feature_category or feature_category_not_owned!"
end end
end end
...@@ -54,7 +58,7 @@ describe 'Every Sidekiq worker' do ...@@ -54,7 +58,7 @@ describe 'Every Sidekiq worker' do
# The category should match a value in `config/feature_categories.yml`. # The category should match a value in `config/feature_categories.yml`.
# Please see doc/development/sidekiq_style_guide.md#Feature-Categorization for more details. # Please see doc/development/sidekiq_style_guide.md#Feature-Categorization for more details.
it 'has a feature_category that maps to a value in feature_categories.yml', :aggregate_failures do it 'has a feature_category that maps to a value in feature_categories.yml', :aggregate_failures do
workers_with_feature_categories = Gitlab::SidekiqConfig.workers workers_with_feature_categories = workers_without_defaults
.select(&:get_feature_category) .select(&:get_feature_category)
.reject(&:feature_category_not_owned?) .reject(&:feature_category_not_owned?)
...@@ -69,7 +73,7 @@ describe 'Every Sidekiq worker' do ...@@ -69,7 +73,7 @@ describe 'Every Sidekiq worker' do
# rather than scaling the hardware to meet the SLO. For this reason, memory-bound, # rather than scaling the hardware to meet the SLO. For this reason, memory-bound,
# latency-sensitive jobs are explicitly discouraged and disabled. # latency-sensitive jobs are explicitly discouraged and disabled.
it 'is (exclusively) memory-bound or latency-sentitive, not both', :aggregate_failures do it 'is (exclusively) memory-bound or latency-sentitive, not both', :aggregate_failures do
latency_sensitive_workers = Gitlab::SidekiqConfig.workers latency_sensitive_workers = workers_without_defaults
.select(&:latency_sensitive_worker?) .select(&:latency_sensitive_worker?)
latency_sensitive_workers.each do |worker| latency_sensitive_workers.each do |worker|
...@@ -86,7 +90,7 @@ describe 'Every Sidekiq worker' do ...@@ -86,7 +90,7 @@ describe 'Every Sidekiq worker' do
# Please see doc/development/sidekiq_style_guide.md#Jobs-with-External-Dependencies for more # Please see doc/development/sidekiq_style_guide.md#Jobs-with-External-Dependencies for more
# details. # details.
it 'has (exclusively) external dependencies or is latency-sentitive, not both', :aggregate_failures do it 'has (exclusively) external dependencies or is latency-sentitive, not both', :aggregate_failures do
latency_sensitive_workers = Gitlab::SidekiqConfig.workers latency_sensitive_workers = workers_without_defaults
.select(&:latency_sensitive_worker?) .select(&:latency_sensitive_worker?)
latency_sensitive_workers.each do |worker| latency_sensitive_workers.each do |worker|
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment