mina 1.2.3 → 1.2.5

Sign up to get free protection for your applications and to get access to all the features.
Files changed (125) hide show
  1. checksums.yaml +5 -5
  2. data/.github/workflows/ci.yml +26 -0
  3. data/.gitignore +0 -1
  4. data/.rspec +1 -1
  5. data/.rubocop.yml +28 -1126
  6. data/CHANGELOG.md +126 -3
  7. data/Gemfile +2 -0
  8. data/Gemfile.lock +73 -0
  9. data/Rakefile +2 -0
  10. data/Readme.md +8 -12
  11. data/bin/mina +2 -0
  12. data/data/deploy.rb +10 -6
  13. data/docs/3rd_party_plugins.md +3 -0
  14. data/docs/assets/images/mina.png +0 -0
  15. data/docs/cookbook.md +1 -1
  16. data/docs/default_plugins.md +5 -5
  17. data/docs/how_mina_works.md +3 -3
  18. data/lib/Minafile +1 -0
  19. data/lib/mina/application.rb +45 -35
  20. data/lib/mina/backend/local.rb +2 -0
  21. data/lib/mina/backend/remote.rb +3 -1
  22. data/lib/mina/commands.rb +10 -7
  23. data/lib/mina/configuration.rb +6 -3
  24. data/lib/mina/dsl.rb +2 -2
  25. data/lib/mina/helpers/internal.rb +9 -9
  26. data/lib/mina/helpers/output.rb +5 -3
  27. data/lib/mina/runner/exec.rb +2 -0
  28. data/lib/mina/runner/pretty.rb +25 -19
  29. data/lib/mina/runner/printer.rb +2 -0
  30. data/lib/mina/runner/system.rb +2 -0
  31. data/lib/mina/runner.rb +9 -10
  32. data/lib/mina/version.rb +3 -1
  33. data/lib/mina/windows_patches.rb +4 -2
  34. data/lib/mina.rb +4 -3
  35. data/mina.gemspec +8 -7
  36. data/spec/configs/default.rb +8 -0
  37. data/spec/configs/dsl.rb +55 -0
  38. data/spec/configs/e2e.rb +25 -0
  39. data/spec/e2e/docker-compose.yml +21 -0
  40. data/spec/e2e/e2e_run.sh +11 -0
  41. data/spec/e2e/e2e_spec.rb +35 -0
  42. data/spec/e2e/ssh +27 -0
  43. data/spec/e2e/ssh.pub +1 -0
  44. data/spec/lib/mina/application_spec.rb +94 -35
  45. data/spec/lib/mina/backend/local_spec.rb +5 -2
  46. data/spec/lib/mina/backend/remote_spec.rb +5 -3
  47. data/spec/lib/mina/commands_spec.rb +7 -7
  48. data/spec/lib/mina/configuration_spec.rb +63 -3
  49. data/spec/lib/mina/dsl_spec.rb +94 -0
  50. data/spec/lib/mina/helpers/internal_spec.rb +89 -11
  51. data/spec/lib/mina/helpers/output_spec.rb +13 -10
  52. data/spec/lib/mina/runner/exec_spec.rb +19 -0
  53. data/spec/lib/mina/runner/pretty_spec.rb +17 -0
  54. data/spec/lib/mina/runner/printer_spec.rb +19 -0
  55. data/spec/lib/mina/runner/system_spec.rb +19 -0
  56. data/spec/lib/mina/runner_spec.rb +6 -10
  57. data/spec/spec_helper.rb +33 -14
  58. data/spec/support/outputs/bundle_clean.txt +2 -2
  59. data/spec/support/outputs/chruby_with_env.txt +7 -0
  60. data/spec/support/outputs/chruby_without_env.txt +2 -0
  61. data/spec/support/outputs/debug_configuration_variables.txt +11 -0
  62. data/spec/support/outputs/dsl_deploy.txt +4 -0
  63. data/spec/support/outputs/dsl_in_path.txt +1 -0
  64. data/spec/support/outputs/dsl_local_run.txt +5 -0
  65. data/spec/support/outputs/dsl_on.txt +6 -0
  66. data/spec/support/outputs/dsl_remote_run.txt +5 -0
  67. data/spec/support/outputs/dsl_reset.txt +2 -0
  68. data/spec/support/outputs/e2e_deploy_after_setup.txt +1 -0
  69. data/spec/support/outputs/e2e_deploy_without_setup.txt +1 -0
  70. data/spec/support/outputs/e2e_setup.txt +1 -0
  71. data/spec/support/outputs/environment.txt +1 -0
  72. data/spec/support/outputs/git_clone.txt +1 -1
  73. data/spec/support/outputs/git_clone_commit.txt +1 -1
  74. data/spec/support/outputs/git_ensure_pushed.txt +15 -0
  75. data/spec/support/outputs/rails_assets_precompile_force_precompile.txt +2 -0
  76. data/spec/support/outputs/rails_assets_precompile_outside_deploy_block.txt +1 -0
  77. data/spec/support/outputs/rails_assets_precompile_with_diff.txt +7 -0
  78. data/spec/support/outputs/rails_console.txt +1 -0
  79. data/spec/support/outputs/rails_db_migrate_force_migrate.txt +2 -0
  80. data/spec/support/outputs/rails_db_migrate_outside_deploy_block.txt +1 -0
  81. data/spec/support/outputs/rails_db_migrate_with_diff.txt +7 -0
  82. data/spec/support/outputs/rails_log.txt +1 -0
  83. data/spec/support/outputs/rails_with_arguments.txt +1 -0
  84. data/spec/support/outputs/rails_without_arguments.txt +1 -0
  85. data/spec/support/outputs/rake_with_arguments.txt +1 -0
  86. data/spec/support/outputs/rake_without_arguments.txt +1 -0
  87. data/spec/support/outputs/rbenv_load.txt +9 -1
  88. data/spec/support/outputs/rvm_use_with_env.txt +8 -0
  89. data/spec/support/outputs/rvm_use_without_env.txt +2 -0
  90. data/spec/support/outputs/rvm_wrapper_with_arguments.txt +8 -0
  91. data/spec/support/outputs/rvm_wrapper_without_arguments.txt +2 -0
  92. data/spec/support/outputs/ry_with_env.txt +13 -0
  93. data/spec/support/outputs/ry_without_env.txt +13 -0
  94. data/spec/support/outputs/ssh.txt +1 -0
  95. data/spec/support/outputs/ssh_keyscan_domain.txt +3 -0
  96. data/spec/support/rake_example_group.rb +23 -19
  97. data/spec/tasks/bundler_spec.rb +6 -0
  98. data/spec/tasks/chruby_spec.rb +29 -0
  99. data/spec/tasks/default_spec.rb +79 -7
  100. data/spec/tasks/deploy_spec.rb +6 -0
  101. data/spec/tasks/git_spec.rb +12 -0
  102. data/spec/tasks/init_spec.rb +13 -4
  103. data/spec/tasks/rails_spec.rb +126 -15
  104. data/spec/tasks/rbenv_spec.rb +15 -0
  105. data/spec/tasks/rvm_spec.rb +51 -0
  106. data/spec/tasks/ry_spec.rb +43 -0
  107. data/tasks/mina/bundler.rb +7 -5
  108. data/tasks/mina/chruby.rb +7 -5
  109. data/tasks/mina/default.rb +19 -12
  110. data/tasks/mina/deploy.rb +27 -25
  111. data/tasks/mina/git.rb +28 -15
  112. data/tasks/mina/install.rb +9 -0
  113. data/tasks/mina/rails.rb +29 -27
  114. data/tasks/mina/rbenv.rb +8 -6
  115. data/tasks/mina/rvm.rb +13 -11
  116. data/tasks/mina/ry.rb +11 -11
  117. data/test_env/config/deploy.rb +9 -8
  118. metadata +69 -37
  119. data/spec/support/outputs/chruby.txt +0 -9
  120. data/spec/support/outputs/console.txt +0 -1
  121. data/spec/support/outputs/log.txt +0 -1
  122. data/spec/support/outputs/rails_db_migrate.txt +0 -1
  123. data/spec/support/outputs/rvm_use.txt +0 -1
  124. data/spec/support/outputs/ry.txt +0 -15
  125. data/spec/tasks/ruby_managers_spec.rb +0 -33
