Changeset 460:7394f2097327
- Timestamp:
- 08/04/08 13:06:58 (5 months ago)
- Files:
-
- ChangeLog (modified) (1 diff)
- foolscap/logging/filter.py (modified) (6 diffs)
- foolscap/test/test_logging.py (modified) (6 diffs)
Legend:
- Unmodified
- Added
- Removed
- Modified
- Copied
- Moved
ChangeLog
r459 r460 1 1 2008-08-04 Brian Warner <warner@lothar.com> 2 3 * foolscap/test/test_logging.py (Filter): test 'flogtool filter' 4 * foolscap/logging/filter.py: control stdout/stderr better 2 5 3 6 * foolscap/test/test_logging.py (Dumper): test 'flogtool dump' foolscap/logging/filter.py
r382 r460 1 1 2 2 from twisted.python import usage 3 import os, pickle, bz2, time3 import sys, os, pickle, bz2, time 4 4 from foolscap.logging import log 5 5 6 6 class FilterOptions(usage.Options): 7 stdout = sys.stdout 8 stderr = sys.stderr 7 9 synopsis = "Usage: flogtool filter [options] OLDFILE.pickle NEWFILE.pickle" 8 10 … … 23 25 self.newfile = newfile 24 26 if newfile is None: 25 print "modifying event file in place"26 27 self.newfile = oldfile 27 28 … … 51 52 52 53 def run(self, options): 54 stdout = options.stdout 53 55 newfilename = options.newfile 54 56 if options.newfile == options.oldfile: 57 print >>stdout, "modifying event file in place" 55 58 newfilename = newfilename + ".tmp" 56 59 if options.newfile.endswith(".bz2"): … … 60 63 after = options['after'] 61 64 if after is not None: 62 print " --after: removing events before %s" % time.ctime(after)65 print >>stdout, " --after: removing events before %s" % time.ctime(after) 63 66 before = options['before'] 64 67 if before is not None: 65 print " --before: removing events after %s" % time.ctime(before)68 print >>stdout, " --before: removing events after %s" % time.ctime(before) 66 69 above = options['above'] 67 70 if above: 68 print " --above: removing events below level %d" % above71 print >>stdout, " --above: removing events below level %d" % above 69 72 from_tubid = options['from'] 70 73 if from_tubid: 71 print " --from: retaining events only from tubid prefix %s" % from_tubid74 print >>stdout, " --from: retaining events only from tubid prefix %s" % from_tubid 72 75 strip_facility = options['strip-facility'] 73 76 if strip_facility is not None: 74 print "--strip-facility: removing events for %s and children" % strip_facility77 print >>stdout, "--strip-facility: removing events for %s and children" % strip_facility 75 78 total = 0 76 79 copied = 0 … … 78 81 if options['verbose']: 79 82 if "d" in e: 80 print e['d']['num']83 print >>stdout, e['d']['num'] 81 84 else: 82 print "HEADER"85 print >>stdout, "HEADER" 83 86 total += 1 84 87 if "d" in e: … … 99 102 if options.newfile == options.oldfile: 100 103 os.rename(newfilename, options.newfile) 101 print "copied %d of %d events into new file" % (copied, total)104 print >>stdout, "copied %d of %d events into new file" % (copied, total) 102 105 103 106 def get_events(self, fn): foolscap/test/test_logging.py
r459 r460 1528 1528 self.failUnless("to launch the daemon" in out, out) 1529 1529 1530 class Dumper(unittest.TestCase, LogfileReaderMixin): 1531 # create a logfile, then dump it, and examine the output to make sure it 1532 # worked right. 1530 class LogfileWriterMixin: 1533 1531 1534 1532 def create_logfile(self): … … 1537 1535 fn = os.path.join(self.basedir, "dump.flog") 1538 1536 l = log.FoolscapLogger() 1539 lfo = log.LogFileObserver(fn )1537 lfo = log.LogFileObserver(fn, level=0) 1540 1538 l.addObserver(lfo.msg) 1541 l.msg("one") 1542 l.msg("two") 1539 l.msg("one", facility="big.facility") 1540 time.sleep(0.2) # give filter --after something to work with 1541 l.msg("two", level=log.OPERATIONAL-1) 1543 1542 try: 1544 1543 raise SampleError("whoops1") 1545 1544 except: 1546 l.err( )1547 l.msg(" three")1545 l.err(message="three") 1546 l.msg("four") 1548 1547 d = fireEventually() 1549 1548 def _done(res): … … 1554 1553 d.addCallback(_done) 1555 1554 return d 1555 1556 def create_incident(self): 1557 if not os.path.exists(self.basedir): 1558 os.makedirs(self.basedir) 1559 l = log.FoolscapLogger() 1560 l.setLogDir(self.basedir) 1561 l.setIncidentReporterFactory(NoFollowUpReporter) 1562 1563 d = defer.Deferred() 1564 def _done(name, trigger): 1565 d.callback( (name,trigger) ) 1566 l.addImmediateIncidentObserver(_done) 1567 1568 l.msg("one") 1569 l.msg("two") 1570 l.msg("boom", level=log.WEIRD) 1571 l.msg("four") 1572 1573 d.addCallback(lambda (name,trigger): 1574 os.path.join(self.basedir, name+".flog.bz2")) 1575 1576 return d 1577 1578 class Dumper(unittest.TestCase, LogfileWriterMixin, LogfileReaderMixin): 1579 # create a logfile, then dump it, and examine the output to make sure it 1580 # worked right. 1556 1581 1557 1582 def test_dump(self): … … 1594 1619 d.format_time(events[1]["d"]["time"])) 1595 1620 self.failUnlessEqual(lines[0].strip(), line0) 1596 self.failUnless(lines[-1].strip().endswith(" three"))1621 self.failUnless(lines[-1].strip().endswith(" four")) 1597 1622 1598 1623 argv = ["flogtool", "dump", "--verbose", fn] … … 1602 1627 self.failUnless("'message': 'one'" in lines[0]) 1603 1628 self.failUnless("'level': 20" in lines[0]) 1604 self.failUnless(": three: {" in lines[-1])1629 self.failUnless(": four: {" in lines[-1]) 1605 1630 1606 1631 d.addCallback(_check) 1607 return d1608 1609 def create_incident(self):1610 if not os.path.exists(self.basedir):1611 os.makedirs(self.basedir)1612 l = log.FoolscapLogger()1613 l.setLogDir(self.basedir)1614 l.setIncidentReporterFactory(NoFollowUpReporter)1615 1616 d = defer.Deferred()1617 def _done(name, trigger):1618 d.callback( (name,trigger) )1619 l.addImmediateIncidentObserver(_done)1620 1621 l.msg("one")1622 l.msg("two")1623 l.msg("boom", level=log.WEIRD)1624 l.msg("four")1625 1626 d.addCallback(lambda (name,trigger):1627 os.path.join(self.basedir, name+".flog.bz2"))1628 1629 1632 return d 1630 1633 … … 1649 1652 d.addCallback(_check) 1650 1653 return d 1654 1655 class Filter(unittest.TestCase, LogfileWriterMixin, LogfileReaderMixin): 1656 1657 def compare_events(self, a, b): 1658 # cmp(a,b) won't quite work, because two instances of CopiedFailure 1659 # loaded from the same pickle don't compare as equal 1660 self.failUnlessEqual(len(a), len(b)) 1661 for i in range(len(a)): 1662 a1,b1 = a[i],b[i] 1663 self.failUnlessEqual(set(a1.keys()), set(b1.keys())) 1664 for k in a1: 1665 if k == "d": 1666 self.failUnlessEqual(set(a1["d"].keys()), 1667 set(b1["d"].keys())) 1668 for k2 in a1["d"]: 1669 if k2 == "failure": 1670 f1 = a1["d"][k2] 1671 f2 = b1["d"][k2] 1672 self.failUnlessEqual(f1.value, f2.value) 1673 self.failUnlessEqual(f1.getTraceback(), 1674 f2.getTraceback()) 1675 else: 1676 self.failUnlessEqual(a1["d"][k2], b1["d"][k2]) 1677 else: 1678 self.failUnlessEqual(a1[k], b1[k]) 1679 1680 1681 def test_basic(self): 1682 self.basedir = "logging/Filter/basic" 1683 d = self.create_logfile() 1684 def _check(fn): 1685 events = self._read_logfile(fn) 1686 count = len(events) 1687 assert count == 5 1688 1689 dirname,filename = os.path.split(fn) 1690 fn2 = os.path.join(dirname, "filtered-" + filename) 1691 1692 # pass-through 1693 argv = ["flogtool", "filter", fn, fn2] 1694 (out,err) = cli.run_flogtool(argv[1:], run_by_human=False) 1695 self.failUnless("copied 5 of 5 events into new file" in out, out) 1696 self.compare_events(events, self._read_logfile(fn2)) 1697 1698 # convert to .bz2 while we're at it 1699 fn2bz2 = fn2 + ".bz2" 1700 argv = ["flogtool", "filter", fn, fn2bz2] 1701 (out,err) = cli.run_flogtool(argv[1:], run_by_human=False) 1702 self.failUnless("copied 5 of 5 events into new file" in out, out) 1703 self.compare_events(events, self._read_logfile(fn2bz2)) 1704 1705 # modify the file in place 1706 argv = ["flogtool", "filter", "--above", "20", fn2] 1707 (out,err) = cli.run_flogtool(argv[1:], run_by_human=False) 1708 self.failUnless("modifying event file in place" in out, out) 1709 self.failUnless("--above: removing events below level 20" in out, out) 1710 self.failUnless("copied 4 of 5 events into new file" in out, out) 1711 self.compare_events([events[0], events[1], events[3], events[4]], 1712 self._read_logfile(fn2)) 1713 1714 # modify the file in place, two-argument version 1715 argv = ["flogtool", "filter", fn2, fn2] 1716 (out,err) = cli.run_flogtool(argv[1:], run_by_human=False) 1717 self.failUnless("modifying event file in place" in out, out) 1718 self.failUnless("copied 4 of 4 events into new file" in out, out) 1719 self.compare_events([events[0], events[1], events[3], events[4]], 1720 self._read_logfile(fn2)) 1721 1722 # --above with a string argument 1723 argv = ["flogtool", "filter", "--above", "OPERATIONAL", fn, fn2] 1724 (out,err) = cli.run_flogtool(argv[1:], run_by_human=False) 1725 self.failUnless("--above: removing events below level 20" in out, out) 1726 self.failUnless("copied 4 of 5 events into new file" in out, out) 1727 self.compare_events([events[0], events[1], events[3], events[4]], 1728 self._read_logfile(fn2)) 1729 1730 t_one = events[1]["d"]["time"] 1731 # we can only pass integers into --before and --after, so we'll 1732 # just test that we get all or nothing 1733 argv = ["flogtool", "filter", "--before", str(int(t_one - 10)), 1734 fn, fn2] 1735 (out,err) = cli.run_flogtool(argv[1:], run_by_human=False) 1736 self.failUnless("copied 1 of 5 events into new file" in out, out) 1737 # we always get the header, so it's 1 instead of 0 1738 self.compare_events(events[:1], self._read_logfile(fn2)) 1739 1740 argv = ["flogtool", "filter", "--after", str(int(t_one + 10)), 1741 fn, fn2] 1742 (out,err) = cli.run_flogtool(argv[1:], run_by_human=False) 1743 self.failUnless("copied 1 of 5 events into new file" in out, out) 1744 self.compare_events(events[:1], self._read_logfile(fn2)) 1745 1746 # --facility 1747 argv = ["flogtool", "filter", "--strip-facility", "big", fn, fn2] 1748 (out,err) = cli.run_flogtool(argv[1:], run_by_human=False) 1749 self.failUnless("--strip-facility: removing events for big and children" in out, out) 1750 self.failUnless("copied 4 of 5 events into new file" in out, out) 1751 self.compare_events([events[0],events[2],events[3],events[4]], 1752 self._read_logfile(fn2)) 1753 1754 # pass-through, --verbose, read from .bz2 1755 argv = ["flogtool", "filter", "--verbose", fn2bz2, fn2] 1756 (out,err) = cli.run_flogtool(argv[1:], run_by_human=False) 1757 self.failUnless("copied 5 of 5 events into new file" in out, out) 1758 lines = [l.strip() for l in StringIO(out).readlines()] 1759 self.failUnlessEqual(lines, 1760 ["HEADER", "0", "1", "2", "3", 1761 "copied 5 of 5 events into new file"]) 1762 self.compare_events(events, self._read_logfile(fn2)) 1763 1764 # --from . This normally takes a base32 tubid prefix, but the 1765 # things we've logged all say ["from"]="local". So just test 1766 # all-or-nothing. 1767 argv = ["flogtool", "filter", "--from", "local", fn, fn2] 1768 (out,err) = cli.run_flogtool(argv[1:], run_by_human=False) 1769 self.failUnless("--from: retaining events only from tubid prefix local" in out, out) 1770 self.failUnless("copied 5 of 5 events into new file" in out, out) 1771 self.compare_events(events, self._read_logfile(fn2)) 1772 1773 argv = ["flogtool", "filter", "--from", "NOTlocal", fn, fn2] 1774 (out,err) = cli.run_flogtool(argv[1:], run_by_human=False) 1775 self.failUnless("--from: retaining events only from tubid prefix NOTlocal" in out, out) 1776 self.failUnless("copied 1 of 5 events into new file" in out, out) 1777 self.compare_events(events[:1], self._read_logfile(fn2)) 1778 1779 1780 d.addCallback(_check) 1781 return d 1782 1783 1651 1784 1652 1785 class Web(unittest.TestCase):
