samg-timetrap 0.1.2 → 1.0.0
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.
- data/README.md +7 -8
- data/VERSION.yml +3 -3
- data/lib/timetrap/cli.rb +35 -62
- data/lib/timetrap/formatters/text.rb +54 -0
- data/spec/timetrap_spec.rb +11 -6
- metadata +1 -1
data/README.md
CHANGED
@@ -101,19 +101,18 @@ Commands
|
|
101
101
|
|
102
102
|
**display**
|
103
103
|
Display a given timesheet. If no timesheet is specified, show the current
|
104
|
-
timesheet. If ``all`` is passed as
|
104
|
+
timesheet. If ``all`` is passed as SHEET display all timesheets. Accepts
|
105
105
|
an optional ``--ids`` flag which will include the entries' ids in the output.
|
106
106
|
This is useful when editing an non running entry with ``alter``.
|
107
107
|
|
108
|
-
|
108
|
+
Display is designed to support a variety of export formats that can be
|
109
|
+
specified by passing the ``--format`` flag. This currently defaults to
|
110
|
+
text. iCal output is also supported.
|
109
111
|
|
110
|
-
|
111
|
-
Export the current sheet as a comma-separated value format spreadsheet. If
|
112
|
-
the final entry is active, it is ignored.
|
113
|
-
|
114
|
-
Currently must pass 'ical' as FORMATTER
|
112
|
+
usage: ``t display [--ids] [--start DATE] [--end DATE] [--format FMT] [SHEET | all]``
|
115
113
|
|
116
|
-
|
114
|
+
**format**
|
115
|
+
Alias for display
|
117
116
|
|
118
117
|
**in**
|
119
118
|
Start the timer for the current timesheet. Must be called before out. Notes
|
data/VERSION.yml
CHANGED
@@ -1,4 +1,4 @@
|
|
1
1
|
---
|
2
|
-
:patch:
|
3
|
-
:major:
|
4
|
-
:minor:
|
2
|
+
:patch: 0
|
3
|
+
:major: 1
|
4
|
+
:minor: 0
|
data/lib/timetrap/cli.rb
CHANGED
@@ -19,16 +19,14 @@ where COMMAND is one of:
|
|
19
19
|
* backend - open an sqlite shell to the database
|
20
20
|
usage: t backend
|
21
21
|
* display - display the current timesheet or a specific. Pass `all' as
|
22
|
-
|
23
|
-
usage: t display [--ids] [--start DATE] [--end DATE] [
|
22
|
+
SHEET to display all sheets.
|
23
|
+
usage: t display [--ids] [--start DATE] [--end DATE] [--format FMT] [SHEET | all]
|
24
24
|
-v, --ids Print database ids (for use with alter)
|
25
25
|
-s, --start <date:qs> Include entries that start on this date or later
|
26
26
|
-e, --end <date:qs> Include entries that start on this date or earlier
|
27
|
-
|
28
|
-
|
29
|
-
|
30
|
-
-s, --start <date:qs> Include entries that start on this date or later
|
31
|
-
-e, --end <date:qs> Include entries that start on this date or earlier
|
27
|
+
-f, --format <format> The output format. Currently supports ical and
|
28
|
+
text (default).
|
29
|
+
* format - alias for display
|
32
30
|
* in - start the timer for the current timesheet
|
33
31
|
usage: t in [--at TIME] [NOTES]
|
34
32
|
-a, --at <time:qs> Use this time instead of now
|
@@ -43,7 +41,7 @@ where COMMAND is one of:
|
|
43
41
|
usage: t out [--at TIME]
|
44
42
|
-a, --at <time:qs> Use this time instead of now
|
45
43
|
* running - show all running timesheets
|
46
|
-
|
44
|
+
usage: t running
|
47
45
|
* switch - switch to a new timesheet
|
48
46
|
usage: t switch TIMESHEET
|
49
47
|
|
@@ -122,72 +120,46 @@ where COMMAND is one of:
|
|
122
120
|
end
|
123
121
|
|
124
122
|
def display
|
125
|
-
|
126
|
-
|
127
|
-
|
128
|
-
|
129
|
-
|
130
|
-
[Timetrap.current_sheet]
|
131
|
-
end
|
132
|
-
entries = []
|
133
|
-
sheets.each do |sheet|
|
134
|
-
say "Timesheet: #{sheet}"
|
135
|
-
id_heading = args['-v'] ? 'Id' : ' '
|
136
|
-
say "#{id_heading} Day Start End Duration Notes"
|
137
|
-
last_start = nil
|
138
|
-
from_current_day = []
|
139
|
-
ee = Timetrap::Entry.filter(:sheet => sheet).order(:start)
|
140
|
-
ee = ee.filter(:start >= Date.parse(args['-s'])) if args['-s']
|
141
|
-
ee = ee.filter(:start <= Date.parse(args['-e']) + 1) if args['-e']
|
142
|
-
entries += ee.all
|
143
|
-
ee.each_with_index do |e, i|
|
144
|
-
|
145
|
-
|
146
|
-
from_current_day << e
|
147
|
-
e_end = e.end || Time.now
|
148
|
-
say "%-4s%16s%11s -%9s%10s %s" % [
|
149
|
-
(args['-v'] ? e.id : ''),
|
150
|
-
format_date_if_new(e.start, last_start),
|
151
|
-
format_time(e.start),
|
152
|
-
format_time(e.end),
|
153
|
-
format_duration(e.start, e_end),
|
154
|
-
e.note
|
155
|
-
]
|
156
|
-
|
157
|
-
nxt = ee.map[i+1]
|
158
|
-
if nxt == nil or !same_day?(e.start, nxt.start)
|
159
|
-
say "%52s" % format_total(from_current_day)
|
160
|
-
from_current_day = []
|
161
|
-
else
|
162
|
-
end
|
163
|
-
last_start = e.start
|
123
|
+
begin
|
124
|
+
fmt_klass = if args['-f']
|
125
|
+
Timetrap::Formatters.const_get("#{args['-f'].classify}")
|
126
|
+
else
|
127
|
+
Timetrap::Formatters::Text
|
164
128
|
end
|
165
|
-
|
166
|
-
|
167
|
-
|
168
|
-
say " Total%43s" % format_total(ee)
|
169
|
-
say "\n" unless sheet == sheets.last
|
129
|
+
rescue
|
130
|
+
say "Invalid format specified `#{args['-f']}'"
|
131
|
+
return
|
170
132
|
end
|
171
|
-
if
|
172
|
-
|
173
|
-
|
174
|
-
|
175
|
-
|
133
|
+
ee = if (sheet = sheet_name_from_string(unused_args)) == 'all'
|
134
|
+
Timetrap::Entry
|
135
|
+
elsif sheet =~ /.+/
|
136
|
+
Timetrap::Entry.filter(:sheet => sheet)
|
137
|
+
else
|
138
|
+
Timetrap::Entry.filter(:sheet => Timetrap.current_sheet)
|
176
139
|
end
|
140
|
+
ee = ee.filter(:start >= Date.parse(args['-s'])) if args['-s']
|
141
|
+
ee = ee.filter(:start <= Date.parse(args['-e']) + 1) if args['-e']
|
142
|
+
say Timetrap.format(fmt_klass, ee.order(:start).all)
|
177
143
|
end
|
178
144
|
|
179
145
|
# TODO: Consolidate display and format
|
180
146
|
def format
|
181
147
|
begin
|
182
|
-
fmt_klass = Timetrap::Formatters.const_get("#{
|
148
|
+
fmt_klass = Timetrap::Formatters.const_get("#{args['-f'].classify}")
|
183
149
|
rescue
|
184
|
-
say "Invalid format specified `#{
|
150
|
+
say "Invalid format specified `#{args['-f']}'"
|
185
151
|
return
|
186
152
|
end
|
187
|
-
ee =
|
153
|
+
ee = if (sheet = sheet_name_from_string(unused_args)) == 'all'
|
154
|
+
Timetrap::Entry
|
155
|
+
elsif sheet =~ /.+/
|
156
|
+
Timetrap::Entry.filter(:sheet => sheet)
|
157
|
+
else
|
158
|
+
Timetrap::Entry.filter(:sheet => Timetrap.current_sheet)
|
159
|
+
end
|
188
160
|
ee = ee.filter(:start >= Date.parse(args['-s'])) if args['-s']
|
189
161
|
ee = ee.filter(:start <= Date.parse(args['-e']) + 1) if args['-e']
|
190
|
-
say Timetrap.format(fmt_klass,ee.all)
|
162
|
+
say Timetrap.format(fmt_klass, ee.all)
|
191
163
|
end
|
192
164
|
|
193
165
|
def switch
|
@@ -231,7 +203,8 @@ where COMMAND is one of:
|
|
231
203
|
end
|
232
204
|
|
233
205
|
def running
|
234
|
-
say "
|
206
|
+
say "Running Timesheets:"
|
207
|
+
say Timetrap::Entry.filter(:end => nil).map{|e| " #{e.sheet}: #{e.note}"}.uniq.sort
|
235
208
|
end
|
236
209
|
|
237
210
|
private
|
@@ -1 +1,55 @@
|
|
1
|
+
module Timetrap
|
2
|
+
module Formatters
|
3
|
+
class Text
|
4
|
+
attr_accessor :output
|
5
|
+
include Timetrap::Helpers
|
1
6
|
|
7
|
+
def initialize entries
|
8
|
+
self.output = ''
|
9
|
+
sheets = entries.inject({}) do |h, e|
|
10
|
+
h[e.sheet] ||= []
|
11
|
+
h[e.sheet] << e
|
12
|
+
h
|
13
|
+
end
|
14
|
+
(sheet_names = sheets.keys.sort).each do |sheet|
|
15
|
+
self.output << "Timesheet: #{sheet}\n"
|
16
|
+
id_heading = Timetrap::CLI.args['-v'] ? 'Id' : ' '
|
17
|
+
self.output << "#{id_heading} Day Start End Duration Notes\n"
|
18
|
+
last_start = nil
|
19
|
+
from_current_day = []
|
20
|
+
sheets[sheet].each_with_index do |e, i|
|
21
|
+
from_current_day << e
|
22
|
+
e_end = e.end || Time.now
|
23
|
+
self.output << "%-4s%16s%11s -%9s%10s %s\n" % [
|
24
|
+
(Timetrap::CLI.args['-v'] ? e.id : ''),
|
25
|
+
format_date_if_new(e.start, last_start),
|
26
|
+
format_time(e.start),
|
27
|
+
format_time(e.end),
|
28
|
+
format_duration(e.start, e_end),
|
29
|
+
e.note
|
30
|
+
]
|
31
|
+
|
32
|
+
nxt = sheets[sheet].map[i+1]
|
33
|
+
if nxt == nil or !same_day?(e.start, nxt.start)
|
34
|
+
self.output << "%52s\n" % format_total(from_current_day)
|
35
|
+
from_current_day = []
|
36
|
+
else
|
37
|
+
end
|
38
|
+
last_start = e.start
|
39
|
+
end
|
40
|
+
self.output << <<-OUT
|
41
|
+
---------------------------------------------------------
|
42
|
+
OUT
|
43
|
+
self.output << " Total%43s\n" % format_total(sheets[sheet])
|
44
|
+
self.output << "\n" unless sheet == sheet_names.last
|
45
|
+
end
|
46
|
+
if sheets.size > 1
|
47
|
+
self.output << <<-OUT
|
48
|
+
-------------------------------------------------------------
|
49
|
+
OUT
|
50
|
+
self.output << "Grand Total%41s\n" % format_total(sheets.values.flatten)
|
51
|
+
end
|
52
|
+
end
|
53
|
+
end
|
54
|
+
end
|
55
|
+
end
|
data/spec/timetrap_spec.rb
CHANGED
@@ -171,17 +171,17 @@ Grand Total 10:00:00
|
|
171
171
|
end
|
172
172
|
|
173
173
|
it "should filter events by the passed dates" do
|
174
|
-
invoke 'format ical --start 2008-10-03 --end 2008-10-03'
|
174
|
+
invoke 'format --format ical --start 2008-10-03 --end 2008-10-03'
|
175
175
|
$stdout.string.scan(/BEGIN:VEVENT/).should have(1).item
|
176
176
|
end
|
177
177
|
|
178
178
|
it "should not filter events by date when none are passed" do
|
179
|
-
invoke 'format ical'
|
179
|
+
invoke 'format --format ical'
|
180
180
|
$stdout.string.scan(/BEGIN:VEVENT/).should have(2).item
|
181
181
|
end
|
182
182
|
|
183
183
|
it "should export a sheet to an ical format" do
|
184
|
-
invoke 'format ical --start 2008-10-03 --end 2008-10-03'
|
184
|
+
invoke 'format --format ical --start 2008-10-03 --end 2008-10-03'
|
185
185
|
desired = <<-EOF
|
186
186
|
BEGIN:VCALENDAR
|
187
187
|
VERSION:2.0
|
@@ -347,12 +347,16 @@ current sheet: 0:01:00 (a timesheet that is running)
|
|
347
347
|
end
|
348
348
|
|
349
349
|
describe "running" do
|
350
|
-
|
350
|
+
it "should show all running timesheets" do
|
351
351
|
create_entry :sheet => 'one', :end => nil
|
352
352
|
create_entry :sheet => 'two', :end => nil
|
353
|
+
create_entry :sheet => 'three'
|
354
|
+
invoke 'running'
|
355
|
+
$stdout.string.should == "Running Timesheets:\n one: note\n two: note\n"
|
353
356
|
end
|
354
|
-
it "should show
|
355
|
-
|
357
|
+
it "should show no runnig timesheets" do
|
358
|
+
invoke 'running'
|
359
|
+
$stdout.string.should == "Running Timesheets:\n"
|
356
360
|
end
|
357
361
|
end
|
358
362
|
|
@@ -444,6 +448,7 @@ current sheet: 0:01:00 (a timesheet that is running)
|
|
444
448
|
Timetrap.current_sheet.should == 'sheet2'
|
445
449
|
end
|
446
450
|
end
|
451
|
+
|
447
452
|
end
|
448
453
|
|
449
454
|
describe Timetrap::Entry do
|