@@ -1,39 +1,98 @@
1
+ # frozen_string_literal: true
2
+
1
3
  require 'spec_helper'
2
4
 
3
5
  describe Mina::Application do
4
- # let(:app) { Rake.application }
5
- #
6
- # %w(quiet silent dry-run).each do |switch|
7
- # it "doesn't include --#{switch} in help" do
8
- # binding.pry
9
- # expect(out).not_to match(/--#{switch}/)
10
- # end
11
- # end
12
- #
13
- # it 'runs adds two default tasks to the task list' do
14
- # expect(subject.top_level_tasks).to include(:debug_configuration_variables)
15
- # expect(subject.top_level_tasks).to include(:run_commands)
16
- # end
17
- #
18
- # it 'overrides the rake method, but still prints the rake version' do
19
- # out = capture_io do
20
- # flags '--version', '-V'
21
- # end
22
- # expect(out).to match(/\bMina, version\b/)
23
- # expect(out).to match(/\bv#{Mina::VERSION}\b/)
24
- # end
25
- #
26
- # it 'enables simulation mode, and sets the backend Mina::Runner::Printer' do
27
- # capture_io do
28
- # flags '--simulate', '-s'
29
- # end
30
- # expect(Mina::Configuration.instance.fetch(:simulate)).to be true
31
- # end
32
- #
33
- # it 'enables printing all config variables on command line parameter' do
34
- # capture_io do
35
- # flags '--debug-configuration-variables', '-d'
36
- # end
37
- # expect(Mina::Configuration.instance.fetch(:debug_configuration_variables)).to be true
38
- # end
6
+ subject(:application) { described_class.new }
7
+
8
+ describe '#top_level_tasks' do
9
+ let(:default_tasks) { ['debug_configuration_variables', 'run_commands'] }
10
+
11
+ context 'when `init` task is added' do
12
+ it 'removes default tasks' do
13
+ expect do
14
+ application.collect_command_line_tasks(['init'])
15
+ end.to change(application, :top_level_tasks).from(default_tasks).to(['init'])
16
+ end
17
+ end
18
+
19
+ context "when `init` task isn't added" do
20
+ it 'keeps default tasks' do
21
+ expect do
22
+ application.collect_command_line_tasks(['a_task'])
23
+ end.to change(application, :top_level_tasks).from(default_tasks).to(['a_task', *default_tasks])
24
+ end
25
+ end
26
+ end
27
+
28
+ describe 'command-line options' do
29
+ ['--version', '-V'].each do |option|
30
+ describe option do
31
+ it 'prints Mina version and exits' do
32
+ expect do
33
+ application.handle_options([option])
34
+ end.to raise_error(SystemExit)
35
+ .and output("Mina, version v#{Mina::VERSION}\n").to_stdout
36
+ end
37
+ end
38
+ end
39
+
40
+ ['--verbose', '-v'].each do |option|
41
+ describe option do
42
+ it 'sets verbose flag to true' do
43
+ expect do
44
+ application.handle_options([option])
45
+ end.to change { application.fetch(:verbose) }.from(nil).to(true)
46
+ end
47
+ end
48
+ end
49
+
50
+ ['--simulate', '-s'].each do |option|
51
+ describe option do
52
+ it 'sets simulate flag to true' do
53
+ expect do
54
+ application.handle_options([option])
55
+ end.to change { application.fetch(:simulate) }.from(nil).to(true)
56
+ end
57
+ end
58
+ end
59
+
60
+ ['--debug-configuration-variables', '-d'].each do |option|
61
+ describe option do
62
+ it 'sets debug_configuration_variables flag to true' do
63
+ expect do
64
+ application.handle_options([option])
65
+ end.to change { application.fetch(:debug_configuration_variables) }.from(nil).to(true)
66
+ end
67
+ end
68
+ end
69
+
70
+ describe '--no-report-time' do
71
+ it 'sets skip_report_time flag to true' do
72
+ expect do
73
+ application.handle_options(['--no-report-time'])
74
+ end.to change { application.fetch(:skip_report_time) }.from(nil).to(true)
75
+ end
76
+ end
77
+ end
78
+
79
+ describe 'Rake options' do
80
+ let(:options) { application.standard_rake_options }
81
+
82
+ it 'shows --verbose' do
83
+ expect(options.any? { |(switch, *)| switch == '--verbose' }).to eq(true)
84
+ end
85
+
86
+ it "doesn't show --dry-run" do
87
+ expect(options.any? { |(switch, *)| switch == '--dry-run' }).to eq(false)
88
+ end
89
+
90
+ it "doesn't show --quiet" do
91
+ expect(options.any? { |(switch, *)| switch == '--quiet' }).to eq(false)
92
+ end
93
+
94
+ it "doesn't show --silent" do
95
+ expect(options.any? { |(switch, *)| switch == '--silent' }).to eq(false)
96
+ end
97
+ end
39
98
  end
