私はPostgreSQLの通知システムで遊んでいますが、pg_notify(text、text)が機能しない理由を一生理解できません。この機能は過度に文書化されておらず、実際に使用されている例は多くないので、ここで質問しても構わないと思いました。
以下を実行すると、期待どおりに機能します。
LISTEN my_channel;
NOTIFY my_channel, 'my message text';
ただし、pg_notify()関数を使用すると、null値が返され、通知は送信されません。エラーも発生しません。使用例は次のとおりです。
SELECT pg_notify('my_channel', 'my message text');
NOTIFY関数を使用することもできますが、私の目標は、通知を次のようなクエリに合理化することです。
select pg_notify(get_player_error_channel(username)::TEXT, 'test'::TEXT)
from player;
ばかげた何かが欠けているに違いないと思いますが、その理由を理解することはできませんでした。 NOTIFYについて説明しているページは、次の場所にあります。 http://www.postgresql.org/docs/9.0/static/sql-notify.html
その上で、pg_notify()についてこれについて言及しているので、大幅な違いはないと思います。
pg_notify通知を送信するには、関数pg_notify(text、text)を使用することもできます。この関数は、最初の引数としてチャネル名を取り、2番目の引数としてペイロードを取ります。一定でないチャネル名とペイロードを操作する必要がある場合、この関数はNOTIFYコマンドよりもはるかに簡単に使用できます。
いつも助けてくれてありがとう
編集:データベースのバージョンは次のとおりです。「i686-pc-linux-gnu上のPostgreSQL 9.0.3、GCC gcc(GCC)4.2.4、32ビットでコンパイル」
これについては、PostgreSQLメーリングリスト(http://archives.postgresql.org/pgsql-bugs/2011-03/msg00041.php)で説明し、動作の理由について通知を受けました。
彼らの答えは、「.. relnamesを二重引用符で囲む必要があります(「Test」をリッスンします)。サーバーで大文字と小文字を区別しないようにするには、pg_notifyはrelnameではなく文字列を取ります。 (マーリンとトムに感謝します)
これは、チャネルが常に小文字に強制されるため、以下が機能することを意味します
LISTEN ERRORCHANNEL;
NOTIFY ERRORCHANNEL, 'something!';
NOTIFY eRrorChanNel, 'something!';
チャネル名を二重引用符で囲む場合は、大文字と小文字が区別されます。
したがって、次の場合、最初の通知は受信されますが、2番目の通知は受信されません。
LISTEN "ERRORCHANNEL";
NOTIFY "ERRORCHANNEL", 'something!';
NOTIFY "eRrorChanNel", 'something!';
同様に、二重引用符はERRORCHANNELのケースを強制的に維持するため、以下が機能します。
LISTEN "ERRORCHANNEL";
SELECT pg_notify('ERRORCHANNEL', 'something!');
これは機能しませんが:
LISTEN ERRORCHANNEL;
SELECT pg_notify('ERRORCHANNEL', 'something!');
この状況では、ERRORCHANNELはLISTENコマンドで二重引用符で囲まれていないため、PostgreSQLはそれを小文字に強制します。チャネルパラメータはrelnameではなくtext型であるため、pg_notify()関数では大文字と小文字は変更されません。一緒にチャネルが一致しないため(ERRORCHANNE!= errorchannel)、通知が受信されることはありません。