indocker 0.1.6 → 0.1.11

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (38) hide show
  1. checksums.yaml +4 -4
  2. data/Gemfile +5 -0
  3. data/Gemfile.lock +10 -4
  4. data/README.md +13 -2
  5. data/example/indocker/bin/deploy +19 -13
  6. data/example/indocker/bounded_contexts/shared/bad_container_build/Dockerfile +3 -0
  7. data/example/indocker/bounded_contexts/shared/bad_container_build/container.rb +5 -0
  8. data/example/indocker/bounded_contexts/shared/bad_container_build/image.rb +3 -0
  9. data/example/indocker/bounded_contexts/shared/bad_container_start/Dockerfile +8 -0
  10. data/example/indocker/bounded_contexts/shared/bad_container_start/build_context/bin/run +3 -0
  11. data/example/indocker/bounded_contexts/shared/bad_container_start/container.rb +5 -0
  12. data/example/indocker/bounded_contexts/shared/bad_container_start/image.rb +3 -0
  13. data/example/indocker/bounded_contexts/shared/good_container/Dockerfile +4 -0
  14. data/example/indocker/bounded_contexts/shared/good_container/container.rb +5 -0
  15. data/example/indocker/bounded_contexts/shared/good_container/image.rb +3 -0
  16. data/example/indocker/configurations/external.rb +18 -0
  17. data/example/indocker/infrastructure/build_servers.rb +11 -0
  18. data/example/indocker/infrastructure/servers.rb +11 -0
  19. data/example/indocker/setup.rb +1 -1
  20. data/example/spec/indocker_spec.rb +39 -0
  21. data/example/spec/spec_helper.rb +39 -0
  22. data/indocker.gemspec +1 -1
  23. data/lib/indocker.rb +37 -57
  24. data/lib/indocker/build_context.rb +13 -12
  25. data/lib/indocker/build_context_pool.rb +5 -1
  26. data/lib/indocker/configuration_deployer.rb +125 -93
  27. data/lib/indocker/container_deployer.rb +17 -7
  28. data/lib/indocker/context_args.rb +2 -0
  29. data/lib/indocker/deploy_context.rb +10 -8
  30. data/lib/indocker/deployment_policy.rb +22 -0
  31. data/lib/indocker/deployment_progress.rb +7 -2
  32. data/lib/indocker/images_compiler.rb +1 -1
  33. data/lib/indocker/logger_factory.rb +37 -0
  34. data/lib/indocker/server_pool.rb +9 -1
  35. data/lib/indocker/ssh_session.rb +21 -10
  36. data/lib/indocker/version.rb +1 -1
  37. metadata +19 -5
  38. data/lib/indocker/ssh_result_logger.rb +0 -18
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 69e124a571ae32781f28cbe640d3f406914c9cbbf88ebe5178d31280844c0ea6
4
- data.tar.gz: 78f3b3a06fd08188b48ad8fedae468a62ea6d9dc348442bf22fc9fdd1b6cf93d
3
+ metadata.gz: 8625d37ada817f2f83c30f154bd2ed9a104a023e5b554f4c91f3708ed4aa2770
4
+ data.tar.gz: 24950eb94bd956f7f10ad81da4330bffa78495a4852733a1bec5d0713cce4896
5
5
  SHA512:
6
- metadata.gz: d169e30efdcf9ae6c97bf01a836be681c9bdc6cf9515fc61d30b4ae57ad9368a96e7619703fe0ad54cba968123de6ce6da6b96f1272cd7eab95ea73e7ed6416c
7
- data.tar.gz: e4b61302d306cc10d85edfffd37db51b668399a6c0ebb214451693394318b389bcf106fc116ee9f2ad1cf17f301c9ba17b1b4d6031a1218351f6c5210b3bd7b0
6
+ metadata.gz: e50ef7ed88a688bb1119e55b1d1662d6827e5667cc66c61dc85933687e9d4834c785c03c7fb917a2709adf04d909f7e611f8c844741b1532211dddad340dc149
7
+ data.tar.gz: 1e52f25fff3bf09ddb7f1d097b46ad0e858555892d3b4721a628c8817a16e165694dbf3650e940eb83cb6ac05d8ded47c6359ada9d3cba39d3885ff95e9e88d0
data/Gemfile CHANGED
@@ -4,3 +4,8 @@ git_source(:github) {|repo_name| "https://github.com/#{repo_name}" }
4
4
 
