class RubyYacht::Runner::BuildImages
This command builds the images for the system.
Public Class Methods
The identifier for the command.
# File lib/ruby_yacht/runner/build_images.rb, line 7 def self.command; 'build_images'; end
The description for the command.
# File lib/ruby_yacht/runner/build_images.rb, line 10 def self.description "Build images for your environment" end
Public Instance Methods
This method builds an image.
This will copy a Dockerfile template from a folder underneath the ‘images` folder, as well as any other files in that folder, into the tmp folder. It will then evaluate the Dockerfile.erb file, using the binding from the current context, and write it to the Dockerfile in the tmp folder. It will then build the image, and clear out the tmp folder.
Depending on the image type, it may also copy and interpret other template files. For instance, for app containers we also have erb files for the ‘startup.bash` and `before_startup.bash` scripts.
### Parameters
-
**folder_name: String** The name of the folder containing the
Dockerfile and related files.
-
**image_name: String** The name for the new image. If this is not
provided, the image name will be the current project's prefix, followed by a dash, followed by the folder name.
# File lib/ruby_yacht/runner/build_images.rb, line 85 def build_image(folder_name, image_name = nil) Dir[File.join(File.dirname(File.dirname(__FILE__)), 'images', folder_name, '*')].each do |path| FileUtils.cp(path, File.join('tmp', File.basename(path))) end set_image_settings(folder_name) fetch_behaviors(@hook_servers, @hook_events).each do |behavior| next unless behavior.is_a?(RubyYacht::Hook::CopyFileBehavior) FileUtils.cp behavior.file_path, "tmp" end @templates.each do |template_name| File.open(File.join('tmp', template_name), 'w') do |file| template_contents = File.read(File.join('tmp', template_name + '.erb')) file_contents = ERB.new(template_contents, nil, '<>').result(binding) file_contents.gsub!(/\n\n\n+/, "\n\n") file_contents.gsub!(/\n*\Z/, "") file.write(file_contents) end end image_name ||= "#{@project.system_prefix}-#{folder_name}" docker "build -t #{image_name} tmp" FileUtils.rm(Dir[File.join("tmp", "*")]) end
This method builds the images for a project.
### Parameters
-
**project: Project** The project we are building.
# File lib/ruby_yacht/runner/build_images.rb, line 37 def build_images(project) @project = project project.apps.map(&:server_type).uniq.each do |type_name| @server_type = RubyYacht.configuration.find_server_type(type_name) build_image 'app-dependencies', "#{@project.system_prefix}-#{@server_type.name}-app-dependencies" end @app_server_type = RubyYacht.configuration.find_server_type(project.apps.first.server_type) project.databases.select(&:local?).each do |database| @database = database @server_type = RubyYacht.configuration.find_server_type(@database.server_type) build_image 'database', @database.container_name end @database = nil @project.apps.each do |app| @app = app @server_type = RubyYacht.configuration.find_server_type(@app.server_type) build_image 'app', @app.container_name end @app = nil project.web_servers.each do |server| @server = server build_image 'web', @server.container_name end end
This method includes commands for copying script files for the hooks for the current app type.
### Parameters
-
**servers: Database/App/Array**: The server or servers whose hooks we
are running.
-
**event_types: [Symbol]** The events whose hooks we should include.
### Returns
A String with the contents of the Dockerfile for copying the script.
# File lib/ruby_yacht/runner/build_images.rb, line 215 def copy_hooks(servers, event_types) result = "" fetch_behaviors(servers, event_types).each do |behavior| next unless behavior.is_a?(RubyYacht::Hook::CopyFileBehavior) result += behavior.dockerfile_command + "\n" end result end
This method includes the hooks for an event in a Dockerfile.
It will run the commands for the before hooks, then the during hooks, then the after hooks.
### Parameters
-
**servers: Database/App/Array**: The server or servers whose hooks we
are running.
-
**event_type: Symbol** The event whose hooks we are running.
-
**times: [Symbol]** The event times whose hooks we want to
include. You can also pass a symbol to this method, which will cause it to include only that event time.
-
**options: [Hash]** Additional flags for customizing the output.
At this time, the only option is `in_bash`, which indicates whether the commands are running in bash rather than a Dockerfile.
-
block This also takes a block, which should yield
fixed contents for the "during" section of the event.
### Returns
A String with the contents of the Dockerfile for running the hooks.
# File lib/ruby_yacht/runner/build_images.rb, line 177 def include_event(servers, event_type, times = [:before, :during, :after], options = {}) result = "" if times.is_a?(Symbol) times = [times] end times.each do |time| if time == :during && block_given? result += yield result += "\n" next end fetch_behaviors(servers, [event_type], time).each do |behavior| behavior.context = self if options[:in_bash] result += "#{behavior.shell_command}\n" else result += "#{behavior.dockerfile_command}\n" end end end result end
This method runs the logic for the command.
# File lib/ruby_yacht/runner/build_images.rb, line 15 def run FileUtils.mkdir_p 'tmp' projects.each do |project| log "Building images for #{project.name}" docker "network create #{project.system_prefix} 2> /dev/null" id_path = File.join(ENV['HOME'], '.ssh', 'id_rsa') tmp_id_path = File.join('tmp', 'id_rsa') FileUtils.cp(id_path, tmp_id_path) if File.exist?(id_path) build_images(project) end true end
This method establishes settings for building an image.
This will set the ‘@templates`, `@hook_events`, and `@hook_servers` instance variables.
### Parameters
-
**folder_name: String** The name of the folder containing the image
files.
# File lib/ruby_yacht/runner/build_images.rb, line 123 def set_image_settings(folder_name) @templates = case folder_name when 'app' then ['Dockerfile', 'before_startup.bash', 'startup.bash'] when 'database' then ['Dockerfile', 'startup.bash'] when 'web' then ['Dockerfile'] else ['Dockerfile'] end @hook_events = case folder_name when 'app' then [:startup, :build_checkout, :build_new_app, :cleanup] when 'app-dependencies' then [:initialize_app_environment, :install_libraries, :cleanup] when 'database' then [:create_databases, :install_libraries, :load_database_seeds, :cleanup] when 'web' then [:install_libraries, :add_project_landing, :add_app_config, :cleanup] else [] end @hook_servers = case folder_name when 'database' then [@database] when 'app' then [@app] when 'app-dependencies' then @project.apps when 'web' then [@server] else [] end end
Private Instance Methods
This method fetches the behaviors for the hooks for an event.
-
**servers: Database/App/Array**: The server or servers whose hooks we
are running.
-
**event_types: Array**: The events for the hooks we are running.
-
**event_time: Symbol**: The time relative to the event for the hooks
we are running. If this is nil, it will include all event times.
# File lib/ruby_yacht/runner/build_images.rb, line 236 def fetch_behaviors(servers, event_types, event_time = nil) unless servers.is_a?(Array) servers = [servers] end hooks = servers.collect do |server| event_types.collect do |type| RubyYacht.configuration.fetch_hooks(server, type) end end.flatten.uniq hooks = hooks.select do |hook| event_time.nil? || event_time == hook.event_time end hooks.map(&:behaviors).flatten end