@@ -1,11 +1,14 @@
1
+ # frozen_string_literal: true
2
+
1
3
  require 'spec_helper'
2
4
 
3
5
  describe Mina::Backend::Local do
4
- let(:backend) { Mina::Backend::Local.new ['ls -al'] }
6
+ let(:backend) { described_class.new ['ls -al'] }
7
+
5
8
  describe '#prepare' do
6
9
  it 'escpaces shellwords' do
7
10
  Mina::Configuration.instance.remove(:simulate)
8
- expect(backend.prepare).to eq("\\[\\\"ls\\ -al\\\"\\]")
11
+ expect(backend.prepare).to eq('\\[\\"ls\\ -al\\"\\]')
9
12
  end
10
13
 
11
14
  it 'adds debug if simualte' do
@@ -1,13 +1,15 @@
1
+ # frozen_string_literal: true
2
+
1
3
  require 'spec_helper'
2
4
 
3
5
  describe Mina::Backend::Remote do
4
- let(:backend) { Mina::Backend::Remote.new ['ls -al'] }
6
+ let(:backend) { described_class.new ['ls -al'] }
7
+
5
8
  before { Mina::Configuration.instance.set(:domain, 'localhost') }
6
- after { Mina::Configuration.instance.remove(:domain) }
7
9
 
