pg-transactional-outbox
Version:
A PostgreSQL based transactional outbox and inbox pattern implementation to support exactly once message processing (with at least once message delivery).
64 lines • 5.8 kB
JavaScript
;
var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
return new (P || (P = Promise))(function (resolve, reject) {
function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
step((generator = generator.apply(thisArg, _arguments || [])).next());
});
};
Object.defineProperty(exports, "__esModule", { value: true });
exports.initializeReplicationMessageListener = void 0;
const create_error_handler_1 = require("../handler/create-error-handler");
const create_message_handler_1 = require("../handler/create-message-handler");
const message_not_found_retry_strategy_1 = require("../strategies/message-not-found-retry-strategy");
const message_processing_db_client_strategy_1 = require("../strategies/message-processing-db-client-strategy");
const message_processing_timeout_strategy_1 = require("../strategies/message-processing-timeout-strategy");
const message_processing_transaction_level_strategy_1 = require("../strategies/message-processing-transaction-level-strategy");
const message_retry_strategy_1 = require("../strategies/message-retry-strategy");
const poisonous_message_retry_strategy_1 = require("../strategies/poisonous-message-retry-strategy");
const config_1 = require("./config");
const logical_replication_listener_1 = require("./logical-replication-listener");
const concurrency_strategy_1 = require("./strategies/concurrency-strategy");
const listener_restart_strategy_1 = require("./strategies/listener-restart-strategy");
/**
* Initialize the listener to watch for outbox or inbox table inserts via
* PostgreSQL logical replication.
* @param config The configuration object with required values to connect to the WAL.
* @param messageHandlers A list of message handlers to handle specific messages or a single general message handler that handles all messages.
* @param logger A logger instance for logging trace up to error logs
* @param strategies Strategies to provide custom logic for handling specific scenarios
* @returns Functions for a clean shutdown.
*/
const initializeReplicationMessageListener = (config, messageHandlers, logger, strategies) => {
const fullConfig = (0, config_1.applyDefaultReplicationListenerConfigValues)(config);
const allStrategies = applyDefaultStrategies(strategies, fullConfig, logger);
const messageHandler = (0, create_message_handler_1.createMessageHandler)(messageHandlers, allStrategies, fullConfig, logger, 'replication');
const errorHandler = (0, create_error_handler_1.createErrorHandler)(messageHandlers, allStrategies, fullConfig, logger);
const [shutdown] = (0, logical_replication_listener_1.createLogicalReplicationListener)(fullConfig, messageHandler, errorHandler, logger, allStrategies);
return [
() => __awaiter(void 0, void 0, void 0, function* () {
var _a;
yield Promise.all([
(_a = allStrategies.messageProcessingDbClientStrategy) === null || _a === void 0 ? void 0 : _a.shutdown(),
shutdown(),
]);
}),
];
};
exports.initializeReplicationMessageListener = initializeReplicationMessageListener;
const applyDefaultStrategies = (strategies, config, logger) => {
var _a, _b, _c, _d, _e, _f, _g, _h;
return ({
concurrencyStrategy: (_a = strategies === null || strategies === void 0 ? void 0 : strategies.concurrencyStrategy) !== null && _a !== void 0 ? _a : (0, concurrency_strategy_1.defaultReplicationConcurrencyStrategy)(),
messageProcessingDbClientStrategy: (_b = strategies === null || strategies === void 0 ? void 0 : strategies.messageProcessingDbClientStrategy) !== null && _b !== void 0 ? _b : (0, message_processing_db_client_strategy_1.defaultMessageProcessingDbClientStrategy)(config, logger),
messageProcessingTimeoutStrategy: (_c = strategies === null || strategies === void 0 ? void 0 : strategies.messageProcessingTimeoutStrategy) !== null && _c !== void 0 ? _c : (0, message_processing_timeout_strategy_1.defaultMessageProcessingTimeoutStrategy)(config),
messageProcessingTransactionLevelStrategy: (_d = strategies === null || strategies === void 0 ? void 0 : strategies.messageProcessingTransactionLevelStrategy) !== null && _d !== void 0 ? _d : (0, message_processing_transaction_level_strategy_1.defaultMessageProcessingTransactionLevelStrategy)(),
messageRetryStrategy: (_e = strategies === null || strategies === void 0 ? void 0 : strategies.messageRetryStrategy) !== null && _e !== void 0 ? _e : (0, message_retry_strategy_1.defaultMessageRetryStrategy)(config),
poisonousMessageRetryStrategy: (_f = strategies === null || strategies === void 0 ? void 0 : strategies.poisonousMessageRetryStrategy) !== null && _f !== void 0 ? _f : (0, poisonous_message_retry_strategy_1.defaultPoisonousMessageRetryStrategy)(config),
listenerRestartStrategy: (_g = strategies === null || strategies === void 0 ? void 0 : strategies.listenerRestartStrategy) !== null && _g !== void 0 ? _g : (0, listener_restart_strategy_1.defaultReplicationListenerRestartStrategy)(config),
messageNotFoundRetryStrategy: (_h = strategies === null || strategies === void 0 ? void 0 : strategies.messageNotFoundRetryStrategy) !== null && _h !== void 0 ? _h : (0, message_not_found_retry_strategy_1.defaultMessageNotFoundRetryStrategy)(config),
});
};
//# sourceMappingURL=replication-message-listener.js.map