atlassian-connect-express
Version:
Library for building Atlassian Add-ons on top of Express
115 lines (89 loc) • 2.86 kB
JavaScript
const redis = require("redis");
const util = require("util");
const { getAsObject, getAsString } = require("./utils");
const REDIS_COMMANDS = ["get", "set", "del", "keys"];
const redisKey = (key, clientKey) => {
return clientKey ? `${clientKey}:${key}` : key;
};
const installationKey = forgeInstallationId => {
return `installation:${forgeInstallationId};`;
};
const forgeKey = (key, installationId) => {
return `forge:${installationId}:${key}`;
};
class RedisAdapter {
constructor(logger, opts) {
const redisClient = redis.createClient(process.env["DB_URL"] || opts.url);
this.client = REDIS_COMMANDS.reduce((client, command) => {
client[command] = util.promisify(redisClient[command]).bind(redisClient);
return client;
}, {});
}
async get(key, clientKey) {
const val = await this.client.get(redisKey(key, clientKey));
return getAsObject(val);
}
async saveInstallation(val, clientKey) {
const clientSetting = await this.set("clientInfo", val, clientKey);
const forgeInstallationId = clientSetting.installationId;
if (forgeInstallationId) {
await this.associateInstallations(forgeInstallationId, clientKey);
}
return clientSetting;
}
async set(key, val, clientKey) {
await this.client.set(redisKey(key, clientKey), getAsString(val));
return this.get(key, clientKey);
}
async del(key, clientKey) {
await this.client.del(redisKey(key, clientKey));
}
async getAllClientInfos() {
const keys = await this.client.keys("*:clientInfo");
return Promise.all(
keys.map(key => {
return this.get(key);
})
);
}
isMemoryStore() {
return false;
}
async associateInstallations(forgeInstallationId, clientKey) {
await this.client.set(installationKey(forgeInstallationId), clientKey);
}
async deleteAssociation(forgeInstallationId) {
await this.client.del(installationKey(forgeInstallationId));
}
async getClientSettingsForForgeInstallation(forgeInstallationId) {
const clientKey = await this.client.get(
installationKey(forgeInstallationId)
);
if (!clientKey) {
return null;
}
return this.get("clientInfo", clientKey);
}
// Storage interface for Forge settings
forForgeInstallation(installationId) {
return {
del: async key => {
await this.client.del(forgeKey(key, installationId));
},
get: async key => {
const val = await this.client.get(forgeKey(key, installationId));
return getAsObject(val);
},
set: async (key, val) => {
await this.client.set(forgeKey(key, installationId), getAsString(val));
return val;
}
};
}
}
module.exports = function (logger, opts) {
if (arguments.length === 0) {
return RedisAdapter;
}
return new RedisAdapter(logger, opts);
};