howzit 2.0.14 → 2.0.17
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/.travis.yml +1 -1
- data/CHANGELOG.md +33 -0
- data/bin/howzit +8 -2
- data/lib/howzit/buildnote.rb +272 -155
- data/lib/howzit/colors.rb +9 -0
- data/lib/howzit/config.rb +1 -0
- data/lib/howzit/prompt.rb +20 -4
- data/lib/howzit/stringutils.rb +18 -2
- data/lib/howzit/task.rb +161 -5
- data/lib/howzit/topic.rb +6 -96
- data/lib/howzit/util.rb +8 -3
- data/lib/howzit/version.rb +1 -1
- data/lib/howzit.rb +12 -0
- data/spec/prompt_spec.rb +37 -0
- data/spec/spec_helper.rb +7 -9
- data/spec/task_spec.rb +7 -2
- data/spec/topic_spec.rb +45 -15
- data/spec/util_spec.rb +52 -0
- metadata +6 -2
data/lib/howzit/prompt.rb
CHANGED
@@ -75,18 +75,32 @@ module Howzit
|
|
75
75
|
## options and accepts a numeric response
|
76
76
|
##
|
77
77
|
## @param matches [Array] The options list
|
78
|
+
## @param height [Symbol] height of fzf menu
|
79
|
+
## (:auto adjusts height to
|
80
|
+
## number of options, anything
|
81
|
+
## else gets max height for
|
82
|
+
## terminal)
|
78
83
|
##
|
79
84
|
## @return [Array] the selected results
|
80
85
|
##
|
81
|
-
def choose(matches)
|
86
|
+
def choose(matches, height: :auto)
|
87
|
+
return [] if !$stdout.isatty || matches.count.zero?
|
88
|
+
|
82
89
|
if Util.command_exist?('fzf')
|
90
|
+
height = if height == :auto
|
91
|
+
matches.count + 3
|
92
|
+
else
|
93
|
+
TTY::Screen.rows
|
94
|
+
end
|
95
|
+
|
83
96
|
settings = [
|
84
97
|
'-0',
|
85
98
|
'-1',
|
86
99
|
'-m',
|
87
|
-
"--height=#{
|
100
|
+
"--height=#{height}",
|
88
101
|
'--header="Use tab to mark multiple selections, enter to display/run"',
|
89
|
-
'--prompt="Select a section > "'
|
102
|
+
'--prompt="Select a section > "',
|
103
|
+
'--preview="howzit {}"'
|
90
104
|
]
|
91
105
|
res = `echo #{Shellwords.escape(matches.join("\n"))} | fzf #{settings.join(' ')}`.strip
|
92
106
|
if res.nil? || res.empty?
|
@@ -96,6 +110,8 @@ module Howzit
|
|
96
110
|
return res.split(/\n/)
|
97
111
|
end
|
98
112
|
|
113
|
+
return matches if matches.count == 1
|
114
|
+
|
99
115
|
res = matches[0..9]
|
100
116
|
stty_save = `stty -g`.chomp
|
101
117
|
|
@@ -120,7 +136,7 @@ module Howzit
|
|
120
136
|
puts 'Out of range'
|
121
137
|
options_list(matches)
|
122
138
|
end
|
123
|
-
|
139
|
+
ensure
|
124
140
|
system('stty', stty_save)
|
125
141
|
exit
|
126
142
|
end
|
data/lib/howzit/stringutils.rb
CHANGED
@@ -16,6 +16,22 @@ module Howzit
|
|
16
16
|
true
|
17
17
|
end
|
18
18
|
|
19
|
+
##
|
20
|
+
## Get the title of the build note (top level header)
|
21
|
+
##
|
22
|
+
## @param truncate [Integer] Truncate to width
|
23
|
+
##
|
24
|
+
def note_title(file, truncate = 0)
|
25
|
+
title = match(/(?:^(\S.*?)(?=\n==)|^# ?(.*?)$)/)
|
26
|
+
title = if title
|
27
|
+
title[1].nil? ? title[2] : title[1]
|
28
|
+
else
|
29
|
+
file.sub(/(\.\w+)?$/, '')
|
30
|
+
end
|
31
|
+
|
32
|
+
title && truncate.positive? ? title.trunc(truncate) : title
|
33
|
+
end
|
34
|
+
|
19
35
|
##
|
20
36
|
## Replace slash escaped characters in a string with a
|
21
37
|
## zero-width space that will prevent a shell from
|
@@ -275,9 +291,9 @@ module Howzit
|
|
275
291
|
data = {}
|
276
292
|
meta.each do |k, v|
|
277
293
|
case k
|
278
|
-
when /^
|
294
|
+
when /^te?m?pl(ate)?s?$/
|
279
295
|
data['template'] = v
|
280
|
-
when /^req\w
|
296
|
+
when /^req\w*$/
|
281
297
|
data['required'] = v
|
282
298
|
else
|
283
299
|
data[k] = v
|
data/lib/howzit/task.rb
CHANGED
@@ -8,23 +8,179 @@ module Howzit
|
|
8
8
|
##
|
9
9
|
## Initialize a Task object
|
10
10
|
##
|
11
|
-
|
12
|
-
|
13
|
-
|
14
|
-
|
15
|
-
|
11
|
+
## @param attributes [Hash] the task attributes
|
12
|
+
## @param optional [Boolean] Task requires
|
13
|
+
## confirmation
|
14
|
+
## @param default [Boolean] Default response
|
15
|
+
## for confirmation dialog
|
16
|
+
##
|
17
|
+
## @option attributes :type [Symbol] task type (:block, :run, :include, :copy)
|
18
|
+
## @option attributes :title [String] task title
|
19
|
+
## @option attributes :action [String] task action
|
20
|
+
## @option attributes :parent [String] title of nested (included) topic origin
|
21
|
+
def initialize(attributes, optional: false, default: true)
|
22
|
+
@type = attributes[:type] || :run
|
23
|
+
@title = attributes[:title] || nil
|
24
|
+
@action = attributes[:action].render_arguments || nil
|
25
|
+
@parent = attributes[:parent] || nil
|
16
26
|
@optional = optional
|
17
27
|
@default = default
|
18
28
|
end
|
19
29
|
|
30
|
+
##
|
31
|
+
## Inspect
|
32
|
+
##
|
33
|
+
## @return [String] description
|
34
|
+
##
|
20
35
|
def inspect
|
21
36
|
%(<#Howzit::Task @type=:#{@type} @title="#{@title}" @block?=#{@action.split(/\n/).count > 1}>)
|
22
37
|
end
|
23
38
|
|
39
|
+
##
|
40
|
+
## Output string representation
|
41
|
+
##
|
42
|
+
## @return [String] string representation of the object.
|
43
|
+
##
|
24
44
|
def to_s
|
25
45
|
@title
|
26
46
|
end
|
27
47
|
|
48
|
+
##
|
49
|
+
## Execute a block type
|
50
|
+
##
|
51
|
+
def run_block
|
52
|
+
Howzit.console.info "{bg}Running block {bw}#{@title}{x}".c if Howzit.options[:log_level] < 2
|
53
|
+
block = @action
|
54
|
+
script = Tempfile.new('howzit_script')
|
55
|
+
begin
|
56
|
+
script.write(block)
|
57
|
+
script.close
|
58
|
+
File.chmod(0o777, script.path)
|
59
|
+
system(%(/bin/sh -c "#{script.path}"))
|
60
|
+
ensure
|
61
|
+
script.close
|
62
|
+
script.unlink
|
63
|
+
end
|
64
|
+
end
|
65
|
+
|
66
|
+
##
|
67
|
+
## Execute an include task
|
68
|
+
##
|
69
|
+
## @return [Array] [[Array] output, [Integer] number of tasks executed]
|
70
|
+
##
|
71
|
+
def run_include
|
72
|
+
output = []
|
73
|
+
matches = Howzit.buildnote.find_topic(@action)
|
74
|
+
raise "Topic not found: #{@action}" if matches.empty?
|
75
|
+
|
76
|
+
$stderr.puts "{by}Running tasks from {bw}#{matches[0].title}{x}".c if Howzit.options[:log_level] < 2
|
77
|
+
output.concat(matches[0].run(nested: true))
|
78
|
+
$stderr.puts "{by}End include: #{matches[0].tasks.count} tasks{x}".c if Howzit.options[:log_level] < 2
|
79
|
+
[output, matches[0].tasks.count]
|
80
|
+
end
|
81
|
+
|
82
|
+
##
|
83
|
+
## Execute a run task
|
84
|
+
##
|
85
|
+
def run_run
|
86
|
+
title = Howzit.options[:show_all_code] ? @action : @title
|
87
|
+
$stderr.puts "{bg}Running {bw}#{title}{x}".c if Howzit.options[:log_level] < 2
|
88
|
+
system(@action)
|
89
|
+
end
|
90
|
+
|
91
|
+
##
|
92
|
+
## Execute a copy task
|
93
|
+
##
|
94
|
+
def run_copy
|
95
|
+
title = Howzit.options[:show_all_code] ? @action : @title
|
96
|
+
$stderr.puts "{bg}Copied {bw}#{title}{bg} to clipboard{x}".c if Howzit.options[:log_level] < 2
|
97
|
+
os_copy(@action)
|
98
|
+
end
|
99
|
+
|
100
|
+
##
|
101
|
+
## Platform-agnostic copy-to-clipboard
|
102
|
+
##
|
103
|
+
## @param string [String] The string to copy
|
104
|
+
##
|
105
|
+
def os_copy(string)
|
106
|
+
os = RbConfig::CONFIG['target_os']
|
107
|
+
out = "{bg}Copying {bw}#{string}".c
|
108
|
+
case os
|
109
|
+
when /darwin.*/i
|
110
|
+
$stderr.puts "#{out} (macOS){x}".c if Howzit.options[:log_level].zero?
|
111
|
+
`echo #{Shellwords.escape(string)}'\\c'|pbcopy`
|
112
|
+
when /mingw|mswin/i
|
113
|
+
$stderr.puts "#{out} (Windows){x}".c if Howzit.options[:log_level].zero?
|
114
|
+
`echo #{Shellwords.escape(string)} | clip`
|
115
|
+
else
|
116
|
+
if 'xsel'.available?
|
117
|
+
$stderr.puts "#{out} (Linux, xsel){x}".c if Howzit.options[:log_level].zero?
|
118
|
+
`echo #{Shellwords.escape(string)}'\\c'|xsel -i`
|
119
|
+
elsif 'xclip'.available?
|
120
|
+
$stderr.puts "#{out} (Linux, xclip){x}".c if Howzit.options[:log_level].zero?
|
121
|
+
`echo #{Shellwords.escape(string)}'\\c'|xclip -i`
|
122
|
+
else
|
123
|
+
$stderr.puts out if Howzit.options[:log_level].zero?
|
124
|
+
$stderr.puts 'Unable to determine executable for clipboard.'
|
125
|
+
end
|
126
|
+
end
|
127
|
+
end
|
128
|
+
|
129
|
+
##
|
130
|
+
## Platform-agnostic open command
|
131
|
+
##
|
132
|
+
## @param command [String] The command
|
133
|
+
##
|
134
|
+
def os_open(command)
|
135
|
+
os = RbConfig::CONFIG['target_os']
|
136
|
+
out = "{bg}Opening {bw}#{command}".c
|
137
|
+
case os
|
138
|
+
when /darwin.*/i
|
139
|
+
Howzit.console.debug "#{out} (macOS){x}".c if Howzit.options[:log_level] < 2
|
140
|
+
`open #{Shellwords.escape(command)}`
|
141
|
+
when /mingw|mswin/i
|
142
|
+
Howzit.console.debug "#{out} (Windows){x}".c if Howzit.options[:log_level] < 2
|
143
|
+
`start #{Shellwords.escape(command)}`
|
144
|
+
else
|
145
|
+
if 'xdg-open'.available?
|
146
|
+
Howzit.console.debug "#{out} (Linux){x}".c if Howzit.options[:log_level] < 2
|
147
|
+
`xdg-open #{Shellwords.escape(command)}`
|
148
|
+
else
|
149
|
+
Howzit.console.debug out if Howzit.options[:log_level] < 2
|
150
|
+
Howzit.console.debug 'Unable to determine executable for `open`.'
|
151
|
+
end
|
152
|
+
end
|
153
|
+
end
|
154
|
+
|
155
|
+
##
|
156
|
+
## Execute the task
|
157
|
+
##
|
158
|
+
def run
|
159
|
+
output = []
|
160
|
+
tasks = 1
|
161
|
+
if @type == :block
|
162
|
+
run_block
|
163
|
+
else
|
164
|
+
case @type
|
165
|
+
when :include
|
166
|
+
output, tasks = run_include
|
167
|
+
when :run
|
168
|
+
run_run
|
169
|
+
when :copy
|
170
|
+
run_copy
|
171
|
+
when :open
|
172
|
+
os_open(@action)
|
173
|
+
end
|
174
|
+
end
|
175
|
+
|
176
|
+
[output, tasks]
|
177
|
+
end
|
178
|
+
|
179
|
+
##
|
180
|
+
## Output terminal-formatted list item
|
181
|
+
##
|
182
|
+
## @return [String] List representation of the object.
|
183
|
+
##
|
28
184
|
def to_list
|
29
185
|
" * #{@type}: #{@title.preserve_escapes}"
|
30
186
|
end
|
data/lib/howzit/topic.rb
CHANGED
@@ -56,52 +56,16 @@ module Howzit
|
|
56
56
|
task_count = Howzit.buildnote.find_topic(task.action)[0].tasks.count
|
57
57
|
" (#{task_count} tasks)"
|
58
58
|
else
|
59
|
-
|
59
|
+
''
|
60
60
|
end
|
61
61
|
q = %({bg}#{task.type.to_s.capitalize} {xw}"{bw}#{task.title}{xw}"#{note}{x}).c
|
62
62
|
res = Prompt.yn(q, default: task.default)
|
63
63
|
next unless res
|
64
64
|
|
65
65
|
end
|
66
|
-
|
67
|
-
|
68
|
-
|
69
|
-
block = task.action
|
70
|
-
script = Tempfile.new('howzit_script')
|
71
|
-
begin
|
72
|
-
script.write(block)
|
73
|
-
script.close
|
74
|
-
File.chmod(0777, script.path)
|
75
|
-
system(%(/bin/sh -c "#{script.path}"))
|
76
|
-
tasks += 1
|
77
|
-
ensure
|
78
|
-
script.close
|
79
|
-
script.unlink
|
80
|
-
end
|
81
|
-
else
|
82
|
-
title = Howzit.options[:show_all_code] ? task.action : task.title
|
83
|
-
case task.type
|
84
|
-
when :include
|
85
|
-
matches = Howzit.buildnote.find_topic(task.action)
|
86
|
-
raise "Topic not found: #{task.action}" if matches.empty?
|
87
|
-
|
88
|
-
$stderr.puts "{by}Running tasks from {bw}#{matches[0].title}{x}".c if Howzit.options[:log_level] < 2
|
89
|
-
output.push(matches[0].run(nested: true))
|
90
|
-
$stderr.puts "{by}End include: #{matches[0].tasks.count} tasks{x}".c if Howzit.options[:log_level] < 2
|
91
|
-
tasks += matches[0].tasks.count
|
92
|
-
when :run
|
93
|
-
$stderr.puts "{bg}Running {bw}#{title}{x}".c if Howzit.options[:log_level] < 2
|
94
|
-
system(task.action)
|
95
|
-
tasks += 1
|
96
|
-
when :copy
|
97
|
-
$stderr.puts "{bg}Copied {bw}#{title}{bg} to clipboard{x}".c if Howzit.options[:log_level] < 2
|
98
|
-
os_copy(task.action)
|
99
|
-
tasks += 1
|
100
|
-
when :open
|
101
|
-
os_open(task.action)
|
102
|
-
tasks += 1
|
103
|
-
end
|
104
|
-
end
|
66
|
+
run_output, total = task.run
|
67
|
+
output.concat(run_output)
|
68
|
+
tasks += total
|
105
69
|
end
|
106
70
|
else
|
107
71
|
Howzit.console.warn "{r}--run: No {br}@directive{xr} found in {bw}#{@title}{x}".c
|
@@ -113,61 +77,6 @@ module Howzit
|
|
113
77
|
output
|
114
78
|
end
|
115
79
|
|
116
|
-
##
|
117
|
-
## Platform-agnostic copy-to-clipboard
|
118
|
-
##
|
119
|
-
## @param string [String] The string to copy
|
120
|
-
##
|
121
|
-
def os_copy(string)
|
122
|
-
os = RbConfig::CONFIG['target_os']
|
123
|
-
out = "{bg}Copying {bw}#{string}".c
|
124
|
-
case os
|
125
|
-
when /darwin.*/i
|
126
|
-
$stderr.puts "#{out} (macOS){x}".c if Howzit.options[:log_level].zero?
|
127
|
-
`echo #{Shellwords.escape(string)}'\\c'|pbcopy`
|
128
|
-
when /mingw|mswin/i
|
129
|
-
$stderr.puts "#{out} (Windows){x}".c if Howzit.options[:log_level].zero?
|
130
|
-
`echo #{Shellwords.escape(string)} | clip`
|
131
|
-
else
|
132
|
-
if 'xsel'.available?
|
133
|
-
$stderr.puts "#{out} (Linux, xsel){x}".c if Howzit.options[:log_level].zero?
|
134
|
-
`echo #{Shellwords.escape(string)}'\\c'|xsel -i`
|
135
|
-
elsif 'xclip'.available?
|
136
|
-
$stderr.puts "#{out} (Linux, xclip){x}".c if Howzit.options[:log_level].zero?
|
137
|
-
`echo #{Shellwords.escape(string)}'\\c'|xclip -i`
|
138
|
-
else
|
139
|
-
$stderr.puts out if Howzit.options[:log_level].zero?
|
140
|
-
$stderr.puts 'Unable to determine executable for clipboard.'
|
141
|
-
end
|
142
|
-
end
|
143
|
-
end
|
144
|
-
|
145
|
-
##
|
146
|
-
## Platform-agnostic open command
|
147
|
-
##
|
148
|
-
## @param command [String] The command
|
149
|
-
##
|
150
|
-
def os_open(command)
|
151
|
-
os = RbConfig::CONFIG['target_os']
|
152
|
-
out = "{bg}Opening {bw}#{command}".c
|
153
|
-
case os
|
154
|
-
when /darwin.*/i
|
155
|
-
Howzit.console.debug "#{out} (macOS){x}".c if Howzit.options[:log_level] < 2
|
156
|
-
`open #{Shellwords.escape(command)}`
|
157
|
-
when /mingw|mswin/i
|
158
|
-
Howzit.console.debug "#{out} (Windows){x}".c if Howzit.options[:log_level] < 2
|
159
|
-
`start #{Shellwords.escape(command)}`
|
160
|
-
else
|
161
|
-
if 'xdg-open'.available?
|
162
|
-
Howzit.console.debug "#{out} (Linux){x}".c if Howzit.options[:log_level] < 2
|
163
|
-
`xdg-open #{Shellwords.escape(command)}`
|
164
|
-
else
|
165
|
-
Howzit.console.debug out if Howzit.options[:log_level] < 2
|
166
|
-
Howzit.console.debug 'Unable to determine executable for `open`.'
|
167
|
-
end
|
168
|
-
end
|
169
|
-
end
|
170
|
-
|
171
80
|
# Output a topic with fancy title and bright white text.
|
172
81
|
#
|
173
82
|
# @param options [Hash] The options
|
@@ -228,6 +137,7 @@ module Howzit
|
|
228
137
|
cmd = m[:cmd]
|
229
138
|
obj = m[:action]
|
230
139
|
title = m[:title].empty? ? obj : m[:title].strip
|
140
|
+
title = Howzit.options[:show_all_code] ? obj : title
|
231
141
|
optional = m[:optional] =~ /[?!]+/ ? true : false
|
232
142
|
default = m[:optional] =~ /!/ ? false : true
|
233
143
|
option = if optional
|
@@ -313,7 +223,7 @@ module Howzit
|
|
313
223
|
default = c[:optional] =~ /!/ ? false : true
|
314
224
|
obj = c[:action]
|
315
225
|
title = c[:title].nil? ? obj : c[:title].strip
|
316
|
-
|
226
|
+
title = Howzit.options[:show_all_code] ? obj : title
|
317
227
|
case cmd
|
318
228
|
when /include/i
|
319
229
|
# matches = Howzit.buildnote.find_topic(obj)
|
data/lib/howzit/util.rb
CHANGED
@@ -4,7 +4,6 @@ module Howzit
|
|
4
4
|
# Util class
|
5
5
|
module Util
|
6
6
|
class << self
|
7
|
-
|
8
7
|
##
|
9
8
|
## Read a file with UTF-8 encoding and
|
10
9
|
## leading/trailing whitespace removed
|
@@ -90,7 +89,7 @@ module Howzit
|
|
90
89
|
args = case pg
|
91
90
|
when 'delta'
|
92
91
|
'--pager="less -FXr"'
|
93
|
-
when
|
92
|
+
when 'less'
|
94
93
|
'-FXr'
|
95
94
|
when 'bat'
|
96
95
|
if Howzit.options[:highlight]
|
@@ -117,6 +116,11 @@ module Howzit
|
|
117
116
|
|
118
117
|
# Paginate the output
|
119
118
|
def page(text)
|
119
|
+
unless $stdout.isatty
|
120
|
+
puts text
|
121
|
+
return
|
122
|
+
end
|
123
|
+
|
120
124
|
read_io, write_io = IO.pipe
|
121
125
|
|
122
126
|
input = $stdin
|
@@ -153,6 +157,7 @@ module Howzit
|
|
153
157
|
options = {
|
154
158
|
color: true,
|
155
159
|
highlight: false,
|
160
|
+
paginate: true,
|
156
161
|
wrap: 0
|
157
162
|
}
|
158
163
|
|
@@ -168,7 +173,7 @@ module Howzit
|
|
168
173
|
|
169
174
|
output = `echo #{Shellwords.escape(string.strip)}#{pipes}`.strip
|
170
175
|
|
171
|
-
if Howzit.options[:paginate]
|
176
|
+
if options[:paginate] && Howzit.options[:paginate]
|
172
177
|
page(output)
|
173
178
|
else
|
174
179
|
puts output
|
data/lib/howzit/version.rb
CHANGED
data/lib/howzit.rb
CHANGED
@@ -55,18 +55,30 @@ module Howzit
|
|
55
55
|
@config ||= Config.new
|
56
56
|
end
|
57
57
|
|
58
|
+
##
|
59
|
+
## Array for tracking inclusions and avoiding duplicates in output
|
60
|
+
##
|
58
61
|
def inclusions
|
59
62
|
@inclusions ||= []
|
60
63
|
end
|
61
64
|
|
65
|
+
##
|
66
|
+
## Module storage for Howzit::Config.options
|
67
|
+
##
|
62
68
|
def options
|
63
69
|
config.options
|
64
70
|
end
|
65
71
|
|
72
|
+
##
|
73
|
+
## Module storage for buildnote
|
74
|
+
##
|
66
75
|
def buildnote
|
67
76
|
@buildnote ||= BuildNote.new
|
68
77
|
end
|
69
78
|
|
79
|
+
##
|
80
|
+
## Convenience method for logging with Howzit.console.warn, etc.
|
81
|
+
##
|
70
82
|
def console
|
71
83
|
@console ||= Howzit::ConsoleLogger.new(options[:log_level])
|
72
84
|
end
|
data/spec/prompt_spec.rb
ADDED
@@ -0,0 +1,37 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require 'spec_helper'
|
4
|
+
|
5
|
+
describe Howzit::Prompt do
|
6
|
+
subject(:prompt) { Howzit::Prompt }
|
7
|
+
|
8
|
+
describe '.yn' do
|
9
|
+
it 'returns default response' do
|
10
|
+
Howzit.options[:default] = true
|
11
|
+
expect(prompt.yn('Test prompt', default: true)).to be_truthy
|
12
|
+
expect(prompt.yn('Test prompt', default: false)).not_to be_truthy
|
13
|
+
end
|
14
|
+
end
|
15
|
+
|
16
|
+
describe '.color_single_options' do
|
17
|
+
it 'returns uncolored string' do
|
18
|
+
Howzit::Color.coloring = false
|
19
|
+
expect(prompt.color_single_options(%w[y n])).to eq "[y/n]"
|
20
|
+
end
|
21
|
+
end
|
22
|
+
|
23
|
+
describe '.options_list' do
|
24
|
+
it 'creates a formatted list of options' do
|
25
|
+
options = %w[one two three four five].each_with_object([]) do |x, arr|
|
26
|
+
arr << "Option item #{x}"
|
27
|
+
end
|
28
|
+
expect { prompt.options_list(options) }.to output(/ 2 \) Option item two/).to_stdout
|
29
|
+
end
|
30
|
+
end
|
31
|
+
|
32
|
+
describe '.choose' do
|
33
|
+
it 'returns a single match' do
|
34
|
+
expect(prompt.choose(['option 1']).count).to eq 1
|
35
|
+
end
|
36
|
+
end
|
37
|
+
end
|
data/spec/spec_helper.rb
CHANGED
@@ -1,13 +1,11 @@
|
|
1
|
-
#
|
1
|
+
# frozen_string_literal: true
|
2
2
|
|
3
|
-
|
4
|
-
|
5
|
-
|
6
|
-
|
7
|
-
|
8
|
-
|
9
|
-
# SimpleCov.formatter = SimpleCov::Formatter::HTMLFormatter
|
10
|
-
# end
|
3
|
+
unless ENV['CI'] == 'true'
|
4
|
+
# SimpleCov::Formatter::Codecov # For CI
|
5
|
+
require 'simplecov'
|
6
|
+
SimpleCov.formatter = SimpleCov::Formatter::HTMLFormatter
|
7
|
+
SimpleCov.start
|
8
|
+
end
|
11
9
|
|
12
10
|
require 'howzit'
|
13
11
|
require 'cli-test'
|
data/spec/task_spec.rb
CHANGED
@@ -6,8 +6,7 @@ describe Howzit::Task do
|
|
6
6
|
subject(:task) do
|
7
7
|
Howzit::Task.new({ type: :run,
|
8
8
|
title: 'List Directory',
|
9
|
-
action: 'ls'
|
10
|
-
parent: nil })
|
9
|
+
action: 'ls &> /dev/null' })
|
11
10
|
end
|
12
11
|
|
13
12
|
describe ".new" do
|
@@ -15,4 +14,10 @@ describe Howzit::Task do
|
|
15
14
|
expect(task).to be_a Howzit::Task
|
16
15
|
end
|
17
16
|
end
|
17
|
+
|
18
|
+
describe ".to_s" do
|
19
|
+
it "outputs title string" do
|
20
|
+
expect(task.to_s).to match(/List Directory/)
|
21
|
+
end
|
22
|
+
end
|
18
23
|
end
|
data/spec/topic_spec.rb
CHANGED
@@ -7,14 +7,14 @@ describe Howzit::Topic do
|
|
7
7
|
content = 'Test Content'
|
8
8
|
subject(:topic) { Howzit::Topic.new(title, content) }
|
9
9
|
|
10
|
-
describe
|
11
|
-
it
|
10
|
+
describe '.new' do
|
11
|
+
it 'makes a new topic instance' do
|
12
12
|
expect(topic).to be_a Howzit::Topic
|
13
13
|
end
|
14
|
-
it
|
14
|
+
it 'has the correct title' do
|
15
15
|
expect(topic.title).to eq title
|
16
16
|
end
|
17
|
-
it
|
17
|
+
it 'has the correct content' do
|
18
18
|
expect(topic.content).to eq content
|
19
19
|
end
|
20
20
|
end
|
@@ -23,34 +23,49 @@ end
|
|
23
23
|
describe Howzit::Topic do
|
24
24
|
subject(:topic) { @hz.find_topic('Topic Balogna')[0] }
|
25
25
|
|
26
|
-
describe
|
27
|
-
it
|
28
|
-
expect(topic.title).to match
|
26
|
+
describe '.title' do
|
27
|
+
it 'has the correct title' do
|
28
|
+
expect(topic.title).to match(/Topic Balogna/)
|
29
29
|
end
|
30
30
|
end
|
31
31
|
|
32
|
-
describe
|
33
|
-
it
|
32
|
+
describe '.tasks' do
|
33
|
+
it 'has 2 tasks' do
|
34
34
|
expect(topic.tasks.count).to eq 2
|
35
35
|
end
|
36
36
|
end
|
37
37
|
|
38
|
-
describe
|
39
|
-
it
|
38
|
+
describe '.prereqs' do
|
39
|
+
it 'has prereq' do
|
40
40
|
expect(topic.prereqs.count).to eq 1
|
41
41
|
end
|
42
|
-
|
42
|
+
end
|
43
|
+
|
44
|
+
describe '.postreqs' do
|
45
|
+
it 'has postreq' do
|
43
46
|
expect(topic.postreqs.count).to eq 1
|
44
47
|
end
|
45
48
|
end
|
46
49
|
|
47
|
-
describe
|
50
|
+
describe '.grep' do
|
51
|
+
it 'returns true for matching pattern in content' do
|
52
|
+
expect(topic.grep('prereq.*?ite')).to be_truthy
|
53
|
+
end
|
54
|
+
it 'returns true for matching pattern in title' do
|
55
|
+
expect(topic.grep('bal.*?na')).to be_truthy
|
56
|
+
end
|
57
|
+
it 'fails on bad pattern' do
|
58
|
+
expect(topic.grep('xxx+')).to_not be_truthy
|
59
|
+
end
|
60
|
+
end
|
61
|
+
|
62
|
+
describe '.run' do
|
48
63
|
Howzit.options[:default] = true
|
49
|
-
it
|
64
|
+
it 'shows prereq and postreq' do
|
50
65
|
expect { topic.run }.to output(/prerequisite/).to_stdout
|
51
66
|
expect { topic.run }.to output(/postrequisite/).to_stdout
|
52
67
|
end
|
53
|
-
it
|
68
|
+
it 'Copies to clipboard' do
|
54
69
|
expect {
|
55
70
|
ENV['RUBYOPT'] = '-W1'
|
56
71
|
Howzit.options[:log_level] = 0
|
@@ -58,4 +73,19 @@ describe Howzit::Topic do
|
|
58
73
|
}.to output(/Copied/).to_stderr
|
59
74
|
end
|
60
75
|
end
|
76
|
+
|
77
|
+
describe '.print_out' do
|
78
|
+
Howzit.options[:header_format] = :block
|
79
|
+
Howzit.options[:color] = false
|
80
|
+
it 'prints the topic title' do
|
81
|
+
expect(topic.print_out({single: true, header: true}).join("\n").uncolor).to match(/▌Topic Balogna/)
|
82
|
+
end
|
83
|
+
it 'prints a task title' do
|
84
|
+
expect(topic.print_out({single: true, header: true}).join("\n").uncolor).to match(/▶ Null Output/)
|
85
|
+
end
|
86
|
+
it 'prints task action with --show-code' do
|
87
|
+
Howzit.options[:show_all_code] = true
|
88
|
+
expect(topic.print_out({single: true, header: true}).join("\n").uncolor).to match(/▶ ls -1/)
|
89
|
+
end
|
90
|
+
end
|
61
91
|
end
|