roach-storm
Version:
Apache Kafka to Google Pub/Sub Gateway, API controlled
98 lines (97 loc) • 3.38 kB
JavaScript
;
Object.defineProperty(exports, "__esModule", { value: true });
const Debug = require("debug");
const Mongoose = require("mongoose");
const debug = Debug("roach:model:topicconfig");
class TopicConfigModel {
constructor(roachStorm, mongoWrapper = null) {
this.metrics = roachStorm.metrics;
this.mongoWrapper = mongoWrapper;
this.name = "topicconfig";
this.model = null;
}
registerModel(mongoose, schemaConstructor) {
const schemaDefinition = {
sourceTopic: String,
parseAsJson: Boolean,
timestamp: Number,
pipes: [
{
targetTopic: String,
filter: Mongoose.Schema.Types.Mixed,
chunkSize: Number,
publishTombstones: Boolean,
},
],
};
const schema = new schemaConstructor(schemaDefinition);
schema.index({ sourceTopic: 1, type: -1 });
this.model = mongoose.model(this.name, schema);
this.model.on("index", (error) => {
if (error) {
debug("Index creation failed", error.message);
}
else {
debug("Index creation successfull.");
}
});
debug("Registered model with schema.");
}
get(topic) {
return this.model.findOne({ topic }).lean().exec();
}
async listAsTopics() {
const topicConfigs = await this.list();
return topicConfigs.map((topicConfig) => topicConfig.sourceTopic);
}
list() {
return this.model.find({}).lean().exec();
}
upsert(sourceTopic, pipes = [], timestamp = Date.now(), parseAsJson = true) {
if (!pipes || !pipes.length) {
throw new Error("Pipes must be set.");
}
pipes.forEach((pipe) => this.validatePipe(pipe));
const document = {
sourceTopic,
timestamp,
pipes,
parseAsJson,
};
const query = {
sourceTopic,
};
const queryOptions = {
upsert: true,
};
return this.model.findOneAndUpdate(query, document, queryOptions).exec();
}
delete(sourceTopic) {
return this.model.deleteMany({ sourceTopic }).exec();
}
truncateCollection() {
debug("Truncating collection");
return this.model.deleteMany({}).exec();
}
validatePipe(pipe) {
if (!pipe || typeof pipe !== "object") {
throw new Error("Pipe is not an object");
}
if (!pipe.targetTopic || typeof pipe.targetTopic !== "string") {
throw new Error("Pipe has no targetTopic.");
}
if (!pipe.filter) {
return;
}
Object.keys(pipe.filter).map((key) => {
if (key.indexOf("[") !== -1 || key.indexOf("]") !== -1) {
throw new Error("Character not allowed in filter key [], only dot strings as path allowed.");
}
if (Array.isArray(pipe.filter[key]) || (typeof pipe.filter[key] === "object"
&& pipe.filter[key] !== null)) {
throw new Error("Filter field values, must not be arrays or objects, please resolve via flat string paths. " + key);
}
});
}
}
exports.TopicConfigModel = TopicConfigModel;