net-snmp2 0.3.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (59) hide show
  1. checksums.yaml +7 -0
  2. data/.gitignore +5 -0
  3. data/.rspec +1 -0
  4. data/Gemfile +4 -0
  5. data/LICENSE +20 -0
  6. data/README.md +28 -0
  7. data/Rakefile +24 -0
  8. data/TODO.md +6 -0
  9. data/bin/mib2rb +129 -0
  10. data/bin/net-snmp2 +64 -0
  11. data/examples/agent.rb +104 -0
  12. data/examples/manager.rb +11 -0
  13. data/examples/trap_handler.rb +46 -0
  14. data/examples/v1_trap_session.rb +24 -0
  15. data/examples/v2_trap_session.rb +21 -0
  16. data/lib/net-snmp2.rb +85 -0
  17. data/lib/net/snmp.rb +27 -0
  18. data/lib/net/snmp/agent/agent.rb +48 -0
  19. data/lib/net/snmp/agent/provider.rb +51 -0
  20. data/lib/net/snmp/agent/provider_dsl.rb +124 -0
  21. data/lib/net/snmp/agent/request_dispatcher.rb +38 -0
  22. data/lib/net/snmp/constants.rb +287 -0
  23. data/lib/net/snmp/debug.rb +54 -0
  24. data/lib/net/snmp/dispatcher.rb +108 -0
  25. data/lib/net/snmp/error.rb +29 -0
  26. data/lib/net/snmp/listener.rb +76 -0
  27. data/lib/net/snmp/message.rb +142 -0
  28. data/lib/net/snmp/mib/mib.rb +67 -0
  29. data/lib/net/snmp/mib/module.rb +39 -0
  30. data/lib/net/snmp/mib/node.rb +122 -0
  31. data/lib/net/snmp/mib/templates.rb +48 -0
  32. data/lib/net/snmp/oid.rb +134 -0
  33. data/lib/net/snmp/pdu.rb +235 -0
  34. data/lib/net/snmp/repl/manager_repl.rb +243 -0
  35. data/lib/net/snmp/session.rb +560 -0
  36. data/lib/net/snmp/trap_handler/trap_handler.rb +42 -0
  37. data/lib/net/snmp/trap_handler/v1_trap_dsl.rb +44 -0
  38. data/lib/net/snmp/trap_handler/v2_trap_dsl.rb +38 -0
  39. data/lib/net/snmp/trap_session.rb +92 -0
  40. data/lib/net/snmp/utility.rb +10 -0
  41. data/lib/net/snmp/varbind.rb +57 -0
  42. data/lib/net/snmp/version.rb +5 -0
  43. data/lib/net/snmp/wrapper.rb +450 -0
  44. data/net-snmp2.gemspec +30 -0
  45. data/spec/README.md +105 -0
  46. data/spec/async_spec.rb +123 -0
  47. data/spec/em_spec.rb +23 -0
  48. data/spec/error_spec.rb +34 -0
  49. data/spec/fiber_spec.rb +41 -0
  50. data/spec/mib_spec.rb +68 -0
  51. data/spec/net-snmp_spec.rb +18 -0
  52. data/spec/oid_spec.rb +21 -0
  53. data/spec/spec_helper.rb +10 -0
  54. data/spec/sync_spec.rb +132 -0
  55. data/spec/thread_spec.rb +19 -0
  56. data/spec/trap_spec.rb +45 -0
  57. data/spec/utility_spec.rb +10 -0
  58. data/spec/wrapper_spec.rb +69 -0
  59. metadata +166 -0
