Add credentials to redis sentinel configuration (#31768)

This commit is contained in:
David Roetzel 2024-09-05 16:06:58 +02:00 committed by GitHub
parent b4b639ee4a
commit f85694acfd
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
2 changed files with 45 additions and 23 deletions

View file

@ -63,33 +63,44 @@ class Mastodon::RedisConfiguration
host = ENV.fetch("#{prefix}HOST", defaults[:host]) host = ENV.fetch("#{prefix}HOST", defaults[:host])
port = ENV.fetch("#{prefix}PORT", defaults[:port]) port = ENV.fetch("#{prefix}PORT", defaults[:port])
db = ENV.fetch("#{prefix}DB", defaults[:db]) db = ENV.fetch("#{prefix}DB", defaults[:db])
name = ENV.fetch("#{prefix}SENTINEL_MASTER", nil)
sentinel_port = ENV.fetch("#{prefix}SENTINEL_PORT", 26_379)
sentinel_list = ENV.fetch("#{prefix}SENTINELS", nil)
return { url:, driver: } if url return { url:, driver: } if url
sentinels = parse_sentinels(sentinel_list, default_port: sentinel_port) sentinel_options = setup_sentinels(prefix, default_user: user, default_password: password)
if name.present? && sentinels.present? if sentinel_options.present?
host = name host = sentinel_options[:name]
port = nil port = nil
db ||= 0 db ||= 0
else
sentinels = nil
end end
url = construct_uri(host, port, db, user, password) url = construct_uri(host, port, db, user, password)
if url.present? if url.present?
{ url:, driver:, name:, sentinels: } { url:, driver: }.merge(sentinel_options)
else else
# Fall back to base config. This has defaults for the URL # Fall back to base config, which has defaults for the URL
# so this cannot lead to an endless loop. # so this cannot lead to endless recursion.
base base
end end
end end
def setup_sentinels(prefix, default_user: nil, default_password: nil)
name = ENV.fetch("#{prefix}SENTINEL_MASTER", nil)
sentinel_port = ENV.fetch("#{prefix}SENTINEL_PORT", 26_379)
sentinel_list = ENV.fetch("#{prefix}SENTINELS", nil)
sentinel_username = ENV.fetch("#{prefix}SENTINEL_USERNAME", default_user)
sentinel_password = ENV.fetch("#{prefix}SENTINEL_PASSWORD", default_password)
sentinels = parse_sentinels(sentinel_list, default_port: sentinel_port)
if name.present? && sentinels.present?
{ name:, sentinels:, sentinel_username:, sentinel_password: }
else
{}
end
end
def construct_uri(host, port, db, user, password) def construct_uri(host, port, db, user, password)
return nil if host.blank? return nil if host.blank?

View file

@ -100,10 +100,27 @@ RSpec.describe Mastodon::RedisConfiguration do
expect(subject[:url]).to eq 'redis://:testpass1@mainsentinel/0' expect(subject[:url]).to eq 'redis://:testpass1@mainsentinel/0'
end end
it 'uses the redis password to authenticate with sentinels' do
expect(subject[:sentinel_password]).to eq 'testpass1'
end
it 'includes the sentinel master name and list of sentinels' do it 'includes the sentinel master name and list of sentinels' do
expect(subject[:name]).to eq 'mainsentinel' expect(subject[:name]).to eq 'mainsentinel'
expect(subject[:sentinels]).to contain_exactly({ host: '192.168.0.1', port: 3000 }, { host: '192.168.0.2', port: 4000 }) expect(subject[:sentinels]).to contain_exactly({ host: '192.168.0.1', port: 3000 }, { host: '192.168.0.2', port: 4000 })
end end
context "when giving dedicated credentials in `#{prefix}REDIS_SENTINEL_USERNAME` and `#{prefix}REDIS_SENTINEL_PASSWORD`" do
around do |example|
ClimateControl.modify "#{prefix}REDIS_SENTINEL_USERNAME": 'sentinel_user', "#{prefix}REDIS_SENTINEL_PASSWORD": 'sentinel_pass1' do
example.run
end
end
it 'uses the credential to authenticate with sentinels' do
expect(subject[:sentinel_username]).to eq 'sentinel_user'
expect(subject[:sentinel_password]).to eq 'sentinel_pass1'
end
end
end end
context 'when giving sentinels without port numbers' do context 'when giving sentinels without port numbers' do
@ -154,8 +171,6 @@ RSpec.describe Mastodon::RedisConfiguration do
url: 'redis://localhost:6379/0', url: 'redis://localhost:6379/0',
driver: :hiredis, driver: :hiredis,
namespace: nil, namespace: nil,
name: nil,
sentinels: nil,
}) })
end end
end end
@ -188,8 +203,6 @@ RSpec.describe Mastodon::RedisConfiguration do
url: 'redis://:testpass@redis.example.com:3333/3', url: 'redis://:testpass@redis.example.com:3333/3',
driver: :hiredis, driver: :hiredis,
namespace: nil, namespace: nil,
name: nil,
sentinels: nil,
}) })
end end
end end
@ -218,8 +231,6 @@ RSpec.describe Mastodon::RedisConfiguration do
namespace: 'cache', namespace: 'cache',
expires_in: 10.minutes, expires_in: 10.minutes,
connect_timeout: 5, connect_timeout: 5,
name: nil,
sentinels: nil,
pool: { pool: {
size: 5, size: 5,
timeout: 5, timeout: 5,