You've already forked pgbackrest
mirror of
https://github.com/pgbackrest/pgbackrest.git
synced 2025-11-06 08:49:29 +02:00
Remove integration expect log testing.
Integration expect log testing was originally used as a rough-and-ready way to make sure that certain code paths were being executed before the unit tests existed. Now that we have 100% unit test coverage (with expect log testing) the value of the integration expect tests seems minimal at best.
But they do cause numerous issues:
- Maintenance of the expect code and replacements that are required to keep logs reproducible.
- Even a trivial change can cause massive churn in the expect logs, e.g. d9088b2. These changes should be minutely audited but since the expect logs have little value now it is seldom worth the effort.
- The OS version used to do expect testing (RHEL7) can only be used to test one version of PostgreSQL. This makes it hard to balance the PostgreSQL version testing between OS versions.
- When a commit affects expect logs it is not clear (especially for new developers) how to regenerate them and our contributing guide is silent on the issue.
The goal is to migrate the integration tests to C and expect testing is not part of that plan. It seems best to get rid of them now.
This commit is contained in:
@@ -62,7 +62,6 @@ sub codeCountScan
|
||||
$strFile =~ '^test/certificate/' ||
|
||||
$strFile =~ '^test/code-count/' ||
|
||||
$strFile =~ '^test/data/' ||
|
||||
$strFile =~ '^test/expect/' ||
|
||||
$strFile =~ '^test/patch/' ||
|
||||
$strFile =~ '^test/result/' ||
|
||||
$strFile =~ '^test/scratch' ||
|
||||
|
||||
@@ -48,8 +48,6 @@ use constant TESTDEF_COVERAGE => 'coverage
|
||||
push @EXPORT, qw(TESTDEF_COVERAGE);
|
||||
use constant TESTDEF_CORE => 'core';
|
||||
push @EXPORT, qw(TESTDEF_CORE);
|
||||
use constant TESTDEF_EXPECT => 'expect';
|
||||
push @EXPORT, qw(TESTDEF_EXPECT);
|
||||
use constant TESTDEF_C => 'c';
|
||||
push @EXPORT, qw(TESTDEF_C);
|
||||
use constant TESTDEF_DEFINE => 'define';
|
||||
@@ -121,13 +119,11 @@ sub testDefLoad
|
||||
{
|
||||
my $hModuleType = $hTestDef->{$strModuleType};
|
||||
|
||||
my $bExpect = false; # By default don't run expect tests
|
||||
my $bContainer = true; # By default run tests in a single container
|
||||
my $bIndividual = false; # By default runs are all executed in the same container
|
||||
|
||||
if ($strModuleType eq TESTDEF_INTEGRATION)
|
||||
{
|
||||
$bExpect = true; # Integration tests run expect tests
|
||||
$bContainer = false; # Integration tests can run in multiple containers
|
||||
$bIndividual = true; # Integration tests can change containers on each run
|
||||
}
|
||||
@@ -167,7 +163,6 @@ sub testDefLoad
|
||||
$hTestDefHash->{$strModule}{$strTest}{&TESTDEF_C} =
|
||||
$strModuleType ne TESTDEF_INTEGRATION && $strTest !~ /perl$/ ? true : false;
|
||||
$hTestDefHash->{$strModule}{$strTest}{&TESTDEF_INTEGRATION} = $strModuleType eq TESTDEF_INTEGRATION ? true : false;
|
||||
$hTestDefHash->{$strModule}{$strTest}{&TESTDEF_EXPECT} = $bExpect;
|
||||
$hTestDefHash->{$strModule}{$strTest}{&TESTDEF_CONTAINER} = $bContainer;
|
||||
$hTestDefHash->{$strModule}{$strTest}{&TESTDEF_INDIVIDUAL} = $bIndividual;
|
||||
|
||||
|
||||
@@ -211,17 +211,6 @@ sub endRetry
|
||||
$self->{strErrorLog} .= "${strLine}\n";
|
||||
}
|
||||
|
||||
# Pass the log to the LogTest object
|
||||
if (defined($self->{oLogTest}))
|
||||
{
|
||||
if (defined($self->{strErrorLog}) && $self->{strErrorLog} ne '')
|
||||
{
|
||||
$self->{strOutLog} .= "STDERR:\n" . $self->{strErrorLog};
|
||||
}
|
||||
|
||||
$self->{oLogTest}->logAdd($self->{strCommand}, $self->{strComment}, $self->{bLogOutput} ? $self->{strOutLog} : undef);
|
||||
}
|
||||
|
||||
# If an error was expected then return success if that error occurred
|
||||
if ($self->{iExpectedExitStatus} != 0 && $iExitStatus == $self->{iExpectedExitStatus})
|
||||
{
|
||||
|
||||
@@ -27,7 +27,6 @@ use pgBackRestDoc::Common::String;
|
||||
|
||||
use pgBackRestTest::Common::ExecuteTest;
|
||||
use pgBackRestTest::Common::HostGroupTest;
|
||||
use pgBackRestTest::Common::LogTest;
|
||||
use pgBackRestTest::Common::RunTest;
|
||||
use pgBackRestTest::Common::StorageBase;
|
||||
use pgBackRestTest::Common::VmTest;
|
||||
|
||||
@@ -62,7 +62,6 @@ sub new
|
||||
$self->{strLogLevelTest},
|
||||
$self->{strLogLevelTestFile},
|
||||
$self->{bLogTimestamp},
|
||||
$self->{bLogForce},
|
||||
$self->{bShowOutputAsync},
|
||||
$self->{bNoCleanup},
|
||||
$self->{iRetry},
|
||||
@@ -96,7 +95,6 @@ sub new
|
||||
{name => 'strLogLevelTest'},
|
||||
{name => 'strLogLevelTestFile'},
|
||||
{name => 'bLogTimestamp'},
|
||||
{name => 'bLogForce'},
|
||||
{name => 'bShowOutputAsync'},
|
||||
{name => 'bNoCleanup'},
|
||||
{name => 'iRetry'},
|
||||
@@ -748,7 +746,6 @@ sub run
|
||||
($self->{bLogTimestamp} ? '' : ' --no-log-timestamp') .
|
||||
' --pgsql-bin=' . $self->{oTest}->{&TEST_PGSQL_BIN} .
|
||||
($self->{strTimeZone} ? " --tz='$self->{strTimeZone}'" : '') .
|
||||
($self->{bLogForce} ? ' --log-force' : '') .
|
||||
($self->{bDryRun} ? ' --dry-run' : '') .
|
||||
($self->{bDryRun} ? ' --vm-out' : '') .
|
||||
($self->{bNoCleanup} ? " --no-cleanup" : '');
|
||||
|
||||
@@ -1,492 +0,0 @@
|
||||
####################################################################################################################################
|
||||
# LogTest.pm - Capture the output of commands to compare them with an expected version
|
||||
####################################################################################################################################
|
||||
package pgBackRestTest::Common::LogTest;
|
||||
|
||||
####################################################################################################################################
|
||||
# Perl includes
|
||||
####################################################################################################################################
|
||||
use strict;
|
||||
use warnings FATAL => qw(all);
|
||||
use Carp qw(confess);
|
||||
|
||||
use Cwd qw(abs_path);
|
||||
use Exporter qw(import);
|
||||
our @EXPORT = qw();
|
||||
use File::Basename qw(dirname);
|
||||
|
||||
use pgBackRestDoc::Common::Log;
|
||||
use pgBackRestDoc::ProjectInfo;
|
||||
|
||||
use pgBackRestTest::Common::ContainerTest;
|
||||
use pgBackRestTest::Common::ExecuteTest;
|
||||
|
||||
####################################################################################################################################
|
||||
# Expect log cache for supplemental files so they are only added to expect logs when they have changed
|
||||
####################################################################################################################################
|
||||
my $hyExpectCache = undef;
|
||||
|
||||
####################################################################################################################################
|
||||
# new
|
||||
####################################################################################################################################
|
||||
sub new
|
||||
{
|
||||
my $class = shift; # Class name
|
||||
|
||||
# Create the class hash
|
||||
my $self = {};
|
||||
bless $self, $class;
|
||||
|
||||
# Assign function parameters, defaults, and log debug info
|
||||
(
|
||||
my $strOperation,
|
||||
$self->{strModule},
|
||||
$self->{strTest},
|
||||
$self->{iRun},
|
||||
$self->{bForce},
|
||||
$self->{strComment},
|
||||
$self->{strCommandMain},
|
||||
$self->{strPgSqlBin},
|
||||
$self->{strTestPath},
|
||||
$self->{strRepoPath},
|
||||
) =
|
||||
logDebugParam
|
||||
(
|
||||
__PACKAGE__ . '->new', \@_,
|
||||
{name => 'strModule', trace => true},
|
||||
{name => 'strTest', trace => true},
|
||||
{name => 'iRun', trace => true},
|
||||
{name => 'bForce', trace => true},
|
||||
{name => 'strComment', trace => true},
|
||||
{name => 'strCommandMain', trace => true},
|
||||
{name => 'strPgSqlBin', required => false, trace => true},
|
||||
{name => 'strTestPath', trace => true},
|
||||
{name => 'strRepoPath', trace => true},
|
||||
);
|
||||
|
||||
# Initialize the test log
|
||||
$self->{strLog} = 'run ' . sprintf('%03d', $self->{iRun}) . ' - ' . $self->{strComment};
|
||||
$self->{strLog} .= "\n" . ('=' x length($self->{strLog})) . "\n";
|
||||
|
||||
# Initialize the filename
|
||||
$self->{strFileName} = sprintf("expect/$self->{strModule}-$self->{strTest}-%03d.log", $self->{iRun});
|
||||
|
||||
# Initialize the replacement hash
|
||||
$self->{oReplaceHash} = {};
|
||||
|
||||
# Return from function and log return values if any
|
||||
return logDebugReturn
|
||||
(
|
||||
$strOperation,
|
||||
{name => 'self', value => $self, trace => true}
|
||||
);
|
||||
}
|
||||
|
||||
####################################################################################################################################
|
||||
# logAdd
|
||||
####################################################################################################################################
|
||||
sub logAdd
|
||||
{
|
||||
my $self = shift;
|
||||
|
||||
# Assign function parameters, defaults, and log debug info
|
||||
my
|
||||
(
|
||||
$strOperation,
|
||||
$strCommand,
|
||||
$strComment,
|
||||
$strLog
|
||||
) =
|
||||
logDebugParam
|
||||
(
|
||||
__PACKAGE__ . '->logAdd', \@_,
|
||||
{name => 'strCommand', trace => true},
|
||||
{name => 'strComment', required => false, trace => true},
|
||||
{name => 'strLog', required => false, trace => true}
|
||||
);
|
||||
|
||||
$self->{strLog} .= "\n";
|
||||
|
||||
if (defined($strComment))
|
||||
{
|
||||
$self->{strLog} .= $self->regExpReplaceAll($strComment) . "\n";
|
||||
}
|
||||
|
||||
$self->{strLog} .= '> ' . $self->regExpReplaceAll($strCommand) . "\n" . ('-' x '132') . "\n";
|
||||
|
||||
# Make sure there is a log before trying to output it
|
||||
if (defined($strLog))
|
||||
{
|
||||
# Do replacements on each line of the log
|
||||
foreach my $strLine (split("\n", $strLog))
|
||||
{
|
||||
# Remove timestamp from log line
|
||||
$strLine =~ s/^[0-9]{4}-[0-1][0-9]-[0-3][0-9] [0-2][0-9]:[0-6][0-9]:[0-6][0-9]\.[0-9]{3} //;
|
||||
|
||||
# Don't include test points in the final log
|
||||
if ($strLine !~ /^ TEST/)
|
||||
{
|
||||
# Remove spaces that provided padding for the timetamp
|
||||
$strLine =~ s/^ //;
|
||||
|
||||
# Remove any final CRs
|
||||
$strLine =~ s/\r$//;
|
||||
|
||||
# Do other replacements
|
||||
$strLine = $self->regExpReplaceAll($strLine);
|
||||
|
||||
# Add to the log
|
||||
$self->{strLog} .= "${strLine}\n";
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
# Return from function and log return values if any
|
||||
logDebugReturn($strOperation);
|
||||
}
|
||||
|
||||
####################################################################################################################################
|
||||
# supplementalAdd
|
||||
####################################################################################################################################
|
||||
sub supplementalAdd
|
||||
{
|
||||
my $self = shift;
|
||||
my $strFileName = shift;
|
||||
my $strComment = shift;
|
||||
my $strContent = shift;
|
||||
|
||||
# Get content if it is not defined
|
||||
if (!defined($strContent))
|
||||
{
|
||||
open(my $hFile, '<', $strFileName)
|
||||
or confess &log(ERROR, "unable to open ${strFileName} for appending to test log");
|
||||
|
||||
while (my $strLine = readline($hFile))
|
||||
{
|
||||
$strContent .= $strLine;
|
||||
}
|
||||
|
||||
close($hFile);
|
||||
}
|
||||
|
||||
# Only output when the content of this file has changed
|
||||
if (!defined($hyExpectCache->{$strFileName}) || $hyExpectCache->{$strFileName} ne $strContent)
|
||||
{
|
||||
# $hyExpectCache->{$strFileName} = $strContent;
|
||||
|
||||
my $strHeader = "+ supplemental file: " . $self->regExpReplaceAll($strFileName);
|
||||
|
||||
if (defined($strComment))
|
||||
{
|
||||
$self->{strLog} .= "\n" . $self->regExpReplaceAll($strComment) . "\n" . ('=' x '132') . "\n";
|
||||
}
|
||||
|
||||
$self->{strLog} .= "\n${strHeader}\n" . ('-' x length($strHeader)) . "\n";
|
||||
|
||||
if (length($strContent) > 0)
|
||||
{
|
||||
foreach my $strLine (split("\n", $strContent))
|
||||
{
|
||||
$self->{strLog} .= $self->regExpReplaceAll($strLine) . "\n";
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
####################################################################################################################################
|
||||
# logWrite
|
||||
####################################################################################################################################
|
||||
sub logWrite
|
||||
{
|
||||
my $self = shift;
|
||||
|
||||
# Assign function parameters, defaults, and log debug info
|
||||
my
|
||||
(
|
||||
$strOperation,
|
||||
$strBasePath,
|
||||
$strTestPath,
|
||||
$strFileName
|
||||
) =
|
||||
logDebugParam
|
||||
(
|
||||
__PACKAGE__ . '->logWrite', \@_,
|
||||
{name => 'strBasePath', trace => true},
|
||||
{name => 'strTestPath', trace => true},
|
||||
{name => 'strFileName', default => $self->{strFileName}, trace => true}
|
||||
);
|
||||
|
||||
my $strReferenceLogFile = "${strBasePath}/test/${strFileName}";
|
||||
my $strTestLogFile;
|
||||
|
||||
if ($self->{bForce})
|
||||
{
|
||||
$strTestLogFile = $strReferenceLogFile;
|
||||
}
|
||||
else
|
||||
{
|
||||
my $strTestLogPath = "${strTestPath}/expect";
|
||||
|
||||
if (!-e $strTestLogPath)
|
||||
{
|
||||
mkdir($strTestLogPath, 0750) or
|
||||
confess "unable to create expect log path ${strTestLogPath}";
|
||||
}
|
||||
|
||||
$strTestLogFile = "${strTestPath}/${strFileName}";
|
||||
}
|
||||
|
||||
open(my $hFile, '>', $strTestLogFile)
|
||||
or confess "unable to open expect log file '${strTestLogFile}': $!";
|
||||
|
||||
syswrite($hFile, $self->{strLog})
|
||||
or confess "unable to write expect log file '${strTestLogFile}': $!";
|
||||
|
||||
close($hFile);
|
||||
|
||||
if (!$self->{bForce})
|
||||
{
|
||||
executeTest("diff ${strReferenceLogFile} ${strTestLogFile}");
|
||||
}
|
||||
|
||||
# Return from function and log return values if any
|
||||
logDebugReturn($strOperation);
|
||||
}
|
||||
|
||||
####################################################################################################################################
|
||||
# regExpReplace
|
||||
####################################################################################################################################
|
||||
sub regExpReplace
|
||||
{
|
||||
my $self = shift;
|
||||
my $strLine = shift;
|
||||
my $strType = shift;
|
||||
my $strExpression = shift;
|
||||
my $strToken = shift;
|
||||
my $bIndex = shift;
|
||||
|
||||
my @stryReplace = ($strLine =~ /$strExpression/g);
|
||||
|
||||
foreach my $strReplace (@stryReplace)
|
||||
{
|
||||
my $iIndex;
|
||||
my $strTypeReplacement;
|
||||
my $strReplacement;
|
||||
|
||||
if (!defined($bIndex) || $bIndex)
|
||||
{
|
||||
if (defined($strToken))
|
||||
{
|
||||
my @stryReplacement = ($strReplace =~ /$strToken/g);
|
||||
|
||||
if (@stryReplacement != 1)
|
||||
{
|
||||
my $strError = "'${strToken}'";
|
||||
|
||||
if (@stryReplacement == 0)
|
||||
{
|
||||
confess &log(ASSERT, $strError . " is not a sub-regexp of '${strExpression}' or" .
|
||||
" matches " . @stryReplacement . " times on {[${strReplace}]}");
|
||||
}
|
||||
|
||||
confess &log(
|
||||
ASSERT, $strError . " matches '${strExpression}' " . @stryReplacement . " times on '${strReplace}': " .
|
||||
join(',', @stryReplacement));
|
||||
}
|
||||
|
||||
$strReplacement = $stryReplacement[0];
|
||||
}
|
||||
else
|
||||
{
|
||||
$strReplacement = $strReplace;
|
||||
}
|
||||
|
||||
if (defined($strType))
|
||||
{
|
||||
if (defined(${$self->{oReplaceHash}}{$strType}{$strReplacement}))
|
||||
{
|
||||
$iIndex = ${$self->{oReplaceHash}}{$strType}{$strReplacement}{index};
|
||||
}
|
||||
else
|
||||
{
|
||||
if (!defined(${$self->{oReplaceHash}}{$strType}{index}))
|
||||
{
|
||||
${$self->{oReplaceHash}}{$strType}{index} = 1;
|
||||
}
|
||||
|
||||
$iIndex = ${$self->{oReplaceHash}}{$strType}{index}++;
|
||||
${$self->{oReplaceHash}}{$strType}{$strReplacement}{index} = $iIndex;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
$strTypeReplacement = defined($strType) ? "[${strType}" . (defined($iIndex) ? "-${iIndex}" : '') . ']' : '';
|
||||
|
||||
if (defined($strToken))
|
||||
{
|
||||
$strReplacement = $strReplace;
|
||||
$strReplacement =~ s/$strToken/$strTypeReplacement/;
|
||||
}
|
||||
else
|
||||
{
|
||||
$strReplacement = $strTypeReplacement;
|
||||
}
|
||||
|
||||
$strReplace =~ s/\//\\\//g;
|
||||
$strReplace =~ s/\+/\\\+/g;
|
||||
$strLine =~ s/$strReplace/$strReplacement/g;
|
||||
}
|
||||
|
||||
return $strLine;
|
||||
}
|
||||
|
||||
####################################################################################################################################
|
||||
# regExpReplaceAll
|
||||
#
|
||||
# Replaces dynamic test output so that the expected test output can be verified against actual test output.
|
||||
####################################################################################################################################
|
||||
sub regExpReplaceAll
|
||||
{
|
||||
my $self = shift;
|
||||
my $strLine = shift;
|
||||
|
||||
my $strBinPath = dirname(dirname(abs_path($0))) . '/bin';
|
||||
|
||||
# Replace the exe path/file with sh ' prepended
|
||||
my $strLineBefore = $strLine;
|
||||
$strLine =~ s/bash -l -c '$self->{strCommandMain}/[BACKREST-BIN]/g;
|
||||
|
||||
# Replace the final ' if the previous expression made changes
|
||||
if ($strLine ne $strLineBefore)
|
||||
{
|
||||
$strLine =~ s/'$//g;
|
||||
}
|
||||
|
||||
# Replace the exe path/file with sh ' prepended
|
||||
$strLine =~ s/$self->{strCommandMain}/[BACKREST-BIN]/g;
|
||||
|
||||
# Replace the test path
|
||||
$strLine =~ s/$self->{strTestPath}/[TEST_PATH]/g;
|
||||
|
||||
# Replace the repo path
|
||||
$strLine =~ s/$self->{strRepoPath}/[REPO_PATH]/g;
|
||||
|
||||
# Replace the pgsql path (if exists)
|
||||
if (defined($self->{strPgSqlBin}))
|
||||
{
|
||||
$strLine =~ s/$self->{strPgSqlBin}/[PGSQL_BIN_PATH]/g;
|
||||
}
|
||||
|
||||
$strLine = $self->regExpReplace($strLine, 'BACKREST-NAME-VERSION', '^' . PROJECT_NAME . ' ' . PROJECT_VERSION,
|
||||
undef, false);
|
||||
$strLine = $self->regExpReplace(
|
||||
$strLine, 'BACKREST-VERSION', ' begin ' . PROJECT_VERSION . '\:', PROJECT_VERSION, false);
|
||||
|
||||
$strLine = $self->regExpReplace($strLine, undef, '^docker exec -u [a-z]* test-[0-9]+\-', 'test-[0-9]+\-', false);
|
||||
$strLine = $self->regExpReplace($strLine, 'CONTAINER-EXEC', '^docker exec -u [a-z]*', '^docker exec -u [a-z]*', false);
|
||||
|
||||
$strLine = $self->regExpReplace($strLine, 'PROCESS-ID', 'sent term signal to process [0-9]+', '[0-9]+$', false);
|
||||
$strLine = $self->regExpReplace($strLine, 'YEAR', 'backup\.history\/20[0-9]{2}', '20[0-9]{2}$');
|
||||
|
||||
$strLine = $self->regExpReplace($strLine, 'BACKUP-INCR', '[0-9]{8}\-[0-9]{6}F\_[0-9]{8}\-[0-9]{6}I');
|
||||
$strLine = $self->regExpReplace($strLine, 'BACKUP-DIFF', '[0-9]{8}\-[0-9]{6}F\_[0-9]{8}\-[0-9]{6}D');
|
||||
$strLine = $self->regExpReplace($strLine, 'BACKUP-FULL', '[0-9]{8}\-[0-9]{6}F');
|
||||
|
||||
$strLine = $self->regExpReplace(
|
||||
$strLine, 'BACKUP-EXPR', 'strExpression \= \_[0-9]{8}\-[0-9]{6}', '\_[0-9]{8}\-[0-9]{6}$', false);
|
||||
|
||||
if ($strLine =~ /^P00 DETAIL\: statistics\: /)
|
||||
{
|
||||
$strLine = 'P00 DETAIL: statistics: STATISTICS'
|
||||
}
|
||||
|
||||
$strLine = $self->regExpReplace($strLine, 'GROUP', 'strGroup = [^ \n,\[\]]+', '[^ \n,\[\]]+$');
|
||||
$strLine = $self->regExpReplace($strLine, 'GROUP', 'unknown group in backup manifest mapped to \'[^\']+', '[^\']+$');
|
||||
$strLine = $self->regExpReplace($strLine, 'GROUP', 'group"[ ]{0,1}:[ ]{0,1}"[^"]+', '[^"]+$');
|
||||
$strLine = $self->regExpReplace($strLine, 'GROUP', 'group=\"[^"]+', '[^"]+$');
|
||||
$strLine = $self->regExpReplace($strLine, 'GROUP', 'group for .* was not mapped to a name\, set to .+$', '[^ ]+$');
|
||||
$strLine = $self->regExpReplace($strLine, 'GROUP', 'set ownership [^\:]+:[^ ]+', '[^\:]+$');
|
||||
$strLine = $self->regExpReplace($strLine, 'GROUP', TEST_USER . '\, ' . TEST_GROUP, '[^ ]+$');
|
||||
|
||||
$strLine = $self->regExpReplace($strLine, 'USER', 'strRemoteHostUser = [^ \n,\[\]]+', '[^ \n,\[\]]+$');
|
||||
$strLine = $self->regExpReplace($strLine, 'USER', 'unknown user in backup manifest mapped to \'[^\']+', '[^\']+$');
|
||||
$strLine = $self->regExpReplace($strLine, 'USER', 'strUser = [^ \n,\[\]]+', '[^ \n,\[\]]+$');
|
||||
$strLine = $self->regExpReplace($strLine, 'USER', 'user"[ ]{0,1}:[ ]{0,1}"[^"]+', '[^"]+$');
|
||||
$strLine = $self->regExpReplace($strLine, 'USER', 'user=\"[^"]+', '[^"]+$');
|
||||
$strLine = $self->regExpReplace($strLine, 'USER', '^pg-host-user=.+$', '[^=]+$');
|
||||
$strLine = $self->regExpReplace($strLine, 'USER', 'user for .* was not mapped to a name\, set to .+$', '[^ ]+$');
|
||||
$strLine = $self->regExpReplace($strLine, 'USER', 'set ownership [^\:]+', '[^ ]+$');
|
||||
$strLine = $self->regExpReplace($strLine, 'USER', 'cannot be used for restore\, set to .+$', '[^ ]+$');
|
||||
$strLine = $self->regExpReplace($strLine, 'USER', '-user=[a-z0-9_]+', '[^=]+$');
|
||||
$strLine = $self->regExpReplace($strLine, 'USER', '[^ ]+\@db\-primary', '^[^\@]+');
|
||||
$strLine = $self->regExpReplace($strLine, 'USER', '[\( ]{1}' . TEST_USER . '[\,\)]{1}', TEST_USER);
|
||||
|
||||
$strLine = $self->regExpReplace($strLine, 'EXEC-ID', '--exec-id=[^ ]+', '[^=]+$', false);
|
||||
|
||||
$strLine = $self->regExpReplace($strLine, 'CIPHER-PASS', '^cipher\-pass\=.+$', '[^\=]+$');
|
||||
|
||||
$strLine = $self->regExpReplace($strLine, 'PORT', 'db[1-9]{0,1}-port=[0-9]+', '[0-9]+$');
|
||||
|
||||
# Replace year when it falls on a single line when executing ls -1R
|
||||
$strLine = $self->regExpReplace($strLine, 'YEAR', '^20[0-9]{2}$');
|
||||
|
||||
# Replace year when it is the last part of a path when executing ls -1R
|
||||
$strLine = $self->regExpReplace($strLine, 'YEAR', 'history\/20[0-9]{2}\:$', '20[0-9]{2}');
|
||||
|
||||
my $strTimestampRegExp = "[0-9]{4}-[0-1][0-9]-[0-3][0-9] [0-2][0-9]:[0-6][0-9]:[0-6][0-9]";
|
||||
|
||||
$strLine = $self->regExpReplace($strLine, 'TS_PATH', "PG\\_[0-9]\\.[0-9]\\_[0-9]{9}");
|
||||
my $strProjectVersion = PROJECT_VERSION;
|
||||
$strProjectVersion =~ s/\./\\./g;
|
||||
$strLine = $self->regExpReplace($strLine, 'VERSION',
|
||||
"version[\"]{0,1}[ ]{0,1}[\:\=)]{1}[ ]{0,1}[\"]{0,1}" . $strProjectVersion, $strProjectVersion . '$');
|
||||
|
||||
$strLine = $self->regExpReplace($strLine, 'TIMESTAMP', 'timestamp"[ ]{0,1}:[ ]{0,1}[0-9]{10}','[0-9]{10}$');
|
||||
|
||||
$strLine = $self->regExpReplace($strLine, 'TIMESTAMP',
|
||||
"timestamp-[a-z-]+[\"]{0,1}[ ]{0,1}[\:\=)]{1}[ ]{0,1}[\"]{0,1}[0-9]{10}", '[0-9]{10}$', false);
|
||||
$strLine = $self->regExpReplace($strLine, 'TIMESTAMP', "start\" : [0-9]{10}", '[0-9]{10}$', false);
|
||||
$strLine = $self->regExpReplace($strLine, 'TIMESTAMP', "stop\" : [0-9]{10}", '[0-9]{10}$', false);
|
||||
$strLine = $self->regExpReplace($strLine, 'TIMESTAMP', TEST_GROUP . '\, [0-9]{10}', '[0-9]{10}$', false);
|
||||
$strLine = $self->regExpReplace(
|
||||
$strLine, 'TIMESTAMP', 'generated by pgBackRest restore on .*$',
|
||||
'[0-9]{4}\-[0-9]{2}\-[0-9]{2} [0-9]{2}\:[0-9]{2}\:[0-9]{2}$', false);
|
||||
$strLine = $self->regExpReplace($strLine, 'SIZE', "size\"[ ]{0,1}:[ ]{0,1}[0-9]+", '[0-9]+$', false);
|
||||
$strLine = $self->regExpReplace($strLine, 'DELTA', "delta\"[ ]{0,1}:[ ]{0,1}[0-9]+", '[0-9]+$', false);
|
||||
$strLine = $self->regExpReplace(
|
||||
$strLine, 'TIMESTAMP-STR', "timestamp start\/stop: $strTimestampRegExp / $strTimestampRegExp",
|
||||
"${strTimestampRegExp} / ${strTimestampRegExp}\$", false);
|
||||
$strLine = $self->regExpReplace($strLine, 'CHECKSUM', 'checksum=[\"]{0,1}[0-f]{40}', '[0-f]{40}$', false);
|
||||
|
||||
$strLine = $self->regExpReplace($strLine, 'LOG-LEVEL-FILE', 'log-level-file=[a-z]+', '[a-z]+$', false);
|
||||
$strLine = $self->regExpReplace($strLine, 'LOG-SUBPROCESS', 'log-subprocess=[a-z]+', '[a-z]+$', false);
|
||||
$strLine = $self->regExpReplace($strLine, '', ' --log-subprocess', undef, false);
|
||||
$strLine = $self->regExpReplace($strLine, '', ' --no-log-subprocess', undef, false);
|
||||
$strLine = $self->regExpReplace($strLine, 'BUFFER-SIZE', 'buffer-size=[0-9a-z]+', '[0-9a-z]+$', false);
|
||||
|
||||
$strLine = $self->regExpReplace($strLine, 'REMOTE-PROCESS-TERMINATED-MESSAGE',
|
||||
'remote process terminated.*: (ssh.*|no output from terminated process)$',
|
||||
'(ssh.*|no output from terminated process)$', false);
|
||||
|
||||
# Full test time-based recovery
|
||||
$strLine = $self->regExpReplace($strLine, 'TIMESTAMP-TARGET', "\\, target \\'.*UTC", "[^\\']+UTC\$");
|
||||
$strLine = $self->regExpReplace($strLine, 'TIMESTAMP-TARGET', " \\-\\-target\\=\\\".*UTC", "[^\\\"]+UTC\$");
|
||||
$strLine = $self->regExpReplace($strLine, 'TIMESTAMP-TARGET', "^recovery_target_time \\= \\'.*UTC", "[^\\']+UTC\$");
|
||||
|
||||
$strLine = $self->regExpReplace($strLine, 'TIMESTAMP-TARGET', "\\, target \\'.*\\+00", "[^\\']+\\+00\$");
|
||||
$strLine = $self->regExpReplace($strLine, 'TIMESTAMP-TARGET', " \\-\\-target\\=\\\".*\\+00", "[^\\\"]+\\+00\$");
|
||||
$strLine = $self->regExpReplace($strLine, 'TIMESTAMP-TARGET', "^recovery_target_time \\= \\'.*\\+00", "[^\\']+\\+00\$");
|
||||
|
||||
# Full test xid-based recovery (this expressions only work when time-based expressions above have already been applied
|
||||
$strLine = $self->regExpReplace($strLine, 'XID-TARGET', "\\, target \\'[0-9]+", "[0-9]+\$");
|
||||
$strLine = $self->regExpReplace($strLine, 'XID-TARGET', " \\-\\-target\\=\\\"[0-9]+", "[0-9]+\$");
|
||||
$strLine = $self->regExpReplace($strLine, 'XID-TARGET', "^recovery_target_xid \\= \\'[0-9]+", "[0-9]+\$");
|
||||
|
||||
$strLine = $self->regExpReplace(
|
||||
$strLine, 'MODIFICATION-TIME', '(' . (substr(time(), 0, 5) - 1) . '[0-9]{5}|' . substr(time(), 0, 5) . '[0-9]{5})',
|
||||
'^[0-9]{10}$');
|
||||
|
||||
return $strLine;
|
||||
}
|
||||
|
||||
1;
|
||||
@@ -23,7 +23,6 @@ use pgBackRestDoc::ProjectInfo;
|
||||
use pgBackRestTest::Common::BuildTest;
|
||||
use pgBackRestTest::Common::DefineTest;
|
||||
use pgBackRestTest::Common::ExecuteTest;
|
||||
use pgBackRestTest::Common::LogTest;
|
||||
use pgBackRestTest::Common::Storage;
|
||||
use pgBackRestTest::Common::StoragePosix;
|
||||
use pgBackRestTest::Common::VmTest;
|
||||
@@ -124,7 +123,6 @@ sub process
|
||||
$self->{bOutput},
|
||||
$self->{bDryRun},
|
||||
$self->{bCleanup},
|
||||
$self->{bLogForce},
|
||||
$self->{strLogLevelTestFile},
|
||||
$self->{strPgUser},
|
||||
$self->{strGroup},
|
||||
@@ -146,7 +144,6 @@ sub process
|
||||
{name => 'bOutput'},
|
||||
{name => 'bDryRun'},
|
||||
{name => 'bCleanup'},
|
||||
{name => 'bLogForce'},
|
||||
{name => 'strLogLevelTestFile'},
|
||||
{name => 'strPgUser'},
|
||||
{name => 'strGroup'},
|
||||
@@ -159,10 +156,9 @@ sub process
|
||||
$oStorage = new pgBackRestTest::Common::Storage(
|
||||
$self->testPath(), new pgBackRestTest::Common::StoragePosix({bFileSync => false, bPathSync => false}));
|
||||
|
||||
# Init, run, and end the test(s)
|
||||
# Init, run, and clean the test(s)
|
||||
$self->initModule();
|
||||
$self->run();
|
||||
$self->end();
|
||||
$self->cleanModule();
|
||||
|
||||
# Make sure the correct number of tests ran
|
||||
@@ -193,34 +189,13 @@ sub begin
|
||||
(
|
||||
$strOperation,
|
||||
$strDescription,
|
||||
$bExpect,
|
||||
) =
|
||||
logDebugParam
|
||||
(
|
||||
__PACKAGE__ . '->begin', \@_,
|
||||
{name => 'strDescription'},
|
||||
{name => 'bExpect', required => false},
|
||||
);
|
||||
|
||||
# Save the previous expect log
|
||||
$self->end();
|
||||
|
||||
# If bExpect is defined then it is an override of the default
|
||||
$self->{bExpect} = false;
|
||||
|
||||
if ($self->vm() eq VM_EXPECT)
|
||||
{
|
||||
if (defined($bExpect))
|
||||
{
|
||||
$self->{bExpect} = $bExpect;
|
||||
}
|
||||
# Else get the default expect setting
|
||||
else
|
||||
{
|
||||
$self->{bExpect} = (testDefModuleTest($self->{strModule}, $self->{strModuleTest}))->{&TESTDEF_EXPECT};
|
||||
}
|
||||
}
|
||||
|
||||
# Increment the run counter;
|
||||
$self->{iRun}++;
|
||||
|
||||
@@ -238,17 +213,6 @@ sub begin
|
||||
return false;
|
||||
}
|
||||
|
||||
# Create an ExpectTest object
|
||||
if ($self->doExpect())
|
||||
{
|
||||
$self->{oExpect} = new pgBackRestTest::Common::LogTest(
|
||||
$self->module(), $self->moduleTest(), $self->runCurrent(), $self->doLogForce(), $strDescription,
|
||||
$self->{strBackRestExe}, $self->pgBinPath(), $self->testPath(), $self->basePath());
|
||||
|
||||
&log(INFO, ' expect log: ' . $self->{oExpect}->{strFileName});
|
||||
}
|
||||
|
||||
|
||||
if (!$self->{bFirstTest})
|
||||
{
|
||||
$self->cleanTest();
|
||||
@@ -260,21 +224,6 @@ sub begin
|
||||
return true;
|
||||
}
|
||||
|
||||
####################################################################################################################################
|
||||
# end
|
||||
####################################################################################################################################
|
||||
sub end
|
||||
{
|
||||
my $self = shift;
|
||||
|
||||
# Save the previous test log
|
||||
if (defined($self->expect()))
|
||||
{
|
||||
$self->expect()->logWrite($self->basePath(), $self->testPath());
|
||||
delete($self->{oExpect});
|
||||
}
|
||||
}
|
||||
|
||||
####################################################################################################################################
|
||||
# testResult
|
||||
####################################################################################################################################
|
||||
@@ -290,8 +239,6 @@ sub testResult
|
||||
$strExpected,
|
||||
$strDescription,
|
||||
$iWaitSeconds,
|
||||
$strLogExpect,
|
||||
$strLogLevel,
|
||||
) =
|
||||
logDebugParam
|
||||
(
|
||||
@@ -300,8 +247,6 @@ sub testResult
|
||||
{name => 'strExpected', required => false, trace => true},
|
||||
{name => 'strDescription', trace => true},
|
||||
{name => 'iWaitSeconds', optional => true, default => 0, trace => true},
|
||||
{name => 'strLogExpect', optional => true, trace => true},
|
||||
{name => 'strLogLevel', optional => true, default => WARN, trace => true},
|
||||
);
|
||||
|
||||
&log(INFO, ' ' . $strDescription);
|
||||
@@ -311,10 +256,6 @@ sub testResult
|
||||
my $oWait = waitInit($iWaitSeconds);
|
||||
my $bDone = false;
|
||||
|
||||
# Save the current log levels and set the file level to strLogLevel, console to off, and timestamp false
|
||||
my ($strLogLevelFile, $strLogLevelConsole, $strLogLevelStdErr, $bLogTimestamp) = logLevel();
|
||||
logLevelSet($strLogLevel, OFF, undef, false);
|
||||
|
||||
# Clear the cache for this test
|
||||
logFileCacheClear();
|
||||
|
||||
@@ -335,15 +276,10 @@ sub testResult
|
||||
$strActual = ${logDebugBuild(\@stryResult)};
|
||||
}
|
||||
|
||||
# Restore the log level
|
||||
logLevelSet($strLogLevelFile, $strLogLevelConsole, $strLogLevelStdErr, $bLogTimestamp);
|
||||
return true;
|
||||
}
|
||||
or do
|
||||
{
|
||||
# Restore the log level
|
||||
logLevelSet($strLogLevelFile, $strLogLevelConsole, $strLogLevelStdErr, $bLogTimestamp);
|
||||
|
||||
if (!isException(\$EVAL_ERROR))
|
||||
{
|
||||
confess "unexpected standard Perl exception" . (defined($EVAL_ERROR) ? ": ${EVAL_ERROR}" : '');
|
||||
@@ -367,23 +303,6 @@ sub testResult
|
||||
}
|
||||
} while (!$bDone);
|
||||
|
||||
# If we get here then test any warning message
|
||||
if (defined($strLogExpect))
|
||||
{
|
||||
my $strLogMessage = trim(logFileCache());
|
||||
|
||||
# Strip leading Process marker and whitespace from each line
|
||||
$strLogMessage =~ s/^(P[0-9]{2})*\s+//mg;
|
||||
|
||||
# If the expected message does not exactly match the logged message or is not at least contained in it, then error
|
||||
if (!($strLogMessage eq $strLogExpect || $strLogMessage =~ $strLogExpect))
|
||||
{
|
||||
confess &log(ERROR,
|
||||
"the log message:\n$strLogMessage\ndoes not match or does not contain the expected message:\n" .
|
||||
$strLogExpect);
|
||||
}
|
||||
}
|
||||
|
||||
# Return from function and log return values if any
|
||||
return logDebugReturn
|
||||
(
|
||||
@@ -392,60 +311,6 @@ sub testResult
|
||||
);
|
||||
}
|
||||
|
||||
####################################################################################################################################
|
||||
# testException
|
||||
####################################################################################################################################
|
||||
sub testException
|
||||
{
|
||||
my $self = shift;
|
||||
my $fnSub = shift;
|
||||
my $iCodeExpected = shift;
|
||||
my $strMessageExpected = shift;
|
||||
|
||||
# Output first line of the error message
|
||||
&log(INFO,
|
||||
" [${iCodeExpected}] " . (defined($strMessageExpected) ? (split('\n', $strMessageExpected))[0] : 'undef error message'));
|
||||
|
||||
my $bError = false;
|
||||
my $strError =
|
||||
"exception ${iCodeExpected}, " . (defined($strMessageExpected) ? "'${strMessageExpected}'" : '[UNDEF]') . " was expected";
|
||||
|
||||
eval
|
||||
{
|
||||
logDisable();
|
||||
$fnSub->();
|
||||
logEnable();
|
||||
return true;
|
||||
}
|
||||
or do
|
||||
{
|
||||
logEnable();
|
||||
|
||||
if (!isException(\$EVAL_ERROR))
|
||||
{
|
||||
confess "${strError} but actual was standard Perl exception" . (defined($EVAL_ERROR) ? ": ${EVAL_ERROR}" : '');
|
||||
}
|
||||
|
||||
if (!($EVAL_ERROR->code() == $iCodeExpected &&
|
||||
(!defined($strMessageExpected) && !defined($EVAL_ERROR->message()) ||
|
||||
(defined($strMessageExpected) && defined($EVAL_ERROR->message()) &&
|
||||
($EVAL_ERROR->message() eq $strMessageExpected || $EVAL_ERROR->message() =~ "^${strMessageExpected}" ||
|
||||
$EVAL_ERROR->message() =~ "^${strMessageExpected} at ")))))
|
||||
{
|
||||
confess
|
||||
"${strError} but actual was " . $EVAL_ERROR->code() . ', ' .
|
||||
(defined($EVAL_ERROR->message()) ? qw{'} . $EVAL_ERROR->message() . qw{'} : '[UNDEF]');
|
||||
}
|
||||
|
||||
$bError = true;
|
||||
};
|
||||
|
||||
if (!$bError)
|
||||
{
|
||||
confess "${strError} but no exception was thrown";
|
||||
}
|
||||
}
|
||||
|
||||
####################################################################################################################################
|
||||
# testRunName
|
||||
#
|
||||
@@ -544,12 +409,9 @@ sub backrestExeHelper {return shift->{strBackRestExeHelper}}
|
||||
sub basePath {return shift->{strBasePath}}
|
||||
sub dataPath {return shift->basePath() . '/test/data'}
|
||||
sub doCleanup {return shift->{bCleanup}}
|
||||
sub doExpect {return shift->{bExpect}}
|
||||
sub doLogForce {return shift->{bLogForce}}
|
||||
sub logLevelTestFile {return shift->{strLogLevelTestFile}}
|
||||
sub group {return shift->{strGroup}}
|
||||
sub isDryRun {return shift->{bDryRun}}
|
||||
sub expect {return shift->{oExpect}}
|
||||
sub module {return shift->{strModule}}
|
||||
sub moduleTest {return shift->{strModuleTest}}
|
||||
sub pgBinPath {return shift->{strPgBinPath}}
|
||||
|
||||
@@ -93,10 +93,6 @@ use constant VM_U20 => 'u20';
|
||||
use constant VM_D9 => 'd9';
|
||||
push @EXPORT, qw(VM_D9);
|
||||
|
||||
# Defines the vm that will be used for expect testing
|
||||
use constant VM_EXPECT => VM_RH7;
|
||||
push @EXPORT, qw(VM_EXPECT);
|
||||
|
||||
# VM aliases for run matrices (numbered oldest to newest)
|
||||
use constant VM2 => VM_D9;
|
||||
push @EXPORT, qw(VM2);
|
||||
|
||||
Reference in New Issue
Block a user