doing 1.0.60 → 1.0.64
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/README.md +28 -9
- data/bin/doing +73 -10
- data/lib/doing/version.rb +1 -1
- data/lib/doing/wwid.rb +123 -78
- 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: 6e6ebff7b78368227b7642297b5b88c8f018f0a9049f42478fc070f545421b1c
|
4
|
+
data.tar.gz: bff5c3852e60db87cacaba489f30fcf93fbdb01a8b7e4cba5fd06b6fc23db936
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 3c987d7c4a54bb331a3d9db464c5e35b86b1bcc777418547067b8f3bf609756663990c42b53b12d0f36a536f86b3041943eacd539d4d0cf8d1610ff7f3333801
|
7
|
+
data.tar.gz: 514fa3c1e8acefc9ebfde3e71e517918648b57c6b52c6d2c86bc9fe79d555d158edae4a9a2dc54c91bbfc32962280e328d97e26875114d4e1b0c98f693923b04
|
data/README.md
CHANGED
@@ -29,7 +29,7 @@ _Side note:_ I actually use the library behind this utility as part of another s
|
|
29
29
|
|
30
30
|
## Installation
|
31
31
|
|
32
|
-
The current version of `doing` is <!--VER-->1.0.
|
32
|
+
The current version of `doing` is <!--VER-->1.0.63<!--END VER-->.
|
33
33
|
|
34
34
|
$ [sudo] gem install doing
|
35
35
|
|
@@ -167,7 +167,7 @@ The config also contains templates for various command outputs. Include placehol
|
|
167
167
|
- there are some random special combo colors. Use `doing colors` to see the list
|
168
168
|
- `%interval`: when used with the `-t` switch on the `show` command, it will display the time between a timestamp or _@start(date)_ tag and the _@done(date)_ tag, if it exists. Otherwise, it will remain empty.
|
169
169
|
|
170
|
-
Date formats are based on Ruby [`strftime`](http://www.ruby-doc.org/stdlib-2.1.1/libdoc/date/rdoc/Date.html#method-i-strftime) formatting.
|
170
|
+
Date formats are based on Ruby [`strftime`](http://www.ruby-doc.org/stdlib-2.1.1/libdoc/date/rdoc/Date.html#method-i-strftime) formatting. You can try it out [here](http://strftime.net).
|
171
171
|
|
172
172
|
My normal template for the `recent` command looks like this:
|
173
173
|
|
@@ -394,24 +394,41 @@ Note that you can include a tag with synonyms in the whitelist as well to tag it
|
|
394
394
|
|
395
395
|
#### Adding entries:
|
396
396
|
|
397
|
-
now,
|
397
|
+
now, next - Add an entry
|
398
398
|
later - Add an item to the Later section
|
399
|
-
done
|
399
|
+
done, did - Add a completed item with @done(date). No argument finishes last entry.
|
400
400
|
meanwhile - Finish any @meanwhile tasks and optionally create a new one
|
401
401
|
again, resume - Duplicate the last entry as new entry (without @done tag)
|
402
402
|
|
403
|
-
|
403
|
+
##### now
|
404
404
|
|
405
|
-
|
405
|
+
The `doing now` command adds an entry to the "Currently" section by default. It accepts `-s section_name` to send the new entry straight to a non-default section. It also accepts `--back=AMOUNT` to let you specify a start date in the past using "natural language." For example, `doing now --back=25m ENTRY` or `doing now --back="yesterday 3:30pm" ENTRY`.
|
406
406
|
|
407
407
|
You can finish the last unfinished task when starting a new one using `doing now` with the `-f` switch. It will look for the last task not marked _@done_ and add the _@done_ tag with the start time of the new task (either the current time or what you specified with `--back`).
|
408
408
|
|
409
|
-
|
409
|
+
> __Examples:__
|
410
|
+
>
|
411
|
+
> - `doing now Working on project X` --- Add a new entry at the current time
|
412
|
+
> - `doing now --section=Projects Working on @projectX` --- Add a new entry to a section titled "Projects"
|
413
|
+
> - `doing now --back 30m` --- Add a new entry with a backdated start time, indicating you've been working on it for 30 minutes already
|
414
|
+
> - `doing now --back 8am` --- Backdate a new entry to a specific time
|
415
|
+
> - `doing now -f Starting the next thing` --- Add a new entry at the current time, and add a @done tag to the previous item with the current time as its completion date
|
416
|
+
> - `doing now -f --back 30m Working on something new` --- Add a new entry and complete the last entry, but use a timestamp from 30 minutes ago for both.
|
410
417
|
|
411
|
-
|
418
|
+
##### done/finish
|
419
|
+
|
420
|
+
`doing done` is used to add an entry that you've already completed. Like `now`, you can specify a section with `-s section_name`. You can also skip straight to the Archive with `-a`.
|
421
|
+
|
422
|
+
`doing done` can also backdate entries using natural language with `--back 15m` or `--back "3/15 3pm"`. That will modify the starting timestamp of the entry. Used on its own, it will set the start date, and the finish date will be the current time. You can also use `--took 1h20m` or `--took 1:20` to set the finish date based on a "natural language" time interval. If `--took` is used without `--back`, then the start date is adjusted (`--took` interval is subtracted) so that the completion date is the current time.
|
412
423
|
|
413
424
|
When used with `doing done`, `--back` and `--took` allow time intervals to be accurately counted when entering items after the fact. `--took` is also available for the `doing finish` command, but cannot be used in conjunction with `--back`. (In `finish` they both set the end date, and neither has priority. `--back` allows specific days/times, `--took` uses time intervals.)
|
414
425
|
|
426
|
+
> __Examples:__
|
427
|
+
>
|
428
|
+
> - `doing done --back 1h The thing I just did` --- Add an entry for a completed task that you started an hour ago and just finished
|
429
|
+
> - `doing done --back 1h --took 20m The thing I just finished` --- Record an entry you started an hour ago and finished 20 minutes later
|
430
|
+
> - `doing done --took 20m` --- Finish the last task but change the finish date so that the total elapsed time is only 20 minutes (if the finish date would be in the future, start date will be adjusted accordingly)
|
431
|
+
|
415
432
|
All of these commands accept a `-e` argument. This opens your command line editor (as defined in the environment variable `$EDITOR`). Add your entry, save the temp file, and close it. The new entry is added. Anything after the first line is included as a note on the entry.
|
416
433
|
|
417
434
|
`doing again` (or `doing resume`) will duplicate the last @done entry (most recently completed) with a new start date (and without the @done tag). To resume the last entry matching specific tags, use `--tag=TAG`. You can specify multiple tags by separating with a comma. Multiple tags are combined with 'AND' by default (all tags must exist on the entry to match), but you can use `--bool=` to set it to 'OR' or 'NOT'. By default the new entry will be added to the same section as the matching entry, but you can specify a section with `--in=SECTION`.
|
@@ -429,7 +446,7 @@ See `doing help meanwhile` for more options.
|
|
429
446
|
|
430
447
|
##### Finishing
|
431
448
|
|
432
|
-
`doing finish` by itself is the same as `doing done` by itself. It adds _@done(timestamp)_ to the last entry. It also accepts a numeric argument to complete X number of tasks back in history. Add `-a` to also archive the affected entries.
|
449
|
+
`doing finish` by itself is the same as `doing done` by itself. It adds _@done(timestamp)_ to the last entry. It also accepts a numeric argument to complete X number of tasks back in history (0 affects all entries). Add `-a` to also archive the affected entries.
|
433
450
|
|
434
451
|
`doing finish` also provides an `--auto` flag, which you can use to set the end time of any entry to 1 minute before the start time of the next. Running a command such as `doing finish --auto 10` will go through the last 10 entries and sequentially update any without a _@done_ tag with one set to the time just before the next entry in the list.
|
435
452
|
|
@@ -445,6 +462,8 @@ You can change the boolean using `--bool=OR` (last entry containing any of the s
|
|
445
462
|
|
446
463
|
You can also include a `--no-date` switch to add `@done` without a finish date, meaning no time is tracked for the task. `doing cancel` is an alias for this. Like `finish`, `cancel` accepts a count to act on the last X entries, as well as `--archive` and `--section` options. `cancel` also accepts the `--tag` and `--bool` flags for tag filtering.
|
447
464
|
|
465
|
+
By default `doing finish` works on a single entry, the last entry or the most recent entry matching a `--tag` or `--search` query. Specifying `doing finish 10` would finish any unfinished entries within the last 10 entries. In the case of `--tag` or `--search` queries, the count serves as the maximum number of matches doing will act on, sorted in reverse date order (most recent first). A count of 0 will disable the limit entirely, acting on all matching entries.
|
466
|
+
|
448
467
|
|
449
468
|
##### Tagging and Autotagging
|
450
469
|
|
data/bin/doing
CHANGED
@@ -310,7 +310,7 @@ end
|
|
310
310
|
|
311
311
|
desc 'Add a completed item with @done(date). No argument finishes last entry.'
|
312
312
|
arg_name 'ENTRY'
|
313
|
-
command [
|
313
|
+
command %i[done did] do |c|
|
314
314
|
c.desc 'Remove @done tag'
|
315
315
|
c.switch %i[r remove], negatable: false, default_value: false
|
316
316
|
|
@@ -367,15 +367,18 @@ command [:done, :did] do |c|
|
|
367
367
|
|
368
368
|
date = options[:took] ? finish_date - took : finish_date
|
369
369
|
elsif options[:took]
|
370
|
-
finish_date = date + took
|
370
|
+
finish_date = options[:back] ? date + took : nil
|
371
371
|
elsif options[:back]
|
372
372
|
finish_date = date
|
373
373
|
else
|
374
374
|
finish_date = Time.now
|
375
375
|
end
|
376
376
|
|
377
|
+
if finish_date
|
378
|
+
donedate = options[:date] ? "(#{finish_date.strftime('%F %R')})" : ''
|
379
|
+
end
|
380
|
+
|
377
381
|
section = wwid.guess_section(options[:s]) || options[:s].cap_first
|
378
|
-
donedate = options[:date] ? "(#{finish_date.strftime('%F %R')})" : ''
|
379
382
|
|
380
383
|
if options[:e]
|
381
384
|
raise 'No EDITOR variable defined in environment' if ENV['EDITOR'].nil?
|
@@ -394,8 +397,15 @@ command [:done, :did] do |c|
|
|
394
397
|
if options[:r]
|
395
398
|
wwid.tag_last({ tags: ['done'], count: 1, section: section, remove: true })
|
396
399
|
else
|
397
|
-
|
398
|
-
|
400
|
+
options = { tags: ['done'],
|
401
|
+
archive: options[:a],
|
402
|
+
back: finish_date,
|
403
|
+
count: 1,
|
404
|
+
date: options[:date],
|
405
|
+
section: section,
|
406
|
+
took: took == 0 ? nil : took
|
407
|
+
}
|
408
|
+
wwid.tag_last(options)
|
399
409
|
end
|
400
410
|
elsif !args.empty?
|
401
411
|
title, note = wwid.format_input(args.join(' '))
|
@@ -1230,14 +1240,17 @@ desc 'Move entries between sections'
|
|
1230
1240
|
arg_name 'SECTION_NAME'
|
1231
1241
|
default_value wwid.current_section
|
1232
1242
|
command :archive do |c|
|
1233
|
-
c.desc '
|
1234
|
-
c.arg_name '
|
1235
|
-
c.flag %i[k keep],
|
1243
|
+
c.desc 'How many items to keep (ignored if archiving by tag or search)'
|
1244
|
+
c.arg_name 'X'
|
1245
|
+
c.flag %i[k keep], must_match: /^\d+$/, type: Integer
|
1236
1246
|
|
1237
1247
|
c.desc 'Move entries to'
|
1238
1248
|
c.arg_name 'SECTION_NAME'
|
1239
1249
|
c.flag %i[t to], default_value: 'Archive'
|
1240
1250
|
|
1251
|
+
c.desc 'Label moved items with @from(SECTION_NAME)'
|
1252
|
+
c.switch [:label], default_value: true, negatable: true
|
1253
|
+
|
1241
1254
|
c.desc 'Tag filter, combine multiple tags with a comma. Added for compatibility with other commands.'
|
1242
1255
|
c.arg_name 'TAG'
|
1243
1256
|
c.flag [:tag]
|
@@ -1246,21 +1259,36 @@ command :archive do |c|
|
|
1246
1259
|
c.arg_name 'BOOLEAN'
|
1247
1260
|
c.flag [:bool], must_match: /(and|or|not)/i, default_value: 'AND'
|
1248
1261
|
|
1262
|
+
c.desc 'Search filter'
|
1263
|
+
c.arg_name 'QUERY'
|
1264
|
+
c.flag [:search]
|
1265
|
+
|
1249
1266
|
c.action do |_global_options, options, args|
|
1250
1267
|
if args.empty?
|
1251
1268
|
section = wwid.current_section
|
1252
1269
|
tags = []
|
1270
|
+
elsif args[0] =~ /^all/i
|
1271
|
+
section = 'all'
|
1253
1272
|
elsif args[0] =~ /^@\S+/
|
1254
1273
|
section = 'all'
|
1255
1274
|
tags = args.map { |t| t.sub(/^@/, '').strip }
|
1256
1275
|
else
|
1257
1276
|
section = args[0].cap_first
|
1258
|
-
tags = args.length > 1 ? args[1..].map { |t| t.sub(/^@/, '').strip } :
|
1277
|
+
tags = args.length > 1 ? args[1..].map { |t| t.sub(/^@/, '').strip } : []
|
1259
1278
|
end
|
1260
1279
|
|
1280
|
+
raise '--keep and --count can\'t be used together' if options[:keep] && options[:count]
|
1281
|
+
|
1261
1282
|
tags.concat(options[:tag].split(/ *, */).map { |t| t.sub(/^@/, '').strip }) if options[:tag]
|
1262
1283
|
|
1263
|
-
|
1284
|
+
opts = {
|
1285
|
+
bool: options[:bool],
|
1286
|
+
destination: options[:to],
|
1287
|
+
keep: options[:keep],
|
1288
|
+
search: options[:search],
|
1289
|
+
tags: tags
|
1290
|
+
}
|
1291
|
+
wwid.archive(section, opts)
|
1264
1292
|
end
|
1265
1293
|
end
|
1266
1294
|
|
@@ -1363,6 +1391,41 @@ command :undo do |c|
|
|
1363
1391
|
end
|
1364
1392
|
end
|
1365
1393
|
|
1394
|
+
desc 'Import entries from an external source'
|
1395
|
+
long_desc 'Imports entries from other sources. Currently only handles JSON reports exported from Timing.app.'
|
1396
|
+
arg_name 'PATH'
|
1397
|
+
command [:import] do |c|
|
1398
|
+
c.desc 'Import type'
|
1399
|
+
c.arg_name 'TYPE'
|
1400
|
+
c.flag [:type], default_value: 'timing'
|
1401
|
+
|
1402
|
+
c.desc 'Target section'
|
1403
|
+
c.arg_name 'NAME'
|
1404
|
+
c.flag %i[s section], default_value: wwid.current_section
|
1405
|
+
|
1406
|
+
c.desc 'Tag all imported entries'
|
1407
|
+
c.arg_name 'TAGS'
|
1408
|
+
c.flag [:tag]
|
1409
|
+
|
1410
|
+
c.desc 'Prefix entries with'
|
1411
|
+
c.arg_name 'PREFIX'
|
1412
|
+
c.flag [:prefix]
|
1413
|
+
|
1414
|
+
c.action do |_global_options, options, args|
|
1415
|
+
|
1416
|
+
section = wwid.guess_section(options[:s]) || options[:s].cap_first
|
1417
|
+
|
1418
|
+
if options[:type] =~ /^tim/i
|
1419
|
+
args.each do |path|
|
1420
|
+
wwid.import_timing(path, { section: section, tag: options[:tag], prefix: options[:prefix] })
|
1421
|
+
wwid.write(wwid.doing_file)
|
1422
|
+
end
|
1423
|
+
else
|
1424
|
+
raise 'Invalid import type'
|
1425
|
+
end
|
1426
|
+
end
|
1427
|
+
end
|
1428
|
+
|
1366
1429
|
pre do |global, _command, _options, _args|
|
1367
1430
|
if global[:config_file] && global[:config_file] != wwid.config_file
|
1368
1431
|
wwid.config_file = global[:config_file]
|
data/lib/doing/version.rb
CHANGED
data/lib/doing/wwid.rb
CHANGED
@@ -310,7 +310,7 @@ class WWID
|
|
310
310
|
else
|
311
311
|
@content[section]['items'][current - 1]['note'] = [] unless @content[section]['items'][current - 1].key? 'note'
|
312
312
|
|
313
|
-
@content[section]['items'][current - 1]['note'].push(line.
|
313
|
+
@content[section]['items'][current - 1]['note'].push(line.chomp)
|
314
314
|
# end
|
315
315
|
end
|
316
316
|
end
|
@@ -667,6 +667,55 @@ class WWID
|
|
667
667
|
@results.push(%(Added "#{entry['title']}" to #{section}))
|
668
668
|
end
|
669
669
|
|
670
|
+
##
|
671
|
+
## @brief Imports a Timing report
|
672
|
+
##
|
673
|
+
## @param path (String) Path to JSON report file
|
674
|
+
## @param section (String) The section to add to
|
675
|
+
## @param opt (Hash) Additional Options
|
676
|
+
##
|
677
|
+
def import_timing(path, opt = {})
|
678
|
+
section = opt[:section] || @current_section
|
679
|
+
add_section(section) unless @content.has_key?(section)
|
680
|
+
|
681
|
+
add_tags = opt[:tag] ? opt[:tag].split(/[ ,]+/).map { |t| t.sub(/^@?/, '@') }.join(' ') : ''
|
682
|
+
prefix = opt[:prefix] ? opt[:prefix] : '[Timing.app]'
|
683
|
+
raise "File not found" unless File.exist?(File.expand_path(path))
|
684
|
+
|
685
|
+
data = JSON.parse(IO.read(File.expand_path(path)))
|
686
|
+
new_items = []
|
687
|
+
data.each do |entry|
|
688
|
+
# Only process task entries
|
689
|
+
next if entry.key?('activityType') && entry['activityType'] != 'Task'
|
690
|
+
# Only process entries with a start and end date
|
691
|
+
next unless entry.key?('startDate') && entry.key?('endDate')
|
692
|
+
|
693
|
+
start_time = Time.parse(entry['startDate'])
|
694
|
+
end_time = Time.parse(entry['endDate'])
|
695
|
+
next unless start_time && end_time
|
696
|
+
tags = entry['project'].split(/ ▸ /).map {|proj| proj.gsub(/ +/, '').downcase }
|
697
|
+
title = "#{prefix} "
|
698
|
+
title += entry.key?('activityTitle') && entry['activityTitle'] != '(Untitled Task)' ? entry['activityTitle'] : 'Working on'
|
699
|
+
tags.each do |tag|
|
700
|
+
if title =~ /\b#{tag}\b/i
|
701
|
+
title.sub!(/\b#{tag}\b/i, "@#{tag}")
|
702
|
+
else
|
703
|
+
title += " @#{tag}"
|
704
|
+
end
|
705
|
+
end
|
706
|
+
title = autotag(title) if @auto_tag
|
707
|
+
title += " @done(#{end_time.strftime('%Y-%m-%d %H:%M')})"
|
708
|
+
title.gsub!(/ +/, ' ')
|
709
|
+
title.strip!
|
710
|
+
new_entry = { 'title' => title, 'date' => start_time, 'section' => section }
|
711
|
+
new_entry['note'] = entry['notes'].split(/\n/).map(&:chomp) if entry.key?('notes')
|
712
|
+
new_items.push(new_entry)
|
713
|
+
end
|
714
|
+
|
715
|
+
@content[section]['items'].concat(new_items)
|
716
|
+
@results.push(%(Imported #{new_items.count} items to #{section}))
|
717
|
+
end
|
718
|
+
|
670
719
|
##
|
671
720
|
## @brief Return the content of the last note for a given section
|
672
721
|
##
|
@@ -776,6 +825,7 @@ class WWID
|
|
776
825
|
opt[:remove] ||= false
|
777
826
|
opt[:autotag] ||= false
|
778
827
|
opt[:back] ||= false
|
828
|
+
opt[:took] ||= nil
|
779
829
|
|
780
830
|
sec_arr = []
|
781
831
|
|
@@ -833,6 +883,13 @@ class WWID
|
|
833
883
|
else
|
834
884
|
done_date = item['date'] + (opt[:back] - item['date'])
|
835
885
|
end
|
886
|
+
elsif opt[:took]
|
887
|
+
if item['date'] + opt[:took] > Time.now
|
888
|
+
item['date'] = Time.now - opt[:took]
|
889
|
+
done_date = Time.now
|
890
|
+
else
|
891
|
+
done_date = item['date'] + opt[:took]
|
892
|
+
end
|
836
893
|
else
|
837
894
|
done_date = Time.now
|
838
895
|
end
|
@@ -1551,31 +1608,24 @@ class WWID
|
|
1551
1608
|
## section
|
1552
1609
|
##
|
1553
1610
|
## @param section (String) The source section
|
1554
|
-
## @param
|
1555
|
-
## @param destination (String) The destination section
|
1556
|
-
## @param tags (Array) Tags to archive
|
1557
|
-
## @param bool (String) Tag boolean combinator
|
1611
|
+
## @param options (Hash) Options
|
1558
1612
|
##
|
1559
|
-
def archive(section = 'Currently',
|
1613
|
+
def archive(section = 'Currently', options = {})
|
1614
|
+
count = options[:keep] || 0
|
1615
|
+
destination = options[:destination] || 'Archive'
|
1616
|
+
tags = options[:tags] || []
|
1617
|
+
bool = options[:bool] || 'AND'
|
1618
|
+
|
1560
1619
|
section = choose_section if section.nil? || section =~ /choose/i
|
1561
|
-
archive_all = section =~
|
1620
|
+
archive_all = section =~ /^all$/i # && !(tags.nil? || tags.empty?)
|
1562
1621
|
section = guess_section(section) unless archive_all
|
1563
1622
|
|
1564
|
-
add_section('Archive') if destination =~
|
1623
|
+
add_section('Archive') if destination =~ /^archive$/i && !sections.include?('Archive')
|
1565
1624
|
|
1566
1625
|
destination = guess_section(destination)
|
1567
1626
|
|
1568
1627
|
if sections.include?(destination) && (sections.include?(section) || archive_all)
|
1569
|
-
|
1570
|
-
to_archive = sections.dup
|
1571
|
-
to_archive.delete(destination)
|
1572
|
-
to_archive.each do |source, _v|
|
1573
|
-
do_archive(source, destination, { count: count, tags: tags, bool: bool, label: true })
|
1574
|
-
end
|
1575
|
-
else
|
1576
|
-
do_archive(section, destination, { count: count, tags: tags, bool: bool, label: true })
|
1577
|
-
end
|
1578
|
-
|
1628
|
+
do_archive(section, destination, { count: count, tags: tags, bool: bool, search: options[:search], label: options[:label] })
|
1579
1629
|
write(doing_file)
|
1580
1630
|
else
|
1581
1631
|
raise 'Either source or destination does not exist'
|
@@ -1589,74 +1639,69 @@ class WWID
|
|
1589
1639
|
## @param destination (String) The destination section
|
1590
1640
|
## @param opt (Hash) Additional Options
|
1591
1641
|
##
|
1592
|
-
def do_archive(
|
1593
|
-
count = opt[:count] ||
|
1594
|
-
tags
|
1595
|
-
bool
|
1596
|
-
label = opt[:label] ||
|
1642
|
+
def do_archive(sect, destination, opt = {})
|
1643
|
+
count = opt[:count] || 0
|
1644
|
+
tags = opt[:tags] || []
|
1645
|
+
bool = opt[:bool] || 'AND'
|
1646
|
+
label = opt[:label] || true
|
1597
1647
|
|
1598
|
-
|
1599
|
-
|
1648
|
+
if sect =~ /^all$/i
|
1649
|
+
all_sections = sections.dup
|
1650
|
+
all_sections.delete(destination)
|
1651
|
+
else
|
1652
|
+
all_sections = [sect]
|
1653
|
+
end
|
1600
1654
|
|
1601
|
-
|
1602
|
-
|
1603
|
-
|
1604
|
-
|
1605
|
-
|
1606
|
-
|
1607
|
-
|
1608
|
-
|
1609
|
-
|
1610
|
-
|
1611
|
-
|
1612
|
-
|
1613
|
-
|
1614
|
-
|
1615
|
-
del = true if item['title'] =~ /@#{tag}/i
|
1655
|
+
counter = 0
|
1656
|
+
|
1657
|
+
all_sections.each do |section|
|
1658
|
+
items = @content[section]['items']
|
1659
|
+
|
1660
|
+
moved_items = []
|
1661
|
+
if !tags.empty? || opt[:search]
|
1662
|
+
items.delete_if do |item|
|
1663
|
+
if (!tags.empty? && item.has_tags?(tags, bool) || (opt[:search] && item.matches_search?(opt[:search].to_s)))
|
1664
|
+
moved_items.push(item)
|
1665
|
+
counter += 1
|
1666
|
+
true
|
1667
|
+
else
|
1668
|
+
false
|
1616
1669
|
end
|
1617
|
-
|
1618
|
-
|
1619
|
-
|
1620
|
-
|
1621
|
-
|
1622
|
-
del = false if item['title'] =~ /@#{tag}/i
|
1670
|
+
end
|
1671
|
+
moved_items.each do |item|
|
1672
|
+
if label && section != 'Currently'
|
1673
|
+
item['title'] =
|
1674
|
+
item['title'].sub(/(?:@from\(.*?\))?(.*)$/, "\\1 @from(#{section})")
|
1623
1675
|
end
|
1624
|
-
moved_items.push(item) if del
|
1625
|
-
del
|
1626
1676
|
end
|
1627
|
-
|
1628
|
-
|
1629
|
-
|
1630
|
-
|
1631
|
-
|
1677
|
+
|
1678
|
+
@content[section]['items'] = items
|
1679
|
+
@content[destination]['items'].concat(moved_items)
|
1680
|
+
@results.push("Archived #{moved_items.length} items from #{section} to #{destination}")
|
1681
|
+
else
|
1682
|
+
count = items.length if count == 0 || items.length < count
|
1683
|
+
|
1684
|
+
@content[section]['items'] = if count.zero?
|
1685
|
+
[]
|
1686
|
+
else
|
1687
|
+
items[0..count - 1]
|
1688
|
+
end
|
1689
|
+
|
1690
|
+
items.map! do |item|
|
1691
|
+
if label && section != 'Currently'
|
1692
|
+
item['title'] =
|
1693
|
+
item['title'].sub(/(?:@from\(.*?\))?(.*)$/, "\\1 @from(#{section})")
|
1694
|
+
end
|
1695
|
+
item
|
1632
1696
|
end
|
1633
|
-
|
1634
|
-
|
1635
|
-
|
1636
|
-
|
1637
|
-
else
|
1638
|
-
count = items.length if items.length < count
|
1639
|
-
|
1640
|
-
@content[section]['items'] = if count.zero?
|
1641
|
-
[]
|
1642
|
-
else
|
1643
|
-
items[0..count - 1]
|
1644
|
-
end
|
1645
|
-
|
1646
|
-
items.map! do |item|
|
1647
|
-
if label && section != 'Currently'
|
1648
|
-
item['title'] =
|
1649
|
-
item['title'].sub(/(?:@from\(.*?\))?(.*)$/, "\\1 @from(#{section})")
|
1697
|
+
if items.count > count
|
1698
|
+
@content[destination]['items'].concat(items[count..-1])
|
1699
|
+
else
|
1700
|
+
@content[destination]['items'].concat(items)
|
1650
1701
|
end
|
1651
|
-
item
|
1652
|
-
end
|
1653
|
-
if items.count > count
|
1654
|
-
@content[destination]['items'].concat(items[count..-1])
|
1655
|
-
else
|
1656
|
-
@content[destination]['items'].concat(items)
|
1657
|
-
end
|
1658
1702
|
|
1659
|
-
|
1703
|
+
@results.push("Archived #{items.length - count} items from #{section} to #{destination}")
|
1704
|
+
end
|
1660
1705
|
end
|
1661
1706
|
end
|
1662
1707
|
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: doing
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 1.0.
|
4
|
+
version: 1.0.64
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Brett Terpstra
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2021-07-
|
11
|
+
date: 2021-07-22 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: rake
|