mtik 4.0.5 → 4.1.0

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.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 0c85bb344286cb8faf3504f84bb617a6af422a5703972e8b9795601c2bc0b0ee
4
- data.tar.gz: 9f727afa04a97fc3b366c54c637b6ba5274a057a9b460188022a2dc986ce0dca
3
+ metadata.gz: 5ce416fc9ce5a6d6768f40c11b68fc983fcf75ba69e10e3bc660a0b405fc1bcc
4
+ data.tar.gz: 910a34bcb91770ea3f5607fd91297fa1d518f0020e35e27e810deb4eb797cd71
5
5
  SHA512:
6
- metadata.gz: 0ceb27e8ea2f409882128ace3557563987f4e3a4d140d504e304ed903c51ef9025b4fd4aab6a3efbfb52063a7008a59f029e48ef8d094c7e0ceca6d153bc2c41
7
- data.tar.gz: 9ac0bd5e67ad3004c427637edb3436f96eec96298678b440b76cdd9582bf3ca98e3dc000a1c3e3990761236b9f3858633b72f785b4a931d980d67d3fdab2353a
6
+ metadata.gz: 86879188b9b9af32b1d61f61d3c539a3f8482ef1da078f4a347ea548e1480e0c5b6502d73784a7acda610a17d4b6be141dae93a20b07c1c85959aec538834be5
7
+ data.tar.gz: 6778bcf64f479677ccdaec744a8356b936527471870e21aa6878749ceb22d79d43452415113a2e15de4d4be0bbc133d7a32b1d0c7d70807cf7066eb94acab91e
@@ -1,3 +1,18 @@
1
+ 2020-08-23 (23 AUG 2020) VERSION 4.1.0
2
+ * Minor version bump due to changing argument passing for the call to
3
+ MTik.interactive_client()
4
+ * Updated tikcli, tikcommand, and tikfetch commands to add options for
5
+ enabling SSL and/or to use unencrypted plaintext logins (newer API
6
+ login style). Also one can set environment variables MTIK_SSL to
7
+ specify SSL use, or MTIK_UNENCRYPTED_PLAINTEXT to enable unencrypted
8
+ plaintext logins if SSL is NOT used for compatibility with cleartext
9
+ API usage on RouterOS versions 6.43+
10
+ * THANKS to Zdenek Crha (zdenek-crha on github) for pointing out that
11
+ the binary commands were lacking proper argument passing to allow
12
+ for SSL and/or unencrypted plaintext options, and for suggesting the
13
+ use of environment variables as an alterative to CLI options for
14
+ enabling such.
15
+
1
16
  2020-08-22 (22 AUG 2020) VERSION 4.0.5
2
17
  * This is a cosmetic version bump for the purpose of updating the gem for wider
3
18
  availability via rubygems in addition to directly from github prior to some
@@ -66,7 +81,7 @@
66
81
  * Fixed RDoc formatting in several files, and added an RDocTask to the Rakefile
67
82
 
