Giter Club home page Giter Club logo

picotest's Introduction

= Picotest - simple reduced tests

Picotest is a gem which allows to write complete test suites in a few lines, targeted primarily to test separated methods, algorithms or little snippets of code

== Installation

The install is as simple as execute the well-known gem install:

sudo gem install picotest

== Known Limitations & Issues

* Reverse oracle test only can be compared using exact equals (see sqrt example)
* Metaprogramming of input/output pairs are ugly
* Oracle testing does not allow expectation test making difficult to debug failing tests
* Complete lack of RDoc

== Usage

To use picotest you should write suites using suite method, each suite is defined by a hash and an optional
description, the keys of the hash are used as input for the method and the corresponding values as expected output

For example, to specify that the method receiving 1 should return 1, receiving 4 should return 2 and receiving 9 should return 3, use the following syntax:

  suite(1 => 1, 4 => 2, 9 => 3)

Or:

  suite("integer sqrt", 1 => 1, 4 => 2, 9 => 3)

After that, you should specify the test:

  suite("integer sqrt", 1 => 1, 4 => 2, 9 => 3).test(Math.method(:sqrt))

To run test, you should set the environment variable PICOTEST_RUN to 1

=== Environment variables

All environments are activated setting their value to 1, other values distinct from 1 will be ignored

PICOTEST_RUN        enables the execution of test
PICOTEST_REPORT     enables reports of test on standard output and disables Picotest::Fail exceptions when test fails
PICOTEST_AUTOTEST   enables tests of picotest itself
PICOTEST_FAIL       simulate failure of all tests, for picotest test purpose

== Code Examples

See samples directory under the gem root

=== Example 1: basic usage of suite and test method

  class X
    def foo(data)
      data.split(";")[2].to_f
    end
  end

  suite( "aaa;xxx;1.0;999" => 1.0, ";;3.2" => 3.2).test X.new.method(:foo)

=== Example 2: Input sets

Both -2 and 2 should evaluate to 4 on lambda{|x|x*x}

  suite(_set(-2,2) => 4).test lambda{|x|x*x}

=== Example 3: Oracle testing

Using a lambda as value on the hash can be used to specify a rule to validate output-input pairs, useful for oracle testing

  suite(4 => lambda{|y,x| y*y == x}).test Math.method(:sqrt)

=== Example 4: Oracle testing with input sets

This time, the validation rule must considerate the imprecision of floats and check using a error margin

  suite(_set(1,2,3,4,5) => lambda{|y,x| (y*y - x).abs<0.00001}).test Math.method(:sqrt)
  suite(_set(*(1..100) ) => lambda{|y,x| (y*y - x).abs<0.00001}).test Math.method(:sqrt)

=== Example 5: Reversed oracle

When valid inputs can be generated from output (i.e. float 1.0 output correspond to string "aaa;xxx;1.0;" input)

  class X
    def foo(data)
      data.split(";")[2].to_f
    end
  end

  suite( lambda{|x| ";;#{x}"} => _set(*(1..20).map(&:to_f)) ).test X.new.method(:foo)

=== Example 6: Testing methods of input objects

  suite( "a b" => ["a","b"]).test :split
  suite( lambda{|x|x.join " "} => _set(["a","b"], ["x","y","z","1"], ["aaa","bbb"]) ).test :split

=== Example 7: Testing multiple argument inputs

  class X
    def sum(*x)
      x.inject{|a,b| a+b}
    end
  end

  suite( 1 => 1, [1,2] => 3, [1,2,3] => 6 ).test X.new.method(:sum)
  suite(_set(*(1..100)) => lambda{|y,x| y == x},
      _set([1,2],[3,4],[4,6],[5,6]) => lambda{|y,x1,x2| y == x1+x2},
      _set([1,2,3],[3,4,5],[4,6,7],[5,6,7]) => lambda{|y,x1,x2,x3| y == x1+x2+x3}
      ).test X.new.method(:sum)

=== Example 8: Mocking instance variable

  class X
    def foo(data)
      data.split(";")[@fieldno].to_f
    end
  end

  suite(hash).test X.new.method(:foo).mock(:@fieldno => 2)

=== Example 9: Mocking method on receiver object

  class X
    attr_accessor :fieldno
    def foo(data)
      data.split(";")[fieldno].to_f
    end
  end

  suite(hash).test X.new.method(:foo).mock(:fieldno => 2)

=== Example 10: Mock objects

  class X
    attr_accessor :another_object
    def foo(data)
      data.split(";")[another_object.fieldno].to_f
    end
  end

  suite(hash).test X.new.method(:foo).mock(:another_object => mock(:fieldno => 2) )

=== Example 11: Mocking method on receiver object

  class X
    attr_accessor :another_object
    def foo(data)
      another_object.invented_here_split(data,";")[@fieldno].to_f
    end
  end

  # you can specify the implementatioin of methods using lambdas
  suite(hash).test X.new.method(:foo).mock(
    :another_object => mock(:invented_here_split => lambda{|str,sep| str.split(sep) }), 
    :@fieldno => 2 )

  # Since :split.to_proc is equivalent to lambda{|str,sep| str.split(sep) }, you can also use:
  suite(hash).test X.new.method(:foo).mock(
    :another_object => mock(:invented_here_split => :split.to_proc), 
    :@fieldno => 2 )


=== Example 12: Exceptions

  class X
    def foo(a)
      raise ArgumentError unless a.kind_of? Numeric

      a*2
    end
  end

  suite(1 => 2, 2 => 4, 3 => 6, "00" => _raise(ArgumentError)).test(X.new.method(:foo))

== Copying

Copyright (c) 2012 Dario Seminara, released under the GPL License (see LICENSE)

picotest's People

Contributors

tario avatar

Stargazers

 avatar  avatar

Watchers

 avatar  avatar

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    ๐Ÿ–– Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. ๐Ÿ“Š๐Ÿ“ˆ๐ŸŽ‰

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google โค๏ธ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.