8
10
  describe '#prepare' do
9
11
  it 'escpaces shellwords' do
10
- expect(backend.prepare).to eq("ssh localhost -p 22 -tt -- \\[\\\"ls\\ -al\\\"\\]")
12
+ expect(backend.prepare).to eq('ssh localhost -p 22 -tt -- \\[\\"ls\\ -al\\"\\]')
11
13
  end
12
14
 
13
15
  it 'adds debug if simualte' do
@@ -1,7 +1,9 @@
1
+ # frozen_string_literal: true
2
+
1
3
  require 'spec_helper'
2
4
 
3
5
  describe Mina::Commands do
4
- let(:commands) { Mina::Commands.new(:default) }
6
+ let(:commands) { described_class.new(:default) }
5
7
 
6
8
  describe '#command' do
7
9
  it 'adds a command to the queue' do
@@ -18,7 +20,6 @@ describe Mina::Commands do
18
20
 
19
21
  context 'when verbose' do
20
22
  before { Mina::Configuration.instance.set(:verbose, true) }
21
- after { Mina::Configuration.instance.remove(:verbose) }
22
23
 
23
24
  it 'adds a echo command to the queue' do
24
25
  commands.command('ls -al')
@@ -73,20 +74,19 @@ describe Mina::Commands do
73
74
 
74
75
  context 'when verbose' do
75
76
  before { Mina::Configuration.instance.set(:verbose, true) }
76
- after { Mina::Configuration.instance.remove(:verbose) }
77
77
 
78
78
  it 'joins all the commands within a path and echoes it' do
79
- expect(commands.process('some/path')).to eq("(cd some/path && echo \"$ cd some/path\" && ls -al && pwd && cd -)")
79
+ expect(commands.process('some/path')).to eq('(cd some/path && echo "$ cd some/path" && ls -al && pwd && cd -)')
80
80
  end
81
81
  end
82
82
  end
83
83
 
84
84
  describe '#run' do
85
- it 'calls run on a backend' do
85
+ it 'calls run on a backend', :suppressed_output do
86
86
  commands.command('ls -al')
87
- runner = double(:runner)
87
+ runner = instance_double(Mina::Runner)
88
88
  allow(Mina::Runner).to receive(:new).and_return(runner)