68
83
  2010-04-23 (23 APR 2010) VERSION 3.0.5 Aaron D. Gifford (http://www.aarongifford.com)
69
- * Double bug-fix (typo fix and logic fix) to request.rb thanks to Allan Eising and
84
+ * Double bug-fix (typo fix and logic fix) to request.rb thanks to Allan Eising and
70
85
  Søren Daugaard. Thank you both for the patch!
71
86
  * Added a brief sanity-check in request.rb to help spotlight logic errors.
72
87
 
data/README.txt CHANGED
@@ -27,7 +27,7 @@ The latest version of MTik can be found at
27
27
 
28
28
  Ruby RDoc documentation can be found online at
29
29
 
30
- * http://www.aarongifford.com/computers/mtik/latest/doc/
30
+ * http://www.aarongifford.com/computers/mtik/latest/doc/
31
31
 
32
32
  Additional documentation is available at
33
33
 
@@ -1 +1 @@
1
- 4.0.5
1
+ 4.1.0
data/bin/tikcli CHANGED
@@ -42,10 +42,46 @@ $LOAD_PATH.unshift(File.dirname(__FILE__)+'/../lib')
42
42
  require 'rubygems'
43
43
  require 'mtik'
44
44
 
45
- unless ARGV.length == 3
46
- STDERR.print("Usage: #{$0} <host> <user> <pass>\n")
45
+ def usage(msg='')
46
+ STDERR.print(
47
+ (msg.size > 0 ? msg + "\n\n" : '') +
48
+ "Usage: #{$0} [-s|--ssl] [-u|--unencrypted_plaintext] <host> <user> <pass>\n" +
49
+ " --unencrypted_plaintext OR -u - Use the 6.43+ login API even if NOT\n" +
50
+ " using SSL.\n" +
51
+ " --ssl OR -s - Use SSL for the API connection.\n"
52
+ )
47
53
  exit(-1)
48
54
  end
49
55
 
50
- MTik::interactive_client(ARGV[0], ARGV[1], ARGV[2])
56
+ use_ssl = unencrypted_plaintext = false
57
+ while !ARGV[0].nil? && ARGV[0][0] == '-'
58
+ arg = ARGV.shift
59
+ case arg
60
+ when '--ssl', '-s'
61
+ usage("Please do not repeat the --ssl (or -s) parameter") if use_ssl
62
+ use_ssl = true
63
+ when '--unencrypted_plaintext', '-u'
64
+ usage("Please do not repeat the --unencrypted_plaintext (or -u) parameter") if unencrypted_plaintext
65
+ unencrypted_plaintext = true
66
+ else
67
+ usage("Unknown argument #{arg.inspect}")
68
+ end
69
+ end
70
+ usage("Too many arguments.") if ARGV.size > 3
71
+ usage("Insufficient arguments.") if ARGV.size < 3
72
+
73
+ ## Permit setting use_ssl and unencrypted_plaintext via environment variables:
74
+ use_ssl = true if ENV['MTIK_SSL']
75
+ unencrypted_plaintext = true if ENV['MTIK_UNENCRYPTED_PLAINTEXT']
76
+
77
+ args = {
78
+ :host => ARGV[0],
79
+ :user => ARGV[1],
80
+ :pass => ARGV[2],
81
+ :ssl => use_ssl,
82
+ :unencrypted_plaintext => unencrypted_plaintext
83
+ }
84
+ p args
85
+
86
+ MTik::interactive_client(args)
51
87
 
@@ -42,12 +42,39 @@ $LOAD_PATH.unshift(File.dirname(__FILE__)+'/../lib')
42
42
  require 'rubygems'
43
43
  require 'mtik'
44
44
 
45
- unless ARGV.length > 3
46
- STDERR.print("Usage: #{$0} <host> <user> <pass> <command> [<args>...] [<command> [<args> ...]]\n")
45
+ def usage(msg='')
46
+ STDERR.print(
47
+ (msg.size > 0 ? msg + "\n\n" : '') +
48
+ "Usage: #{$0} [-s|--ssl] [-u|--unencrypted_plaintext] <host> <user> <pass> <command> [<args>...] [<command> [<args> ...]]\n" +
49
+ " --unencrypted_plaintext OR -u - Use the 6.43+ login API even if NOT\n" +
50
+ " using SSL.\n" +
51
+ " --ssl OR -s - Use SSL for the API connection.\n"
52
+ )
47
53
  exit(-1)
48
54
  end
49
55
 
50
- MTik::verbose = true ## Set how you want
56
+ MTik::verbose = true ## Set how verbose you want things
57
+
58
+ use_ssl = unencrypted_plaintext = false
59
+ while !ARGV[0].nil? && ARGV[0][0] == '-'
60
+ arg = ARGV.shift
61
+ case arg
62
+ when '--ssl', '-s'
63
+ usage("Please do not repeat the --ssl (or -s) parameter") if use_ssl
64
+ use_ssl = true
65
+ when '--unencrypted_plaintext', '-u'
66
+ usage("Please do not repeat the --unencrypted_plaintext (or -u) parameter") if unencrypted_plaintext
67
+ unencrypted_plaintext = true
68
+ else
69
+ usage("Unknown argument #{arg.inspect}")
70
+ end
71
+ end
72
+ usage("Too few arguments.") if ARGV.size < 4
73
+ usage("First command must start with a slash '/' character. #{ARGV[3].inspect}") if ARGV[3].nil? || ARGV[3][0] != '/'
74
+
75
+ ## Permit setting use_ssl and unencrypted_plaintext via environment variables:
76
+ use_ssl = true if ENV['MTIK_SSL']
77
+ unencrypted_plaintext = true if ENV['MTIK_UNENCRYPTED_PLAINTEXT']
51
78
 
52
79
  ## Detect multiple command sequences and build an array of arrays
53
80
  ## where each outer array element is a command plus arguments:
@@ -62,10 +89,14 @@ while i < ARGV.length
62
89
  i += 1
63
90
  end
64
91
 
65
- p MTik::command(
66
- :host=>ARGV[0],
67
- :user=>ARGV[1],
68
- :pass=>ARGV[2],
69
- :command=>command
70
- )
92
+ args = {
93
+ :host => ARGV[0],
94
+ :user => ARGV[1],
95
+ :pass => ARGV[2],
96
+ :command => command,
97
+ :ssl => use_ssl,
98
+ :unencrypted_plaintext => unencrypted_plaintext
99
+ }
100
+
101
+ p MTik::command(args)
71
102
 
@@ -46,16 +46,48 @@ require 'mtik'
46
46
  ## output of all API interactions:
47
47
  #MTik::verbose = true
48
48
 
49
- if ARGV.length < 4
50
- print "Usage: #{$0} <device> <user> <pass> <url> [<localfilename> [<url> [<localfilename> ... ]]]\n"
51
- exit
49
+ def usage(msg='')
50
+ STDERR.print(
51
+ (msg.size > 0 ? msg + "\n\n" : '') +
52
+ "Usage: #{$0} [-s|--ssl] [-u|--unencrypted_plaintext] <device> <user> <pass> <url> [<localfilename> [<url> [<localfilename> ... ]]]\n" +
53
+ " --unencrypted_plaintext OR -u - Use the 6.43+ login API even if NOT\n" +
54
+ " using SSL.\n" +
55
+ " --ssl OR -s - Use SSL for the API connection.\n"
56
+ )
57
+ exit(-1)
58
+ end
59
+
60
+ use_ssl = unencrypted_plaintext = false
61
+ while !ARGV[0].nil? && ARGV[0][0] == '-'
62
+ arg = ARGV.shift
63
+ case arg
64
+ when '--ssl', '-s'
65
+ usage("Please do not repeat the --ssl (or -s) parameter") if use_ssl
66
+ use_ssl = true
67
+ when '--unencrypted_plaintext', '-u'
68
+ usage("Please do not repeat the --unencrypted_plaintext (or -u) parameter") if unencrypted_plaintext
69
+ unencrypted_plaintext = true
70
+ else
71
+ usage("Unknown argument #{arg.inspect}")
72
+ end
52
73
  end
74
+ usage("Too few arguments.") if ARGV.size < 4
75
+
76
+ ## Permit setting use_ssl and unencrypted_plaintext via environment variables:
77
+ use_ssl = true if ENV['MTIK_SSL']
78
+ unencrypted_plaintext = true if ENV['MTIK_UNENCRYPTED_PLAINTEXT']
79
+
80
+ args = {
81
+ :host => ARGV.shift,
82
+ :user => ARGV.shift,
83
+ :pass => ARGV.shift,
84
+ :ssl => use_ssl,
85
+ :unencrypted_plaintext => unencrypted_plaintext
86
+ }
87
+
53
88
 
54
- host = ARGV.shift
55
- user = ARGV.shift
56
- pass = ARGV.shift
57
89
  begin
58
- mt = MTik::Connection.new(:host=>host, :user=>user, :pass=>pass)
90
+ mt = MTik::Connection.new(args)
59
91
  rescue Errno::ETIMEDOUT, Errno::ENETUNREACH, Errno::EHOSTUNREACH, MTik::Error => e
60
92
  print ">>> ERROR CONNECTING: #{e}\n"
61
93
  exit
@@ -129,6 +161,7 @@ print "SIZE CREATED FILENAME\n"
129
161
  print "====================================================================\n"
130
162
  mt.get_reply_each('/file/getall') do |req, s|
131
163
  unless s.key?('!done')
164
+ s['size'] = 'directory' if s['type'] == 'directory'
132
165
  print "#{(s['size']+' ')[0,10]} #{s['creation-time']} #{s['name']}\n"
133
166
  end
134
167
  end
@@ -49,7 +49,7 @@ module MTik
49
49
  USER = 'admin'
50
50
  ## Default password to use if none is specified:
51
51
  PASS = ''
52
- ## Connection timeout default -- *NOT USED*
52
+ ## Connection timeout default -- *NOT USED*
53
53
  CONN_TIMEOUT = 60
54
54
  ## Command timeout -- The maximum number of seconds to wait for more
55
55
  ## API data when expecting one or more command responses.
@@ -86,12 +86,30 @@ module MTik
86
86
 
87
87
 
88
88
  ## Act as an interactive client with the device, accepting user
89
- ## input from STDIN.
90
- def self.interactive_client(host, user, pass)
89
+ ## input from STDIN. Arguments are key/value pairs, and are
90
+ ## simply passed directly to MTik::Connection(). The below
91
+ ## documentation is taken directly from MTik::Connection. One
92
+ ## more ## key/value pair style arguments must be specified.
93
+ ## The one ## required argument is the host or IP of the device
94
+ ## to connect to.
95
+ ## +host+:: This is the only _required_ argument. Example:
96
+ ## <i> :host => "rb411.example.org" </i>
97
+ ## +ssl+:: Use SSL to encrypt communications
98
+ ## +port+:: Override the default API port (8728/8729)
99
+ ## +user+:: Override the default API username ('admin')
100
+ ## +pass+:: Override the default API password (blank)
101
+ ## +conn_timeout+:: Override the default connection
102
+ ## timeout (60 seconds)
103
+ ## +cmd_timeout+:: Override the default command timeout
104
+ ## (60 seconds) -- the number of seconds
105
+ ## to wait for additional API input.
106
+ ## +unencrypted_plaintext+:: Attempt to use the 6.43+ login API
107
+ ## even without SSL
108
+ def self.interactive_client(args)
91
109
  old_verbose = MTik::verbose
92
110
  MTik::verbose = true
93
111
  begin
94
- tk = MTik::Connection.new(:host => host, :user => user, :pass => pass)
112
+ tk = MTik::Connection.new(args)
95
113
  rescue MTik::Error, Errno::ECONNREFUSED => e
96
114
  print "=== LOGIN ERROR: #{e.message}\n"
97
115
  exit
@@ -132,7 +150,7 @@ module MTik
132
150
  cmd == '/tool/fetch' && sentence['status'] == 'finished'
133
151
  ) || (maxreply > 0 && count == maxreply)
