mirror of
https://github.com/strapi/strapi.git
synced 2025-11-12 00:03:40 +00:00
Merge pull request #3770 from strapi/chore/boostrap-async
make boostrap functions async only
This commit is contained in:
commit
5bd4b0d747
@ -83,9 +83,36 @@ The `bootstrap` function is called at every server start. You can use it to add
|
|||||||
|
|
||||||
Here are some use cases:
|
Here are some use cases:
|
||||||
|
|
||||||
- Create an admin user if there isn't.
|
- Create an admin user if there isn't one.
|
||||||
- Fill the database with some necessary data.
|
- Fill the database with some necessary data.
|
||||||
- Check that the database is up-and-running.
|
- Check that the database is up-and-running.
|
||||||
|
- Load some envrionments variables.
|
||||||
|
|
||||||
|
The bootstrap function can be synchronous or asynchronous
|
||||||
|
|
||||||
|
**Synchronous**
|
||||||
|
|
||||||
|
```js
|
||||||
|
module.exports = () => {
|
||||||
|
// some sync code
|
||||||
|
};
|
||||||
|
```
|
||||||
|
|
||||||
|
**Return a promise**
|
||||||
|
|
||||||
|
```js
|
||||||
|
module.exports = () => {
|
||||||
|
return new Promise(/* some code */);
|
||||||
|
};
|
||||||
|
```
|
||||||
|
|
||||||
|
**Be async**
|
||||||
|
|
||||||
|
```js
|
||||||
|
module.exports = async () => {
|
||||||
|
await someSetup();
|
||||||
|
};
|
||||||
|
```
|
||||||
|
|
||||||
### CRON tasks
|
### CRON tasks
|
||||||
|
|
||||||
|
|||||||
@ -8,6 +8,4 @@
|
|||||||
* run jobs, or perform some special logic.
|
* run jobs, or perform some special logic.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
module.exports = cb => {
|
module.exports = () => {};
|
||||||
cb();
|
|
||||||
};
|
|
||||||
|
|||||||
@ -6,8 +6,8 @@
|
|||||||
*
|
*
|
||||||
* This gives you an opportunity to set up your data model,
|
* This gives you an opportunity to set up your data model,
|
||||||
* run jobs, or perform some special logic.
|
* run jobs, or perform some special logic.
|
||||||
|
*
|
||||||
|
* See more details here: https://strapi.io/documentation/3.0.0-beta.x/configurations/configurations.html#bootstrap
|
||||||
*/
|
*/
|
||||||
|
|
||||||
module.exports = cb => {
|
module.exports = () => {};
|
||||||
cb();
|
|
||||||
};
|
|
||||||
|
|||||||
@ -10,8 +10,8 @@ const {
|
|||||||
/**
|
/**
|
||||||
* Synchronize content manager schemas
|
* Synchronize content manager schemas
|
||||||
*/
|
*/
|
||||||
module.exports = cb => {
|
module.exports = () => {
|
||||||
syncSchemas().then(() => cb(), err => cb(err));
|
return syncSchemas();
|
||||||
};
|
};
|
||||||
|
|
||||||
async function syncSchemas() {
|
async function syncSchemas() {
|
||||||
|
|||||||
@ -2,11 +2,11 @@ const fs = require('fs');
|
|||||||
const path = require('path');
|
const path = require('path');
|
||||||
const _ = require('lodash');
|
const _ = require('lodash');
|
||||||
|
|
||||||
module.exports = async cb => {
|
module.exports = async () => {
|
||||||
// Check if the plugin users-permissions is installed because the documentation needs it
|
// Check if the plugin users-permissions is installed because the documentation needs it
|
||||||
if (Object.keys(strapi.plugins).indexOf('users-permissions') === -1) {
|
if (Object.keys(strapi.plugins).indexOf('users-permissions') === -1) {
|
||||||
throw new Error(
|
throw new Error(
|
||||||
'In order to make the documentation plugin works the users-permissions one is required',
|
'In order to make the documentation plugin works the users-permissions one is required'
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -26,16 +26,24 @@ module.exports = async cb => {
|
|||||||
// Generate plugins' documentation
|
// Generate plugins' documentation
|
||||||
const pluginsWithDocumentationNeeded = services.getPluginsWithDocumentationNeeded();
|
const pluginsWithDocumentationNeeded = services.getPluginsWithDocumentationNeeded();
|
||||||
pluginsWithDocumentationNeeded.forEach(plugin => {
|
pluginsWithDocumentationNeeded.forEach(plugin => {
|
||||||
const isDocExisting = services.checkIfPluginDocumentationFolderExists(plugin);
|
const isDocExisting = services.checkIfPluginDocumentationFolderExists(
|
||||||
|
plugin
|
||||||
|
);
|
||||||
|
|
||||||
if (!isDocExisting) {
|
if (!isDocExisting) {
|
||||||
services.createDocumentationDirectory(services.getPluginDocumentationPath(plugin));
|
services.createDocumentationDirectory(
|
||||||
|
services.getPluginDocumentationPath(plugin)
|
||||||
|
);
|
||||||
// create the overrides directory
|
// create the overrides directory
|
||||||
services.createDocumentationDirectory(services.getPluginOverrideDocumentationPath(plugin));
|
services.createDocumentationDirectory(
|
||||||
|
services.getPluginOverrideDocumentationPath(plugin)
|
||||||
|
);
|
||||||
services.createPluginDocumentationFile(plugin);
|
services.createPluginDocumentationFile(plugin);
|
||||||
shouldUpdateFullDoc = true;
|
shouldUpdateFullDoc = true;
|
||||||
} else {
|
} else {
|
||||||
const needToUpdatePluginDoc = services.checkIfPluginDocNeedsUpdate(plugin);
|
const needToUpdatePluginDoc = services.checkIfPluginDocNeedsUpdate(
|
||||||
|
plugin
|
||||||
|
);
|
||||||
|
|
||||||
if (needToUpdatePluginDoc) {
|
if (needToUpdatePluginDoc) {
|
||||||
services.createPluginDocumentationFile(plugin);
|
services.createPluginDocumentationFile(plugin);
|
||||||
@ -54,7 +62,9 @@ module.exports = async cb => {
|
|||||||
// If the documentation directory doesn't exist create it
|
// If the documentation directory doesn't exist create it
|
||||||
services.createDocumentationDirectory(services.getDocumentationPath(api));
|
services.createDocumentationDirectory(services.getDocumentationPath(api));
|
||||||
// Create the overrides directory
|
// Create the overrides directory
|
||||||
services.createDocumentationDirectory(services.getDocumentationOverridesPath(api));
|
services.createDocumentationDirectory(
|
||||||
|
services.getDocumentationOverridesPath(api)
|
||||||
|
);
|
||||||
// Create the documentation files per version
|
// Create the documentation files per version
|
||||||
services.createDocumentationFile(api); // Then create the {api}.json documentation file
|
services.createDocumentationFile(api); // Then create the {api}.json documentation file
|
||||||
shouldUpdateFullDoc = true;
|
shouldUpdateFullDoc = true;
|
||||||
@ -96,7 +106,10 @@ module.exports = async cb => {
|
|||||||
.sort((a, b) => a - b)
|
.sort((a, b) => a - b)
|
||||||
.join('.');
|
.join('.');
|
||||||
};
|
};
|
||||||
const oldDoc = require(path.resolve(documentationPath, 'full_documentation.json'));
|
const oldDoc = require(path.resolve(
|
||||||
|
documentationPath,
|
||||||
|
'full_documentation.json'
|
||||||
|
));
|
||||||
const oldDocTags = getDocTagsToString(oldDoc);
|
const oldDocTags = getDocTagsToString(oldDoc);
|
||||||
const currentDocTags = getDocTagsToString(fullDoc);
|
const currentDocTags = getDocTagsToString(fullDoc);
|
||||||
|
|
||||||
@ -113,8 +126,7 @@ module.exports = async cb => {
|
|||||||
fs.writeFileSync(
|
fs.writeFileSync(
|
||||||
path.resolve(documentationPath, 'full_documentation.json'),
|
path.resolve(documentationPath, 'full_documentation.json'),
|
||||||
JSON.stringify(fullDoc, null, 2),
|
JSON.stringify(fullDoc, null, 2),
|
||||||
'utf8',
|
'utf8'
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
cb();
|
|
||||||
};
|
};
|
||||||
|
|||||||
@ -9,7 +9,7 @@
|
|||||||
*/
|
*/
|
||||||
const _ = require('lodash');
|
const _ = require('lodash');
|
||||||
|
|
||||||
module.exports = async cb => {
|
module.exports = async () => {
|
||||||
// set plugin store
|
// set plugin store
|
||||||
const pluginStore = strapi.store({
|
const pluginStore = strapi.store({
|
||||||
environment: strapi.config.environment,
|
environment: strapi.config.environment,
|
||||||
@ -27,7 +27,6 @@ module.exports = async cb => {
|
|||||||
strapi.plugins.email.config.providers.push(require(installedProvider));
|
strapi.plugins.email.config.providers.push(require(installedProvider));
|
||||||
}
|
}
|
||||||
|
|
||||||
try {
|
|
||||||
// if provider config does not exist set one by default
|
// if provider config does not exist set one by default
|
||||||
const config = await pluginStore.get({ key: 'provider' });
|
const config = await pluginStore.get({ key: 'provider' });
|
||||||
|
|
||||||
@ -42,10 +41,4 @@ module.exports = async cb => {
|
|||||||
|
|
||||||
await pluginStore.set({ key: 'provider', value });
|
await pluginStore.set({ key: 'provider', value });
|
||||||
}
|
}
|
||||||
} catch (err) {
|
|
||||||
strapi.log.error(err);
|
|
||||||
strapi.stop();
|
|
||||||
}
|
|
||||||
|
|
||||||
cb();
|
|
||||||
};
|
};
|
||||||
|
|||||||
@ -8,20 +8,18 @@
|
|||||||
* run jobs, or perform some special logic.
|
* run jobs, or perform some special logic.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
module.exports = async cb => {
|
module.exports = async () => {
|
||||||
const pluginStore = strapi.store({
|
const pluginStore = strapi.store({
|
||||||
environment: '',
|
environment: '',
|
||||||
type: 'core'
|
type: 'core',
|
||||||
});
|
});
|
||||||
|
|
||||||
if (!await pluginStore.get({key: 'application'})) {
|
if (!(await pluginStore.get({ key: 'application' }))) {
|
||||||
const value = {
|
const value = {
|
||||||
name: 'Default Application',
|
name: 'Default Application',
|
||||||
description: 'This API is going to be awesome!'
|
description: 'This API is going to be awesome!',
|
||||||
};
|
};
|
||||||
|
|
||||||
await pluginStore.set({ key: 'application', value });
|
await pluginStore.set({ key: 'application', value });
|
||||||
}
|
}
|
||||||
|
|
||||||
cb();
|
|
||||||
};
|
};
|
||||||
|
|||||||
@ -9,7 +9,7 @@
|
|||||||
*/
|
*/
|
||||||
const _ = require('lodash');
|
const _ = require('lodash');
|
||||||
|
|
||||||
module.exports = async cb => {
|
module.exports = async () => {
|
||||||
// set plugin store
|
// set plugin store
|
||||||
const pluginStore = strapi.store({
|
const pluginStore = strapi.store({
|
||||||
environment: strapi.config.environment,
|
environment: strapi.config.environment,
|
||||||
@ -27,7 +27,6 @@ module.exports = async cb => {
|
|||||||
strapi.plugins.upload.config.providers.push(require(installedProvider));
|
strapi.plugins.upload.config.providers.push(require(installedProvider));
|
||||||
}
|
}
|
||||||
|
|
||||||
try {
|
|
||||||
// if provider config does not exist set one by default
|
// if provider config does not exist set one by default
|
||||||
const config = await pluginStore.get({ key: 'provider' });
|
const config = await pluginStore.get({ key: 'provider' });
|
||||||
|
|
||||||
@ -44,9 +43,4 @@ module.exports = async cb => {
|
|||||||
|
|
||||||
await pluginStore.set({ key: 'provider', value });
|
await pluginStore.set({ key: 'provider', value });
|
||||||
}
|
}
|
||||||
} catch (err) {
|
|
||||||
strapi.log.error(err);
|
|
||||||
strapi.stop();
|
|
||||||
}
|
|
||||||
cb();
|
|
||||||
};
|
};
|
||||||
|
|||||||
@ -10,12 +10,16 @@
|
|||||||
const _ = require('lodash');
|
const _ = require('lodash');
|
||||||
const uuid = require('uuid/v4');
|
const uuid = require('uuid/v4');
|
||||||
|
|
||||||
module.exports = async cb => {
|
module.exports = async () => {
|
||||||
if (!_.get(strapi.plugins['users-permissions'], 'config.jwtSecret')) {
|
if (!_.get(strapi.plugins['users-permissions'], 'config.jwtSecret')) {
|
||||||
const jwtSecret = uuid();
|
const jwtSecret = uuid();
|
||||||
_.set(strapi.plugins['users-permissions'], 'config.jwtSecret', jwtSecret);
|
_.set(strapi.plugins['users-permissions'], 'config.jwtSecret', jwtSecret);
|
||||||
|
|
||||||
await strapi.fs.writePluginFile('users-permissions', 'config/jwt.json', JSON.stringify({ jwtSecret }, null, 2));
|
await strapi.fs.writePluginFile(
|
||||||
|
'users-permissions',
|
||||||
|
'config/jwt.json',
|
||||||
|
JSON.stringify({ jwtSecret }, null, 2)
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
const pluginStore = strapi.store({
|
const pluginStore = strapi.store({
|
||||||
@ -144,14 +148,14 @@ module.exports = async cb => {
|
|||||||
unique_email: true,
|
unique_email: true,
|
||||||
allow_register: true,
|
allow_register: true,
|
||||||
email_confirmation: false,
|
email_confirmation: false,
|
||||||
email_confirmation_redirection: `http://${
|
email_confirmation_redirection: `http://${strapi.config.currentEnvironment.server.host}:${strapi.config.currentEnvironment.server.port}/admin`,
|
||||||
strapi.config.currentEnvironment.server.host
|
|
||||||
}:${strapi.config.currentEnvironment.server.port}/admin`,
|
|
||||||
default_role: 'authenticated',
|
default_role: 'authenticated',
|
||||||
};
|
};
|
||||||
|
|
||||||
await pluginStore.set({ key: 'advanced', value });
|
await pluginStore.set({ key: 'advanced', value });
|
||||||
}
|
}
|
||||||
|
|
||||||
strapi.plugins['users-permissions'].services.userspermissions.initialize(cb);
|
return strapi.plugins[
|
||||||
|
'users-permissions'
|
||||||
|
].services.userspermissions.initialize();
|
||||||
};
|
};
|
||||||
|
|||||||
@ -462,18 +462,14 @@ module.exports = {
|
|||||||
return Promise.resolve();
|
return Promise.resolve();
|
||||||
},
|
},
|
||||||
|
|
||||||
async initialize(cb) {
|
async initialize() {
|
||||||
const roleCount = await strapi.query('role', 'users-permissions').count();
|
const roleCount = await strapi.query('role', 'users-permissions').count();
|
||||||
|
|
||||||
// It has already been initialized.
|
// It has already been initialized.
|
||||||
if (roleCount > 0) {
|
if (roleCount > 0) {
|
||||||
try {
|
|
||||||
await this.updatePermissions();
|
await this.updatePermissions();
|
||||||
await this.removeDuplicate();
|
await this.removeDuplicate();
|
||||||
return cb();
|
return;
|
||||||
} catch (err) {
|
|
||||||
return cb(err);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// Create two first default roles.
|
// Create two first default roles.
|
||||||
@ -490,7 +486,7 @@ module.exports = {
|
|||||||
}),
|
}),
|
||||||
]);
|
]);
|
||||||
|
|
||||||
this.updatePermissions().then(() => cb(), err => cb(err));
|
return this.updatePermissions();
|
||||||
},
|
},
|
||||||
|
|
||||||
async updateRole(roleID, body) {
|
async updateRole(roleID, body) {
|
||||||
|
|||||||
@ -366,60 +366,39 @@ class Strapi extends EventEmitter {
|
|||||||
}
|
}
|
||||||
|
|
||||||
async runBootstrapFunctions() {
|
async runBootstrapFunctions() {
|
||||||
const execBootstrap = fn => {
|
|
||||||
if (!fn) return Promise.resolve();
|
|
||||||
|
|
||||||
return new Promise((resolve, reject) => {
|
|
||||||
const timeoutMs = this.config.bootstrapTimeout || 3500;
|
const timeoutMs = this.config.bootstrapTimeout || 3500;
|
||||||
const timer = setTimeout(() => {
|
const warnOnTimeout = () =>
|
||||||
|
setTimeout(() => {
|
||||||
this.log.warn(
|
this.log.warn(
|
||||||
`The bootstrap function is taking unusually long to execute (${timeoutMs} miliseconds).`
|
`The bootstrap function is taking unusually long to execute (${timeoutMs} miliseconds).`
|
||||||
);
|
);
|
||||||
this.log.warn('Make sure you call it?');
|
this.log.warn('Make sure you call it?');
|
||||||
}, timeoutMs);
|
}, timeoutMs);
|
||||||
|
|
||||||
let ranBootstrapFn = false;
|
async function execBootstrap(fn) {
|
||||||
|
if (!fn) return;
|
||||||
|
|
||||||
|
const timer = warnOnTimeout();
|
||||||
try {
|
try {
|
||||||
fn(err => {
|
await fn();
|
||||||
if (ranBootstrapFn) {
|
} finally {
|
||||||
this.log.error(
|
|
||||||
'You called the callback in `strapi.config.boostrap` more than once!'
|
|
||||||
);
|
|
||||||
|
|
||||||
return reject();
|
|
||||||
}
|
|
||||||
|
|
||||||
ranBootstrapFn = true;
|
|
||||||
clearTimeout(timer);
|
clearTimeout(timer);
|
||||||
|
|
||||||
if (err instanceof Error) {
|
|
||||||
return reject(err);
|
|
||||||
}
|
}
|
||||||
return resolve(err);
|
}
|
||||||
|
|
||||||
|
const pluginBoostraps = Object.keys(this.plugins).map(plugin => {
|
||||||
|
return execBootstrap(
|
||||||
|
_.get(this.plugins[plugin], 'config.functions.bootstrap')
|
||||||
|
).catch(err => {
|
||||||
|
strapi.log.error(`Bootstrap function in plugin "${plugin}" failed`);
|
||||||
|
strapi.log.error(err);
|
||||||
|
strapi.stop();
|
||||||
});
|
});
|
||||||
} catch (e) {
|
|
||||||
if (ranBootstrapFn) {
|
|
||||||
this.log.error(
|
|
||||||
'The bootstrap function threw an error after its callback was called.'
|
|
||||||
);
|
|
||||||
|
|
||||||
return reject(e);
|
|
||||||
}
|
|
||||||
|
|
||||||
ranBootstrapFn = true;
|
|
||||||
clearTimeout(timer);
|
|
||||||
|
|
||||||
return resolve(e);
|
|
||||||
}
|
|
||||||
});
|
});
|
||||||
};
|
|
||||||
|
|
||||||
return Promise.all(
|
await Promise.all(pluginBoostraps);
|
||||||
Object.values(this.plugins).map(plugin =>
|
|
||||||
execBootstrap(_.get(plugin, 'config.functions.bootstrap'))
|
return execBootstrap(_.get(this.config, ['functions', 'bootstrap']));
|
||||||
)
|
|
||||||
).then(() => execBootstrap(this.config.functions.bootstrap));
|
|
||||||
}
|
}
|
||||||
|
|
||||||
async freeze() {
|
async freeze() {
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user