@@ -0,0 +1,30 @@
1
+ # -*- encoding: utf-8 -*-
2
+ lib = File.expand_path("../lib", __FILE__)
3
+ $:.unshift lib
4
+ require 'net/snmp/version'
5
+
6
+ Gem::Specification.new do |s|
7
+ s.name = "net-snmp2"
8
+ s.version = Net::SNMP::VERSION
9
+ s.platform = Gem::Platform::RUBY
10
+ s.authors = ["Ron McClain", "Jared Breeden"]
11
+ s.email = ["jared.breeden@gmail.com"]
12
+ s.homepage = "https://github.com/jbreeden/net-snmp2"
13
+ s.summary = %q{Object oriented wrapper around C net-snmp libraries}
14
+ s.description = %q{Cross platform net-snmp wrapper for Ruby, building on the original net-snmp gem}
15
+
16
+ s.files = `git ls-files`.split("\n")
17
+ s.test_files = `git ls-files -- {test,spec,features}/*`.split("\n")
18
+ s.executables = `git ls-files -- bin/*`.split("\n").map{ |f| File.basename(f) }
19
+ s.require_paths = ["lib"]
20
+
21
+ # Documentation options
22
+ s.has_rdoc = true
23
+ s.extra_rdoc_files = %w{ README.md }
24
+ s.rdoc_options = ["--main=README.md", "--line-numbers", "--inline-source", "--title=#{s.name}-#{s.version} Documentation"]
25
+
26
+ s.add_dependency 'nice-ffi'
27
+ s.add_dependency 'pry'
28
+ s.add_development_dependency "rspec"
29
+ s.add_development_dependency "eventmachine"
30
+ end
@@ -0,0 +1,105 @@
1
+ Notes
2
+ -----
3
+
4
+ - To test sets, you have to have a local snmpd running with write permissions
5
+ - For your local agent, use read community "public" & write community "private"
6
+ - A free simulator can be downloaded from [veraxsystems](http://www.veraxsystems.com/en/products/free-snmp-agent-simulator)
7
+ + TODO: This simulator could be used to replace the dependency on test.net-snmp.org
8
+
9
+ Latest Results
10
+ --------------
11
+
12
+ Generated with `rspec -f d -o spec/spec.txt --no-color`
13
+
14
+ ```
15
+ async
16
+ version 1
17
+ get should work
18
+ get should return an error
19
+ getnext should work
20
+ version 2
21
+ get should work
22
+ getnext should work
23
+ version 3
24
+ should get async using snmpv3
25
+ get should work
26
+ getnext should work
27
+
28
+ em
29
+ should work in event_machine
30
+
31
+ snmp errors
32
+ should rescue a timeout error
33
+ should rescue timeout error in a fiber
34
+
35
+ in fiber
36
+ get should work in a fiber with synchronous calling style
37
+ getnext
38
+ should get using snmpv3
39
+
40
+ Net::SNMP::MIB::Node
41
+ should get info for sysDescr
42
+ should get parent
43
+ should get node children
44
+ should get siblings
45
+ should get oid
46
+ should get by oid
47
+ should do stuff
48
+
49
+ Net::SNMP::OID
50
+ should instantiate valid oid with numeric
51
+ should instantiate valid oid with string
52
+ should to_s correctly
53
+
54
+ synchronous calls
55
+ version 1
56
+ get should succeed
57
+ multiple calls within session should succeed
58
+ get should succeed with multiple oids
59
+ set should succeed
60
+ getnext should succeed
61
+ getbulk should succeed
62
+ getbulk should succeed with multiple oids
63
+ get should return error with invalid oid
64
+ get_table should work
65
+ walk should work
66
+ walk should work with multiple oids
67
+ get_columns should work
68
+ get a value with oid type should work
69
+ version 3
70
+ should get using snmpv3
71
+ should set using snmpv3 (PENDING: No reason given)
72
+ should get using authpriv (PENDING: No reason given)
73
+
74
+ in a thread
75
+ should get an oid asynchronously in a thread
76
+
77
+ snmp traps
78
+ should send a v1 trap
79
+ should send a v2 inform (PENDING: still working on it)
80
+ should send v2 trap (PENDING: still working on it)
81
+
82
+ Net::SNMP::Utility
83
+ should compare oids
84
+
85
+ Net::SNMP::Wrapper
86
+ wrapper should snmpget synchronously
87
+ wrapper should snmpget asynchronously
88
+
89
+ Pending:
90
+ synchronous calls version 3 should set using snmpv3
91
+ # No reason given
92
+ # ./spec/sync_spec.rb:117
93
+ synchronous calls version 3 should get using authpriv
94
+ # No reason given
95
+ # ./spec/sync_spec.rb:125
96
+ snmp traps should send a v2 inform
97
+ # still working on it
98
+ # ./spec/trap_spec.rb:14
99
+ snmp traps should send v2 trap
100
+ # still working on it
101
+ # ./spec/trap_spec.rb:26
102
+
103
+ Finished in 25.41 seconds (files took 0.38735 seconds to load)
104
+ 47 examples, 0 failures, 4 pending
105
+ ```
@@ -0,0 +1,123 @@
1
+ require File.expand_path(File.dirname(__FILE__) + '/spec_helper')
2
+
3
+ describe "async" do
4
+ context "version 1" do
5
+ it "get should work" do
6
+ did_callback = false
7
+ sess = Net::SNMP::Session.open(:peername => 'test.net-snmp.org', :community => 'demopublic') do |s|
8
+ s.get(["sysDescr.0", "sysContact.0"]) do |op, pdu|
9
+ did_callback = true
10
+ pdu.varbinds[0].value.should eql("test.net-snmp.org")
11
+ pdu.varbinds[1].value.should match(/Coders/)
12
+ end
13
+ end
14
+ Net::SNMP::Dispatcher.select(false)
15
+ did_callback.should be(true)
16
+ end
17
+
18
+ it "get should return an error" do
19
+ did_callback = false
20
+ sess = Net::SNMP::Session.open(:peername => 'www.yahoo.com', :timeout => 1, :retries => 0) do |sess|
21
+ sess.get("sysDescr.0") do |op, pdu|
22
+ did_callback = true
23
+ op.should eql(:timeout)
24
+ end
25
+ end
26
+ sleep 2
27
+ pdu = sess.select(10)
28
+
29
+ pdu.should eql(0)
30
+ did_callback.should eq(true)
31
+ end
32
+
33
+ it "getnext should work" do
34
+ did_callback = false
35
+ Net::SNMP::Session.open(:peername => 'test.net-snmp.org', :community => 'demopublic') do |s|
36
+ s.get_next(["sysDescr", "sysContact"]) do |op, pdu|
37
+ did_callback = true
38
+ pdu.varbinds[0].value.should eql("test.net-snmp.org")
39
+ pdu.varbinds[1].value.should match(/Coders/)
40
+ end
41
+ end
42
+ Net::SNMP::Dispatcher.select(false)
43
+ did_callback.should be(true)
44
+ end
45
+ end
46
+
47
+ context "version 2" do
48
+ it "get should work" do
49
+ did_callback = false
50
+ Net::SNMP::Session.open(:peername => 'test.net-snmp.org', :community => 'demopublic', :version => '2c') do |s|
51
+ s.get(["sysDescr.0", "sysContact.0"]) do |op, pdu|
52
+ did_callback = true
53
+ pdu.varbinds[0].value.should eql("test.net-snmp.org")
54
+ pdu.varbinds[1].value.should match(/Coders/)
55
+ end
56
+ end
57
+ Net::SNMP::Dispatcher.select(false)
58
+ did_callback.should be(true)
59
+ end
60
+
61
+ it "getnext should work" do
62
+ did_callback = false
63
+ Net::SNMP::Session.open(:peername => 'test.net-snmp.org', :community => 'demopublic', :version => '2c') do |s|
64
+ s.get_next(["sysDescr", "sysContact"]) do |op, pdu|
65
+ did_callback = true
66
+ pdu.varbinds[0].value.should eql("test.net-snmp.org")
67
+ pdu.varbinds[1].value.should match(/Coders/)
68
+ end
69
+ end
70
+ Net::SNMP::Dispatcher.select(false)
71
+ did_callback.should be(true)
72
+ end
73
+
74
+ end
75
+
76
+ context "version 3" do
77
+ #failing intermittently
78
+ it "should get async using snmpv3" do
79
+ did_callback = false
80
+ Net::SNMP::Session.open(:peername => 'test.net-snmp.org', :version => 3, :username => 'MD5User',:security_level => Net::SNMP::Constants::SNMP_SEC_LEVEL_AUTHNOPRIV, :auth_protocol => :md5, :password => 'The Net-SNMP Demo Password') do |sess|
81
+ sess.get(["sysDescr.0"]) do |op, pdu|
82
+ did_callback = true
83
+ pdu.varbinds[0].value.should eql('test.net-snmp.org')
84
+ end
85
+ sleep(0.5)
86
+ Net::SNMP::Dispatcher.select(false)
87
+ #Net::SNMP::Dispatcher.select(false)
88
+ #puts "done select"
89
+ did_callback.should be(true)
90
+ end
91
+ end
92
+
93
+ it "get should work" do
94
+ did_callback = false
95
+ sess = Net::SNMP::Session.open(:peername => 'test.net-snmp.org', :version => 3, :username => 'MD5User',:security_level => Net::SNMP::Constants::SNMP_SEC_LEVEL_AUTHNOPRIV, :auth_protocol => :md5, :password => 'The Net-SNMP Demo Password') do |sess|
96
+ sess.get(["sysDescr.0", "sysContact.0"]) do |op,pdu|
97
+ did_callback = true
98
+ pdu.varbinds[0].value.should eql("test.net-snmp.org")
99
+ pdu.varbinds[1].value.should match(/Coders/)
100
+ end
101
+ end
102
+ Net::SNMP::Dispatcher.select(false)
103
+ sess.close
104
+ did_callback.should be(true)
105
+ end
106
+
107
+ # XXX occasionally segfaulting
108
+ it "getnext should work" do
109
+ did_callback = false
110
+
111
+ sess = Net::SNMP::Session.open(:peername => 'test.net-snmp.org', :version => 3, :username => 'MD5User',:security_level => Net::SNMP::Constants::SNMP_SEC_LEVEL_AUTHNOPRIV, :auth_protocol => :md5, :password => 'The Net-SNMP Demo Password') do |sess|
112
+ sess.get_next(["sysDescr", "sysContact"]) do |op, pdu|
113
+ did_callback = true
114
+ pdu.varbinds[0].value.should eql("test.net-snmp.org")
115
+ pdu.varbinds[1].value.should match(/Coders/)
116
+ end
117
+ end
118
+ Net::SNMP::Dispatcher.select(false)
119
+ sess.close
120
+ did_callback.should be(true)
121
+ end
122
+ end
123
+ end
@@ -0,0 +1,23 @@
1
+ require File.expand_path(File.dirname(__FILE__) + '/spec_helper')
2
+ require 'eventmachine'
3
+
4
+ describe "em" do
5
+ it "should work in event_machine" do
6
+ did_callback = false
7
+ EM.run do
8
+ Net::SNMP::Dispatcher.em_loop
9
+
10
+ session = Net::SNMP::Session.open(:peername => 'test.net-snmp.org', :community => 'demopublic') do |s|
11
+ s.get("sysDescr.0") do |op, result|
12
+ did_callback = true
13
+ result.varbinds[0].value.should eql("test.net-snmp.org")
14
+ end
15
+ end
16
+
17
+ EM.add_timer(3) do
18
+ did_callback.should eq(true)
19
+ EM.stop
20
+ end
21
+ end
22
+ end
23
+ end
@@ -0,0 +1,34 @@
1
+ require File.expand_path(File.dirname(__FILE__) + '/spec_helper')
2
+ require 'eventmachine'
3
+
4
+ describe "snmp errors" do
5
+ it "should rescue a timeout error" do
6
+ Net::SNMP::Session.open(:peername => 'www.yahoo.com') do |sess|
7
+ begin
8
+ sess.get("sysDescr.0")
9
+ rescue Net::SNMP::Error => e
10
+ e.print
11
+ e.status.should eql(Net::SNMP::Constants::STAT_TIMEOUT)
12
+ end
13
+ end
14
+ end
15
+
16
+ it "should rescue timeout error in a fiber" do
17
+ got_error = false
18
+ EM.run {
19
+ Fiber.new {
20
+ Net::SNMP::Dispatcher.fiber_loop
21
+ Net::SNMP::Session.open(:peername => 'www.yahoo.com') do |sess|
22
+ begin
23
+ sess.get("sysDescr.0")
24
+ rescue Net::SNMP::TimeoutError => e
25
+ got_error = true
26
+ end
27
+ end
28
+ EM.stop
29
+ }.resume(nil)
30
+ }
31
+ got_error.should eq(true)
32
+ end
33
+
34
+ end
@@ -0,0 +1,41 @@
1
+ require File.expand_path(File.dirname(__FILE__) + '/spec_helper')
2
+ require 'eventmachine'
3
+ require 'fiber'
4
+
5
+ describe "in fiber" do
6
+
7
+ def wrap_fiber
8
+ EM.run do
9
+ Net::SNMP::Dispatcher.fiber_loop
10
+ Fiber.new { yield; EM.stop }.resume(nil)
11
+ end
12
+ end
13
+
14
+ it "get should work in a fiber with synchronous calling style" do
15
+ wrap_fiber do
16
+ session = Net::SNMP::Session.open(:peername => 'test.net-snmp.org', :community => 'demopublic')
17
+ result = session.get("sysDescr.0")
18
+ result.varbinds[0].value.should eql("test.net-snmp.org")
19
+ end
20
+ end
21
+
22
+ it "getnext" do
23
+ wrap_fiber do
24
+ Net::SNMP::Session.open(:peername => "test.net-snmp.org", :community => "demopublic" ) do |sess|
25
+ result = sess.get_next(["sysUpTimeInstance.0"])
26
+ result.varbinds.first.oid.oid.should eql("1.3.6.1.2.1.1.4.0")
27
+ result.varbinds.first.value.should match(/Net-SNMP Coders/)
28
+ end
29
+ end
30
+ end
31
+
32
+ it "should get using snmpv3" do
33
+ wrap_fiber do
34
+ Net::SNMP::Session.open(:peername => 'test.net-snmp.org', :version => 3, :username => 'MD5User', :security_level => Net::SNMP::Constants::SNMP_SEC_LEVEL_AUTHNOPRIV, :auth_protocol => :md5, :password => 'The Net-SNMP Demo Password') do |sess|
35
+ result = sess.get(["sysDescr.0"])
36
+ result.varbinds.first.value.should eql('test.net-snmp.org')
37
+ end
38
+ end
39
+ end
40
+
41
+ end
@@ -0,0 +1,68 @@
1
+ require File.expand_path(File.dirname(__FILE__) + '/spec_helper')
2
+
3
+ describe Net::SNMP::MIB do
4
+ describe '::translate' do
5
+ it "translates OIDs to variable names including instance indexes" do
6
+ expect(Net::SNMP::MIB.translate('sysContact.0')).to eql '1.3.6.1.2.1.1.4.0'
7
+ end
8
+
9
+ it "translates variable names to OIDs including instance indexes" do
10
+ expect(Net::SNMP::MIB.translate('1.3.6.1.2.1.1.4.0')).to eql 'sysContact.0'
11
+ end
12
+ end
13
+
14
+ describe '::[]' do
15
+ it "can retrieve MIB nodes by variable name" do
16
+ node = Net::SNMP::MIB["sysDescr"]
17
+ node.label.should eq("sysDescr")
18
+ end
19
+
20
+ it "can retrieve MIB nodes by numeric oid" do
21
+ node = Net::SNMP::MIB["1.3.6.1.2.1.1.1"]
22
+ node.label.should eq("sysDescr")
23
+ end
24
+ end
25
+ end
26
+
27
+ describe Net::SNMP::MIB::Node do
28
+ describe "::get_node" do
29
+ it "retrieves MIB nodes by variable name" do
30
+ node = Net::SNMP::MIB::Node.get_node("sysDescr")
31
+ node.label.should eq("sysDescr")
32
+ end
33
+
34
+ it "retrieves MIB nodes by numeric oid" do
35
+ node = Net::SNMP::MIB::Node.get_node("1.3.6.1.2.1.1.1")
36
+ node.label.should eq("sysDescr")
37
+ end
38
+ end
39
+
40
+ describe "#parent" do
41
+ it "links to the parent node" do
42
+ node = Net::SNMP::MIB::Node.get_node("sysDescr")
43
+ node.parent.label.should eq("system")
44
+ end
45
+ end
46
+
47
+ describe "#children" do
48
+ it "contains Node objects for all child nodes" do
49
+ node = Net::SNMP::MIB::Node.get_node("ifTable")
50
+ if_entry = node.children.first
51
+ if_entry.children.should include { |n| n.label == "ifIndex" }
52
+ end
53
+ end
54
+
55
+ describe "#siblings" do
56
+ it "contains an array of sibling nodes" do
57
+ node = Net::SNMP::MIB::Node.get_node("sysDescr")
58
+ node.siblings.should include { |n| n.label == "sysName" }
59
+ end
60
+ end
61
+
62
+ describe "#oid" do
63
+ it "is an OID object for the node" do
64
+ node = Net::SNMP::MIB::Node.get_node("sysDescr")
65
+ node.oid.to_s.should eq("1.3.6.1.2.1.1.1")
66
+ end
67
+ end
68
+ end
@@ -0,0 +1,18 @@
1
+ require File.expand_path(File.dirname(__FILE__) + '/spec_helper')
2
+
3
+ describe "NetSnmp" do
4
+
5
+
6
+
7
+ # it "should get columns" do
8
+ # Net::SNMP::Session.open(:peername => 'localhost', :version => '2c', :community => 'public') do |sess|
9
+ # result = sess.get_columns(['ifIndex', 'ifInOctets', 'ifOutOctets'])
10
+ # result.size.should eql(7)
11
+ # result['1']['ifIndex'].should eql('1')
12
+ # result['2']['ifInOctets'].should be > 10
13
+ # end
14
+ # end
15
+
16
+
17
+
18
+ end