5
5
  # Specify your gem's dependencies in indocker.gemspec
6
6
  gemspec
7
+
8
+ group :test do
9
+ gem 'rspec'
10
+ gem 'pry'
11
+ end
@@ -1,15 +1,20 @@
1
1
  PATH
2
2
  remote: .
3
3
  specs:
4
- indocker (0.1.6)
4
+ indocker (0.1.11)
5
5
  net-ssh
6
6
 
7
7
  GEM
8
8
  remote: https://rubygems.org/
9
9
  specs:
10
+ coderay (1.1.3)
10
11
  diff-lcs (1.3)
12
+ method_source (1.0.0)
11
13
  net-ssh (6.1.0)
12
- rake (10.5.0)
14
+ pry (0.13.1)
15
+ coderay (~> 1.1)
16
+ method_source (~> 1.0)
17
+ rake (12.3.3)
13
18
  rspec (3.9.0)
14
19
  rspec-core (~> 3.9.0)
15
20
  rspec-expectations (~> 3.9.0)
@@ -30,8 +35,9 @@ PLATFORMS
30
35
  DEPENDENCIES
31
36
  bundler (~> 1.17)
32
37
  indocker!
33
- rake (~> 10.0)
34
- rspec (~> 3.0)
38
+ pry
39
+ rake (~> 12.3.3)
40
+ rspec
35
41
 
36
42
  BUNDLED WITH
37
43
  1.17.3
data/README.md CHANGED
@@ -1,5 +1,7 @@
1
1
  # InDocker
2
2
 
