Example 31-2. libpq Example Program 2

Started by Niko Wareabout 5 years ago3 messagesgeneral
Jump to latest
#1Niko Ware
nikowareinc@gmail.com

I need notifications to a C application on inserts to a table. The
notification funcion is listed below. My program and "Example 31-2. libpq
Example Program 2" receive the notification, but the payload message in
"PGnotify *notify->extra" is invalid.

The example code is located here:
https://www.postgresql.org/docs/current/libpq-example.html

I modified the code to include the "extra" member in the following
statement:

fprintf(stderr,
"ASYNC NOTIFY of '%s' received from backend PID %d:
%s\n",
notify->relname, notify->be_pid, *notify->extra*);

Both the example and my application core on an invalid address for "extra".
Using psql with LISTEN works correctly. My application works as expected
except for the payload message. I was unable to locate any example of how
to retrieve the payload in C. The "extra" member is a char*.

================================================

CREATE OR REPLACE FUNCTION OS_FB_UPDATE_FCNFY()
RETURNS trigger
LANGUAGE 'plpgsql'
AS $BODY$
DECLARE
notification TEXT;
BEGIN
notification :=
NEW.node_id || ':' ||
NEW.block_id || ':' ||
NEW.operation || ':' ||
NEW.update_class || ':' ||
NEW.update_data || ':' ||
to_char(COALESCE(NEW.time_stamp, current_timestamp), 'MM-DD-YYY
HH24:MI:SS');

PERFORM pg_notify('notifyondatachange', row_to_json(NEW)::text);

RETURN NEW;

EXCEPTION
WHEN others THEN
RAISE WARNING '[ONSITE.OS_FB_UPDATE_FCNFY] - UDF ERROR [OTHER] -
SQLSTATE: %, SQLERRM: %', SQLSTATE, SQLERRM;
END
$BODY$;

#2David G. Johnston
david.g.johnston@gmail.com
In reply to: Niko Ware (#1)
Re: Example 31-2. libpq Example Program 2

On Wednesday, March 10, 2021, Niko Ware <nikowareinc@gmail.com> wrote:

I modified the code to include the "extra" member in the following
statement:

fprintf(stderr,
"ASYNC NOTIFY of '%s' received from backend PID %d:
%s\n",
notify->relname, notify->be_pid, *notify->extra*);

I was unable to locate any example of how to retrieve the payload in C.

Since psql does it correctly that is a good place to find code.

https://github.com/postgres/postgres/blob/3f0daeb02f8dd605f89de9aa2349137c09cc7fb4/src/bin/psql/common.c#L689

Yes, your modification should work. Looking at the history that extra
field is 18 years old. I’m not in a position to confirm whether or not this
is somehow broken on head but has gone undiscovered, but it seems
unlikely. Only advice I can think of besides waiting for a more
experienced hacker is to check the relevant header files and
breakpoint/trace the code and see what “notify” actually looks like. Or
start from scratch on a clean setup and try again confirming you have
checked out master/head from the official repository.

David J.

#3Tom Lane
tgl@sss.pgh.pa.us
In reply to: Niko Ware (#1)
Re: Example 31-2. libpq Example Program 2

Niko Ware <nikowareinc@gmail.com> writes:

I modified the code to include the "extra" member in the following
statement:

fprintf(stderr,
"ASYNC NOTIFY of '%s' received from backend PID %d: %s\n",
notify->relname, notify->be_pid, *notify->extra*);

Both the example and my application core on an invalid address for "extra".

Modifying testlibpq2.c like that works for me, FWIW.

I speculate maybe you have a macro definition of "extra" that is bollixing
things somehow? Kind of a weak theory, but nothing else comes to mind.

regards, tom lane