Module: Performa::Images

Extended by:
ShellHelper
Defined in:
lib/performa/images.rb

Constant Summary collapse

CACHED_IMAGES_NAME =
"performa_env"

Class Method Summary collapse

Methods included from ShellHelper

run_capture_command, run_command, run_container_command, run_no_capture_command

Class Method Details

.cache_container(container_id, tag:) ⇒ Object



77
78
79
# File 'lib/performa/images.rb', line 77

def cache_container(container_id, tag:)
  run_command("docker commit #{container_id} #{CACHED_IMAGES_NAME}:#{tag}")
end

.cache_presence(hash) ⇒ Object



60
61
62
# File 'lib/performa/images.rb', line 60

def cache_presence(hash)
  presence("#{CACHED_IMAGES_NAME}:#{hash}")
end

.clear_cachedObject



81
82
83
84
85
86
# File 'lib/performa/images.rb', line 81

def clear_cached
  ids = run_command("docker images --filter=reference='#{CACHED_IMAGES_NAME}' --format '{{.ID}}'").split("\n")
  ids.each do |id|
    run_command("docker rmi -f #{id.strip}")
  end
end

.container_id_for_cached_image(env) ⇒ Object



30
31
32
33
34
35
36
37
38
39
# File 'lib/performa/images.rb', line 30

def container_id_for_cached_image(env)
  commands = env.stage.commands
  last_cached_stage_command = commands.reverse.find(&:cache)
  return unless last_cached_stage_command

  container_id = start_image_container(last_cached_stage_command.cache, volumes: env.volumes)
  uncached_commands = commands[commands.index(last_cached_stage_command) + 1..-1]
  run_and_cache_commands(uncached_commands, container_id: container_id)
  container_id
end

.presence(image) ⇒ Object



56
57
58
# File 'lib/performa/images.rb', line 56

def presence(image)
  image unless run_command("docker images -q #{image}").empty?
end

.process(env, config:) ⇒ Object



10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
# File 'lib/performa/images.rb', line 10

def process(env, config:)
  if config.cachable_envs?
    container_id = container_id_for_cached_image(env)
    return container_id if container_id
  end

  pull_if_missing(env.image)
  container_id = start_image_container(env.image, volumes: env.volumes)

  if env.stage&.commands
    run_and_cache_commands(
      env.stage.commands,
      cacheable_envs: config.cachable_envs?,
      container_id: container_id
    )
  end

  container_id
end

.pull(image) ⇒ Object



48
49
50
# File 'lib/performa/images.rb', line 48

def pull(image)
  run_command("docker pull #{image}", no_capture: true)
end

.pull_if_missing(image) ⇒ Object



52
53
54
# File 'lib/performa/images.rb', line 52

def pull_if_missing(image)
  pull(image) unless presence(image)
end

.run_and_cache_commands(commands, cacheable_envs: true, container_id:) ⇒ Object



41
42
43
44
45
46
# File 'lib/performa/images.rb', line 41

def run_and_cache_commands(commands, cacheable_envs: true, container_id:)
  commands.each do |command|
    run_container_command(container_id, command.value, success_only: false)
    cache_container(container_id, tag: command.hash) if cacheable_envs
  end
end

.start_image_container(image, volumes: []) ⇒ Object



64
65
66
67
68
69
70
71
72
73
74
75
# File 'lib/performa/images.rb', line 64

def start_image_container(image, volumes: [])
  volumes_options = volumes.map do |volume|
    volume[0] = Dir.pwd if volume[0] == "."
    " -v #{volume}"
  end.join

  command = "docker run #{volumes_options} -d #{image} tail -f /dev/null"

  run_command(command).strip.tap do |container_id|
    ContainerRegistry.add(container_id)
  end
end