]> git.pld-linux.org Git - packages/nagios-alert-jabber.git/blob - nagios-jabber.alert
- allow setting custom subject
[packages/nagios-alert-jabber.git] / nagios-jabber.alert
1 #!/usr/bin/python -u
2 # arekm@pld-linux.org, 2006-01
3 # glen@pld-linux.org, 2006-03-14
4 # glen@pld-linux.org,arekm@pld-linux.org, 2006-10-30 - added ssl support (for gmail.com)
5 # glen@pld-linux.org 2006-11-03 - made it work with jabber.pld-linux.org again
6 # glen@pld-linux.org,arekm@pld-linux.org, 2006-11-13 - added config file support
7 # glen@pld-linux.org, 2006-12-07 - added html messages support (-x), thx goes to to jajcus
8 # luzik@pld-linux.org, 2007-03 - added digest auth method(jabber.gda.pl)
9 # arekm@pld-linux.org, 2009-07 - added fallback accounts support
10 # usage:
11 #   jabber.alert [-x] [-c config] [-a account_id][,otheraccount_id] [-t timeout ] [-J from_jid -P password] to_jid1 to_jid2 to_jid3
12
13 import os
14 import hashlib
15 import re
16 import sys
17 import getopt
18 import logging
19 import socket
20 import string
21 import time
22 import libxml2
23
24 from pyxmpp.jid import JID
25 from pyxmpp.message import Message
26 from pyxmpp.jabber.client import JabberClient
27 from pyxmpp.streamtls import TLSSettings
28
29 try:
30     opts, args = getopt.getopt(sys.argv[1:], "J:P:a:b:c:ds:t:x")
31 except getopt.GetoptError, e:
32     print >> sys.stderr, "%s: %s " % (sys.argv[0], e)
33     sys.exit(1)
34
35 jids = []
36 html = False
37 debug = False
38 timeout = 20
39 cfg = "/etc/nagios/jabber-notify.ini"
40 tjid = None
41 body = ""
42 subject = "Nagios alert"
43 for o, a in opts:
44     if o == '-b':
45         body = a
46     if o == '-c':
47         cfg = a
48     if o == '-d':
49         debug = True
50     if o == '-t':
51         timeout = float(a)
52     if o == '-x':
53         html = True
54     if o == '-J':
55         tjid = a
56     if o == '-P':
57         jids.append({ 'jid': tjid, 'password': a })
58     if o == '-s':
59         subject = a
60     if o == '-a':
61         import ConfigParser
62
63         config = ConfigParser.ConfigParser()
64         config.read(cfg)
65
66         for section in a.split(','):
67             jids.append({ 'jid': config.get(section, 'jid'), 'password': config.get(section, 'password')})
68
69 socket.setdefaulttimeout(timeout)
70
71 recpt = args
72
73 for section in jids:
74     if not section['jid'] or not section['password']:
75         print >> sys.stderr, "%s: jid (-J) and password (-P) are required for `%s'" % (sys.argv[0], section)
76         sys.exit(1)
77
78 if not jids:
79     print >> sys.stderr, "%s: no configured jid accounts found" % sys.argv[0]
80     sys.exit(1)
81
82 if not recpt:
83     print >> sys.stderr, "%s: recipient jids are required" % sys.argv[0]
84     sys.exit(1)
85
86 if debug:
87     logger=logging.getLogger()
88     logger.addHandler(logging.StreamHandler())
89     logger.setLevel(logging.DEBUG)
90
91 if not body:
92     stdin_body = ""
93     for line in sys.stdin.readlines():
94         stdin_body += line
95
96     body += stdin_body
97
98 if len(body.strip()) == 0:
99     body = "(nagios-jabber.alert warning: missing message body)";
100
101 message_type = 'chat'
102
103 class XMPPStreamError(Exception):
104     def __init__(self, msg):
105         self.msg = msg
106     def __str__(self):
107         return self.msg
108
109 class Client(JabberClient):
110     def session_started(self):
111         if (html == True):
112             import re
113             message = re.sub('<.*?>', '', body)
114             doc = libxml2.parseDoc('<body>' + body + '</body>')
115             doc_element = doc.getRootElement().children
116         else:
117             message = body
118
119         for r in recpt:
120             jid_r = JID(r)
121             msg = Message(to_jid = jid_r, body = message, subject = subject,
122                             stanza_type = message_type, thread = "Nagios")
123
124             if (html == True):
125                 node = msg.add_new_content('http://jabber.org/protocol/xhtml-im', 'html')
126                 xbody = node.newChild(None, "body", None)
127                 html_ns = xbody.newNs('http://www.w3.org/1999/xhtml', None)
128                 xbody.setNs(html_ns)
129                 xbody.addChildList(doc_element.docCopyNodeList(xbody.doc))
130
131             self.stream.send(msg)
132         self.disconnect()
133
134     def stream_state_changed(self,state,arg):
135         if debug:
136             print "*** State changed: %s %r ***" % (state,arg)
137
138     def stream_error(self,err):
139         raise XMPPStreamError(err.get_message())
140
141
142 err = []
143 for section in jids:
144     for attempt in ('first', 'second'):
145         jid = JID(section['jid'])
146         resource = "Nagios/" + hashlib.md5(''.join(recpt)).hexdigest()[:10]
147         if attempt == 'second':
148             # if something went wrong the second time around, it's
149             # most likely a resource name conflict on login, so let's
150             # wait a bit, randomize the resource name and try again
151             resource = resource + '/' + repr(os.getpid())
152             time.sleep(0.8)
153         if not jid.resource:
154             jid = JID(jid.node, jid.domain, resource)
155
156         c = Client(jid, section['password'], auth_methods = ['sasl:DIGEST-MD5', 'sasl:PLAIN', 'digest'],
157                         tls_settings = TLSSettings(require = False, verify_peer = False))
158         try:
159             c.connect()
160             try:
161                 c.loop(1)
162             except XMPPStreamError, e:
163                 # Most likely a duplicate stream problem
164                 # don't log anything, just try again
165                 c.disconnect()
166                 continue
167             except Exception, e:
168                 err.append("ERROR1: %s: %s" % (section['jid'], e))
169                 c.disconnect()
170                 # don't try another attempt, jump straigt to
171                 # another section
172                 break
173             c.disconnect()
174             # stop after first successful attempt at sending the msg
175             sys.exit(0)
176         except Exception, e:
177             err.append("ERROR2: %s: %s" % (section['jid'], e))
178
179 print >> sys.stderr, "\n".join(err)
180 sys.exit(1)
This page took 0.147879 seconds and 3 git commands to generate.