~hazmat/launchpad-work-items-tracker/cdo-austin

57 by Martin Pitt
burndown-chart: directly read from DB, simplify
1
#!/usr/bin/python
2
#
3
# Create a burndown chart from a work item database.
282 by Martin Pitt
add license file and copyright headers
4
#
5
# Copyright (C) 2010, 2011 Canonical Ltd.
6
# License: GPL-3
57 by Martin Pitt
burndown-chart: directly read from DB, simplify
7
144 by Colin Watson
fix pyflakes unhappiness (trailing whitespace, unused imports)
8
import optparse, datetime, sys
57 by Martin Pitt
burndown-chart: directly read from DB, simplify
9
import report_tools
10
1 by Martin Pitt
initial commit
11
from pychart import *
12
13
def date_to_ordinal(s):
57 by Martin Pitt
burndown-chart: directly read from DB, simplify
14
    '''Turn yyyy-mm-dd strings to ordinals'''
240.1.27 by James Westby
Report on how many workitems have to be fixed.
15
    return report_tools.date_to_python(s).toordinal()
57 by Martin Pitt
burndown-chart: directly read from DB, simplify
16
1 by Martin Pitt
initial commit
17
57 by Martin Pitt
burndown-chart: directly read from DB, simplify
18
def ordinal_to_date(ordinal):
19
    '''Turn an ordinal date into a string'''
20
    d = datetime.date.fromordinal(int(ordinal))
21
    return d.strftime('%Y-%m-%d')
22
1 by Martin Pitt
initial commit
23
def format_date(ordinal):
24
    d = datetime.date.fromordinal(int(ordinal))
57 by Martin Pitt
burndown-chart: directly read from DB, simplify
25
    return '/a60{}' + d.strftime('%b %d, %y')
26
205.1.17 by Clint Byrum
- changing link for users to their wi tracker page on team pages
27
def do_chart(data, start_date, end_date, trend_start, title, filename, only_weekdays, inverted,noforeign):
57 by Martin Pitt
burndown-chart: directly read from DB, simplify
28
    #set up default values
72 by Martin Pitt
use svg to avoid ghostscript, looks better too
29
    format = 'svg'
57 by Martin Pitt
burndown-chart: directly read from DB, simplify
30
    height = 450
31
    width = 1000
32
    legend_x = 700
33
    legend_y = 200
34
    title_x = 300
35
    title_y = 350
36
205.2.7 by Thierry Carrez
base lines on the day before, since current day is work in progress
37
    if inverted:
38
        legend_x=200
39
57 by Martin Pitt
burndown-chart: directly read from DB, simplify
40
    # Tell pychart to use colors
41
    theme.use_color = True
42
    theme.default_font_size = 12
43
    theme.reinitialize()
44
144 by Colin Watson
fix pyflakes unhappiness (trailing whitespace, unused imports)
45
    # turn into pychart data model and calculate maximum number of WIs
209 by Martin Pitt
burndown-chart: start at 1 to avoid zero division
46
    max_items = 1 # start at 1 to avoid zero div
205.2.9 by Thierry Carrez
Initialize lastactive
47
    lastactive = 0
57 by Martin Pitt
burndown-chart: directly read from DB, simplify
48
    pcdata = []
49
50
    for date in xrange(date_to_ordinal(start_date), date_to_ordinal(end_date)+1):
205.2.2 by Thierry Carrez
Code cleanup
51
        if (not only_weekdays or datetime.date.fromordinal(date).weekday() < 5):
219 by Thierry Carrez
Fix error in --only-weekdays when milestone ends on a Sunday
52
            end_date = ordinal_to_date(date)
205.2.1 by Thierry Carrez
Added inverted and only-weekdays options
53
            i = data.get(ordinal_to_date(date), {})
205.1.11 by Clint Byrum
merging with trunk
54
            count = i.get('done', 0) + i.get('todo', 0) + i.get('blocked', 0) + i.get('inprogress', 0) + i.get('postponed', 0)
205.2.1 by Thierry Carrez
Added inverted and only-weekdays options
55
            if max_items < count:
56
                max_items = count
205.1.17 by Clint Byrum
- changing link for users to their wi tracker page on team pages
57
            if noforeign:
58
                # This total is always higher
59
                pcdata.append((date, i.get('todo', 0),0,
60
                            i.get('blocked', 0),0,
61
                            i.get('inprogress', 0),0,
62
                            i.get('done',0),0,
63
                            i.get('postponed',0),0, count))
