mirror of
https://github.com/pgbackrest/pgbackrest.git
synced 2025-01-18 04:58:51 +02:00
Add Perl interface to C PgQuery object.
This validates that all current queries work with the new interface and removes the dependency on DBD::Pg.
This commit is contained in:
parent
415542b4a3
commit
d8ca0e5c5b
@ -458,24 +458,24 @@
|
|||||||
</execute-list>
|
</execute-list>
|
||||||
|
|
||||||
<!-- Perl installation -->
|
<!-- Perl installation -->
|
||||||
<p><backrest/> contains embedded Perl which requires some additional modules.</p>
|
<p><backrest/> contains embedded Perl which requires some additional packages.</p>
|
||||||
|
|
||||||
<execute-list host="{[br-install-host]}">
|
<execute-list host="{[br-install-host]}">
|
||||||
<title>Install required Perl packages</title>
|
<title>Install required Perl packages</title>
|
||||||
|
|
||||||
<execute if="{[os-type-is-debian]}" user="root" pre="y">
|
<execute if="{[os-type-is-debian]}" user="root" pre="y">
|
||||||
<exe-cmd>apt-get install libdbd-pg-perl</exe-cmd>
|
<exe-cmd>apt-get install perl</exe-cmd>
|
||||||
<exe-cmd-extra>-y 2>&1</exe-cmd-extra>
|
<exe-cmd-extra>-y 2>&1</exe-cmd-extra>
|
||||||
</execute>
|
</execute>
|
||||||
|
|
||||||
<execute if="{[os-type-is-centos6]}" user="root" pre="y">
|
<execute if="{[os-type-is-centos6]}" user="root" pre="y">
|
||||||
<exe-cmd>yum install perl perl-Time-HiRes perl-parent perl-JSON
|
<exe-cmd>yum install perl perl-Time-HiRes perl-parent perl-JSON
|
||||||
perl-Digest-SHA perl-DBD-Pg</exe-cmd>
|
perl-Digest-SHA</exe-cmd>
|
||||||
<exe-cmd-extra>-y 2>&1</exe-cmd-extra>
|
<exe-cmd-extra>-y 2>&1</exe-cmd-extra>
|
||||||
</execute>
|
</execute>
|
||||||
|
|
||||||
<execute if="{[os-type-is-centos7]}" user="root" pre="y">
|
<execute if="{[os-type-is-centos7]}" user="root" pre="y">
|
||||||
<exe-cmd>yum install perl perl-Time-HiRes perl-Digest-SHA perl-DBD-Pg perl-JSON-PP</exe-cmd>
|
<exe-cmd>yum install perl perl-Time-HiRes perl-Digest-SHA perl-JSON-PP</exe-cmd>
|
||||||
<exe-cmd-extra>-y 2>&1</exe-cmd-extra>
|
<exe-cmd-extra>-y 2>&1</exe-cmd-extra>
|
||||||
</execute>
|
</execute>
|
||||||
</execute-list>
|
</execute-list>
|
||||||
|
@ -6,13 +6,13 @@ package pgBackRest::Db;
|
|||||||
use strict;
|
use strict;
|
||||||
use warnings FATAL => qw(all);
|
use warnings FATAL => qw(all);
|
||||||
use Carp qw(confess);
|
use Carp qw(confess);
|
||||||
|
use English '-no_match_vars';
|
||||||
|
|
||||||
use DBD::Pg ':async';
|
|
||||||
use DBI;
|
|
||||||
use Exporter qw(import);
|
use Exporter qw(import);
|
||||||
our @EXPORT = qw();
|
our @EXPORT = qw();
|
||||||
use Fcntl qw(O_RDONLY);
|
use Fcntl qw(O_RDONLY);
|
||||||
use File::Basename qw(dirname);
|
use File::Basename qw(dirname);
|
||||||
|
use JSON::PP;
|
||||||
|
|
||||||
use pgBackRest::DbVersion;
|
use pgBackRest::DbVersion;
|
||||||
use pgBackRest::Common::Exception;
|
use pgBackRest::Common::Exception;
|
||||||
@ -126,10 +126,10 @@ sub DESTROY
|
|||||||
# Assign function parameters, defaults, and log debug info
|
# Assign function parameters, defaults, and log debug info
|
||||||
my ($strOperation) = logDebugParam(__PACKAGE__ . '->DESTROY');
|
my ($strOperation) = logDebugParam(__PACKAGE__ . '->DESTROY');
|
||||||
|
|
||||||
if (defined($self->{hDb}))
|
if (defined($self->{oDb}))
|
||||||
{
|
{
|
||||||
$self->{hDb}->disconnect();
|
$self->{oDb}->close();
|
||||||
undef($self->{hDb});
|
undef($self->{oDb});
|
||||||
}
|
}
|
||||||
|
|
||||||
# Return from function and log return values if any
|
# Return from function and log return values if any
|
||||||
@ -167,63 +167,46 @@ sub connect
|
|||||||
# Else run locally
|
# Else run locally
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
if (!defined($self->{hDb}))
|
if (!defined($self->{oDb}))
|
||||||
{
|
{
|
||||||
# Connect to the db
|
$self->{oDb} = new pgBackRest::LibC::PgClient(
|
||||||
my $strDbName = 'postgres';
|
cfgOption(cfgOptionIdFromIndex(CFGOPT_PG_SOCKET_PATH, $self->{iRemoteIdx}), false),
|
||||||
my $strDbSocketPath = cfgOption(cfgOptionIdFromIndex(CFGOPT_PG_SOCKET_PATH, $self->{iRemoteIdx}), false);
|
cfgOption(cfgOptionIdFromIndex(CFGOPT_PG_PORT, $self->{iRemoteIdx})), 'postgres',
|
||||||
|
cfgOption(CFGOPT_DB_TIMEOUT) * 1000);
|
||||||
|
|
||||||
# Make sure the socket path is absolute
|
if ($bWarnOnError)
|
||||||
if (defined($strDbSocketPath) && $strDbSocketPath !~ /^\//)
|
|
||||||
{
|
{
|
||||||
confess &log(ERROR, "'${strDbSocketPath}' is not valid for '" . cfgOptionName(CFGOPT_PG_SOCKET_PATH) . "' option:" .
|
eval
|
||||||
" path must be absolute", ERROR_OPTION_INVALID_VALUE);
|
|
||||||
}
|
|
||||||
|
|
||||||
# Construct the URI
|
|
||||||
my $strDbUri =
|
|
||||||
"dbi:Pg:dbname=${strDbName};port=" . cfgOption(cfgOptionIdFromIndex(CFGOPT_PG_PORT, $self->{iRemoteIdx})) .
|
|
||||||
(defined($strDbSocketPath) ? ";host=${strDbSocketPath}" : '');
|
|
||||||
|
|
||||||
logDebugMisc
|
|
||||||
(
|
|
||||||
$strOperation, undef,
|
|
||||||
{name => 'strDbUri', value => $strDbUri},
|
|
||||||
);
|
|
||||||
|
|
||||||
$self->{hDb} = DBI->connect($strDbUri, undef, undef,
|
|
||||||
{AutoCommit => 1, RaiseError => 0, PrintError => 0, Warn => 0});
|
|
||||||
|
|
||||||
# If db handle is not valid then check error
|
|
||||||
if (!$self->{hDb})
|
|
||||||
{
|
|
||||||
# Throw an error unless a warning was requested
|
|
||||||
if (!$bWarnOnError)
|
|
||||||
{
|
{
|
||||||
confess &log(ERROR, $DBI::errstr, ERROR_DB_CONNECT);
|
$self->{oDb}->open();
|
||||||
|
return true;
|
||||||
}
|
}
|
||||||
|
or do
|
||||||
|
{
|
||||||
|
&log(WARN, exceptionMessage($EVAL_ERROR));
|
||||||
|
$bResult = false;
|
||||||
|
|
||||||
# Log a warning
|
undef($self->{oDb});
|
||||||
&log(WARN, $DBI::errstr);
|
}
|
||||||
|
|
||||||
$bResult = false;
|
|
||||||
undef($self->{hDb});
|
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
|
{
|
||||||
|
$self->{oDb}->open();
|
||||||
|
}
|
||||||
|
|
||||||
|
if (defined($self->{oDb}))
|
||||||
{
|
{
|
||||||
my ($fDbVersion) = $self->versionGet();
|
my ($fDbVersion) = $self->versionGet();
|
||||||
|
|
||||||
if ($fDbVersion >= PG_VERSION_APPLICATION_NAME)
|
if ($fDbVersion >= PG_VERSION_APPLICATION_NAME)
|
||||||
{
|
{
|
||||||
# Set application name for monitoring and debugging
|
# Set application name for monitoring and debugging
|
||||||
$self->{hDb}->do(
|
$self->{oDb}->query(
|
||||||
"set application_name = '" . PROJECT_NAME . ' [' .
|
"set application_name = '" . PROJECT_NAME . ' [' .
|
||||||
(cfgOptionValid(CFGOPT_COMMAND) ? cfgOption(CFGOPT_COMMAND) : cfgCommandName(cfgCommandGet())) . "]'")
|
(cfgOptionValid(CFGOPT_COMMAND) ? cfgOption(CFGOPT_COMMAND) : cfgCommandName(cfgCommandGet())) . "]'");
|
||||||
or confess &log(ERROR, $self->{hDb}->errstr, ERROR_DB_QUERY);
|
|
||||||
|
|
||||||
# Clear search path to prevent possible function overrides
|
# Clear search path to prevent possible function overrides
|
||||||
$self->{hDb}->do("set search_path = 'pg_catalog'")
|
$self->{oDb}->query("set search_path = 'pg_catalog'");
|
||||||
or confess &log(ERROR, $self->{hDb}->errstr, ERROR_DB_QUERY);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -273,73 +256,11 @@ sub executeSql
|
|||||||
else
|
else
|
||||||
{
|
{
|
||||||
$self->connect();
|
$self->connect();
|
||||||
|
my $strResult = $self->{oDb}->query($strSql);
|
||||||
|
|
||||||
# Prepare the query
|
if (defined($strResult))
|
||||||
my $hStatement = $self->{hDb}->prepare($strSql, {pg_async => PG_ASYNC})
|
|
||||||
or confess &log(ERROR, $DBI::errstr . ":\n${strSql}", ERROR_DB_QUERY);
|
|
||||||
|
|
||||||
# Execute the query
|
|
||||||
$hStatement->execute()
|
|
||||||
or confess &log(ERROR, $DBI::errstr. ":\n${strSql}", ERROR_DB_QUERY);
|
|
||||||
|
|
||||||
# Wait for the query to return
|
|
||||||
my $oWait = waitInit(cfgOption(CFGOPT_DB_TIMEOUT));
|
|
||||||
my $bTimeout = true;
|
|
||||||
|
|
||||||
do
|
|
||||||
{
|
{
|
||||||
# Is the statement done?
|
@stryResult = @{JSON::PP->new()->allow_nonref()->decode($strResult)};
|
||||||
if ($hStatement->pg_ready())
|
|
||||||
{
|
|
||||||
# return now if there is no result expected
|
|
||||||
if (!$bResult)
|
|
||||||
{
|
|
||||||
return \@stryResult;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!$hStatement->pg_result())
|
|
||||||
{
|
|
||||||
# Return if the error should be ignored
|
|
||||||
if ($bIgnoreError)
|
|
||||||
{
|
|
||||||
return \@stryResult;
|
|
||||||
}
|
|
||||||
|
|
||||||
# Else report it
|
|
||||||
confess &log(ERROR, $DBI::errstr . ":\n${strSql}", ERROR_DB_QUERY);
|
|
||||||
}
|
|
||||||
|
|
||||||
# Get rows and return them
|
|
||||||
my @stryRow;
|
|
||||||
|
|
||||||
do
|
|
||||||
{
|
|
||||||
# Get next row
|
|
||||||
@stryRow = $hStatement->fetchrow_array;
|
|
||||||
|
|
||||||
# If the row has data then add it to the result
|
|
||||||
if (@stryRow)
|
|
||||||
{
|
|
||||||
push(@{$stryResult[@stryResult]}, @stryRow);
|
|
||||||
}
|
|
||||||
# Else check for error
|
|
||||||
elsif ($hStatement->err)
|
|
||||||
{
|
|
||||||
confess &log(ERROR, $DBI::errstr . ":\n${strSql}", ERROR_DB_QUERY);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
while (@stryRow);
|
|
||||||
|
|
||||||
$bTimeout = false;
|
|
||||||
}
|
|
||||||
} while ($bTimeout && waitMore($oWait));
|
|
||||||
|
|
||||||
# If timeout then cancel the query and confess
|
|
||||||
if ($bTimeout)
|
|
||||||
{
|
|
||||||
$hStatement->pg_cancel();
|
|
||||||
confess &log(ERROR, 'statement timed out after ' . waitInterval($oWait) .
|
|
||||||
" second(s):\n${strSql}", ERROR_DB_TIMEOUT);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -864,7 +785,7 @@ sub walSwitch
|
|||||||
# the user if there have been no writes since the last WAL switch.
|
# the user if there have been no writes since the last WAL switch.
|
||||||
if ($self->{strDbVersion} >= PG_VERSION_91)
|
if ($self->{strDbVersion} >= PG_VERSION_91)
|
||||||
{
|
{
|
||||||
$self->executeSql("select pg_create_restore_point('" . PROJECT_NAME . " Archive Check');");
|
$self->executeSql("select pg_create_restore_point('" . PROJECT_NAME . " Archive Check')::text;");
|
||||||
}
|
}
|
||||||
|
|
||||||
my $strWalFileName = $self->executeSqlOne(
|
my $strWalFileName = $self->executeSqlOne(
|
||||||
@ -1005,7 +926,7 @@ sub replayWait
|
|||||||
|
|
||||||
if ($self->{strDbVersion} >= PG_VERSION_96)
|
if ($self->{strDbVersion} >= PG_VERSION_96)
|
||||||
{
|
{
|
||||||
$strCheckpointLSN = $self->executeSqlOne('select checkpoint_' . $self->lsnId() .' from pg_control_checkpoint()');
|
$strCheckpointLSN = $self->executeSqlOne('select checkpoint_' . $self->lsnId() .'::text from pg_control_checkpoint()');
|
||||||
|
|
||||||
if (lsnNormalize($strCheckpointLSN) le lsnNormalize($strTargetLSN))
|
if (lsnNormalize($strCheckpointLSN) le lsnNormalize($strTargetLSN))
|
||||||
{
|
{
|
||||||
|
@ -72,6 +72,7 @@ These includes define data structures that are required for the C to Perl interf
|
|||||||
***********************************************************************************************************************************/
|
***********************************************************************************************************************************/
|
||||||
#include "xs/crypto/hash.xsh"
|
#include "xs/crypto/hash.xsh"
|
||||||
#include "xs/common/encode.xsh"
|
#include "xs/common/encode.xsh"
|
||||||
|
#include "xs/postgres/client.xsh"
|
||||||
#include "xs/storage/storage.xsh"
|
#include "xs/storage/storage.xsh"
|
||||||
#include "xs/storage/storageRead.xsh"
|
#include "xs/storage/storageRead.xsh"
|
||||||
#include "xs/storage/storageWrite.xsh"
|
#include "xs/storage/storageWrite.xsh"
|
||||||
@ -102,6 +103,7 @@ INCLUDE: xs/config/configTest.xs
|
|||||||
INCLUDE: xs/config/define.xs
|
INCLUDE: xs/config/define.xs
|
||||||
INCLUDE: xs/crypto/hash.xs
|
INCLUDE: xs/crypto/hash.xs
|
||||||
INCLUDE: xs/crypto/random.xs
|
INCLUDE: xs/crypto/random.xs
|
||||||
|
INCLUDE: xs/postgres/client.xs
|
||||||
INCLUDE: xs/postgres/pageChecksum.xs
|
INCLUDE: xs/postgres/pageChecksum.xs
|
||||||
INCLUDE: xs/storage/storage.xs
|
INCLUDE: xs/storage/storage.xs
|
||||||
INCLUDE: xs/storage/storageRead.xs
|
INCLUDE: xs/storage/storageRead.xs
|
||||||
|
@ -99,6 +99,7 @@ my @stryCFile =
|
|||||||
'protocol/parallel.c',
|
'protocol/parallel.c',
|
||||||
'protocol/parallelJob.c',
|
'protocol/parallelJob.c',
|
||||||
'protocol/server.c',
|
'protocol/server.c',
|
||||||
|
'postgres/client.c',
|
||||||
'postgres/pageChecksum.c',
|
'postgres/pageChecksum.c',
|
||||||
'storage/posix/read.c',
|
'storage/posix/read.c',
|
||||||
'storage/posix/storage.c',
|
'storage/posix/storage.c',
|
||||||
@ -132,6 +133,7 @@ WriteMakefile
|
|||||||
-D_POSIX_C_SOURCE=200112L
|
-D_POSIX_C_SOURCE=200112L
|
||||||
-D_FILE_OFFSET_BITS=64
|
-D_FILE_OFFSET_BITS=64
|
||||||
`xml2-config --cflags`
|
`xml2-config --cflags`
|
||||||
|
-I`pg_config --includedir`
|
||||||
)),
|
)),
|
||||||
|
|
||||||
INC => join(' ', qw(
|
INC => join(' ', qw(
|
||||||
@ -141,7 +143,7 @@ WriteMakefile
|
|||||||
|
|
||||||
C => \@stryCFile,
|
C => \@stryCFile,
|
||||||
|
|
||||||
LIBS => '-lcrypto -lssl -lxml2',
|
LIBS => '-lcrypto -lpq -lssl -lxml2',
|
||||||
|
|
||||||
OBJECT => '$(O_FILES)',
|
OBJECT => '$(O_FILES)',
|
||||||
);
|
);
|
||||||
|
@ -1,3 +1,4 @@
|
|||||||
|
pgBackRest::LibC::PgClient T_PTROBJ
|
||||||
pgBackRest::LibC::Storage T_PTROBJ
|
pgBackRest::LibC::Storage T_PTROBJ
|
||||||
pgBackRest::LibC::StorageRead T_PTROBJ
|
pgBackRest::LibC::StorageRead T_PTROBJ
|
||||||
pgBackRest::LibC::StorageWrite T_PTROBJ
|
pgBackRest::LibC::StorageWrite T_PTROBJ
|
||||||
|
89
libc/xs/postgres/client.xs
Normal file
89
libc/xs/postgres/client.xs
Normal file
@ -0,0 +1,89 @@
|
|||||||
|
# ----------------------------------------------------------------------------------------------------------------------------------
|
||||||
|
# PostgreSQL Query Client
|
||||||
|
# ----------------------------------------------------------------------------------------------------------------------------------
|
||||||
|
|
||||||
|
MODULE = pgBackRest::LibC PACKAGE = pgBackRest::LibC::PgClient
|
||||||
|
|
||||||
|
####################################################################################################################################
|
||||||
|
pgBackRest::LibC::PgClient
|
||||||
|
new(class, host, port, database, queryTimeout)
|
||||||
|
PREINIT:
|
||||||
|
MEM_CONTEXT_XS_TEMP_BEGIN()
|
||||||
|
{
|
||||||
|
INPUT:
|
||||||
|
const String *class = STR_NEW_SV($arg);
|
||||||
|
const String *host = STR_NEW_SV($arg);
|
||||||
|
U32 port
|
||||||
|
const String *database = STR_NEW_SV($arg);
|
||||||
|
UV queryTimeout
|
||||||
|
CODE:
|
||||||
|
CHECK(strEqZ(class, PACKAGE_NAME_LIBC "::PgClient"));
|
||||||
|
|
||||||
|
memContextSwitch(MEM_CONTEXT_XS_OLD());
|
||||||
|
RETVAL = pgClientNew(host, port, database, NULL, queryTimeout);
|
||||||
|
memContextSwitch(MEM_CONTEXT_XS_TEMP());
|
||||||
|
OUTPUT:
|
||||||
|
RETVAL
|
||||||
|
CLEANUP:
|
||||||
|
}
|
||||||
|
MEM_CONTEXT_XS_TEMP_END();
|
||||||
|
|
||||||
|
####################################################################################################################################
|
||||||
|
void
|
||||||
|
open(self)
|
||||||
|
PREINIT:
|
||||||
|
MEM_CONTEXT_XS_TEMP_BEGIN()
|
||||||
|
{
|
||||||
|
INPUT:
|
||||||
|
pgBackRest::LibC::PgClient self
|
||||||
|
CODE:
|
||||||
|
pgClientOpen(self);
|
||||||
|
CLEANUP:
|
||||||
|
}
|
||||||
|
MEM_CONTEXT_XS_TEMP_END();
|
||||||
|
|
||||||
|
####################################################################################################################################
|
||||||
|
const char *
|
||||||
|
query(self, query)
|
||||||
|
PREINIT:
|
||||||
|
MEM_CONTEXT_XS_TEMP_BEGIN()
|
||||||
|
{
|
||||||
|
INPUT:
|
||||||
|
pgBackRest::LibC::PgClient self
|
||||||
|
const String *query = STR_NEW_SV($arg);
|
||||||
|
CODE:
|
||||||
|
VariantList *result = pgClientQuery(self, query);
|
||||||
|
RETVAL = result ? strPtr(jsonFromVar(varNewVarLst(result), 0)) : NULL;
|
||||||
|
OUTPUT:
|
||||||
|
RETVAL
|
||||||
|
CLEANUP:
|
||||||
|
}
|
||||||
|
MEM_CONTEXT_XS_TEMP_END();
|
||||||
|
|
||||||
|
####################################################################################################################################
|
||||||
|
void
|
||||||
|
close(self)
|
||||||
|
PREINIT:
|
||||||
|
MEM_CONTEXT_XS_TEMP_BEGIN()
|
||||||
|
{
|
||||||
|
INPUT:
|
||||||
|
pgBackRest::LibC::PgClient self
|
||||||
|
CODE:
|
||||||
|
pgClientClose(self);
|
||||||
|
CLEANUP:
|
||||||
|
}
|
||||||
|
MEM_CONTEXT_XS_TEMP_END();
|
||||||
|
|
||||||
|
####################################################################################################################################
|
||||||
|
void
|
||||||
|
DESTROY(self)
|
||||||
|
PREINIT:
|
||||||
|
MEM_CONTEXT_XS_TEMP_BEGIN()
|
||||||
|
{
|
||||||
|
INPUT:
|
||||||
|
pgBackRest::LibC::PgClient self
|
||||||
|
CODE:
|
||||||
|
pgClientFree(self);
|
||||||
|
CLEANUP:
|
||||||
|
}
|
||||||
|
MEM_CONTEXT_XS_TEMP_END();
|
6
libc/xs/postgres/client.xsh
Normal file
6
libc/xs/postgres/client.xsh
Normal file
@ -0,0 +1,6 @@
|
|||||||
|
/***********************************************************************************************************************************
|
||||||
|
PostgreSQL Query Client Header
|
||||||
|
***********************************************************************************************************************************/
|
||||||
|
#include "postgres/client.h"
|
||||||
|
|
||||||
|
typedef PgClient *pgBackRest__LibC__PgClient;
|
@ -447,7 +447,7 @@ main.o: main.c build.auto.h command/archive/get/get.h command/archive/push/push.
|
|||||||
perl/config.o: perl/config.c build.auto.h common/assert.h common/debug.h common/error.auto.h common/error.h common/lock.h common/log.h common/logLevel.h common/memContext.h common/stackTrace.h common/time.h common/type/buffer.h common/type/convert.h common/type/json.h common/type/keyValue.h common/type/string.h common/type/stringList.h common/type/variant.h common/type/variantList.h config/config.auto.h config/config.h config/define.auto.h config/define.h
|
perl/config.o: perl/config.c build.auto.h common/assert.h common/debug.h common/error.auto.h common/error.h common/lock.h common/log.h common/logLevel.h common/memContext.h common/stackTrace.h common/time.h common/type/buffer.h common/type/convert.h common/type/json.h common/type/keyValue.h common/type/string.h common/type/stringList.h common/type/variant.h common/type/variantList.h config/config.auto.h config/config.h config/define.auto.h config/define.h
|
||||||
$(CC) $(CPPFLAGS) $(CFLAGS) $(CMAKE) -c perl/config.c -o perl/config.o
|
$(CC) $(CPPFLAGS) $(CFLAGS) $(CMAKE) -c perl/config.c -o perl/config.o
|
||||||
|
|
||||||
perl/exec.o: perl/exec.c ../libc/LibC.h build.auto.h common/assert.h common/compress/gzip/compress.h common/compress/gzip/decompress.h common/crypto/cipherBlock.h common/crypto/common.h common/crypto/hash.h common/debug.h common/encode.h common/error.auto.h common/error.h common/io/filter/filter.h common/io/filter/group.h common/io/filter/size.h common/io/http/client.h common/io/http/header.h common/io/http/query.h common/io/io.h common/io/read.h common/io/read.intern.h common/io/write.h common/io/write.intern.h common/lock.h common/log.h common/logLevel.h common/memContext.h common/stackTrace.h common/time.h common/type/buffer.h common/type/convert.h common/type/json.h common/type/keyValue.h common/type/string.h common/type/stringList.h common/type/variant.h common/type/variantList.h config/config.auto.h config/config.h config/define.auto.h config/define.h config/load.h config/parse.h perl/config.h perl/embed.auto.c perl/exec.h perl/libc.auto.c postgres/interface.h postgres/pageChecksum.h storage/helper.h storage/info.h storage/posix/storage.h storage/read.h storage/read.intern.h storage/s3/storage.h storage/s3/storage.intern.h storage/storage.h storage/storage.intern.h storage/write.h storage/write.intern.h version.h ../libc/xs/common/encode.xsh ../libc/xs/crypto/hash.xsh ../libc/xs/storage/storage.xsh ../libc/xs/storage/storageRead.xsh ../libc/xs/storage/storageWrite.xsh
|
perl/exec.o: perl/exec.c ../libc/LibC.h build.auto.h common/assert.h common/compress/gzip/compress.h common/compress/gzip/decompress.h common/crypto/cipherBlock.h common/crypto/common.h common/crypto/hash.h common/debug.h common/encode.h common/error.auto.h common/error.h common/io/filter/filter.h common/io/filter/group.h common/io/filter/size.h common/io/http/client.h common/io/http/header.h common/io/http/query.h common/io/io.h common/io/read.h common/io/read.intern.h common/io/write.h common/io/write.intern.h common/lock.h common/log.h common/logLevel.h common/memContext.h common/stackTrace.h common/time.h common/type/buffer.h common/type/convert.h common/type/json.h common/type/keyValue.h common/type/string.h common/type/stringList.h common/type/variant.h common/type/variantList.h config/config.auto.h config/config.h config/define.auto.h config/define.h config/load.h config/parse.h perl/config.h perl/embed.auto.c perl/exec.h perl/libc.auto.c postgres/client.h postgres/interface.h postgres/pageChecksum.h storage/helper.h storage/info.h storage/posix/storage.h storage/read.h storage/read.intern.h storage/s3/storage.h storage/s3/storage.intern.h storage/storage.h storage/storage.intern.h storage/write.h storage/write.intern.h version.h ../libc/xs/common/encode.xsh ../libc/xs/crypto/hash.xsh ../libc/xs/postgres/client.xsh ../libc/xs/storage/storage.xsh ../libc/xs/storage/storageRead.xsh ../libc/xs/storage/storageWrite.xsh
|
||||||
$(CC) $(CPPFLAGS) $(CFLAGS) $(CMAKE) -c perl/exec.c -o perl/exec.o
|
$(CC) $(CPPFLAGS) $(CFLAGS) $(CMAKE) -c perl/exec.c -o perl/exec.o
|
||||||
|
|
||||||
postgres/client.o: postgres/client.c build.auto.h common/assert.h common/debug.h common/error.auto.h common/error.h common/log.h common/logLevel.h common/macro.h common/memContext.h common/object.h common/stackTrace.h common/time.h common/type/buffer.h common/type/convert.h common/type/keyValue.h common/type/list.h common/type/string.h common/type/stringList.h common/type/variant.h common/type/variantList.h common/wait.h postgres/client.h
|
postgres/client.o: postgres/client.c build.auto.h common/assert.h common/debug.h common/error.auto.h common/error.h common/log.h common/logLevel.h common/macro.h common/memContext.h common/object.h common/stackTrace.h common/time.h common/type/buffer.h common/type/convert.h common/type/keyValue.h common/type/list.h common/type/string.h common/type/stringList.h common/type/variant.h common/type/variantList.h common/wait.h postgres/client.h
|
||||||
|
@ -6889,13 +6889,13 @@ static const EmbeddedModule embeddedModule[] =
|
|||||||
"use strict;\n"
|
"use strict;\n"
|
||||||
"use warnings FATAL => qw(all);\n"
|
"use warnings FATAL => qw(all);\n"
|
||||||
"use Carp qw(confess);\n"
|
"use Carp qw(confess);\n"
|
||||||
|
"use English '-no_match_vars';\n"
|
||||||
"\n"
|
"\n"
|
||||||
"use DBD::Pg ':async';\n"
|
|
||||||
"use DBI;\n"
|
|
||||||
"use Exporter qw(import);\n"
|
"use Exporter qw(import);\n"
|
||||||
"our @EXPORT = qw();\n"
|
"our @EXPORT = qw();\n"
|
||||||
"use Fcntl qw(O_RDONLY);\n"
|
"use Fcntl qw(O_RDONLY);\n"
|
||||||
"use File::Basename qw(dirname);\n"
|
"use File::Basename qw(dirname);\n"
|
||||||
|
"use JSON::PP;\n"
|
||||||
"\n"
|
"\n"
|
||||||
"use pgBackRest::DbVersion;\n"
|
"use pgBackRest::DbVersion;\n"
|
||||||
"use pgBackRest::Common::Exception;\n"
|
"use pgBackRest::Common::Exception;\n"
|
||||||
@ -6984,10 +6984,10 @@ static const EmbeddedModule embeddedModule[] =
|
|||||||
"\n\n"
|
"\n\n"
|
||||||
"my ($strOperation) = logDebugParam(__PACKAGE__ . '->DESTROY');\n"
|
"my ($strOperation) = logDebugParam(__PACKAGE__ . '->DESTROY');\n"
|
||||||
"\n"
|
"\n"
|
||||||
"if (defined($self->{hDb}))\n"
|
"if (defined($self->{oDb}))\n"
|
||||||
"{\n"
|
"{\n"
|
||||||
"$self->{hDb}->disconnect();\n"
|
"$self->{oDb}->close();\n"
|
||||||
"undef($self->{hDb});\n"
|
"undef($self->{oDb});\n"
|
||||||
"}\n"
|
"}\n"
|
||||||
"\n\n"
|
"\n\n"
|
||||||
"return logDebugReturn($strOperation);\n"
|
"return logDebugReturn($strOperation);\n"
|
||||||
@ -7018,58 +7018,45 @@ static const EmbeddedModule embeddedModule[] =
|
|||||||
"\n"
|
"\n"
|
||||||
"else\n"
|
"else\n"
|
||||||
"{\n"
|
"{\n"
|
||||||
"if (!defined($self->{hDb}))\n"
|
"if (!defined($self->{oDb}))\n"
|
||||||
"{\n"
|
"{\n"
|
||||||
|
"$self->{oDb} = new pgBackRest::LibC::PgClient(\n"
|
||||||
|
"cfgOption(cfgOptionIdFromIndex(CFGOPT_PG_SOCKET_PATH, $self->{iRemoteIdx}), false),\n"
|
||||||
|
"cfgOption(cfgOptionIdFromIndex(CFGOPT_PG_PORT, $self->{iRemoteIdx})), 'postgres',\n"
|
||||||
|
"cfgOption(CFGOPT_DB_TIMEOUT) * 1000);\n"
|
||||||
"\n"
|
"\n"
|
||||||
"my $strDbName = 'postgres';\n"
|
"if ($bWarnOnError)\n"
|
||||||
"my $strDbSocketPath = cfgOption(cfgOptionIdFromIndex(CFGOPT_PG_SOCKET_PATH, $self->{iRemoteIdx}), false);\n"
|
|
||||||
"\n\n"
|
|
||||||
"if (defined($strDbSocketPath) && $strDbSocketPath !~ /^\\//)\n"
|
|
||||||
"{\n"
|
"{\n"
|
||||||
"confess &log(ERROR, \"'${strDbSocketPath}' is not valid for '\" . cfgOptionName(CFGOPT_PG_SOCKET_PATH) . \"' option:\" .\n"
|
"eval\n"
|
||||||
"\" path must be absolute\", ERROR_OPTION_INVALID_VALUE);\n"
|
"{\n"
|
||||||
|
"$self->{oDb}->open();\n"
|
||||||
|
"return true;\n"
|
||||||
"}\n"
|
"}\n"
|
||||||
"\n\n"
|
"or do\n"
|
||||||
"my $strDbUri =\n"
|
|
||||||
"\"dbi:Pg:dbname=${strDbName};port=\" . cfgOption(cfgOptionIdFromIndex(CFGOPT_PG_PORT, $self->{iRemoteIdx})) .\n"
|
|
||||||
"(defined($strDbSocketPath) ? \";host=${strDbSocketPath}\" : '');\n"
|
|
||||||
"\n"
|
|
||||||
"logDebugMisc\n"
|
|
||||||
"(\n"
|
|
||||||
"$strOperation, undef,\n"
|
|
||||||
"{name => 'strDbUri', value => $strDbUri},\n"
|
|
||||||
");\n"
|
|
||||||
"\n"
|
|
||||||
"$self->{hDb} = DBI->connect($strDbUri, undef, undef,\n"
|
|
||||||
"{AutoCommit => 1, RaiseError => 0, PrintError => 0, Warn => 0});\n"
|
|
||||||
"\n\n"
|
|
||||||
"if (!$self->{hDb})\n"
|
|
||||||
"{\n"
|
"{\n"
|
||||||
"\n"
|
"&log(WARN, exceptionMessage($EVAL_ERROR));\n"
|
||||||
"if (!$bWarnOnError)\n"
|
|
||||||
"{\n"
|
|
||||||
"confess &log(ERROR, $DBI::errstr, ERROR_DB_CONNECT);\n"
|
|
||||||
"}\n"
|
|
||||||
"\n\n"
|
|
||||||
"&log(WARN, $DBI::errstr);\n"
|
|
||||||
"\n"
|
|
||||||
"$bResult = false;\n"
|
"$bResult = false;\n"
|
||||||
"undef($self->{hDb});\n"
|
"\n"
|
||||||
|
"undef($self->{oDb});\n"
|
||||||
|
"}\n"
|
||||||
"}\n"
|
"}\n"
|
||||||
"else\n"
|
"else\n"
|
||||||
"{\n"
|
"{\n"
|
||||||
|
"$self->{oDb}->open();\n"
|
||||||
|
"}\n"
|
||||||
|
"\n"
|
||||||
|
"if (defined($self->{oDb}))\n"
|
||||||
|
"{\n"
|
||||||
"my ($fDbVersion) = $self->versionGet();\n"
|
"my ($fDbVersion) = $self->versionGet();\n"
|
||||||
"\n"
|
"\n"
|
||||||
"if ($fDbVersion >= PG_VERSION_APPLICATION_NAME)\n"
|
"if ($fDbVersion >= PG_VERSION_APPLICATION_NAME)\n"
|
||||||
"{\n"
|
"{\n"
|
||||||
"\n"
|
"\n"
|
||||||
"$self->{hDb}->do(\n"
|
"$self->{oDb}->query(\n"
|
||||||
"\"set application_name = '\" . PROJECT_NAME . ' [' .\n"
|
"\"set application_name = '\" . PROJECT_NAME . ' [' .\n"
|
||||||
"(cfgOptionValid(CFGOPT_COMMAND) ? cfgOption(CFGOPT_COMMAND) : cfgCommandName(cfgCommandGet())) . \"]'\")\n"
|
"(cfgOptionValid(CFGOPT_COMMAND) ? cfgOption(CFGOPT_COMMAND) : cfgCommandName(cfgCommandGet())) . \"]'\");\n"
|
||||||
"or confess &log(ERROR, $self->{hDb}->errstr, ERROR_DB_QUERY);\n"
|
|
||||||
"\n\n"
|
"\n\n"
|
||||||
"$self->{hDb}->do(\"set search_path = 'pg_catalog'\")\n"
|
"$self->{oDb}->query(\"set search_path = 'pg_catalog'\");\n"
|
||||||
"or confess &log(ERROR, $self->{hDb}->errstr, ERROR_DB_QUERY);\n"
|
|
||||||
"}\n"
|
"}\n"
|
||||||
"}\n"
|
"}\n"
|
||||||
"}\n"
|
"}\n"
|
||||||
@ -7112,66 +7099,11 @@ static const EmbeddedModule embeddedModule[] =
|
|||||||
"else\n"
|
"else\n"
|
||||||
"{\n"
|
"{\n"
|
||||||
"$self->connect();\n"
|
"$self->connect();\n"
|
||||||
"\n\n"
|
"my $strResult = $self->{oDb}->query($strSql);\n"
|
||||||
"my $hStatement = $self->{hDb}->prepare($strSql, {pg_async => PG_ASYNC})\n"
|
|
||||||
"or confess &log(ERROR, $DBI::errstr . \":\\n${strSql}\", ERROR_DB_QUERY);\n"
|
|
||||||
"\n\n"
|
|
||||||
"$hStatement->execute()\n"
|
|
||||||
"or confess &log(ERROR, $DBI::errstr. \":\\n${strSql}\", ERROR_DB_QUERY);\n"
|
|
||||||
"\n\n"
|
|
||||||
"my $oWait = waitInit(cfgOption(CFGOPT_DB_TIMEOUT));\n"
|
|
||||||
"my $bTimeout = true;\n"
|
|
||||||
"\n"
|
"\n"
|
||||||
"do\n"
|
"if (defined($strResult))\n"
|
||||||
"{\n"
|
"{\n"
|
||||||
"\n"
|
"@stryResult = @{JSON::PP->new()->allow_nonref()->decode($strResult)};\n"
|
||||||
"if ($hStatement->pg_ready())\n"
|
|
||||||
"{\n"
|
|
||||||
"\n"
|
|
||||||
"if (!$bResult)\n"
|
|
||||||
"{\n"
|
|
||||||
"return \\@stryResult;\n"
|
|
||||||
"}\n"
|
|
||||||
"\n"
|
|
||||||
"if (!$hStatement->pg_result())\n"
|
|
||||||
"{\n"
|
|
||||||
"\n"
|
|
||||||
"if ($bIgnoreError)\n"
|
|
||||||
"{\n"
|
|
||||||
"return \\@stryResult;\n"
|
|
||||||
"}\n"
|
|
||||||
"\n\n"
|
|
||||||
"confess &log(ERROR, $DBI::errstr . \":\\n${strSql}\", ERROR_DB_QUERY);\n"
|
|
||||||
"}\n"
|
|
||||||
"\n\n"
|
|
||||||
"my @stryRow;\n"
|
|
||||||
"\n"
|
|
||||||
"do\n"
|
|
||||||
"{\n"
|
|
||||||
"\n"
|
|
||||||
"@stryRow = $hStatement->fetchrow_array;\n"
|
|
||||||
"\n\n"
|
|
||||||
"if (@stryRow)\n"
|
|
||||||
"{\n"
|
|
||||||
"push(@{$stryResult[@stryResult]}, @stryRow);\n"
|
|
||||||
"}\n"
|
|
||||||
"\n"
|
|
||||||
"elsif ($hStatement->err)\n"
|
|
||||||
"{\n"
|
|
||||||
"confess &log(ERROR, $DBI::errstr . \":\\n${strSql}\", ERROR_DB_QUERY);\n"
|
|
||||||
"}\n"
|
|
||||||
"}\n"
|
|
||||||
"while (@stryRow);\n"
|
|
||||||
"\n"
|
|
||||||
"$bTimeout = false;\n"
|
|
||||||
"}\n"
|
|
||||||
"} while ($bTimeout && waitMore($oWait));\n"
|
|
||||||
"\n\n"
|
|
||||||
"if ($bTimeout)\n"
|
|
||||||
"{\n"
|
|
||||||
"$hStatement->pg_cancel();\n"
|
|
||||||
"confess &log(ERROR, 'statement timed out after ' . waitInterval($oWait) .\n"
|
|
||||||
"\" second(s):\\n${strSql}\", ERROR_DB_TIMEOUT);\n"
|
|
||||||
"}\n"
|
"}\n"
|
||||||
"}\n"
|
"}\n"
|
||||||
"\n\n"
|
"\n\n"
|
||||||
@ -7593,7 +7525,7 @@ static const EmbeddedModule embeddedModule[] =
|
|||||||
"\n\n\n"
|
"\n\n\n"
|
||||||
"if ($self->{strDbVersion} >= PG_VERSION_91)\n"
|
"if ($self->{strDbVersion} >= PG_VERSION_91)\n"
|
||||||
"{\n"
|
"{\n"
|
||||||
"$self->executeSql(\"select pg_create_restore_point('\" . PROJECT_NAME . \" Archive Check');\");\n"
|
"$self->executeSql(\"select pg_create_restore_point('\" . PROJECT_NAME . \" Archive Check')::text;\");\n"
|
||||||
"}\n"
|
"}\n"
|
||||||
"\n"
|
"\n"
|
||||||
"my $strWalFileName = $self->executeSqlOne(\n"
|
"my $strWalFileName = $self->executeSqlOne(\n"
|
||||||
@ -7705,7 +7637,7 @@ static const EmbeddedModule embeddedModule[] =
|
|||||||
"\n"
|
"\n"
|
||||||
"if ($self->{strDbVersion} >= PG_VERSION_96)\n"
|
"if ($self->{strDbVersion} >= PG_VERSION_96)\n"
|
||||||
"{\n"
|
"{\n"
|
||||||
"$strCheckpointLSN = $self->executeSqlOne('select checkpoint_' . $self->lsnId() .' from pg_control_checkpoint()');\n"
|
"$strCheckpointLSN = $self->executeSqlOne('select checkpoint_' . $self->lsnId() .'::text from pg_control_checkpoint()');\n"
|
||||||
"\n"
|
"\n"
|
||||||
"if (lsnNormalize($strCheckpointLSN) le lsnNormalize($strTargetLSN))\n"
|
"if (lsnNormalize($strCheckpointLSN) le lsnNormalize($strTargetLSN))\n"
|
||||||
"{\n"
|
"{\n"
|
||||||
|
@ -80,6 +80,7 @@ These includes define data structures that are required for the C to Perl interf
|
|||||||
***********************************************************************************************************************************/
|
***********************************************************************************************************************************/
|
||||||
#include "xs/crypto/hash.xsh"
|
#include "xs/crypto/hash.xsh"
|
||||||
#include "xs/common/encode.xsh"
|
#include "xs/common/encode.xsh"
|
||||||
|
#include "xs/postgres/client.xsh"
|
||||||
#include "xs/storage/storage.xsh"
|
#include "xs/storage/storage.xsh"
|
||||||
#include "xs/storage/storageRead.xsh"
|
#include "xs/storage/storageRead.xsh"
|
||||||
#include "xs/storage/storageWrite.xsh"
|
#include "xs/storage/storageWrite.xsh"
|
||||||
@ -268,7 +269,10 @@ XS_EUPXS(XS_pgBackRest__LibC_libcUvSize)
|
|||||||
/* INCLUDE: Including 'xs/crypto/random.xs' from 'xs/crypto/hash.xs' */
|
/* INCLUDE: Including 'xs/crypto/random.xs' from 'xs/crypto/hash.xs' */
|
||||||
|
|
||||||
|
|
||||||
/* INCLUDE: Including 'xs/postgres/pageChecksum.xs' from 'xs/crypto/random.xs' */
|
/* INCLUDE: Including 'xs/postgres/client.xs' from 'xs/crypto/random.xs' */
|
||||||
|
|
||||||
|
|
||||||
|
/* INCLUDE: Including 'xs/postgres/pageChecksum.xs' from 'xs/postgres/client.xs' */
|
||||||
|
|
||||||
|
|
||||||
/* INCLUDE: Including 'xs/storage/storage.xs' from 'xs/postgres/pageChecksum.xs' */
|
/* INCLUDE: Including 'xs/storage/storage.xs' from 'xs/postgres/pageChecksum.xs' */
|
||||||
@ -1570,7 +1574,162 @@ XS_EUPXS(XS_pgBackRest__LibC_pageChecksum)
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/* INCLUDE: Returning to 'xs/crypto/random.xs' from 'xs/postgres/pageChecksum.xs' */
|
/* INCLUDE: Returning to 'xs/postgres/client.xs' from 'xs/postgres/pageChecksum.xs' */
|
||||||
|
|
||||||
|
|
||||||
|
XS_EUPXS(XS_pgBackRest__LibC__PgClient_new); /* prototype to pass -Wmissing-prototypes */
|
||||||
|
XS_EUPXS(XS_pgBackRest__LibC__PgClient_new)
|
||||||
|
{
|
||||||
|
dVAR; dXSARGS;
|
||||||
|
if (items != 5)
|
||||||
|
croak_xs_usage(cv, "class, host, port, database, queryTimeout");
|
||||||
|
{
|
||||||
|
MEM_CONTEXT_XS_TEMP_BEGIN()
|
||||||
|
{
|
||||||
|
const String * class = STR_NEW_SV(ST(0));
|
||||||
|
const String * host = STR_NEW_SV(ST(1));
|
||||||
|
U32 port = (unsigned long)SvUV(ST(2))
|
||||||
|
;
|
||||||
|
const String * database = STR_NEW_SV(ST(3));
|
||||||
|
UV queryTimeout = (UV)SvUV(ST(4))
|
||||||
|
;
|
||||||
|
pgBackRest__LibC__PgClient RETVAL;
|
||||||
|
CHECK(strEqZ(class, PACKAGE_NAME_LIBC "::PgClient"));
|
||||||
|
|
||||||
|
memContextSwitch(MEM_CONTEXT_XS_OLD());
|
||||||
|
RETVAL = pgClientNew(host, port, database, NULL, queryTimeout);
|
||||||
|
memContextSwitch(MEM_CONTEXT_XS_TEMP());
|
||||||
|
{
|
||||||
|
SV * RETVALSV;
|
||||||
|
RETVALSV = sv_newmortal();
|
||||||
|
sv_setref_pv(RETVALSV, "pgBackRest::LibC::PgClient", (void*)RETVAL);
|
||||||
|
ST(0) = RETVALSV;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
MEM_CONTEXT_XS_TEMP_END();
|
||||||
|
}
|
||||||
|
XSRETURN(1);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
XS_EUPXS(XS_pgBackRest__LibC__PgClient_open); /* prototype to pass -Wmissing-prototypes */
|
||||||
|
XS_EUPXS(XS_pgBackRest__LibC__PgClient_open)
|
||||||
|
{
|
||||||
|
dVAR; dXSARGS;
|
||||||
|
if (items != 1)
|
||||||
|
croak_xs_usage(cv, "self");
|
||||||
|
{
|
||||||
|
MEM_CONTEXT_XS_TEMP_BEGIN()
|
||||||
|
{
|
||||||
|
pgBackRest__LibC__PgClient self;
|
||||||
|
|
||||||
|
if (SvROK(ST(0)) && sv_derived_from(ST(0), "pgBackRest::LibC::PgClient")) {
|
||||||
|
IV tmp = SvIV((SV*)SvRV(ST(0)));
|
||||||
|
self = INT2PTR(pgBackRest__LibC__PgClient,tmp);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
Perl_croak_nocontext("%s: %s is not of type %s",
|
||||||
|
"pgBackRest::LibC::PgClient::open",
|
||||||
|
"self", "pgBackRest::LibC::PgClient")
|
||||||
|
;
|
||||||
|
pgClientOpen(self);
|
||||||
|
}
|
||||||
|
MEM_CONTEXT_XS_TEMP_END();
|
||||||
|
}
|
||||||
|
XSRETURN_EMPTY;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
XS_EUPXS(XS_pgBackRest__LibC__PgClient_query); /* prototype to pass -Wmissing-prototypes */
|
||||||
|
XS_EUPXS(XS_pgBackRest__LibC__PgClient_query)
|
||||||
|
{
|
||||||
|
dVAR; dXSARGS;
|
||||||
|
if (items != 2)
|
||||||
|
croak_xs_usage(cv, "self, query");
|
||||||
|
{
|
||||||
|
MEM_CONTEXT_XS_TEMP_BEGIN()
|
||||||
|
{
|
||||||
|
pgBackRest__LibC__PgClient self;
|
||||||
|
const String * query = STR_NEW_SV(ST(1));
|
||||||
|
const char * RETVAL;
|
||||||
|
dXSTARG;
|
||||||
|
|
||||||
|
if (SvROK(ST(0)) && sv_derived_from(ST(0), "pgBackRest::LibC::PgClient")) {
|
||||||
|
IV tmp = SvIV((SV*)SvRV(ST(0)));
|
||||||
|
self = INT2PTR(pgBackRest__LibC__PgClient,tmp);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
Perl_croak_nocontext("%s: %s is not of type %s",
|
||||||
|
"pgBackRest::LibC::PgClient::query",
|
||||||
|
"self", "pgBackRest::LibC::PgClient")
|
||||||
|
;
|
||||||
|
VariantList *result = pgClientQuery(self, query);
|
||||||
|
RETVAL = result ? strPtr(jsonFromVar(varNewVarLst(result), 0)) : NULL;
|
||||||
|
sv_setpv(TARG, RETVAL); XSprePUSH; PUSHTARG;
|
||||||
|
}
|
||||||
|
MEM_CONTEXT_XS_TEMP_END();
|
||||||
|
}
|
||||||
|
XSRETURN(1);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
XS_EUPXS(XS_pgBackRest__LibC__PgClient_close); /* prototype to pass -Wmissing-prototypes */
|
||||||
|
XS_EUPXS(XS_pgBackRest__LibC__PgClient_close)
|
||||||
|
{
|
||||||
|
dVAR; dXSARGS;
|
||||||
|
if (items != 1)
|
||||||
|
croak_xs_usage(cv, "self");
|
||||||
|
{
|
||||||
|
MEM_CONTEXT_XS_TEMP_BEGIN()
|
||||||
|
{
|
||||||
|
pgBackRest__LibC__PgClient self;
|
||||||
|
|
||||||
|
if (SvROK(ST(0)) && sv_derived_from(ST(0), "pgBackRest::LibC::PgClient")) {
|
||||||
|
IV tmp = SvIV((SV*)SvRV(ST(0)));
|
||||||
|
self = INT2PTR(pgBackRest__LibC__PgClient,tmp);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
Perl_croak_nocontext("%s: %s is not of type %s",
|
||||||
|
"pgBackRest::LibC::PgClient::close",
|
||||||
|
"self", "pgBackRest::LibC::PgClient")
|
||||||
|
;
|
||||||
|
pgClientClose(self);
|
||||||
|
}
|
||||||
|
MEM_CONTEXT_XS_TEMP_END();
|
||||||
|
}
|
||||||
|
XSRETURN_EMPTY;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
XS_EUPXS(XS_pgBackRest__LibC__PgClient_DESTROY); /* prototype to pass -Wmissing-prototypes */
|
||||||
|
XS_EUPXS(XS_pgBackRest__LibC__PgClient_DESTROY)
|
||||||
|
{
|
||||||
|
dVAR; dXSARGS;
|
||||||
|
if (items != 1)
|
||||||
|
croak_xs_usage(cv, "self");
|
||||||
|
{
|
||||||
|
MEM_CONTEXT_XS_TEMP_BEGIN()
|
||||||
|
{
|
||||||
|
pgBackRest__LibC__PgClient self;
|
||||||
|
|
||||||
|
if (SvROK(ST(0))) {
|
||||||
|
IV tmp = SvIV((SV*)SvRV(ST(0)));
|
||||||
|
self = INT2PTR(pgBackRest__LibC__PgClient,tmp);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
Perl_croak_nocontext("%s: %s is not a reference",
|
||||||
|
"pgBackRest::LibC::PgClient::DESTROY",
|
||||||
|
"self")
|
||||||
|
;
|
||||||
|
pgClientFree(self);
|
||||||
|
}
|
||||||
|
MEM_CONTEXT_XS_TEMP_END();
|
||||||
|
}
|
||||||
|
XSRETURN_EMPTY;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/* INCLUDE: Returning to 'xs/crypto/random.xs' from 'xs/postgres/client.xs' */
|
||||||
|
|
||||||
|
|
||||||
XS_EUPXS(XS_pgBackRest__LibC_cryptoRandomBytes); /* prototype to pass -Wmissing-prototypes */
|
XS_EUPXS(XS_pgBackRest__LibC_cryptoRandomBytes); /* prototype to pass -Wmissing-prototypes */
|
||||||
@ -2142,6 +2301,11 @@ XS_EXTERNAL(boot_pgBackRest__LibC)
|
|||||||
newXS_deffile("pgBackRest::LibC::Storage::type", XS_pgBackRest__LibC__Storage_type);
|
newXS_deffile("pgBackRest::LibC::Storage::type", XS_pgBackRest__LibC__Storage_type);
|
||||||
newXS_deffile("pgBackRest::LibC::storageRepoFree", XS_pgBackRest__LibC_storageRepoFree);
|
newXS_deffile("pgBackRest::LibC::storageRepoFree", XS_pgBackRest__LibC_storageRepoFree);
|
||||||
newXS_deffile("pgBackRest::LibC::pageChecksum", XS_pgBackRest__LibC_pageChecksum);
|
newXS_deffile("pgBackRest::LibC::pageChecksum", XS_pgBackRest__LibC_pageChecksum);
|
||||||
|
newXS_deffile("pgBackRest::LibC::PgClient::new", XS_pgBackRest__LibC__PgClient_new);
|
||||||
|
newXS_deffile("pgBackRest::LibC::PgClient::open", XS_pgBackRest__LibC__PgClient_open);
|
||||||
|
newXS_deffile("pgBackRest::LibC::PgClient::query", XS_pgBackRest__LibC__PgClient_query);
|
||||||
|
newXS_deffile("pgBackRest::LibC::PgClient::close", XS_pgBackRest__LibC__PgClient_close);
|
||||||
|
newXS_deffile("pgBackRest::LibC::PgClient::DESTROY", XS_pgBackRest__LibC__PgClient_DESTROY);
|
||||||
newXS_deffile("pgBackRest::LibC::cryptoRandomBytes", XS_pgBackRest__LibC_cryptoRandomBytes);
|
newXS_deffile("pgBackRest::LibC::cryptoRandomBytes", XS_pgBackRest__LibC_cryptoRandomBytes);
|
||||||
newXS_deffile("pgBackRest::LibC::cryptoHashOne", XS_pgBackRest__LibC_cryptoHashOne);
|
newXS_deffile("pgBackRest::LibC::cryptoHashOne", XS_pgBackRest__LibC_cryptoHashOne);
|
||||||
newXS_deffile("pgBackRest::LibC::cfgCommandId", XS_pgBackRest__LibC_cfgCommandId);
|
newXS_deffile("pgBackRest::LibC::cfgCommandId", XS_pgBackRest__LibC_cfgCommandId);
|
||||||
|
@ -13,10 +13,8 @@
|
|||||||
# - docker tag pgbackrest/test:{vm}-base pgbackrest/test:{vm}-base-YYYYMMDDA
|
# - docker tag pgbackrest/test:{vm}-base pgbackrest/test:{vm}-base-YYYYMMDDA
|
||||||
# - docker push pgbackrest/test:{vm}-base-YYYYMMDDA
|
# - docker push pgbackrest/test:{vm}-base-YYYYMMDDA
|
||||||
# **********************************************************************************************************************************
|
# **********************************************************************************************************************************
|
||||||
20190705A:
|
20190725A:
|
||||||
u18: de2136d4a4ed6a7b8eaf6934c7e6f8e5c59f5ad4
|
u18: 91252e3e21ff553b231094194e13966065c32d6b
|
||||||
|
co6: 194df5323239146733c51e77e9324b495bb2c727
|
||||||
20190701A:
|
co7: 3373903192a6dcf7c0b88c66ce9223da54ee2deb
|
||||||
co6: b3812cda61c33e959f309a9eceb23ef731fc0da2
|
u12: d3f1c8123b747b479586c2bbbf544c9a9cc42619
|
||||||
co7: d645dbac2f094d980ac266094d0c26e84aca3ca6
|
|
||||||
u12: c919aa8562ff89713ee9ecf7dd41479798dde4d7
|
|
||||||
|
@ -11,7 +11,6 @@ use strict;
|
|||||||
use warnings FATAL => qw(all);
|
use warnings FATAL => qw(all);
|
||||||
use Carp qw(confess);
|
use Carp qw(confess);
|
||||||
|
|
||||||
use DBI;
|
|
||||||
use Exporter qw(import);
|
use Exporter qw(import);
|
||||||
our @EXPORT = qw();
|
our @EXPORT = qw();
|
||||||
use File::Basename qw(dirname);
|
use File::Basename qw(dirname);
|
||||||
|
@ -11,7 +11,6 @@ use strict;
|
|||||||
use warnings FATAL => qw(all);
|
use warnings FATAL => qw(all);
|
||||||
use Carp qw(confess);
|
use Carp qw(confess);
|
||||||
|
|
||||||
use DBI;
|
|
||||||
use Exporter qw(import);
|
use Exporter qw(import);
|
||||||
our @EXPORT = qw();
|
our @EXPORT = qw();
|
||||||
use Fcntl ':mode';
|
use Fcntl ':mode';
|
||||||
|
@ -98,8 +98,7 @@ sub run
|
|||||||
$self->optionTestSetBool(CFGOPT_ONLINE, true);
|
$self->optionTestSetBool(CFGOPT_ONLINE, true);
|
||||||
$self->configTestLoad(CFGCMD_STANZA_CREATE);
|
$self->configTestLoad(CFGCMD_STANZA_CREATE);
|
||||||
|
|
||||||
$self->testException(sub {(new pgBackRest::Stanza())}, ERROR_DB_CONNECT,
|
$self->testException(sub {(new pgBackRest::Stanza())}, ERROR_DB_CONNECT, "unable to connect to.*");
|
||||||
"could not connect to server: No such file or directory\n");
|
|
||||||
|
|
||||||
$self->optionTestSetBool(CFGOPT_ONLINE, false);
|
$self->optionTestSetBool(CFGOPT_ONLINE, false);
|
||||||
}
|
}
|
||||||
|
@ -13,7 +13,13 @@
|
|||||||
libxml2-dev,
|
libxml2-dev,
|
||||||
txt2man,
|
txt2man,
|
||||||
zlib1g-dev
|
zlib1g-dev
|
||||||
@@ -24,7 +22,7 @@
|
@@ -19,12 +18,12 @@
|
||||||
|
|
||||||
|
Package: pgbackrest
|
||||||
|
Architecture: any
|
||||||
|
-Depends: libdbd-pg-perl,
|
||||||
|
+Depends: perl,
|
||||||
|
postgresql-common,
|
||||||
${misc:Depends},
|
${misc:Depends},
|
||||||
${perl:Depends},
|
${perl:Depends},
|
||||||
${shlibs:Depends}
|
${shlibs:Depends}
|
||||||
|
@ -1,6 +1,6 @@
|
|||||||
--- pgbackrest.spec
|
--- pgbackrest.spec
|
||||||
+++ pgbackrest.spec
|
+++ pgbackrest.spec
|
||||||
@@ -10,7 +10,6 @@
|
@@ -10,15 +10,14 @@
|
||||||
Source0: https://github.com/pgbackrest/pgbackrest/archive/release/%{version}.tar.gz
|
Source0: https://github.com/pgbackrest/pgbackrest/archive/release/%{version}.tar.gz
|
||||||
Source1: pgbackrest-conf.patch
|
Source1: pgbackrest-conf.patch
|
||||||
BuildRoot: %{_tmppath}/%{name}-%{version}-%{release}-root-%(%{__id_u} -n)
|
BuildRoot: %{_tmppath}/%{name}-%{version}-%{release}-root-%(%{__id_u} -n)
|
||||||
@ -8,3 +8,13 @@
|
|||||||
%if 0%{?rhel} && 0%{?rhel} <= 6
|
%if 0%{?rhel} && 0%{?rhel} <= 6
|
||||||
Requires: perl-parent perl-JSON perl-Time-HiRes
|
Requires: perl-parent perl-JSON perl-Time-HiRes
|
||||||
%else
|
%else
|
||||||
|
Requires: perl-JSON-PP
|
||||||
|
%endif
|
||||||
|
-Requires: perl-Digest-SHA perl-DBD-Pg perl-Time-HiRes zlib
|
||||||
|
+Requires: perl-Digest-SHA perl-Time-HiRes zlib libxml2
|
||||||
|
Requires: perl(:MODULE_COMPAT_%(eval "`%{__perl} -V:version`"; echo $version))
|
||||||
|
-BuildRequires: openssl-devel zlib-devel perl-ExtUtils-Embed
|
||||||
|
+BuildRequires: openssl-devel zlib-devel postgresql-libs perl-ExtUtils-Embed
|
||||||
|
|
||||||
|
%description
|
||||||
|
pgBackRest aims to be a simple, reliable backup and restore system that can
|
||||||
|
Loading…
x
Reference in New Issue
Block a user