Skip to content

A Perl module to declare subtests using subroutine attributes

License

Notifications You must be signed in to change notification settings

bmarcotte/Test-Subtest-Attribute

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

20 Commits
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

NAME
    Test::Subtest::Attribute - Declare subtests using subroutine attributes

VERSION
    version 0.04

SYNOPSIS
      use Test::More;
      use Test::Subtest::Attribute qw( subtests );

      sub subtest_foo :Subtest {
          ok( 1, 'foo is OK' );
          return 1;
      }

      sub subtest_bar :Subtest( 'name for bar' ) {
          ok( 1, 'bar is OK' );
          return 1;
      }

      subtests()->run();
      done_testing();

DESCRIPTION
    This module provides a simple way, using a subroutine attribute called
    ":Subtest", to declare normal subroutines to be subtests in a test
    script.

    Subtests are typically declared using a call to the "subtest()" function
    from Test::More, in one of the two following ways:

      subtest 'name1'  => sub { ... };  # An anonymous sub
      subtest 'name 2' => \&some_named_sub;

    The first way can quickly lead to long anonymous subs that can present
    issues when looking at stacktraces for debugging, profiling, logging,
    etc. The second way usually leads to repeating the same, or similar,
    names for each subtest subroutine, in addition to declaring the sub
    itself, e.g.:

      subtest 'test_this' => \&test_this;
      subtest 'test_that' => \&test_that;
      ...
      sub test_this { ... }
      sub test_that { ... }
      ...

    This module lets you declare those subtests without calls to the
    "subtest()" function, by simply adding a ":Subtest" attribute to any
    subroutine that you'd like to have executed as a subtest, like so:

      sub subtest_name1 :Subtest {
        ...
      }

    That declares a subtest named 'name1' (the subtest_ part of the name, if
    present, is automatically stripped off).

    If you'd like to specify the name of the subtest explicitly, which is
    handy if you'd like to use a name that includes characters. such as
    spaces, that aren't allowed in bareword identifiers, you can do so by
    providing an argument to the ":Subtest" attribute like so:

      sub some_named_sub :Subtest('name 2') {
        ...
      }

    When you're done declaring subtests, you run all the ones you've queued
    up by calling "subtests()-"run()>.

    From this module, most test scripts will only need to use the ":Subtest"
    attribute and the "run()" method described below. Most of the other
    methods described below are for more advanced usage, such as in test
    modules that might want to conditionally add, remove, or otherwise
    manipulate the subtests managed herein.

METHODS
  add
      subtests()->add( coderef => \%my_sub );

    Adds a subroutine to the current queue of subtests. This method can
    accept a number of named arguments.

    name
        Indicates the name of this particular subtest. If the name isn't
        unique, it will replace the previously declared subtest with the
        same name.

    where
        A value of 'prepend' indicates the subtest should be added to the
        head of the queue of subtests. A value of 'append' indicates the
        subtest should be added to the end of the queue of subtests. If not
        given, the default is to append the subtest.

    coderef
        A reference to the subroutine (named or anonymous) to eventually
        call for this subtest.

    package
        The package from which the subtest should be invoked. Typically,
        this would be the package that the subroutine lives in. Calling the
        "run()" method with an "invocant" argument takes precedence over
        this. It also appears in the fully qualified subroutine name, if
        "run()" is called in verbose mode. Defaults to "main" if not given.

    sub_name
        The name of the subroutine to call for this subtest. If "coderef" is
        defined, this is only needed for display purposes. If "coderef" is
        not defined, the "run()" method will attempt to find a sub with this
        name that can be called via the "invocant" or "package" arguments.

  prepend
      subtests()->prepend( coderef => \%my_sub );

    Adds a subtest to the head of the current queue of subtests. Takes the
    same arguments as the "add()" method, and sets the "where" param to
    "prepend".

  append
      subtests()->append( coderef => \%my_sub );

    Adds a subtest to the end of the current queue of subtests. Takes the
    same arguments as the "add()" method, and sets the "where" param to
    "append".

  remove
      subtests()->remove( $name_or_coderef );

    Removes the indicated subtest(s) from the queue. The argument can either
    be the name or the coderef associated with the subtest.

  get_all
      subtests()->get_all();

    Returns a list of all of the subtests currently in the queue.

  run
      subtests()->run( %args );

    Runs all of the subtests that are currently in the queue.

    This method can be called with any of the following arguments:

    builder
        The test builder to use. If none is given, a new Test::Builder
        instance will be created.

    invocant
        If given, the subtest subroutines will be invoked via this
        reference.

        NOTE: When the ":Subtest" attribute is used, the name of the package
        that the subroutine appears in will be remembered in the subtest
        metadata, and that package name will be used if no "invocant"
        argument is given explicitly when calling this method. If that value
        happens to be undefined for any reason, the package name "main" is
        the default instead.

    verbose_names
        When given, and set to a true value, subtest names will be displayed
        with " [sub name]" appended. If the package name can be determined,
        and is not "main", the sub name will be fully qualified with such.

FUNCTIONS
  subtests
    Returns a handle that can be used to invoke the methods in this module.
    As such, this is the only function exported by this module.

    Currently, this just returns the name of this package, but, in the
    future, it could return an object instance.

SEE ALSO
    Attribute::Handlers Test::Builder

AUTHOR
    Ben Marcotte <bmarcotte NOSPAM cpan.org>

COPYRIGHT AND LICENSE
    This software is copyright (c) 2017 by Ben Marcotte.

    This is free software; you can redistribute it and/or modify it under
    the same terms as the Perl 5 programming language system itself.

About

A Perl module to declare subtests using subroutine attributes

Topics

Resources

License

Stars

Watchers

Forks

Packages

No packages published

Languages