lib/caricature/expectation.rb in caricature-0.7.6 vs lib/caricature/expectation.rb in caricature-0.7.7

- old
+ new

@@ -1,264 +1,265 @@ -module Caricature - - # A collection of expectations with some methods to make it easier to work with them. - # It allows you to add and find expectations based on certain criteria. - class Expectations - - #initializes a new empty instance of the +Expectation+ collection - def initialize - @instance_expectations = [] - @class_expectations = [] - end - - # Adds an expectation to this collection. From then on it can be found in the collection. - def add_expectation(expectation, mode=:instance) - @instance_expectations << expectation unless mode == :class - @class_expectations << expectation if mode == :class - end - - # Finds an expectation in the collection. It matches by +method_name+ first. - # Then it tries to figure out if you care about the arguments. You can say you don't care by providing - # the symbol +:any+ as first argument to this method. When you don't care the first match is being returned - # When you specify arguments other than +:any+ it will try to match the specified arguments in addition - # to the method name. It will then also return the first result it can find. - def find(method_name, mode=:instance, *args) - expectations = mode == :class ? @class_expectations : @instance_expectations - - candidates = expectations.select { |exp| exp.method_name.to_s.underscore =~ /#{method_name}|#{method_name.to_s.underscore}/ } - with_arguments_candidates = candidates.select { |exp| exp.args == args } - - with_arguments_candidates.first || candidates.select { |exp| exp.any_args? }.first - end - - end - - # contains the syntax for building up an expectation - # This is shared between the +ExpecationBuilder+ and the +Expectation+ - module ExpectationSyntax - - # tell the expection which arguments it needs to respond to - # there is a magic argument here +any+ which configures - # the expectation to respond to any arguments - def with(*ags, &b) - collected[:any_args] = ags.first.is_a?(Symbol) and ags.first == :any - collected[:args] = ags - collected[:callback] = b unless b.nil? - self - end - - # tell the expectation it nees to return this value or the value returned by the block - # you provide to this method. - def return(value=nil, &b) - collected[:return_value] = value - collected[:return_callback] = b if b - self - end - - # Sets up arguments for the block that is being passed into the isolated method call - def pass_block(*ags, &b) - collected[:any_block_args] = ags.first.is_a?(Symbol) and args.first == :any - collected[:block_args] = ags - collected[:block_callback] = b unless b.nil? - self - end - - # tell the expectation it needs to raise an error with the specified arguments - alias_method :actual_raise, :raise - def raise(*args) - collected[:error_args] = args - self - end - - # tell the expecation it needs to call the super before the expectation exectution - def super_before(&b) - collected[:super] = :before - collected[:block] = b if b - self - end - - # tell the expectation it needs to call the super after the expecation execution - def super_after(&b) - collected[:super] = :after - collected[:block] = b if b - self - end - - # indicates whether this expectation should match with any arguments - # or only for the specified arguments - def any_args? - collected[:any_args] - end - - - private - - def collected - @collected ||= {} - end - end - - # A description of an expectation. - # An expectation has the power to call the proxy method or completely ignore it - class Expectation - - include ExpectationSyntax - - # the error_args that this expectation will raise an error with - def error_args - collected[:error_args] - end - - # the value that this expecation will return when executed - def return_value - collected[:return_value] - end - - # indicator for the mode to call the super +:before+, +:after+ and +nil+ - def super - collected[:super] - end - - # contains the callback if one is given - def callback - collected[:callback] - end - - # contains the callback that is used to return the value when this expectation - # is executed - def return_callback - collected[:return_callback] - end - - # contains the arguments that will be passed on to the block - def block_args - collected[:block_args] - end - - # The block that will be used as value provider for the block in the method - def block_callback - collected[:block_callback] - end - - # the block that will be used - def block - collected[:block] - end - - # sets the block callback - def block=(val) - collected[:block] = val - end - - # gets the method_name to which this expectation needs to listen to - def method_name - collected[:method_name] - end - - # the arguments that this expectation needs to be constrained by - def args - collected[:args] - end - - # Initializes a new instance of an expectation - def initialize(options={}) - collected[:any_args] = true - collected.merge!(options) - end - - # indicates whether this expecation will raise an event. - def has_error_args? - !collected[:error_args].nil? - end - - # indicates whether this expectation will return a value. - def has_return_value? - !collected[:return_value].nil? - end - - # call the super before the expectation - def super_before? - collected[:super] == :before - end - - # indicates whether super needs to be called somewhere - def call_super? - !collected[:super].nil? - end - - # indicates whether this expecation has a callback it needs to execute - def has_callback? - !collected[:callback].nil? - end - - # indicates whether this expectation has a block as value provider for the method call block - def has_block_callback? - !collected[:block_callback].nil? - end - - # a flag to indicate it has a return value callback - def has_return_callback? - !collected[:return_callback].nil? - end - - # executes this expectation with its configuration - def execute(*margs,&b) - ags = any_args? ? :any : (margs.empty? ? collected[:args] : margs) - do_raise_error - do_callback(ags) - do_block_callback(&b) - do_event_raise if respond_to?(:events) - - return collected[:return_callback].call(*margs) if has_return_callback? - return return_value if has_return_value? - nil - end - - def to_s #:nodoc: - "<Caricature::Expecation, method_name: #{method_name}, args: #{args}, error args: #{error_args}>" - end - alias :inspect :to_s - - - private - - def do_raise_error #:nodoc: - actual_raise *collected[:error_args] if has_error_args? - end - - def do_callback(ags) #:nodoc: - callback.call(*ags) if has_callback? - end - - def do_block_callback(&b) #:nodoc: - if b - ags = has_block_callback? ? collected[:block_callback].call : collected[:block_args] - b.call(*ags) - end - end - - - end - - # Constructs the expecation object. - # Used as a boundary between the definition and usage of the expectation - class ExpectationBuilder - - include ExpectationSyntax - - # initialises a new instance of the expectation builder - # this builder is passed into the block to allow only certain - # operations in the block. - def initialize(method_name) - @collected = { :method_name => method_name, :args => [], :any_args => true } - end - - - - # build up the expectation with the provided arguments - def build - Expectation.new collected - end - - end - +module Caricature + + # A collection of expectations with some methods to make it easier to work with them. + # It allows you to add and find expectations based on certain criteria. + class Expectations + + #initializes a new empty instance of the +Expectation+ collection + def initialize + @instance_expectations = [] + @class_expectations = [] + end + + # Adds an expectation to this collection. From then on it can be found in the collection. + def add_expectation(expectation, mode=:instance) + @instance_expectations << expectation unless mode == :class + @class_expectations << expectation if mode == :class + end + + # Finds an expectation in the collection. It matches by +method_name+ first. + # Then it tries to figure out if you care about the arguments. You can say you don't care by providing + # the symbol +:any+ as first argument to this method. When you don't care the first match is being returned + # When you specify arguments other than +:any+ it will try to match the specified arguments in addition + # to the method name. It will then also return the first result it can find. + def find(method_name, mode=:instance, *args) + expectations = mode == :class ? @class_expectations : @instance_expectations + + candidates = expectations.select { |exp| exp.method_name.to_s.underscore =~ /#{method_name}|#{method_name.to_s.underscore}/ } + with_arguments_candidates = candidates.select { |exp| exp.args == args } + + with_arguments_candidates.first || candidates.select { |exp| exp.any_args? }.first + end + + end + + # contains the syntax for building up an expectation + # This is shared between the +ExpecationBuilder+ and the +Expectation+ + module ExpectationSyntax + + # tell the expection which arguments it needs to respond to + # there is a magic argument here +any+ which configures + # the expectation to respond to any arguments + def with(*ags, &b) + collected[:any_args] = ags.first.is_a?(Symbol) and ags.first == :any + collected[:args] = ags + collected[:callback] = b unless b.nil? + self + end + + # tell the expectation it nees to return this value or the value returned by the block + # you provide to this method. + def return(value=nil, &b) + collected[:return_value] = value + collected[:return_callback] = b if b + self + end + alias_method :returns, :return + + # Sets up arguments for the block that is being passed into the isolated method call + def pass_block(*ags, &b) + collected[:any_block_args] = ags.first.is_a?(Symbol) and args.first == :any + collected[:block_args] = ags + collected[:block_callback] = b unless b.nil? + self + end + + # tell the expectation it needs to raise an error with the specified arguments + alias_method :actual_raise, :raise + def raise(*args) + collected[:error_args] = args + self + end + + # tell the expecation it needs to call the super before the expectation exectution + def super_before(&b) + collected[:super] = :before + collected[:block] = b if b + self + end + + # tell the expectation it needs to call the super after the expecation execution + def super_after(&b) + collected[:super] = :after + collected[:block] = b if b + self + end + + # indicates whether this expectation should match with any arguments + # or only for the specified arguments + def any_args? + collected[:any_args] + end + + + private + + def collected + @collected ||= {} + end + end + + # A description of an expectation. + # An expectation has the power to call the proxy method or completely ignore it + class Expectation + + include ExpectationSyntax + + # the error_args that this expectation will raise an error with + def error_args + collected[:error_args] + end + + # the value that this expecation will return when executed + def return_value + collected[:return_value] + end + + # indicator for the mode to call the super +:before+, +:after+ and +nil+ + def super + collected[:super] + end + + # contains the callback if one is given + def callback + collected[:callback] + end + + # contains the callback that is used to return the value when this expectation + # is executed + def return_callback + collected[:return_callback] + end + + # contains the arguments that will be passed on to the block + def block_args + collected[:block_args] + end + + # The block that will be used as value provider for the block in the method + def block_callback + collected[:block_callback] + end + + # the block that will be used + def block + collected[:block] + end + + # sets the block callback + def block=(val) + collected[:block] = val + end + + # gets the method_name to which this expectation needs to listen to + def method_name + collected[:method_name] + end + + # the arguments that this expectation needs to be constrained by + def args + collected[:args] + end + + # Initializes a new instance of an expectation + def initialize(options={}) + collected[:any_args] = true + collected.merge!(options) + end + + # indicates whether this expecation will raise an event. + def has_error_args? + !collected[:error_args].nil? + end + + # indicates whether this expectation will return a value. + def has_return_value? + !collected[:return_value].nil? + end + + # call the super before the expectation + def super_before? + collected[:super] == :before + end + + # indicates whether super needs to be called somewhere + def call_super? + !collected[:super].nil? + end + + # indicates whether this expecation has a callback it needs to execute + def has_callback? + !collected[:callback].nil? + end + + # indicates whether this expectation has a block as value provider for the method call block + def has_block_callback? + !collected[:block_callback].nil? + end + + # a flag to indicate it has a return value callback + def has_return_callback? + !collected[:return_callback].nil? + end + + # executes this expectation with its configuration + def execute(*margs,&b) + ags = any_args? ? :any : (margs.empty? ? collected[:args] : margs) + do_raise_error + do_callback(ags) + do_block_callback(&b) + do_event_raise if respond_to?(:events) + + return collected[:return_callback].call(*margs) if has_return_callback? + return return_value if has_return_value? + nil + end + + def to_s #:nodoc: + "<Caricature::Expecation, method_name: #{method_name}, args: #{args}, error args: #{error_args}>" + end + alias :inspect :to_s + + + private + + def do_raise_error #:nodoc: + actual_raise *collected[:error_args] if has_error_args? + end + + def do_callback(ags) #:nodoc: + callback.call(*ags) if has_callback? + end + + def do_block_callback(&b) #:nodoc: + if b + ags = has_block_callback? ? collected[:block_callback].call : collected[:block_args] + b.call(*ags) + end + end + + + end + + # Constructs the expecation object. + # Used as a boundary between the definition and usage of the expectation + class ExpectationBuilder + + include ExpectationSyntax + + # initialises a new instance of the expectation builder + # this builder is passed into the block to allow only certain + # operations in the block. + def initialize(method_name) + @collected = { :method_name => method_name, :args => [], :any_args => true } + end + + + + # build up the expectation with the provided arguments + def build + Expectation.new collected + end + + end + end \ No newline at end of file