Revision history for Perl extension POE::Component::SNMP.
0.01 Mon Apr 21 13:28:31 2003
- original version; created by h2xs 1.22 with options
-AX -n POE::Component::SNMP
0.90 Mon Jun 7 18:44:00 2004
- Module inherited by Rob Bloodgood, from the previous
maintainer, Todd Caine.
- added POE::Component::SNMP::Dispatcher module, to subclass
Net::SNMP::Dispatcher such that all socket and scheduling
operations were processed by POE's event loop.
- updated the callback variables so that the hostname and
session alias of the SNMP object queried are returned to the
callback event.
- made write tests optional during install, so that the module
would install correctly even where a writeable host was
unavailable.
0.92 Mon Sep 6 13:19:53 2004
- Updated to be compatible with new Net::SNMP release 5.0.0
0.93 Thu Aug 11 11:57:29 2005
- Updated POE session constructor from the deprecated new() to
the new create() method.
- Removed a bunch of commented, deprecated code that was still
a holdover from the 0.01
0.94 Thu Mar 30 14:43:19 2006
- Reorganized the module distribution to use a lib/ dir, cuz
MakeMaker was being dumb.
- Updated Makefile.PL to remove the config file on 'make
realclean'
- Tweaked the docs.
- Altered the sample script in the SYNOPSIS to actually work.
- Removed remaining commented references to deprecated code.
- Followed a suggestion from Curtis J. Coleman to re-order
component shutdown so that finish() worked correctly.
- Lots of minor cleanups in the text
- At LAST: removed the duplicate methods to account for the
difference between Net::SNMP 4.x and 5.x. Now this is
achieved by aliasing the functions that need to be
duplicated in the symbol table.
0.95 Sat Apr 8 14:46:54 PDT 2006
- Collapsed all the identical method calls into a dispatch
mechanism around a single method call template.
- VASTLY improved error handling.
- Added the snmp method (eg get, set, walk) and request args
to the request packet returned to callbacks.
- Reorganized Dispatcher.pm, trimmed old commented
code. Removed unneeded debugging statements.
- trimmed unnecessary parameters from calls to
__invoke_callback().
- added new tests for various aspects of error handling.
0.96 Mon Apr 10 01:29:40 PDT 2006
- re-ordered the hostname and community checks so that the
fatal "hostname is required" is thrown BEFORE the warning
"using default community".
- added new tests for error conditions and parameter errors
- changed the return values to always return something sane,
e.g. a string or a ref, not a string or a ref or maybe an
undef, THEN a string! The only reason I didn't change this
before is that I mistakenly thought this weird error
structure came directly from Net::SNMP, but it turns out I
just inherited it. <sigh>
- for compatibility, continue to return the $snmp_object->error
value in the second slot, since the last change alters the API.
- Also, changed the original args returned to callbacks from
being a listref to a simple list, in the same way they
came in.
- Unified style in docs. Cleaned up internal and external POD
links.
0.97 Mon Apr 10 13:14:01 PDT 2006
- Fixed some formatting tweaks in the docs.
- Renamed the function snmp_last_error_message to snmp_errmsg,
to correspond the the component request 'errmsg', like the
other method names.
- DANG! Left in some debugging references to YAML and Spiffy
that I meant to comment out. Which breaks systems that don't
have those modules installed. Grr. Fixed.
- Also pulled references to YAML from the sample script... not
everybody has YAML.
0.98 Wed Apr 12 20:02:12 PDT 2006
- Improved dispatcher tracing by making all calls consistently
trace their execution. Use Net::SNMP debug functions to
report our activities when the debug flag to trace the
Dispatcher is set in the constructor. Gives nice,
consistent trace output.
- Started work to remove the requirement that each host have a
different -localport parameter. I chased it down. The
fundemental question is, how is it possible for Net::SNMP to
reuse the same socket for every remote host, without parsing
the internals of the packet and matching them to a "replies
expected" table? The answer is, it is not. Net::SNMP
dispatches all queries in the order received, serially. The
workaround we used is correct. Note to self: NOW STOP
WONDERING IF THIS IS POSSIBLE!
- Accidentally optimized the whole module by a factor of at
least 3x by copying Net::SNMP::Dispatcher's send_pdu() into
PoCo::SNMP::Dispatcher. See notes on send_pdu().
- Changed __schedule_event so that events with no delay simply
invoke their callback args instead of post()ing to
__invoke_callback. This saves me a POE state call.
- Updated _send_pdu to return TRUE, just like the Net::SNMP
version does.
0.99
- Changed send_pdu() optimization. Instead of being a copy of
the N:S:D's, we simply change the function reference
involved, with local(), before invoking SUPER::send_pdu().
- Changed __send_next_pdu and __pdu_sent around... the 2nd
half of __send_next_pdu belonged logically in __pdu_sent.
This saves me a POE state call and is cleaner.
- Renamed __send_next_pdu to __dispatch_pdu.
- Discovered that select_read() can take additional args to
pass back to the event triggered when a handle goes live.
Duuhh. What this means is, I no longer have to dig into
Net::SNMP to find out where they stashed the callback,
indexed by the fileno of the socket. Instead I can simply
pass and invoke the supplied callback. This changed
register(), __listen, and __socket_callback.
- Discovered that extra args support for select_read() wasn't
added until 0.32. <sigh> Coded it back, only this time
without mucking around with private attributes of my parent
class.
- Tweaked whitespace so stuff looks consistent.
- Copied the sanity check from Net::SNMP that loads and
verifies the dispatcher instance. Now P:C:S:Dispatcher
doesn't muck around with Net::SNMP's package space, just
subclasses it. Instead, P:C:S loads the Dispatcher in a
BEGIN block, just like Net::SNMP. THEN it mucks with
Net::SNMP's namespace. <evil grin>
- Replaced references to $self in the constructor with $this,
following Net::SNMP's convention and the rest of the module.
- Removed alot of folds. I had folds around every function,
now I just have them around major sections.
- Started working on the edge case where somebody is dumb
enough to call finish() while data is still pending.
- Updated constructor to accept all forms of -alias, alias,
Alias, and the same for -hostname.
- Removed the check for a valid varbindlist in the error
handler of the snmp_request(). Just return the error.
- Changed tracking of _current_pdu from a reference to the
callback args to a simple flag. All it needs to do is
*exist*.
- Triple-checked that the reference changing done in
send_pdu() was indeed persisting for subsequent
invocations of _send_pdu().
- Adusted the debug output to have a more verbose mode
available.
- More work on the finish() cleanup... now we delete pending
requests but allow the current request to complete.
- Altered socket listen/unlisten operations to use
select_pause_read() and select_resume_read(), because docs
say they are more lightweight. Initial tests show reduction
of approx. 20% in system loadavg with loadavg_multi_snmp.
- moved the socket ops to two new private methods,
_watch_handle() and _unwatch_handle(). These functions
maintain the reference counting of who has what handle,
without any of the rest of the module having to count any
part of it. that's good. :)
- had to adjust _unwatch_handle() to NOT stop listening when
there are replies due, in __clean_pending
- put the folds back in, not quite as many before tho. it's
easier to go from block to block that way, and only have the
functions unfolded that I'm working on.
- moved tracking of current and pending requests from the
session heap to the dispatcher object, so that the info can
be retrieved in POE or non-POE space.
- added the private method _pending_pdu_count(), based on
the last change.
- renamed __pdu_sent to __dispatch_pending_pdu
- use _pending_pdu_count() check to skip invoking
__dispatch_pending_pdu unless there is actually anything
pending. this saves me a POE state call for most situations.
- added accessors for current and pending pdus, instead of
getting directly into the heap hash or object.
- tried to change __clear_pending from an event to an object
method, but it hangs when I do that.
- way, way more tests. almost rewrote 40_set from
scratch... now instead of just blindly setting something, it
reads it, sets something else, verifies, then puts it back
and verifies. Much more robust.
- turns out that a better hook for subclassing than schedule()
is _event_insert(). By using it instead, we get A) the same
$event reference that cancel() receives, and B) a method
name that does *not* change between 4.x and 5.x. The logic
for cancel() stays the same.
- commented references to schedule/_schedule in the
compatibility section.
- changed _event_insert() so that if the time to invoke the
callback is immediate, it is invoked right then, *instead*
of calling __schedule. This saves me another POE state
call, woo-hoo!
- created a global debug flag in the config file so that I can
turn on and off debug output in *all* tests with one change.
- followed to the suggestion of Curtis J. Coleman to add the
ability to set arbitrary callback arguments to be returned
to callback events along with ordinary response data.
created tests for it. actually, I put in a couple of lines
of code and then wrote the tests... and then actually put in
the feature. :) tests are cool.
- changed a coupla stray call()'s in the tests to posts().
- added tests and logic for localport conflicts... my previous
code didn't work, and I ran into this error: "Failed to bind
UDP/IPv4 socket: Address already in use at ~/bin/wackastat
line 38", followed by "POE::Kernel's run() method was never
called."
- added an _arg_scan() to flexibly fetch values from a *list*
of key/value pairs.
- finally tracked down and eliminated the last stray reference
that was holding our sessions open when we called 'finish'
with requests still in the pipe!!!! It turns out the
$MESSAGE_PROCESSING subsystem was holding a cached copy of
our request, including its callback.
- put an error check in __dispatch_pending_pdu based on an
error report from Curtis Coleman
1.00 Mon Apr 24 15:55:23 PDT 2006
- release
1.01 Mon Apr 24 17:41:08 PDT 2006
- already got an error report from Curtis
Coleman.. __socket_callback ended up seeing an empty
callback. Fix by deferring unless there is a current callback.
1.02 Tue Apr 25 11:38:00 PDT 2006
- CPAN automated testing indicates not being able to correctly
locate TestPCS.pm. Turns out I forgot to put it into the
MANIFEST, so it wasn't bundled in the distribution!
- Turns out my tests were anticipating the wealth of results
available from the Net-SNMP daemon, which is not delivered
from, for example, an Alcatel DSLAM. With the invaluable
assistance of Curtis Coleman again, as well as a few others
in #PoE, got the tests straightened out. Thanks guys!
1.03 Fri Jun 2 18:51:19 PDT 2006
- small doc tweaks
- micro-optimized _pending_pdu_count by skipping exists() and
just using ref().
- added a check to __schedule_event to execute immediately if
for some strange reason the time of execution has already
arrived and yet we're still invoking __schedule.
- fixed a logic error in the -localport initializer that was
preventing retries if the random port chosen was already in
use. Thanks to Curtis Coleman for the spot.
1.04 Tue Jun 6 14:35:30 PDT 2006
- my fix was broken. fixed for real this time. thanks to
Curtis AGAIN!
1.05
- turned off $VERBOSE in Dispatcher.pm... even when debug
messages weren't being shown, VERBOSE added some extra
processing that was unnecessary (unless, of course, you're
developing PoCo::SNMP :).
- my assumptions about having a singleton dispatcher session
fell apart when a user tried to run the POE kernel more than
once... after the first run, the session is destroyed,
causing subsequent runs to fail. added destructor logic to
the dispatcher's _stop event, and constructor logic to the
main component's create() method. Now it functions properly
if run more than once. Thanks to Nigel Bowden for the spot.