~bzr-pqm/bzr/bzr.dev

« back to all changes in this revision

Viewing changes to bzrlib/progress.py

  • Committer: John Arbash Meinel
  • Date: 2008-08-25 21:50:11 UTC
  • mfrom: (0.11.3 tools)
  • mto: This revision was merged to the branch mainline in revision 3659.
  • Revision ID: john@arbash-meinel.com-20080825215011-de9esmzgkue3e522
Merge in Lukáš's helper scripts.
Update the packaging documents to describe how to do the releases
using bzr-builddeb to package all distro platforms
simultaneously.

Show diffs side-by-side

added added

removed removed

Lines of Context:
16
16
# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
17
17
 
18
18
 
19
 
"""Simple text-mode progress indicator.
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.
 
19
"""Progress indicators.
 
20
 
 
21
The usual way to use this is via bzrlib.ui.ui_factory.nested_progress_bar which
 
22
will maintain a ProgressBarStack for you.
 
23
 
 
24
For direct use, the factory ProgressBar will return an auto-detected progress
 
25
bar that should match your terminal type. You can manually create a
 
26
ProgressBarStack too if you need multiple levels of cooperating progress bars.
 
27
Note that bzrlib's internal functions use the ui module, so if you are using
 
28
bzrlib it really is best to use bzrlib.ui.ui_factory.
27
29
"""
28
30
 
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
 
 
33
 
# TODO: If not on a tty perhaps just print '......' for the benefit of IDEs, etc
34
 
 
35
31
# TODO: Optionally show elapsed time instead/as well as ETA; nicer
36
32
# when the rate is unpredictable
37
33
 
193
189
    def finished(self):
194
190
        """Return this bar to its progress stack."""
195
191
        self.clear()
196
 
        assert self._stack is not None
197
192
        self._stack.return_pb(self)
198
193
 
199
194
    def note(self, fmt_string, *args, **kwargs):
298
293
        self.child_fraction = 0
299
294
        self._have_output = False
300
295
    
301
 
 
302
296
    def throttle(self, old_msg):
303
297
        """Return True if the bar was updated too recently"""
304
298
        # time.time consistently takes 40/4000 ms = 0.01 ms.
320
314
        return False
321
315
        
322
316
    def tick(self):
323
 
        self.update(self.last_msg, self.last_cnt, self.last_total, 
 
317
        self.update(self.last_msg, self.last_cnt, self.last_total,
324
318
                    self.child_fraction)
325
319
 
326
320
    def child_update(self, message, current, total):
330
324
                pass
331
325
            elif self.last_cnt + child_fraction <= self.last_total:
332
326
                self.child_fraction = child_fraction
333
 
            else:
334
 
                mutter('not updating child fraction')
335
327
        if self.last_msg is None:
336
328
            self.last_msg = ''
337
329
        self.tick()
338
330
 
339
 
    def update(self, msg, current_cnt=None, total_cnt=None, 
 
331
    def update(self, msg, current_cnt=None, total_cnt=None,
340
332
               child_fraction=0):
341
333
        """Update and redraw progress bar."""
342
334
        if msg is None:
438
430
        self._have_output = True
439
431
        #self.to_file.flush()
440
432
            
441
 
    def clear(self):        
 
433
    def clear(self):
442
434
        if self._have_output:
443
435
            self.to_file.write('\r%s\r' % (' ' * (self.width - 1)))
444
436
        self._have_output = False
461
453
 
462
454
    def update(self, msg, current_cnt=None, total_cnt=None):
463
455
        self.current = current_cnt
464
 
        self.total = total_cnt
 
456
        if total_cnt is not None:
 
457
            self.total = total_cnt
465
458
        self.message = msg
466
459
        self.child_fraction = 0
467
460
        self.tick()
490
483
    def note(self, *args, **kwargs):
491
484
        self.parent.note(*args, **kwargs)
492
485
 
493
 
 
 
486
 
 
487
class InstrumentedProgress(TTYProgressBar):
 
488
    """TTYProgress variant that tracks outcomes"""
 
489
 
 
490
    def __init__(self, *args, **kwargs):
 
491
        self.always_throttled = True
 
492
        self.never_throttle = False
 
493
        TTYProgressBar.__init__(self, *args, **kwargs)
 
494
 
 
495
    def throttle(self, old_message):
 
496
        if self.never_throttle:
 
497
            result =  False
 
498
        else:
 
499
            result = TTYProgressBar.throttle(self, old_message)
 
500
        if result is False:
 
501
            self.always_throttled = False
 
502
 
 
503
 
494
504
def str_tdelta(delt):
495
505
    if delt is None:
496
506
        return "-:--:--"
520
530
    
521
531
    total_duration = float(elapsed) * float(total) / float(current)
522
532
 
523
 
    assert total_duration >= elapsed
524
 
 
525
533
    if last_updates and len(last_updates) >= n_recent:
526
534
        avg = sum(last_updates) / float(len(last_updates))
527
535
        time_left = avg * (total - current)
548
556
            self.cur_phase = 0
549
557
        else:
550
558
            self.cur_phase += 1
551
 
        assert self.cur_phase < self.total 
552
559
        self.pb.update(self.message, self.cur_phase, self.total)
553
 
 
554
 
 
555
 
def run_tests():
556
 
    import doctest
557
 
    result = doctest.testmod()
558
 
    if result[1] > 0:
559
 
        if result[0] == 0:
560
 
            print "All tests passed"
561
 
    else:
562
 
        print "No tests to run"
563
 
 
564
 
 
565
 
def demo():
566
 
    sleep = time.sleep
567
 
    
568
 
    print 'dumb-terminal test:'
569
 
    pb = DotsProgressBar()
570
 
    for i in range(100):
571
 
        pb.update('Leoparden', i, 99)
572
 
        sleep(0.1)
573
 
    sleep(1.5)
574
 
    pb.clear()
575
 
    sleep(1.5)
576
 
    
577
 
    print 'smart-terminal test:'
578
 
    pb = ProgressBar(show_pct=True, show_bar=True, show_spinner=False)
579
 
    for i in range(100):
580
 
        pb.update('Elephanten', i, 99)
581
 
        sleep(0.1)
582
 
    sleep(2)
583
 
    pb.clear()
584
 
    sleep(1)
585
 
 
586
 
    print 'done!'
587
 
 
588
 
if __name__ == "__main__":
589
 
    demo()