Skip to content
Open
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
60 changes: 42 additions & 18 deletions k
Original file line number Diff line number Diff line change
Expand Up @@ -1162,24 +1162,41 @@ def pg_unused_indexes
SQL
end

# Parse named options from ARGV, modifying it in place. Remaining positional args stay in ARGV.
#
# flags: boolean switches that can appear anywhere (eg. --disable-timeout)
# params: options that take a value and must appear before positional args
# accepts --key=value or --key value syntax
#
# Returns a Hash keyed by the option name without leading dashes, eg. { "tag" => "v1", "disable-timeout" => true }
def parse_options!(flags: [], params: [])
options = {}

flags.each { |flag| options[flag.delete_prefix("--")] = !!ARGV.delete(flag) }

params.each do |param|
key = param.delete_prefix("--")
if ARGV[0]&.start_with?("#{param}=")
options[key] = ARGV.delete_at(0).split("=", 2).last
abort "ERROR: Must provide a value with #{param}=" if options[key].empty?
elsif ARGV[0] == param
ARGV.delete_at(0)
options[key] = ARGV.delete_at(0)
abort "ERROR: Must provide a value with #{param}" if options[key].nil? || options[key].empty?
elsif ARGV.any? { |arg| arg == param || arg.start_with?("#{param}=") }
puts yellow('Warning: ') + gray("#{param} argument will be part of the running command, if you intended to use it you must pass it before the command")
end
end

options
end

def run
application = ARGV.delete_at(0)
disable_timeout = ARGV.delete("--disable-timeout")
options = parse_options!(flags: %w[--disable-timeout], params: %w[--tag --node])

# Handle --tag=<tag> argument, can be passed as --tag=<tag> or --tag <tag> and must be before the command
if ARGV[0]&.start_with?("--tag=")
tag = ARGV.delete_at(0).split("=", 2).last
abort "ERROR: Must provide a tag value with --tag=" if tag.empty?
elsif ARGV[0] == "--tag"
ARGV.delete_at(0)
tag = ARGV.delete_at(0)
abort "ERROR: Must provide a tag value with --tag" if tag.nil? || tag.empty?
elsif ARGV.any? { |arg| arg == "--tag" || arg.start_with?("--tag=") }
puts yellow('Warning: ') + gray("--tag argument will be part of the running command, if you intended to set the image tag you must pass it before the command")
end

abort "Must pass name of application, eg. k run <application> [--tag=<tag>] <command> [--disable-timeout] " unless application
abort "Must pass command to run, eg. k run <application> [--tag=<tag>] <command> [--disable-timeout]" if ARGV.empty?
abort "Must pass name of application, eg. k run <application> [--tag=<tag>] [--node=<node>] <command> [--disable-timeout] " unless application
abort "Must pass command to run, eg. k run <application> [--tag=<tag>] [--node=<node>] <command> [--disable-timeout]" if ARGV.empty?

resources = resources_for_argocd_application("deployments", application)
if resources.empty?
Expand Down Expand Up @@ -1212,11 +1229,13 @@ def run
image = run_container.fetch("image")

# replace image tag if --tag was provided
if tag
image = "#{image.split(':').first}:#{tag}"
if options["tag"]
image = "#{image.split(':').first}:#{options['tag']}"
puts gray("applying --tag argument to image: #{image}")
end



pod_template = {
apiVersion: "v1",
kind: "Pod",
Expand All @@ -1233,12 +1252,17 @@ def run
envFrom: run_container["envFrom"] || [],
env: run_container["env"] || [],
imagePullPolicy: "IfNotPresent",
command: ["sleep", disable_timeout ? "86400" : "3600"], # shutdown the pod after 1 hour or 24 hours
command: ["sleep", options["disable-timeout"] ? "86400" : "3600"], # shutdown the pod after 1 hour or 24 hours
},
],
},
}

if options["node"]
puts gray("applying nodeName: #{options["node"]} to pod template spec")
pod_template[:spec][:nodeName] = options["node"]
end

puts "Creating pod #{pod_name}..."
system("echo '#{pod_template.to_json}' | kubectl --context #{KUBECTL_CONTEXT} apply -f -") || abort("failed to create pod")

Expand Down