# frozen_string_literal: true # ========================================================== # dtic-BKPs/lib/menu.rb — Menú TUI interactivo + editor CRUD # ========================================================== module DTICBKPs class Menu def initialize(config, dispatcher, log) @config = config @dispatcher = dispatcher @log = log end def ejecutar loop do system('clear') || system('cls') mostrar_encabezado opciones = construir_opciones opciones.each { |op| puts op[:linea] } puts "#{C::CYAN}────────────────────────#{C::RESET}" print "\n#{C::YELLOW}Selecciona > #{C::RESET}" $stdout.flush entrada = $stdin.gets&.chomp&.strip&.upcase next if entrada.nil? || entrada.empty? op = opciones.find { |o| o[:id] == entrada } unless op @log.error("Opción no válida: #{entrada}") sleep 1 next end case op[:tipo] when :tarea @dispatcher.ejecutar_tarea(op[:config]) when :comando @dispatcher.ejecutar_comando(op[:config]) when :editor editor_interactivo @config.reload! when :salir puts "Saliendo..." exit 0 end unless [:editor, :salir].include?(op[:tipo]) || @config.auto_avanzar print "\nPresiona Enter para continuar..." $stdin.gets end end end private def mostrar_encabezado puts "#{C::BOLD}#{C::CYAN}╔══════════════════════════════════════════╗#{C::RESET}" puts "#{C::BOLD}#{C::CYAN}║ dtic-BKPs — Procesador de Backups v6.0 ║#{C::RESET}" puts "#{C::BOLD}#{C::CYAN}╚══════════════════════════════════════════╝#{C::RESET}" end def construir_opciones opciones = [] puts "\n#{C::BOLD}Tareas Individuales:#{C::RESET}" @config.tareas.each_with_index do |t, i| id = "T#{i + 1}" opciones << { id: id, tipo: :tarea, config: t, linea: " #{C::YELLOW}#{id}.#{C::RESET} #{t[:texto]}" } end puts "\n#{C::BOLD}Comandos (Secuencias):#{C::RESET}" @config.comandos.each_with_index do |c, i| id = "C#{i + 1}" opciones << { id: id, tipo: :comando, config: c, linea: " #{C::YELLOW}#{id}.#{C::RESET} #{c[:texto]}" } end puts "\n#{C::CYAN}────────────────────────#{C::RESET}" opciones << { id: 'E', tipo: :editor, linea: " #{C::YELLOW}E.#{C::RESET} Editar tareas y comandos" } opciones << { id: 'S', tipo: :salir, linea: " #{C::YELLOW}S.#{C::RESET} Salir" } opciones.each { |op| puts op[:linea] if op[:tipo].is_a?(Symbol) && [:editor, :salir].include?(op[:tipo]) } opciones end # ─── Editor CRUD ────────────────────────────────────────────── def editor_interactivo loop do system('clear') || system('cls') puts "#{C::BOLD}#{C::CYAN}--- Editor de Tareas y Comandos ---#{C::RESET}\n\n" puts "#{C::BOLD}Tareas:#{C::RESET}" @config.tareas.each_with_index do |t, i| puts " #{C::YELLOW}T#{i+1}.#{C::RESET} #{t[:texto]} #{C::DIM}(#{t[:id]})#{C::RESET}" end puts "\n#{C::BOLD}Comandos:#{C::RESET}" @config.comandos.each_with_index do |c, i| puts " #{C::YELLOW}C#{i+1}.#{C::RESET} #{c[:texto]} #{C::DIM}(#{c[:id]}, tareas: #{c[:tareas]&.join(', ')})#{C::RESET}" end puts "\n#{C::CYAN}[Tx]=Editar, [NT]=Nueva Tarea, [BT]=Borrar Tarea, [G]=Guardar y Volver#{C::RESET}" print "> " $stdout.flush op = $stdin.gets&.chomp&.strip&.downcase return if op.nil? case op when /^t(\d+)$/ idx = $1.to_i - 1 editar_tarea(idx) if @config.tareas[idx] when 'nt' nueva_tarea when 'bt' print "Número a borrar (ej: 1): " idx = $stdin.gets&.chomp.to_i - 1 @config.remove_tarea(idx) if idx >= 0 && @config.tareas[idx] when 'g' @config.save! @log.ok("Configuración guardada.") sleep 1 return end end end def editar_tarea(idx) tarea = @config.tareas[idx] puts "\n#{C::CYAN}Editando: #{tarea[:texto]}#{C::RESET}" puts "#{C::DIM}(Dejar vacío = mantener valor actual)#{C::RESET}\n" tarea.each do |k, v| next if k == :id tipo_hint = [true, false].include?(v) ? " (true/false)" : "" print " #{C::YELLOW}#{k}#{C::RESET}#{tipo_hint} [#{v}]: " $stdout.flush nuevo = $stdin.gets&.chomp&.strip next if nuevo.nil? || nuevo.empty? tarea[k] = case v when Symbol then nuevo.to_sym when TrueClass, FalseClass then nuevo.downcase == 'true' else nuevo end end @log.ok("Tarea actualizada.") end def nueva_tarea tarea = { id: "tarea_#{Time.now.to_i}", texto: "Nueva Tarea", tipo: "rclone", origen: "", destino: "", eliminar_origen: false, sobrescribir: false } editar_tarea_hash(tarea) @config.add_tarea(tarea) end def editar_tarea_hash(tarea) tarea.each do |k, v| print " #{C::YELLOW}#{k}#{C::RESET} [#{v}]: " $stdout.flush nuevo = $stdin.gets&.chomp&.strip tarea[k] = nuevo unless nuevo.nil? || nuevo.empty? end end end end