1
2
3
4
5
6
7
8
9
10
11
12
13
14 import logging
15 from twisted.internet import reactor
16 from twisted.internet.defer import Deferred
17 from pynetsnmp.twistedsnmp import AgentProxy
18
19 _LOG = logging.getLogger("zen.ZenUtils.snmp")
22 succeeded = None
23 sysName = None
24
25 @property
28
29 @property
31 return self._community
32
33 @property
35 return self._weight is None and self.defaultWeight or self._weight
36
37
38 - def __init__(self, ip, weight=None, port=161, timeout=2.5, retries=2,
39 community='public'):
46
47
49 return "(%s) %s:%s, SNMP%s, timeout=%ss, retries=%s, community=%s" % (
50 self.weight, self._ip, self._port, self.version, self._timeout,
51 self._retries, self.community)
52
53
62
63
64 - def test(self, oid='.1.3.6.1.2.1.1.5.0'):
69
70
82
87
92
95 version = 'v3'
96 defaultWeight = 30
97
98 - def __init__(self, ip, weight=None, port=161, timeout=2.5, retries=2,
99 community='public', securityName=None, authType=None,
100 authPassphrase=None, privType=None, privPassphrase=None):
101 super(SnmpV3Config, self).__init__(
102 ip, weight, port, timeout, retries, community)
103
104 self._securityName = securityName
105 self._authType = authType
106 self._authPassphrase = authPassphrase
107 self._privType = privType
108 self._privPassphrase = privPassphrase
109
110
112 v3string = "securityName=%s" % self._securityName
113 if self._authType:
114 v3string += ", authType=%s, authPassphrase=%s" % (
115 self._authType, self._authPassphrase)
116
117 if self._privType:
118 v3string += " privType=%s, privPassphrase=%s" % (
119 self._privType, self._privPassphrase)
120
121 return "(%s) %s:%s, SNMP%s, timeout=%ss, retries=%s, %s" % (
122 self.weight, self._ip, self._port, self.version, self._timeout,
123 self._retries, v3string)
124
125
127 cmdLineArgs = ['-u', self._securityName]
128
129 if self._privType:
130 cmdLineArgs += [
131 '-l', 'authPriv',
132 '-x', self._privType,
133 '-X', self._privPassphrase]
134 elif self._authType:
135 cmdLineArgs += [
136 '-l', 'authNoPriv']
137 else:
138 cmdLineArgs += [
139 '-l', 'noAuthNoPriv']
140
141 if self._authType:
142 cmdLineArgs += [
143 '-a', self._authType,
144 '-A', self._authPassphrase]
145
146 return AgentProxy(
147 ip=self._ip,
148 port=self._port,
149 timeout=self._timeout,
150 tries=self._retries,
151 snmpVersion=self.version,
152 community=self._community,
153 cmdLineArgs=cmdLineArgs)
154
155
167
168
169 -class SnmpAgentDiscoverer(object):
170 _bestsofar = None
171
172 - def _handleResult(self, result):
173 if not hasattr(result, 'weight'):
174
175 return
176
177 for i, p in enumerate(self._pending):
178 if p.weight == result.weight:
179 self._pending.pop(i)
180
181 if result.succeeded:
182
183 if self._bestsofar:
184 if result.weight > self._bestsofar.weight:
185 self._bestsofar = result
186 else:
187 self._bestsofar = result
188
189
190
191 for config in self._pending:
192 if config.weight >= self._bestsofar.weight:
193 break
194 else:
195 if not self._d.called:
196 self._d.callback(self._bestsofar)
197
198 return
199
200
201
202 if len(self._pending) < 1 and not self._d.called:
203 self._d.callback(self._bestsofar)
204
205
206 - def findBestConfig(self, configs):
207 """
208 Returns the best SnmpConfig in the provided configs list.
209 """
210 _LOG.debug("findBestConfig: configs=%s" % configs)
211 self._pending = configs
212 self._d = Deferred()
213
214 for c in configs:
215 c.test().addBoth(self._handleResult)
216
217 return self._d
218
219
220 if __name__ == '__main__':
221 """
222 The following snmpd.conf is a good one to run the following tests on.
223
224 rocommunity zenosszenoss
225 rouser noauthtest noauth
226 createUser noauthtest MD5 "zenosszenoss"
227 rouser authtest
228 createUser authtest SHA "zenosszenoss"
229 rouser privtest
230 createUser privtest SHA "zenosszenoss" DES "zenosszenoss"
231 """
235
236 configs = [
237 SnmpV3Config('127.0.0.1', weight=33, securityName='privtest',
238 authType='SHA', authPassphrase='zenosszenoss',
239 privType='DES', privPassphrase='zenosszenoss'),
240
241 SnmpV3Config('127.0.0.1', weight=32, securityName='authtest',
242 authType='SHA', authPassphrase='zenosszenoss'),
243
244 SnmpV3Config('127.0.0.1', weight=31, securityName='noauthtest'),
245
246 SnmpV2cConfig('127.0.0.1', weight=22, community='zenosszenoss'),
247 SnmpV2cConfig('127.0.0.1', weight=21, community='public'),
248
249 SnmpV1Config('127.0.0.1', weight=12, community='zenosszenoss'),
250 SnmpV1Config('127.0.0.1', weight=11, community='public'),
251 ]
252
253 sad = SnmpAgentDiscoverer()
254 sad.findBestConfig(configs).addBoth(printAndExit)
255 reactor.run()
256