service_image_builder 0.1.2 → 0.1.3
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/.gitignore +1 -0
- data/Dockerfile +2 -0
- data/Gemfile.lock +14 -8
- data/README.md +6 -3
- data/bin/sib +13 -21
- data/lib/service_image_builder.rb +6 -1
- data/lib/service_image_builder/errors.rb +10 -0
- data/lib/service_image_builder/image.rb +59 -3
- data/lib/service_image_builder/logger.rb +14 -0
- data/lib/service_image_builder/version.rb +1 -1
- data/service_image_builder.gemspec +3 -0
- metadata +52 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 900269f5179222514b60a9801fcb2185eca190de7549de06f0c3581acfed50a9
|
4
|
+
data.tar.gz: '0395906fef0ff745d19954216b22ee62afe597d52b8d6a1389cab9228f006b38'
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: ae08276865478e406ba0982559f8dcf8d02201b03067d54476db6360ccca516408d6f01d3b2280cf968aa3b3bcfe04bdb1663c8f58f5ab8dfb6be16f06b220cb
|
7
|
+
data.tar.gz: 1e505048f31b20719cf88505c1e5d49c877dd4bbf1bd171aa979d141c35a9c392b9c09e54dd08ef21f10ac7c1c7c288945216ec39907ad835d693c98a972b416
|
data/.gitignore
CHANGED
data/Dockerfile
CHANGED
data/Gemfile.lock
CHANGED
@@ -1,19 +1,23 @@
|
|
1
1
|
PATH
|
2
2
|
remote: .
|
3
3
|
specs:
|
4
|
-
service_image_builder (0.1.
|
4
|
+
service_image_builder (0.1.3)
|
5
5
|
activesupport (~> 5.2)
|
6
|
+
awesome_print (~> 1.8)
|
6
7
|
docker-api (~> 1.34)
|
8
|
+
logger (~> 1.4, >= 1.4.2)
|
9
|
+
oj (~> 3.10)
|
7
10
|
|
8
11
|
GEM
|
9
12
|
remote: https://rubygems.org/
|
10
13
|
specs:
|
11
|
-
activesupport (5.2.
|
14
|
+
activesupport (5.2.4.1)
|
12
15
|
concurrent-ruby (~> 1.0, >= 1.0.2)
|
13
16
|
i18n (>= 0.7, < 2)
|
14
17
|
minitest (~> 5.1)
|
15
18
|
tzinfo (~> 1.1)
|
16
19
|
ast (2.4.0)
|
20
|
+
awesome_print (1.8.0)
|
17
21
|
byebug (11.0.1)
|
18
22
|
coderay (1.1.2)
|
19
23
|
concurrent-ruby (1.1.5)
|
@@ -21,13 +25,15 @@ GEM
|
|
21
25
|
docker-api (1.34.2)
|
22
26
|
excon (>= 0.47.0)
|
23
27
|
multi_json
|
24
|
-
excon (0.
|
25
|
-
i18n (1.
|
28
|
+
excon (0.71.1)
|
29
|
+
i18n (1.7.0)
|
26
30
|
concurrent-ruby (~> 1.0)
|
27
31
|
jaro_winkler (1.5.2)
|
32
|
+
logger (1.4.2)
|
28
33
|
method_source (0.9.2)
|
29
|
-
minitest (5.
|
30
|
-
multi_json (1.
|
34
|
+
minitest (5.13.0)
|
35
|
+
multi_json (1.14.1)
|
36
|
+
oj (3.10.0)
|
31
37
|
parallel (1.17.0)
|
32
38
|
parser (2.6.3.0)
|
33
39
|
ast (~> 2.4.0)
|
@@ -61,7 +67,7 @@ GEM
|
|
61
67
|
unicode-display_width (>= 1.4.0, < 1.7)
|
62
68
|
ruby-progressbar (1.10.1)
|
63
69
|
thread_safe (0.3.6)
|
64
|
-
tzinfo (1.2.
|
70
|
+
tzinfo (1.2.6)
|
65
71
|
thread_safe (~> 0.1)
|
66
72
|
unicode-display_width (1.6.0)
|
67
73
|
|
@@ -77,4 +83,4 @@ DEPENDENCIES
|
|
77
83
|
service_image_builder!
|
78
84
|
|
79
85
|
BUNDLED WITH
|
80
|
-
2.0.
|
86
|
+
2.0.2
|
data/README.md
CHANGED
@@ -7,10 +7,13 @@ registry.
|
|
7
7
|
|
8
8
|
SIB is configured through environment variables:
|
9
9
|
|
10
|
-
- CI_COMMIT_SHA — Automatically provided by gitlab CI; commit sha from source
|
10
|
+
- CI_COMMIT_SHA — Automatically provided by gitlab CI; commit sha from source
|
11
|
+
control; # TODO pick this up from VCS directly if unset
|
11
12
|
- SIB_BUILD_DIR — Docker build context directory; optional & defaults to $PWD
|
12
|
-
- SIB_DOCKER_FILE — Dockerfile to use in build; optional & defaults to
|
13
|
+
- SIB_DOCKER_FILE — Dockerfile to use in build; optional & defaults to
|
14
|
+
'Dockerfile'
|
13
15
|
- SIB_IMAGE_REPO — *required* Docker repo
|
14
16
|
- SIB_REGISTRY_USER — *required* Username to authenticate with the registry
|
15
17
|
- SIB_REGISTRY_PASS — *required* Password to authenticate with the registry
|
16
|
-
- SIB_UPSTREAM_TAG — Upstream tag to compare against and push to; optional &
|
18
|
+
- SIB_UPSTREAM_TAG — Upstream tag to compare against and push to; optional &
|
19
|
+
defaults to 'latest'
|
data/bin/sib
CHANGED
@@ -16,7 +16,7 @@ require_relative '../lib/service_image_builder.rb'
|
|
16
16
|
|
17
17
|
build_dir = ENV.fetch('SIB_BUILD_DIR', '.')
|
18
18
|
current_commit_id = ENV.fetch('CI_COMMIT_SHA')
|
19
|
-
|
19
|
+
dockerfile = ENV.fetch('SIB_DOCKER_FILE', 'Dockerfile')
|
20
20
|
image_repo = ENV.fetch('SIB_IMAGE_REPO')
|
21
21
|
image_upstream_tag = ENV.fetch('SIB_UPSTREAM_TAG', 'latest')
|
22
22
|
registry_pass = ENV.fetch('SIB_REGISTRY_PASS')
|
@@ -25,31 +25,23 @@ squash = ENV.fetch('SIB_SQUASH', false)
|
|
25
25
|
|
26
26
|
Docker.authenticate!('username' => registry_user, 'password' => registry_pass)
|
27
27
|
|
28
|
-
|
29
|
-
Docker::Image.create('fromImage' => "#{image_repo}:#{image_upstream_tag}")
|
30
|
-
rescue Docker::Error::NotFoundError
|
31
|
-
nil
|
32
|
-
end
|
33
|
-
|
34
|
-
upstream = SIB::Image.new(image: upstream_docker_image) unless upstream_docker_image.nil?
|
28
|
+
upstream = SIB::Image.import(repo: image_repo, tag: image_upstream_tag)
|
35
29
|
|
36
|
-
|
37
|
-
|
38
|
-
|
30
|
+
build_args = {
|
31
|
+
repo: image_repo,
|
32
|
+
build_dir: build_dir,
|
33
|
+
dockerfile: dockerfile,
|
34
|
+
labels: {
|
39
35
|
'maintainer' => 'Slush Systems <ci@slush.systems>',
|
40
36
|
'systems.slush.commit-id' => current_commit_id,
|
41
37
|
'systems.slush.timestamp' => Time.now.utc.iso8601
|
42
|
-
}
|
43
|
-
|
38
|
+
},
|
39
|
+
squash: squash
|
44
40
|
}
|
45
|
-
canary = SIB::Image.new(
|
46
|
-
image: Docker::Image.build_from_dir(build_dir, canary_build_args)
|
47
|
-
)
|
48
41
|
|
49
|
-
|
50
|
-
canary.image.tag(repo: image_repo, tag: image_upstream_tag)
|
51
|
-
canary.image.push(nil, tag: image_upstream_tag)
|
42
|
+
canary = SIB::Image.build(build_args)
|
52
43
|
|
53
|
-
|
54
|
-
canary.
|
44
|
+
if upstream.nil? || (canary <=> upstream).positive?
|
45
|
+
canary.push_tag(tag: image_upstream_tag)
|
46
|
+
canary.push_tag(tag: canary.factor_hash)
|
55
47
|
end
|
@@ -5,8 +5,13 @@ require 'active_support/core_ext/time' # cherry pick Time extensions
|
|
5
5
|
require 'active_support/core_ext/numeric/time' # cherry pick Time extensions
|
6
6
|
require 'active_support/core_ext/integer/time' # cherry pick Time extensions
|
7
7
|
require 'active_support/core_ext/object/blank' # cherry pick Object#blank?
|
8
|
+
require 'awesome_print'
|
8
9
|
require 'digest'
|
9
10
|
require 'docker'
|
10
|
-
require '
|
11
|
+
require 'logger'
|
12
|
+
require 'oj'
|
13
|
+
require 'pathname'
|
11
14
|
|
15
|
+
require_relative 'service_image_builder/errors'
|
16
|
+
require_relative 'service_image_builder/logger'
|
12
17
|
require_relative 'service_image_builder/image'
|
@@ -1,11 +1,42 @@
|
|
1
1
|
# frozen_string_literal: true
|
2
2
|
|
3
3
|
module SIB
|
4
|
-
# SIB::
|
4
|
+
# SIB::ImageError is raised when an unrecoverable error occurs in Image
|
5
|
+
# operations
|
6
|
+
class ImageError < SIB::Error; end
|
7
|
+
# SIB::Image represents a docker image
|
5
8
|
class Image
|
6
|
-
attr_accessor :image
|
7
|
-
|
9
|
+
attr_accessor :image, :repo
|
10
|
+
|
11
|
+
def self.build(repo:, build_dir:, dockerfile: 'Dockerfile', labels: {}, squash: false)
|
12
|
+
build_dir ||= Dir.pwd
|
13
|
+
build_args = {
|
14
|
+
'dockerfile' => dockerfile,
|
15
|
+
'labels' => labels_to_json(labels),
|
16
|
+
'squash' => squash
|
17
|
+
}
|
18
|
+
SIB.log.info("Building #{repo} from #{Pathname.new(build_dir).join(dockerfile)}")
|
19
|
+
|
20
|
+
# TODO: maybe have parse_api_response do the logging & just raise an error
|
21
|
+
# when one gets detected
|
22
|
+
image = Docker::Image.build_from_dir(build_dir, build_args) do |resp|
|
23
|
+
parse_api_response(resp).each do |r|
|
24
|
+
SIB.log.info(r['stream'].rstrip) if r.key?('stream')
|
25
|
+
end
|
26
|
+
end
|
27
|
+
|
28
|
+
new(repo: repo, image: image)
|
29
|
+
end
|
30
|
+
|
31
|
+
def self.import(repo:, tag:)
|
32
|
+
new(repo: repo, image: Docker::Image.create('fromImage' => "#{repo}:#{tag}"))
|
33
|
+
rescue Docker::Error::NotFoundError
|
34
|
+
nil
|
35
|
+
end
|
36
|
+
|
37
|
+
def initialize(repo:, image:)
|
8
38
|
@image = image
|
39
|
+
@repo = repo
|
9
40
|
end
|
10
41
|
|
11
42
|
# Image#<=> is a comparison operator implementation for SIB::Image. If the
|
@@ -52,8 +83,33 @@ module SIB
|
|
52
83
|
end
|
53
84
|
end
|
54
85
|
|
86
|
+
def push_tag(tag:)
|
87
|
+
image.tag(repo: repo, tag: tag)
|
88
|
+
image.push(nil, tag: tag) do |msg|
|
89
|
+
SIB::Image.parse_api_response(msg).each do |r|
|
90
|
+
raise SIB::ImageError, r if r.key?('error')
|
91
|
+
|
92
|
+
SIB.log.info(r)
|
93
|
+
end
|
94
|
+
end
|
95
|
+
end
|
96
|
+
|
55
97
|
def timestamp
|
56
98
|
@timestamp ||= Time.parse(labels.fetch('systems.slush.timestamp', nil))
|
57
99
|
end
|
100
|
+
|
101
|
+
class << self
|
102
|
+
def labels_to_json(labels)
|
103
|
+
Oj.dump(labels || {})
|
104
|
+
rescue Oj::Error => e
|
105
|
+
raise ImageError, "Couldn't convert labels to json: #{e.message}"
|
106
|
+
end
|
107
|
+
|
108
|
+
def parse_api_response(response)
|
109
|
+
response.split("\r\n").map { |r| Oj.load(r) }
|
110
|
+
rescue Oj::Error => e
|
111
|
+
raise ImageError, "Couldn't parse api repsonse: #{e.message}"
|
112
|
+
end
|
113
|
+
end
|
58
114
|
end
|
59
115
|
end
|
@@ -0,0 +1,14 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
# SIB is a module for building Slush Systems docker images
|
4
|
+
module SIB
|
5
|
+
# SIB::log serves as a module-level logging method
|
6
|
+
def self.log
|
7
|
+
@log ||= Logger.new(STDOUT).tap do |lager|
|
8
|
+
lager.formatter = proc do |severity, datetime, progname, msg|
|
9
|
+
out = msg.is_a?(String) ? msg : msg.ai(multiline: false)
|
10
|
+
"#{datetime} #{severity} #{progname}: #{out}\n"
|
11
|
+
end
|
12
|
+
end
|
13
|
+
end
|
14
|
+
end
|
@@ -31,7 +31,10 @@ registry.'
|
|
31
31
|
spec.require_paths = ['lib']
|
32
32
|
|
33
33
|
spec.add_dependency 'activesupport', '~> 5.2'
|
34
|
+
spec.add_dependency 'awesome_print', '~> 1.8'
|
34
35
|
spec.add_dependency 'docker-api', '~> 1.34'
|
36
|
+
spec.add_dependency 'logger', '~> 1.4', '>= 1.4.2'
|
37
|
+
spec.add_dependency 'oj', '~> 3.10'
|
35
38
|
|
36
39
|
spec.add_development_dependency 'bundler', '~> 2'
|
37
40
|
spec.add_development_dependency 'pry-byebug', '~> 3.7'
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: service_image_builder
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.1.
|
4
|
+
version: 0.1.3
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Eric Jacobs
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2019-12-
|
11
|
+
date: 2019-12-31 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: activesupport
|
@@ -24,6 +24,20 @@ dependencies:
|
|
24
24
|
- - "~>"
|
25
25
|
- !ruby/object:Gem::Version
|
26
26
|
version: '5.2'
|
27
|
+
- !ruby/object:Gem::Dependency
|
28
|
+
name: awesome_print
|
29
|
+
requirement: !ruby/object:Gem::Requirement
|
30
|
+
requirements:
|
31
|
+
- - "~>"
|
32
|
+
- !ruby/object:Gem::Version
|
33
|
+
version: '1.8'
|
34
|
+
type: :runtime
|
35
|
+
prerelease: false
|
36
|
+
version_requirements: !ruby/object:Gem::Requirement
|
37
|
+
requirements:
|
38
|
+
- - "~>"
|
39
|
+
- !ruby/object:Gem::Version
|
40
|
+
version: '1.8'
|
27
41
|
- !ruby/object:Gem::Dependency
|
28
42
|
name: docker-api
|
29
43
|
requirement: !ruby/object:Gem::Requirement
|
@@ -38,6 +52,40 @@ dependencies:
|
|
38
52
|
- - "~>"
|
39
53
|
- !ruby/object:Gem::Version
|
40
54
|
version: '1.34'
|
55
|
+
- !ruby/object:Gem::Dependency
|
56
|
+
name: logger
|
57
|
+
requirement: !ruby/object:Gem::Requirement
|
58
|
+
requirements:
|
59
|
+
- - "~>"
|
60
|
+
- !ruby/object:Gem::Version
|
61
|
+
version: '1.4'
|
62
|
+
- - ">="
|
63
|
+
- !ruby/object:Gem::Version
|
64
|
+
version: 1.4.2
|
65
|
+
type: :runtime
|
66
|
+
prerelease: false
|
67
|
+
version_requirements: !ruby/object:Gem::Requirement
|
68
|
+
requirements:
|
69
|
+
- - "~>"
|
70
|
+
- !ruby/object:Gem::Version
|
71
|
+
version: '1.4'
|
72
|
+
- - ">="
|
73
|
+
- !ruby/object:Gem::Version
|
74
|
+
version: 1.4.2
|
75
|
+
- !ruby/object:Gem::Dependency
|
76
|
+
name: oj
|
77
|
+
requirement: !ruby/object:Gem::Requirement
|
78
|
+
requirements:
|
79
|
+
- - "~>"
|
80
|
+
- !ruby/object:Gem::Version
|
81
|
+
version: '3.10'
|
82
|
+
type: :runtime
|
83
|
+
prerelease: false
|
84
|
+
version_requirements: !ruby/object:Gem::Requirement
|
85
|
+
requirements:
|
86
|
+
- - "~>"
|
87
|
+
- !ruby/object:Gem::Version
|
88
|
+
version: '3.10'
|
41
89
|
- !ruby/object:Gem::Dependency
|
42
90
|
name: bundler
|
43
91
|
requirement: !ruby/object:Gem::Requirement
|
@@ -135,7 +183,9 @@ files:
|
|
135
183
|
- bin/setup
|
136
184
|
- bin/sib
|
137
185
|
- lib/service_image_builder.rb
|
186
|
+
- lib/service_image_builder/errors.rb
|
138
187
|
- lib/service_image_builder/image.rb
|
188
|
+
- lib/service_image_builder/logger.rb
|
139
189
|
- lib/service_image_builder/version.rb
|
140
190
|
- service_image_builder.gemspec
|
141
191
|
homepage: https://slush.systems/
|