This is a controller from an Express app that lets users view and manage articles. There are at least a couple of issues I'd like to address...
The program displays a list of articles in a sidebar that appears on each page. Right now, the app queries the database for article names, caches them, and includes them in the payload. It does this for each route that loads a view.
Is there a more efficient way to do this?
A good bit of code is repeated in the first two methods (retrieve
and settings
). Both methods get a list of articles for the sidebar and show an article or the settings for an article.
Is there a way to DRY up this code?
const { Article } = require('../models');
import CacheService from '../services/cache';
const ttl = 60 * 60 * 1;
const cache = new CacheService(ttl);
module.exports = {
// display one article
retrieve (req, res, next) {
// list of articles displayed in the sidebar
const allArticles = module.exports.getUserArticles(req.user.id);
// the article to display
const thisArticle = module.exports.getArticleById(req.params.publicId);
Promise
.all([allArticles, thisArticle])
.then((result) => {
const articles = result[0];
const article = result[1];
if (!article) {
const error = new Error('Article not found');
error.status = 404;
return next(error);
}
return res.render('article', { articles, article, title: article.name });
})
.catch(next);
},
// show settings page for an article
settings (req, res, next) {
// list of articles displayed in the sidebar
const allArticles = module.exports.getUserArticles(req.user.id);
// the article to display
const thisArticle = module.exports.getArticleById(req.params.publicId);
Promise
.all([allArticles, thisArticle])
.then((result) => {
const articles = result[0];
const article = result[1];
if (!article) {
const error = new Error('Article not found');
error.status = 404;
return next(error);
}
const { page } = req.params;
const pageTitle = module.exports.getSettingsPageTitle(page);
const pageTemplate = `settings-${page}`;
return res.render(pageTemplate, { articles, article, title: `${article.name}: ${pageTitle}` });
})
.catch(next);
},
getUserArticles (userId) {
return cache.get(`getUserArticles_${userId}`, () => Article.findAll({ where: { userId }, order: [['name']] }));
},
getArticleById (publicId) {
return cache.get(`getArticleById_${publicId}`, () => Article.findOne({ where: { publicId } }));
},
getSettingsPageTitle (page) {
return {
edit: 'Edit name, URL',
response: 'Edit email response',
notifications: 'Configure notifications'
}[page];
}
};