The London Perl and Raku Workshop takes place on 26th Oct 2024. If your company depends on Perl, please consider sponsoring and/or attending.

NAME

PGObject::Util::LogRep::TestDecoding - Parse Pg's test_decoding messages

VERSION

Version 0.1.4

SYNOPSIS

    use PGObject::util::LogRep::TestDecoding qw(parse_msg);

    my $msg = parse_msg($repmsg); # procedural interace
    # tells you the operation, transaction status etc.

    # or the OO interface which gives more functionality

    my $decoder = PGObject::util::LogRep::TestDecoding->new(
        schema=> ['myschema'], txn_status => 0
    );
    handle_message($decoder->parse($repmsg)) if $decoder->matches($repmsg);

DESCRIPTION

This module provides parse capabiltiies for the test_decoding plugin for PostgreSQL's logical replication. The test_decoding plugin does not recognize or handle publications and simply replicates everything.

Messages follow formats like:

  table public.data: INSERT: id[integer]:3 data[text]:'5'

or for begin or commit messages:

  BEGIN 529
  COMMIT 529

Transactions are always processed sequentially in the test decoding stack.

This module can be combined with AnyEvent::PGRecvLogical to create programs which process PostgreSQL's logical replication streams.

Note that PostgreSQL's logical replication sends out transactions in commit order and this module assumes that it will process most messages if transaction information is important (which it might not be for some applications).

EXPORT

parse_msg # single message / non-OO parser

ATTRIBUTES/ACCESSORS

These are for the OO interface only. These are read-ony after the object is created but can be set in the constructor. If you need to change them. create a new object instead.

schema Maybe[ArrayRef[Str]]

Undef or an arrayref of schalars. If it is set, then matches returns true if the message matches any table in any schema mentioned.

txn_status Bool

Whether to report transactoin status.

tables Maybe[ArrayRef[Str]]

A list of fully qualified tablenames to match against. Note that this filter operates along with the schema filter and if either matches, the match is met.

current_txn (calculated)

Logical replication sends messages out for transactions in commit order. Assuming the transaction numbers have been requested, this will produce the transaction number of the most recent BEGIN statement. Note that this information is only available when certain options are passed so it may return undef.

GRAMMAR

Test_decoding lines come in two basic formats: transaction control lines and DML lines. The former have a syntax like BEGIN 123 (or COMMIT).

The DML records have a longer and more complex. They have a format begins with the word "table" followed by a fully qualified tablename, then an operation, then a column list in name[type]:value format. Identifiers can be SQL escaped. So can literals.

Since transactions are handled sequentially in commit order, the DML records do not carry transaction identifiers in them.

SUBROUTINES/METHODS

output

The Parsing routines return a consistent payload in the form of a hashref with one of two formats depending on the message type. Both forms have a "type" field which is set to "txn" or "dml" depending on the record type.

txn messages

The txn message output has three fields:

type = txn
txnid

Integer, may be omitted if data not available

txncmd

Either BEGIN or COMMIT

Examples:

  { type   => "txn",
    txncmd => "BEGIN',
    txnid  => 50123 }

  { type   => "txn",
    txncmd => "COMMIT',
    txnid  => 50123 }

Or if transaction numbers are not available"

  { type   => "txn",
    txncmd => "BEGIN' }

dml messages

The dml lessages have a number of fields:

type = "dml"
schema

Namespace of the table

tablename

Name of the table

row_data

A hashref of name => value.

operation

One of INSERT, UPDATE, or DELETE

Examples:

  { type      => 'dml',
    tablename => 'sometable',
    schema    => 'public',
    row_data  => { id => 1, key => 'test', value => 123 },
    operation => 'INSERT' }

  { type      => 'dml',
    tablename => 'sometable',
    schema    => 'public',
    row_data  => { id => 1, key => 'test', value => 123 },
    operation => 'DELETE' }

parse (OOP interface)

In the OOP interface, the parse function parses the message and returns the output.

matches (OOP Interface)

Evaluates whether the schema AND tablename match rules are met. If the message is a txn message it will then be processed (and possibly affect the txnid state).

Note that only txn messages are parsed here.

parse_msg

parse_msg parses the message provided and returns a hashref as detailed above.

AUTHOR

Chris Travers, <chris.travers at gmail.com>

BUGS

Please report any bugs or feature requests to bug-pgobject-util-logrep-testdecoding at rt.cpan.org, or through the web interface at https://rt.cpan.org/NoAuth/ReportBug.html?Queue=PGObject-util-LogRep-TestDecoding. I will be notified, and then you'll automatically be notified of progress on your bug as I make changes.

SUPPORT

You can find documentation for this module with the perldoc command.

    perldoc PGObject::util::LogRep::TestDecoding

You can also look for information at:

ACKNOWLEDGEMENTS

LICENSE AND COPYRIGHT

This software is Copyright (c) 2023 by Chris Travers.

This program is released under the following license:

  BSD2