64
            else:
65
                pcdata.append((date, i.get('todo_teamonly', 0), i.get('todo', 0),
66
                    i.get('blocked_teamonly', 0), i.get('blocked', 0),
67
                    i.get('inprogress_teamonly', 0), i.get('inprogress', 0),
68
                    i.get('done_teamonly', 0), i.get('done', 0),
69
                    i.get('postponed_teamonly', 0), i.get('postponed', 0), count))
205.2.1 by Thierry Carrez
Added inverted and only-weekdays options
70
            if count > 0:
71
                lastactive = len(pcdata) - 1
57 by Martin Pitt
burndown-chart: directly read from DB, simplify
72
73
    # add some extra space to look nicer
74
    max_items = int(max_items * 1.05)
75
76
    x_interval = len(pcdata)/20
73 by Martin Pitt
burndown-chart: automatically calculate a sensible y interval
77
    if max_items > 500:
78
        y_interval = max_items/200*10
240.1.32 by James Westby
Force minimum y interval to 1.
79
    elif max_items < 20:
80
        y_interval = 1
73 by Martin Pitt
burndown-chart: automatically calculate a sensible y interval
81
    else:
82
        y_interval = max_items/20
57 by Martin Pitt
burndown-chart: directly read from DB, simplify
83
84
    # create the chart object
144 by Colin Watson
fix pyflakes unhappiness (trailing whitespace, unused imports)
85
    chart_object.set_defaults(area.T, size=(width, height),
57 by Martin Pitt
burndown-chart: directly read from DB, simplify
86
            y_range=(0, None), x_coord=category_coord.T(pcdata, 0))
87
88
    # tell the chart object it will use a bar chart, and will
89
    # use the data list for it's model
90
    chart_object.set_defaults(bar_plot.T, data=pcdata)
91
92
    # create the chart area
93
    # tell it to start at coords 0,0
94
    # tell it the labels, and the tics, etc..
205.1.8 by Clint Byrum
only show user direct assigned items on personal page
95
    # HACK: to prevent 0 div
96
    if max_items == 0:
97
        max_items = 1
57 by Martin Pitt
burndown-chart: directly read from DB, simplify
98
    ar = area.T(legend=legend.T(loc=(legend_x,legend_y)), loc=(0,0),
99
            x_axis=axis.X(label='Date', tic_interval=x_interval,format=format_date),
100
            y_axis=axis.Y(label='Work Items', tic_interval=y_interval),
101
            y_range=(0, max_items))
102
103
    #initialize the blar_plot fill styles
104
    bar_plot.fill_styles.reset()
105
106
    # create each set of data to plot
107
    # note that index zero is the label col
108
    # for each column of data, tell it what to use for the legend and
109
    # what color to make the bar, no lines, and
110
    # what plot to stack on
205.1.17 by Clint Byrum
- changing link for users to their wi tracker page on team pages
111
112
    # Suppressed when running w/o foreign numbers
113
    if noforeign:
114
        tlabel = ''
115
    else:
116
        tlabel = ' (team)'
117
205.2.2 by Thierry Carrez
Code cleanup
118
    if inverted:
227.1.1 by Clint Byrum
fixing inverted chart missing foreign done items (good eyes ttx)
119
        plot1 = bar_plot.T(label='done' + tlabel, hcol=7)
240.1.26 by James Westby
Some style updates to the burndowns and overview page.
120
        plot1.fill_style = fill_style.Plain(bgcolor=color.seagreen)
227.1.1 by Clint Byrum
fixing inverted chart missing foreign done items (good eyes ttx)
121
        plot2 = bar_plot.T(label='done (foreign)', hcol=8)
240.1.26 by James Westby
Some style updates to the burndowns and overview page.
122
        plot2.fill_style = fill_style.Plain(bgcolor=color.limegreen)
205.2.2 by Thierry Carrez
Code cleanup
123
205.1.17 by Clint Byrum
- changing link for users to their wi tracker page on team pages
124
        plot3 = bar_plot.T(label='inprogress' + tlabel, hcol=5, stack_on = plot2)
240.1.26 by James Westby
Some style updates to the burndowns and overview page.
125
        plot3.fill_style = fill_style.Plain(bgcolor=color.gray65)
205.1.11 by Clint Byrum
merging with trunk
126
        plot4 = bar_plot.T(label='inprogress (foreign)', hcol=6, stack_on = plot2)
