na 1.2.6 → 1.2.7
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/CHANGELOG.md +13 -0
- data/Gemfile.lock +1 -1
- data/README.md +13 -7
- data/bin/na +7 -11
- data/lib/na/next_action.rb +38 -56
- data/lib/na/version.rb +1 -1
- data/src/README.md +12 -6
- metadata +2 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 77270e07e7c7d4332a5fb8ec87f4e9ad5496bd220d188e75adfb71026aff1180
|
4
|
+
data.tar.gz: a3521feaefc9573bd78344b6a16ae57719284bde611e8f9f6e664238fcc1b5c3
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 2a714a764879036b9ad51626445e9ef920909da333e3fc6ecb18b8b3755cf8afad811c7baf1e3aea622a5d74b1ca41e1cf64c43541f772db9ae50cfc03c1de90
|
7
|
+
data.tar.gz: 06b865817db9731ded06c415f5c71a10a2f8b928b0f6da5ee9cca083f951e35ee716eaf6e2558daf89ec5378910286be4304fbdbe67e17756eae2be553fee0ea
|
data/CHANGELOG.md
CHANGED
data/Gemfile.lock
CHANGED
data/README.md
CHANGED
@@ -9,7 +9,7 @@
|
|
9
9
|
_If you're one of the rare people like me who find this useful, feel free to
|
10
10
|
[buy me some coffee][donate]._
|
11
11
|
|
12
|
-
The current version of `na` is 1.2.
|
12
|
+
The current version of `na` is 1.2.7
|
13
13
|
.
|
14
14
|
|
15
15
|
`na` ("next action") is a command line tool designed to make it easy to see what your next actions are for any project, right from the command line. It works with TaskPaper-formatted files (but any plain text format will do), looking for `@na` tags (or whatever you specify) in todo files in your current folder.
|
@@ -31,9 +31,13 @@ If you don't have Ruby/RubyGems, you can install them pretty easily with Homebre
|
|
31
31
|
|
32
32
|
|
33
33
|
|
34
|
+
### Optional Dependencies
|
35
|
+
|
36
|
+
If you have [gum][] installed, na will use it for command line input when adding tasks and notes. If you have [fzf][] installed, it will be used for menus, falling back to gum if available.
|
37
|
+
|
34
38
|
### Features
|
35
39
|
|
36
|
-
You can list next actions in files in the current directory by typing `na`. By default, `na` looks for `*.taskpaper` files and extracts items tagged `@na` and not `@done`.
|
40
|
+
You can list next actions in files in the current directory by typing `na`. By default, `na` looks for `*.taskpaper` files and extracts items tagged `@na` and not `@done`. This can be modified to work with a single global file, and all of these options can be changed in the configuration.
|
37
41
|
|
38
42
|
#### Easy matching
|
39
43
|
|
@@ -73,7 +77,7 @@ SYNOPSIS
|
|
73
77
|
na [global options] command [command options] [arguments...]
|
74
78
|
|
75
79
|
VERSION
|
76
|
-
1.2.
|
80
|
+
1.2.7
|
77
81
|
|
78
82
|
GLOBAL OPTIONS
|
79
83
|
-a, --[no-]add - Add a next action (deprecated, for backwards compatibility)
|
@@ -479,6 +483,9 @@ EXAMPLES
|
|
479
483
|
|
480
484
|
Global options such as todo extension and default next action tag can be stored permanently by using the `na initconfig` command. Run na with the global options you'd like to set, and add `initconfig` at the end of the command. A file will be written to `~/.na.rc`. You can edit this manually, or just update it using the `initconfig --force` command to overwrite it with new settings.
|
481
485
|
|
486
|
+
> You can see all available global options by running `na help`.
|
487
|
+
|
488
|
+
|
482
489
|
Example: `na --ext md --na_tag next initconfig --force`
|
483
490
|
|
484
491
|
When this command is run, it doesn't include options for subcommands, but inserts placeholders for them. If you want to permanently set an option for a subcommand, you'll need to edit `~/.na.rc`. For example, if you wanted the `next` command to always recurse 2 levels deep, you could edit it to look like this:
|
@@ -509,12 +516,14 @@ When using a global file, you can additionally include `--cwd_as TYPE` to determ
|
|
509
516
|
|
510
517
|
#### Add tasks at the end of a project
|
511
518
|
|
512
|
-
By default, tasks are added at the top of the target project (Inbox, etc.). If you prefer new tasks to go at the
|
519
|
+
By default, tasks are added at the top of the target project (Inbox, etc.). If you prefer new tasks to go at the end of the project by default, include `--add_at end` as a global option when running `initconfig`.
|
513
520
|
|
514
521
|
### Prompt Hooks
|
515
522
|
|
516
523
|
You can add a prompt command to your shell to have na automatically list your next actions when you `cd` into a directory. To install a prompt command for your current shell, just run `na prompt install`. It works with Zsh, Bash, and Fish. If you'd rather make the changes to your startup file yourself, run `na prompt show` to get the hook and instructions printed out for copying.
|
517
524
|
|
525
|
+
If you're using a single global file, you'll need `--cwd_as` to be `tag` or `project` for a prompt command to work. na will detect which system you're using and provide a prompt command that lists actions based on the current directory using either project or tag.
|
526
|
+
|
518
527
|
> You can also get output for shells other than the one you're currently using by adding "bash", "zsh", or "fish" to the show or install command.
|
519
528
|
|
520
529
|
|
@@ -523,9 +532,6 @@ You can add a prompt command to your shell to have na automatically list your ne
|
|
523
532
|
|
524
533
|
After installing a hook, you'll need to close your terminal and start a new session to initialize the new commands.
|
525
534
|
|
526
|
-
### Misc
|
527
|
-
|
528
|
-
If you have [gum][] installed, na will use it for command line input when adding tasks and notes. If you have [fzf][] installed, it will be used for menus, falling back to gum if available.
|
529
535
|
|
530
536
|
[fzf]: https://github.com/junegunn/fzf
|
531
537
|
[gum]: https://github.com/charmbracelet/gum
|
data/bin/na
CHANGED
@@ -232,6 +232,7 @@ class App
|
|
232
232
|
end
|
233
233
|
elsif options[:todo]
|
234
234
|
todo = []
|
235
|
+
all_req = options[:todo] !~ /[+!\-]/
|
235
236
|
options[:todo].split(/ *, */).each do |a|
|
236
237
|
m = a.match(/^(?<req>[+\-!])?(?<tok>.*?)$/)
|
237
238
|
todo.push({
|
@@ -249,13 +250,10 @@ class App
|
|
249
250
|
unless File.exist?(target)
|
250
251
|
|
251
252
|
res = NA.yn(NA::Color.template("{by}Specified file not found, create #{todo}"), default: true)
|
252
|
-
|
253
|
-
basename = File.basename(target, ".#{NA.extension}")
|
254
|
-
NA.create_todo(target, basename)
|
255
|
-
else
|
256
|
-
NA.notify('{r}Cancelled{x}', exit_code: 1)
|
253
|
+
NA.notify('{r}Cancelled{x}', exit_code: 1) unless res
|
257
254
|
|
258
|
-
|
255
|
+
basename = File.basename(target, ".#{NA.extension}")
|
256
|
+
NA.create_todo(target, basename)
|
259
257
|
end
|
260
258
|
|
261
259
|
end
|
@@ -271,10 +269,8 @@ class App
|
|
271
269
|
end
|
272
270
|
end
|
273
271
|
target = files.count > 1 ? NA.select_file(files) : files[0]
|
274
|
-
unless files.count.positive? && File.exist?(target)
|
275
|
-
NA.notify('{r}Cancelled{x}', exit_code: 1)
|
272
|
+
NA.notify('{r}Cancelled{x}', exit_code: 1) unless files.count.positive? && File.exist?(target)
|
276
273
|
|
277
|
-
end
|
278
274
|
end
|
279
275
|
|
280
276
|
action = if args.count.positive?
|
@@ -1009,7 +1005,7 @@ class App
|
|
1009
1005
|
global[:cwd_as] =~ /^p/ ? :project : :tag
|
1010
1006
|
end
|
1011
1007
|
NA.weed_cache_file
|
1012
|
-
NA.notify("{dw}{ globals: #{NA.globals}, command_line: #{NA.command_line},
|
1008
|
+
NA.notify("{dw}{ globals: #{NA.globals}, command_line: #{NA.command_line}, command: #{NA.command}}", debug: true)
|
1013
1009
|
true
|
1014
1010
|
end
|
1015
1011
|
|
@@ -1057,6 +1053,6 @@ ARGV.each do |arg|
|
|
1057
1053
|
in_globals = false
|
1058
1054
|
end
|
1059
1055
|
end
|
1060
|
-
|
1056
|
+
NA.command = NA.command_line[0]
|
1061
1057
|
|
1062
1058
|
exit App.run(ARGV)
|
data/lib/na/next_action.rb
CHANGED
@@ -3,7 +3,7 @@
|
|
3
3
|
# Next Action methods
|
4
4
|
module NA
|
5
5
|
class << self
|
6
|
-
attr_accessor :verbose, :extension, :na_tag, :command_line, :globals, :global_file, :cwd_is, :cwd, :stdin
|
6
|
+
attr_accessor :verbose, :extension, :na_tag, :command_line, :command, :globals, :global_file, :cwd_is, :cwd, :stdin
|
7
7
|
|
8
8
|
##
|
9
9
|
## Output to STDERR
|
@@ -116,31 +116,13 @@ module NA
|
|
116
116
|
## @param files [Array] The files
|
117
117
|
## @param multiple [Boolean] allow multiple selections
|
118
118
|
##
|
119
|
+
## @return [String, Array] array if multiple
|
119
120
|
def select_file(files, multiple: false)
|
120
|
-
|
121
|
-
res = choose_from(files, prompt: 'Use which file?', multiple: multiple)
|
122
|
-
unless res
|
123
|
-
notify('{r}No file selected, cancelled', exit_code: 1)
|
124
|
-
end
|
121
|
+
res = choose_from(files, prompt: multiple ? 'Select files' : 'Select a file', multiple: multiple)
|
125
122
|
|
126
|
-
|
127
|
-
|
128
|
-
|
129
|
-
'--cursor.foreground="151"',
|
130
|
-
'--item.foreground=""'
|
131
|
-
]
|
132
|
-
args.push('--no-limit') if multiple
|
133
|
-
res = `echo #{Shellwords.escape(files.join("\n"))}|#{TTY::Which.which('gum')} choose #{args.join(' ')}`
|
134
|
-
multiple ? res.split("\n") : res.strip
|
135
|
-
else
|
136
|
-
reader = TTY::Reader.new
|
137
|
-
puts
|
138
|
-
files.each.with_index do |f, i|
|
139
|
-
puts NA::Color.template(format("{bw}%<idx> 2d{xw}) {y}%<file>s{x}\n", idx: i + 1, file: f))
|
140
|
-
end
|
141
|
-
res = reader.read_line(NA::Color.template('{bw}Use which file? {x}')).strip.to_i
|
142
|
-
files[res - 1]
|
143
|
-
end
|
123
|
+
notify('{r}No file selected, cancelled', exit_code: 1) unless res && res.length.positive?
|
124
|
+
|
125
|
+
res
|
144
126
|
end
|
145
127
|
|
146
128
|
def shift_index_after(projects, idx, length = 1)
|
@@ -166,33 +148,12 @@ module NA
|
|
166
148
|
return [projects, actions] if actions.count == 1 || all
|
167
149
|
|
168
150
|
options = actions.map { |action| "#{action.line} % #{action.parent.join('/')} : #{action.action}" }
|
169
|
-
res =
|
170
|
-
choose_from(options, prompt: 'Make a selection: ', multiple: true, sorted: true)
|
171
|
-
elsif TTY::Which.exist?('gum')
|
172
|
-
args = [
|
173
|
-
'--cursor.foreground="151"',
|
174
|
-
'--item.foreground=""',
|
175
|
-
'--no-limit'
|
176
|
-
]
|
177
|
-
`echo #{Shellwords.escape(options.join("\n"))}|#{TTY::Which.which('gum')} choose #{args.join(' ')}`.strip
|
178
|
-
else
|
179
|
-
reader = TTY::Reader.new
|
180
|
-
puts
|
181
|
-
options.each.with_index do |f, i|
|
182
|
-
puts NA::Color.template(format("{bw}%<idx> 2d{xw}) {y}%<action>s{x}\n", idx: i + 1, action: f))
|
183
|
-
end
|
184
|
-
result = reader.read_line(NA::Color.template('{bw}Use which file? {x}')).strip
|
185
|
-
if result && result.to_i.positive?
|
186
|
-
options[result.to_i - 1]
|
187
|
-
else
|
188
|
-
nil
|
189
|
-
end
|
190
|
-
end
|
151
|
+
res = choose_from(options, prompt: 'Make a selection: ', multiple: true, sorted: true)
|
191
152
|
|
192
153
|
NA.notify('{r}Cancelled', exit_code: 1) unless res && res.length.positive?
|
193
154
|
|
194
155
|
selected = []
|
195
|
-
res.
|
156
|
+
res.each do |result|
|
196
157
|
idx = result.match(/^(\d+)(?= % )/)[1]
|
197
158
|
action = actions.select { |a| a.line == idx.to_i }.first
|
198
159
|
selected.push(action)
|
@@ -327,6 +288,7 @@ module NA
|
|
327
288
|
projects.select { |proj| proj.project =~ /^#{action.parent.join(':')}$/ }.first
|
328
289
|
end
|
329
290
|
|
291
|
+
|
330
292
|
indent = "\t" * target_proj.indent
|
331
293
|
note = note.split("\n") unless note.is_a?(Array)
|
332
294
|
note = if note.empty?
|
@@ -537,7 +499,7 @@ module NA
|
|
537
499
|
parent = []
|
538
500
|
in_action = false
|
539
501
|
content.split("\n").each.with_index do |line, idx|
|
540
|
-
if line =~ /^([ \t]*)([
|
502
|
+
if line =~ /^([ \t]*)([^\-][^@()]+?): *(@\S+ *)*$/
|
541
503
|
in_action = false
|
542
504
|
proj = Regexp.last_match(2)
|
543
505
|
indent = line.indent_level
|
@@ -822,21 +784,41 @@ module NA
|
|
822
784
|
## @param sorted [Boolean] If true, sort selections alphanumerically
|
823
785
|
## @param fzf_args [Array] Additional fzf arguments
|
824
786
|
##
|
787
|
+
## @return [String, Array] array if multiple is true
|
825
788
|
def choose_from(options, prompt: 'Make a selection: ', multiple: false, sorted: true, fzf_args: [])
|
826
789
|
return nil unless $stdout.isatty
|
827
790
|
|
828
|
-
default_args = [%(--prompt="#{prompt}"), "--height=#{options.count + 2}", '--info=inline']
|
829
|
-
default_args << '--multi' if multiple
|
830
|
-
default_args << '--bind ctrl-a:select-all'
|
831
|
-
header = "esc: cancel,#{multiple ? ' tab: multi-select, ctrl-a: select all,' : ''} return: confirm"
|
832
|
-
default_args << %(--header="#{header}")
|
833
|
-
default_args.concat(fzf_args)
|
834
791
|
options.sort! if sorted
|
835
792
|
|
836
|
-
res =
|
793
|
+
res = if TTY::Which.exist?('fzf')
|
794
|
+
default_args = [%(--prompt="#{prompt}"), "--height=#{options.count + 2}", '--info=inline']
|
795
|
+
default_args << '--multi' if multiple
|
796
|
+
default_args << '--bind ctrl-a:select-all' if multiple
|
797
|
+
header = "esc: cancel,#{multiple ? ' tab: multi-select, ctrl-a: select all,' : ''} return: confirm"
|
798
|
+
default_args << %(--header="#{header}")
|
799
|
+
default_args.concat(fzf_args)
|
800
|
+
`echo #{Shellwords.escape(options.join("\n"))}|#{TTY::Which.which('fzf')} #{default_args.join(' ')}`.strip
|
801
|
+
elsif TTY::Which.exist?('gum')
|
802
|
+
args = [
|
803
|
+
'--cursor.foreground="151"',
|
804
|
+
'--item.foreground=""'
|
805
|
+
]
|
806
|
+
args.push '--no-limit' if multiple
|
807
|
+
puts NS::Color.template("{bw}#{prompt}{x}")
|
808
|
+
`echo #{Shellwords.escape(options.join("\n"))}|#{TTY::Which.which('gum')} choose #{args.join(' ')}`.strip
|
809
|
+
else
|
810
|
+
reader = TTY::Reader.new
|
811
|
+
puts
|
812
|
+
options.each.with_index do |f, i|
|
813
|
+
puts NA::Color.template(format("{bw}%<idx> 2d{xw}) {y}%<action>s{x}\n", idx: i + 1, action: f))
|
814
|
+
end
|
815
|
+
result = reader.read_line(NA::Color.template("{bw}#{prompt}{x}")).strip
|
816
|
+
result.to_i&.positive? ? options[result.to_i - 1] : nil
|
817
|
+
end
|
818
|
+
|
837
819
|
return false if res.strip.size.zero?
|
838
820
|
|
839
|
-
res
|
821
|
+
multiple ? res.split(/\n/) : res
|
840
822
|
end
|
841
823
|
|
842
824
|
def parse_search(tag, negate)
|
data/lib/na/version.rb
CHANGED
data/src/README.md
CHANGED
@@ -9,7 +9,7 @@
|
|
9
9
|
_If you're one of the rare people like me who find this useful, feel free to
|
10
10
|
[buy me some coffee][donate]._
|
11
11
|
|
12
|
-
The current version of `na` is <!--VER-->1.2.
|
12
|
+
The current version of `na` is <!--VER-->1.2.6<!--END VER-->.
|
13
13
|
|
14
14
|
`na` ("next action") is a command line tool designed to make it easy to see what your next actions are for any project, right from the command line. It works with TaskPaper-formatted files (but any plain text format will do), looking for `@na` tags (or whatever you specify) in todo files in your current folder.
|
15
15
|
|
@@ -30,9 +30,13 @@ If you don't have Ruby/RubyGems, you can install them pretty easily with Homebre
|
|
30
30
|
|
31
31
|
<!--JEKYLL> You can find the na source code (MIT license) on [GitHub][].-->
|
32
32
|
|
33
|
+
### Optional Dependencies
|
34
|
+
|
35
|
+
If you have [gum][] installed, na will use it for command line input when adding tasks and notes. If you have [fzf][] installed, it will be used for menus, falling back to gum if available.
|
36
|
+
|
33
37
|
### Features
|
34
38
|
|
35
|
-
You can list next actions in files in the current directory by typing `na`. By default, `na` looks for `*.taskpaper` files and extracts items tagged `@na` and not `@done`.
|
39
|
+
You can list next actions in files in the current directory by typing `na`. By default, `na` looks for `*.taskpaper` files and extracts items tagged `@na` and not `@done`. This can be modified to work with a single global file, and all of these options can be changed in the configuration.
|
36
40
|
|
37
41
|
#### Easy matching
|
38
42
|
|
@@ -209,6 +213,9 @@ See the help output for a list of all available actions.
|
|
209
213
|
|
210
214
|
Global options such as todo extension and default next action tag can be stored permanently by using the `na initconfig` command. Run na with the global options you'd like to set, and add `initconfig` at the end of the command. A file will be written to `~/.na.rc`. You can edit this manually, or just update it using the `initconfig --force` command to overwrite it with new settings.
|
211
215
|
|
216
|
+
> You can see all available global options by running `na help`.
|
217
|
+
<!--JEKYLL{:.tip}-->
|
218
|
+
|
212
219
|
Example: `na --ext md --na_tag next initconfig --force`
|
213
220
|
|
214
221
|
When this command is run, it doesn't include options for subcommands, but inserts placeholders for them. If you want to permanently set an option for a subcommand, you'll need to edit `~/.na.rc`. For example, if you wanted the `next` command to always recurse 2 levels deep, you could edit it to look like this:
|
@@ -239,12 +246,14 @@ When using a global file, you can additionally include `--cwd_as TYPE` to determ
|
|
239
246
|
|
240
247
|
#### Add tasks at the end of a project
|
241
248
|
|
242
|
-
By default, tasks are added at the top of the target project (Inbox, etc.). If you prefer new tasks to go at the
|
249
|
+
By default, tasks are added at the top of the target project (Inbox, etc.). If you prefer new tasks to go at the end of the project by default, include `--add_at end` as a global option when running `initconfig`.
|
243
250
|
|
244
251
|
### Prompt Hooks
|
245
252
|
|
246
253
|
You can add a prompt command to your shell to have na automatically list your next actions when you `cd` into a directory. To install a prompt command for your current shell, just run `na prompt install`. It works with Zsh, Bash, and Fish. If you'd rather make the changes to your startup file yourself, run `na prompt show` to get the hook and instructions printed out for copying.
|
247
254
|
|
255
|
+
If you're using a single global file, you'll need `--cwd_as` to be `tag` or `project` for a prompt command to work. na will detect which system you're using and provide a prompt command that lists actions based on the current directory using either project or tag.
|
256
|
+
|
248
257
|
> You can also get output for shells other than the one you're currently using by adding "bash", "zsh", or "fish" to the show or install command.
|
249
258
|
<!--JEKYLL{:.tip}-->
|
250
259
|
|
@@ -253,9 +262,6 @@ You can add a prompt command to your shell to have na automatically list your ne
|
|
253
262
|
|
254
263
|
After installing a hook, you'll need to close your terminal and start a new session to initialize the new commands.
|
255
264
|
|
256
|
-
### Misc
|
257
|
-
|
258
|
-
If you have [gum][] installed, na will use it for command line input when adding tasks and notes. If you have [fzf][] installed, it will be used for menus, falling back to gum if available.
|
259
265
|
|
260
266
|
[fzf]: https://github.com/junegunn/fzf
|
261
267
|
[gum]: https://github.com/charmbracelet/gum
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: na
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 1.2.
|
4
|
+
version: 1.2.7
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Brett Terpstra
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2022-10-
|
11
|
+
date: 2022-10-28 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: rake
|