butler-mainframe 0.1.0 → 0.2.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/CHANGELOG.md +7 -0
- data/README.md +43 -22
- data/lib/butler-mainframe.rb +3 -1
- data/lib/config/config.rb +3 -5
- data/lib/config/config_EXAMPLE_x3270.rb +6 -0
- data/lib/mainframe/{passport.rb → emulators/passport.rb} +1 -1
- data/lib/mainframe/{pcomm.rb → emulators/pcomm.rb} +0 -0
- data/lib/mainframe/emulators/x3270.rb +135 -0
- data/lib/mainframe/host_base.rb +41 -37
- metadata +7 -5
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 622cd36fbabc8ca579e69b36ef0d3ce535995854
|
4
|
+
data.tar.gz: bb98f4819d07e639c8cb88e092cc3a3a443fa648
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 98f255d73ae417b65735be57cea9571d8d9f181ff794e4459a07e494ee8d1866af234d681a1f3af8301233d2b66ca166985677bbd94c14f23f33ae7c5a6565b7
|
7
|
+
data.tar.gz: 0f7ae6b50f6f8d5bdd0f0ede9fae786f3927f88ef707531f4c8fa871a8f3ddd0885331d98176b9a1fcdb6d4a82c9eeb0a30ac3ecfe6719b394505b6124e6c391
|
data/CHANGELOG.md
CHANGED
@@ -1,3 +1,10 @@
|
|
1
|
+
0.2.0 [☰](https://github.com/marcomd/butler-mainframe/compare/v0.1.0...v0.2.0) October 20th, 2015
|
2
|
+
------------------------------
|
3
|
+
* Added support for the free and open source x3270 terminal emulator, use :x3270 as host gateway in butler configuration
|
4
|
+
* Added x3270 sections to documentation
|
5
|
+
* Passport sub class now remove spaces from command input
|
6
|
+
* Added :erase_field_first param to write method in the host base class in addition to :clean_first_chars to clear a given number of chars
|
7
|
+
|
1
8
|
0.1.0 [☰](https://github.com/marcomd/butler-mainframe/compare/v0.0.6...v0.1.0) October 14th, 2015
|
2
9
|
------------------------------
|
3
10
|
* Added IBM personal communication support (tested on 6.0.16), use :pcomm as host gateway in butler configuration
|
data/README.md
CHANGED
@@ -18,17 +18,15 @@ Instal the gem from rubygems
|
|
18
18
|
gem install butler-mainframe
|
19
19
|
|
20
20
|
Then you have to install your favorite emulator.
|
21
|
-
At the moment is supported only [Passport web to host by rocket software](http://www.rocketsoftware.com/products/rocket-passport-web-to-host)
|
22
21
|
|
23
|
-
## Emulator
|
24
|
-
|
25
|
-
At the moment are managed two emulators both are commercial which must be purchased and installed on the machine.
|
26
|
-
Both have x days free trial.
|
27
22
|
|
28
|
-
|
29
|
-
* [Personal communication by IBM](http://www-03.ibm.com/software/products/en/pcomm)
|
23
|
+
## Emulator
|
30
24
|
|
25
|
+
At the moment are managed the below emulators. First two are commercial which must be purchased and installed on the machine (both have x days free trial). The last is free and open source.
|
31
26
|
|
27
|
+
* [Passport web to host by Rocket Software](http://www.rocketsoftware.com/resource/rocket-passport-web-host-overview)
|
28
|
+
* [Personal communication by IBM](http://www-03.ibm.com/software/products/en/pcomm)
|
29
|
+
* [x3270 maintained by Paul Mates](http://x3270.bgp.nu/)
|
32
30
|
|
33
31
|
|
34
32
|
## Configuration
|
@@ -43,29 +41,37 @@ In the config folder there are two files:
|
|
43
41
|
config.rb can be used for the configuration of the gem and the emulator
|
44
42
|
|
45
43
|
```ruby
|
46
|
-
# Example to
|
44
|
+
# Example to configure Passport web to host
|
47
45
|
|
48
46
|
ButlerMainframe.configure do |config|
|
49
|
-
config.host_gateway = :
|
50
|
-
config.browser_path =
|
51
|
-
config.session_path =
|
52
|
-
config.session_tag =
|
47
|
+
config.host_gateway = :passport
|
48
|
+
config.browser_path = 'c:/Program Files (x86)/Internet Explorer/iexplore.exe'
|
49
|
+
config.session_path = 'https://localhost/zephyr/Ecomes.zwh?sessionprofile=3270dsp/Sessions/host3270'
|
50
|
+
config.session_tag = 1
|
53
51
|
config.timeout = 3000
|
54
52
|
end
|
55
53
|
```
|
56
54
|
|
57
55
|
```ruby
|
58
|
-
# Example to
|
56
|
+
# Example to configure Personal communication
|
59
57
|
|
60
58
|
ButlerMainframe.configure do |config|
|
61
|
-
config.host_gateway = :
|
62
|
-
config.
|
63
|
-
config.
|
64
|
-
config.session_tag = 1
|
59
|
+
config.host_gateway = :pcomm
|
60
|
+
config.session_path = '"C:/Program Files (x86)/IBM/Personal Communications/pcsws.exe" "C:/Users/Marco/AppData/Roaming/IBM/Personal Communications/host3270.ws"'
|
61
|
+
config.session_tag = 'A'
|
65
62
|
config.timeout = 3000
|
66
63
|
end
|
67
64
|
```
|
68
65
|
|
66
|
+
```ruby
|
67
|
+
# Example to configure X3270
|
68
|
+
ButlerMainframe.configure do |config|
|
69
|
+
config.host_gateway = :x3270
|
70
|
+
config.session_path = '"C:/Program Files (x86)/wc3270/ws3270.exe" 127.0.0.1 -model 2 --'
|
71
|
+
config.timeout = 5 # In seconds
|
72
|
+
end
|
73
|
+
```
|
74
|
+
|
69
75
|
### Use configuration
|
70
76
|
|
71
77
|
settings.yml for the variables necessary to use the emulator like user, password, cics selection and everything else. It has one section for every environment in rails style.
|
@@ -89,7 +95,7 @@ In this example, I dont start the session and immediately create a new instance:
|
|
89
95
|
Session not found, starting new...
|
90
96
|
Starting session with process id 8560, wait please...
|
91
97
|
** Connection established with host3270 **
|
92
|
-
=> #<ButlerMainframe::Host:0x29f3358 @debug=true, @wait=0.01, @wait_debug=2, @session=1, @close_session=:evaluate, @pid=8560, @action=#<WIN32OLE:0x29ebe10
|
98
|
+
=> #<ButlerMainframe::Host:0x29f3358 @debug=true, @wait=0.01, @wait_debug=2, @session=1, @close_session=:evaluate, @pid=8560, @action=#<WIN32OLE:0x29ebe10>>
|
93
99
|
|
94
100
|
now session is ready to use:
|
95
101
|
|
@@ -128,8 +134,7 @@ host.write 'ruby on rails', :y => 6, :x => 15, hook: 'SYSTEM='
|
|
128
134
|
|
129
135
|
The aim is to speed up browsing through static screens.
|
130
136
|
The butler detects the current screen and It moves towards the target.
|
131
|
-
For example, if the current screen is the login_session and you want to go to the next,
|
132
|
-
In this case it identifies the first map the session login to the mainframe and it does the login to go to the next screen.
|
137
|
+
For example, if the current screen is the login_session and you want to go to the next, Butler log in for you.
|
133
138
|
|
134
139
|
```ruby
|
135
140
|
# Go to the login session screen
|
@@ -153,7 +158,6 @@ My advice is to use navigate method for generic navigation and use a specific mo
|
|
153
158
|
|
154
159
|
## With Rails
|
155
160
|
|
156
|
-
__In development...__
|
157
161
|
This module can be use on rails project.
|
158
162
|
Add in your gemfile
|
159
163
|
|
@@ -195,10 +199,14 @@ end
|
|
195
199
|
```
|
196
200
|
|
197
201
|
Create a polimorphic model:
|
198
|
-
|
202
|
+
|
203
|
+
rails generate screen hook_id:integer 'hook_type:string{30}' 'screen_type:integer{1}' video:text 'message:string{160}' 'cursor_x:integer{1}' 'cursor_y:integer{1}'
|
199
204
|
|
200
205
|
In the model to be related to screen we insert:
|
206
|
+
|
207
|
+
```ruby
|
201
208
|
has_many :screens, :as => :hook, :dependent => :destroy
|
209
|
+
```
|
202
210
|
|
203
211
|
|
204
212
|
## Test with rake
|
@@ -325,11 +333,24 @@ session.autECLOIA.ole_methods (screen):
|
|
325
333
|
# CancelWaits # RegisterCommEvent # UnregisterCommEvent # RegisterOIAEvent
|
326
334
|
# UnregisterOIAEvent # GetTypeInfoCount # GetTypeInfo # GetIDsOfNames
|
327
335
|
|
336
|
+
### x3270
|
337
|
+
|
338
|
+
Documentation can be found [here](http://x3270.bgp.nu/documentation-manpages.html)
|
339
|
+
__At the moment it doesn't support check on protect area__
|
340
|
+
__x3270 module works only on ruby 1.9+__
|
341
|
+
|
342
|
+
```ruby
|
343
|
+
require 'open3'
|
344
|
+
stdin, stdout, thread = Open3.popen2e('"C:/Program Files (x86)/wc3270/ws3270.exe" YOUR_HOST_IP -model 2 --')
|
345
|
+
```
|
346
|
+
|
347
|
+
Read the methods list documentation: [windows](http://x3270.bgp.nu/Windows/wc3270-script.html) or [unix](http://x3270.bgp.nu/Unix/x3270-script.html)
|
328
348
|
|
329
349
|
## ToDo
|
330
350
|
|
331
351
|
* Improve unit test
|
332
352
|
* Improve static navigation
|
353
|
+
* Add meta class to choose your host method name and multi language support as well
|
333
354
|
|
334
355
|
## License
|
335
356
|
|
data/lib/butler-mainframe.rb
CHANGED
@@ -25,7 +25,9 @@ env = Rails.env if defined?(Rails)
|
|
25
25
|
env ||= $ARGV[0] if $ARGV
|
26
26
|
env ||= "development"
|
27
27
|
debug = env == "development" ? true : false
|
28
|
-
|
28
|
+
|
29
|
+
# require the emulator sub class specified in the config.rb
|
30
|
+
require "mainframe/emulators/#{ButlerMainframe.configuration.host_gateway.to_s.downcase}"
|
29
31
|
|
30
32
|
|
31
33
|
ButlerMainframe::Settings.load!(File.join(ButlerMainframe.root,'lib','config','settings.yml'), :env => env)
|
data/lib/config/config.rb
CHANGED
@@ -1,8 +1,6 @@
|
|
1
1
|
ButlerMainframe.configure do |config|
|
2
|
-
config.host_gateway =
|
3
|
-
config.
|
4
|
-
config.
|
5
|
-
config.session_tag = 1
|
6
|
-
config.timeout = 3000
|
2
|
+
config.host_gateway = :x3270
|
3
|
+
config.session_path = '"C:/Program Files (x86)/wc3270/ws3270.exe" YOUR_HOST_IP -model 2 --'
|
4
|
+
config.timeout = 5 # In seconds
|
7
5
|
end
|
8
6
|
|
@@ -48,7 +48,7 @@ module ButlerMainframe
|
|
48
48
|
#Execute keyboard command like PF1 or PA2 or ENTER ...
|
49
49
|
def sub_exec_command cmd, options={}
|
50
50
|
# Cast cmd to_s cause it could be passed as label
|
51
|
-
@screen.SendKeys "<#{cmd}>"
|
51
|
+
@screen.SendKeys "<#{cmd.gsub /\s/, ''}>"
|
52
52
|
@screen.WaitHostQuiet
|
53
53
|
end
|
54
54
|
|
File without changes
|
@@ -0,0 +1,135 @@
|
|
1
|
+
require 'open3'
|
2
|
+
require 'mainframe/host_base'
|
3
|
+
|
4
|
+
# This class use X3270, an interesting project open source
|
5
|
+
# http://x3270.bgp.nu/Windows/wc3270-script.html
|
6
|
+
# http://x3270.bgp.nu/Windows/ws3270-man.html
|
7
|
+
module ButlerMainframe
|
8
|
+
class Host < HostBase
|
9
|
+
|
10
|
+
private
|
11
|
+
|
12
|
+
def sub_create_object options={}
|
13
|
+
str_obj = "#{options[:session_path]}"
|
14
|
+
puts "#{Time.now.strftime "%H:%M:%S"} Creating object #{str_obj}..." if @debug == :full
|
15
|
+
@action = {}
|
16
|
+
@action[:in], @action[:out], @action[:thr] = Open3.popen2e(str_obj)
|
17
|
+
@pid = @action[:thr].pid
|
18
|
+
end
|
19
|
+
|
20
|
+
# Check is session is started
|
21
|
+
def sub_object_created?
|
22
|
+
res = @action[:in] && @action[:out] && @action[:thr]
|
23
|
+
puts "#{Time.now.strftime "%H:%M:%S"} Terminal successfully detected" if @debug == :full && res
|
24
|
+
res
|
25
|
+
end
|
26
|
+
|
27
|
+
# Check is session is operative
|
28
|
+
def sub_object_ready?
|
29
|
+
res = !x_cmd("Query(ConnectionState)").strip.empty?
|
30
|
+
puts "#{Time.now.strftime "%H:%M:%S"} Session ready" if @debug == :full && res
|
31
|
+
res
|
32
|
+
end
|
33
|
+
|
34
|
+
def sub_name
|
35
|
+
"X3270 #{x_cmd "Query(Host)"}".strip
|
36
|
+
end
|
37
|
+
|
38
|
+
def sub_fullname
|
39
|
+
"#{sub_name} #{x_cmd "Query(LuName)"}".strip
|
40
|
+
end
|
41
|
+
|
42
|
+
#Ends the connection and closes the session
|
43
|
+
def sub_close_session
|
44
|
+
@action[:in].close
|
45
|
+
@action[:out].close
|
46
|
+
end
|
47
|
+
|
48
|
+
#Execute keyboard command like PF1 or PA2 or ENTER ...
|
49
|
+
def sub_exec_command cmd, options={}
|
50
|
+
cmd = cmd.split.map(&:capitalize).join
|
51
|
+
if m=/^(Pf|Pa)(\d+)$/.match(cmd)
|
52
|
+
cmd = "#{m[1]}(#{m[2]})"
|
53
|
+
end
|
54
|
+
x_cmd cmd
|
55
|
+
|
56
|
+
command_skip_wait = %w(^erase ^delete)
|
57
|
+
x_cmd "Wait(#{@timeout}, Output)" unless /(#{command_skip_wait.join('|')})/i === cmd
|
58
|
+
end
|
59
|
+
|
60
|
+
#It reads one line part of the screen
|
61
|
+
def sub_scan_row y, x, len
|
62
|
+
x_cmd "Ascii(#{y-1},#{x-1},#{len})"
|
63
|
+
end
|
64
|
+
|
65
|
+
#It reads a rectangle on the screen
|
66
|
+
def sub_scan_area y1, x1, y2, x2
|
67
|
+
x_cmd "Ascii(#{y1-1},#{x1-1},#{y2-y1+1},#{x2-x1+1})"
|
68
|
+
end
|
69
|
+
|
70
|
+
# Get cursor coordinates
|
71
|
+
def sub_get_cursor_axes
|
72
|
+
res = x_cmd "Query(Cursor)"
|
73
|
+
res.split.map{|c| c.to_i + 1}
|
74
|
+
end
|
75
|
+
|
76
|
+
# Move cursor to given coordinates
|
77
|
+
def sub_set_cursor_axes y, x, options={}
|
78
|
+
options = {
|
79
|
+
:wait => true
|
80
|
+
}.merge(options)
|
81
|
+
x_cmd "MoveCursor(#{y-1},#{x-1})"
|
82
|
+
if options[:wait]
|
83
|
+
x_cmd "Wait(#{@timeout},InputField)"
|
84
|
+
raise "Positioning the cursor at the coordinates (#{y}, #{x}) failed!" unless sub_get_cursor_axes == [y, x]
|
85
|
+
end
|
86
|
+
end
|
87
|
+
|
88
|
+
# Write text on the screen at given coordinates
|
89
|
+
# :check_protect => true add sensitivity to protected areas
|
90
|
+
def sub_write_text text, y, x, options={}
|
91
|
+
options = {
|
92
|
+
:check_protect => true
|
93
|
+
}.merge(options)
|
94
|
+
sub_set_cursor_axes y, x
|
95
|
+
x_cmd "String(#{text})"
|
96
|
+
# TODO
|
97
|
+
# if options[:check_protect]
|
98
|
+
# end
|
99
|
+
end
|
100
|
+
|
101
|
+
# Wait text at given coordinates and wait the session is available again
|
102
|
+
def sub_wait_for_string text, y, x
|
103
|
+
x_cmd "Wait(#{@timeout},InputField)"
|
104
|
+
total_time = 0.0
|
105
|
+
sleep_time = 0.5
|
106
|
+
while sub_scan_row(y, x, text.size) != text do
|
107
|
+
sleep sleep_time
|
108
|
+
total_time = total_time + sleep_time
|
109
|
+
# @timeout should be in milliseconds but everything is possible
|
110
|
+
break if total_time >= @timeout
|
111
|
+
end
|
112
|
+
raise "sub_wait_for_string: string #{text} not found at (#{y}, #{x})" unless sub_scan_row(y, x, text.size) == text
|
113
|
+
true
|
114
|
+
end
|
115
|
+
|
116
|
+
def x_cmd cmd
|
117
|
+
puts "x_cmd in: #{cmd}" if @debug
|
118
|
+
@action[:in].print "#{cmd}\n"
|
119
|
+
@action[:in].flush
|
120
|
+
|
121
|
+
str_res_ok = 'ok'
|
122
|
+
ar_res = [str_res_ok, 'error']
|
123
|
+
|
124
|
+
line, str_out = '', ''
|
125
|
+
while line = @action[:out].gets.chomp do
|
126
|
+
puts "x_cmd out: '#{line}'" if @debug
|
127
|
+
break if ar_res.include? line
|
128
|
+
str_out << "#{line[6..-1]}" if /^data:\s/ === line
|
129
|
+
end
|
130
|
+
line == str_res_ok ? str_out : raise(str_out)
|
131
|
+
end
|
132
|
+
|
133
|
+
end
|
134
|
+
end
|
135
|
+
|
data/lib/mainframe/host_base.rb
CHANGED
@@ -31,7 +31,7 @@ module ButlerMainframe
|
|
31
31
|
@session_tag = options[:session_tag]
|
32
32
|
@close_session = options[:close_session]
|
33
33
|
@timeout = options[:timeout]
|
34
|
-
@pid
|
34
|
+
@pid = nil
|
35
35
|
|
36
36
|
create_object options
|
37
37
|
end
|
@@ -45,9 +45,9 @@ module ButlerMainframe
|
|
45
45
|
puts "Session closed" if @debug
|
46
46
|
wait_session 0.1
|
47
47
|
when :evaluate
|
48
|
-
if @
|
48
|
+
if @pid
|
49
49
|
sub_close_session
|
50
|
-
puts "Session closed
|
50
|
+
puts "Session closed because started by this process with id #{@pid}" if @debug
|
51
51
|
wait_session 0.1
|
52
52
|
else
|
53
53
|
puts "Session not closed because it was already existing" if @debug
|
@@ -95,7 +95,7 @@ module ButlerMainframe
|
|
95
95
|
:check => true,
|
96
96
|
:raise_error_on_check => true,
|
97
97
|
:sensible_data => nil,
|
98
|
-
:clean_first_chars => nil
|
98
|
+
:clean_first_chars => nil # clean x chars before writing a value
|
99
99
|
}.merge(options)
|
100
100
|
|
101
101
|
y = options[:y]
|
@@ -104,18 +104,19 @@ module ButlerMainframe
|
|
104
104
|
raise "Missing coordinates! y(row)=#{y} x(column)=#{x} " unless x && y
|
105
105
|
raise "Sorry, cannot write null values" unless text
|
106
106
|
|
107
|
-
bol_written =
|
107
|
+
bol_written = false
|
108
108
|
if options[:hook]
|
109
109
|
(y-hooked_rows..y+hooked_rows).each do |row_number|
|
110
110
|
if /#{options[:hook]}/ === scan_row(row_number, 1, MAX_TERMINAL_COLUMNS)
|
111
111
|
puts "Change y from #{y} to #{row_number} cause hook to:#{options[:hook]}" if row_number != y && @debug
|
112
|
-
bol_written =
|
112
|
+
bol_written = write_text_on_map text, row_number, x, options
|
113
113
|
break
|
114
114
|
end
|
115
115
|
end
|
116
|
+
else
|
117
|
+
#If no control is required or was not found the label reference
|
118
|
+
bol_written = write_text_on_map(text, y, x, options) unless bol_written
|
116
119
|
end
|
117
|
-
#If no control is required or was not found the label reference
|
118
|
-
bol_written = write_clean_text_on_map(text, y, x, options) unless bol_written
|
119
120
|
bol_written
|
120
121
|
end
|
121
122
|
|
@@ -144,8 +145,10 @@ module ButlerMainframe
|
|
144
145
|
|
145
146
|
sub_create_object options
|
146
147
|
|
147
|
-
|
148
|
-
|
148
|
+
if sub_object_created?
|
149
|
+
puts "Using the terminal with process id #{@pid}" if @pid && @debug
|
150
|
+
else
|
151
|
+
# if the terminal is not found then we start it
|
149
152
|
puts "Session #{@session_tag} not found, starting new..." if @debug
|
150
153
|
|
151
154
|
executable, args = if options[:browser_path] && !options[:browser_path].empty?
|
@@ -172,7 +175,6 @@ module ButlerMainframe
|
|
172
175
|
sub_create_object
|
173
176
|
sub_object_created? ? break : sleep(seconds_between_attempts)
|
174
177
|
end
|
175
|
-
@session_started_by_me = true
|
176
178
|
end
|
177
179
|
|
178
180
|
raise "Session #{@session_tag} not started. Check the session #{options[:browser_path]} #{options[:session_path]}" unless sub_object_created?
|
@@ -210,47 +212,49 @@ module ButlerMainframe
|
|
210
212
|
str
|
211
213
|
end
|
212
214
|
|
213
|
-
# It has an additional option to clean the line before writing a value
|
214
|
-
def write_clean_text_on_map text, y, x, options={}
|
215
|
-
if options[:clean_first_chars] && options[:clean_first_chars].to_i > 0
|
216
|
-
puts "Clean #{options[:clean_first_chars]} char#{options[:clean_first_chars] == 1 ? '' : 's'} y:#{y} x:#{x}" if @debug
|
217
|
-
bol_cleaned = write_text_on_map(" " * options[:clean_first_chars], y, x, options)
|
218
|
-
unless bol_cleaned
|
219
|
-
puts "EHI! Impossible to clean the area specified" if @debug
|
220
|
-
return false
|
221
|
-
end
|
222
|
-
end
|
223
|
-
puts "Clean: #{options[:sensible_data] ? ('*' * text.size) : text} y:#{y} x:#{x}" if @debug
|
224
|
-
write_text_on_map(text, y, x, options)
|
225
|
-
end
|
226
|
-
|
227
215
|
# Write a text on the screen
|
228
216
|
# It also contains the logic to control the successful writing
|
229
217
|
def write_text_on_map text, y, x, options={}
|
230
218
|
options = {
|
231
219
|
:check => true,
|
232
220
|
:raise_error_on_check => true,
|
233
|
-
:sensible_data => nil
|
221
|
+
:sensible_data => nil,
|
222
|
+
:clean_first_chars => nil,
|
223
|
+
:erase_field_first => nil
|
234
224
|
}.merge(options)
|
235
|
-
raise "Impossible to write beyond row #{MAX_TERMINAL_ROWS}"
|
225
|
+
raise "Impossible to write beyond row #{MAX_TERMINAL_ROWS}" if y > MAX_TERMINAL_ROWS
|
236
226
|
raise "Impossible to write beyond column #{MAX_TERMINAL_COLUMNS}" if x > MAX_TERMINAL_COLUMNS
|
237
|
-
raise "Impossible to write a null value"
|
227
|
+
raise "Impossible to write a null value" unless text
|
228
|
+
|
229
|
+
if options[:clean_first_chars] && options[:clean_first_chars].to_i > 0
|
230
|
+
puts "write_text_on_map: Clean #{options[:clean_first_chars]} char#{options[:clean_first_chars] == 1 ? '' : 's'} y:#{y} x:#{x}" if @debug
|
231
|
+
bol_cleaned = write_text_on_map(" " * options[:clean_first_chars], y, x, options)
|
232
|
+
unless bol_cleaned
|
233
|
+
puts "write_text_on_map: EHI! Impossible to clean the area specified" if @debug
|
234
|
+
return false
|
235
|
+
end
|
236
|
+
end
|
237
|
+
|
238
|
+
if options[:erase_field_first]
|
239
|
+
set_cursor_axes y, x
|
240
|
+
do_erase
|
241
|
+
end
|
242
|
+
|
238
243
|
sub_write_text text, y, x, :check_protect => options[:check]
|
239
|
-
|
240
|
-
|
244
|
+
res = true
|
245
|
+
# If check is required it verify text is on the screen at given coordinates
|
246
|
+
# Sensible data option disable the check because it could be on hidden fields
|
247
|
+
if options[:check] && !options[:sensible_data]
|
241
248
|
# It expects the string is present on the session at the specified coordinates
|
242
|
-
|
243
|
-
return true
|
244
|
-
else
|
249
|
+
unless sub_wait_for_string text, y, x
|
245
250
|
if options[:raise_error_on_check]
|
246
|
-
raise "Impossible to write #{options[:sensible_data] ? ('*' * text.size) : text} at row #{y} column #{x}"
|
251
|
+
raise "write_text_on_map: Impossible to write #{options[:sensible_data] ? ('*' * text.size) : text} at row #{y} column #{x}"
|
247
252
|
else
|
248
|
-
|
253
|
+
res = false
|
249
254
|
end
|
250
255
|
end
|
251
|
-
else
|
252
|
-
return true
|
253
256
|
end
|
257
|
+
res
|
254
258
|
end
|
255
259
|
|
256
260
|
# If is called a not existing method there is the chance that an optional module may not have been added
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: butler-mainframe
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
4
|
+
version: 0.2.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Marco Mastrodonato
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2015-10-
|
11
|
+
date: 2015-10-20 00:00:00.000000000 Z
|
12
12
|
dependencies: []
|
13
13
|
description: This gem provides a virtual butler which can perform your custom tasks
|
14
14
|
on a 3270 emulator. You just have to choose your emulator (atm only one choice)
|
@@ -27,6 +27,7 @@ files:
|
|
27
27
|
- lib/config/config.rb
|
28
28
|
- lib/config/config_EXAMPLE_passport.rb
|
29
29
|
- lib/config/config_EXAMPLE_pcomm.rb
|
30
|
+
- lib/config/config_EXAMPLE_x3270.rb
|
30
31
|
- lib/config/settings.yml
|
31
32
|
- lib/config/settings_EXAMPLE.yml
|
32
33
|
- lib/core/configuration.rb
|
@@ -37,9 +38,10 @@ files:
|
|
37
38
|
- lib/generators/butler_mainframe.rb
|
38
39
|
- lib/mainframe/customization/active_record.rb
|
39
40
|
- lib/mainframe/customization/generic_functions.rb
|
41
|
+
- lib/mainframe/emulators/passport.rb
|
42
|
+
- lib/mainframe/emulators/pcomm.rb
|
43
|
+
- lib/mainframe/emulators/x3270.rb
|
40
44
|
- lib/mainframe/host_base.rb
|
41
|
-
- lib/mainframe/passport.rb
|
42
|
-
- lib/mainframe/pcomm.rb
|
43
45
|
- lib/vendor/deep_symbolize.rb
|
44
46
|
- rakefile
|
45
47
|
- test/test.rake
|
@@ -62,7 +64,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
62
64
|
- !ruby/object:Gem::Version
|
63
65
|
version: '0'
|
64
66
|
requirements:
|
65
|
-
-
|
67
|
+
- A bit of awesomeness
|
66
68
|
rubyforge_project:
|
67
69
|
rubygems_version: 2.2.5
|
68
70
|
signing_key:
|