cluster/lib/cluster/runner.rb in sct-0.1.35 vs cluster/lib/cluster/runner.rb in sct-1.0.0
- old
+ new
@@ -1,343 +1,73 @@
module Cluster
- class Runner
+ class Runner
- def start
- SctCore::Helper.ensure_windows_administrator # "sct hostfile" will need it later on
-
- existing_cluster = cluster_exists?
-
- start_cluster
-
- if existing_cluster
- run_command "kubectl rollout restart -n kube-system deployment registry-creds"
- run_command "kubectl rollout status -n kube-system deployment registry-creds"
- else
- create_secrets
- enable_addons
- wait_for_gcr_secret
- run_command "kubectl apply -f ~/development/spend-cloud/k8s/ingress.yml"
- wait_for_ingress_ip
- run_command "kubectl apply -f ~/development/spend-cloud/k8s/dependencies.yml"
- wait_for_pods
- create_keycloak_database_user
- run_command "kubectl apply -f ~/development/spend-cloud/k8s/keycloak-server.yml"
- wait_for_pods
- run_command "kubectl apply -f ~/development/spend-cloud/k8s/"
- end
-
- post_start
+ def run command, options = {}
+ begin
+ if !system command, options
+ raise command.red
end
+ rescue Interrupt
+ # user pressed Ctrl+C, do nothing
+ end
+ end
- def stop
- run_command "minikube stop"
- end
+ def run_dc command, options = {}
+ run "docker-compose -f ~/development/spend-cloud/docker-compose.yml #{command}", options
+ end
- def restart
- SctCore::Helper.ensure_windows_administrator # "sct hostfile" will need it later on
+ def start args, options
+ if options.pull
+ run_dc "pull"
+ end
- stop
- start
- end
+ if options.build
+ run_dc "build #{options.pull ? "--pull" : ""}"
+ end
- def delete
- run_command "minikube delete"
- end
+ run_dc "up --detach"
- def reset
- SctCore::Helper.ensure_windows_administrator # "sct hostfile" will need it later on
+ if options.pull or options.build
+ system "docker image prune -f"
+ end
- delete
- start
- end
+ UI.success("\nāļø You can visit your environment at š https://spend-cloud.dev.spend.cloud š")
+ end
- def status
- print_contexts
- print_minikube_status
+ def stop
+ run_dc "down --remove-orphans"
+ end
- if get_minikube_status.find_all { |status| status[1] == 'Stopped' }.count == 0
- print_pods_status("kube-system")
- print_pods_status
- else
- UI.important("Please check your minikube status. If all services are stopped you should start the minikube first.")
- end
- end
+ def restart
+ run_dc "restart"
+ end
- def update_config
- run_command "kubectl config use-context minikube"
+ def delete
+ run_dc "down --remove-orphans -v"
+ end
- run_command "kubectl replace -n kube-system -f #{File.expand_path('resources/corefile.yml', __dir__)}"
- run_command "kubectl rollout restart -n kube-system deployment coredns"
- run_command "kubectl rollout status -n kube-system deployment coredns"
- end
+ def reset args, options
+ delete
+ start args, options
+ end
- def apply_deployments
- run_command "kubectl apply -f ~/development/spend-cloud/k8s/"
- end
+ def pull
+ run_dc "pull"
+ run "docker image prune -f"
+ end
+ def status
+ run_dc "ps"
+ end
- def cluster_exists?
- if system "minikube status", { out: "/dev/null" }
- # cluster exists and is running
- return true
- end
+ def logs args, options
+ command = "logs"
- if $?.exitstatus == 85
- # cluster does not exist
- return false
- end
+ command << " --follow" if options.f or options.follow
+ command << " --timestamps" if options.t or options.timestamps
+ command << " --tail #{options.tail}" if options.tail
- # cluster exists but is stopped
- return true
- end
-
- def start_cluster
- if SctCore::Helper.operatingSystem == SctCore::Helper::MAC_OS
- run_command "minikube start --driver=hyperkit --vm=true --cpus=$(sysctl -n hw.ncpu) --memory=8G"
- else
- run_command "minikube start --driver=docker --cpus=$(cat /proc/cpuinfo | grep processor | wc -l) --memory=3G"
- end
- update_config
- end
-
- def post_start
- wait_for_pods
- copy_proactive_accounts_file
- if SctCore::Helper.operatingSystem == SctCore::Helper::UBUNTU
- UI.success("\nAdding SSH tunnel to port 443!")
- run_command "sudo ssh -f -N -i $(minikube ssh-key) docker@$(minikube ip) -L 443:127.0.0.1:443"
- end
-# run_command "sudo sct hostfile"
- run_command "minikube tunnel &", { out: "/dev/null", err: "/dev/null" } if SctCore::Helper::is_windows? # leave this running detached forever in the background
- UI.success("\nāļø You can visit your environment at š https://spend-cloud.dev.spend.cloud š")
- end
-
- def enable_addons
- enable_addon "registry-creds"
- enable_addon "ingress"
- end
-
- def enable_addon(addon)
- run_command "minikube addons enable #{addon}"
-
- deployment = deployments("kube-system").find { |deployment| deployment[:name].include? addon }
-
- run_command "kubectl rollout status -n kube-system deployment #{deployment[:name]}"
- end
-
- def wait_for_pods
- UI.important("Waiting for pods to become ready...")
-
- previous_lines = 0
-
- while ! pods.all? { |pod| pod[:ready] }
- pods_status_lines = get_pods_status.to_s.lines.map { |line| line.chomp }
-
- current_lines = pods_status_lines.length
-
- line_difference = current_lines - previous_lines
-
- if line_difference < 0 # there are now less lines than before
- line_difference.abs.times do
- print "\033[1A\033[K" # move the cursor up a line and clear the line
- end
-
- print "\033[#{current_lines}A" # move the cursor all the way up to the start of the table
- elsif previous_lines > 0
- print "\033[#{previous_lines}A" # move the cursor all the way up to the start of the table
- end
-
- pods_status_lines.each do |line|
- print "#{line}\033[K#{$/}" # print the content of the line, clear remaining characters and add a new line
- end
-
- previous_lines = current_lines
-
- sleep 5
- end
-
- previous_lines.times do
- print "\033[1A\033[K" # move the cursor up a line and clear the line
- end
-
- UI.success("Pods are now ready.")
- end
-
- def deployments(namespace = "default")
- output = `kubectl get deployments -n #{namespace}`
-
- # split output lines
- lines = output.split "\n"
-
- # exclude first line (table header)
- lines = lines[1..-1]
-
- # get name and status of each pod
- lines.map do |line|
- columns = line.split(" ")
-
- name = columns[0]
-
- {
- name: name
- }
- end
- end
-
- def pods(namespace = "default")
- output = `kubectl get pods -n #{namespace}`
-
- # split output lines
- lines = output.split "\n"
-
- # exclude first line (table header)
- lines = lines[1..-1]
-
- # get name and status of each pod
- lines.map do |line|
- columns = line.split(" ")
-
- name = columns[0]
- ready = columns[1].split("/").reduce { |l, r| l == r }
- replicas = columns[1]
- status = columns[2]
-
- {
- name: name,
- ready: ready,
- replicas: replicas,
- status: status
- }
- end
- end
-
- def create_secrets
- run_command "kubectl create secret generic gcloud-credentials --from-file=\"$(echo ~)/.config/gcloud/application_default_credentials.json\""
- run_command "kubectl create secret generic -n kube-system registry-creds-dpr --from-literal DOCKER_PRIVATE_REGISTRY_PASSWORD=changeme --from-literal DOCKER_PRIVATE_REGISTRY_SERVER=changeme --from-literal DOCKER_PRIVATE_REGISTRY_USER=changeme"
- run_command "kubectl patch secret -n kube-system registry-creds-dpr -p='{\"metadata\": {\"labels\": { \"app\": \"registry-creds\", \"cloud\": \"dpr\", \"kubernetes.io/minikube-addons\": \"registry-creds\"}}}'"
- run_command "kubectl create secret generic -n kube-system registry-creds-ecr --from-literal AWS_ACCESS_KEY_ID=changeme --from-literal AWS_SECRET_ACCESS_KEY=changeme --from-literal AWS_SESSION_TOKEN=\"\" --from-literal aws-account=changeme --from-literal aws-assume-role=changeme --from-literal aws-region=changeme"
- run_command "kubectl patch secret -n kube-system registry-creds-ecr -p='{\"metadata\": {\"labels\": { \"app\": \"registry-creds\", \"cloud\": \"ecr\", \"kubernetes.io/minikube-addons\": \"registry-creds\"}}}'"
- run_command "kubectl create secret generic -n kube-system registry-creds-gcr --from-file=\"$(echo ~)/.config/gcloud/application_default_credentials.json\" --from-literal=gcrurl=\"https://eu.gcr.io\""
- run_command "kubectl patch secret -n kube-system registry-creds-gcr -p='{\"metadata\": {\"labels\": { \"app\": \"registry-creds\", \"cloud\": \"gcr\", \"kubernetes.io/minikube-addons\": \"registry-creds\"}}}'"
- run_command "kubectl create secret generic -n kube-system registry-creds-acr --from-literal ACR_PASSWORD=changeme --from-literal ACR_CLIENT_ID=changeme --from-literal ACR_URL=changeme"
- run_command "kubectl patch secret -n kube-system registry-creds-acr -p='{\"metadata\": {\"labels\": { \"app\": \"registry-creds\", \"cloud\": \"acr\", \"kubernetes.io/minikube-addons\": \"registry-creds\"}}}'"
- end
-
- def wait_for_gcr_secret
- UI.important("Waiting for Google Cloud Registry secret to become available...")
-
- while ! `kubectl get secrets`.include? "gcr-secret"
- sleep 5
- end
-
- UI.success("Google Cloud Registry secret is now available.")
- end
-
- def wait_for_ingress_ip
- UI.important("Waiting for ingress IP to become available...")
-
- while `kubectl describe ingress | grep "Address" | awk '{print $2}'`.empty?
- sleep 5
- end
-
- UI.success("Ingress IP is now available.")
- end
-
- def print_contexts
- output = `kubectl config get-contexts`
-
- lines = output.split "\n"
- lines = lines[1..-1]
-
- rows = lines.map do |line|
- columns = line.split(" ")
-
- current_context = columns[0] == "*" ? "Yes".green : "No".red
-
- [columns[2], current_context]
- end
-
- puts Terminal::Table.new title: "Contexts".green, headings: ['Cluster', 'Using context'], rows: rows
- end
-
- def print_minikube_status
- puts Terminal::Table.new title: "Minikube status".green, headings: ['Name', 'Status'], rows: get_minikube_status
- end
-
- def get_minikube_status
- output = `minikube status`
-
- lines = output.split "\n"
-
- rows = lines.map do |line|
- columns = line.split(" ")
-
- [columns[0][0..-2], columns[1]]
- end
- end
-
- def print_pods_status(namespace = "default")
- output = get_pods_status(namespace)
-
- puts output if output
- end
-
- def get_pods_status(namespace = "default")
- rows = pods(namespace).map do |pod|
- status = pod[:status]
- replicas = pod[:replicas]
-
- [
- pod[:name],
- status == "Running" ? status.green : status.red,
- pod[:ready] ? replicas.green : replicas.red
- ]
- end
-
- if rows.empty?
- return
- end
-
- return Terminal::Table.new title: "Pods (namespace: #{namespace})".green, headings: ['Name', 'Status', 'Replicas ready'], rows: rows
- end
-
- def copy_proactive_accounts_file
- container_name = "proactive-config"
- pod_id = pods().select {|pod| pod[:name].start_with?(container_name)}.first[:name]
-
- begin
- UI.important("Checking ProActive accounts file...")
- run_command "kubectl exec #{pod_id} -- test -e /data/proactive_accounts.ini", [:out, :err] => File::NULL
- rescue => e
- UI.important("Copying ProActive accounts file to deployments...")
- src_path = "#{Dir.home()}/development/spend-cloud/k8s/conf/proactive_accounts.ini"
- command = "kubectl cp #{src_path} #{pod_id}:/data/proactive_accounts.ini -c #{container_name}"
- run_command command
- end
-
- UI.success("ProActive accounts file is available")
- end
-
- def create_keycloak_database_user
- container_name = "mysql-service"
- pod_id = pods().select {|pod| pod[:name].start_with?(container_name)}.first[:name]
-
- UI.important("Creating keycloak user")
- create_user = 'CREATE USER "keycloak"@"%" IDENTIFIED BY "keycloak";'
- run_command "kubectl exec #{pod_id} -- mysql -e '#{create_user}' >> /dev/null"
-
- UI.important("Creating keycloak database")
- create_database = "CREATE DATABASE keycloak CHARACTER SET utf8 COLLATE UTF8_UNICODE_CI;"
- run_command "kubectl exec #{pod_id} -- mysql -e '#{create_database}' >> /dev/null"
-
- UI.important("Granting privileges to keycloak user")
- grant_privileges = 'GRANT ALL PRIVILEGES ON keycloak.* TO "keycloak"@"%";'
- run_command "kubectl exec #{pod_id} -- mysql -e '#{grant_privileges}' >> /dev/null"
- end
-
- def run_command command, options = {}
- if ! system command, options
- raise command.red
- end
- end
+ run_dc "#{command} #{args.join " "}"
end
+
+ end
end