0.8.0 • Published 3 years ago

@fetchq/pg-pubsub v0.8.0

Weekly downloads
25
License
MIT
Repository
github
Last release
3 years ago

PG PubSub

A Publish/Subscribe implementation on top of PostgreSQL NOTIFY/LISTEN

Linting Build Status Node CI Build Status Coverage Status dependencies Status Known Vulnerabilities js-semistandard-style

Installation

npm install pg-pubsub --save

Requirements

Node.js >= 10.x Postgres >= 9.4

Usage

const PGPubsub = require('pg-pubsub');
const pubsubInstance = new PGPubsub(uri[, options]);

Options

{
  [log]: Function // default: silent when NODE_ENV=production, otherwise defaults to console.log(...)
}

Methods

  • addChannel(channelName, eventListener) – starts listening on a channel and optionally adds an event listener for that event. As PGPubsub inherits from EventEmitter one also add it oneself.
  • removeChannel(channelName, eventListener) – either removes all event listeners and stops listeneing on the channel or removes the specified event listener and stops listening on the channel if that was the last listener attached.
  • publish(channelName, data) – publishes the specified data JSON-encoded to the specified channel. It may be better to do this by sending the NOTIFY channelName, '{"hello":"world"}' query yourself using your ordinary Postgres pool, rather than relying on the single connection of this module. Returns a Promise that will become rejected or resolved depending on the success of the Postgres call.
  • close(): Promise – closes down the database connection and removes all listeners. Useful for graceful shutdowns.
  • All EventEmitter methods are inherited from EventEmitter

Examples

Simple

const pubsubInstance = new PGPubsub('postgres://username@localhost/database');

pubsubInstance.addChannel('channelName', function (channelPayload) {
  // Process the payload – if it was JSON that JSON has been parsed into an object for you
});

pubsubInstance.publish('channelName', { hello: "world" });

The above sends NOTIFY channelName, '{"hello":"world"}' to PostgreSQL, which will trigger the above listener with the parsed JSON in channelPayload.

Advanced

const pubsubInstance = new PGPubsub('postgres://username@localhost/database');

pubsubInstance.addChannel('channelName');

// pubsubInstance is a full EventEmitter object that sends events on channel names
pubsubInstance.once('channelName', function (channelPayload) {
  // Process the payload
});

Description

Creating a PGPubsub instance will not do much up front. It will prepare itself to start a Postgres connection once the first channel is added and then it will keep a connection open until its shut down, reconnecting it if it gets lost, so that it can constantly listen for new notifications.

Lint / Test

Automate via Make/Docker

The easiest way to run tests is via Makefile on a Linux compatible environment:

make test

Manual Execution

In case you want to run the tests manually, you first need to be able to access a PostgreSQL instance. You can do that in 2 ways:

Via Docker

docker run --rm -it -p 5432:5432 -e \
POSTGRES_DB=pgpubsub_test -e \
POSTGRES_PASSWORD=postgres postgres

Via Environment File

You can create an environment file in test/.env:

DATABASE_TEST_URL=postgres://postgres:postgres@localhost:5432/postgres

DATABASE_TEST_URL_INVALID_USER=postgres://invalidUser:postgres@localhost:5432/postgres

DATABASE_TEST_URL_INVALID_PASSWORD=postgres://postgres:invalidPassword@localhost:5432/postgres

Once the PostgreSQL setup is done, you can run the test with your Node environment:

npm i
npm test