Module: Doing::Completion
- Defined in:
- lib/doing/completion.rb
Overview
Completion script generator
Constant Summary collapse
- OPTIONS_RX =
/(?:-(?<short>\w), )?(?:--(?:\[no-\])?(?<long>\w+)(?:=(?<arg>\w+))?)\s+- (?<desc>.*?)$/.freeze
- SECTIONS_RX =
/(?m-i)^([A-Z ]+)\n([\s\S]*?)(?=\n+[A-Z]+|\Z)/.freeze
- COMMAND_RX =
/^(?<cmd>[^, \t]+)(?<alias>(?:, [^, \t]+)*)?\s+- (?<desc>.*?)$/.freeze
Class Method Summary collapse
-
.generate_completion(type: 'zsh', file: :default, link: true) ⇒ Object
Generate a completion script and output to file or stdout.
- .get_help_sections(command = '') ⇒ Object
- .install_builtin(type) ⇒ Object
- .link_default(type) ⇒ Object
- .normalize_type(type) ⇒ Object
- .parse_command(command) ⇒ Object
- .parse_commands(commands) ⇒ Object
- .parse_option(option) ⇒ Object
- .parse_options(options) ⇒ Object
Class Method Details
.generate_completion(type: 'zsh', file: :default, link: true) ⇒ Object
Generate a completion script and output to file or stdout
68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 |
# File 'lib/doing/completion.rb', line 68 def generate_completion(type: 'zsh', file: :default, link: true) return generate_all if type =~ /^all$/i file = file == :default ? default_file(type) : file file = validate_target(file) result = generate_type(type) if file =~ /^stdout$/i $stdout.puts result else File.open(file, 'w') { |f| f.puts result } Doing.logger.warn('File written:', "#{type} completions written to #{file}") link_completion_type(type, file) if link end end |
.get_help_sections(command = '') ⇒ Object
19 20 21 22 23 24 25 26 27 28 29 |
# File 'lib/doing/completion.rb', line 19 def get_help_sections(command = '') res = `doing help #{command}`.strip scanned = res.scan(SECTIONS_RX) sections = {} scanned.each do |sect| title = sect[0].downcase.strip.gsub(/ +/, '_').to_sym content = sect[1].split(/\n/).map(&:strip).delete_if(&:empty?) sections[title] = content end sections end |
.install_builtin(type) ⇒ Object
96 97 98 99 100 101 102 103 104 105 106 |
# File 'lib/doing/completion.rb', line 96 def install_builtin(type) FileUtils.mkdir_p(default_dir) src = File.(File.join(File.dirname(__FILE__), '..', 'completion', default_filenames[type])) if File.exist?(File.join(default_dir, default_filenames[type])) return unless Doing::Prompt.yn("Update #{type} completion script", default_response: 'n') end FileUtils.cp(src, default_dir) Doing.logger.warn('File written:', "#{type} completions saved to #{default_file(type)}") end |
.link_default(type) ⇒ Object
85 86 87 88 89 90 91 92 93 94 |
# File 'lib/doing/completion.rb', line 85 def link_default(type) type = normalize_type(type) raise InvalidArgument, 'Unrecognized shell specified' if type == :invalid return i[zsh bash fish].each { |t| link_default(t) } if type == :all install_builtin(type) link_completion_type(type, File.join(default_dir, default_filenames[type])) end |
.normalize_type(type) ⇒ Object
108 109 110 111 112 113 114 115 116 117 118 119 120 121 |
# File 'lib/doing/completion.rb', line 108 def normalize_type(type) case type.to_s when /^f/i :fish when /^b/i :bash when /^z/i :zsh when /^a/i :all else :invalid end end |
.parse_command(command) ⇒ Object
47 48 49 50 51 52 53 54 55 56 |
# File 'lib/doing/completion.rb', line 47 def parse_command(command) res = command.match(COMMAND_RX) commands = [res['cmd']] commands.concat(res['alias'].split(/, /).delete_if(&:empty?)) if res['alias'] { commands: commands, description: res['desc'].short_desc } end |
.parse_commands(commands) ⇒ Object
58 59 60 |
# File 'lib/doing/completion.rb', line 58 def parse_commands(commands) commands.map { |cmd| parse_command(cmd) } end |
.parse_option(option) ⇒ Object
31 32 33 34 35 36 37 38 39 40 41 |
# File 'lib/doing/completion.rb', line 31 def parse_option(option) res = option.match(OPTIONS_RX) return nil unless res { short: res['short'], long: res['long'], arg: res['arg'], description: res['desc'].short_desc } end |
.parse_options(options) ⇒ Object
43 44 45 |
# File 'lib/doing/completion.rb', line 43 def () .map { |opt| parse_option(opt) } end |