doing 2.1.0pre → 2.1.1pre
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/.yardoc/checksums +3 -2
- data/.yardoc/object_types +0 -0
- data/.yardoc/objects/root.dat +0 -0
- data/CHANGELOG.md +14 -11
- data/Gemfile.lock +1 -1
- data/README.md +1 -1
- data/bin/doing +112 -87
- data/doc/Array.html +1 -1
- data/doc/Doing/Color.html +1 -1
- data/doc/Doing/Completion.html +1 -1
- data/doc/Doing/Configuration.html +1 -1
- data/doc/Doing/Errors/DoingNoTraceError.html +1 -1
- data/doc/Doing/Errors/DoingRuntimeError.html +1 -1
- data/doc/Doing/Errors/DoingStandardError.html +1 -1
- data/doc/Doing/Errors/EmptyInput.html +1 -1
- data/doc/Doing/Errors/NoResults.html +1 -1
- data/doc/Doing/Errors/PluginException.html +1 -1
- data/doc/Doing/Errors/UserCancelled.html +1 -1
- data/doc/Doing/Errors/WrongCommand.html +1 -1
- data/doc/Doing/Errors.html +1 -1
- data/doc/Doing/Hooks.html +1 -1
- data/doc/Doing/Item.html +1 -1
- data/doc/Doing/Items.html +1 -1
- data/doc/Doing/LogAdapter.html +1 -1
- data/doc/Doing/Note.html +1 -1
- data/doc/Doing/Pager.html +1 -1
- data/doc/Doing/Plugins.html +1 -1
- data/doc/Doing/Prompt.html +1 -1
- data/doc/Doing/Section.html +1 -1
- data/doc/Doing/Util.html +1 -1
- data/doc/Doing/WWID.html +1 -181
- data/doc/Doing.html +3 -3
- data/doc/GLI/Commands/MarkdownDocumentListener.html +1 -1
- data/doc/GLI/Commands.html +1 -1
- data/doc/GLI.html +1 -1
- data/doc/Hash.html +1 -1
- data/doc/Status.html +1 -1
- data/doc/String.html +207 -3
- data/doc/Symbol.html +1 -1
- data/doc/Time.html +1 -1
- data/doc/_index.html +1 -1
- data/doc/file.README.html +2 -2
- data/doc/index.html +2 -2
- data/doc/method_list.html +84 -84
- data/doc/top-level-namespace.html +1 -1
- data/doing.rdoc +85 -18
- data/lib/completion/doing.bash +11 -11
- data/lib/doing/string_chronify.rb +81 -0
- data/lib/doing/version.rb +1 -1
- data/lib/doing/wwid.rb +87 -75
- data/lib/doing.rb +1 -0
- metadata +2 -1
checksums.yaml
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
SHA256:
|
|
3
|
-
metadata.gz:
|
|
4
|
-
data.tar.gz:
|
|
3
|
+
metadata.gz: 76184cb36ec77d6a090e120f4bafa0bef504086a0bf47d6f51952fe69979df14
|
|
4
|
+
data.tar.gz: dab9d3052b4f8b4149444c904cf0e062c7b3da5dbead58e5987dd6818870e6b0
|
|
5
5
|
SHA512:
|
|
6
|
-
metadata.gz:
|
|
7
|
-
data.tar.gz:
|
|
6
|
+
metadata.gz: be80495dceebdccb5f4303d35f41613a8da5a9e4487fa359eb3c0cea107d21cda8d3b9cbb62f9ba61007421494db8566c8830c43a50c2be3a53caa2e05907b3b
|
|
7
|
+
data.tar.gz: a650dba9a9eb18d13a073b33a42f820fac78eb02f5433e516ed70a59426a68f9ee537ce19f50ffeb1d28fd52ebd03461fbf6c755b7d75247d3e6da04bf0a8f19
|
data/.yardoc/checksums
CHANGED
|
@@ -3,7 +3,7 @@ lib/doing/item.rb 49aa74a14f59f0c790b69369c9c97feaa1917e84
|
|
|
3
3
|
lib/doing/note.rb 99d7be3e45605d32da7e188d7ec749ba84a3d2f8
|
|
4
4
|
lib/doing/time.rb d83c862e7fffd841e12150a3d954b445a6003da9
|
|
5
5
|
lib/doing/util.rb 94fc3c3ac1cc0b3b4b1d832fe30bd6e882d1acb2
|
|
6
|
-
lib/doing/wwid.rb
|
|
6
|
+
lib/doing/wwid.rb 77ec1fe1a5e369f21b29d6e28ef5bd69facf99c3
|
|
7
7
|
lib/doing/array.rb dc9b3aeed89df820e003743e8d36078469c1aab7
|
|
8
8
|
lib/doing/hooks.rb 00feacdbf24dc67951c49ca8c1ca9a568441920e
|
|
9
9
|
lib/doing/items.rb c7b81ce1fe6a8804c62af3c83e510add5f025a8c
|
|
@@ -14,10 +14,11 @@ lib/doing/prompt.rb ebf82d725111b99717954b3083cc529da8f53f3d
|
|
|
14
14
|
lib/doing/string.rb 2c90835a9b567643ce57de0030b339cfea234f46
|
|
15
15
|
lib/doing/symbol.rb 37f5b1f006181597703911494887a11fe0c63d39
|
|
16
16
|
lib/doing/section.rb 206e119cf818f1e76798753e611180fe77bc299a
|
|
17
|
-
lib/doing/version.rb
|
|
17
|
+
lib/doing/version.rb 7680c3aed9bca99795b2abd6af1854d207775bba
|
|
18
18
|
lib/doing/cli_status.rb dbedd454c4cbbd0fed9ef30120f6ec85d18b9356
|
|
19
19
|
lib/doing/completion.rb 3b291eb38e651ea993d04db592a5e743057626e6
|
|
20
20
|
lib/doing/log_adapter.rb 5d21f966449977536452e22fa64de4a1fe334002
|
|
21
21
|
lib/doing/configuration.rb 33efe2921a604e68853abbbc026d1d28c4138a18
|
|
22
22
|
lib/doing/plugin_manager.rb fb926e3998bac0b14dd4548b16ece0d32bbe0b9e
|
|
23
|
+
lib/doing/string_chronify.rb 8e4a59db180fbb63d101cb10ee371544c48376f8
|
|
23
24
|
lib/doing/markdown_document_listener.rb 45485f225068a34951ec818a345f642323e5ba35
|
data/.yardoc/object_types
CHANGED
|
Binary file
|
data/.yardoc/objects/root.dat
CHANGED
|
Binary file
|
data/CHANGELOG.md
CHANGED
|
@@ -1,3 +1,17 @@
|
|
|
1
|
+
### 2.1.1pre
|
|
2
|
+
|
|
3
|
+
#### NEW
|
|
4
|
+
|
|
5
|
+
- --before, --after, and --from date filters for select command
|
|
6
|
+
- --from flag for `doing today` and `doing yesterday`, filter by time range
|
|
7
|
+
- --from flag for `doing search`, filter by date/time range
|
|
8
|
+
- Commands that accept --before, --after, and --from can now filter on time ranges. If the date string given contains only a time (no day or date), it will be interpreted as a time range, meaning the date isn't filtered, but only entries within the time range are shown/processed
|
|
9
|
+
|
|
10
|
+
#### FIXED
|
|
11
|
+
|
|
12
|
+
- `finish --took 60m` is supposed to backdate the start date if needed to finish at the current time and maintain an elapsed time
|
|
13
|
+
- If an editor was specified for config (or default as fallback) with command line options (e.g. `emacs -nw`), Doing would fail to recognize that the executable was available.
|
|
14
|
+
|
|
1
15
|
### 2.1.0pre
|
|
2
16
|
|
|
3
17
|
#### NEW
|
|
@@ -15,17 +29,6 @@
|
|
|
15
29
|
- System agnostic method for checking available executables (pager, editor)
|
|
16
30
|
- Using `config set` and selecting a local config will no longer write the entire config to the local .doingrc. Instead, a nested path to the particular setting will be added to the config file.
|
|
17
31
|
|
|
18
|
-
### 2.0.26
|
|
19
|
-
|
|
20
|
-
#### NEW
|
|
21
|
-
|
|
22
|
-
- BREAKING CHANGE: custom classes for Section (hash) and Items (Array). @content is still a regular Hash. Sections have methods :original and :items. This will affect plugins as wwid.content[section][:items] is now wwid[section].items (same for :original)
|
|
23
|
-
|
|
24
|
-
#### IMPROVED
|
|
25
|
-
|
|
26
|
-
- Config -o raw outputs value as YAML if result is a Hash/mapping, unquoted string if a single value, comma-separated list if it's an Array.
|
|
27
|
-
- Config -o json no longer includes key, only value.
|
|
28
|
-
|
|
29
32
|
### 2.0.25
|
|
30
33
|
|
|
31
34
|
#### NEW
|
data/Gemfile.lock
CHANGED
data/README.md
CHANGED
|
@@ -6,7 +6,7 @@ _If you're one of the rare people like me who find this useful, feel free to [bu
|
|
|
6
6
|
|
|
7
7
|
<!--README-->
|
|
8
8
|
|
|
9
|
-
The current version of `doing` is <!--VER-->2.0
|
|
9
|
+
The current version of `doing` is <!--VER-->2.1.0<!--END VER-->.
|
|
10
10
|
|
|
11
11
|
Find all of the documentation in the [doing wiki](https://github.com/ttscoff/doing/wiki).
|
|
12
12
|
|
data/bin/doing
CHANGED
|
@@ -146,9 +146,9 @@ command %i[now next] do |c|
|
|
|
146
146
|
|
|
147
147
|
c.action do |_global_options, options, args|
|
|
148
148
|
if options[:back]
|
|
149
|
-
date =
|
|
149
|
+
date = options[:back].chronify(guess: :begin)
|
|
150
150
|
|
|
151
|
-
raise InvalidTimeExpression.new('unable to parse date string', topic: '
|
|
151
|
+
raise InvalidTimeExpression.new('unable to parse date string', topic: 'Parser:') if date.nil?
|
|
152
152
|
else
|
|
153
153
|
date = Time.now
|
|
154
154
|
end
|
|
@@ -421,7 +421,7 @@ command :meanwhile do |c|
|
|
|
421
421
|
|
|
422
422
|
c.action do |_global_options, options, args|
|
|
423
423
|
if options[:back]
|
|
424
|
-
date =
|
|
424
|
+
date = options[:back].chronify(guess: :begin)
|
|
425
425
|
|
|
426
426
|
raise InvalidTimeExpression, 'Unable to parse date string' if date.nil?
|
|
427
427
|
else
|
|
@@ -548,6 +548,25 @@ command :select do |c|
|
|
|
548
548
|
c.arg_name 'QUERY'
|
|
549
549
|
c.flag %i[q query search]
|
|
550
550
|
|
|
551
|
+
c.desc 'Select from entries older than date. If this is only a time (8am, 1:30pm, 15:00), all dates will be included, but entries will be filtered by time of day.'
|
|
552
|
+
c.arg_name 'DATE_STRING'
|
|
553
|
+
c.flag [:before]
|
|
554
|
+
|
|
555
|
+
c.desc 'Select from entries newer than date. If this is only a time (8am, 1:30pm, 15:00), all dates will be included, but entries will be filtered by time of day.'
|
|
556
|
+
c.arg_name 'DATE_STRING'
|
|
557
|
+
c.flag [:after]
|
|
558
|
+
|
|
559
|
+
c.desc %(
|
|
560
|
+
Date range to show, or a single day to filter date on.
|
|
561
|
+
Date range argument should be quoted. Date specifications can be natural language.
|
|
562
|
+
To specify a range, use "to" or "through": `doing select --from "monday 8am to friday 5pm"`.
|
|
563
|
+
|
|
564
|
+
If values are only time(s) (6am to noon) all dates will be included, but entries will be filtered
|
|
565
|
+
by time of day.
|
|
566
|
+
)
|
|
567
|
+
c.arg_name 'DATE_OR_RANGE'
|
|
568
|
+
c.flag [:from]
|
|
569
|
+
|
|
551
570
|
c.desc 'Force exact search string matching (case sensitive)'
|
|
552
571
|
c.switch %i[x exact], default_value: false, negatable: false
|
|
553
572
|
|
|
@@ -620,7 +639,7 @@ command :later do |c|
|
|
|
620
639
|
|
|
621
640
|
c.action do |_global_options, options, args|
|
|
622
641
|
if options[:back]
|
|
623
|
-
date =
|
|
642
|
+
date = options[:back].chronify(guess: :begin)
|
|
624
643
|
raise InvalidTimeExpression, 'Unable to parse date string' if date.nil?
|
|
625
644
|
else
|
|
626
645
|
date = Time.now
|
|
@@ -715,19 +734,19 @@ command %i[done did] do |c|
|
|
|
715
734
|
donedate = nil
|
|
716
735
|
|
|
717
736
|
if options[:took]
|
|
718
|
-
took =
|
|
737
|
+
took = options[:took].chronify_qty
|
|
719
738
|
raise InvalidTimeExpression, 'Unable to parse date string for --took' if took.nil?
|
|
720
739
|
end
|
|
721
740
|
|
|
722
741
|
if options[:back]
|
|
723
|
-
date =
|
|
742
|
+
date = options[:back].chronify(guess: :begin)
|
|
724
743
|
raise InvalidTimeExpression, 'Unable to parse date string for --back' if date.nil?
|
|
725
744
|
else
|
|
726
745
|
date = options[:took] ? Time.now - took : Time.now
|
|
727
746
|
end
|
|
728
747
|
|
|
729
748
|
if options[:at]
|
|
730
|
-
finish_date =
|
|
749
|
+
finish_date = options[:at].chronify(guess: :begin)
|
|
731
750
|
raise InvalidTimeExpression, 'Unable to parse date string for --at' if finish_date.nil?
|
|
732
751
|
|
|
733
752
|
date = options[:took] ? finish_date - took : finish_date
|
|
@@ -1028,7 +1047,7 @@ command :finish do |c|
|
|
|
1028
1047
|
options[:fuzzy] = false
|
|
1029
1048
|
unless options[:auto]
|
|
1030
1049
|
if options[:took]
|
|
1031
|
-
took =
|
|
1050
|
+
took = options[:took].chronify_qty
|
|
1032
1051
|
raise InvalidTimeExpression, 'Unable to parse date string for --took' if took.nil?
|
|
1033
1052
|
end
|
|
1034
1053
|
|
|
@@ -1037,21 +1056,21 @@ command :finish do |c|
|
|
|
1037
1056
|
raise InvalidArgument, '--search and --tag can not be used together' if options[:search] && options[:tag]
|
|
1038
1057
|
|
|
1039
1058
|
if options[:at]
|
|
1040
|
-
finish_date =
|
|
1059
|
+
finish_date = options[:at].chronify(guess: :begin)
|
|
1041
1060
|
raise InvalidTimeExpression, 'Unable to parse date string for --at' if finish_date.nil?
|
|
1042
1061
|
|
|
1043
1062
|
date = options[:took] ? finish_date - took : finish_date
|
|
1044
1063
|
elsif options[:back]
|
|
1045
|
-
date =
|
|
1064
|
+
date = options[:back].chronify()
|
|
1046
1065
|
|
|
1047
1066
|
raise InvalidTimeExpression, 'Unable to parse date string' if date.nil?
|
|
1048
|
-
elsif options[:took]
|
|
1049
|
-
date = wwid.chronify_qty(options[:took])
|
|
1050
1067
|
else
|
|
1051
1068
|
date = Time.now
|
|
1052
1069
|
end
|
|
1053
1070
|
end
|
|
1054
1071
|
|
|
1072
|
+
options[:took] = options[:took].chronify_qty if options[:took]
|
|
1073
|
+
|
|
1055
1074
|
if options[:tag].nil?
|
|
1056
1075
|
tags = []
|
|
1057
1076
|
else
|
|
@@ -1091,6 +1110,7 @@ command :finish do |c|
|
|
|
1091
1110
|
tag: tags,
|
|
1092
1111
|
tag_bool: options[:bool].normalize_bool,
|
|
1093
1112
|
tags: ['done'],
|
|
1113
|
+
took: options[:took],
|
|
1094
1114
|
unfinished: options[:unfinished]
|
|
1095
1115
|
}
|
|
1096
1116
|
|
|
@@ -1481,14 +1501,26 @@ command :show do |c|
|
|
|
1481
1501
|
c.arg_name 'AGE'
|
|
1482
1502
|
c.flag %i[a age], default_value: 'newest'
|
|
1483
1503
|
|
|
1484
|
-
c.desc '
|
|
1504
|
+
c.desc 'Show entries older than date. If this is only a time (8am, 1:30pm, 15:00), all dates will be included, but entries will be filtered by time of day.'
|
|
1485
1505
|
c.arg_name 'DATE_STRING'
|
|
1486
1506
|
c.flag [:before]
|
|
1487
1507
|
|
|
1488
|
-
c.desc '
|
|
1508
|
+
c.desc 'Show entries newer than date. If this is only a time (8am, 1:30pm, 15:00), all dates will be included, but entries will be filtered by time of day.'
|
|
1489
1509
|
c.arg_name 'DATE_STRING'
|
|
1490
1510
|
c.flag [:after]
|
|
1491
1511
|
|
|
1512
|
+
c.desc %(
|
|
1513
|
+
Date range to show, or a single day to filter date on.
|
|
1514
|
+
Date range argument should be quoted. Date specifications can be natural language.
|
|
1515
|
+
To specify a range, use "to" or "through": `doing show --from "monday 8am to friday 5pm"`.
|
|
1516
|
+
|
|
1517
|
+
If values are only time(s) (6am to noon) all dates will be included, but entries will be filtered
|
|
1518
|
+
by time of day.
|
|
1519
|
+
)
|
|
1520
|
+
|
|
1521
|
+
c.arg_name 'DATE_OR_RANGE'
|
|
1522
|
+
c.flag [:from]
|
|
1523
|
+
|
|
1492
1524
|
c.desc 'Search filter, surround with slashes for regex (/query/), start with single quote for exact match ("\'query")'
|
|
1493
1525
|
c.arg_name 'QUERY'
|
|
1494
1526
|
c.flag [:search]
|
|
@@ -1510,14 +1542,6 @@ command :show do |c|
|
|
|
1510
1542
|
c.arg_name 'ORDER'
|
|
1511
1543
|
c.flag %i[s sort], must_match: REGEX_SORT_ORDER, default_value: 'asc'
|
|
1512
1544
|
|
|
1513
|
-
c.desc %(
|
|
1514
|
-
Date range to show, or a single day to filter date on.
|
|
1515
|
-
Date range argument should be quoted. Date specifications can be natural language.
|
|
1516
|
-
To specify a range, use "to" or "through": `doing show --from "monday to friday"`
|
|
1517
|
-
)
|
|
1518
|
-
c.arg_name 'DATE_OR_RANGE'
|
|
1519
|
-
c.flag %i[f from]
|
|
1520
|
-
|
|
1521
1545
|
c.desc 'Show time intervals on @done tasks'
|
|
1522
1546
|
c.switch %i[t times], default_value: true, negatable: true
|
|
1523
1547
|
|
|
@@ -1592,21 +1616,6 @@ command :show do |c|
|
|
|
1592
1616
|
}
|
|
1593
1617
|
end
|
|
1594
1618
|
|
|
1595
|
-
if options[:from]
|
|
1596
|
-
|
|
1597
|
-
date_string = options[:from]
|
|
1598
|
-
if date_string =~ / (to|through|thru|(un)?til|-+) /
|
|
1599
|
-
dates = date_string.split(/ (to|through|thru|(un)?til|-+) /)
|
|
1600
|
-
start = wwid.chronify(dates[0], guess: :begin)
|
|
1601
|
-
finish = wwid.chronify(dates[2], guess: :end)
|
|
1602
|
-
else
|
|
1603
|
-
start = wwid.chronify(date_string, guess: :begin)
|
|
1604
|
-
finish = false
|
|
1605
|
-
end
|
|
1606
|
-
raise InvalidTimeExpression, 'Unrecognized date string' unless start
|
|
1607
|
-
dates = [start, finish]
|
|
1608
|
-
end
|
|
1609
|
-
|
|
1610
1619
|
options[:times] = true if options[:totals]
|
|
1611
1620
|
|
|
1612
1621
|
template = settings['templates']['default'].deep_merge({
|
|
@@ -1627,7 +1636,6 @@ command :show do |c|
|
|
|
1627
1636
|
opt = options.dup
|
|
1628
1637
|
opt[:sort_tags] = options[:tag_sort] =~ /^n/i
|
|
1629
1638
|
opt[:count] = options[:count].to_i
|
|
1630
|
-
opt[:date_filter] = dates
|
|
1631
1639
|
opt[:highlight] = true
|
|
1632
1640
|
opt[:order] = options[:sort].normalize_order
|
|
1633
1641
|
opt[:section] = section
|
|
@@ -1658,14 +1666,25 @@ command %i[grep search] do |c|
|
|
|
1658
1666
|
c.arg_name 'NAME'
|
|
1659
1667
|
c.flag %i[s section], default_value: 'All'
|
|
1660
1668
|
|
|
1661
|
-
c.desc '
|
|
1669
|
+
c.desc 'Search entries older than date. If this is only a time (8am, 1:30pm, 15:00), all dates will be included, but entries will be filtered by time of day.'
|
|
1662
1670
|
c.arg_name 'DATE_STRING'
|
|
1663
1671
|
c.flag [:before]
|
|
1664
1672
|
|
|
1665
|
-
c.desc '
|
|
1673
|
+
c.desc 'Search entries newer than date. If this is only a time (8am, 1:30pm, 15:00), all dates will be included, but entries will be filtered by time of day.'
|
|
1666
1674
|
c.arg_name 'DATE_STRING'
|
|
1667
1675
|
c.flag [:after]
|
|
1668
1676
|
|
|
1677
|
+
c.desc %(
|
|
1678
|
+
Date range to show, or a single day to filter date on.
|
|
1679
|
+
Date range argument should be quoted. Date specifications can be natural language.
|
|
1680
|
+
To specify a range, use "to" or "through": `doing search --from "monday 8am to friday 5pm"`.
|
|
1681
|
+
|
|
1682
|
+
If values are only time(s) (6am to noon) all dates will be included, but entries will be filtered
|
|
1683
|
+
by time of day.
|
|
1684
|
+
)
|
|
1685
|
+
c.arg_name 'DATE_OR_RANGE'
|
|
1686
|
+
c.flag [:from]
|
|
1687
|
+
|
|
1669
1688
|
c.desc "Output to export format (#{Doing::Plugins.plugin_names(type: :export)})"
|
|
1670
1689
|
c.arg_name 'FORMAT'
|
|
1671
1690
|
c.flag %i[o output]
|
|
@@ -1825,19 +1844,20 @@ command :today do |c|
|
|
|
1825
1844
|
c.arg_name 'TIME_STRING'
|
|
1826
1845
|
c.flag [:after]
|
|
1827
1846
|
|
|
1847
|
+
c.desc %(
|
|
1848
|
+
Time range to show `doing today --from "12pm to 4pm"`
|
|
1849
|
+
)
|
|
1850
|
+
c.arg_name 'DATE_OR_RANGE'
|
|
1851
|
+
c.flag [:from]
|
|
1852
|
+
|
|
1828
1853
|
c.action do |_global_options, options, _args|
|
|
1829
1854
|
raise DoingRuntimeError, %(Invalid output type "#{options[:output]}") if options[:output] && options[:output] !~ Doing::Plugins.plugin_regex(type: :export)
|
|
1830
1855
|
|
|
1831
1856
|
options[:times] = true if options[:totals]
|
|
1832
1857
|
options[:sort_tags] = options[:tag_sort] =~ /^n/i
|
|
1833
|
-
|
|
1834
|
-
|
|
1835
|
-
|
|
1836
|
-
section: options[:section],
|
|
1837
|
-
sort_tags: options[:sort_tags],
|
|
1838
|
-
totals: options[:totals]
|
|
1839
|
-
}
|
|
1840
|
-
Doing::Pager.page wwid.today(options[:times], options[:output], opt).chomp
|
|
1858
|
+
filter_options = %i[after before from section sort_tags totals].each_with_object({}) { |k, hsh| hsh[k] = options[k] }
|
|
1859
|
+
|
|
1860
|
+
Doing::Pager.page wwid.today(options[:times], options[:output], filter_options).chomp
|
|
1841
1861
|
end
|
|
1842
1862
|
end
|
|
1843
1863
|
|
|
@@ -1880,10 +1900,10 @@ command :on do |c|
|
|
|
1880
1900
|
|
|
1881
1901
|
if date_string =~ / (to|through|thru) /
|
|
1882
1902
|
dates = date_string.split(/ (to|through|thru) /)
|
|
1883
|
-
start =
|
|
1884
|
-
finish =
|
|
1903
|
+
start = dates[0].chronify(guess: :begin)
|
|
1904
|
+
finish = dates[2].chronify(guess: :end)
|
|
1885
1905
|
else
|
|
1886
|
-
start =
|
|
1906
|
+
start = date_string.chronify(guess: :begin)
|
|
1887
1907
|
finish = false
|
|
1888
1908
|
end
|
|
1889
1909
|
|
|
@@ -1939,7 +1959,7 @@ command :since do |c|
|
|
|
1939
1959
|
date_string.sub!(/(day) (\d)/, '\1 at \2')
|
|
1940
1960
|
date_string.sub!(/(\d+)d( ago)?/, '\1 days ago')
|
|
1941
1961
|
|
|
1942
|
-
start =
|
|
1962
|
+
start = date_string.chronify(guess: :begin)
|
|
1943
1963
|
finish = Time.now
|
|
1944
1964
|
|
|
1945
1965
|
raise InvalidTimeExpression, 'Unrecognized date string' unless start
|
|
@@ -1987,6 +2007,12 @@ command :yesterday do |c|
|
|
|
1987
2007
|
c.arg_name 'TIME_STRING'
|
|
1988
2008
|
c.flag [:after]
|
|
1989
2009
|
|
|
2010
|
+
c.desc %(
|
|
2011
|
+
Time range to show, e.g. `doing yesterday --from "1am to 8am"`
|
|
2012
|
+
)
|
|
2013
|
+
c.arg_name 'TIME_RANGE'
|
|
2014
|
+
c.flag [:from]
|
|
2015
|
+
|
|
1990
2016
|
c.desc 'Tag sort direction (asc|desc)'
|
|
1991
2017
|
c.arg_name 'DIRECTION'
|
|
1992
2018
|
c.flag [:tag_order], must_match: REGEX_SORT_ORDER, default_value: 'asc'
|
|
@@ -1996,9 +2022,16 @@ command :yesterday do |c|
|
|
|
1996
2022
|
|
|
1997
2023
|
options[:sort_tags] = options[:tag_sort] =~ /^n/i
|
|
1998
2024
|
|
|
2025
|
+
if options[:from]
|
|
2026
|
+
options[:from] = options[:from].split(/ (?:to|through|thru|(?:un)?til|-+) /).map do |time|
|
|
2027
|
+
"yesterday #{time.sub(/(?mi)(^.*?(?=\d+)|(?<=[ap]m).*?$)/, '')}"
|
|
2028
|
+
end.join(' to ')
|
|
2029
|
+
end
|
|
2030
|
+
|
|
1999
2031
|
opt = {
|
|
2000
2032
|
after: options[:after],
|
|
2001
2033
|
before: options[:before],
|
|
2034
|
+
from: options[:from],
|
|
2002
2035
|
sort_tags: options[:sort_tags],
|
|
2003
2036
|
tag_order: options[:tag_order].normalize_order,
|
|
2004
2037
|
totals: options[:totals],
|
|
@@ -2245,14 +2278,25 @@ command :view do |c|
|
|
|
2245
2278
|
c.arg_name 'DIRECTION'
|
|
2246
2279
|
c.flag [:tag_order], must_match: REGEX_SORT_ORDER
|
|
2247
2280
|
|
|
2248
|
-
c.desc 'View entries older than date'
|
|
2281
|
+
c.desc 'View entries older than date. If this is only a time (8am, 1:30pm, 15:00), all dates will be included, but entries will be filtered by time of day.'
|
|
2249
2282
|
c.arg_name 'DATE_STRING'
|
|
2250
2283
|
c.flag [:before]
|
|
2251
2284
|
|
|
2252
|
-
c.desc 'View entries newer than date'
|
|
2285
|
+
c.desc 'View entries newer than date. If this is only a time (8am, 1:30pm, 15:00), all dates will be included, but entries will be filtered by time of day.'
|
|
2253
2286
|
c.arg_name 'DATE_STRING'
|
|
2254
2287
|
c.flag [:after]
|
|
2255
2288
|
|
|
2289
|
+
c.desc %(
|
|
2290
|
+
Date range to show, or a single day to filter date on.
|
|
2291
|
+
Date range argument should be quoted. Date specifications can be natural language.
|
|
2292
|
+
To specify a range, use "to" or "through": `doing view --from "monday 8am to friday 5pm" view_name`.
|
|
2293
|
+
|
|
2294
|
+
If values are only time(s) (6am to noon) all dates will be included, but entries will be filtered
|
|
2295
|
+
by time of day.
|
|
2296
|
+
)
|
|
2297
|
+
c.arg_name 'DATE_OR_RANGE'
|
|
2298
|
+
c.flag [:from]
|
|
2299
|
+
|
|
2256
2300
|
c.desc 'Only show items with recorded time intervals (override view settings)'
|
|
2257
2301
|
c.switch [:only_timed], default_value: false, negatable: false
|
|
2258
2302
|
|
|
@@ -2346,27 +2390,8 @@ command :view do |c|
|
|
|
2346
2390
|
else
|
|
2347
2391
|
false
|
|
2348
2392
|
end
|
|
2349
|
-
if view.key?('after') && !options[:after]
|
|
2350
|
-
options[:after] = view['after']
|
|
2351
|
-
end
|
|
2352
2393
|
|
|
2353
|
-
if view.key?(
|
|
2354
|
-
options[:before] = view['before']
|
|
2355
|
-
end
|
|
2356
|
-
|
|
2357
|
-
if view.key?('from')
|
|
2358
|
-
date_string = view['from']
|
|
2359
|
-
if date_string =~ / (to|through|thru|(un)?til|-+) /
|
|
2360
|
-
dates = date_string.split(/ (to|through|thru|(un)?til|-+) /)
|
|
2361
|
-
start = wwid.chronify(dates[0], guess: :begin)
|
|
2362
|
-
finish = wwid.chronify(dates[2], guess: :end)
|
|
2363
|
-
else
|
|
2364
|
-
start = wwid.chronify(date_string, guess: :begin)
|
|
2365
|
-
finish = false
|
|
2366
|
-
end
|
|
2367
|
-
raise InvalidTimeExpression, 'Unrecognized date string' unless start
|
|
2368
|
-
dates = [start, finish]
|
|
2369
|
-
end
|
|
2394
|
+
%w[before after from].each { |k| options[k.to_sym] = view[k] if view.key?(k) && !options[k.to_sym] }
|
|
2370
2395
|
|
|
2371
2396
|
options[:case] = options[:case].normalize_case
|
|
2372
2397
|
|
|
@@ -2378,22 +2403,21 @@ command :view do |c|
|
|
|
2378
2403
|
end
|
|
2379
2404
|
|
|
2380
2405
|
opts = options.dup
|
|
2381
|
-
opts[:search] = search
|
|
2382
|
-
opts[:output] = output_format
|
|
2383
2406
|
opts[:count] = count
|
|
2384
2407
|
opts[:format] = date_format
|
|
2385
2408
|
opts[:highlight] = options[:color]
|
|
2386
2409
|
opts[:only_timed] = only_timed
|
|
2387
2410
|
opts[:order] = order
|
|
2411
|
+
opts[:output] = options[:interactive] ? nil : options[:output]
|
|
2412
|
+
opts[:output] = output_format
|
|
2413
|
+
opts[:page_title] = page_title
|
|
2414
|
+
opts[:search] = search
|
|
2388
2415
|
opts[:section] = section
|
|
2389
2416
|
opts[:tag_filter] = tag_filter
|
|
2390
2417
|
opts[:tag_order] = tag_order
|
|
2391
2418
|
opts[:tags_color] = tags_color
|
|
2392
2419
|
opts[:template] = template
|
|
2393
2420
|
opts[:totals] = totals
|
|
2394
|
-
opts[:page_title] = page_title
|
|
2395
|
-
opts[:date_filter] = dates
|
|
2396
|
-
opts[:output] = options[:interactive] ? nil : options[:output]
|
|
2397
2421
|
|
|
2398
2422
|
Doing::Pager.page wwid.list_section(opts)
|
|
2399
2423
|
elsif title.instance_of?(FalseClass)
|
|
@@ -2597,7 +2621,7 @@ command :open do |c|
|
|
|
2597
2621
|
end
|
|
2598
2622
|
|
|
2599
2623
|
if options[:editor]
|
|
2600
|
-
raise MissingEditor, "Editor #{options[:editor]} not found" unless Doing::Util.exec_available(options[:editor])
|
|
2624
|
+
raise MissingEditor, "Editor #{options[:editor]} not found" unless Doing::Util.exec_available(options[:editor].split(/ /).first)
|
|
2601
2625
|
|
|
2602
2626
|
editor = TTY::Which.which(options[:editor])
|
|
2603
2627
|
system %(#{editor} "#{File.expand_path(wwid.doing_file)}")
|
|
@@ -2608,7 +2632,7 @@ command :open do |c|
|
|
|
2608
2632
|
system %(open -b "#{options[:bundle_id]}" "#{File.expand_path(wwid.doing_file)}")
|
|
2609
2633
|
elsif Doing::Util.find_default_editor('doing_file')
|
|
2610
2634
|
editor = Doing::Util.find_default_editor('doing_file')
|
|
2611
|
-
if Doing::Util.exec_available(editor)
|
|
2635
|
+
if Doing::Util.exec_available(editor.split(/ /).first)
|
|
2612
2636
|
system %(#{editor} "#{File.expand_path(wwid.doing_file)}")
|
|
2613
2637
|
else
|
|
2614
2638
|
system %(open -a "#{editor}" "#{File.expand_path(wwid.doing_file)}")
|
|
@@ -2703,7 +2727,7 @@ command :config do |c|
|
|
|
2703
2727
|
if options[:default]
|
|
2704
2728
|
editor = Doing::Util.find_default_editor('config')
|
|
2705
2729
|
if editor
|
|
2706
|
-
if Doing::Util.exec_available(editor)
|
|
2730
|
+
if Doing::Util.exec_available(editor.split(/ /).first)
|
|
2707
2731
|
system %(#{editor} "#{config_file}")
|
|
2708
2732
|
else
|
|
2709
2733
|
`open -a "#{editor}" "#{config_file}"`
|
|
@@ -2722,7 +2746,7 @@ command :config do |c|
|
|
|
2722
2746
|
|
|
2723
2747
|
raise MissingEditor, 'No viable editor defined in config or environment' unless editor
|
|
2724
2748
|
|
|
2725
|
-
if Doing::Util.exec_available(editor)
|
|
2749
|
+
if Doing::Util.exec_available(editor.split(/ /).first)
|
|
2726
2750
|
system %(#{editor} "#{config_file}")
|
|
2727
2751
|
else
|
|
2728
2752
|
`open -a "#{editor}" "#{config_file}"`
|
|
@@ -2730,7 +2754,7 @@ command :config do |c|
|
|
|
2730
2754
|
end
|
|
2731
2755
|
else
|
|
2732
2756
|
editor = options[:editor] || Doing::Util.default_editor
|
|
2733
|
-
raise MissingEditor, 'No EDITOR variable defined in environment' unless editor && Doing::Util.exec_available(editor)
|
|
2757
|
+
raise MissingEditor, 'No EDITOR variable defined in environment' unless editor && Doing::Util.exec_available(editor.split(/ /).first)
|
|
2734
2758
|
|
|
2735
2759
|
system %(#{editor} "#{config_file}")
|
|
2736
2760
|
end
|
|
@@ -2906,6 +2930,7 @@ command :import do |c|
|
|
|
2906
2930
|
c.arg_name 'PREFIX'
|
|
2907
2931
|
c.flag :prefix
|
|
2908
2932
|
|
|
2933
|
+
# TODO: Allow time range filtering
|
|
2909
2934
|
c.desc 'Import entries older than date'
|
|
2910
2935
|
c.arg_name 'DATE_STRING'
|
|
2911
2936
|
c.flag [:before]
|
|
@@ -2935,10 +2960,10 @@ command :import do |c|
|
|
|
2935
2960
|
date_string = options[:from]
|
|
2936
2961
|
if date_string =~ / (to|through|thru|(un)?til|-+) /
|
|
2937
2962
|
dates = date_string.split(/ (to|through|thru|(un)?til|-+) /)
|
|
2938
|
-
start =
|
|
2939
|
-
finish =
|
|
2963
|
+
start = dates[0].chronify(guess: :begin)
|
|
2964
|
+
finish = dates[2].chronify(guess: :end)
|
|
2940
2965
|
else
|
|
2941
|
-
start =
|
|
2966
|
+
start = date_string.chronify(guess: :begin)
|
|
2942
2967
|
finish = false
|
|
2943
2968
|
end
|
|
2944
2969
|
raise InvalidTimeExpression, 'Unrecognized date string' unless start
|
data/doc/Array.html
CHANGED
|
@@ -478,7 +478,7 @@ with</p>
|
|
|
478
478
|
</div>
|
|
479
479
|
|
|
480
480
|
<div id="footer">
|
|
481
|
-
Generated on Sat Nov 27
|
|
481
|
+
Generated on Sat Nov 27 13:57:12 2021 by
|
|
482
482
|
<a href="http://yardoc.org" title="Yay! A Ruby Documentation Tool" target="_parent">yard</a>
|
|
483
483
|
0.9.26 (ruby-3.0.1).
|
|
484
484
|
</div>
|
data/doc/Doing/Color.html
CHANGED
|
@@ -508,7 +508,7 @@ ANSI-sequences are stripped from the string.</p>
|
|
|
508
508
|
</div>
|
|
509
509
|
|
|
510
510
|
<div id="footer">
|
|
511
|
-
Generated on Sat Nov 27
|
|
511
|
+
Generated on Sat Nov 27 13:57:12 2021 by
|
|
512
512
|
<a href="http://yardoc.org" title="Yay! A Ruby Documentation Tool" target="_parent">yard</a>
|
|
513
513
|
0.9.26 (ruby-3.0.1).
|
|
514
514
|
</div>
|
data/doc/Doing/Completion.html
CHANGED
|
@@ -206,7 +206,7 @@ stdout</p>
|
|
|
206
206
|
</div>
|
|
207
207
|
|
|
208
208
|
<div id="footer">
|
|
209
|
-
Generated on Sat Nov 27
|
|
209
|
+
Generated on Sat Nov 27 13:57:12 2021 by
|
|
210
210
|
<a href="http://yardoc.org" title="Yay! A Ruby Documentation Tool" target="_parent">yard</a>
|
|
211
211
|
0.9.26 (ruby-3.0.1).
|
|
212
212
|
</div>
|
|
@@ -1005,7 +1005,7 @@ matched, first match wins)</p>
|
|
|
1005
1005
|
</div>
|
|
1006
1006
|
|
|
1007
1007
|
<div id="footer">
|
|
1008
|
-
Generated on Sat Nov 27
|
|
1008
|
+
Generated on Sat Nov 27 13:57:12 2021 by
|
|
1009
1009
|
<a href="http://yardoc.org" title="Yay! A Ruby Documentation Tool" target="_parent">yard</a>
|
|
1010
1010
|
0.9.26 (ruby-3.0.1).
|
|
1011
1011
|
</div>
|
|
@@ -176,7 +176,7 @@
|
|
|
176
176
|
</div>
|
|
177
177
|
|
|
178
178
|
<div id="footer">
|
|
179
|
-
Generated on Sat Nov 27
|
|
179
|
+
Generated on Sat Nov 27 13:57:12 2021 by
|
|
180
180
|
<a href="http://yardoc.org" title="Yay! A Ruby Documentation Tool" target="_parent">yard</a>
|
|
181
181
|
0.9.26 (ruby-3.0.1).
|
|
182
182
|
</div>
|
|
@@ -176,7 +176,7 @@
|
|
|
176
176
|
</div>
|
|
177
177
|
|
|
178
178
|
<div id="footer">
|
|
179
|
-
Generated on Sat Nov 27
|
|
179
|
+
Generated on Sat Nov 27 13:57:12 2021 by
|
|
180
180
|
<a href="http://yardoc.org" title="Yay! A Ruby Documentation Tool" target="_parent">yard</a>
|
|
181
181
|
0.9.26 (ruby-3.0.1).
|
|
182
182
|
</div>
|
|
@@ -176,7 +176,7 @@
|
|
|
176
176
|
</div>
|
|
177
177
|
|
|
178
178
|
<div id="footer">
|
|
179
|
-
Generated on Sat Nov 27
|
|
179
|
+
Generated on Sat Nov 27 13:57:12 2021 by
|
|
180
180
|
<a href="http://yardoc.org" title="Yay! A Ruby Documentation Tool" target="_parent">yard</a>
|
|
181
181
|
0.9.26 (ruby-3.0.1).
|
|
182
182
|
</div>
|
|
@@ -176,7 +176,7 @@
|
|
|
176
176
|
</div>
|
|
177
177
|
|
|
178
178
|
<div id="footer">
|
|
179
|
-
Generated on Sat Nov 27
|
|
179
|
+
Generated on Sat Nov 27 13:57:12 2021 by
|
|
180
180
|
<a href="http://yardoc.org" title="Yay! A Ruby Documentation Tool" target="_parent">yard</a>
|
|
181
181
|
0.9.26 (ruby-3.0.1).
|
|
182
182
|
</div>
|
|
@@ -176,7 +176,7 @@
|
|
|
176
176
|
</div>
|
|
177
177
|
|
|
178
178
|
<div id="footer">
|
|
179
|
-
Generated on Sat Nov 27
|
|
179
|
+
Generated on Sat Nov 27 13:57:12 2021 by
|
|
180
180
|
<a href="http://yardoc.org" title="Yay! A Ruby Documentation Tool" target="_parent">yard</a>
|
|
181
181
|
0.9.26 (ruby-3.0.1).
|
|
182
182
|
</div>
|
|
@@ -238,7 +238,7 @@
|
|
|
238
238
|
</div>
|
|
239
239
|
|
|
240
240
|
<div id="footer">
|
|
241
|
-
Generated on Sat Nov 27
|
|
241
|
+
Generated on Sat Nov 27 13:57:12 2021 by
|
|
242
242
|
<a href="http://yardoc.org" title="Yay! A Ruby Documentation Tool" target="_parent">yard</a>
|
|
243
243
|
0.9.26 (ruby-3.0.1).
|
|
244
244
|
</div>
|
|
@@ -176,7 +176,7 @@
|
|
|
176
176
|
</div>
|
|
177
177
|
|
|
178
178
|
<div id="footer">
|
|
179
|
-
Generated on Sat Nov 27
|
|
179
|
+
Generated on Sat Nov 27 13:57:12 2021 by
|
|
180
180
|
<a href="http://yardoc.org" title="Yay! A Ruby Documentation Tool" target="_parent">yard</a>
|
|
181
181
|
0.9.26 (ruby-3.0.1).
|
|
182
182
|
</div>
|
|
@@ -176,7 +176,7 @@
|
|
|
176
176
|
</div>
|
|
177
177
|
|
|
178
178
|
<div id="footer">
|
|
179
|
-
Generated on Sat Nov 27
|
|
179
|
+
Generated on Sat Nov 27 13:57:12 2021 by
|
|
180
180
|
<a href="http://yardoc.org" title="Yay! A Ruby Documentation Tool" target="_parent">yard</a>
|
|
181
181
|
0.9.26 (ruby-3.0.1).
|
|
182
182
|
</div>
|