[libtest-bdd-cucumber-perl] 02/02: Highlight parameters correctly using @- and @+
Intrigeri
intrigeri at moszumanska.debian.org
Thu Jun 19 10:18:54 UTC 2014
This is an automated email from the git hooks/post-receive script.
intrigeri pushed a commit to annotated tag 0.25
in repository libtest-bdd-cucumber-perl.
commit 963e24908a5531a8f12d92880d2cee8d48b968f2
Author: Peter Sergeant <pete at clueball.com>
Date: Sun Jun 8 09:32:18 2014 +0100
Highlight parameters correctly using @- and @+
---
CHANGES | 3 ++
dist.ini | 3 +-
lib/Test/BDD/Cucumber/Errors.pm | 3 +-
lib/Test/BDD/Cucumber/Executor.pm | 66 +++++++++++++++++++++--
lib/Test/BDD/Cucumber/Harness.pm | 5 +-
lib/Test/BDD/Cucumber/Harness/Data.pm | 3 +-
lib/Test/BDD/Cucumber/Harness/TermColor.pm | 22 ++++----
t/260_match_matcher.t | 84 ++++++++++++++++++++++++++++++
8 files changed, 171 insertions(+), 18 deletions(-)
diff --git a/CHANGES b/CHANGES
index c74fe71..1f2c909 100644
--- a/CHANGES
+++ b/CHANGES
@@ -1,4 +1,7 @@
-----
+0.25: 08 Jun 2014
+ - Highlight parameters properly in TermColor output using @+ and @-
+ https://github.com/sheriff/test-bdd-cucumber-perl/issues/24
0.24: 07 Jun 2014
- Replacing string `eval` with block `eval` for requiring test harnesses -
thanks Paul Cochrane
diff --git a/dist.ini b/dist.ini
index de0d179..6d06616 100644
--- a/dist.ini
+++ b/dist.ini
@@ -1,5 +1,5 @@
name = Test-BDD-Cucumber
-version = 0.24
+version = 0.25
abstract = Feature-complete Cucumber-style testing in Perl
main_module = lib/Test/BDD/Cucumber.pm
author = ['Peter Sergeant <pete at clueball.com>','Ben Rogers <ben at bdr.org>']
@@ -29,6 +29,7 @@ Getopt::Long = 0
JSON::MaybeXS = 0
Module::Runtime = 0
Moose = 0
+Number::Range = 0
Path::Class = 0
Storable = 0
Term::ANSIColor = 3.00
diff --git a/lib/Test/BDD/Cucumber/Errors.pm b/lib/Test/BDD/Cucumber/Errors.pm
index 33128ed..2c97fc3 100644
--- a/lib/Test/BDD/Cucumber/Errors.pm
+++ b/lib/Test/BDD/Cucumber/Errors.pm
@@ -68,7 +68,7 @@ sub parse_error_from_line {
_get_context_range( $line->document, $feature_line );
my $formatted_lines;
- for ( 0 .. 4 ) {
+ for ( 0 .. $#lines ) {
my $actual_line = $start_line + $_;
my $mark = ($feature_line == $actual_line) ? '*' : '|';
$formatted_lines .=
@@ -112,6 +112,7 @@ sub _get_context_range {
# Then cut it off
@range = grep { $_ >= $min_range } @range;
+ @range = grep { $_ <= $max_range } @range;
return( $range[0], map { $document->lines->[$_ - 1]->raw_content } @range );
}
diff --git a/lib/Test/BDD/Cucumber/Executor.pm b/lib/Test/BDD/Cucumber/Executor.pm
index 38c61ec..f940ca9 100644
--- a/lib/Test/BDD/Cucumber/Executor.pm
+++ b/lib/Test/BDD/Cucumber/Executor.pm
@@ -15,7 +15,9 @@ use Moose;
use FindBin::libs;
use Storable qw(dclone);
use List::Util qw/first/;
+use List::MoreUtils qw/pairwise/;
use Test::Builder;
+use Number::Range;
use Test::BDD::Cucumber::StepContext;
use Test::BDD::Cucumber::Util;
@@ -362,6 +364,9 @@ sub dispatch {
# Say we're about to start it up
$context->harness->step( $context );
+ # Store the string position of matches for highlighting
+ my @match_locations;
+
# New scope for the localization
my $result;
{
@@ -371,6 +376,8 @@ sub dispatch {
# Execute!
eval {
no warnings 'redefine';
+
+ # Set S and C to be step-specific values before executing the step
local *Test::BDD::Cucumber::StepFile::S = sub {
return $context->stash->{'scenario'}
};
@@ -378,8 +385,17 @@ sub dispatch {
return $context
};
- # Rematch the regex, setting $1, $2, and friends correctly
- $context->matches([ $context->text =~ $regular_expression ]);
+ # Take a copy of this. Turns out actually matching against it
+ # directly causes all sorts of weird-ass eisenbugs which mst has
+ # promised to investigate.
+ my $text = $context->text;
+
+ # Save the matches
+ $context->matches([ $text =~ $regular_expression ]);
+
+ # Save the location of matched subgroups for highlighting hijinks
+ my @starts = @-; my @ends = @+;
+ @match_locations = pairwise {[$a, $b]} @starts, @ends;
# OK, actually execute
$coderef->( $context )
@@ -401,14 +417,58 @@ sub dispatch {
});
}
+
+ my @clean_matches = $self->_extract_match_strings(
+ $context->text, \@match_locations
+ );
+ @clean_matches = [ 0, $context->text ] unless @clean_matches;
+
# Say the step is done, and return the result. Happens outside
# the above block so that we don't have the localized harness
# anymore...
$context->harness->add_result( $result );
- $context->harness->step_done( $context, $result );
+ $context->harness->step_done( $context, $result, \@clean_matches );
return $result;
}
+sub _extract_match_strings {
+ my ($self, $text, $locations) = @_;
+
+ # Clean up the match locations
+ my @match_locations = grep {
+ ( $_->[0] != $_->[1] ) && # No zero-length matches
+ # And nothing that matched the full string
+ (! (( $_->[0] == 0 ) && (( $_->[1] == length $text ) )))
+ } grep { defined $_ && ref $_ && defined $_->[0] && defined $_->[1] }
+ @$locations;
+
+ return unless @match_locations;
+
+ # Consolidate overlaps
+ my $range = Number::Range->new();
+
+ {
+ # Don't want a complain about numbers already in range, as that's
+ # expected for nested matches
+ no warnings;
+ $range->addrange($_->[0] . '..' . ($_->[1]-1) ) for @match_locations;
+ }
+
+ # Walk the string, splitting
+ my @parts = ([0,'']);
+ for ( 0 .. ((length $text) - 1) ) {
+ my $to_highlight = $range->inrange( $_ );
+ my $character = substr( $text, $_, 1 );
+
+ if ( $parts[-1]->[0] != $to_highlight ) {
+ push( @parts, [$to_highlight, ''] );
+ }
+
+ $parts[-1]->[1] .= $character;
+ }
+
+ return @parts;
+}
sub _test_status {
my $self = shift;
diff --git a/lib/Test/BDD/Cucumber/Harness.pm b/lib/Test/BDD/Cucumber/Harness.pm
index 32ad781..0219606 100644
--- a/lib/Test/BDD/Cucumber/Harness.pm
+++ b/lib/Test/BDD/Cucumber/Harness.pm
@@ -68,7 +68,10 @@ sub scenario_done { my ( $self, $scenario, $dataset ) = @_; }
Called at the start and end of step execution respectively. Both methods
accept a L<Test::BDD::Cucmber::StepContext> object. C<step_done> also accepts
-a L<Test::BDD::Cucumber::Model::Result> object.
+a L<Test::BDD::Cucumber::Model::Result> object and an arrayref of arrayrefs with
+locations of consolidated matches, for highlighting.
+
+ [ [2,5], [7,9] ]
=cut
diff --git a/lib/Test/BDD/Cucumber/Harness/Data.pm b/lib/Test/BDD/Cucumber/Harness/Data.pm
index c5ff28a..f29f2c2 100644
--- a/lib/Test/BDD/Cucumber/Harness/Data.pm
+++ b/lib/Test/BDD/Cucumber/Harness/Data.pm
@@ -124,9 +124,10 @@ sub step {
}
sub step_done {
- my ($self, $context, $result) = @_;
+ my ($self, $context, $result, $highlights) = @_;
$self->current_step->{'result'} = $result;
+ $self->current_step->{'highlights'} = $highlights;
push( @{ $self->current_scenario->{'steps'} }, $self->current_step );
$self->current_step({});
}
diff --git a/lib/Test/BDD/Cucumber/Harness/TermColor.pm b/lib/Test/BDD/Cucumber/Harness/TermColor.pm
index b4b055e..e7b0164 100644
--- a/lib/Test/BDD/Cucumber/Harness/TermColor.pm
+++ b/lib/Test/BDD/Cucumber/Harness/TermColor.pm
@@ -37,7 +37,6 @@ BEGIN {
}
use Term::ANSIColor;
-use Test::BDD::Cucumber::Util;
use Test::BDD::Cucumber::Model::Result;
extends 'Test::BDD::Cucumber::Harness';
@@ -82,7 +81,7 @@ sub scenario_done { print "\n"; }
sub step {}
sub step_done {
- my ($self, $context, $result ) = @_;
+ my ($self, $context, $result, $highlights ) = @_;
my $color;
my $follow_up = [];
@@ -109,20 +108,20 @@ sub step_done {
my $text;
- if ( $context->is_hook )
- {
+ if ( $context->is_hook ) {
$color eq 'red' or return;
$text = 'In ' . ucfirst( $context->verb ) . ' Hook';
- }
- else
- {
+ undef $highlights;
+ } else {
$text = $context->step->verb_original . ' ' . $context->text;
+ $highlights = [[ 0, $context->step->verb_original . ' ' ], @$highlights];
}
$self->_display({
indent => 4,
color => $color,
text => $text,
+ highlights => $highlights,
highlight => 'bright_cyan',
trailing => 0,
follow_up => $follow_up,
@@ -174,14 +173,15 @@ sub _display {
# Highlight as appropriate
my $color = color $options->{'color'};
- if ( $options->{'highlight'} ) {
+ if ( $options->{'highlight'} && $options->{'highlights'} ) {
my $reset = color 'reset';
my $base = color $options->{'color'};
my $hl = color $options->{'highlight'};
- my $text = $base . Test::BDD::Cucumber::Util::bs_quote( $options->{'text'} );
- $text =~ s/("(.+?)"|[ ^](\d[-?\d\.]*))/$reset$hl$1$reset$base/g;
- print Test::BDD::Cucumber::Util::bs_unquote( $text );
+ for ( @{$options->{'highlights'}} ) {
+ my ($flag, $text) = @$_;
+ print $reset . ( $flag ? $hl : $base ) . $text . $reset;
+ }
# Normal output
} else {
diff --git a/t/260_match_matcher.t b/t/260_match_matcher.t
new file mode 100644
index 0000000..2983b85
--- /dev/null
+++ b/t/260_match_matcher.t
@@ -0,0 +1,84 @@
+#!perl
+
+use strict;
+use warnings;
+
+use Test::More;
+use Test::Differences;
+use Test::BDD::Cucumber::Parser;
+use Test::BDD::Cucumber::Executor;
+use Test::BDD::Cucumber::Harness::Data;
+
+# Check that when we execute steps we get a nicely split string back for
+# highlighting
+for (
+ [
+ "Simple example",
+ "the quick brown fox",
+ qr/the (quick) brown (fox)/,
+ [
+ [ 0 => 'the ' ],
+ [ 1 => 'quick' ],
+ [ 0 => ' brown ' ],
+ [ 1 => 'fox' ],
+ ]
+ ],
+ [
+ "Non-capture",
+ "the quick brown fox",
+ qr/the (?:quick) brown (fox)/,
+ [
+ [ 0 => 'the quick brown ' ],
+ [ 1 => 'fox' ],
+ ]
+ ],
+ [
+ "Nested-capture",
+ "the quick brown fox",
+ qr/the (q(uic)k) brown (fox)/,
+ [
+ [ 0 => 'the ' ],
+ [ 1 => 'quick' ],
+ [ 0 => ' brown ' ],
+ [ 1 => 'fox' ],
+ ]
+ ],
+ [
+ "Multi-group",
+ "the quick brown fox",
+ qr/the (.)+ brown (fox)/,
+ [
+ [ 0 => 'the quic' ],
+ [ 1 => 'k' ],
+ [ 0 => ' brown ' ],
+ [ 1 => 'fox' ],
+ ]
+ ],
+) {
+ my ( $test_name, $step_text, $step_re, $expected ) = @$_;
+
+ # Set up a feature
+ my $feature = Test::BDD::Cucumber::Parser->parse_string(
+ "Feature: Foo\n\tScenario:\n\t\tGiven $step_text\n"
+ );
+
+ # Set up step definitions
+ my $executor = Test::BDD::Cucumber::Executor->new();
+ $executor->add_steps(
+ [ Given => $step_re, sub { 1; } ],
+ );
+
+ # Instantiate the harness, and run it
+ my $harness = Test::BDD::Cucumber::Harness::Data->new();
+ $executor->execute( $feature, $harness );
+
+ # Get the step result
+ my $step = $harness->features->[0]->{'scenarios'}->[0]->{'steps'}->[0];
+ my $highlights = $step->{'highlights'};
+
+ is_deeply( $highlights, $expected, $test_name ) || eq_or_diff(
+ $highlights, $expected
+ );
+}
+
+done_testing();
\ No newline at end of file
--
Alioth's /usr/local/bin/git-commit-notice on /srv/git.debian.org/git/pkg-perl/packages/libtest-bdd-cucumber-perl.git
More information about the Pkg-perl-cvs-commits
mailing list