class Regextest
This routine defines Regextest
class
Copyright © 2016 Mikio Ikoma
Constants
- VERSION
Attributes
@!attribute [r] reason
Reason if failed to generate @return [hash] return reasons if failed to generate @return [nil] return nil unless error
@!attribute [r] seed
Seed for randomization @return [Fixnum] return seed for randomization @return [nil] return nil if no seed provided
Public Class Methods
Constructor of Regextest
class @param [String|Regexp] regex regular expression object (or string) @param [Hash] options parameters for generating @option options [Regextest::RegexOption] :reg_options Regex option parameter @option options [Fixnum] :seed seed for randomization @option options [TrueClass] :verification specify true (or not speficy) to verify generated string using ruby Regexp
. @option options [FalseClass] :verification specify false if skip to verify generated string. @return [Regextest] constructed object
# File lib/regextest.rb, line 33 def initialize(regex, options = {}) @@parse_options = options @@parse_options[:reg_options] ||= Regextest::RegexOption.new @verification = (options && options[:verification] == false)?false:true @reg_string = nil @reg_exp = nil # Set seed for randomizing @seed = set_seed_for_randomizing(@@parse_options[:seed]) # Covert to source string if necessary set_regex(regex) # Parse string @front_end = Regextest::Front.new(@reg_string, @@parse_options) # Prepare back-end process. (use generate method for generating string) @back_end = Regextest::Back.new(@front_end) @result = nil @reason = nil end
Public Instance Methods
Genetate string matched with specified regular expression @return [MatchData] if matched and verified. @return [String] if matched without verification (i.e. return unverified matched string). @return [nil] nil if failed to generate @raise [RuntimeError] if something wrong… @raise [Regextest::RegextestTimeout] if detected timeout while verification. Option ‘verification: false’ may be workaround.
# File lib/regextest.rb, line 74 def generate start_time = Time.now 0.step(TstFixnumMax) do | retry_count | duration = Time.now - start_time break if retry_count >= TstConstRetryMax && duration >= TstConstRetryMaxSecond # generate string reset_random_called @result = @back_end.generate(retry_count) if !@result TstLog "NG: Failed to generate" @reason = :failed_to_generate if !is_random? raise(RegextestError, "It is impossible to generate sample string of #{@reg_string}.") end next end result_string = @result.pre_match + @result.match + @result.post_match # verify generated string if @verification @result = verify(result_string) # returns a match-object if !@result TstLog "NG: Failed to verify" @reason = :failed_to_verify next end # break if @result is verified else @result = result_string # returns a string end break end if !@result raise(RegextestFailedToGenerate, "Regextest failed to generate sample string of #{@reg_string}.") end @result end
Get parsed result as JSON string @return [String] parsed result as JSON string
# File lib/regextest.rb, line 117 def to_json @front_end.get_json_string end
Private Instance Methods
add built-in functions if any
# File lib/regextest.rb, line 158 def check_builtin(param) builtin_functions = {} param.scan(/\\g[\<\'](_\w+_)[\>\']/) do | func_name | builtin_functions[func_name[0]] = true end if builtin_functions.keys.size > 0 require 'regextest/front/builtin-functions' functions = Regextest::Front::BuiltinFunctions.new builtin_functions.keys.each do | func_name | if func_string = functions.find_func(func_name) param = param + func_string else raise "invalid built-in function name (#{func_name})" end end end param end
Covert to source string if necessary
# File lib/regextest.rb, line 136 def set_regex(param) case param when String if md = param.match(/^\/(.*)\/([imx]*)$/) @reg_exp = eval(param) @reg_string = @reg_exp.source else new_param = check_builtin(param) @reg_string = new_param @reg_exp = /#{@reg_string}/ end when Regexp @reg_exp = param @@parse_options[:reg_options].set(@reg_exp.options) # inner regex options have priorty @reg_string = @@parse_options[:reg_options].prefix_reg + @reg_exp.source else raise "Error: string or regular expression required" end @@parse_options[:reg_source] = @reg_string end
Set seed for randomizing
# File lib/regextest.rb, line 125 def set_seed_for_randomizing(seed) if seed raise "Invalid seed (#{seed}: #{seed.class}) specified" if !(Integer === seed) srand seed seed else srand # return preset seed end end
Verifies the result
# File lib/regextest.rb, line 178 def verify(result_string) md = nil begin Timeout.timeout(TstConstTimeout){ md = @reg_exp.match(result_string) } rescue Timeout::Error => ex raise(RegextestTimeout, "Timeout(#{TstConstTimeout} sec) detected while verifying string(#{result_string}) matched with regex(#{@reg_exp}).") end if(md) # matched string sometime differs from expected one... if(md.pre_match != @result.pre_match || md.to_a[0] != @result.match || md.post_match != @result.post_match) @reason = :invalid_match_string TstLog "WARN: Invalid matched string, expected <--> actual" TstLog " proc: #{md.pre_match.inspect} <--> #{@result.pre_match.inspect}" TstLog " body: #{md.to_a[0].inspect} <--> #{@result.match.inspect}" TstLog " succ: #{md.post_match.inspect} <--> #{@result.post_match.inspect}" end else @reason = { rc: :not_matched, string: result_string} raise("failed to generate. Not matched regex(#{@reg_string}) string(#{result_string.inspect})") end md end