Skip to content

Commit adc3dc0

Browse files
committed
Merge branch 'main' of github.com:queil/image
2 parents 1b35deb + 9c45590 commit adc3dc0

File tree

1 file changed

+257
-0
lines changed

1 file changed

+257
-0
lines changed

init/home/queil/nuk8s.nu

Lines changed: 257 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,257 @@
1+
use std log
2+
3+
def init-env [] { {names: {}} }
4+
5+
$env.KUBE_CACHE = (init-env)
6+
7+
def makectx [] {
8+
{
9+
namespace: "default"
10+
ctx: (kubectl config current-context | str trim)
11+
current: {name: null, type_alias: null}
12+
type_aliases: (kubectl api-resources | from ssv -a | each {|x| let n = ($x.shortnames | split row ',' | get 0 | str trim ); if ($n | is-empty) { $x.name } else { $n } })
13+
}
14+
}
15+
16+
$env.K = (makectx)
17+
18+
def type-aliases [] { $env.K.type_aliases }
19+
20+
def --env get-kube-names [
21+
alias: string
22+
] {
23+
let alias_value = $env.KUBE_CACHE.names | get -i $alias
24+
25+
if $alias_value == null {
26+
let new_names = (invoke-kubectl get $alias -o name | lines | each { |line| ($line | split row "/" | get 1) })
27+
let cache = $env.KUBE_CACHE.names | upsert $"($alias)" $new_names
28+
$env.KUBE_CACHE = {names: $cache }
29+
return $new_names
30+
}
31+
32+
return $alias_value
33+
}
34+
35+
def --env typed-kube-names [context: string] {
36+
let type = $context | split words | last
37+
get-kube-names $type
38+
}
39+
40+
41+
def rsname [] {
42+
$"($env.K.current.type_alias)/($env.K.current.name)"
43+
}
44+
45+
def --env reload [
46+
--hard (-h)
47+
] {
48+
let names_record = $env.KUBE_CACHE.names
49+
let namespaces = $names_record | get -i "ns"
50+
let namespace = $env.K.namespace
51+
52+
$env.K = (makectx)
53+
$env.KUBE_CACHE = {names: {}}
54+
55+
if not $hard {
56+
if $namespaces != null {
57+
$env.KUBE_CACHE.names = ($env.KUBE_CACHE.names | upsert "ns" $namespaces)
58+
}
59+
$env.K = ($env.K | upsert "namespace" $namespace)
60+
}
61+
}
62+
63+
def --wrapped invoke-kubectl [...args] {
64+
let namespace = $env.K.namespace
65+
let kargs = if $namespace != null { ["-n", $namespace] } else { [] }
66+
let full_args = ($kargs | append $args)
67+
log debug ([kubectl] | append $full_args | str join " ")
68+
kubectl ...$full_args
69+
}
70+
71+
def get-contexts [] { kubectl config get-contexts -o name | lines }
72+
73+
def --env select-kube-context [
74+
name?: string@get-contexts
75+
] {
76+
if $name == null { return get-contexts }
77+
78+
let contexts = (get-contexts)
79+
if $name not-in $contexts {
80+
error make {msg: $"Context '($name)' not found"}
81+
}
82+
83+
reload --hard
84+
$env.K = ($env.K | upsert "ctx" $name)
85+
kubectl config use-context $name
86+
}
87+
88+
89+
def --env get-namespaces [] = { get-kube-names "ns" }
90+
91+
def --env select-kube-namespace [
92+
name?: string@get-namespaces
93+
] {
94+
if $name == null {
95+
get-namespaces
96+
return
97+
}
98+
99+
let namespaces = (get-namespaces)
100+
if $name not-in $namespaces {
101+
error make {msg: $"Namespace '($name)' not found"}
102+
}
103+
104+
reload
105+
$env.K = ($env.K | upsert "namespace" $name)
106+
}
107+
108+
def --env select-kube-resource [
109+
type: string@type-aliases,
110+
name?: string@typed-kube-names
111+
] {
112+
113+
if $name == null {
114+
reload
115+
invoke-kubectl get po
116+
return
117+
}
118+
typed-kube-names $type # this is needed for caching only - calling it in completion doesn't seem to export env changes
119+
$env.K = ($env.K | upsert "current" {name: $name, type_alias: $type})
120+
}
121+
122+
def get-kube-yaml [] {
123+
invoke-kubectl get (rsname) --output yaml
124+
}
125+
126+
def get-kube-jsonpath [
127+
jsonpath: string
128+
] {
129+
invoke-kubectl get (rsname) -o $"jsonpath={($jsonpath)}"
130+
}
131+
132+
def get-kube-describe-resource [] {
133+
invoke-kubectl describe (rsname)
134+
}
135+
136+
def get-kube-logs [
137+
--follow (-f),
138+
--tail (-t): int = 0,
139+
--container (-c): string
140+
] {
141+
let tail_arg = if $tail > 0 { $"--tail=($tail)" } else { "" }
142+
let follow_arg = if $follow { "--follow" } else { "" }
143+
let container_arg = if $container != null { $"--container=($container)" } else { "" }
144+
145+
let args = [$tail_arg, $follow_arg, $container_arg] | where { is-not-empty }
146+
invoke-kubectl logs (rsname) ...$args
147+
}
148+
149+
def delete-kube-resource [] {
150+
invoke-kubectl delete (rsname)
151+
reload
152+
}
153+
154+
def restart-kube-resource [] {
155+
invoke-kubectl rollout restart (rsname)
156+
wait-for-kube-resource available
157+
invoke-kubectl get po --watch
158+
reload
159+
}
160+
161+
def wait-for-kube-resource [
162+
condition: string = "available"
163+
] {
164+
invoke-kubectl wait (rsname) $"--for=condition=($condition)"
165+
}
166+
167+
def follow-kube-logs [
168+
container?: string
169+
] {
170+
get-kube-logs --tail 1 --follow --container $container
171+
}
172+
173+
def invoke-kube-pod-cmd [
174+
cmd?: string = "sh",
175+
container?: string
176+
] {
177+
let container_arg = if $container != null { $"--container=($container)" } else { "" }
178+
invoke-kubectl exec -it (rsname) $container_arg -- $cmd
179+
}
180+
181+
def invoke-kube-port-forward [
182+
remote_port?: int,
183+
local_port?: int = 0,
184+
--browse (-b)
185+
] {
186+
if $remote_port == null {
187+
let target = (rsname)
188+
let port_jsonpath = if ($target | str starts-with "svc/") {
189+
"jsonpath='{.spec.ports[*].port}'"
190+
} else if ($target | str starts-with "pod/") {
191+
"jsonpath='{.spec.containers[*].ports[*].containerPort}'"
192+
} else {
193+
""
194+
}
195+
196+
if $port_jsonpath != "" {
197+
invoke-kubectl get $target "-o" $port_jsonpath | split row " "
198+
}
199+
return
200+
}
201+
202+
let final_local_port = if $local_port == 0 {
203+
if $remote_port <= 1024 { $remote_port + 8000 } else { $remote_port }
204+
} else {
205+
$local_port
206+
}
207+
208+
if $browse {
209+
x-www-browser $"http://127.0.0.1:($final_local_port)"
210+
}
211+
212+
invoke-kubectl port-forward (rsname) $"($final_local_port):($remote_port)"
213+
}
214+
215+
def create_prompt [] {
216+
217+
let ctx = $env.K.ctx
218+
let namespace = $env.K.namespace
219+
let current = $env.K.current
220+
221+
let ctx_part = $"($ctx) /"
222+
223+
if $namespace == null {
224+
$"λ ($ctx_part)"
225+
} else {
226+
let ns_part = $" ($namespace) /"
227+
228+
if $current == null or $current.name == null {
229+
$"λ ($ctx_part)($ns_part)"
230+
} else {
231+
let type_alias = $current.type_alias
232+
let name = $current.name
233+
let rs_type_part = $" ($type_alias) /"
234+
let rs_name_part = $" ($name) /"
235+
$"λ ($ctx_part)($ns_part)($rs_type_part)($rs_name_part)"
236+
}
237+
}
238+
}
239+
240+
$env.PROMPT_COMMAND_RIGHT = { create_prompt }
241+
242+
reload --hard
243+
244+
alias k = invoke-kubectl
245+
alias kx = select-kube-context
246+
alias ns = select-kube-namespace
247+
alias rs = select-kube-resource
248+
alias yaml = get-kube-yaml
249+
alias jp = get-kube-jsonpath
250+
alias desc = get-kube-describe-resource
251+
alias delete = delete-kube-resource
252+
alias restart = restart-kube-resource
253+
alias w8 = wait-for-kube-resource
254+
alias pf = invoke-kube-port-forward
255+
alias logs = get-kube-logs
256+
alias flogs = follow-kube-logs
257+
alias x = invoke-kube-pod-cmd

0 commit comments

Comments
 (0)