89
- expect(runner).to receive(:run).and_return(true)
89
+ allow(runner).to receive(:run).and_return(true)
90
90
  commands.run(:local)
91
91
  end
92
92
  end
@@ -1,7 +1,9 @@
1
+ # frozen_string_literal: true
2
+
1
3
  require 'spec_helper'
2
4
 
3
5
  describe Mina::Configuration do
4
- let(:config) { Class.new(Mina::Configuration).instance }
6
+ let(:config) { Class.new(described_class).instance }
5
7
  let(:key) { config.fetch(:key, :default) }
6
8
 
7
9
  describe '#set' do
@@ -26,6 +28,44 @@ describe Mina::Configuration do
26
28
  expect(key).to eq 'env'
27
29
  ENV['key'] = nil
28
30
  end
31
+
32
+ it "returns nil if a default value isn't provided" do
33
+ expect(config.fetch(:key)).to eq(nil)
34
+ end
35
+ end
36
+
37
+ describe '#remove' do
38
+ context 'when key exists' do
39
+ before do
40
+ config.set(:key, :value)
41
+ end
42
+
43
+ it 'removes the key' do
44
+ expect(config.set?(:key)).to eq(true)
45
+
46
+ config.remove(:key)
47
+
48
+ expect(config.set?(:key)).to eq(false)
49
+ end
50
+
51
+ it 'returns key value' do
52
+ expect(config.remove(:key)).to eq(:value)
53
+ end
54
+ end
55
+
56
+ context "when key doesn't exist" do
57
+ it "doesn't do anything" do
58
+ expect(config.set?(:key)).to eq(false)
59
+
60
+ config.remove(:key)
61
+
62
+ expect(config.set?(:key)).to eq(false)
63
+ end
64
+
65
+ it 'returns nil' do
66
+ expect(config.remove(:key)).to eq(nil)
67
+ end
68
+ end
29
69
  end
30
70
 
31
71
  describe '#set?' do
@@ -34,6 +74,11 @@ describe Mina::Configuration do
34
74
  expect(config.set?(:key)).to be true
35
75
  end
36
76
 
77
+ it 'returns false if key is set with nil value' do
78
+ config.set(:key, nil)
79
+ expect(config.set?(:key)).to be false
80
+ end
81
+
37
82
  it 'returns false if key is not set' do
38
83
  expect(config.set?(:key)).to be false
39
84
  end
@@ -42,11 +87,26 @@ describe Mina::Configuration do
42
87
  describe '#ensure!' do
43
88
  it 'does not raise error if key is set' do
44
89
  config.set(:key, :value)
45
- expect { config.ensure!(:key) }.to_not raise_error
90
+ expect { config.ensure!(:key) }.not_to raise_error
46
91
  end
47
92
 
48
93
  it 'raises an error if key is not set' do
49
94
  expect { config.ensure!(:key) }.to raise_error(SystemExit)
95
+ .and output(/key must be defined!/).to_stdout
96
+ end
97
+ end
98
+
99
+ describe '#reset!' do
100
+ before do
101
+ config.set(:key, :value)
102
+ end
103
+
104
+ it 'cleans all variables' do
105
+ expect(config.variables).not_to be_empty
106
+
107
+ config.reset!
108
+
109
+ expect(config.variables).to be_empty
50
110
  end
51
111
  end
52
112
 
@@ -55,7 +115,7 @@ describe Mina::Configuration do
55
115
  let(:host) { host_class.new }
56
116
 
57
117
  [:fetch, :set].each do |method|
58
- it "should respond to #{method}" do
118
+ it "responds to #{method}" do
59
119
  expect(host).to respond_to(method)
60
120
  end
61
121
  end