134
152
  state = 2
135
- req.cancel do |r, s|
153
+ req.cancel do |r, s|
136
154
  state = 1
137
155
  end
138
156
  end
@@ -159,7 +177,7 @@ module MTik
159
177
  end
160
178
  end
161
179
  end
162
-
180
+
163
181
  reply = tk.get_reply('/quit')
164
182
  unless reply[0].key?('!fatal')
165
183
  raise MTik::Error.new("Unexpected response to '/quit' command.")
@@ -245,16 +263,9 @@ module MTik
245
263
  ## Remember that the limit applies separately to each API command
246
264
  ## executed.
247
265
  def self.command(args)
248
- tk = MTik::Connection.new(
249
- :host => args[:host],
250
- :user => args[:user],
251
- :pass => args[:pass],
252
- :port => args[:port],
253
- :conn_timeout => args[:conn_timeout],
254
- :cmd_timeout => args[:cmd_timeout]
255
- )
256
- limit = args[:limit] ## Optional reply limit
257
- cmd = args[:command]
266
+ tk = MTik::Connection.new(args)
267
+ limit = args[:limit] ## Optional reply limit
268
+ cmd = args[:command]
258
269
  replies = Array.new
259
270
  if cmd.is_a?(String)
260
271
  ## Single command, no arguments
