+#!/usr/bin/env python
+
+import sys
+import gtk
+import appindicator
+
+import imaplib
+import re
+
+import os
+import pynotify
+
+PING_FREQUENCY = 10 # seconds
+
+def exec_command(command):
+ stream = os.popen(command)
+ out = stream.read()
+ out = re.split('\n',out);
+ res = []
+ for newline in out:
+ if len(newline)==0:
+ continue;
+ elif newline.startswith("Error:"):
+ res=[];
+ break;
+ else:
+ res.append(newline)
+ return res
+
+class CheckNUT:
+
+ def __init__(self):
+ self.ind = appindicator.Indicator("nut-indicator",
+ "gpm-ups-100-charging",
+ appindicator.CATEGORY_APPLICATION_STATUS)
+ self.ind.set_status(appindicator.STATUS_ACTIVE)
+ self.ind.set_attention_icon("gpm-ups-000")
+
+ hosts = sys.argv[1:]
+
+ if len(hosts)==0:
+ hosts = {'localhost'}
+
+ self.upses=[]
+ for host in hosts :
+ command = "upsc -l {0}".format(host)
+ try:
+ local_upses=exec_command(command)
+ for ups in local_upses:
+ self.upses.append('{0}@{1}'.format(ups,host))
+ except:
+ pass
+
+ if self.upses == []:
+ print "No connected ups'es found!\n"
+ sys.exit(1)
+
+ self.menu_setup()
+ self.ind.set_menu(self.menu)
+
+ if not pynotify.init ("nut-indicator"):
+ self.disable_notify=1
+ else:
+ self.disable_notify=0
+
+ self.ups_dictionary = {}
+ self.ups_dictionary['battery charge'] = 'Battery charge %'
+ self.ups_dictionary['input voltage'] = 'Input voltage'
+ self.ups_dictionary['output voltage'] = 'Output voltage'
+ self.ups_dictionary['ups load'] = 'UPS load %'
+ self.ups_dictionary['ups status'] = 'UPS status'
+
+ self.ups_value_dictionary = {}
+ self.ups_value_dictionary['ups status'] = {}
+ self.ups_value_dictionary['ups status']['OL'] = {1,'online'}
+ self.ups_value_dictionary['ups status']['OB'] = {0,'on battery'}
+ self.ups_value_dictionary['ups status']['LB'] = {-1,'low batter'}
+
+ def menu_setup(self):
+ self.menu = gtk.Menu()
+
+ self.menuitems = {}
+ for ups in self.upses:
+ print ups;
+ menu_item = gtk.MenuItem(ups)
+ menu_item.connect("activate",self.call_check_local_ups,ups)
+ menu_item.show()
+ self.menu.append(menu_item)
+ self.menuitems[ups]=menu_item
+
+ separator = gtk.SeparatorMenuItem()
+ separator.show()
+ self.menu.append(separator)
+
+ self.quit_item = gtk.MenuItem("Quit")
+ self.quit_item.connect("activate", self.quit)
+ self.quit_item.show()
+ self.menu.append(self.quit_item)
+
+ def main(self):
+ self.check_ups()
+ gtk.timeout_add(PING_FREQUENCY * 1000, self.check_ups)
+ gtk.main()
+
+ def quit(self, widget):
+ sys.exit(0)
+
+ def call_check_local_ups(self,item,ups):
+ return self.check_local_ups(ups,1)
+
+ def check_local_ups(self,ups,notify):
+ command = "upsc {0}".format(ups)
+ res = exec_command(command)
+ status="?"
+ battery="?"
+ ups_status="?"
+ text=""
+ minstatus=1
+ for newline in res:
+ paramname,paramvalue = newline.split(': ',1)
+ paramname = paramname.replace('.',' ')
+ try:
+ status,paramvalue = self.ups_value_dictionary[paramname][paramvalue]
+ if status<minstatus:
+ status=minstatus
+ except:
+ pass
+ try:
+ printname = self.ups_dictionary[paramname]
+ text="{0}\n{1} = {2}".format(text,printname,paramvalue)
+ except:
+ pass
+
+ if paramname=="battery charge":
+ battery=paramvalue
+ elif paramname=="ups status":
+ ups_status=paramvalue
+
+ if battery=='?':
+ self.menuitems[ups].get_child().set_text('{0}: {1}'.format(ups,ups_status))
+ else:
+ self.menuitems[ups].get_child().set_text('{0}: {1}, {2}%'.format(ups,ups_status,battery))
+ if (notify==1 or minstatus<0) and self.disable_notify==0:
+ n = pynotify.Notification(ups,text)
+ helper = gtk.Button()
+ icon = helper.render_icon(gtk.STOCK_DIALOG_INFO, gtk.ICON_SIZE_DIALOG)
+ n.set_icon_from_pixbuf(icon)
+ n.show()
+ return minstatus
+
+ def check_ups(self):
+
+ min_status=1;
+
+ for ups in self.upses:
+ status=self.check_local_ups(ups,0)
+ if status<min_status:
+ min_status=status
+
+ if status < 0:
+ self.ind.set_status(appindicator.STATUS_ATTENTION)
+ self.ind.set_attention_icon("gpm-ups-000")
+ elif status==0:
+ self.ind.set_status(appindicator.STATUS_ATTENTION)
+ self.ind.set_attention_icon("gpm-ups-060")
+ else:
+ self.ind.set_status(appindicator.STATUS_ACTIVE)
+ return True
+
+if __name__ == "__main__":
+ indicator = CheckNUT()
+ indicator.main()
+