[Author Prev][Author Next][Thread Prev][Thread Next][Author Index][Thread Index]

[or-cvs] r23378: {arm} added: option to save log events to a file change: bolding E (in arm/trunk: . src src/interface)



Author: atagar
Date: 2010-10-01 16:36:12 +0000 (Fri, 01 Oct 2010)
New Revision: 23378

Added:
   arm/trunk/src/version.py
Modified:
   arm/trunk/armrc.sample
   arm/trunk/setup.py
   arm/trunk/src/interface/logPanel.py
   arm/trunk/src/starter.py
Log:
added: option to save log events to a file
change: bolding ERR events



Modified: arm/trunk/armrc.sample
===================================================================
--- arm/trunk/armrc.sample	2010-10-01 15:18:17 UTC (rev 23377)
+++ arm/trunk/armrc.sample	2010-10-01 16:36:12 UTC (rev 23378)
@@ -7,6 +7,10 @@
 
 features.colorInterface true
 
+# If set, arm saves any log messages it reports while running to the given
+# path. This does not take filters into account or include prepopulated events.
+features.logPath 
+
 # log panel parameters
 # showDateDividers: show borders with dates for entries from previous days
 # maxLinesPerEntry: max number of lines to display for a single log entry
@@ -101,6 +105,8 @@
 log.graph.bw.prepopulateFailure NOTICE
 log.logPanel.prepopulateSuccess INFO
 log.logPanel.prepopulateFailed WARN
+log.logPanel.logFileOpened NOTICE
+log.logPanel.logFileWriteFailed ERR
 log.connLookupFailed INFO
 log.connLookupFailover NOTICE
 log.connLookupAbandon WARN

Modified: arm/trunk/setup.py
===================================================================
--- arm/trunk/setup.py	2010-10-01 15:18:17 UTC (rev 23377)
+++ arm/trunk/setup.py	2010-10-01 16:36:12 UTC (rev 23378)
@@ -1,10 +1,9 @@
 #!/usr/bin/env python
 import os
 import sys
+from src.version import VERSION
 from distutils.core import setup
 
