@restorecommerce/chassis-srv
Version:
Restore Commerce microservice chassis
119 lines • 4.88 kB
JavaScript
"use strict";
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
if (k2 === undefined) k2 = k;
var desc = Object.getOwnPropertyDescriptor(m, k);
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
desc = { enumerable: true, get: function() { return m[k]; } };
}
Object.defineProperty(o, k2, desc);
}) : (function(o, m, k, k2) {
if (k2 === undefined) k2 = k;
o[k2] = m[k];
}));
var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
Object.defineProperty(o, "default", { enumerable: true, value: v });
}) : function(o, v) {
o["default"] = v;
});
var __importStar = (this && this.__importStar) || function (mod) {
if (mod && mod.__esModule) return mod;
var result = {};
if (mod != null) for (var k in mod) if (k !== "default" && Object.prototype.hasOwnProperty.call(mod, k)) __createBinding(result, mod, k);
__setModuleDefault(result, mod);
return result;
};
Object.defineProperty(exports, "__esModule", { value: true });
exports.OffsetStore = void 0;
const _ = __importStar(require("lodash"));
const redis_1 = require("redis");
/**
* Stores the offsets of the provided topics to redis periodically
*/
class OffsetStore {
constructor(events, config, logger) {
if (!logger) {
throw new Error('Missing logger config or object');
}
if (_.isNil(events)) {
logger.error('No Kafka client was provided, offsets will not be stored to redis');
return;
}
this.config = config;
this.logger = logger;
if (!(this.config.get('events'))
|| !(this.config.get('events:kafka'))
|| !(this.config.get('events:kafka:topics'))) {
throw new Error('Kafka events configuration was not provided.');
}
this.kafkaEvents = events;
if (this.config.get('redis')) {
const redisConfig = this.config.get('redis');
if (_.has(redisConfig, 'db-indexes.db-offsetStore')) {
redisConfig.database = _.get(redisConfig, 'db-indexes.db-offsetStore');
}
this.redisClient = (0, redis_1.createClient)(redisConfig);
this.redisClient.on('error', (err) => logger.error('Redis Client Error in offsetstore', { code: err.code, message: err.message, stack: err.stack }));
this.redisClient.connect().then((val) => logger.info('Redis client connection successful for offsetstore'));
}
this.topics = {};
this.timerID = [];
setTimeout(this.updateTopicOffsets.bind(this), 5000);
}
/**
* updates the topic offset in redis periodically
*
*/
updateTopicOffsets() {
// Iterate through the topics and updateOffsets periodically for each topic
// events.topic(TopicName) - gives the topic object
const kafkaCfg = this.config.get('events:kafka');
const topicTypes = _.keys(kafkaCfg.topics);
for (let i = 0; i < topicTypes.length; i += 1) {
const topicType = topicTypes[i];
const topicName = kafkaCfg.topics[topicType].topic;
this.kafkaEvents.topic(topicName).then(topic => {
this.topics[topicType] = topic;
this.timerID[i] = setInterval(this.storeOffset.bind(this), this.config.get('redis:offsetStoreInterval'), this.topics[topicType], topicName);
});
}
}
/**
* stores the offset to redis
* @param {object} topic Topic object
* @param {object} redisClient
* @return {object}
*/
async storeOffset(topic, topicName) {
// get the latest offset here each time and store it.
const offsetValue = await topic.$offset(-1);
const redisKey = this.config.get('events:kafka:kafka:clientId') + ':' + topicName;
this.redisClient.set(redisKey, offsetValue);
}
/**
* get the offset value for the topic from redis
* @param {string} topic Topic name
* @return {object}
*/
async getOffset(topicName) {
const redisKey = this.config.get('events:kafka:kafka:clientId') + ':' + topicName;
const offsetValue = await this.redisClient.get(redisKey);
this.logger.info('The offset value retreived from redis for topic is:', { topicName, offsetValue });
return Number(offsetValue);
}
/**
* stops the redis client
* @param {object} topic Topic object
* @param {object} redisClient
* @return {object}
*/
async stop() {
for (let i = 0; i < this.timerID.length; i += 1) {
clearInterval(this.timerID[i]);
}
if (this.redisClient) {
await this.redisClient.quit();
}
}
}
exports.OffsetStore = OffsetStore;
//# sourceMappingURL=index.js.map