@@ -62,7 +62,7 @@ class MTik::Connection
62
62
  @ssl_sock = nil
63
63
  @requests = Hash.new
64
64
  @use_ssl = args[:ssl] || MTik::USE_SSL
65
- @unencrypted_plaintext = args[:unecrypted_plaintext]
65
+ @unencrypted_plaintext = args[:unencrypted_plaintext]
66
66
  @host = args[:host]
67
67
  @port = args[:port] || (@use_ssl ? MTik::PORT_SSL : MTik::PORT)
68
68
  @user = args[:user] || MTik::USER
@@ -151,23 +151,20 @@ class MTik::Connection
151
151
  return unless @sock.nil?
152
152
  ## TODO: Perhaps catch more errors
153
153
  begin
154
- addr = Socket.getaddrinfo(@host, nil)
154
+ addr = Socket.getaddrinfo(@host, nil)
155
155
  @sock = Socket.new(Socket.const_get(addr[0][0]), Socket::SOCK_STREAM, 0)
156
156
 
157
157
  begin
158
158
  @sock.connect_nonblock(Socket.pack_sockaddr_in(@port, addr[0][3]))
159
159
  rescue Errno::EINPROGRESS
160
160
  ready = IO.select([@sock], [@sock], [], @conn_timeout)
161
- if ready
162
- @sock
163
- else
164
- raise Errno::ETIMEDOUT
161
+ raise Errno::ETIMEDOUT unless ready
165
162
  end
166
- end
167
-
168
- connect_ssl(@sock) if @use_ssl
169
163
 
170
- rescue Errno::ECONNREFUSED, Errno::ETIMEDOUT, Errno::ENETUNREACH,
164
+ connect_ssl(@sock) if @use_ssl
165
+ rescue Errno::ECONNREFUSED,
166
+ Errno::ETIMEDOUT,
167
+ Errno::ENETUNREACH,
171
168
  Errno::EHOSTUNREACH => e
172
169
  @sock = nil
173
170
  raise e ## Re-raise the exception
@@ -417,12 +414,16 @@ class MTik::Connection
417
414
 
418
415
  ## Send the request object over the socket
419
416
  def xmit(req)
420
- if @ssl_sock
421
- @ssl_sock.write(req.request)
422
- else
423
- @sock.send(req.request, 0)
417
+ begin
418
+ if @ssl_sock
419
+ @ssl_sock.write(req.request)
420
+ else
421
+ @sock.send(req.request, 0)
422
+ end
423
+ rescue Errno::EPIPE => e
424
+ @sock = @ssl_sock = nil
425
+ raise e ## Re-raise the exception
424
426
  end
425
-
426
427
  return req
427
428
  end
428
429
 
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: mtik
3
3
  version: !ruby/object:Gem::Version
4
- version: 4.0.5
4
+ version: 4.1.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Aaron D. Gifford