docker-builder 0.1.5

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 (72) hide show
  1. checksums.yaml +7 -0
  2. data/.gitignore +11 -0
  3. data/CODE_OF_CONDUCT.md +49 -0
  4. data/Gemfile +4 -0
  5. data/LICENSE.txt +21 -0
  6. data/Rakefile +140 -0
  7. data/bin/console +14 -0
  8. data/bin/setup +8 -0
  9. data/docker-builder.gemspec +36 -0
  10. data/examples/example-apps-php/.chef/knife.rb +6 -0
  11. data/examples/example-apps-php/config.rb +19 -0
  12. data/examples/example-apps-php/servers/apps-php/.chef/knife.rb +2 -0
  13. data/examples/example-apps-php/servers/apps-php/config.rb +69 -0
  14. data/examples/example-apps-php/servers/apps-php/cookbooks/apps-php/README.md +1 -0
  15. data/examples/example-apps-php/servers/apps-php/cookbooks/apps-php/metadata.rb +9 -0
  16. data/examples/example-apps-php/servers/apps-php/cookbooks/apps-php/recipes/build.rb +43 -0
  17. data/examples/example-apps-php/servers/apps-php/cookbooks/apps-php/recipes/install.rb +55 -0
  18. data/examples/example-apps-php/servers/apps-php/cookbooks/apps-php/recipes/install_app.rb +27 -0
  19. data/examples/example-apps-php/servers/apps-php/cookbooks/apps-php/recipes/install_host.rb +9 -0
  20. data/examples/example-apps-php/servers/apps-php/cookbooks/apps-php/templates/index.html.erb +4 -0
  21. data/examples/example-apps-php/servers/apps-php/cookbooks/apps-php/templates/nginx-sites/app.conf.erb +55 -0
  22. data/examples/example-apps-php/servers/apps-php/cookbooks/apps-php/templates/nginx-sites/app.conf.erb.1 +55 -0
  23. data/examples/example-apps-php/servers/apps-php/cookbooks/apps-php/templates/nginx-sites/default.conf.erb +45 -0
  24. data/examples/example-apps-php/servers/apps-php/readme.md +0 -0
  25. data/examples/example-nginx/config.rb +19 -0
  26. data/examples/example-nginx/servers/nginx/.chef/knife.rb +8 -0
  27. data/examples/example-nginx/servers/nginx/config.rb +54 -0
  28. data/examples/example-nginx/servers/nginx/cookbooks/nginx/README.md +1 -0
  29. data/examples/example-nginx/servers/nginx/cookbooks/nginx/metadata.rb +9 -0
  30. data/examples/example-nginx/servers/nginx/cookbooks/nginx/recipes/build.rb +10 -0
  31. data/examples/example-nginx/servers/nginx/cookbooks/nginx/recipes/install.rb +28 -0
  32. data/examples/example-nginx/servers/nginx/cookbooks/nginx/recipes/install_host.rb +9 -0
  33. data/examples/example-nginx/servers/nginx/cookbooks/nginx/templates/index.html.erb +4 -0
  34. data/examples/example-nginx/servers/nginx/cookbooks/nginx/templates/nginx-sites/default.conf.erb +45 -0
  35. data/examples/example-nginx/servers/nginx/readme.md +0 -0
  36. data/examples/example-nginx/temp/ex_nginx.json +20 -0
  37. data/examples/example-nginx/temp/nginx.json +1 -0
  38. data/exe/docker-builder +20 -0
  39. data/install_local.sh +2 -0
  40. data/lib/docker_builder.rb +18 -0
  41. data/lib/docker_builder/chef/.chef/knife.rb +115 -0
  42. data/lib/docker_builder/chef/chef_build_image.copy0.rb +60 -0
  43. data/lib/docker_builder/chef/chef_destroy_image.copy0.rb +35 -0
  44. data/lib/docker_builder/cli.rb +346 -0
  45. data/lib/docker_builder/config.rb +199 -0
  46. data/lib/docker_builder/config/dsl.rb +48 -0
  47. data/lib/docker_builder/config/helpers.rb +99 -0
  48. data/lib/docker_builder/manager.rb +364 -0
  49. data/lib/docker_builder/server_settings.rb +286 -0
  50. data/lib/docker_builder/version.rb +3 -0
  51. data/lib/templates/example-chef/config.rb.erb +18 -0
  52. data/lib/templates/example-chef/servers/server1/.chef/knife.rb +8 -0
  53. data/lib/templates/example-chef/servers/server1/config.rb.erb +54 -0
  54. data/lib/templates/example-chef/servers/server1/cookbooks/server1/README.md +1 -0
  55. data/lib/templates/example-chef/servers/server1/cookbooks/server1/metadata.rb.erb +8 -0
  56. data/lib/templates/example-chef/servers/server1/cookbooks/server1/recipes/build.rb +10 -0
  57. data/lib/templates/example-chef/servers/server1/cookbooks/server1/recipes/install.rb +36 -0
  58. data/lib/templates/example-chef/servers/server1/cookbooks/server1/recipes/install_host.rb +9 -0
  59. data/lib/templates/example-chef/servers/server1/cookbooks/server1/templates/index.html.erb +5 -0
  60. data/lib/templates/example-chef/servers/server1/cookbooks/server1/templates/nginx-sites/default.conf.erb +45 -0
  61. data/readme.md +233 -0
  62. data/readme_developers.md +54 -0
  63. data/temp.sh +21 -0
  64. data/temp/app-php.json +1 -0
  65. data/temp/build.sh +29 -0
  66. data/temp/chef_build_image.rb +37 -0
  67. data/temp/chef_destroy_image.rb +16 -0
  68. data/temp/cookbooks/temp1/README.md +1 -0
  69. data/temp/cookbooks/temp1/metadata.rb +9 -0
  70. data/temp/cookbooks/temp1/recipes/build.rb +42 -0
  71. data/temp/run.sh +2 -0
  72. metadata +157 -0
