-
Notifications
You must be signed in to change notification settings - Fork 1
/
Copy pathical-from-pivotal.rb
132 lines (105 loc) · 3.21 KB
/
ical-from-pivotal.rb
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
require 'rubygems'
require "JSON"
require 'highline/import'
require 'icalendar'
require 'date'
require 'trollop'
require 'date'
require 'tzinfo'
require_relative 'lib/ical-patch'
# commandline option parsing, trollop is much more concise than optparse
options = Trollop::options do
banner "Usage: #{$0} [options]"
opt :month, 'Month to filter results with', :type => :int, :required => true
opt :year, 'Year to filter results with', :type => :int, :required => true
opt :out, 'Output file to put the resulting ics', :type => :string
end
# This is using version 5 of the pivotal API
abort("Need to set PIVOTAL_TOKEN env variable") if !ENV['PIVOTAL_TOKEN'] || ENV['PIVOTAL_TOKEN'].empty?
first_of_month = Time.local(options[:year],options[:month]).to_datetime.iso8601
end_of_month = (Time.local(options[:year], options[:month]).to_datetime >> 1).iso8601
PT_QUERY = "envelope=true&limit=100&occurred_after=#{first_of_month}&occurred_before=#{end_of_month}"
PT_URL = "https://www.pivotaltracker.com/services/v5/my/activity?#{PT_QUERY}"
def get_data(url)
puts "PT URL: #{url}"
`curl -X GET -H "X-TrackerToken: #{ENV['PIVOTAL_TOKEN']}" "#{url}"`
end
total = 1
loaded = 0
month_activity = []
while loaded < total do
response = get_data(PT_URL + "&offset=#{loaded}")
envelope = JSON.parse(response)
total = envelope["pagination"]["total"]
loaded += envelope["pagination"]["limit"]
month_activity.push(*envelope["data"])
end
def event_time(event)
DateTime.parse(event['occurred_at']).to_time
end
class VisitEventTrail
attr_accessor :events
def initialize()
@events = []
end
def add(event)
events.push event
end
def dtstart
event_time(events.first).to_datetime
end
def dtend
first_time = event_time(events.first)
# use a 8 minute minimun event size
end_time = first_time + 8*60
if event_time(events.last) > end_time
end_time = event_time(events.last)
end
end_time.to_datetime
end
def event_summary(event)
if (event['highlight'] == "added comment:")
event['message'].gsub("Scott Cytacki ","") + " to " + event['primary_resources'][0]['name']
else
"#{event['highlight']} #{event['primary_resources'][0]['name']}"
end
end
def description
output = ""
output += events.collect{|event|
"#{event_time(event).to_datetime.strftime('%R')} #{event_summary(event)[0...200]}"
}.join("\n")
end
def summary
"#{events.first['project']['name']}: #{events.size} events"
end
end
pt_events = []
trails = []
month_activity.reverse.each { |activity|
puts "- #{activity['occurred_at']}: #{activity['message'].gsub("Scott Cytacki ","").gsub("\n"," ")[0...100]}"
last_event = pt_events.last
pt_events.push(activity)
# look for overlaping events
if (last_event and
activity['project']['name'] == last_event['project']['name'] and
(event_time(last_event) + 180) > event_time(activity))
trails.last.add activity
next
end
trail = VisitEventTrail.new
trail.add activity
trails.push trail
}
cal = Icalendar::Calendar.new
trails.each {|trail|
cal.event{
dtstart trail.dtstart
dtend trail.dtend
summary trail.summary
description trail.description
}
}
File.open(options[:out], 'w') {|f|
cal.to_ical_file(f)
}