-VERSION = '1.3.6_dev'
-
 setup(name='arm',
       version=VERSION,
       description='Terminal tor status monitor',

Modified: arm/trunk/src/interface/logPanel.py
===================================================================
--- arm/trunk/src/interface/logPanel.py	2010-10-01 15:18:17 UTC (rev 23377)
+++ arm/trunk/src/interface/logPanel.py	2010-10-01 16:36:12 UTC (rev 23378)
@@ -5,12 +5,14 @@
 """
 
 import time
+import os
 import curses
 import threading
 from curses.ascii import isprint
 
 from TorCtl import TorCtl
 
+from version import VERSION
 from util import log, panel, sysTools, torTools, uiTools
 
 TOR_EVENT_TYPES = {
@@ -36,14 +38,17 @@
 DAYBREAK_EVENT = "DAYBREAK" # special event for marking when the date changes
 
 ENTRY_INDENT = 2 # spaces an entry's message is indented after the first line
-DEFAULT_CONFIG = {"features.log.showDateDividers": True,
+DEFAULT_CONFIG = {"features.logPath": "",
+                  "features.log.showDateDividers": True,
                   "features.log.maxLinesPerEntry": 4,
                   "features.log.prepopulate": True,
                   "features.log.prepopulateReadLimit": 5000,
                   "features.log.maxRefreshRate": 300,
                   "cache.logPanel.size": 1000,
                   "log.logPanel.prepopulateSuccess": log.INFO,
-                  "log.logPanel.prepopulateFailed": log.WARN}
+                  "log.logPanel.prepopulateFailed": log.WARN,
+                  "log.logPanel.logFileOpened": log.NOTICE,
+                  "log.logPanel.logFileWriteFailed": log.ERR}
 
 DUPLICATE_MSG = " [%i duplicate%s hidden]"
 
@@ -59,6 +64,7 @@
 # [ARM_DEBUG] system call: ps
 # [ARM_DEBUG] system call: netstat
 # [ARM_DEBUG] GETINFO accounting/
+# [BW] READ: 0, WRITTEN: 0
 COMMON_LOG_MESSAGES = {"NOTICE": [
                          "We stalled too much while trying to write",
                          "I learned some more directory information, but not enough to build a circuit",
@@ -71,7 +77,9 @@
                          "refresh rate: ",
                          "system call: ps",
                          "system call: netstat",
-                         "GETINFO accounting/"]
+                         "GETINFO accounting/"],
+                       "BW": [
+                         "READ:"]
                       }
 
 # cached values and the arguments that generated it for the getDaybreaks and
@@ -369,11 +377,20 @@
     self.color = color
     self._displayMessage = None
   
-  def getDisplayMessage(self):
+  def getDisplayMessage(self, includeDate = False):
     """
     Provides the entry's message for the log.
+    
+    Arguments:
+      includeDate - appends the event's date to the start of the message
     """
     
+    if includeDate:
+      # not the common case so skip caching
+      entryTime = time.localtime(self.timestamp)
+      timeLabel =  "%i/%i/%i %02i:%02i:%02i" % (entryTime[1], entryTime[2], entryTime[0], entryTime[3], entryTime[4], entryTime[5])
+      return "%s [%s] %s" % (timeLabel, self.type, self.msg)
+    
     if not self._displayMessage:
       entryTime = time.localtime(self.timestamp)
       self._displayMessage = "%02i:%02i:%02i [%s] %s" % (entryTime[3], entryTime[4], entryTime[5], self.type, self.msg)
@@ -480,6 +497,7 @@
     self.loggedEvents = loggedEvents    # events we're listening to
     self.regexFilter = None             # filter for presented log events (no filtering if None)
     self.lastContentHeight = 0          # height of the rendered content when last drawn
+    self.logFile = None                 # file log messages are saved to (skipped if None)
     self.scroll = 0
     self._isPaused = False
     self._pauseBuffer = []              # location where messages are buffered if paused
@@ -546,6 +564,21 @@
     conn = torTools.getConn()
     conn.addEventListener(TorEventObserver(self.registerEvent))
     conn.addTorCtlListener(self._registerTorCtlEvent)
+    
+    # opens log file if we'll be saving entries
+    if self._config["features.logPath"]:
+      logPath = self._config["features.logPath"]
+      
+      # make dir if the path doesn't already exist
+      baseDir = os.path.dirname(logPath)
+      if not os.path.exists(baseDir): os.makedirs(baseDir)
+      
+      try:
+        self.logFile = open(logPath, "a")
+        log.log(self._config["log.logPanel.logFileOpened"], "arm %s opening log file (%s)" % (VERSION, logPath))
+      except IOError, exc:
+        log.log(self._config["log.logPanel.logFileWriteFailed"], "Unable to write to log file: %s" % exc)
+        self.logFile = None
   
   def registerEvent(self, event):
     """
@@ -560,6 +593,15 @@
     # strips control characters to avoid screwing up the terminal
     event.msg = "".join([char for char in event.msg if (isprint(char) or char == "\n")])
     
+    # note event in the log file if we're saving them
+    if self.logFile:
+      try:
+        self.logFile.write(event.getDisplayMessage(True) + "\n")
+        self.logFile.flush()
+      except IOError, exc:
+        log.log(self._config["log.logPanel.logFileWriteFailed"], "Unable to write to log file: %s" % exc)
+        self.logFile = None
+    
     cacheSize = self._config["cache.logPanel.size"]
     if self._isPaused:
       self._pauseBuffer.insert(0, event)
@@ -729,7 +771,8 @@
         
         msgComp = entry.getDisplayMessage().split("\n")
         for i in range(len(msgComp)):
-          displayQueue.append((msgComp[i].strip(), uiTools.getColor(entry.color), i != len(msgComp) - 1))
+          font = curses.A_BOLD if "ERR" in entry.type else curses.A_NORMAL # emphasizes ERR messages
+          displayQueue.append((msgComp[i].strip(), font | uiTools.getColor(entry.color), i != len(msgComp) - 1))
         
         if duplicateCount:
           pluralLabel = "s" if duplicateCount > 1 else ""

Modified: arm/trunk/src/starter.py
===================================================================
--- arm/trunk/src/starter.py	2010-10-01 15:18:17 UTC (rev 23377)
+++ arm/trunk/src/starter.py	2010-10-01 16:36:12 UTC (rev 23378)
@@ -10,6 +10,7 @@
 import sys
 import getopt
 
+import version
 import interface.controller
 import interface.logPanel
 import util.conf
@@ -23,9 +24,6 @@
 import TorCtl.TorCtl
 import TorCtl.TorUtil
 
-VERSION = "1.3.6_dev"
-LAST_MODIFIED = "July 7, 2010"
-
 DEFAULT_CONFIG = os.path.expanduser("~/.armrc")
 DEFAULTS = {"startup.controlPassword": None,
             "startup.interface.ipAddress": "127.0.0.1",
@@ -110,7 +108,7 @@
     elif opt in ("-e", "--event"):
       param["startup.events"] = arg                   # set event flags
     elif opt in ("-v", "--version"):
-      print "arm version %s (released %s)\n" % (VERSION, LAST_MODIFIED)
+      print "arm version %s (released %s)\n" % (version.VERSION, version.LAST_MODIFIED)
       sys.exit()
     elif opt in ("-h", "--help"):
       print HELP_MSG

Added: arm/trunk/src/version.py
===================================================================
--- arm/trunk/src/version.py	                        (rev 0)
+++ arm/trunk/src/version.py	2010-10-01 16:36:12 UTC (rev 23378)
@@ -0,0 +1,7 @@
+"""
+Provides arm's version and release date.
+"""
+
+VERSION = '1.3.6_dev'
+LAST_MODIFIED = "July 7, 2010"
+