240.1.26 by James Westby
Some style updates to the burndowns and overview page.
127
        plot4.fill_style = fill_style.Plain(bgcolor=color.gray74)
205.2.4 by Thierry Carrez
Merge latest HEAD, add newchart_teams trigger
128
205.1.17 by Clint Byrum
- changing link for users to their wi tracker page on team pages
129
        plot5 = bar_plot.T(label='blocked' + tlabel, hcol=3, stack_on = plot4)
240.1.26 by James Westby
Some style updates to the burndowns and overview page.
130
        plot5.fill_style = fill_style.Plain(bgcolor=color.red1)
205.1.11 by Clint Byrum
merging with trunk
131
        plot6 = bar_plot.T(label='blocked (foreign)', hcol=4, stack_on = plot4)
240.1.26 by James Westby
Some style updates to the burndowns and overview page.
132
        plot6.fill_style = fill_style.Plain(bgcolor=color.red3)
205.1.11 by Clint Byrum
merging with trunk
133
205.1.17 by Clint Byrum
- changing link for users to their wi tracker page on team pages
134
        plot7 = bar_plot.T(label='todo' + tlabel, hcol=1, stack_on = plot6)
240.1.26 by James Westby
Some style updates to the burndowns and overview page.
135
        plot7.fill_style = fill_style.Plain(bgcolor=color.darkorange1)
205.1.11 by Clint Byrum
merging with trunk
136
        plot8 = bar_plot.T(label='todo (foreign)', hcol=2, stack_on = plot6)
240.1.26 by James Westby
Some style updates to the burndowns and overview page.
137
        plot8.fill_style = fill_style.Plain(bgcolor=color.orangered1)
205.2.2 by Thierry Carrez
Code cleanup
138
    else:
205.1.17 by Clint Byrum
- changing link for users to their wi tracker page on team pages
139
        plot1 = bar_plot.T(label='todo' + tlabel, hcol=1)
240.1.26 by James Westby
Some style updates to the burndowns and overview page.
140
        plot1.fill_style = fill_style.Plain(bgcolor=color.darkorange1)
205.2.2 by Thierry Carrez
Code cleanup
141
        plot2 = bar_plot.T(label='todo (foreign)', hcol=2)
240.1.26 by James Westby
Some style updates to the burndowns and overview page.
142
        plot2.fill_style = fill_style.Plain(bgcolor=color.orangered1)
205.2.2 by Thierry Carrez
Code cleanup
143
205.1.17 by Clint Byrum
- changing link for users to their wi tracker page on team pages
144
        plot3 = bar_plot.T(label='blocked' + tlabel, hcol=3, stack_on = plot2)
240.1.26 by James Westby
Some style updates to the burndowns and overview page.
145
        plot3.fill_style = fill_style.Plain(bgcolor=color.red1)
205.1.11 by Clint Byrum
merging with trunk
146
        plot4 = bar_plot.T(label='blocked (foreign)', hcol=4, stack_on = plot2)
240.1.26 by James Westby
Some style updates to the burndowns and overview page.
147
        plot4.fill_style = fill_style.Plain(bgcolor=color.red3)
205.1.11 by Clint Byrum
merging with trunk
148
205.1.17 by Clint Byrum
- changing link for users to their wi tracker page on team pages
149
        plot5 = bar_plot.T(label='inprogress' + tlabel, hcol=5, stack_on = plot4)
240.1.26 by James Westby
Some style updates to the burndowns and overview page.
150
        plot5.fill_style = fill_style.Plain(bgcolor=color.gray65)
205.1.11 by Clint Byrum
merging with trunk
151
        plot6 = bar_plot.T(label='inprogress (foreign)', hcol=6, stack_on = plot4)
240.1.26 by James Westby
Some style updates to the burndowns and overview page.
152
        plot6.fill_style = fill_style.Plain(bgcolor=color.gray74)
205.1.11 by Clint Byrum
merging with trunk
153
205.1.17 by Clint Byrum
- changing link for users to their wi tracker page on team pages
154
        plot7 = bar_plot.T(label='done' + tlabel, hcol=7, stack_on = plot6)
240.1.26 by James Westby
Some style updates to the burndowns and overview page.
155
        plot7.fill_style = fill_style.Plain(bgcolor=color.seagreen)
205.1.11 by Clint Byrum
merging with trunk
156
        plot8 = bar_plot.T(label='done (foreign)', hcol=8, stack_on = plot6)
240.1.26 by James Westby
Some style updates to the burndowns and overview page.
157
        plot8.fill_style = fill_style.Plain(bgcolor=color.limegreen)
205.2.4 by Thierry Carrez
Merge latest HEAD, add newchart_teams trigger
158
205.2.2 by Thierry Carrez
Code cleanup
159
57 by Martin Pitt
burndown-chart: directly read from DB, simplify
160
    plot1.line_style = None
161
    plot2.line_style = None
162
    plot3.line_style = None
92 by Martin Pitt
burndown-chart: show both team-only and foreign counts
163
    plot4.line_style = None
164
    plot5.line_style = None
165
    plot6.line_style = None
205.1.3 by Clint Byrum
adding inprogress status support
166
    plot7.line_style = None
167
    plot8.line_style = None
168
205.1.11 by Clint Byrum
merging with trunk
169
205.1.17 by Clint Byrum
- changing link for users to their wi tracker page on team pages
170
    plot9 = bar_plot.T(label='postponed' + tlabel, hcol=9, stack_on = plot8)
240.1.26 by James Westby
Some style updates to the burndowns and overview page.
171
    plot9.fill_style = fill_style.Plain(bgcolor=color.purple)
205.1.9 by Clint Byrum
- adding blocked status
172
    plot9.line_style = None
173
    plot10 = bar_plot.T(label="postponed (foreign)  ", hcol=10, stack_on = plot8)
240.1.26 by James Westby
Some style updates to the burndowns and overview page.
174
    plot10.fill_style = fill_style.Plain(bgcolor=color.mediumorchid)
205.1.9 by Clint Byrum
- adding blocked status
175
    plot10.line_style = None
176
177
    plot11 = bar_plot.T(label='total', hcol=9)
205.1.15 by Clint Byrum
Re-showing data points accidentally hidden in burndown chart
178
    plot11.fill_style = None
179
    plot11.line_style = line_style.gray30
57 by Martin Pitt
burndown-chart: directly read from DB, simplify
180
181
    # create the canvas with the specified filename and file format
182
    can = canvas.init(filename,format)
183
184
    # add the data to the area and  draw it
205.1.17 by Clint Byrum
- changing link for users to their wi tracker page on team pages
185
    if noforeign:
186
        plot3.stack_on = plot1
187
        plot5.stack_on = plot3
188
        plot7.stack_on = plot5
189
        plot9.stack_on = plot7
190
        ar.add_plot(plot1, plot3, plot5, plot7, plot9)
191
    else:
192
        ar.add_plot(plot2, plot1, plot4, plot3, plot6, plot5, plot8, plot7, plot10, plot9)
193
57 by Martin Pitt
burndown-chart: directly read from DB, simplify
194
    ar.draw()
195
196
    # create and arrow for the trend line
197
    trend_line = arrow.T(head_style=1)
198
    # remove heads so arrow becomes a line
199
    trend_line.head_len = 0
200
    trend_line.thickness = 0
201
    trend_line.line_style.width = 3
202
203
    # set up the trend line position and draw it
205.2.1 by Thierry Carrez
Added inverted and only-weekdays options
204
    if inverted:
205.2.7 by Thierry Carrez
base lines on the day before, since current day is work in progress
205
        if lastactive > 1:
205.1.18 by Clint Byrum
- fixing burnup chart trend line
206
            trend_line.draw([(0, 0), (ar.x_pos(pcdata[lastactive-1][0]),ar.y_pos(pcdata[lastactive-1][8]))])
205.2.7 by Thierry Carrez
base lines on the day before, since current day is work in progress
207
            trend_line.line_style = line_style.black_dash1
205.2.1 by Thierry Carrez
Added inverted and only-weekdays options
208
        trend_line.line_style.width = 3
227 by Clint Byrum
fixing inverted chart line missing inprogress
209
        trend_line.draw([(ar.x_pos(pcdata[lastactive-1][0]),ar.y_pos(pcdata[lastactive-1][8])), (ar.x_pos(date_to_ordinal(end_date)),ar.y_pos(pcdata[lastactive][2]+pcdata[lastactive][4]+pcdata[lastactive][6]+pcdata[lastactive][8]))])
205.2.1 by Thierry Carrez
Added inverted and only-weekdays options
210
    else:
205.2.2 by Thierry Carrez
Code cleanup
211
        if not trend_start:
205.1.17 by Clint Byrum
- changing link for users to their wi tracker page on team pages
212
            if noforeign:
243 by Martin Pitt
burndown-chart: fix trend line start to consider "in progress" and "blocked" items
213
                trend_start = pcdata[0][1] + pcdata[0][3] + pcdata[0][5]
205.1.17 by Clint Byrum
- changing link for users to their wi tracker page on team pages
214
            else:
243 by Martin Pitt
burndown-chart: fix trend line start to consider "in progress" and "blocked" items
215
                trend_start = pcdata[0][2] + pcdata[0][4] + pcdata[0][6]
205.2.1 by Thierry Carrez
Added inverted and only-weekdays options
216
        trend_line.draw([(0, ar.y_pos(trend_start)), (ar.x_pos(date_to_ordinal(end_date)), 0)])
217
57 by Martin Pitt
burndown-chart: directly read from DB, simplify
218
    # title
219
    tb = text_box.T(loc=(title_x, title_y), text=title, line_style=None)
72 by Martin Pitt
use svg to avoid ghostscript, looks better too
220
    tb.fill_style = None
57 by Martin Pitt
burndown-chart: directly read from DB, simplify
221
    tb.draw()
222
223
#
224
# main
225
#
226
227
# argv parsing
228
optparser = optparse.OptionParser()
229
optparser.add_option('-d', '--database',
230
    help='Path to database', dest='database', metavar='PATH')
231
optparser.add_option('-t', '--team',
232
        help='Restrict report to a particular team', dest='team')
233
optparser.add_option('-m', '--milestone',
234
        help='Restrict report to a particular milestone', dest='milestone')
235
optparser.add_option('-o', '--output',
236
        help='Output file', dest='output')
237
optparser.add_option('--trend-start', type='int',
238
        help='Explicitly set start of trend line', dest='trendstart')
205.1.8 by Clint Byrum
only show user direct assigned items on personal page
239
optparser.add_option('-u', '--user', 
240
        help='Run for this user', dest='user')
205.2.1 by Thierry Carrez
Added inverted and only-weekdays options
241
optparser.add_option('--only-weekdays', action='store_true',
242
        help='Skip Saturdays and Sundays in the resulting graph', dest='only_weekdays')
243
optparser.add_option('--inverted', action='store_true',
244
        help='Generate an inverted burndown chart', dest='inverted')
210 by Jamie Bennett
Add support for specifying a start and end date for creating burndown charts
245
optparser.add_option('-s', '--start-date', 
246
        help='Explicitly set the start date of the burndown data', dest='start_date')
247
optparser.add_option('-e', '--end-date', 
248
        help='Explicitly set the end date of the burndown data', dest='end_date')
205.1.17 by Clint Byrum
- changing link for users to their wi tracker page on team pages
249
optparser.add_option('--no-foreign', action='store_true', default=False,
250
        help='Do not show foreign totals separate', dest='noforeign')
249.2.34 by James Westby
Add TR burndowns.
251
optparser.add_option('--group',
252
        help='Run for this group', dest='group')
240.11.2 by James Westby
Add a set of pages for date-based milestone views.
253
optparser.add_option('--date',
254
        help='Run for this date', dest='date')
57 by Martin Pitt
burndown-chart: directly read from DB, simplify
255
256
(opts, args) = optparser.parse_args()
257
if not opts.database:
258
    optparser.error('No database given')
259
if not opts.output:
260
    optparser.error('No output file given')
261
205.1.8 by Clint Byrum
only show user direct assigned items on personal page
262
if opts.user and  opts.team:
263
    optparser.error('team and user options are mutually exclusive')
249.2.34 by James Westby
Add TR burndowns.
264
if opts.user and opts.group:
265
    optparser.error('user and group options are mutually exclusive')
266
if opts.team and opts.group:
267
    optparser.error('team and group options are mutually exclusive')
240.11.2 by James Westby
Add a set of pages for date-based milestone views.
268
if opts.milestone and opts.date:
269
    optparser.error('milestone and date options are mutually exclusive')
205.1.8 by Clint Byrum
only show user direct assigned items on personal page
270
271
# The typing allows polymorphic behavior
272
if opts.user:
273
    opts.team = report_tools.user_string(opts.user)
274
elif opts.team:
275
    opts.team = report_tools.team_string(opts.team)
276
282.1.1 by Mattias Backman
Change all SQL queries to go through the Storm API instead of SQLite directly.
277
store = report_tools.get_store(opts.database)
240.11.4 by James Westby
Rework to use polymorpism for milestone due dates.
278
240.11.6 by James Westby
Comments from review. Thanks Michael.
279
milestone_collection = None
240.11.4 by James Westby
Rework to use polymorpism for milestone due dates.
280
if opts.milestone:
282.1.1 by Mattias Backman
Change all SQL queries to go through the Storm API instead of SQLite directly.
281
    milestone_collection = report_tools.get_milestone(store, opts.milestone)
240.11.4 by James Westby
Rework to use polymorpism for milestone due dates.
282
elif opts.date:
240.11.7 by James Westby
Ensure to create MilesstoneGroups with python dates.
283
    milestone_collection = report_tools.MilestoneGroup(
284
        report_tools.date_to_python(opts.date))
240.11.4 by James Westby
Rework to use polymorpism for milestone due dates.
285
286
57 by Martin Pitt
burndown-chart: directly read from DB, simplify
287
# get date -> state -> count mapping
282.1.1 by Mattias Backman
Change all SQL queries to go through the Storm API instead of SQLite directly.
288
data = report_tools.workitems_over_time(store, team=opts.team, group=opts.group, milestone_collection=milestone_collection)
57 by Martin Pitt
burndown-chart: directly read from DB, simplify
289
61 by Martin Pitt
burndown-chart: cleanly handle 0 work items
290
if len(data) == 0:
240.11.4 by James Westby
Rework to use polymorpism for milestone due dates.
291
    print 'WARNING: no work items, not generating chart (team: %s, group: %s, due date: %s)' % (
240.11.6 by James Westby
Comments from review. Thanks Michael.
292
        opts.team or 'all', opts.group or 'none', milestone_collection and milestone_collection.display_name or 'none')
61 by Martin Pitt
burndown-chart: cleanly handle 0 work items
293
    sys.exit(0)
294
210 by Jamie Bennett
Add support for specifying a start and end date for creating burndown charts
295
# calculate start/end date if no dates are given
296
if opts.start_date is None:
297
    start_date = sorted(data.keys())[0]
298
else:
299
    start_date=opts.start_date
300
301
if opts.end_date is None:
240.11.6 by James Westby
Comments from review. Thanks Michael.
302
    if milestone_collection is not None:
240.11.8 by James Westby
Use the string version of the due_date.
303
        end_date = milestone_collection.due_date_str
240.11.2 by James Westby
Add a set of pages for date-based milestone views.
304
    else:
282.1.1 by Mattias Backman
Change all SQL queries to go through the Storm API instead of SQLite directly.
305
        end_date=report_tools.milestone_due_date(store)
210 by Jamie Bennett
Add support for specifying a start and end date for creating burndown charts
306
else:
307
    end_date=opts.end_date
57 by Martin Pitt
burndown-chart: directly read from DB, simplify
308
203 by Martin Pitt
burndown-chart: fix crash on empty date ranges
309
if not start_date or not end_date or date_to_ordinal(start_date) > date_to_ordinal(end_date):
240.11.4 by James Westby
Rework to use polymorpism for milestone due dates.
310
    print 'WARNING: empty date range, not generating chart (team: %s, group: %s, due date: %s)' % (
240.1.92 by James Westby
Fix mis-merge.
311
        opts.team or 'all', opts.group or 'none', milestone_collection and milestone_collection.display_name or 'none')
74 by Martin Pitt
burndown-chart: Fix crash on empty date range
312
    sys.exit(0)
313
57 by Martin Pitt
burndown-chart: directly read from DB, simplify
314
# title
315
if opts.team:
316
    title = '/20' + opts.team
205.1.17 by Clint Byrum
- changing link for users to their wi tracker page on team pages
317
    noforeign = opts.noforeign
249.2.34 by James Westby
Add TR burndowns.
318
elif opts.group:
319
    title = "/20" + opts.group
320
    noforeign = True
57 by Martin Pitt
burndown-chart: directly read from DB, simplify
321
else:
322
    title = '/20all teams'
205.1.17 by Clint Byrum
- changing link for users to their wi tracker page on team pages
323
    # It never makese sense in all teams mode
324
    noforeign = True
325
240.11.6 by James Westby
Comments from review. Thanks Michael.
326
if milestone_collection is not None:
327
    title += ' (%s)' % milestone_collection.name
57 by Martin Pitt
burndown-chart: directly read from DB, simplify
328
205.1.17 by Clint Byrum
- changing link for users to their wi tracker page on team pages
329
do_chart(data, start_date, end_date, opts.trendstart, title, opts.output, opts.only_weekdays, opts.inverted, noforeign)