require 'childprocess'
namespace 'ak8s' do
desc 'Port forwards many services from a specific NAMESPACE' task :port_forward, [:namespace] do |_t, args| # Config with defaults setup config = YAML.load_file(ENV['AK8S_CONFIG'] || '.ak8s.yml') config_namespaces = config.keys.reject { |n| n == 'ak8s' } args.with_defaults(namespace: config_namespaces.first) raise 'Bad config file format' if args.namespace.nil? # Helper variables setup first_port = config.dig('ak8s', 'first_port') || 4200 namespaced_services = config[args.namespace] raise 'No services listed in .ak8s.yml' if namespaced_services.empty? # All services to port forward (an array of hashes) services = namespaced_services.each_with_index.map do |service, index| port = first_port.to_i + index export_env = "#{service['name'].upcase}_ENDPOINT" target_port = service['target_port'] || 3000 service_namespace = service['namespace'] || args.namespace rake_task_params = [ service_namespace, service['name'], port, target_port ].map(&:to_s).join(',') { port: port, rake_task: "ak8s:port_forward_service[#{rake_task_params}]", env: "export #{export_env}=\"http://localhost:#{port}/\"" } end # Export ENV variables to `services.env` env_file = services.map { |service| service[:env] }.join("\n") File.write('services.env', env_file) # Execute each 'rake_task' in a child process until CTRL+C is received begin processes = services.map do |service| ChildProcess.build('bin/rake', service[:rake_task]) end processes.each(&:start) puts 'Services should be port forwarded to localhost in a few seconds.' puts 'Execute ". services.env" to source each service URL.' loop { sleep 3 } rescue Interrupt puts "\nExiting child processes..." processes.each(&:stop) puts 'Done!' end end
end