@@ -0,0 +1,94 @@
1
+ # frozen_string_literal: true
2
+
3
+ require 'spec_helper'
4
+
5
+ describe Mina::DSL, type: :rake do
6
+ before do
7
+ load_default_config
8
+ load_config 'dsl'
9
+ end
10
+
11
+ describe '#reset!' do
12
+ let(:task_name) { 'reset_task' }
13
+
14
+ it 'clears all commands before it' do
15
+ expect do
16
+ invoke_all
17
+ end.to output(output_file('dsl_reset')).to_stdout
18
+ end
19
+ end
20
+
21
+ describe '#run' do
22
+ context 'when one run block is inside another' do
23
+ let(:task_name) { 'one_run_inside_another' }
24
+
25
+ it 'exits with an error message' do
26
+ expect do
27
+ invoke_all
28
+ end.to raise_error(SystemExit)
29
+ .and output(/Can't use run block inside another run block./).to_stdout
30
+ end
31
+ end
32
+
33
+ context 'when backend is :local' do
34
+ let(:task_name) { 'local_run' }
35
+
36
+ it 'executes commands locally' do
37
+ expect do
38
+ invoke_all
39
+ end.to output(output_file('dsl_local_run')).to_stdout
40
+ end
41
+ end
42
+
43
+ context 'when backend is :remote' do
44
+ let(:task_name) { 'remote_run' }
45
+
46
+ it 'executes commands on the server' do
47
+ expect do
48
+ invoke_all
49
+ end.to output(output_file('dsl_remote_run')).to_stdout
50
+ end
51
+ end
52
+
53
+ context "when backend doesn't exist" do
54
+ let(:task_name) { 'nonexistent_run' }
55
+
56
+ # TODO: refactor for more user-friendly error handling
57
+ it 'raises a runtime error' do
58
+ expect do
59
+ invoke_all
60
+ end.to raise_error(RuntimeError, /Don't know how to build task 'nonexistent_environment'/)
61
+ end
62
+ end
63
+ end
64
+
65
+ describe '#on' do
66
+ let(:task_name) { 'on_stage_task' }
67
+
68
+ it 'executes the command in the given stage' do
69
+ expect do
70
+ invoke_all
71
+ end.to output(output_file('dsl_on')).to_stdout
72
+ end
73
+ end
74
+
75
+ describe '#in_path' do
76
+ let(:task_name) { 'in_path_task' }
77
+
78
+ it 'executes the command in the given path' do
79
+ expect do
80
+ invoke_all
81
+ end.to output(output_file('dsl_in_path')).to_stdout
82
+ end
83
+ end
84
+
85
+ describe '#deploy' do
86
+ let(:task_name) { 'deploy_block_task' }
87
+
88
+ it 'executes the deploy script and commands on remote' do
89
+ expect do
90
+ invoke_all
91
+ end.to output(output_file('dsl_deploy')).to_stdout
92
+ end
93
+ end
94
+ end
@@ -1,43 +1,46 @@
1
+ # frozen_string_literal: true
2
+
1
3
  require 'spec_helper'
2
4
 
3
5
  describe Mina::Helpers::Internal do
4
- class DummyInternalHelper
5
- include Mina::DSL
6
- include Mina::Helpers::Internal
6
+ let(:dummy_class) do
7
+ Class.new do
8
+ include Mina::DSL
9
+ include Mina::Helpers::Internal
10
+ end
7
11
  end
8
-
9
- let(:helper) { DummyInternalHelper.new }
12
+ let(:helper) { dummy_class.new }
10
13
 
11
14
  describe '#deploy_script' do
12
15
  before do
13
- Mina::Configuration.instance.set(:deploy_script, 'data/deploy.sh.erb')
16
+ Mina::Configuration.instance.set(:deploy_script, Mina.root_path('data/deploy.sh.erb'))
14
17
  Mina::Configuration.instance.set(:version_scheme, :sequence)
15
18
  end
16
19
 
17
20
  it 'returns whole script' do
18
- expect(helper.deploy_script {}).to_not be_empty
21
+ expect(helper.deploy_script {}).not_to be_empty
19
22
  end
20
23
  end
21
24
 
22
25
  describe '#erb' do
23
26
  before { Mina::Configuration.instance.set(:version_scheme, :sequence) }
24
- after { Mina::Configuration.instance.remove(:version_scheme) }
25
27
 
26
28
  it 'returns whole script' do
27
- expect(helper.erb('data/deploy.sh.erb')).to_not be_empty
29
+ expect(helper.erb('data/deploy.sh.erb')).not_to be_empty
28
30
  end
29
31
  end
30
32
 
31
33
  describe '#echo_cmd' do
32
34
  context 'when not verbose' do
33
- it 'reuturns unedited code' do
35
+ before { Mina::Configuration.instance.set(:verbose, false) }
36
+
37
+ it 'returns unedited code' do
34
38
  expect(helper.echo_cmd('ls -al')).to eq('ls -al')
35
39
  end
36
40
  end
37
41
 
38
42
  context 'when verbose' do
39
43
  before { Mina::Configuration.instance.set(:verbose, true) }
40
- after { Mina::Configuration.instance.remove(:verbose) }
41
44
 
42
45
  it 'modifies code' do
43
46
  expect(helper.echo_cmd('ls -al')).to eq("echo \\$\\ ls\\ -al &&\nls -al")
@@ -54,4 +57,79 @@ describe Mina::Helpers::Internal do
54
57
  expect(helper.indent(4, 'ls -al')).to eq(' ls -al')
55
58
  end
56
59
  end
60
+
61
+ describe '#unindent' do
62
+ it 'unindents code' do
63
+ expect(helper.unindent(" ls -al\n")).to eq('ls -al')
64
+ end
65
+ end
66
+
67
+ describe '#report_time' do
68
+ context 'when :skip_report_time is true' do
69
+ before { Mina::Configuration.instance.set(:skip_report_time, true) }
70
+
71
+ it "doesn't output report time" do
72
+ expect do
73
+ helper.report_time {}
74
+ end.not_to output.to_stdout
75
+ end
76
+ end
77
+
78
+ context 'when :skip_report_time is false' do
79
+ before { Mina::Configuration.instance.set(:skip_report_time, false) }
80
+
81
+ it 'outputs report time' do
82
+ expect do
83
+ helper.report_time {}
84
+ end.to output(/Elapsed time: \d+\.\d\d seconds/).to_stdout
85
+ end
86
+ end
87
+ end
88
+
89
+ describe '#next_version' do
90
+ before do
91
+ Mina::Configuration.instance.set(:releases_path, '/releases')
92
+ end
93
+
94
+ context 'when :version_scheme is :datetime' do
95
+ before do
96
+ Mina::Configuration.instance.set(:version_scheme, :datetime)
97
+
98
+ allow(Time).to receive(:now).and_return(Time.parse('2020-05-01 12:34:56 UTC'))
99
+ end
100
+
101
+ after { Mina::Configuration.instance.remove(:version_scheme) }
102
+
103
+ it 'formats current UTC time' do
104
+ expect(helper.next_version).to eq('20200501123456')
105
+ end
106
+ end
107
+
108
+ context 'when :version_scheme is :sequence' do
109
+ before { Mina::Configuration.instance.set(:version_scheme, :sequence) }
110
+
111
+ it 'generates a command to calculate the next version' do
112
+ expect(helper.next_version).to eq('$((`ls -1 /releases | sort -n | tail -n 1`+1))')
113
+ end
114
+ end
115
+
116
+ context 'when :version_scheme is unknown' do
117
+ before { Mina::Configuration.instance.set(:version_scheme, :foobar) }
118
+
119
+ it 'exits with an error message' do
120
+ expect do
121
+ helper.next_version
122
+ end.to raise_error(SystemExit)
123
+ .and output(/Unrecognized version scheme\. Use :datetime or :sequence/).to_stdout
124
+ end
125
+ end
126
+ end
127
+
128
+ describe '#error!' do
129
+ it 'exits with an error message' do
130
+ expect do
131
+ helper.error!('foobar')
132
+ end.to raise_error(SystemExit).and output(/foobar/).to_stdout
133
+ end
134
+ end
57
135
  end
@@ -1,33 +1,36 @@
1
+ # frozen_string_literal: true
2
+
1
3
  require 'spec_helper'
2
4
 
3
5
  describe Mina::Helpers::Output do
4
- class DummyOutputHelper
5
- include Mina::Helpers::Output
6
- end
7
-
8
- let(:helper) { DummyOutputHelper.new }
6
+ let(:dummy_class) { Class.new { include Mina::Helpers::Output } }
7
+ let(:helper) { dummy_class.new }
9
8
 
10
9
  describe '#print_line' do
11
10
  it 'prints normally' do
12
- expect{ helper.print_line('ls -al') }.to output(" ls -al\n").to_stdout
11
+ expect { helper.print_line('ls -al') }.to output(" ls -al\n").to_stdout
13
12
  end
14
13
 
15
14
  it 'prints comment' do
16
- expect{ helper.print_line('-> ls -al') }.to output("\e[32m----->\e[0m ls -al\n").to_stdout
15
+ expect { helper.print_line('-> ls -al') }.to output("\e[32m----->\e[0m ls -al\n").to_stdout
17
16
  end
18
17
 
19
18
  it 'prints error' do
20
- expect{ helper.print_line('! ls -al') }.to output(" \e[33m!\e[0m \e[31mls -al\e[0m\n").to_stdout
19
+ expect { helper.print_line('! ls -al') }.to output(" \e[33m!\e[0m \e[31mls -al\e[0m\n").to_stdout
21
20
  end
22
21
 
23
22
  it 'prints command' do
24
- expect{ helper.print_line('$ ls -al') }.to output(" \e[36m$\e[0m \e[36mls -al\e[0m\n").to_stdout
23
+ expect { helper.print_line('$ ls -al') }.to output(" \e[36m$\e[0m \e[36mls -al\e[0m\n").to_stdout
25
24
  end
26
25
  end
27
26
 
28
27
  describe '#print_stderr' do
28
+ it 'prints normally when the message is formatted by assets precompile' do
29
+ expect { helper.print_stderr('I, [ ls -al') }.to output(" I, [ ls -al\n").to_stdout
30
+ end
31
+
29
32
  it 'prints stderr' do
30
- expect{ helper.print_stderr('ls -al') }.to output(" \e[31mls -al\e[0m\n").to_stdout
33
+ expect { helper.print_stderr('ls -al') }.to output(" \e[31mls -al\e[0m\n").to_stdout
31
34
  end
32
35
  end
33
36
  end
@@ -0,0 +1,19 @@
1
+ # frozen_string_literal: true
2
+
3
+ require 'spec_helper'
4
+
5
+ describe Mina::Runner::Exec do
6
+ subject(:runner) { described_class.new('echo hello') }
7
+
8
+ describe '#run' do
9
+ before do
10
+ allow(Kernel).to receive(:exec)
11
+ end
12
+
13
+ it 'executes the script' do
14
+ runner.run
15
+
16
+ expect(Kernel).to have_received(:exec).with('echo hello')
17
+ end
18
+ end
19
+ end
@@ -0,0 +1,17 @@
1
+ # frozen_string_literal: true
2
+
3
+ require 'spec_helper'
4
+
5
+ describe Mina::Runner::Pretty do
6
+ subject(:runner) { described_class.new('true') }
7
+
8
+ describe '#run', :suppressed_output do
9
+ it 'executes the script' do
10
+ expect { runner.run }.to output('').to_stdout
11
+ end
12
+
13
+ it 'returns true', :suppressed_output do
14
+ expect(runner.run).to eq(true)
15
+ end
16
+ end
17
+ end
@@ -0,0 +1,19 @@
1
+ # frozen_string_literal: true
2
+
3
+ require 'spec_helper'
4
+
5
+ describe Mina::Runner::Printer do
6
+ subject(:runner) { described_class.new('echo hello') }
7
+
8
+ describe '#run' do
9
+ it 'prints the script to stdout' do
10
+ expect do
11
+ runner.run
12
+ end.to output("echo hello\n").to_stdout
13
+ end
14
+
15
+ it 'returns true', :suppressed_output do
16
+ expect(runner.run).to eq(true)
17
+ end
18
+ end
19
+ end
@@ -0,0 +1,19 @@
1
+ # frozen_string_literal: true
2
+
3
+ require 'spec_helper'
4
+
5
+ describe Mina::Runner::System do
6
+ subject(:runner) { described_class.new('echo hello') }
7
+
8
+ describe '#run' do
9
+ before do
10
+ allow(Kernel).to receive(:system)
11
+ end
12
+
13
+ it 'executes the script' do
14
+ runner.run
15
+
16
+ expect(Kernel).to have_received(:system).with('echo hello')
17
+ end
18
+ end
19
+ end