72 lines
1.8 KiB
JavaScript
Raw Normal View History

'use strict';
/**
* Loaders.js service
*
* @description: A set of functions similar to controller's actions to avoid code duplication.
*/
const _ = require('lodash');
const DataLoader = require('dataloader');
module.exports = {
loaders: {},
initializeLoader() {
2019-01-16 17:26:15 +01:00
this.resetLoaders();
// Create loaders for each relational field (exclude core models).
Object.keys(strapi.models)
.filter(model => model.internal !== true)
2019-12-10 16:21:21 +01:00
.forEach(modelKey => {
const model = strapi.models[modelKey];
this.createLoader(model.uid);
});
// Reproduce the same pattern for each plugin.
Object.keys(strapi.plugins).forEach(plugin => {
2019-12-10 16:21:21 +01:00
Object.keys(strapi.plugins[plugin].models).forEach(modelKey => {
const model = strapi.plugins[plugin].models[modelKey];
this.createLoader(model.uid);
});
});
// Add the loader for the AdminUser as well, so we can query `created_by` and `updated_by` AdminUsers
this.createLoader('strapi::user');
},
resetLoaders() {
2019-01-16 17:26:15 +01:00
this.loaders = {};
},
createLoader(modelUID) {
2019-12-10 16:21:21 +01:00
if (this.loaders[modelUID]) {
return this.loaders[modelUID];
2019-01-16 17:26:15 +01:00
}
const loadFn = queries => this.batchQuery(modelUID, queries);
const loadOptions = {
cacheKeyFn: key => this.serializeKey(key),
};
2019-10-01 17:45:16 +02:00
this.loaders[modelUID] = new DataLoader(loadFn, loadOptions);
},
serializeKey(key) {
return _.isObjectLike(key) ? JSON.stringify(_.cloneDeep(key)) : key;
},
async batchQuery(modelUID, queries) {
// Extract queries from keys and merge similar queries.
return Promise.all(queries.map(query => this.makeQuery(modelUID, query)));
2019-01-15 17:16:28 +01:00
},
async makeQuery(modelUID, query = {}) {
if (query.single === true) {
return strapi.query(modelUID).findOne(query.filters, []);
2018-11-27 18:48:37 +01:00
}
return strapi.query(modelUID).find(query.filters, []);
},
};