Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,11 @@ class AgentFactory
attr_reader :customizer, :container, :has_env_secret
attr_accessor :schema_only_mode

def initialize
super
@reloading = false
end

def setup(options)
@options = options
@has_env_secret = options.to_h.key?(:env_secret)
Expand Down Expand Up @@ -75,6 +80,14 @@ def generate_schema_only
end

def reload!
if @reloading
@logger.log('Info', 'Agent is already reloading. Do nothing.')
return
end

@reloading = true
@logger.log('Info', 'Agent is reloading...')

begin
@customizer.reload!(logger: @logger)
rescue StandardError => e
Expand All @@ -89,6 +102,8 @@ def reload!
@logger.log('Info', 'route cache cleared due to agent reload')

send_schema
ensure
@reloading = false
end

def send_schema(force: false)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -160,6 +160,64 @@ module Builder
expect(instance.container).not_to have_received(:register)
expect(instance).not_to have_received(:send_schema)
end

it 'skips reload if another reload is already in progress' do
instance = described_class.instance

logger = instance_spy(Services::LoggerService)
instance.instance_variable_set(:@logger, logger)

# Simulate a long-running reload by blocking inside customizer.reload!
reload_started = Queue.new
proceed = Queue.new

allow(instance.customizer).to receive(:reload!) do
reload_started << true
proceed.pop
end
allow(instance).to receive(:send_schema)

first_thread = Thread.new { instance.reload! }
reload_started.pop # wait until the first reload is inside customizer.reload!

# Second reload should be skipped
instance.reload!

expect(logger).to have_received(:log).with('Info', 'Agent is already reloading. Do nothing.')

proceed << true # unblock first reload
first_thread.join
end

it 'allows a new reload after the previous one completes' do
instance = described_class.instance

allow(instance.customizer).to receive(:reload!)
allow(instance).to receive(:send_schema)

instance.reload!
instance.reload!

expect(instance.customizer).to have_received(:reload!).twice
end

it 'resets the reloading flag even when an error occurs' do
instance = described_class.instance

logger = instance_spy(Services::LoggerService)
instance.instance_variable_set(:@logger, logger)

allow(instance.customizer).to receive(:reload!).and_raise(StandardError.new('Boom'))
allow(instance).to receive(:send_schema)

instance.reload!

# Should allow a subsequent reload (flag was reset despite the error)
allow(instance.customizer).to receive(:reload!)
instance.reload!

expect(instance.customizer).to have_received(:reload!).twice
end
end

describe 'send_schema' do
Expand Down
Loading