riscos 0.1.1 → 0.1.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- data/lib/riscos.rb +177 -78
- metadata +5 -5
data/lib/riscos.rb
CHANGED
@@ -1,12 +1,12 @@
|
|
1
1
|
require 'expect'
|
2
2
|
require 'pty'
|
3
|
+
|
3
4
|
module Cisco
|
4
5
|
|
5
6
|
class Base
|
6
7
|
attr_accessor :timeout, :prompt, :output, :info
|
7
8
|
|
8
9
|
def initialize(options)
|
9
|
-
|
10
10
|
@host = options[:host] || "nil"
|
11
11
|
@user = options[:user] || "nil"
|
12
12
|
@pw = options[:pw] || "nil" #login pass
|
@@ -15,57 +15,52 @@ module Cisco
|
|
15
15
|
@w = "/dev/null" #writer socket
|
16
16
|
@p = nil #pid to kill later
|
17
17
|
@prompt = /\r\n\r.*[#>]\s?\z/n
|
18
|
-
@timeout =
|
18
|
+
@timeout = 10
|
19
19
|
@output = Array.new
|
20
|
-
@info = Array.new
|
20
|
+
@info = Array.new #store configuration info gleaned from config
|
21
|
+
@error = Array.new
|
21
22
|
end
|
22
|
-
|
23
|
+
# Quickly logs into the device.
|
24
|
+
#
|
25
|
+
# * runs a login, enable, and conft to get you where you need to be
|
23
26
|
def loginquick()
|
24
27
|
self.login
|
25
28
|
self.enable
|
26
29
|
self.conft
|
27
30
|
end
|
28
|
-
|
29
|
-
|
30
|
-
|
31
|
-
def enable()
|
32
|
-
begin
|
31
|
+
# Turns on enable or superuser mode on the device.
|
32
|
+
#
|
33
|
+
# * gives you the ability to use the superuser's console
|
34
|
+
def enable()
|
33
35
|
@w.print("enable\n")
|
34
|
-
|
35
|
-
read(@r,@timeout, @prompt)
|
36
|
-
rescue Exception => ee
|
37
|
-
@info.push("ERROR: Exception for host in enable:#{ee.to_s}\n")
|
38
|
-
end
|
36
|
+
run(@enpw)
|
39
37
|
end
|
40
|
-
|
38
|
+
# Turns on 'configuration mode' on the device
|
39
|
+
#
|
40
|
+
# * gives you the set system parameters on the device
|
41
41
|
def conft()
|
42
|
-
|
43
|
-
|
44
|
-
read(@r,@timeout, @prompt)
|
45
|
-
@w.print("pager 0 \n")
|
46
|
-
read(@r,@timeout, @prompt)
|
47
|
-
rescue Exception => ee
|
48
|
-
@info.push("ERROR: Exception for host in conft :#{ee.to_s}\n")
|
49
|
-
end
|
50
|
-
|
42
|
+
run("conf t")
|
43
|
+
run("pager 0")
|
51
44
|
end
|
52
|
-
|
53
|
-
|
45
|
+
# Runs a technical diagnostic on the device. This outputs a lot of information.
|
46
|
+
#
|
47
|
+
# * this is basically one command that gives you almost everything you'd ever want to know
|
54
48
|
def showtech()
|
55
|
-
|
56
|
-
@w.print("show tech\n")
|
57
|
-
#it would be real nice to take this then populate the information about the device
|
58
|
-
read(@r,@timeout, @prompt)
|
59
|
-
rescue Exception => ee
|
60
|
-
@info.push("ERROR: Exception for host in show tech:#{ee.to_s}\n")
|
61
|
-
end
|
49
|
+
run("show tech")
|
62
50
|
end
|
63
|
-
|
64
|
-
|
51
|
+
# Lets us read the command line output of the device. If we error, we return the error in the @error array and the command that failed. We
|
52
|
+
# will also close the reading and writing sockets if we get a timeout. If we don't we end up with stray ruby processes.
|
53
|
+
#
|
54
|
+
# * these can change for each call
|
55
|
+
# * @r is the reader socket
|
56
|
+
# * @timeout is how log we want to wait for this particular read
|
57
|
+
# * @prompt is the prompt we'll wait for on this read
|
58
|
+
def read(r=@r,timeout=@timeout,prompt=@prompt)
|
59
|
+
|
65
60
|
begin
|
66
|
-
r.expect(
|
61
|
+
r.expect(prompt,timeout) do |rec|
|
67
62
|
if rec == nil then
|
68
|
-
@
|
63
|
+
@error.push("ERROR: Timeout talking to device")
|
69
64
|
close()
|
70
65
|
else
|
71
66
|
@output.push(rec)
|
@@ -73,96 +68,200 @@ module Cisco
|
|
73
68
|
end
|
74
69
|
end
|
75
70
|
rescue Exception => ee
|
76
|
-
@
|
71
|
+
@error.push "ERROR:Exception trying to read stream: #{ee.to_s}"
|
77
72
|
return @output
|
78
73
|
end
|
79
|
-
|
80
74
|
end
|
75
|
+
# Logout of the device
|
76
|
+
#
|
77
|
+
#
|
81
78
|
|
82
79
|
def logout()
|
83
|
-
|
84
|
-
|
85
|
-
|
86
|
-
@w.print("write mem\n")
|
87
|
-
read(@r,@timeout, @prompt)
|
88
|
-
@w.print("exit\n")
|
89
|
-
rescue Exception => ee
|
90
|
-
@info.push("ERROR: Exception for host in logout:#{ee.to_s}\n\nAlready closed connection?")
|
91
|
-
end
|
80
|
+
run("pager 30")
|
81
|
+
run("write mem")
|
82
|
+
@w.print("exit")
|
92
83
|
end
|
93
84
|
|
94
|
-
|
95
|
-
|
85
|
+
# Individual commands to run on the device. These would be good for scripts and batch processes.
|
86
|
+
#
|
87
|
+
# * cmd is the command you're sending to the device
|
88
|
+
# * @prompt is the particular prompt we're going to look for. We do a "read" after each run and return the output from the device
|
89
|
+
def run(cmd,prompt=@prompt)
|
96
90
|
begin
|
97
91
|
@w.print("#{cmd}\n")
|
98
|
-
buffer
|
92
|
+
buffer = read(@r,@timeout,prompt)
|
99
93
|
rescue Exception => ee
|
100
|
-
@
|
94
|
+
@error.push("ERROR: Exception for host while executing #{cmd}: #{ee.to_s}")
|
101
95
|
end
|
102
96
|
return buffer
|
103
97
|
end
|
104
98
|
|
99
|
+
# Close the connection. We're through.
|
100
|
+
#
|
101
|
+
# * close the sockets then kill the pid to make sure.
|
102
|
+
|
105
103
|
def close
|
106
|
-
|
107
104
|
begin
|
108
105
|
@w.close
|
109
106
|
@r.close
|
110
107
|
#just to be sure, nuke it
|
111
108
|
Process.kill(:SIGKILL, @p)
|
112
|
-
|
113
109
|
@output.push("connection closed")
|
114
110
|
rescue Exception => ee
|
115
|
-
@
|
111
|
+
@error.push("ERROR: Problem closing connection: #{ee.to_s}")
|
116
112
|
end
|
117
113
|
end
|
118
|
-
|
119
|
-
|
120
114
|
end
|
121
115
|
|
122
116
|
class Asa < Base
|
117
|
+
|
118
|
+
# Login specific to ASAs and FWSMs (since they behave just like ASAs)
|
119
|
+
#
|
120
|
+
#
|
123
121
|
def login()
|
124
122
|
cmd="ssh -o StrictHostKeyChecking=no #{@user}@#{@host}\n"
|
125
123
|
begin
|
126
124
|
PTY.spawn(cmd) do |r,w,p|
|
127
125
|
@r,@w,@p=r,w,p
|
128
126
|
read(@r,@timeout, "word:")
|
129
|
-
|
130
|
-
read(@r,@timeout, @prompt)
|
127
|
+
run(@pw)
|
131
128
|
end
|
132
129
|
|
133
130
|
rescue Exception => ee
|
134
|
-
@
|
131
|
+
@error.push("ERROR: Exception for host in login:#{ee.to_s}\n\nBad ip address?")
|
135
132
|
end
|
136
133
|
end
|
137
|
-
|
138
|
-
|
139
|
-
|
140
134
|
end
|
141
135
|
|
136
|
+
# Login specific to Pixes (since they behave differently than ASAs.)
|
137
|
+
#
|
138
|
+
#
|
142
139
|
|
143
140
|
class Pix < Base
|
144
141
|
|
145
142
|
def login()
|
146
143
|
cmd="ssh -o StrictHostKeyChecking=no #{@user}@#{@host}\n"
|
147
|
-
|
148
|
-
|
149
|
-
|
150
|
-
|
151
|
-
|
152
|
-
|
153
|
-
|
154
|
-
|
155
|
-
|
156
|
-
|
144
|
+
PTY.spawn(cmd) do |r,w,p|
|
145
|
+
@r,@w,@p=r,w,p
|
146
|
+
read(@r,@timeout, "word:")
|
147
|
+
run(@pw)
|
148
|
+
read()
|
149
|
+
#Pix adds an extra <CR> on login, so we remove it for you
|
150
|
+
@output.pop
|
151
|
+
end
|
152
|
+
end
|
153
|
+
end
|
154
|
+
|
155
|
+
|
156
|
+
## these are still being developed.
|
157
|
+
class Css < Base
|
158
|
+
attr_accessor :owner, :service, :sslproxy, :sslfiles
|
159
|
+
|
160
|
+
def initialize(options)
|
161
|
+
super(options)
|
162
|
+
@owner = Hash.new{|h,k| h[k]=Hash.new(&h.default_proc) }
|
163
|
+
@service = Array.new
|
164
|
+
@sslproxy = Hash.new{|h,k| h[k]=Hash.new(&h.default_proc) }
|
165
|
+
@sslfiles = Array.new
|
166
|
+
end
|
167
|
+
|
168
|
+
def login
|
169
|
+
cmd="ssh -o StrictHostKeyChecking=no #{@host}"
|
170
|
+
PTY.spawn(cmd) do |r,w,p|
|
171
|
+
@r,@w,@p=r,w,p
|
172
|
+
read(@r,@timeout, "name:")
|
173
|
+
run(@user, "word:")
|
174
|
+
run(@pw)
|
175
|
+
run("terminal length 65535")
|
176
|
+
end
|
177
|
+
end
|
178
|
+
|
179
|
+
def logout()
|
180
|
+
run("terminal length 30")
|
181
|
+
run("write mem")
|
182
|
+
@w.print("exit")
|
183
|
+
end
|
184
|
+
|
185
|
+
# Runs a 'show service summary' on the related CSS.
|
186
|
+
#
|
187
|
+
# * the output is parsed into Service Name
|
188
|
+
# * next field is State
|
189
|
+
# * next field is Conn
|
190
|
+
# * next field is Weight
|
191
|
+
# * next field is Avg Load
|
192
|
+
# * last field is State Transitions
|
193
|
+
|
194
|
+
def showservices
|
195
|
+
s = run("show service summary")
|
196
|
+
#s = read()
|
197
|
+
s=s.first.split("\r\r\r\n")
|
198
|
+
s[5..-2].each do |l|
|
199
|
+
@service.push(l.split)
|
200
|
+
end
|
201
|
+
end
|
202
|
+
|
203
|
+
def owners
|
204
|
+
o = run("show run owner")
|
205
|
+
o = o.first.split("\r\r\r\n")
|
206
|
+
# we need to chomp the first and last lines
|
207
|
+
o.delete_at(0)
|
208
|
+
o.delete_at(-1)
|
209
|
+
#change to when/case
|
210
|
+
o[2..-1].each do |l|
|
211
|
+
next if l.empty?
|
212
|
+
l = l.split
|
213
|
+
line = case l
|
214
|
+
when /^owner/
|
215
|
+
@ow=l.last
|
216
|
+
@owner[@ow]
|
217
|
+
when /content/
|
218
|
+
@serv=[]
|
219
|
+
@co=l.last
|
220
|
+
@owner[@ow][@co]
|
221
|
+
when /^active/
|
222
|
+
@owner[@ow][@co][l.first]=true
|
223
|
+
when /add service/
|
224
|
+
@serv.push(l.last)
|
225
|
+
@owner[@ow][@co]["add service"]=@serv
|
226
|
+
else
|
227
|
+
@owner[@ow][@co][l[0..-2].to_s]=l.last
|
228
|
+
end
|
157
229
|
end
|
230
|
+
end
|
231
|
+
|
232
|
+
def sslproxies
|
233
|
+
s= run("show run ssl-proxy-list")
|
234
|
+
s=s.first.split("\r\r\r\n")
|
235
|
+
s[3..-2].each do |l|
|
236
|
+
l=l.split
|
237
|
+
#puts l
|
238
|
+
line = case l.first
|
239
|
+
when /ssl-proxy-list/
|
240
|
+
@proxy=l.last
|
241
|
+
@sslproxy[l.last]
|
242
|
+
when /^active/
|
243
|
+
@sslproxy[@proxy]["active"]=true
|
244
|
+
when /ssl-server/
|
245
|
+
@details=[]
|
246
|
+
@server=l[1]
|
247
|
+
@sslproxy[@proxy][@server]
|
248
|
+
when /.*?\\s.*?/
|
249
|
+
puts "here"
|
250
|
+
@details.push((l.last[2..-1].collect {|x| x + " " }).to_s)
|
251
|
+
# @details.delete("")
|
252
|
+
@sslproxy[@proxy][@server]=@details
|
158
253
|
|
159
|
-
|
160
|
-
@
|
161
|
-
end
|
254
|
+
else
|
255
|
+
@sslproxy[@proxy]["active"]=false
|
256
|
+
end
|
162
257
|
end
|
163
|
-
|
164
|
-
|
258
|
+
end
|
259
|
+
|
260
|
+
def sslfile
|
261
|
+
@sslfiles = run("show ssl files")
|
165
262
|
|
166
263
|
end
|
264
|
+
|
265
|
+
end
|
167
266
|
|
168
267
|
end
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: riscos
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.1.
|
4
|
+
version: 0.1.2
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Paul Voccio
|
@@ -9,11 +9,11 @@ autorequire:
|
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
11
|
|
12
|
-
date: 2009-
|
12
|
+
date: 2009-02-16 00:00:00 -06:00
|
13
13
|
default_executable:
|
14
14
|
dependencies: []
|
15
15
|
|
16
|
-
description: Provides a common easy to use interface to talk to Cisco Pix and Cisco
|
16
|
+
description: Provides a common easy to use interface to talk to Cisco Pix, ASA, FWSM and Cisco CSSes.
|
17
17
|
email: paul@substation9.com
|
18
18
|
executables: []
|
19
19
|
|
@@ -26,7 +26,7 @@ files:
|
|
26
26
|
- Changelog
|
27
27
|
- LICENSE
|
28
28
|
- lib/riscos.rb
|
29
|
-
has_rdoc:
|
29
|
+
has_rdoc: true
|
30
30
|
homepage: http://riscos.rubyforge.org/
|
31
31
|
post_install_message:
|
32
32
|
rdoc_options: []
|
@@ -51,6 +51,6 @@ rubyforge_project: riscos
|
|
51
51
|
rubygems_version: 1.3.1
|
52
52
|
signing_key:
|
53
53
|
specification_version: 2
|
54
|
-
summary: Provides a common easy to use interface to talk to Cisco Pix and Cisco
|
54
|
+
summary: Provides a common easy to use interface to talk to Cisco Pix, ASA, FWSM and Cisco CSSes.
|
55
55
|
test_files: []
|
56
56
|
|