Created
December 12, 2018 11:36
-
-
Save marzdgzmn/fe94064b777c084aa4ef0284f0a46290 to your computer and use it in GitHub Desktop.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
require 'rise/mirror_manager/sync' | |
require 'ostruct' | |
require 'pry' | |
require 'tmpdir' | |
require 'tempfile' | |
Sync = Rise::MirrorManager::Sync | |
SyncStatus = Rise::MirrorManager::SyncStatus | |
SyncLog = Rise::MirrorManager::Logging::SyncLog | |
Error = Rise::MirrorManager::Error | |
DB = Rise::MirrorManager::Database | |
tmp_dir = Dir.mktmpdir | |
RSpec.describe Rise::MirrorManager::Sync do | |
after(:all) do | |
FileUtils.rm_rf(tmp_dir) if File.exist?(tmp_dir) | |
end | |
# subject { described_class.new(mirror: mirror) } | |
describe '.run' do | |
remote_source = 'rsync://rise.ph' | |
rsync_opts = '-r -i -s -e' | |
rsync_delete_opts = '-d -d -d' | |
mirror = OpenStruct.new(name: 'dummy_mirror', | |
local_dir: tmp_dir, | |
pre_cmd: true, remote_source: remote_source, | |
rsync_opts: rsync_opts, | |
rsync_delete_opts: rsync_delete_opts) | |
let(:sync) { Sync.new(mirror) } | |
let(:logger) { double(SyncLog, log_info: nil, log_warn: nil, log_error: nil) } | |
before(:each) do | |
allow(SyncLog).to receive(:new).and_return(logger) | |
allow(Sync).to receive(:new).with(mirror).and_return(sync) | |
end | |
context 'when establishing a lock' do | |
lock_file = File.join(mirror.local_dir, "#{mirror.name}.lock") | |
it 'should create a lock file' do | |
allow(sync).to receive(:sync) | |
expect(File).to receive(:open).with(lock_file, File::RDWR | File::CREAT, 0o644) | |
Sync.run(mirror) | |
end | |
context 'when trying to establish a lock when a lock file already exists' do | |
before(:each) do | |
File.open(lock_file, File::RDWR | File::CREAT) do |f| | |
f.write(5) | |
f.flush | |
end | |
end | |
it 'should create a new one if the corresponding process for the existing lock file does not exist' do | |
allow(Process).to receive(:kill).with(0, 5).and_raise Errno::ESRCH | |
expect(File).to receive(:delete).with(lock_file).twice # twice == delete existing lock file + release_lock | |
expect(File).to receive(:open).with(lock_file, File::RDWR | File::CREAT, 0o644) | |
allow(sync).to receive(:sync) | |
sync.run | |
end | |
it 'should log an error and exit if app does not have privilege to send signal to the process' do | |
allow(Process).to receive(:kill).and_raise Errno::EPERM | |
allow(sync).to receive(:exit).and_throw(:exit) | |
expect(logger).to receive(:log_error).with('No permission/privilege to send signal to process(5)') | |
expect { sync.run }.to throw_symbol :exit | |
end | |
it 'should log an error and exit if the corresponding process for the lock file is running' do | |
allow(Process).to receive(:kill) | |
allow(sync).to receive(:exit).and_throw(:exit) | |
expect(logger).to receive(:log_error).with('Cannot establish lock. Another process(5) is currently running and holding the lock.') | |
expect { sync.run }.to throw_symbol :exit | |
end | |
end | |
end | |
context 'when precmd fails' do | |
before(:each) { mirror.pre_cmd = "(echo 'pre_cmd error' >&2; exit 1)" } # simulate a failing error | |
it 'should update database sync status to FAILED' do | |
allow(sync).to receive(:exit).and_throw(:exit) | |
expect(sync).to receive(:update_precmd_result).with(mirror.name, SyncStatus::FAILED) | |
expect { sync.run }.to throw_symbol :exit | |
end | |
it 'should log the error' do | |
allow(sync).to receive(:exit).and_throw(:exit) | |
expect(logger).to receive(:log_error).with(/pre_cmd error/) | |
expect { sync.run }.to throw_symbol :exit | |
end | |
context 'when precmd fails and raises to Errno::ENOENT' do | |
before(:each) { mirror.pre_cmd = 'nonExistingCmd' } | |
it 'should update database sync status to FAILED' do | |
allow(sync).to receive(:exit).and_throw(:exit) | |
expect(sync).to receive(:update_precmd_result).with(mirror.name, SyncStatus::FAILED) | |
expect { sync.run }.to throw_symbol :exit | |
end | |
it 'it should log the error' do | |
allow(sync).to receive(:exit).and_throw(:exit) | |
expect(logger).to receive(:log_error).with(/No such file or directory - nonExistingCmd/) | |
expect { sync.run }.to throw_symbol :exit | |
end | |
end | |
end | |
context 'when running sync' do | |
context 'when syncing fails' do | |
it 'should update database sync status to FAILED' do | |
puts sync.inspect | |
result = OpenStruct.new(output: 'failed rsync', success?: false) | |
allow(Marz::Rsync).to receive(:run).with(remote_source, tmp_dir, (rsync_opts + ' ' + rsync_delete_opts).split).and_yield(result) | |
allow(sync).to receive(:exit).and_throw(:exit) | |
expect(sync).to receive(:update_sync_result).with(SyncStatus::FAILED) | |
expect { sync.run }.to throw_symbol :exit | |
end | |
it 'should log sync error' do | |
result = OpenStruct.new(output: 'failed rsync', success?: false) | |
allow(Marz::Rsync).to receive(:run).with(remote_source, tmp_dir, (rsync_opts + ' ' + rsync_delete_opts).split).and_yield(result) | |
allow(sync).to receive(:exit).and_throw(:exit) | |
expect(logger). to receive(:log_error).with('failed rsync') | |
expect { sync.run }.to throw_symbol :exit | |
end |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment