/brz/remove-bazaar

To get this branch, use:
bzr branch http://gegoxaren.bato24.eu/bzr/brz/remove-bazaar
649 by Martin Pool
- some cleanups for the progressbar method
1
# Copyright (C) 2005 Aaron Bentley <aaron.bentley@utoronto.ca>
1594.1.1 by Robert Collins
Introduce new bzr progress bar api. ui_factory.nested_progress_bar.
2
# Copyright (C) 2005, 2006 Canonical <canonical.com>
648 by Martin Pool
- import aaron's progress-indicator code
3
#
4
#    This program is free software; you can redistribute it and/or modify
5
#    it under the terms of the GNU General Public License as published by
6
#    the Free Software Foundation; either version 2 of the License, or
7
#    (at your option) any later version.
8
#
9
#    This program is distributed in the hope that it will be useful,
10
#    but WITHOUT ANY WARRANTY; without even the implied warranty of
11
#    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12
#    GNU General Public License for more details.
13
#
14
#    You should have received a copy of the GNU General Public License
15
#    along with this program; if not, write to the Free Software
16
#    Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
17
649 by Martin Pool
- some cleanups for the progressbar method
18
889 by Martin Pool
- show progress bar during inventory conversion to weave, and make profiling optional
19
"""Simple text-mode progress indicator.
649 by Martin Pool
- some cleanups for the progressbar method
20
21
To display an indicator, create a ProgressBar object.  Call it,
22
passing Progress objects indicating the current state.  When done,
23
call clear().
24
25
Progress is suppressed when output is not sent to a terminal, so as
26
not to clutter log files.
27
"""
28
652 by Martin Pool
doc
29
# TODO: should be a global option e.g. --silent that disables progress
30
# indicators, preferably without needing to adjust all code that
31
# potentially calls them.
32
962 by Martin Pool
todo
33
# TODO: If not on a tty perhaps just print '......' for the benefit of IDEs, etc
655 by Martin Pool
- better calculation of progress bar position
34
934 by Martin Pool
todo
35
# TODO: Optionally show elapsed time instead/as well as ETA; nicer
36
# when the rate is unpredictable
37
649 by Martin Pool
- some cleanups for the progressbar method
38
648 by Martin Pool
- import aaron's progress-indicator code
39
import sys
660 by Martin Pool
- use plain unix time, not datetime module
40
import time
964 by Martin Pool
- show progress on dumb terminals by printing dots
41
import os
1185.16.75 by Martin Pool
- improved eta estimation for progress bar
42
from collections import deque
648 by Martin Pool
- import aaron's progress-indicator code
43
649 by Martin Pool
- some cleanups for the progressbar method
44
1594.1.1 by Robert Collins
Introduce new bzr progress bar api. ui_factory.nested_progress_bar.
45
import bzrlib.errors as errors
1551.2.27 by Aaron Bentley
Got propogation under test
46
from bzrlib.trace import mutter 
1594.1.1 by Robert Collins
Introduce new bzr progress bar api. ui_factory.nested_progress_bar.
47
48
649 by Martin Pool
- some cleanups for the progressbar method
49
def _supports_progress(f):
695 by Martin Pool
- don't display progress bars on really dumb terminals
50
    if not hasattr(f, 'isatty'):
51
        return False
52
    if not f.isatty():
53
        return False
54
    if os.environ.get('TERM') == 'dumb':
55
        # e.g. emacs compile window
56
        return False
57
    return True
649 by Martin Pool
- some cleanups for the progressbar method
58
59
60
964 by Martin Pool
- show progress on dumb terminals by printing dots
61
def ProgressBar(to_file=sys.stderr, **kwargs):
62
    """Abstract factory"""
63
    if _supports_progress(to_file):
64
        return TTYProgressBar(to_file=to_file, **kwargs)
65
    else:
66
        return DotsProgressBar(to_file=to_file, **kwargs)
67
    
1594.1.1 by Robert Collins
Introduce new bzr progress bar api. ui_factory.nested_progress_bar.
68
 
69
class ProgressBarStack(object):
70
    """A stack of progress bars."""
71
72
    def __init__(self,
73
                 to_file=sys.stderr,
74
                 show_pct=False,
1551.2.33 by Aaron Bentley
Hide ETA, show spinner by default
75
                 show_spinner=True,
76
                 show_eta=False,
1594.1.1 by Robert Collins
Introduce new bzr progress bar api. ui_factory.nested_progress_bar.
77
                 show_bar=True,
78
                 show_count=True,
1594.1.3 by Robert Collins
Fixup pb usage to use nested_progress_bar.
79
                 to_messages_file=sys.stdout,
80
                 klass=None):
1594.1.1 by Robert Collins
Introduce new bzr progress bar api. ui_factory.nested_progress_bar.
81
        """Setup the stack with the parameters the progress bars should have."""
82
        self._to_file = to_file
83
        self._show_pct = show_pct
84
        self._show_spinner = show_spinner
85
        self._show_eta = show_eta
86
        self._show_bar = show_bar
87
        self._show_count = show_count
88
        self._to_messages_file = to_messages_file
89
        self._stack = []
1594.1.3 by Robert Collins
Fixup pb usage to use nested_progress_bar.
90
        self._klass = klass or TTYProgressBar
1594.1.1 by Robert Collins
Introduce new bzr progress bar api. ui_factory.nested_progress_bar.
91
1551.2.29 by Aaron Bentley
Got stack handling under test
92
    def top(self):
93
        if len(self._stack) != 0:
94
            return self._stack[-1]
95
        else:
96
            return None
97
1594.1.1 by Robert Collins
Introduce new bzr progress bar api. ui_factory.nested_progress_bar.
98
    def get_nested(self):
99
        """Return a nested progress bar."""
1551.2.29 by Aaron Bentley
Got stack handling under test
100
        if len(self._stack) == 0:
101
            func = self._klass
102
        else:
103
            func = self.top().child_progress
104
        new_bar = func(to_file=self._to_file,
105
                       show_pct=self._show_pct,
106
                       show_spinner=self._show_spinner,
107
                       show_eta=self._show_eta,
108
                       show_bar=self._show_bar,
109
                       show_count=self._show_count,
110
                       to_messages_file=self._to_messages_file,
111
                       _stack=self)
1594.1.1 by Robert Collins
Introduce new bzr progress bar api. ui_factory.nested_progress_bar.
112
        self._stack.append(new_bar)
113
        return new_bar
114
115
    def return_pb(self, bar):
116
        """Return bar after its been used."""
1594.1.4 by Robert Collins
Fix identity test in ProgressBarStack.return_pb
117
        if bar is not self._stack[-1]:
1594.1.1 by Robert Collins
Introduce new bzr progress bar api. ui_factory.nested_progress_bar.
118
            raise errors.MissingProgressBarFinish()
119
        self._stack.pop()
120
121
 
964 by Martin Pool
- show progress on dumb terminals by printing dots
122
class _BaseProgressBar(object):
1594.1.1 by Robert Collins
Introduce new bzr progress bar api. ui_factory.nested_progress_bar.
123
964 by Martin Pool
- show progress on dumb terminals by printing dots
124
    def __init__(self,
125
                 to_file=sys.stderr,
126
                 show_pct=False,
127
                 show_spinner=False,
128
                 show_eta=True,
129
                 show_bar=True,
1534.5.6 by Robert Collins
split out converter logic into per-format objects.
130
                 show_count=True,
1594.1.1 by Robert Collins
Introduce new bzr progress bar api. ui_factory.nested_progress_bar.
131
                 to_messages_file=sys.stdout,
132
                 _stack=None):
964 by Martin Pool
- show progress on dumb terminals by printing dots
133
        object.__init__(self)
134
        self.to_file = to_file
1534.5.6 by Robert Collins
split out converter logic into per-format objects.
135
        self.to_messages_file = to_messages_file
964 by Martin Pool
- show progress on dumb terminals by printing dots
136
        self.last_msg = None
137
        self.last_cnt = None
138
        self.last_total = None
139
        self.show_pct = show_pct
140
        self.show_spinner = show_spinner
141
        self.show_eta = show_eta
142
        self.show_bar = show_bar
143
        self.show_count = show_count
1594.1.1 by Robert Collins
Introduce new bzr progress bar api. ui_factory.nested_progress_bar.
144
        self._stack = _stack
145
146
    def finished(self):
147
        """Return this bar to its progress stack."""
148
        self.clear()
1594.1.3 by Robert Collins
Fixup pb usage to use nested_progress_bar.
149
        assert self._stack is not None
1594.1.1 by Robert Collins
Introduce new bzr progress bar api. ui_factory.nested_progress_bar.
150
        self._stack.return_pb(self)
1104 by Martin Pool
- Add a simple UIFactory
151
1534.5.6 by Robert Collins
split out converter logic into per-format objects.
152
    def note(self, fmt_string, *args, **kwargs):
153
        """Record a note without disrupting the progress bar."""
154
        self.clear()
155
        self.to_messages_file.write(fmt_string % args)
156
        self.to_messages_file.write('\n')
1104 by Martin Pool
- Add a simple UIFactory
157
1551.2.29 by Aaron Bentley
Got stack handling under test
158
    def child_progress(self, **kwargs):
159
        return ChildProgress(**kwargs)
160
1104 by Martin Pool
- Add a simple UIFactory
161
162
class DummyProgress(_BaseProgressBar):
163
    """Progress-bar standin that does nothing.
164
165
    This can be used as the default argument for methods that
166
    take an optional progress indicator."""
167
    def tick(self):
168
        pass
169
170
    def update(self, msg=None, current=None, total=None):
171
        pass
172
1551.2.27 by Aaron Bentley
Got propogation under test
173
    def child_update(self, message, current, total):
174
        pass
175
1104 by Martin Pool
- Add a simple UIFactory
176
    def clear(self):
177
        pass
964 by Martin Pool
- show progress on dumb terminals by printing dots
178
        
1534.5.6 by Robert Collins
split out converter logic into per-format objects.
179
    def note(self, fmt_string, *args, **kwargs):
180
        """See _BaseProgressBar.note()."""
1534.5.9 by Robert Collins
Advise users running upgrade on a checkout to also run it on the branch.
181
1551.2.29 by Aaron Bentley
Got stack handling under test
182
    def child_progress(self, **kwargs):
183
        return DummyProgress(**kwargs)
1534.5.9 by Robert Collins
Advise users running upgrade on a checkout to also run it on the branch.
184
964 by Martin Pool
- show progress on dumb terminals by printing dots
185
class DotsProgressBar(_BaseProgressBar):
1594.1.3 by Robert Collins
Fixup pb usage to use nested_progress_bar.
186
964 by Martin Pool
- show progress on dumb terminals by printing dots
187
    def __init__(self, **kwargs):
188
        _BaseProgressBar.__init__(self, **kwargs)
189
        self.last_msg = None
190
        self.need_nl = False
191
        
192
    def tick(self):
193
        self.update()
194
        
195
    def update(self, msg=None, current_cnt=None, total_cnt=None):
196
        if msg and msg != self.last_msg:
197
            if self.need_nl:
198
                self.to_file.write('\n')
199
            
200
            self.to_file.write(msg + ': ')
201
            self.last_msg = msg
202
        self.need_nl = True
203
        self.to_file.write('.')
204
        
205
    def clear(self):
206
        if self.need_nl:
207
            self.to_file.write('\n')
208
        
1551.2.28 by Aaron Bentley
Ensure all ProgressBar implementations can be used as parents
209
    def child_update(self, message, current, total):
210
        self.tick()
964 by Martin Pool
- show progress on dumb terminals by printing dots
211
    
212
class TTYProgressBar(_BaseProgressBar):
658 by Martin Pool
- clean up and add a bunch of options to the progress indicator
213
    """Progress bar display object.
214
215
    Several options are available to control the display.  These can
216
    be passed as parameters to the constructor or assigned at any time:
217
218
    show_pct
219
        Show percentage complete.
220
    show_spinner
221
        Show rotating baton.  This ticks over on every update even
222
        if the values don't change.
223
    show_eta
224
        Show predicted time-to-completion.
225
    show_bar
226
        Show bar graph.
227
    show_count
228
        Show numerical counts.
229
230
    The output file should be in line-buffered or unbuffered mode.
231
    """
232
    SPIN_CHARS = r'/-\|'
661 by Martin Pool
- limit rate at which progress bar is updated
233
    MIN_PAUSE = 0.1 # seconds
234
964 by Martin Pool
- show progress on dumb terminals by printing dots
235
236
    def __init__(self, **kwargs):
1185.33.60 by Martin Pool
Use full terminal width for verbose test output.
237
        from bzrlib.osutils import terminal_width
964 by Martin Pool
- show progress on dumb terminals by printing dots
238
        _BaseProgressBar.__init__(self, **kwargs)
658 by Martin Pool
- clean up and add a bunch of options to the progress indicator
239
        self.spin_pos = 0
1185.33.60 by Martin Pool
Use full terminal width for verbose test output.
240
        self.width = terminal_width()
964 by Martin Pool
- show progress on dumb terminals by printing dots
241
        self.start_time = None
242
        self.last_update = None
1185.16.75 by Martin Pool
- improved eta estimation for progress bar
243
        self.last_updates = deque()
1551.2.28 by Aaron Bentley
Ensure all ProgressBar implementations can be used as parents
244
        self.child_fraction = 0
964 by Martin Pool
- show progress on dumb terminals by printing dots
245
    
246
247
    def throttle(self):
248
        """Return True if the bar was updated too recently"""
249
        now = time.time()
250
        if self.start_time is None:
251
            self.start_time = self.last_update = now
252
            return False
253
        else:
254
            interval = now - self.last_update
255
            if interval > 0 and interval < self.MIN_PAUSE:
256
                return True
257
1185.16.75 by Martin Pool
- improved eta estimation for progress bar
258
        self.last_updates.append(now - self.last_update)
964 by Martin Pool
- show progress on dumb terminals by printing dots
259
        self.last_update = now
260
        return False
929 by Martin Pool
- progress bar: avoid repeatedly checking screen width
261
        
658 by Martin Pool
- clean up and add a bunch of options to the progress indicator
262
263
    def tick(self):
1551.2.27 by Aaron Bentley
Got propogation under test
264
        self.update(self.last_msg, self.last_cnt, self.last_total, 
265
                    self.child_fraction)
266
1551.2.28 by Aaron Bentley
Ensure all ProgressBar implementations can be used as parents
267
    def child_update(self, message, current, total):
1551.2.35 by Aaron Bentley
Fix division-by-zero
268
        if current is not None and total != 0:
1551.2.30 by Aaron Bentley
Bugfixes to progress stuff
269
            child_fraction = float(current) / total
270
            if self.last_cnt is None:
271
                pass
272
            elif self.last_cnt + child_fraction <= self.last_total:
273
                self.child_fraction = child_fraction
274
            else:
275
                mutter('not updating child fraction')
276
        if self.last_msg is None:
277
            self.last_msg = ''
1551.2.28 by Aaron Bentley
Ensure all ProgressBar implementations can be used as parents
278
        self.tick()
279
280
1551.2.27 by Aaron Bentley
Got propogation under test
281
    def update(self, msg, current_cnt=None, total_cnt=None, 
282
               child_fraction=0):
658 by Martin Pool
- clean up and add a bunch of options to the progress indicator
283
        """Update and redraw progress bar."""
1551.2.27 by Aaron Bentley
Got propogation under test
284
        self.child_fraction = child_fraction
658 by Martin Pool
- clean up and add a bunch of options to the progress indicator
285
1308 by Martin Pool
- make progress bar more tolerant of out-of-range values
286
        if current_cnt < 0:
287
            current_cnt = 0
288
            
289
        if current_cnt > total_cnt:
290
            total_cnt = current_cnt
1570.1.9 by Robert Collins
Do not throttle updates to progress bars that change the message.
291
        
292
        old_msg = self.last_msg
658 by Martin Pool
- clean up and add a bunch of options to the progress indicator
293
        # save these for the tick() function
294
        self.last_msg = msg
295
        self.last_cnt = current_cnt
296
        self.last_total = total_cnt
297
            
1570.1.9 by Robert Collins
Do not throttle updates to progress bars that change the message.
298
        if old_msg == self.last_msg and self.throttle():
964 by Martin Pool
- show progress on dumb terminals by printing dots
299
            return 
661 by Martin Pool
- limit rate at which progress bar is updated
300
        
658 by Martin Pool
- clean up and add a bunch of options to the progress indicator
301
        if self.show_eta and self.start_time and total_cnt:
1551.2.30 by Aaron Bentley
Bugfixes to progress stuff
302
            eta = get_eta(self.start_time, current_cnt+child_fraction, 
303
                    total_cnt, last_updates = self.last_updates)
658 by Martin Pool
- clean up and add a bunch of options to the progress indicator
304
            eta_str = " " + str_tdelta(eta)
305
        else:
306
            eta_str = ""
307
308
        if self.show_spinner:
309
            spin_str = self.SPIN_CHARS[self.spin_pos % 4] + ' '            
310
        else:
311
            spin_str = ''
312
313
        # always update this; it's also used for the bar
314
        self.spin_pos += 1
315
316
        if self.show_pct and total_cnt and current_cnt:
1551.2.30 by Aaron Bentley
Bugfixes to progress stuff
317
            pct = 100.0 * ((current_cnt + child_fraction) / total_cnt)
658 by Martin Pool
- clean up and add a bunch of options to the progress indicator
318
            pct_str = ' (%5.1f%%)' % pct
319
        else:
320
            pct_str = ''
321
322
        if not self.show_count:
323
            count_str = ''
324
        elif current_cnt is None:
325
            count_str = ''
326
        elif total_cnt is None:
327
            count_str = ' %i' % (current_cnt)
328
        else:
329
            # make both fields the same size
330
            t = '%i' % (total_cnt)
331
            c = '%*i' % (len(t), current_cnt)
332
            count_str = ' ' + c + '/' + t 
333
334
        if self.show_bar:
335
            # progress bar, if present, soaks up all remaining space
929 by Martin Pool
- progress bar: avoid repeatedly checking screen width
336
            cols = self.width - 1 - len(msg) - len(spin_str) - len(pct_str) \
658 by Martin Pool
- clean up and add a bunch of options to the progress indicator
337
                   - len(eta_str) - len(count_str) - 3
338
339
            if total_cnt:
340
                # number of markers highlighted in bar
1551.2.30 by Aaron Bentley
Bugfixes to progress stuff
341
                markers = int(round(float(cols) * 
342
                              (current_cnt + child_fraction) / total_cnt))
658 by Martin Pool
- clean up and add a bunch of options to the progress indicator
343
                bar_str = '[' + ('=' * markers).ljust(cols) + '] '
669 by Martin Pool
- don't show progress bar unless completion is known
344
            elif False:
658 by Martin Pool
- clean up and add a bunch of options to the progress indicator
345
                # don't know total, so can't show completion.
346
                # so just show an expanded spinning thingy
347
                m = self.spin_pos % cols
668 by Martin Pool
- fix sweeping bar progress indicator
348
                ms = (' ' * m + '*').ljust(cols)
658 by Martin Pool
- clean up and add a bunch of options to the progress indicator
349
                
350
                bar_str = '[' + ms + '] '
669 by Martin Pool
- don't show progress bar unless completion is known
351
            else:
352
                bar_str = ''
658 by Martin Pool
- clean up and add a bunch of options to the progress indicator
353
        else:
354
            bar_str = ''
355
356
        m = spin_str + bar_str + msg + count_str + pct_str + eta_str
357
929 by Martin Pool
- progress bar: avoid repeatedly checking screen width
358
        assert len(m) < self.width
359
        self.to_file.write('\r' + m.ljust(self.width - 1))
658 by Martin Pool
- clean up and add a bunch of options to the progress indicator
360
        #self.to_file.flush()
361
            
964 by Martin Pool
- show progress on dumb terminals by printing dots
362
    def clear(self):        
929 by Martin Pool
- progress bar: avoid repeatedly checking screen width
363
        self.to_file.write('\r%s\r' % (' ' * (self.width - 1)))
658 by Martin Pool
- clean up and add a bunch of options to the progress indicator
364
        #self.to_file.flush()        
649 by Martin Pool
- some cleanups for the progressbar method
365
1551.2.27 by Aaron Bentley
Got propogation under test
366
1551.2.28 by Aaron Bentley
Ensure all ProgressBar implementations can be used as parents
367
class ChildProgress(_BaseProgressBar):
1551.2.27 by Aaron Bentley
Got propogation under test
368
    """A progress indicator that pushes its data to the parent"""
1551.2.29 by Aaron Bentley
Got stack handling under test
369
    def __init__(self, _stack, **kwargs):
370
        _BaseProgressBar.__init__(self, _stack=_stack, **kwargs)
371
        self.parent = _stack.top()
1551.2.27 by Aaron Bentley
Got propogation under test
372
        self.current = None
373
        self.total = None
374
        self.child_fraction = 0
375
        self.message = None
376
377
    def update(self, msg, current_cnt=None, total_cnt=None):
378
        self.current = current_cnt
379
        self.total = total_cnt
380
        self.message = msg
381
        self.child_fraction = 0
382
        self.tick()
383
384
    def child_update(self, message, current, total):
1551.2.35 by Aaron Bentley
Fix division-by-zero
385
        if current is None or total == 0:
1551.2.30 by Aaron Bentley
Bugfixes to progress stuff
386
            self.child_fraction = 0
387
        else:
388
            self.child_fraction = float(current) / total
1551.2.27 by Aaron Bentley
Got propogation under test
389
        self.tick()
390
391
    def tick(self):
1551.2.30 by Aaron Bentley
Bugfixes to progress stuff
392
        if self.current is None:
393
            count = None
394
        else:
395
            count = self.current+self.child_fraction
396
            if count > self.total:
397
                mutter('clamping count of %d to %d' % (count, self.total))
398
                count = self.total
1551.2.27 by Aaron Bentley
Got propogation under test
399
        self.parent.child_update(self.message, count, self.total)
400
1551.2.29 by Aaron Bentley
Got stack handling under test
401
    def clear(self):
1551.2.30 by Aaron Bentley
Bugfixes to progress stuff
402
        pass
1551.2.29 by Aaron Bentley
Got stack handling under test
403
1551.2.27 by Aaron Bentley
Got propogation under test
404
 
648 by Martin Pool
- import aaron's progress-indicator code
405
def str_tdelta(delt):
406
    if delt is None:
407
        return "-:--:--"
660 by Martin Pool
- use plain unix time, not datetime module
408
    delt = int(round(delt))
409
    return '%d:%02d:%02d' % (delt/3600,
410
                             (delt/60) % 60,
411
                             delt % 60)
412
413
1185.16.75 by Martin Pool
- improved eta estimation for progress bar
414
def get_eta(start_time, current, total, enough_samples=3, last_updates=None, n_recent=10):
660 by Martin Pool
- use plain unix time, not datetime module
415
    if start_time is None:
416
        return None
417
418
    if not total:
419
        return None
420
421
    if current < enough_samples:
422
        return None
423
424
    if current > total:
425
        return None                     # wtf?
426
427
    elapsed = time.time() - start_time
428
429
    if elapsed < 2.0:                   # not enough time to estimate
430
        return None
431
    
432
    total_duration = float(elapsed) * float(total) / float(current)
433
434
    assert total_duration >= elapsed
435
1185.16.75 by Martin Pool
- improved eta estimation for progress bar
436
    if last_updates and len(last_updates) >= n_recent:
437
        while len(last_updates) > n_recent:
438
            last_updates.popleft()
439
        avg = sum(last_updates) / float(len(last_updates))
440
        time_left = avg * (total - current)
441
442
        old_time_left = total_duration - elapsed
443
444
        # We could return the average, or some other value here
445
        return (time_left + old_time_left) / 2
446
660 by Martin Pool
- use plain unix time, not datetime module
447
    return total_duration - elapsed
648 by Martin Pool
- import aaron's progress-indicator code
448
649 by Martin Pool
- some cleanups for the progressbar method
449
1551.2.32 by Aaron Bentley
Handle progress phases more nicely in merge
450
class ProgressPhase(object):
451
    """Update progress object with the current phase"""
452
    def __init__(self, message, total, pb):
453
        object.__init__(self)
454
        self.pb = pb
455
        self.message = message
456
        self.total = total
457
        self.cur_phase = None
458
459
    def next_phase(self):
460
        if self.cur_phase is None:
461
            self.cur_phase = 0
462
        else:
463
            self.cur_phase += 1
464
        assert self.cur_phase < self.total 
465
        self.pb.update(self.message, self.cur_phase, self.total)
466
467
648 by Martin Pool
- import aaron's progress-indicator code
468
def run_tests():
469
    import doctest
470
    result = doctest.testmod()
471
    if result[1] > 0:
472
        if result[0] == 0:
473
            print "All tests passed"
474
    else:
475
        print "No tests to run"
649 by Martin Pool
- some cleanups for the progressbar method
476
477
478
def demo():
964 by Martin Pool
- show progress on dumb terminals by printing dots
479
    sleep = time.sleep
480
    
481
    print 'dumb-terminal test:'
482
    pb = DotsProgressBar()
483
    for i in range(100):
484
        pb.update('Leoparden', i, 99)
485
        sleep(0.1)
486
    sleep(1.5)
487
    pb.clear()
488
    sleep(1.5)
489
    
490
    print 'smart-terminal test:'
658 by Martin Pool
- clean up and add a bunch of options to the progress indicator
491
    pb = ProgressBar(show_pct=True, show_bar=True, show_spinner=False)
649 by Martin Pool
- some cleanups for the progressbar method
492
    for i in range(100):
658 by Martin Pool
- clean up and add a bunch of options to the progress indicator
493
        pb.update('Elephanten', i, 99)
494
        sleep(0.1)
495
    sleep(2)
496
    pb.clear()
497
    sleep(1)
964 by Martin Pool
- show progress on dumb terminals by printing dots
498
649 by Martin Pool
- some cleanups for the progressbar method
499
    print 'done!'
500
648 by Martin Pool
- import aaron's progress-indicator code
501
if __name__ == "__main__":
649 by Martin Pool
- some cleanups for the progressbar method
502
    demo()