<commit_before>= Assert

Test::Unit style testing framework, just better than Test::Unit.

== What Assert is

* *Framework*: you define tests and the context they run in - Assert runs them.  Everything is pure ruby so use any 3rd party testing tools you like.  Create 3rd party tools that extend Assert behavior.
* *First* *Class*: everything is a first class object and can be extended to your liking (and should be)
* *MVC*: tests and how they are defined (M) and executed (C) are distinct from how you view the test results (V).
* *Backwards* *compatible*: (assuming a few minor tweaks) with Test::Unit test suites

== What Assert is not

* *Rspec*
* *Unit/Functional/Integration/etc*: Assert is agnostic - you define whatever kinds of tests you like (one or more of the above) and assert runs them in context.
* *Mock/Spec/BDD/Factories/etc*: Assert is the framework and there are a variety of 3rd party tools to do such things - feel free to use whatever you like.



== Description

Assert is a Test::Unit style testing framework.  This means you can write tests in Assert the same way you would with Test::Unit.  In addition, Assert adds some helpers and syntax sugar to enhance the way tests are written - most taken from ideas in Shoulda and Leftright.  Assert uses class-based contexts so if you want to nest your contexts, use good old inheritance.

Assert is tested using itself.  The tests are a pretty good place to look for examples and usage patterns.  In addition (TODO) check out the wiki and ./examples in the source.



== Installation

    gem install assert



== Usage

    require 'assert'

    class MyTests < Assert::Context

      def test_something
        assert_equal 1, 1
      end

    end



== Models
Assert models exist to define, collect, structure, and report on Assert test data.

=== Context
Context defines the scope that tests are run in.  When tests are run, a new instance of the test context is created and the test code is evaluated within scope of this context instance.  Context provides methods for defining tests and test callbacks and for generating test results in running tests.  Subclass context classes to achieve nested context behavior

=== Suite
Suite is reponsible for collecting and structuring tests and defines the set of tests to run be the test runner.  Tests are grouped within the suite by their context.  Suite provides access to the contexts, test, and test results to both test runners and views.  In addition, the Suite model provides some stats readers (ie. run_time, runnner_seed, etc...) for use by the test runner and views.

=== Test
Test defines the test code that needs to be run and the results generated by that test code.  Tests are aware of their context and are responsible for running their code in context.

=== Result
Result defines the data related to a test result.  There are a few kinds of test results available:
* Pass
* Fail
* Error
* Skip
* Ignore

Tests produce results as they are executed.  Every assert statement produces a result.  Some results, like Error and Skip, will halt execution.  Pass and Ignore results do not halt execution.  Fail results, by default, halt execution but there is an option to have them not halt execution.  Therefore, tests can have many results of varying types.

=== Macro
Macros are procs that define sets of test code and make it available for easy reuse.  Macros work nicely with the 'should' and 'test' context methods.



== User Options and Helpers
Assert provides ways for setting user-specfic options and helpers.  When Assert is setting itself up, the last setup step is to look for and require the file ~/.assert/options.rb.  This file is essentially a user level test helper file.  Use it to set options, configure assert extensions, setup or define how to view test results, etc.



== Running Tests
Assert uses a Runner object to run tests.  Any runner object should take the test suite and view as arguments and should provide a 'run' method that runs the tests and renders the view.

