stax-helm 0.0.3 → 0.0.8
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.
- checksums.yaml +4 -4
- data/lib/stax/helm.rb +5 -0
- data/lib/stax/helm/base.rb +16 -0
- data/lib/stax/helm/cmd.rb +1 -4
- data/lib/stax/helm/deployment.rb +56 -0
- data/lib/stax/helm/ingress.rb +19 -0
- data/lib/stax/helm/kubectl.rb +11 -41
- data/lib/stax/helm/pod.rb +49 -0
- data/lib/stax/helm/runcmd.rb +101 -0
- data/lib/stax/helm/stern.rb +2 -1
- data/lib/stax/helm/version.rb +1 -1
- metadata +11 -6
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 90efb4bc5fd77b16200e4693747b303df7644ebfe21149d715327a56397f1d25
|
4
|
+
data.tar.gz: 19d2b39ef1cbd165dbd32091f317f8c11b12624d381920bdffd5295b8b8c5b68
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 5566799f8341ace21b46a2ec7c3d90a3c5dc11d26f54c7efa1dc593df439e6dd59732286153823995573a53337252f8249000d54f26dd4813e72ebad23e943ff
|
7
|
+
data.tar.gz: 8d1b6ca7b1e7465cac0f77754438ccff9ad880e12bf7d1eb9b2c58a6f48921bbad3471696ab4cd2e609aeee1cd749c0ce6304c23ad248ece555a2291140c5785
|
data/lib/stax/helm.rb
CHANGED
@@ -1,4 +1,9 @@
|
|
1
|
+
require 'stax/helm/base'
|
1
2
|
require 'stax/helm/cmd'
|
2
3
|
require 'stax/helm/kubectl'
|
4
|
+
require 'stax/helm/ingress'
|
5
|
+
require 'stax/helm/pod'
|
6
|
+
require 'stax/helm/deployment'
|
3
7
|
require 'stax/helm/stern'
|
8
|
+
require 'stax/helm/runcmd'
|
4
9
|
Stax.add_command(:helm, Stax::Helm::Cmd)
|
@@ -0,0 +1,16 @@
|
|
1
|
+
module Stax
|
2
|
+
class Base < Thor
|
3
|
+
|
4
|
+
no_commands do
|
5
|
+
def helm_release_name
|
6
|
+
@_helm_release_name ||= helm_safe("#{app_name}-#{branch_name}")
|
7
|
+
end
|
8
|
+
|
9
|
+
## make string safe to use in naming helm stuff
|
10
|
+
def helm_safe(string)
|
11
|
+
string.slice(0, 53).gsub(/[\W_]/, '-').downcase
|
12
|
+
end
|
13
|
+
end
|
14
|
+
|
15
|
+
end
|
16
|
+
end
|
data/lib/stax/helm/cmd.rb
CHANGED
@@ -1,13 +1,10 @@
|
|
1
1
|
module Stax
|
2
2
|
module Helm
|
3
|
+
|
3
4
|
class Cmd < Base
|
4
5
|
class_option :recon, aliases: '--just-print', type: :boolean, default: false, desc: 'print command that would be run'
|
5
6
|
|
6
7
|
no_commands do
|
7
|
-
def helm_release_name
|
8
|
-
@_helm_release_name ||= "#{app_name}-#{branch_name}"
|
9
|
-
end
|
10
|
-
|
11
8
|
## location of helm chart
|
12
9
|
def helm_dir
|
13
10
|
File.join(Stax.root_path, 'helm')
|
@@ -0,0 +1,56 @@
|
|
1
|
+
## tasks to work on deployments
|
2
|
+
module Stax
|
3
|
+
module Helm
|
4
|
+
class Cmd < Base
|
5
|
+
|
6
|
+
no_commands do
|
7
|
+
def helm_deployments
|
8
|
+
jsonpath = '{.items[*].metadata.name}'
|
9
|
+
%x[kubectl get deployments -o=jsonpath='#{jsonpath}' -l #{helm_selector}].split
|
10
|
+
end
|
11
|
+
|
12
|
+
## prompt user with a list of deployments to choose
|
13
|
+
def helm_ask_deployments(msg)
|
14
|
+
deployments = helm_deployments
|
15
|
+
if deployments.count > 1
|
16
|
+
puts deployments.each_with_index.map { |d, i| "#{i}: #{d}" }
|
17
|
+
resp = ask(msg, default: 'all')
|
18
|
+
if resp != 'all'
|
19
|
+
indices = resp.split.map(&:to_i)
|
20
|
+
deployments = Array(deployments.slice(*indices))
|
21
|
+
end
|
22
|
+
end
|
23
|
+
deployments
|
24
|
+
end
|
25
|
+
end
|
26
|
+
|
27
|
+
desc 'deployments', 'list deployments'
|
28
|
+
def deployments
|
29
|
+
kubectl_run(:get, :deployments, '-l', helm_selector)
|
30
|
+
end
|
31
|
+
|
32
|
+
desc 'restart', 'restart deployments'
|
33
|
+
def restart
|
34
|
+
helm_ask_deployments('choose deployments').each do |deployment|
|
35
|
+
kubectl_run(:rollout, :restart, :deployment, deployment)
|
36
|
+
end
|
37
|
+
end
|
38
|
+
|
39
|
+
desc 'scale', 'show/set scale for deployments'
|
40
|
+
method_option :replicas, aliases: '-r', type: :numeric, default: nil, desc: 'replicas'
|
41
|
+
def scale
|
42
|
+
if options[:replicas]
|
43
|
+
deployments = helm_ask_deployments('choose deployments').join(' ')
|
44
|
+
kubectl_run(:scale, :deployment, deployments, '--replicas', options[:replicas])
|
45
|
+
else
|
46
|
+
debug("Deployment replicas for #{helm_release_name}")
|
47
|
+
deployments = kubectl_json(:get, :deployments, '-l', helm_selector)
|
48
|
+
print_table deployments['items'].map { |i|
|
49
|
+
[ i['metadata']['name'], i['status']['replicas'] || 0 ]
|
50
|
+
}
|
51
|
+
end
|
52
|
+
end
|
53
|
+
|
54
|
+
end
|
55
|
+
end
|
56
|
+
end
|
@@ -0,0 +1,19 @@
|
|
1
|
+
## tasks to get ingress details
|
2
|
+
module Stax
|
3
|
+
module Helm
|
4
|
+
class Cmd < Base
|
5
|
+
|
6
|
+
desc 'ingresses', 'list ingresses'
|
7
|
+
def ingresses
|
8
|
+
kubectl_run(:get, :ingresses, '-l', helm_selector)
|
9
|
+
end
|
10
|
+
|
11
|
+
desc 'dns', 'list external-dns hostnames'
|
12
|
+
def dns
|
13
|
+
jsonpath = '{.items[].metadata.annotations.external-dns\.alpha\.kubernetes\.io/hostname}' + "\n"
|
14
|
+
kubectl_run(:get, :ingresses, "-o=jsonpath='#{jsonpath}'", '-l', helm_selector)
|
15
|
+
end
|
16
|
+
|
17
|
+
end
|
18
|
+
end
|
19
|
+
end
|
data/lib/stax/helm/kubectl.rb
CHANGED
@@ -9,54 +9,24 @@ module Stax
|
|
9
9
|
|
10
10
|
def kubectl_run(*args)
|
11
11
|
cmd = [kubectl_bin, *args].join(' ')
|
12
|
-
options[:
|
12
|
+
options[:recon] ? puts(cmd) : system(cmd)
|
13
13
|
end
|
14
14
|
|
15
|
-
|
16
|
-
|
17
|
-
|
15
|
+
def kubectl_json(*args)
|
16
|
+
args.push('-o=json')
|
17
|
+
cmd = [kubectl_bin, *args].join(' ')
|
18
|
+
options[:recon] ? puts(cmd) : JSON.parse(%x(#{cmd}))
|
19
|
+
end
|
20
|
+
|
21
|
+
## override this to match all objects in your helm release
|
22
|
+
def helm_selector
|
23
|
+
"app.kubernetes.io/instance=#{helm_release_name}"
|
18
24
|
end
|
19
25
|
end
|
20
26
|
|
21
27
|
desc 'services', 'list services'
|
22
28
|
def services
|
23
|
-
kubectl_run(:get, :services,
|
24
|
-
end
|
25
|
-
|
26
|
-
desc 'ingresses', 'list ingresses'
|
27
|
-
def ingresses
|
28
|
-
kubectl_run(:get, :ingresses, selector('app.kubernetes.io/instance': helm_release_name))
|
29
|
-
end
|
30
|
-
|
31
|
-
desc 'deployments', 'list deployments'
|
32
|
-
def deployments
|
33
|
-
kubectl_run(:get, :deployments, selector('app.kubernetes.io/instance': helm_release_name))
|
34
|
-
end
|
35
|
-
|
36
|
-
desc 'pods', 'list pods'
|
37
|
-
def pods
|
38
|
-
kubectl_run(:get, :pods, selector('app.kubernetes.io/instance': helm_release_name))
|
39
|
-
end
|
40
|
-
|
41
|
-
desc 'containers', 'list containers'
|
42
|
-
def containers
|
43
|
-
columns = 'NAME:.metadata.name,CONTAINERS:.spec.containers[*].name'
|
44
|
-
kubectl_run(:get, :pods, '-o', "custom-columns=#{columns}", selector('app.kubernetes.io/instance': helm_release_name))
|
45
|
-
end
|
46
|
-
|
47
|
-
## FIXME this is terrible, will be replaced with something better later
|
48
|
-
desc 'logs COMPONENT [CONTAINER]', 'show container logs'
|
49
|
-
method_option :container, aliases: '-c', type: :string, default: nil, desc: 'container from pod'
|
50
|
-
def logs(component)
|
51
|
-
container = options[:container] ? "-c #{options[:container]}" : ''
|
52
|
-
kubectl_run(
|
53
|
-
:logs,
|
54
|
-
container,
|
55
|
-
selector(
|
56
|
-
'app.kubernetes.io/instance': helm_release_name,
|
57
|
-
'app.kubernetes.io/component': component,
|
58
|
-
)
|
59
|
-
)
|
29
|
+
kubectl_run(:get, :services, '-l', helm_selector)
|
60
30
|
end
|
61
31
|
|
62
32
|
end
|
@@ -0,0 +1,49 @@
|
|
1
|
+
## tasks to work on pods
|
2
|
+
module Stax
|
3
|
+
module Helm
|
4
|
+
class Cmd < Base
|
5
|
+
|
6
|
+
no_commands do
|
7
|
+
def helm_pods
|
8
|
+
jsonpath = '{.items[*].metadata.name}'
|
9
|
+
%x[kubectl get pods -o=jsonpath='#{jsonpath}' -l #{helm_selector}].split
|
10
|
+
end
|
11
|
+
|
12
|
+
def helm_ask_pod(msg)
|
13
|
+
pods = helm_pods
|
14
|
+
index = 0
|
15
|
+
if pods.count > 1
|
16
|
+
puts pods.each_with_index.map { |p, i| "#{i}: #{p}" }
|
17
|
+
index = ask(msg, default: index)
|
18
|
+
end
|
19
|
+
pods[index.to_i]
|
20
|
+
end
|
21
|
+
end
|
22
|
+
|
23
|
+
desc 'pods', 'list pods'
|
24
|
+
def pods
|
25
|
+
kubectl_run(:get, :pods, '-l', helm_selector)
|
26
|
+
end
|
27
|
+
|
28
|
+
desc 'containers', 'list containers'
|
29
|
+
def containers
|
30
|
+
columns = 'NAME:.metadata.name,CONTAINERS:.spec.containers[*].name'
|
31
|
+
kubectl_run(:get, :pods, '-o', "custom-columns=#{columns}", '-l', helm_selector)
|
32
|
+
end
|
33
|
+
|
34
|
+
desc 'logs [OPTIONS]', 'run kubectl logs with same options'
|
35
|
+
def logs(*args)
|
36
|
+
trap('SIGINT', 'EXIT') # clean exit with ctrl-c
|
37
|
+
args = [ '--all-containers', '--prefix', '--follow' ] if args.empty? # helpful default args
|
38
|
+
kubectl_run(:logs, '-l', helm_selector, *args)
|
39
|
+
end
|
40
|
+
|
41
|
+
desc 'exec [CMD]', 'exec command in a web pod'
|
42
|
+
def exec(cmd = 'sh')
|
43
|
+
pod = helm_ask_pod('choose a pod')
|
44
|
+
kubectl_run(:exec, '-it', pod, '--', cmd)
|
45
|
+
end
|
46
|
+
|
47
|
+
end
|
48
|
+
end
|
49
|
+
end
|
@@ -0,0 +1,101 @@
|
|
1
|
+
require 'securerandom'
|
2
|
+
|
3
|
+
module Stax
|
4
|
+
module Helm
|
5
|
+
class Cmd
|
6
|
+
|
7
|
+
no_commands do
|
8
|
+
## construct a Job template from passed container spec
|
9
|
+
def helm_run_template(name, container_spec)
|
10
|
+
{
|
11
|
+
apiVersion: 'batch/v1',
|
12
|
+
kind: :Job,
|
13
|
+
metadata: {
|
14
|
+
name: name,
|
15
|
+
labels: {
|
16
|
+
'app.kubernetes.io/managed-by' => :stax
|
17
|
+
}
|
18
|
+
},
|
19
|
+
spec: {
|
20
|
+
template: {
|
21
|
+
spec: {
|
22
|
+
restartPolicy: :Never,
|
23
|
+
containers: [ container_spec ],
|
24
|
+
}
|
25
|
+
}
|
26
|
+
}
|
27
|
+
}.to_json
|
28
|
+
end
|
29
|
+
|
30
|
+
## Deployment to clone for container
|
31
|
+
def helm_run_deployment
|
32
|
+
"#{helm_release_name}-web"
|
33
|
+
end
|
34
|
+
|
35
|
+
## name of container to clone from Deployment
|
36
|
+
def helm_run_container
|
37
|
+
'web'
|
38
|
+
end
|
39
|
+
|
40
|
+
## name for Job to create based on container
|
41
|
+
def helm_run_job
|
42
|
+
"#{helm_release_name}-run-#{SecureRandom.hex(4)}"
|
43
|
+
end
|
44
|
+
|
45
|
+
## default command to run
|
46
|
+
def helm_run_cmd
|
47
|
+
'bash'
|
48
|
+
end
|
49
|
+
end
|
50
|
+
|
51
|
+
## task creates a dedicated unique kubernetes Job, with
|
52
|
+
## container spec based on the helm release deployment
|
53
|
+
## requested, then does an interactive exec to the pod and
|
54
|
+
## container created, and deletes the Job on exit
|
55
|
+
desc 'runcmd [CMD]', 'run dedicated interactive container'
|
56
|
+
method_option :sleep, type: :string, default: '1h', description: 'kill container after time'
|
57
|
+
method_option :keep, type: :boolean, default: false, description: 'do not delete job'
|
58
|
+
def runcmd(*cmd)
|
59
|
+
## use default if not set
|
60
|
+
cmd = Array(helm_run_cmd) if cmd.empty?
|
61
|
+
|
62
|
+
## name of k8s Job to create
|
63
|
+
job = helm_run_job
|
64
|
+
|
65
|
+
## get deployment and extract container spec
|
66
|
+
deployment = kubectl_json(:get, :deployment, helm_run_deployment)
|
67
|
+
spec = deployment['spec']['template']['spec']['containers'].find do |c|
|
68
|
+
c['name'] == helm_run_container
|
69
|
+
end
|
70
|
+
|
71
|
+
## cleanup the container spec so we can use it in a Job
|
72
|
+
spec.delete('livenessProbe')
|
73
|
+
spec.delete('readinessProbe')
|
74
|
+
spec.delete('volumeMounts')
|
75
|
+
spec['name'] = 'run'
|
76
|
+
spec['args'] = ['sleep', options[:sleep]]
|
77
|
+
|
78
|
+
## create new unique Job based on the container spec
|
79
|
+
debug("Creating job #{job}")
|
80
|
+
Open3.popen2('kubectl create -f -') { |stdin, stdout, _|
|
81
|
+
stdin.print(helm_run_template(job, spec))
|
82
|
+
stdin.close
|
83
|
+
puts stdout.gets
|
84
|
+
}
|
85
|
+
|
86
|
+
## get name of the Pod created by the Job
|
87
|
+
pod = kubectl_json(:get, :pod, '-l', "job-name=#{job}")['items'].first['metadata']['name']
|
88
|
+
|
89
|
+
## exec into the pod and run interactive command
|
90
|
+
debug("Connecting to pod #{pod}")
|
91
|
+
kubectl_run(:wait, '--for=condition=Ready', '--timeout=5m', :pod, pod)
|
92
|
+
kubectl_run(:exec, '-it', pod, '--', *cmd)
|
93
|
+
rescue JSON::ParserError
|
94
|
+
fail_task('cannot get kubernetes resource')
|
95
|
+
ensure
|
96
|
+
## delete Job
|
97
|
+
kubectl_run(:delete, :job, job) unless options[:keep]
|
98
|
+
end
|
99
|
+
end
|
100
|
+
end
|
101
|
+
end
|
data/lib/stax/helm/stern.rb
CHANGED
@@ -16,7 +16,8 @@ module Stax
|
|
16
16
|
## pass through args to stern
|
17
17
|
desc 'stern [STERN_ARGS]', 'use stern to show logs'
|
18
18
|
def stern(*args)
|
19
|
-
|
19
|
+
trap('SIGINT', 'EXIT') # clean exit with ctrl-c
|
20
|
+
stern_run('-l', helm_selector, *args)
|
20
21
|
end
|
21
22
|
|
22
23
|
end
|
data/lib/stax/helm/version.rb
CHANGED
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: stax-helm
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.0.
|
4
|
+
version: 0.0.8
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Richard Lister
|
8
|
-
autorequire:
|
8
|
+
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2020-
|
11
|
+
date: 2020-12-03 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: bundler
|
@@ -67,8 +67,13 @@ files:
|
|
67
67
|
- README.md
|
68
68
|
- Rakefile
|
69
69
|
- lib/stax/helm.rb
|
70
|
+
- lib/stax/helm/base.rb
|
70
71
|
- lib/stax/helm/cmd.rb
|
72
|
+
- lib/stax/helm/deployment.rb
|
73
|
+
- lib/stax/helm/ingress.rb
|
71
74
|
- lib/stax/helm/kubectl.rb
|
75
|
+
- lib/stax/helm/pod.rb
|
76
|
+
- lib/stax/helm/runcmd.rb
|
72
77
|
- lib/stax/helm/stern.rb
|
73
78
|
- lib/stax/helm/version.rb
|
74
79
|
- stax-helm.gemspec
|
@@ -76,7 +81,7 @@ homepage: https://github.com/rlister/stax-helm
|
|
76
81
|
licenses:
|
77
82
|
- MIT
|
78
83
|
metadata: {}
|
79
|
-
post_install_message:
|
84
|
+
post_install_message:
|
80
85
|
rdoc_options: []
|
81
86
|
require_paths:
|
82
87
|
- lib
|
@@ -91,8 +96,8 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
91
96
|
- !ruby/object:Gem::Version
|
92
97
|
version: '0'
|
93
98
|
requirements: []
|
94
|
-
rubygems_version: 3.
|
95
|
-
signing_key:
|
99
|
+
rubygems_version: 3.0.3
|
100
|
+
signing_key:
|
96
101
|
specification_version: 4
|
97
102
|
summary: Control helm charts with stax.
|
98
103
|
test_files: []
|