@@ -0,0 +1,199 @@
1
+ # encoding: utf-8
2
+ require 'docker_builder/config/dsl'
3
+ require 'docker_builder/config/helpers'
4
+
5
+
6
+
7
+ module DockerBuilder
8
+ module Config
9
+ #class Error < DockerBuilder::Error; end
10
+
11
+ DEFAULTS = {
12
+ :config_file => 'config.rb',
13
+ :tmp_path => 'temp'
14
+ }
15
+
16
+ class << self
17
+ #include Utilities::Helpers
18
+
19
+ attr_reader :server, :root_path, :config_file, :tmp_path, :options
20
+
21
+
22
+ # Define on self, since it's a class method
23
+ def method_missing(method_sym, *arguments, &block)
24
+ # the first argument is a Symbol, so you need to_s it if you want to pattern match
25
+ if options.has_key?(method_sym)
26
+ return options[method_sym]
27
+ else
28
+ super
29
+ end
30
+ #if method_sym.to_s =~ /^find_by_(.*)$/
31
+ # find($1.to_sym => arguments.first)
32
+
33
+ end
34
+
35
+
36
+
37
+ # Loads the user's +config.rb+ and all model files.
38
+ def load(opts = {})
39
+ update(opts) # from the command line
40
+
41
+ unless File.exist?(config_file)
42
+ #raise Error, "Could not find configuration file: '#{config_file}'."
43
+ raise "Could not find configuration file: '#{config_file}'."
44
+ end
45
+
46
+ config = File.read(config_file)
47
+
48
+ #version = DockerBuilder::VERSION.split('.').first
49
+ #unless config =~ /^# Backup v#{ version }\.x Configuration$/
50
+ # raise Error, <<-EOS
51
+ # Invalid Configuration File
52
+ # EOS
53
+ #end
54
+
55
+ dsl = DSL.new
56
+ dsl.instance_eval(config, config_file)
57
+
58
+ update(dsl._config_options) # from config.rb
59
+ update(opts) # command line takes precedence
60
+
61
+ #Dir[File.join(File.dirname(config_file), 'models', '*.rb')].each do |model|
62
+ # dsl.instance_eval(File.read(model), model)
63
+ #end
64
+
65
+ # servers
66
+ load_servers(opts)
67
+
68
+ end
69
+
70
+
71
+ def dir_gem_root
72
+ return @dir_gem_root unless @dir_gem_root.nil?
73
+
74
+ #
75
+ spec = Gem::Specification.find_by_name("docker-builder")
76
+ @dir_gem_root = spec.gem_dir
77
+
78
+ @dir_gem_root
79
+ end
80
+
81
+ def options
82
+ return @options unless @options.nil?
83
+
84
+ @options = {}
85
+ @options
86
+ end
87
+
88
+ def servers
89
+ options[:servers]
90
+ end
91
+
92
+ def load_servers(opts)
93
+ # Identify all servers
94
+ if opts[:server]
95
+ options[:servers] = {opts[:server]=>{}}
96
+ else
97
+ # get from config
98
+ #options[:servers] = options[:servers]
99
+ end
100
+
101
+
102
+ end
103
+
104
+
105
+ private
106
+
107
+ # If :root_path is set in the options, all paths will be updated.
108
+ # Otherwise, only the paths given will be updated.
109
+ def update(opts = {})
110
+ #puts "update. opts=#{opts}"
111
+
112
+ # root_path
113
+ root_path = opts[:root_path].to_s.strip
114
+
115
+ #puts "root from opts = #{root_path}"
116
+
117
+ if root_path.empty?
118
+ #puts " set default"
119
+ root_path = File.path(Dir.getwd)
120
+ #puts "default root = #{root_path}"
121
+ end
122
+
123
+ new_root = root_path.empty? ? false : set_root_path(root_path)
124
+
125
+ puts "FINAL root= #{@root_path}"
126
+ #exit
127
+
128
+ DEFAULTS.each do |name, ending|
129
+ set_path_variable(name, options[name], ending, new_root)
130
+ end
131
+
132
+ # options
133
+ opts.each do |name, v|
134
+ set_variable(name, v)
135
+ end
136
+ end
137
+
138
+ # Sets the @root_path to the given +path+ and returns it.
139
+ # Raises an error if the given +path+ does not exist.
140
+ def set_root_path(path)
141
+ #puts "set path = #{path}"
142
+
143
+ # allows #reset! to set the default @root_path,
144
+ # then use #update to set all other paths,
145
+ # without requiring that @root_path exist.
146
+ return @root_path if path == @root_path
147
+
148
+ path = File.expand_path(path)
149
+
150
+ #puts " res root path=#{path}"
151
+
152
+ unless File.directory?(path)
153
+ raise Error, <<-EOS
154
+ Root Path Not Found
155
+ When specifying a --root-path, the path must exist.
156
+ Path was: #{ path }
157
+ EOS
158
+ end
159
+ @root_path = path
160
+ end
161
+
162
+
163
+
164
+ def set_variable(name, v)
165
+ #instance_variable_set(:"@#{name}", v) if v
166
+ options[name] = v
167
+ end
168
+
169
+ def set_path_variable(name, path, ending, root_path)
170
+ # strip any trailing '/' in case the user supplied this as part of
171
+ # an absolute path, so we can match it against File.expand_path()
172
+ path = path.to_s.sub(/\/\s*$/, '').lstrip
173
+ new_path = false
174
+ # If no path is given, the variable will not be set/updated
175
+ # unless a root_path was given. In which case the value will
176
+ # be updated with our default ending.
177
+ if path.empty?
178
+ new_path = File.join(root_path, ending) if root_path
179
+ else
180
+ # When a path is given, the variable will be set/updated.
181
+ # If the path is relative, it will be joined with root_path (if given),
182
+ # or expanded relative to PWD.
183
+ new_path = File.expand_path(path)
184
+ unless path == new_path
185
+ new_path = File.join(root_path, path) if root_path
186
+ end
187
+ end
188
+ instance_variable_set(:"@#{name}", new_path) if new_path
189
+ end
190
+
191
+ #def reset!
192
+ # @root_path = File.join(File.expand_path(ENV['HOME'] || ''), 'DockerBuilder')
193
+ # update(:root_path => @root_path)
194
+ #end
195
+ end
196
+
197
+ #reset! # set defaults on load
198
+ end
199
+ end
@@ -0,0 +1,48 @@
1
+ # encoding: utf-8
2
+
3
+ module DockerBuilder
4
+ module Config
5
+ # Context for loading user config.rb and model files.
6
+ class DSL
7
+ #class Error < Backup::Error; end
8
+ #Server = DockerBuilder::Server
9
+
10
+ attr_reader :_config_options
11
+
12
+ def initialize
13
+ @_config_options = {}
14
+ end
15
+
16
+ # Allow users to set command line path options in config.rb
17
+ [:root_path, :tmp_path].each do |name|
18
+ define_method name, lambda {|path| _config_options[name] = path }
19
+ end
20
+
21
+ # allowed options
22
+ [:servers, :common, :base].each do |name|
23
+ define_method name, lambda {|v| _config_options[name] = v }
24
+ end
25
+
26
+
27
+
28
+ # Allows users to create preconfigured models.
29
+ =begin
30
+ def preconfigure(name, &block)
31
+ unless name.is_a?(String) && name =~ /^[A-Z]/
32
+ raise Error, "Preconfigured model names must be given as a string " +
33
+ "and start with a capital letter."
34
+ end
35
+
36
+ if DSL.const_defined?(name)
37
+ raise Error, "'#{ name }' is already in use " +
38
+ "and can not be used for a preconfigured model."
39
+ end
40
+
41
+ DSL.const_set(name, Class.new(Model))
42
+ DSL.const_get(name).preconfigure(&block)
43
+ end
44
+ =end
45
+
46
+ end
47
+ end
48
+ end
@@ -0,0 +1,99 @@
1
+ # encoding: utf-8
2
+ require 'ostruct'
3
+
4
+ module DockerBuilder
5
+ module Config
6
+ module Helpers
7
+
8
+ def self.included(klass)
9
+ klass.extend ClassMethods
10
+ end
11
+
12
+ module ClassMethods
13
+
14
+ def defaults
15
+ @defaults ||= Config::Defaults.new
16
+
17
+ if block_given?
18
+ yield @defaults
19
+ else
20
+ @defaults
21
+ end
22
+ end
23
+
24
+ # Used only within the specs
25
+ def clear_defaults!
26
+ defaults.reset!
27
+ end
28
+
29
+ def deprecations
30
+ @deprecations ||= {}
31
+ end
32
+
33
+ protected
34
+
35
+
36
+
37
+ end # ClassMethods
38
+
39
+ private
40
+
41
+ ##
42
+ # Sets any pre-configured default values.
43
+ # If a default value was set for an invalid accessor,
44
+ # this will raise a NameError.
45
+ def load_defaults!
46
+ self.class.defaults._attributes.each do |name|
47
+ val = self.class.defaults.send(name)
48
+ val = val.dup rescue val
49
+ send(:"#{ name }=", val)
50
+ end
51
+ end
52
+
53
+ ##
54
+ # Check missing methods for deprecated attribute accessors.
55
+ #
56
+ # If a value is set on an accessor that has been deprecated
57
+ # using #attr_deprecate, a warning will be issued and any
58
+ # :action (Proc) specified will be called with a reference to
59
+ # the class instance and the value set on the deprecated accessor.
60
+ # See #attr_deprecate and #log_deprecation_warning
61
+ #
62
+ # Note that OpenStruct (used for setting defaults) does not allow
63
+ # multiple arguments when assigning values for members.
64
+ # So, we won't allow it here either, even though an attr_accessor
65
+ # will accept and convert them into an Array. Therefore, setting
66
+ # an option value using multiple values, whether as a default or
67
+ # directly on the class' accessor, should not be supported.
68
+ # i.e. if an option will accept being set as an Array, then it
69
+ # should be explicitly set as such. e.g. option = [val1, val2]
70
+ #
71
+ def method_missing(name, *args)
72
+ if method = name.to_s.chomp!('=')
73
+ if (len = args.count) != 1
74
+ raise ArgumentError,
75
+ "wrong number of arguments (#{ len } for 1)", caller(1)
76
+ end
77
+ end
78
+
79
+ super
80
+ end
81
+
82
+ end # Helpers
83
+
84
+ # Store for pre-configured defaults.
85
+ class Defaults < OpenStruct
86
+ # Returns an Array of all attribute method names
87
+ # that default values were set for.
88
+ def _attributes
89
+ @table.keys
90
+ end
91
+
92
+ # Used only within the specs
93
+ def reset!
94
+ @table.clear
95
+ end
96
+ end
97
+
98
+ end
99
+ end
@@ -0,0 +1,364 @@
1
+ module DockerBuilder
2
+ class Manager
3
+
4
+
5
+ def self.load_settings(server_name, opts={})
6
+ settings = Settings.load_settings_for_server(server_name, opts)
7
+
8
+ settings.set 'name', server_name
9
+
10
+ settings
11
+ end
12
+
13
+ def self.save_chef_config(settings)
14
+ require 'json'
15
+ filename = settings.filename_chef_config
16
+ FileUtils.mkdir_p(File.dirname(filename))
17
+ File.open(filename,"w+") do |f|
18
+ f.write(settings.all_attributes.to_json)
19
+ end
20
+
21
+ true
22
+ end
23
+
24
+
25
+ ###
26
+ def self.build_image(server_name, settings=nil)
27
+ puts "building image for #{server_name}..."
28
+ #puts "settings: #{settings}"
29
+ #puts "debug: #{settings['attributes']}"
30
+
31
+ #settings = load_settings(server_name)
32
+
33
+ if settings['build']['build_type']=='dockerfile'
34
+ return build_image_with_dockerfile(settings)
35
+ elsif settings['build']['build_type']=='chef'
36
+ return build_image_with_chef(settings)
37
+ end
38
+ end
39
+
40
+ def self.build_image_with_dockerfile(settings)
41
+ puts "build image with Dockerfile. Image: #{settings.image_name}"
42
+
43
+ name = settings['name']
44
+
45
+ cmd %Q(cd #{name} && docker build -t #{settings.image_name} . )
46
+
47
+ end
48
+
49
+ def self.build_image_with_chef(settings)
50
+ puts "build image with chef"
51
+
52
+ # config json
53
+ save_chef_config(settings)
54
+
55
+ # check node
56
+ cmd %Q(cd #{Config.root_path} && chef exec knife node show #{settings.chef_node_name} -c #{chef_config_knife_path})
57
+
58
+
59
+ #cmd %Q(SERVER_NAME=#{settings.name} SERVER_PATH=#{settings.dir_server_root} chef exec chef-client -z -N #{settings.image_name} -j #{settings.filename_config_json} -c #{chef_config_knife_path} #{chef_recipe_path('chef_build_image.rb')} )
60
+ res_recipe = run_chef_recipe(settings, 'chef_build_image.rb')
61
+ end
62
+
63
+
64
+
65
+
66
+ ### run
67
+
68
+ def self.run_container(server_name, settings={})
69
+ puts "creating and running container.."
70
+ #settings = load_settings(server_name)
71
+
72
+ # provision host before running container
73
+ res_install = _install_container_provision_host(settings)
74
+
75
+ # run container
76
+ res_run = _run_container(settings)
77
+
78
+
79
+ # TODO: systemd service
80
+ #res_service = _install_service_container(settings)
81
+
82
+
83
+ end
84
+
85
+ def self._install_container_provision_host(settings)
86
+ script_type = (settings['install']['host']['script_type'] rescue nil)
87
+ return true unless script_type
88
+
89
+ # run provision script on the host machine
90
+ if script_type=='chef_recipe'
91
+ return _install_container_provision_host_chef_recipe(settings)
92
+ else
93
+ # do nothing
94
+ end
95
+
96
+ true
97
+ end
98
+
99
+
100
+ #
101
+ def self._install_container_provision_host_chef_recipe(settings)
102
+ # run script on host machine
103
+ script_name = settings['install']['host']['script'] || 'install_host'
104
+
105
+ # check script exists
106
+ #script_path = "#{settings.name}/cookbooks/#{settings.name}/recipes/#{script_name}.rb"
107
+ #f = File.expand_path('.', script_path)
108
+
109
+ #if !File.exists?(f)
110
+ # puts "script not found: #{f}. Skipping"
111
+ # return false
112
+ #end
113
+
114
+ #puts "pwd= #{Dir.pwd}"
115
+ #puts "root = #{Config.root_path}"
116
+ #exit
117
+
118
+ #
119
+ res_chef = run_chef_recipe_server_recipe(settings, script_name)
120
+ #cmd %Q(SERVER_NAME=#{settings.name} chef-client -z -N #{settings.name} --override-runlist 'recipe[#{settings.name}::#{script_name}]' )
121
+
122
+ return true
123
+ end
124
+
125
+ # run
126
+ def self._run_container(settings)
127
+ puts "run container ..."
128
+
129
+ script_type = (settings['install']['node']['script_type'] rescue nil)
130
+
131
+ if script_type && script_type=='chef_recipe'
132
+ # run container and provision with chef
133
+ _run_container_chef(settings)
134
+
135
+ # ???
136
+ #_provision_container_chef_recipe(settings)
137
+ else
138
+ #_run_container_docker(settings)
139
+
140
+ # docker run
141
+ cmd %Q(docker run -d --name #{settings.container_name} #{settings.docker_ports_string} #{settings.docker_volumes_string} #{settings.docker_volumes_from_string} #{settings.docker_links_string} #{settings.run_env_variables_string} #{settings.image_name} #{settings['docker']['command']} #{settings['docker']['run_options']})
142
+
143
+ end
144
+
145
+
146
+ # fix hosts
147
+ #puts "adding hosts..."
148
+ #puts "a= #{settings.attributes}"
149
+
150
+ container_hosts = settings.node['hosts'] || []
151
+ container_hosts.each do |r|
152
+ cmd %Q(docker exec #{settings.container_name} bash -c 'echo "#{r[0]} #{r[1]}" >> /etc/hosts')
153
+ end
154
+
155
+
156
+ true
157
+ end
158
+
159
+
160
+ ### systemd service
161
+
162
+ def self._install_service_container(settings)
163
+ # not work
164
+ #cmd %Q(SERVER_NAME=#{settings.name} chef-client -z -N #{settings.name} install_container_service.rb )
165
+
166
+ # work
167
+ #cmd %Q(SERVER_NAME=#{settings.name} chef-client -z -N #{settings.name} -j config_run_install_container_service.json )
168
+
169
+ # work
170
+ #cmd %Q(SERVER_NAME=#{settings.name} chef-client -z -N #{settings.name} --override-runlist 'recipe[server-api::install_container_service]' )
171
+
172
+ #
173
+ cmd %Q(SERVER_NAME=#{settings.name} chef-client -z -N #{settings.name} -j config/config-#{settings.name}.json --override-runlist 'recipe[server-api::install_container_service]' )
174
+ end
175
+
176
+
177
+ def self._remove_service_container(settings)
178
+ cmd %Q(SERVER_NAME=#{settings.name} chef-client -z -N #{settings.name} -j config/config-#{settings.name}.json --override-runlist 'recipe[server-api::remove_container_service]' )
179
+ end
180
+
181
+
182
+ ### provision
183
+
184
+ def self._provision_container_chef_recipe(settings)
185
+ puts "provisioning container #{settings.container_name}"
186
+
187
+ #cmd %Q(SERVER_NAME=#{settings.name} chef-client -z -N #{settings.name} #{settings.name}/cookbooks/#{settings.name}/ )
188
+ end
189
+
190
+ =begin
191
+
192
+ def self._run_container_docker(settings)
193
+
194
+ end
195
+ =end
196
+
197
+ def self._run_container_chef(settings)
198
+ # generate json config for chef
199
+ save_chef_config(settings)
200
+
201
+ # run chef
202
+ #s_run = %Q(cd #{settings.name} && chef-client -z -j config.json -c ../.chef/knife.rb -N #{settings.name} ../lib/chef_container_run.rb)
203
+ #s_run = %Q(cd #{settings.name} && SERVER_NAME=#{settings.name} chef-client -z -j config.common.json -N #{settings.name} ../container.rb)
204
+ #s_run = %Q(cd #{settings.name} && SERVER_NAME=#{settings.name} chef-client -z -N #{settings.name} ../container.rb)
205
+
206
+ # good - 2016-nov-19
207
+ #cmd %Q(SERVER_NAME=#{settings.name} chef-client -z -N #{settings.name} chef_run_container.rb)
208
+
209
+ #
210
+ res_chef = run_chef_recipe(settings, 'chef_run_container.rb')
211
+
212
+ res_chef
213
+ end
214
+
215
+
216
+ def self.destroy_image(server_name, settings={})
217
+ cmd %Q(docker rmi #{settings.image_name} )
218
+ cmd %Q(docker rm -f chef.converge.#{settings.image_name} )
219
+
220
+ # delete chef data
221
+ if settings['build']['build_type']=='chef'
222
+ return destroy_image_chef(settings)
223
+ end
224
+ end
225
+
226
+
227
+ def self.destroy_image_chef(settings)
228
+ puts "destroying image with chef..."
229
+
230
+ # config json
231
+ save_chef_config(settings)
232
+
233
+ # destroy temp container
234
+ cmd %Q(docker rm -f chef-converge.#{settings.image_name} )
235
+
236
+ #
237
+ cmd %Q(cd #{Config.root_path} && chef exec knife node delete #{settings.chef_node_name} -y -c #{chef_config_knife_path})
238
+
239
+ #cmd %Q(SERVER_NAME=#{settings.name} chef-client -z -N #{settings.name} chef_destroy_image.rb)
240
+ #cmd %Q(SERVER_NAME=#{settings.name} SERVER_PATH=#{settings.dir_server_root} chef exec chef-client -z -N #{settings.image_name} -j #{settings.filename_config_json} -c #{chef_config_knife_path} #{chef_recipe_path('chef_destroy_image.rb')} )
241
+
242
+ res_recipe = run_chef_recipe(settings, 'chef_destroy_image.rb')
243
+
244
+ chef_remove_data(settings)
245
+
246
+ # work - before 2016-nov-19
247
+ #cmd %Q(cd #{Config.root_path} && chef exec knife node delete #{settings.chef_node_name} -y -c #{chef_config_knife_path})
248
+
249
+ # clean chef client, node
250
+ #cmd %Q(cd #{Config.root_path} && rm -f #{settings.filename_chef_node_json} )
251
+ #cmd %Q(cd #{Config.root_path} && rm -f #{settings.filename_chef_client_json} )
252
+ end
253
+
254
+ ###
255
+
256
+
257
+ def self.destroy_container(server_name, settings)
258
+ puts "destroying container #{server_name}..."
259
+
260
+ # TODO: stop, remove systemd service
261
+ #res_service = _remove_service_container(settings)
262
+
263
+ #
264
+ cmd %Q(docker rm -f #{settings.container_name} )
265
+
266
+
267
+
268
+ # if chef
269
+ if settings['build']['build_type']=='chef'
270
+ return destroy_container_chef(settings)
271
+ end
272
+
273
+ #
274
+ return true
275
+ end
276
+
277
+
278
+ def self.destroy_container_chef(settings)
279
+ #
280
+ res_chef = run_chef_recipe(settings, 'chef_destroy_container.rb')
281
+ #cmd %Q(SERVER_NAME=#{settings.name} chef-client -z -N #{settings.name} chef_destroy_container.rb)
282
+
283
+ #
284
+ chef_remove_data(settings)
285
+
286
+ end
287
+
288
+
289
+ def self.start_container(server_name)
290
+ settings = load_settings(server_name)
291
+
292
+ #
293
+ cmd %Q(docker start #{settings.container_name} )
294
+
295
+ return true
296
+ end
297
+
298
+ ### run task on running container
299
+ def self.exec_task(server_name, recipe_name)
300
+ #raise 'not implemented'
301
+
302
+ settings = load_settings(server_name)
303
+
304
+ # check script exists
305
+ script_path = "#{settings.name}/cookbooks/#{settings.name}/recipes/#{recipe_name}.rb"
306
+ f = File.expand_path('.', script_path)
307
+
308
+ if !File.exists?(f)
309
+ puts "script not found: #{f}. Skipping"
310
+ return false
311
+ end
312
+
313
+ #
314
+ cmd %Q(SERVER_NAME=#{settings.name} chef-client -z --override-runlist 'recipe[server-api::exec_container]' )
315
+ #cmd %Q(SERVER_NAME=#{settings.name} chef-client -z -N #{settings.name} --override-runlist 'recipe[#{settings.name}::#{recipe_name}]' )
316
+ #cmd %Q(SERVER_NAME=#{settings.name} chef-client -z -N #{settings.name} chef_exec_container.rb )
317
+
318
+ return true
319
+ end
320
+
321
+ ###
322
+
323
+ def self.cmd(s)
324
+ puts "running: #{s}"
325
+
326
+ res = nil
327
+ Bundler.with_clean_env do
328
+ res = `#{s}`
329
+ end
330
+
331
+ puts "#{res}"
332
+ end
333
+
334
+
335
+ ### helpers - chef
336
+
337
+ def self.run_chef_recipe(settings, recipe_rb)
338
+ cmd %Q(cd #{Config.root_path} && SERVER_NAME=#{settings.name} SERVER_PATH=#{settings.dir_server_root} chef exec chef-client -z -N #{settings.image_name} -j #{settings.filename_config_json} -c #{chef_config_knife_path} #{chef_recipe_path(recipe_rb)} )
339
+ end
340
+
341
+ def self.run_chef_recipe_server_recipe(settings, server_recipe)
342
+ cmd %Q(cd #{Config.root_path} && SERVER_NAME=#{settings.name} SERVER_PATH=#{settings.dir_server_root} chef exec chef-client -z -N #{settings.image_name} -c #{chef_config_knife_path} --override-runlist 'recipe[#{settings.name}::#{server_recipe}]' )
343
+ end
344
+
345
+
346
+ def self.chef_config_knife_path
347
+ "#{Config.dir_gem_root}/lib/docker_builder/chef/.chef/knife.rb"
348
+ end
349
+
350
+ def self.chef_recipe_path(p)
351
+ "#{Config.dir_gem_root}/lib/docker_builder/chef/#{p}"
352
+ end
353
+
354
+
355
+ def self.chef_remove_data(settings)
356
+ #
357
+ cmd %Q(cd #{Config.root_path} && chef exec knife node delete #{settings.chef_node_name} -y -c #{chef_config_knife_path})
358
+
359
+ # clean chef client, node
360
+ cmd %Q(cd #{Config.root_path} && rm -f #{settings.filename_chef_node_json} )
361
+ cmd %Q(cd #{Config.root_path} && rm -f #{settings.filename_chef_client_json} )
362
+ end
363
+ end
364
+ end