=== Default Runner
Assert provides a default Runner object for running test suites (https://github.com/teaminsight/assert/blob/master/lib/assert/runner.rb).  The default provides methods for running the tests, randomizing test order, and benchmarking test run time.  Feel free to extend this runner as you see fit.

=== Test Order
The default Runner object runs tests in random order and the `DefaultView` view will display the seed value.  If you want to run tests in a consistant order, set a 'runner_seed' environment variable.  Here's an example running tests with rake:

    $ rake test                   # run tests in random order
    $ rake test runner_seed=1234  # run tests seeding with '1234'

== Viewing Test Results

You have a few options when it comes to viewing test results in Assert.  Assert comes with its own `DefaultView` class that handles displaying test results.  However, you can extend or define your own view class and display your test results anyway you'd like.

First, lets look at the default: `Assert::View:DefaultView`.  This is the default view class.  Its output goes something like this:

# output something info about the test suite that is about to run
# run the test suite, printing out result abbreviations as the tests are run
# display any result details (from failing or error results) in reverse test/result order
# output some summary info

You can run asserts test suite using `rake test` and get a feel for what this default outputs.  This view have a few options you can tweak:

* `styled`: whether to apply ANSI styles to the output, default `true`
* `pass_styles`: how to style pass result output, default `:green`
* `fail_styles`: default `:red, :bold`
* `error_styles`: default `:yellow, :bold`
* `skip_styles`: default `:cyan`
* `ignore_styles`: default: `:magenta`

However, the view you use is configurable.  Define you own view class and specify it in your `~/.assert/options.rb` file:

    class MyCustomView < Assert::View::Base
      # define your view here...
    end

    Assert.options.view  MyCustomView.new

=== Anatomy of a View

A view class handles the logic and templating of test result output.  A view class should inherit from `Assert::View::Base`.  This provides the mechanisms and callbacks necessary for interacting with the test runner and gives access to a bunch of common helpers for reading test result data.

Each view should implement the `template` class method.  This method takes a block that is the template code.  Each template is rendered in its own scope.  This scope is given access to the View class and Runner callback with the `view` and `runner` methods.  The template block should, at some point, call `view.run_tests(runner)` to actually run the test suite.  Use the `_` method to output to the io stream.  See the `DefaultView` template for an example and usage.

Beyond that, each view can do as it sees fit.  Initialize how you wish, take whatever options you'd like, and output results as you see fit.

=== Using 3rd party views

To use a 3rd party custom view, you first require it in and then specify using the `Assert.options.view` option.  Assert provides a helper for requiring in views.  It can be used in two ways.  You can pass a fully qualified path to the helper and if it exists, will require it in.

    Assert::View.require_user_view '/path/to/my/view'

Alternatively, you can install/clone/copy/write your view implementations in `~/.assert/views` and require it in by name.  To have assert require it by name, have it installed at `<name>/lib/<name>.rb`.  For example:

    # assuming ~/.assert/views/my-custom-view/lib/my-custom-view.rb exists
    # this will work require it in
    Assert::View.require_user_view 'my-custom-view'

Once your view class is required in, use it and configure it just as you would any view.

=== Failure Handling
Assert, by default, will halt test execution when a test produces a Fail result.  However, Assert provides an option to not halt when Fail results are produced.  You can control how assert handles fails by either setting an option (in your user .assert/options.rb file) or by setting an env variable:

    Assert::Test.options.halt_on_fail false   # force not halting on fail results

    $ rake test halt_on_fail=true             # force halt on failure using an env var


=== Rake Tasks
Assert provides some rake task helpers that will scan your test folder and recursively generate rake tasks for each one of your test folders or files.  Test files must end in either `'_test.rb'` or `'_tests.rb'`.  Use this as an alternative to running ruby on each one of your test files individually.

As an example, say your test folder has a file structure like so:

    - test
    |  - basic_test.rb<commit_msg>some README feedback from @jcredding<commit_after>= Assert

Test::Unit style testing framework, just better than Test::Unit.

== What Assert is

* *Framework*: you define tests and the context they run in - Assert runs them.  Everything is pure ruby so use any 3rd party testing tools you like.  Create 3rd party tools that extend Assert behavior.
* *First* *Class*: everything is a first class object and can be extended to your liking (and should be)
* *MVC*: tests and how they are defined (M) and executed (C) are distinct from how you view the test results (V).
* *Backwards* *compatible*: (assuming a few minor tweaks) with Test::Unit test suites

== What Assert is not

* *Rspec*
* *Unit/Functional/Integration/etc*: Assert is agnostic - you define whatever kinds of tests you like (one or more of the above) and assert runs them in context.
* *Mock/Spec/BDD/Factories/etc*: Assert is the framework and there are a variety of 3rd party tools to do such things - feel free to use whatever you like.



== Description

Assert is a Test::Unit style testing framework.  This means you can write tests in Assert the same way you would with Test::Unit.  In addition, Assert adds some helpers and syntax sugar to enhance the way tests are written - most taken from ideas in Shoulda and Leftright.  Assert uses class-based contexts so if you want to nest your contexts, use good old inheritance.

Assert is tested using itself.  The tests are a pretty good place to look for examples and usage patterns.  In addition (TODO) check out the wiki and ./examples in the source.



== Installation

    gem install assert



== Usage

    require 'assert'

    class MyTests < Assert::Context

      def test_something
        assert_equal 1, 1
      end

    end



== Models
Assert models exist to define, collect, structure, and report on Assert test data.

=== Context
Context defines the scope that tests are run in.  When tests are run, a new instance of the test context is created and the test code is evaluated within scope of this context instance.  Context provides methods for defining tests and test callbacks and for generating test results in running tests.  Subclass context classes to achieve nested context behavior

=== Suite
Suite is reponsible for collecting and structuring tests and defines the set of tests to run be the test runner.  Tests are grouped within the suite by their context.  Suite provides access to the contexts, test, and test results to both test runners and views.  In addition, the Suite model provides some stats readers (ie. run_time, runnner_seed, etc...) for use by the test runner and views.

=== Test
Test defines the test code that needs to be run and the results generated by that test code.  Tests are aware of their context and are responsible for running their code in context.

=== Result
Result defines the data related to a test result.  There are a few kinds of test results available:
* Pass
* Fail
* Error
* Skip
* Ignore

Tests produce results as they are executed.  Every assert statement produces a result.  Some results, like Error and Skip, will halt execution.  Pass and Ignore results do not halt execution.  Fail results, by default, halt execution but there is an option to have them not halt execution.  Therefore, tests can have many results of varying types.

=== Macro
Macros are procs that define sets of test code and make it available for easy reuse.  Macros work nicely with the 'should' and 'test' context methods.



== User Options and Helpers
Assert provides ways for setting user-specfic options and helpers.  When Assert is setting itself up, the last setup step is to look for and require the file ~/.assert/options.rb.  This file is essentially a user level test helper file.  Use it to set options, configure assert extensions, setup or define how to view test results, etc.



== Running Tests
Assert uses a Runner object to run tests.  Any runner object should take the test suite and view as arguments and should provide a 'run' method that runs the tests and renders the view.

=== Default Runner
Assert provides a default Runner object for running test suites (https://github.com/teaminsight/assert/blob/master/lib/assert/runner.rb).  The default provides methods for running the tests, randomizing test order, and benchmarking test run time.  Feel free to extend this runner as you see fit.

=== Test Order
The default Runner object runs tests in random order and the `DefaultView` view will display the seed value.  If you want to run tests in a consistant order, set a 'runner_seed' environment variable.  Here's an example running tests with rake:

    $ rake test                   # run tests in random order
    $ rake test runner_seed=1234  # run tests seeding with '1234'

== Viewing Test Results

You have a few options when it comes to viewing test results in Assert.  Assert comes with its own `DefaultView` class that handles displaying test results.  However, you can extend or define your own view class and display your test results anyway you'd like.

First, lets look at the default: `Assert::View:DefaultView`.  This is the default view class.  Its output goes something like this:

# output some info about the test suite that is about to run
# run the test suite, printing out result abbreviations as the tests are run
# display any result details (from failing or error results) in reverse test/result order
# output some summary info

You can run asserts test suite using `rake test` and get a feel for what this default outputs.  This view has a few options you can tweak:

* `styled`: whether to apply ANSI styles to the output, default `true`
* `pass_styles`: how to style pass result output, default `:green`
* `fail_styles`: default `:red, :bold`
* `error_styles`: default `:yellow, :bold`
* `skip_styles`: default `:cyan`
* `ignore_styles`: default: `:magenta`

However, the view you use is configurable.  Define you own view class and specify it in your `~/.assert/options.rb` file:

    class MyCustomView < Assert::View::Base
      # define your view here...
    end

    Assert.options.view  MyCustomView.new

=== Anatomy of a View

A view class handles the logic and templating of test result output.  A view class should inherit from `Assert::View::Base`.  This provides the mechanisms and callbacks necessary for interacting with the test runner and gives access to a bunch of common helpers for reading test result data.

Each view should implement the `template` class method.  This method takes a block that is the template code.  Each template is rendered in its own scope.  This scope is given access to the View class and Runner callback with the `view` and `runner` methods.  The template block should, at some point, call `view.run_tests(runner)` to actually run the test suite.  Use the `_` method to output to the io stream.  See the `DefaultView` template for an example and usage.

Beyond that, each view can do as it sees fit.  Initialize how you wish, take whatever options you'd like, and output results as you see fit.

=== Using 3rd party views

To use a 3rd party custom view, you first require it in and then specify using the `Assert.options.view` option.  Assert provides a helper for requiring in views.  It can be used in two ways.  You can pass a fully qualified path to the helper and if it exists, will require it in.

    Assert::View.require_user_view '/path/to/my/view'

Alternatively, you can install/clone/copy/write your view implementations in `~/.assert/views` and require it in by name.  To have assert require it by name, have it installed at `~/assert/views/view_name/lib/view_name.rb` (this structure is compatible with popular conventions in rubygem development). For example:

    # assuming ~/.assert/views/my-custom-view/lib/my-custom-view.rb exists
    # this will work require it in
    Assert::View.require_user_view 'my-custom-view'

Once your view class is required in, use it and configure it just as you would any view.

=== Failure Handling
Assert, by default, will halt test execution when a test produces a Fail result.  However, Assert provides an option to not halt when Fail results are produced.  You can control how assert handles fails by either setting an option (in your user .assert/options.rb file) or by setting an env variable:

    Assert::Test.options.halt_on_fail false   # force not halting on fail results

    $ rake test halt_on_fail=true             # force halt on failure using an env var


=== Rake Tasks
Assert provides some rake task helpers that will scan your test folder and recursively generate rake tasks for each one of your test folders or files.  Test files must end in either `'_test.rb'` or `'_tests.rb'`.  Use this as an alternative to running ruby on each one of your test files individually.

As an example, say your test folder has a file structure like so:

    - test
    |  - basic_test.rb
{'fraction_non_alphanumeric': 0.05556811758055399, 'fraction_numerical': 0.0016958733747880158, 'mean_word_length': 3.8641737695903218, 'pattern_counts': {'":': 0, '<': 9, '<?xml version=': 0, '>': 5, 'https://': 2, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '3973542', 'n_tokens_mistral': 4531, 'n_tokens_neox': 4374, 'n_words': 2695}