3
+ [![Codeship Status for ArtStation/indocker](https://app.codeship.com/projects/bf8888c0-b7e4-0138-fc1f-7e2faa53772a/status?branch=master)](https://app.codeship.com/projects/404716)
4
+
3
5
  Docker Containers Deployment
4
6
 
5
7
  ## Installation
@@ -8,11 +10,20 @@ Docker Containers Deployment
8
10
  $ gem install indocker
9
11
  ```
10
12
 
11
- ## Development: Launch example app
13
+ ## Development: Launch example app locally
14
+
15
+ ```ruby
16
+ cd example
17
+ indocker/bin/deploy -C dev -c ruby -d
18
+ ```
19
+
20
+ ## Development: Launch example with external host
21
+
22
+ NOTE: Default external host requires extra permissions.
12
23
 
13
24
  ```ruby
14
25
  cd example
15
- bundle exec indocker/bin/deploy -C dev -c ruby -d
26
+ indocker/bin/deploy -C external -c ruby -d
16
27
  ```
17
28
 
18
29
  ## License
@@ -8,9 +8,10 @@ configurations = list_configurations(File.expand_path(File.join(__dir__, '../con
8
8
  ARGV << '-h' if ARGV.empty?
9
9
 
10
10
  options = {
11
- skip_build: false,
12
- force_restart: false,
13
- skip_tags: [],
11
+ skip_build: false,
12
+ skip_deploy: false,
13
+ force_restart: false,
14
+ skip_tags: [],
14
15
  skip_force_restart: [],
15
16
  }
16
17
 
@@ -61,6 +62,10 @@ OptionParser.new do |opts|
61
62
  options[:skip_build] = true
62
63
  end
63
64
 
65
+ opts.on("-b", "--skip-deploy", "Skip image deploy") do |val|
66
+ options[:skip_deploy] = true
67
+ end
68
+
64
69
  opts.on("-y", "--auto-confirm", "Automatically confirm deployment") do |val|
65
70
  options[:auto_confirm] = true
66
71
  end
@@ -106,15 +111,16 @@ Indocker.set_configuration_name(options[:configuration])
106
111
  require_relative '../setup'
107
112
 
108
113
  Indocker.deploy(
109
- containers: options[:containers] || [],
110
- tags: options[:tags] || [],
111
- skip_containers: options[:skip_containers] || [],
112
- skip_dependent: !!options[:skip_dependent],
113
- servers: options[:servers] || [],
114
- skip_build: options[:skip_build],
115
- force_restart: options[:force_restart],
116
- skip_tags: options[:skip_tags] || [],
117
- skip_force_restart: options[:skip_force_restart] || [],
118
- auto_confirm: !!options[:auto_confirm],
114
+ containers: options[:containers] || [],
115
+ tags: options[:tags] || [],
116
+ skip_containers: options[:skip_containers] || [],
117
+ skip_dependent: !!options[:skip_dependent],
118
+ servers: options[:servers] || [],
119
+ skip_build: options[:skip_build],
120
+ skip_deploy: options[:skip_deploy],
121
+ force_restart: options[:force_restart],
122
+ skip_tags: options[:skip_tags] || [],
123
+ skip_force_restart: options[:skip_force_restart] || [],
124
+ auto_confirm: !!options[:auto_confirm],
119
125
  require_confirmation: !!options[:require_confirmation],
120
126
  )
@@ -0,0 +1,3 @@
1
+ FROM ruby:2.5.0
2
+
3
+ RUN some-unexisting-command
@@ -0,0 +1,5 @@
1
+ Indocker
2
+ .define_container(:bad_container_build)
3
+ .tags('bad_container_build', 'console=true')
4
+ .image(:bad_container_build)
5
+ .networks(:app_net)
@@ -0,0 +1,3 @@
1
+ Indocker
2
+ .define_image(:bad_container_build)
3
+ .registry(:default)
@@ -0,0 +1,8 @@
1
+ FROM ruby:2.5.0
2
+
3
+ RUN mkdir /app
4
+ WORKDIR /app
5
+
6
+ COPY bin bin
7
+
8
+ CMD ["bin/run"]
@@ -0,0 +1,3 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ raise "Some error"
@@ -0,0 +1,5 @@
1
+ Indocker
2
+ .define_container(:bad_container_start)
3
+ .tags('bad_container_start', 'console=true')
4
+ .image(:bad_container_start)
5
+ .networks(:app_net)
@@ -0,0 +1,3 @@
1
+ Indocker
2
+ .define_image(:bad_container_start)
3
+ .registry(:default)
@@ -0,0 +1,4 @@
1
+ FROM ruby:2.5.0
2
+
3
+ RUN mkdir /app
4
+ WORKDIR /app
@@ -0,0 +1,5 @@
1
+ Indocker
2
+ .define_container(:good_container)
3
+ .tags('good_container', 'console=true')
4
+ .image(:good_container)
5
+ .networks(:app_net)
@@ -0,0 +1,3 @@
1
+ Indocker
2
+ .define_image(:good_container)
3
+ .registry(:default)
@@ -0,0 +1,18 @@
1
+ Indocker
2
+ .build_configuration(:external)
3
+ .use_registry(:dev, as: :default)
4
+ .use_build_server(:external_bs)
5
+ .enabled_containers(
6
+ ruby: {
7
+ servers: [:external],
8
+ },
9
+ good_container: {
10
+ servers: [:external],
11
+ },
12
+ bad_container_build: {
13
+ servers: [:external],
14
+ },
15
+ bad_container_start: {
16
+ servers: [:external],
17
+ }
18
+ )
@@ -5,4 +5,15 @@ Indocker.add_build_server(
5
5
  user: `whoami`.strip,
6
6
  port: 22
7
7
  )
8
+ )
9
+
10
+ external_host = ENV['INDOCKER_EXTERNAL_HOST'] || 'indocker.artstn.ninja'
11
+ external_user = ENV['INDOCKER_EXTERNAL_USER'] || 'indocker'
12
+ Indocker.add_build_server(
13
+ Indocker::BuildServer.new(
14
+ name: :external_bs,
15
+ host: external_host,
16
+ user: external_user,
17
+ port: 22
18
+ )
8
19
  )
@@ -5,4 +5,15 @@ Indocker.add_server(
5
5
  user: `whoami`.strip,
6
6
  port: 22
7
7
  )
8
+ )
9
+
10
+ external_host = ENV['INDOCKER_EXTERNAL_HOST'] || 'indocker.artstn.ninja'
11
+ external_user = ENV['INDOCKER_EXTERNAL_USER'] || 'indocker'
12
+ Indocker.add_server(
13
+ Indocker::Server.new(
14
+ name: :external,
15
+ host: external_host,
16
+ user: external_user,
17
+ port: 22
18
+ )
8
19
  )
@@ -3,7 +3,7 @@ require 'indocker'
3
3
  root_dir = File.join(__dir__, '..', '..')
4
4
 
5
5
  Indocker.set_root_dir(__dir__)
6
- Indocker.set_deploy_dir(File.join(root_dir, 'tmp', 'deployment'))
6
+ Indocker.set_deploy_dir('~/deployment')
7
7
 
8
8
  Indocker.set_dockerignore [
9
9
  'Dockerfile',
@@ -0,0 +1,39 @@
1
+ require 'spec_helper'
2
+
3
+ RSpec.describe Indocker do
4
+ it "has a version number" do
5
+ expect(Indocker::VERSION).not_to be nil
6
+ end
7
+
8
+ describe "successful deployment" do
9
+ it "doesn't raise any error" do
10
+ expect{
11
+ launch_deployment(containers: [:good_container])
12
+ }.to_not raise_error
13
+ end
14
+
15
+ it "shows a message about successful deploy" do
16
+ allow(Indocker.global_logger).to receive(:info).at_least(:once)
17
+
18
+ launch_deployment(containers: [:good_container])
19
+
20
+ expect(Indocker.global_logger).to have_received(:info).at_least(:once).with(/Deployment finished/)
21
+ end
22
+ end
23
+
24
+ describe "failed build" do
25
+ it "exits with an error" do
26
+ expect{
27
+ launch_deployment(containers: [:bad_container_build])
28
+ }.to raise_error(SystemExit)
29
+ end
30
+ end
31
+
32
+ describe "failed start" do
33
+ it "exits without error" do
34
+ expect{
35
+ launch_deployment(containers: [:bad_container_start])
36
+ }.to_not raise_error(SystemExit)
37
+ end
38
+ end
39
+ end
@@ -0,0 +1,39 @@
1
+ require "bundler/setup"
2
+ require "indocker"
3
+ require "pry"
4
+
5
+ RSpec.configure do |config|
6
+ # Enable flags like --only-failures and --next-failure
7
+ config.example_status_persistence_file_path = ".rspec_status"
8
+
9
+ # Disable RSpec exposing methods globally on `Module` and `main`
10
+ config.disable_monkey_patching!
11
+
12
+ config.expect_with :rspec do |c|
13
+ c.syntax = :expect
14
+ end
15
+ end
16
+
17
+ def launch_deployment(options = {})
18
+ require_relative '../indocker/bin/utils/configurations'
19
+
20
+ Indocker.set_configuration_name(options[:configuration] || "external")
21
+ require_relative '../indocker/setup'
22
+
23
+ Indocker.set_log_level(options[:debug] ? Logger::DEBUG : Logger::INFO)
24
+
25
+ Indocker.deploy(
26
+ containers: options[:containers] || [],
27
+ tags: options[:tags] || [],
28
+ skip_containers: options[:skip_containers] || [],
29
+ skip_dependent: !!options[:skip_dependent],
30
+ servers: options[:servers] || [],
31
+ skip_build: options[:skip_build],
32
+ skip_deploy: options[:skip_deploy],
33
+ force_restart: options[:force_restart],
34
+ skip_tags: options[:skip_tags] || [],
35
+ skip_force_restart: options[:skip_force_restart] || [],
36
+ auto_confirm: !!options[:auto_confirm],
37
+ require_confirmation: !!options[:require_confirmation],
38
+ )
39
+ end
@@ -25,6 +25,6 @@ Gem::Specification.new do |spec|
25
25
 
26
26
  spec.add_dependency "net-ssh"
27
27
  spec.add_development_dependency "bundler", "~> 1.17"
28
- spec.add_development_dependency "rake", "~> 10.0"
28
+ spec.add_development_dependency "rake", "~> 12.3.3"
29
29
  spec.add_development_dependency "rspec", "~> 3.0"
30
30
  end
@@ -85,10 +85,11 @@ module Indocker
85
85
  autoload :IndockerHelper, 'indocker_helper'
86
86
  autoload :ImagesCompiler, 'images_compiler'
87
87
  autoload :ContainerRunner, 'container_runner'
88
- autoload :SshResultLogger, 'ssh_result_logger'
89
88
  autoload :DeploymentProgress, 'deployment_progress'
90
89
  autoload :DeploymentChecker, 'deployment_checker'
90
+ autoload :DeploymentPolicy, 'deployment_policy'
91
91
  autoload :CrontabRedeployRulesBuilder, 'crontab_redeploy_rules_builder'
92
+ autoload :LoggerFactory, 'logger_factory'
92
93
 
93
94
  class << self
94
95
  def set_export_command(command)
@@ -318,22 +319,31 @@ module Indocker
318
319
  builder
319
320
  end
320
321
 
321
- def deploy(containers: [], skip_tags: [], tags: [], skip_dependent: false, skip_containers: [], servers: [], skip_build: false, force_restart: false, skip_force_restart: [], auto_confirm: false, require_confirmation: false)
322
+ def deploy(containers: [], skip_tags: [], tags: [], skip_dependent: false,
323
+ skip_containers: [], servers: [], skip_build: false, skip_deploy: false,
324
+ force_restart: false, skip_force_restart: [], auto_confirm: false,
325
+ require_confirmation: false)
326
+
327
+ deployment_policy = Indocker::DeploymentPolicy.new(
328
+ deploy_containers: containers,
329
+ deploy_tags: tags,
330
+ servers: servers,
331
+ skip_dependent: skip_dependent,
332
+ skip_containers: skip_containers,
333
+ skip_build: skip_build,
334
+ skip_deploy: skip_deploy,
335
+ skip_tags: skip_tags,
336
+ force_restart: force_restart,
337
+ skip_force_restart: skip_force_restart,
338
+ auto_confirm: auto_confirm,
339
+ require_confirmation: require_confirmation,
340
+ )
341
+
322
342
  Indocker::ConfigurationDeployer
323
- .new(Indocker.logger)
343
+ .new(logger: Indocker.logger, global_logger: Indocker.global_logger)
324
344
  .run(
325
- configuration: configuration,
326
- deploy_containers: containers,
327
- deploy_tags: tags,
328
- skip_dependent: skip_dependent,
329
- skip_containers: skip_containers,
330
- servers: servers,
331
- skip_build: skip_build,
332
- force_restart: force_restart,
333
- skip_tags: skip_tags,
334
- skip_force_restart: skip_force_restart,
335
- auto_confirm: auto_confirm,
336
- require_confirmation: require_confirmation,
345
+ configuration: configuration,
346
+ deployment_policy: deployment_policy
337
347
  )
338
348
  end
339
349
 
@@ -385,56 +395,26 @@ module Indocker
385
395
  Indocker::BuildContextHelper.new(Indocker.configuration, nil)
386
396
  end
387
397
 
398
+ # This logger outputs progress of the deployment
399
+ # It will not output anything for deployment without debug option
388
400
  def logger
389
401
  @logger ||= begin
390
- logger = if @log_level == Logger::DEBUG
391
- Logger.new(STDOUT)
402
+ logger_stdout = if @log_level == Logger::DEBUG
403
+ STDOUT
392
404
  else
393
- Logger.new(File.open(File::NULL, "w"))
394
- end
395
-
396
- logger.level = @log_level || Logger::INFO
397
-
398
- logger.formatter = proc do |severity, datetime, progname, msg|
399
- level = Logger::SEV_LABEL.index(severity)
400
-
401
- severity = case level
402
- when Logger::INFO
403
- severity.green
404
- when Logger::WARN
405
- severity.purple
406
- when Logger::DEBUG
407
- severity.yellow
408
- when Logger::ERROR
409
- severity.red
410
- when Logger::FATAL
411
- severity.red
412
- else
413
- severity
414
- end
415
-
416
- severity = severity.downcase
417
-
418
- if logger.debug?
419
- if msg == "{timestamp}"
420
- ""
421
- else
422
- "#{datetime.strftime("%Y/%m/%d %H:%M:%S")} #{severity}: #{msg}\n"
423
- end
424
- else
425
- # Use a nicer logging for not debug
426
- if msg == "{timestamp}"
427
- datetime.strftime("%Y/%m/%d %H:%M:%S\n").grey
428
- else
429
- " #{severity}: #{msg}\n"
430
- end
431
- end
405
+ File.open(File::NULL, "w")
432
406
  end
433
407
 
434
- logger
408
+ Indocker::LoggerFactory.create(logger_stdout, @log_level)
435
409
  end
436
410
  end
437
411
 
412
+ # Global logger would output data without dependency on how we deploy the progress
413
+ # Currently it will always output data to stdout
414
+ def global_logger
415
+ @global_logger ||= Indocker::LoggerFactory.create(STDOUT, @log_level)
416
+ end
417
+
438
418
  def set_log_level(level)
439
419
  @log_level = level
440
420
  end