Module: Aquarium::Extras::DesignByContract

Includes:
Aspects
Included in:
Object
Defined in:
lib/aquarium/extras/design_by_contract.rb

Overview

A simple Design by Contract module. Adds advice to test that the contract, which is specified with a block passes. Note that it doesn’t attempt to handle the correct behavior under contract inheritance. A usage example is included in the Examples as part of the distribution and it is also shown on the web site. Normally, you want to disable the contracts in production runs, so you avoid the overhead. To do this effectively, call DesignByContract.disable_all before any contracts are created. That will prevent all of the aspects from being created along with their overhead. Warning: This module automatically includes Aquarium::DSL into the class with the contract and it adds the :precondition, :postcondition, and the :invariant methods to Object!

Defined Under Namespace

Classes: ContractError

Constant Summary collapse

@@enabled =
true

Class Method Summary collapse

Instance Method Summary collapse

Class Method Details

.disable_allObject

Disable creation of any subsequent contracts and disable execution of existing contracts. That is, while contracts are disabled, it no existing contracts will be executed and any attempts to define new contracts will be ignored.



36
37
38
# File 'lib/aquarium/extras/design_by_contract.rb', line 36

def self.disable_all
  @@enabled = false
end

.enable_allObject

Enable creation and execution of contracts



29
30
31
# File 'lib/aquarium/extras/design_by_contract.rb', line 29

def self.enable_all
  @@enabled = true
end

Instance Method Details

#invariant(*args, &contract_block) ⇒ Object



52
53
54
55
56
57
58
59
60
61
# File 'lib/aquarium/extras/design_by_contract.rb', line 52

def invariant *args, &contract_block
  return unless @@enabled
  message = handle_message_arg args
  Aspect.new make_args(:around, *args) do |jp, obj, *params|
    DesignByContract.test_condition "invariant failure (before invocation): #{message}", jp, obj, *params, &contract_block
    result = jp.proceed
    DesignByContract.test_condition "invariant failure (after invocation): #{message}", jp, obj, *params, &contract_block
    result
  end
end

#postcondition(*args, &contract_block) ⇒ Object



46
47
48
49
50
# File 'lib/aquarium/extras/design_by_contract.rb', line 46

def postcondition *args, &contract_block
  return unless @@enabled
  message = handle_message_arg args
  add_advice :after_returning, "postcondition", message, *args, &contract_block
end

#precondition(*args, &contract_block) ⇒ Object



40
41
42
43
44
# File 'lib/aquarium/extras/design_by_contract.rb', line 40

def precondition *args, &contract_block
  return unless @@enabled
  message = handle_message_arg args
  add_advice :before, "precondition", message, *args, &contract_block
end