rdoba 0.1 → 0.9
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 +7 -0
- data/.gitignore +19 -41
- data/LICENSE +5 -17
- data/README.md +9 -29
- data/Rakefile +38 -3
- data/features/bcd.feature +29 -0
- data/features/log.feature +206 -0
- data/features/step_definitions/bcd_steps.rb +69 -0
- data/features/step_definitions/log_steps.rb +164 -0
- data/features/support/env.rb +159 -0
- data/lib/rdoba.rb +31 -15
- data/lib/rdoba/_version_.rb +3 -0
- data/lib/rdoba/a.rb +50 -53
- data/lib/rdoba/bcd.rb +61 -0
- data/lib/rdoba/common.rb +42 -11
- data/lib/rdoba/debug.rb +4 -46
- data/lib/rdoba/{fenc.rb → fe.rb} +2 -1
- data/lib/rdoba/io.rb +47 -17
- data/lib/rdoba/log.rb +248 -0
- data/lib/rdoba/numeric.rb +59 -49
- data/lib/rdoba/strings.rb +4 -3
- data/lib/rdoba/version.rb +51 -3
- data/rdoba.gemspec +13 -9
- metadata +51 -19
@@ -0,0 +1,69 @@
|
|
1
|
+
#encoding: utf-8
|
2
|
+
|
3
|
+
require 'test/unit/assertions'
|
4
|
+
|
5
|
+
World( Test::Unit::Assertions )
|
6
|
+
|
7
|
+
Given 'Apply Rdoba bcd module' do
|
8
|
+
require 'rdoba'
|
9
|
+
end
|
10
|
+
|
11
|
+
When 'Rdoba applied in a code' do
|
12
|
+
rdoba :bcd
|
13
|
+
end
|
14
|
+
|
15
|
+
Then 'Create a new simple BCD string' do
|
16
|
+
@bcd = BCDString.new 12345
|
17
|
+
assert @bcd == "\x45\x23\x01",
|
18
|
+
"The BCD, which has been converted from an integer, has invalid value"
|
19
|
+
end
|
20
|
+
|
21
|
+
Then 'Parse an integer' do
|
22
|
+
@bcd = BCD.parse 12345
|
23
|
+
assert @bcd == "\x45\x23\x01",
|
24
|
+
"The BCD, which has been converted from an integer, has invalid value"
|
25
|
+
end
|
26
|
+
|
27
|
+
Then 'Parse a negative integer' do
|
28
|
+
begin
|
29
|
+
assert BCD.parse( -12345 ),
|
30
|
+
"A negative integer has been parse, that is wrong"
|
31
|
+
rescue BCD::ParseError
|
32
|
+
end
|
33
|
+
end
|
34
|
+
|
35
|
+
Then 'Check class to BCD of parsed integer' do
|
36
|
+
assert @bcd.class == BCDString,
|
37
|
+
"BCD of parsed integer has invalid class #{@bcd.class}"
|
38
|
+
end
|
39
|
+
|
40
|
+
Then 'Convert the simple BCD to an integer' do
|
41
|
+
assert @bcd.to_i == 12345,
|
42
|
+
"The integer that has been converted from BCD has invalid value"
|
43
|
+
end
|
44
|
+
|
45
|
+
Then 'Create a new bignum BCD string' do
|
46
|
+
@bcd = BCDString.new 12345098761029384756
|
47
|
+
assert @bcd == "\x56\x47\x38\x29\x10\x76\x98\x50\x34\x12"
|
48
|
+
.force_encoding( 'ASCII-8BIT' ),
|
49
|
+
"The BCD, which has been converted from Bignum integer, has invalid value"
|
50
|
+
end
|
51
|
+
|
52
|
+
Then 'Convert the BCD to a Bignum integer' do
|
53
|
+
bignum = @bcd.to_i
|
54
|
+
assert bignum.class == Bignum,
|
55
|
+
"BCD number converted has invalid class value '#{bignum.class}'"
|
56
|
+
assert bignum == 12345098761029384756,
|
57
|
+
"BCD number converted to integer has invalid value"
|
58
|
+
end
|
59
|
+
|
60
|
+
Then 'Try to create a BCD class with an erroneous argument' do
|
61
|
+
bcd_string = "\x56\x47\x38\x29\x10\x76\x98\x50\x34\xA2"
|
62
|
+
bcd_string.extend BCD
|
63
|
+
begin
|
64
|
+
assert bcd_string.to_i == 0,
|
65
|
+
"BCD string has been converted into an integer, that is wrong"
|
66
|
+
rescue BCD::ConvertError
|
67
|
+
end
|
68
|
+
end
|
69
|
+
|
@@ -0,0 +1,164 @@
|
|
1
|
+
When /appl(?:y|ied) Rdoba (Log|Debug) module(?: with set([\w\s,:]+ keywords?| a file name) for :(io|as|in|functions|prefix) option| with an (invalid) :io option value)?(?: inside a (class))?/ do |kind, subs, opt, invalid, cls|
|
2
|
+
rdoba_sim kind.downcase.to_sym, :init, opt, subs, cls
|
3
|
+
end
|
4
|
+
|
5
|
+
When /issue a call to the function/ do
|
6
|
+
rdoba_sim :log, :call
|
7
|
+
end
|
8
|
+
|
9
|
+
When /issue a creation of the class/ do
|
10
|
+
rdoba_sim :log, :create
|
11
|
+
end
|
12
|
+
|
13
|
+
When /(issue|define) an output of an? (variable|number|string|array)(?: inside an? (initializer|singleton function))?(?: using (?:the|an?) (keyword|invalid keyword|class))?/ do |issue, subject, inside, cond|
|
14
|
+
|
15
|
+
case inside
|
16
|
+
when 'initializer'
|
17
|
+
rdoba_sim :log, :def, :init
|
18
|
+
when 'singleton function'
|
19
|
+
rdoba_sim :log, :def, :single ; end
|
20
|
+
|
21
|
+
func = :func
|
22
|
+
case subject
|
23
|
+
when 'variable'
|
24
|
+
rdoba_sim :log, func, cond, :>, { variable: 'value' }
|
25
|
+
when 'number'
|
26
|
+
rdoba_sim :log, func, cond, :>, 1
|
27
|
+
when 'string'
|
28
|
+
rdoba_sim :log, func, cond, :>, "string"
|
29
|
+
when 'array'
|
30
|
+
rdoba_sim :log, func, cond, :>, [ 'array value1', 'array value2' ] ; end ; end
|
31
|
+
|
32
|
+
When /issue an? :(extended|info|warn|enter|leave|compat) output of a variable/ do |key|
|
33
|
+
case key
|
34
|
+
when 'extended'
|
35
|
+
rdoba_sim :log, :func, :self, :>>, { variable: 'value' }
|
36
|
+
when 'info'
|
37
|
+
rdoba_sim :log, :func, :self, :*, { variable: 'value' }
|
38
|
+
when 'warn'
|
39
|
+
rdoba_sim :log, :func, :self, :%, { variable: 'value' }
|
40
|
+
when 'enter'
|
41
|
+
rdoba_sim :log, :func, :self, :+, { variable: 'value' }
|
42
|
+
when 'leave'
|
43
|
+
rdoba_sim :log, :func, :self, :-, true # TODO check return
|
44
|
+
when 'compat'
|
45
|
+
rdoba_sim :log, :func, :dbp11, "'variable: \"value\"'" ; end ; end
|
46
|
+
|
47
|
+
When /issue an output of the thrown (exception|standard error)(.*)/ do |type, note|
|
48
|
+
case type
|
49
|
+
when 'exception'
|
50
|
+
if note =~ /out/
|
51
|
+
rdoba_sim :log, :func, :self, :e, :'Exception.new', :$stdout
|
52
|
+
else
|
53
|
+
rdoba_sim :log, :func, :self, :e, :'Exception.new' ; end
|
54
|
+
when 'standard error'
|
55
|
+
if note =~ /notification/
|
56
|
+
rdoba_sim :log, :func, :self, :e, :'StandardError.new',
|
57
|
+
[ 'standard error extended info' ]
|
58
|
+
else
|
59
|
+
rdoba_sim :log, :func, :self, :e, :'StandardError.new' ; end ; end ; end
|
60
|
+
|
61
|
+
When /look into(?: the)? (stdout|stderr|file|IO)/ do |ioname|
|
62
|
+
@res = case ioname
|
63
|
+
when 'file'
|
64
|
+
rdoba_sim :log, :exec, :file
|
65
|
+
when 'IO'
|
66
|
+
rdoba_sim :log, :exec, :io
|
67
|
+
when 'stdout'
|
68
|
+
rdoba_sim :log, :exec, :stdout
|
69
|
+
when 'stderr'
|
70
|
+
rdoba_sim :log, :exec, :stderr; end ; end
|
71
|
+
|
72
|
+
When /(remove|add) :(basic|extended|info|warn|enter|leave|compat) keyword.* :(functions) option/ do |act, key, opt|
|
73
|
+
if act == 'remove'
|
74
|
+
rdoba_sim :log, :func, :self, :>=, [ key.to_sym ]
|
75
|
+
else
|
76
|
+
rdoba_sim :log, :func, :self, :<=, [ key.to_sym ] ; end ; end
|
77
|
+
|
78
|
+
When /clear the :(functions) option/ do |opt|
|
79
|
+
rdoba_sim :log, :func, :self, :>=, [ :* ]
|
80
|
+
end
|
81
|
+
|
82
|
+
Then /see the (variable|string|number|array|'true' value) output(?: with the :(basic|extended|info|warn|enter|leave) notice)?(?: preficed with the :(.*))?/ do |subject, notice, prefices|
|
83
|
+
case subject
|
84
|
+
when 'variable'
|
85
|
+
sym = notice && { 'basic' => '>', 'extended' => '>>', 'info' => '***',
|
86
|
+
'warn' => '%%%', 'enter' => '<<<', 'leave' => '>>>' }[ notice ] || '>'
|
87
|
+
symr = sym.to_s.gsub ( '*' ) do |x| "\\#{x}" end
|
88
|
+
prefices = match_keywords prefices
|
89
|
+
if prefices.empty?
|
90
|
+
if @res !~ /variable: "value"/
|
91
|
+
raise "Invalid answer: #{@res}, must be \"variable: \"value\"" ; end
|
92
|
+
else
|
93
|
+
case prefices
|
94
|
+
when [:timestamp]
|
95
|
+
if @res !~ /\[\d\d:\d\d:\d\d\.\d{9}\]#{symr} variable: "value"/
|
96
|
+
raise "Invalid answer: #{@res.chomp}, must be like " +
|
97
|
+
"[00:00:00.000000000]#{sym} variable: \"value\"" ; end
|
98
|
+
when [:timestamp, :pid]
|
99
|
+
if @res !~ /\[\d\d:\d\d:\d\d\.\d{9}\]\{\d+\}#{symr} variable: "value"/
|
100
|
+
raise "Invalid answer: #{@res.chomp}, must be like " +
|
101
|
+
"[00:00:00.000000000]{0000}#{sym} variable: \"value\"" ; end
|
102
|
+
when [:timestamp, :pid, :function_name]
|
103
|
+
if @res !~ /\[\d\d:\d\d:\d\d\.\d{9}\]\{\d+\}\(.+\)#{symr} variable: "value"/
|
104
|
+
raise "Invalid answer: #{@res.chomp}, must be like " +
|
105
|
+
"[00:00:00.000000000]{0000}(name)#{sym} variable: \"value\"" ; end
|
106
|
+
when [:timestamp, :pid, :function_name, :function_line]
|
107
|
+
if @res !~ /\[\d\d:\d\d:\d\d\.\d{9}\]\{\d+\}\([^:]+:\d+\)#{symr} variable: "value"/
|
108
|
+
raise "Invalid answer: #{@res.chomp}, must be like " +
|
109
|
+
"[00:00:00.000000000]{0000}(name:0)#{sym} variable: \"value\"" ; end
|
110
|
+
else
|
111
|
+
raise "Invalid answer: #{@res}"
|
112
|
+
end
|
113
|
+
end
|
114
|
+
when 'string'
|
115
|
+
if @res !~ /string/
|
116
|
+
raise "Invalid answer: #{@res}, must be \"string\"" ; end
|
117
|
+
when 'number'
|
118
|
+
if @res !~ /1/
|
119
|
+
raise "Invalid answer: #{@res.inspect}, must be \"1\"" ; end
|
120
|
+
when "'true' value"
|
121
|
+
if @res !~ /true/
|
122
|
+
raise "Invalid answer: #{@res.inspect}, must be \"true\"" ; end
|
123
|
+
when 'array'
|
124
|
+
if @res !~ /array value1, array value2/
|
125
|
+
raise "Invalid answer: #{@res.inspect}, must be an enum: \"array value1, array value2\"" ; end ; end ; end
|
126
|
+
|
127
|
+
Then /see the (standard error|exception) info(.*)/ do |subject, notice|
|
128
|
+
case subject
|
129
|
+
when 'exception'
|
130
|
+
if @res !~/Exception:%> Exception/
|
131
|
+
raise "Invalid answer: #{@res.inspect}, must be like " +
|
132
|
+
"'Exception:%> Exception'" ; end
|
133
|
+
when 'standard error'
|
134
|
+
if notice =~ /notification/
|
135
|
+
if @res !~ /StandardError:%> StandardError\n\tstandard error extended info/
|
136
|
+
raise "Invalid answer: #{@res.inspect}, must be like " +
|
137
|
+
"'StandardError:%> StandardError\n\tstandard error " +
|
138
|
+
"extended info'" ; end
|
139
|
+
else
|
140
|
+
if @res !~ /StandardError:%> StandardError/
|
141
|
+
raise "Invalid answer: #{@res.inspect}, must be like " +
|
142
|
+
"'StandardError:%> StandardError'" ; end ; end ; end ; end
|
143
|
+
|
144
|
+
Then /see(?: a| the)? (nothing|warning|.* error exception)/ do |subject|
|
145
|
+
case subject
|
146
|
+
when 'nothing'
|
147
|
+
if !@res.empty?
|
148
|
+
raise "Invalid answer: #{@res.inspect}, must be empty" ; end
|
149
|
+
when 'warning'
|
150
|
+
if @res !~ /Warning:/
|
151
|
+
raise "Invalid answer: #{@res.inspect}, must be a warning " +
|
152
|
+
"with the description" ; end
|
153
|
+
'log\': main is not a class/module (TypeError)'
|
154
|
+
when /no method error/
|
155
|
+
if @res !~ /undefined method .* \(NoMethodError\)/
|
156
|
+
raise "Invalid answer: #{@res.inspect}, must notify" +
|
157
|
+
" that the interpreter has not found the specified method" ; end
|
158
|
+
when /name error/
|
159
|
+
if @res !~ /undefined local variable or method .* \(NameError\)/
|
160
|
+
raise "Invalid answer: #{@res.inspect}, must notify" +
|
161
|
+
" that the the specified name isn't declared" ; end
|
162
|
+
else
|
163
|
+
raise "Invalid answer: #{@res.inspect}" ; end ; end
|
164
|
+
|
@@ -0,0 +1,159 @@
|
|
1
|
+
require 'rdoba'
|
2
|
+
require 'tempfile'
|
3
|
+
require 'open3'
|
4
|
+
|
5
|
+
RdobaSimSimpleHead=<<HEAD
|
6
|
+
#!/usr/bin/env ruby
|
7
|
+
|
8
|
+
require 'rdoba'
|
9
|
+
HEAD
|
10
|
+
|
11
|
+
RdobaSimInHead=<<HEAD
|
12
|
+
#!/usr/bin/env ruby
|
13
|
+
|
14
|
+
require 'rdoba'
|
15
|
+
class Cls
|
16
|
+
def initialize
|
17
|
+
self > {:variable=>"value"}
|
18
|
+
end
|
19
|
+
end
|
20
|
+
HEAD
|
21
|
+
|
22
|
+
RdobaSimClsHead=<<HEAD
|
23
|
+
#!/usr/bin/env ruby
|
24
|
+
|
25
|
+
require 'rdoba'
|
26
|
+
class Cls
|
27
|
+
HEAD
|
28
|
+
|
29
|
+
def format str
|
30
|
+
puts str
|
31
|
+
" " * @deep + str + "\n" ; end
|
32
|
+
|
33
|
+
def store
|
34
|
+
file = @inithead + @init + @echo + ( "end\n" * @deep )
|
35
|
+
puts file
|
36
|
+
File.open( 'tmp.rb', 'w+' ) do |f|
|
37
|
+
f.puts file ; end ; end
|
38
|
+
|
39
|
+
def match_keywords keystr
|
40
|
+
keys = ( keystr || '' ).split( /[,:\s]/ ).map do |k|
|
41
|
+
[ :basic, :extended, :enter, :leave, :compat, :timestamp, :pid,
|
42
|
+
:function_name, :function_line ].include?( k.to_sym ) && k.to_sym || nil
|
43
|
+
end.compact ; end
|
44
|
+
|
45
|
+
def rdoba_sim sub, cmd, *args
|
46
|
+
echo = nil
|
47
|
+
case sub
|
48
|
+
when :log, :debug
|
49
|
+
case cmd
|
50
|
+
when :init
|
51
|
+
opts = match_keywords args[ 1 ]
|
52
|
+
opts = opts.size > 1 && opts || opts.size > 0 && opts[ 0 ] || nil
|
53
|
+
|
54
|
+
if args[ 2 ] == 'class'
|
55
|
+
@deep = 1
|
56
|
+
@inithead = RdobaSimClsHead
|
57
|
+
else
|
58
|
+
@deep = 0
|
59
|
+
@inithead = RdobaSimSimpleHead ; end
|
60
|
+
|
61
|
+
param = case args[ 0 ]
|
62
|
+
when 'io'
|
63
|
+
{ :io => "File.new( 'tmp.log', 'w+' )", :functions => :basic }
|
64
|
+
when 'as'
|
65
|
+
{ :as => ":log", :functions => :basic }
|
66
|
+
when 'in'
|
67
|
+
@inithead = RdobaSimInHead
|
68
|
+
{ :in => "Cls", :functions => :basic }
|
69
|
+
when 'prefix'
|
70
|
+
# basic|extended|enter|leave|compat
|
71
|
+
{ args[ 0 ].to_sym => opts, :functions => :basic }
|
72
|
+
when 'functions'
|
73
|
+
{ args[ 0 ].to_sym => opts }
|
74
|
+
else
|
75
|
+
{ :functions => :basic }
|
76
|
+
end
|
77
|
+
|
78
|
+
param = "{" + ( param ).to_a.map do |v|
|
79
|
+
"#{v[ 0 ].inspect} => #{v[ 1 ].is_a?( String ) &&
|
80
|
+
v[ 1 ] || v[ 1 ].inspect}" end.join(',') + "}"
|
81
|
+
@init = " " * @deep + "rdoba :#{sub} => #{param}\n"
|
82
|
+
puts @init
|
83
|
+
@echo = ''
|
84
|
+
|
85
|
+
when :func
|
86
|
+
call = case args[ 0 ]
|
87
|
+
when 'keyword'
|
88
|
+
'log'
|
89
|
+
when 'invalid keyword'
|
90
|
+
'errlog'
|
91
|
+
when /^db/
|
92
|
+
@echo << "self.dbgl = 0xff\n"
|
93
|
+
args[ 0 ]
|
94
|
+
else
|
95
|
+
'self'
|
96
|
+
end
|
97
|
+
|
98
|
+
sep = ( args[ 1 ] == :e ) && '.' || ' '
|
99
|
+
param = []
|
100
|
+
args[ 2..-1 ].each do |arg|
|
101
|
+
case arg
|
102
|
+
when NilClass
|
103
|
+
when Symbol
|
104
|
+
param << " #{arg}"
|
105
|
+
else
|
106
|
+
param << " #{arg.inspect}" ; end ; end
|
107
|
+
str = "#{call}#{sep}#{args[ 1 ]}#{param.join(',')}"
|
108
|
+
echo = format str
|
109
|
+
@echo << echo
|
110
|
+
while @deep > 0
|
111
|
+
@deep -= 1
|
112
|
+
@echo << ( format "end" ) ; end
|
113
|
+
|
114
|
+
when :create
|
115
|
+
@echo << ( format "Cls.new" )
|
116
|
+
|
117
|
+
when :call
|
118
|
+
@echo << ( format "Cls.singleton" )
|
119
|
+
|
120
|
+
when :def
|
121
|
+
if @inithead == RdobaSimClsHead
|
122
|
+
@deep = 1
|
123
|
+
else
|
124
|
+
@deep = 0 ; end
|
125
|
+
echo = case args[ 0 ]
|
126
|
+
when :init
|
127
|
+
format 'def initialize'
|
128
|
+
when :single
|
129
|
+
format 'def self.singleton'
|
130
|
+
end
|
131
|
+
@deep += 1
|
132
|
+
@echo << echo
|
133
|
+
|
134
|
+
when :exec
|
135
|
+
if !@echo.empty?
|
136
|
+
store
|
137
|
+
puts '-' * 15
|
138
|
+
|
139
|
+
File.chmod 0755, 'tmp.rb'
|
140
|
+
Open3.popen3( "./tmp.rb" ) do |stdin, stdout, stderr, wait_thr|
|
141
|
+
@out = stdout.read
|
142
|
+
@err = stderr.read
|
143
|
+
end
|
144
|
+
@echo = ''
|
145
|
+
end
|
146
|
+
res = case args[ 0 ]
|
147
|
+
when :file
|
148
|
+
File.new( 'tmp.log', 'r' ).read
|
149
|
+
when :stdout
|
150
|
+
@out
|
151
|
+
when :stderr
|
152
|
+
@err;
|
153
|
+
else return; end
|
154
|
+
puts res
|
155
|
+
res
|
156
|
+
end
|
157
|
+
end
|
158
|
+
end
|
159
|
+
|
data/lib/rdoba.rb
CHANGED
@@ -1,17 +1,33 @@
|
|
1
|
-
|
2
|
-
#<Encoding:UTF-8>
|
1
|
+
#encoding: utf-8
|
3
2
|
|
4
|
-
require 'rdoba/a'
|
5
|
-
require 'rdoba/
|
6
|
-
require 'rdoba/
|
7
|
-
require 'rdoba/
|
8
|
-
require 'rdoba/
|
9
|
-
require 'rdoba/
|
10
|
-
require 'rdoba/
|
11
|
-
require 'rdoba/
|
12
|
-
require 'rdoba/
|
13
|
-
require 'rdoba/
|
14
|
-
require 'rdoba/
|
15
|
-
require 'rdoba/
|
16
|
-
require 'rdoba/fenc'
|
3
|
+
#require 'rdoba/a'
|
4
|
+
#require 'rdoba/dup'
|
5
|
+
#require 'rdoba/require'
|
6
|
+
#require 'rdoba/common'
|
7
|
+
#require 'rdoba/debug'
|
8
|
+
#require 'rdoba/yaml'
|
9
|
+
#require 'rdoba/strings'
|
10
|
+
#require 'rdoba/deploy'
|
11
|
+
#require 'rdoba/roman'
|
12
|
+
#require 'rdoba/combinations'
|
13
|
+
#require 'rdoba/hashorder'
|
14
|
+
#require 'rdoba/fenc'
|
17
15
|
|
16
|
+
module Kernel
|
17
|
+
Modules = [ :io, :seqnum, :version, :bcd ]
|
18
|
+
|
19
|
+
def rdoba *options
|
20
|
+
options.each do |option|
|
21
|
+
key, value = ( option.is_a?( Hash ) &&
|
22
|
+
[ ( k = option.keys.shift ).to_s.to_sym, option[ k ] ] ||
|
23
|
+
[ option.to_s.to_sym ] )
|
24
|
+
case key
|
25
|
+
when :log, :debug
|
26
|
+
require "rdoba/#{key}"
|
27
|
+
Rdoba.log( { :in => self }.merge( value || {} ) ) # TODO move log method into module
|
28
|
+
# and resolve some troubles with eval in main
|
29
|
+
when :classmatch
|
30
|
+
require 'rdoba/classmatch'
|
31
|
+
self.extend Rdoba::ClassMatch
|
32
|
+
else nil; end || if Modules.include? key
|
33
|
+
require "rdoba/#{key}"; end; end; end; end
|