@akemona-org/strapi 3.7.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/LICENSE +22 -0
- package/README.md +163 -0
- package/bin/strapi.js +239 -0
- package/index.d.ts +13 -0
- package/lib/Strapi.js +498 -0
- package/lib/commands/admin-reset.js +51 -0
- package/lib/commands/build.js +47 -0
- package/lib/commands/configurationDump.js +50 -0
- package/lib/commands/configurationRestore.js +160 -0
- package/lib/commands/console.js +26 -0
- package/lib/commands/develop.js +155 -0
- package/lib/commands/generate-template.js +97 -0
- package/lib/commands/generate.js +66 -0
- package/lib/commands/install.js +48 -0
- package/lib/commands/new.js +11 -0
- package/lib/commands/start.js +8 -0
- package/lib/commands/uninstall.js +68 -0
- package/lib/commands/watchAdmin.js +35 -0
- package/lib/core/app-configuration/config-loader.js +56 -0
- package/lib/core/app-configuration/config-provider.js +28 -0
- package/lib/core/app-configuration/index.js +99 -0
- package/lib/core/bootstrap.js +166 -0
- package/lib/core/fs.js +52 -0
- package/lib/core/index.js +21 -0
- package/lib/core/load-admin.js +36 -0
- package/lib/core/load-apis.js +22 -0
- package/lib/core/load-components.js +43 -0
- package/lib/core/load-extensions.js +71 -0
- package/lib/core/load-functions.js +21 -0
- package/lib/core/load-hooks.js +117 -0
- package/lib/core/load-middlewares.js +130 -0
- package/lib/core/load-modules.js +61 -0
- package/lib/core/load-plugins.js +68 -0
- package/lib/core/load-policies.js +36 -0
- package/lib/core/walk.js +27 -0
- package/lib/core-api/controller.js +158 -0
- package/lib/core-api/index.js +33 -0
- package/lib/core-api/service/collection-type.js +122 -0
- package/lib/core-api/service/index.js +81 -0
- package/lib/core-api/service/single-type.js +68 -0
- package/lib/hooks/index.js +97 -0
- package/lib/index.js +3 -0
- package/lib/load/check-reserved-filename.js +18 -0
- package/lib/load/filepath-to-prop-path.js +22 -0
- package/lib/load/glob.js +15 -0
- package/lib/load/index.js +9 -0
- package/lib/load/load-config-files.js +22 -0
- package/lib/load/load-files.js +56 -0
- package/lib/load/package-path.js +9 -0
- package/lib/load/require-file-parse.js +15 -0
- package/lib/middlewares/boom/defaults.json +5 -0
- package/lib/middlewares/boom/index.js +147 -0
- package/lib/middlewares/cors/index.js +66 -0
- package/lib/middlewares/cron/defaults.json +5 -0
- package/lib/middlewares/cron/index.js +43 -0
- package/lib/middlewares/csp/defaults.json +5 -0
- package/lib/middlewares/csp/index.js +26 -0
- package/lib/middlewares/favicon/defaults.json +7 -0
- package/lib/middlewares/favicon/index.js +35 -0
- package/lib/middlewares/gzip/defaults.json +6 -0
- package/lib/middlewares/gzip/index.js +19 -0
- package/lib/middlewares/hsts/defaults.json +7 -0
- package/lib/middlewares/hsts/index.js +30 -0
- package/lib/middlewares/index.js +120 -0
- package/lib/middlewares/ip/defaults.json +7 -0
- package/lib/middlewares/ip/index.js +25 -0
- package/lib/middlewares/language/defaults.json +9 -0
- package/lib/middlewares/language/index.js +40 -0
- package/lib/middlewares/logger/defaults.json +8 -0
- package/lib/middlewares/logger/index.js +63 -0
- package/lib/middlewares/p3p/defaults.json +6 -0
- package/lib/middlewares/p3p/index.js +29 -0
- package/lib/middlewares/parser/defaults.json +10 -0
- package/lib/middlewares/parser/index.js +71 -0
- package/lib/middlewares/poweredBy/defaults.json +5 -0
- package/lib/middlewares/poweredBy/index.js +16 -0
- package/lib/middlewares/public/assets/images/group_people_1.png +0 -0
- package/lib/middlewares/public/assets/images/group_people_2.png +0 -0
- package/lib/middlewares/public/assets/images/group_people_3.png +0 -0
- package/lib/middlewares/public/assets/images/logo_login.png +0 -0
- package/lib/middlewares/public/defaults.json +8 -0
- package/lib/middlewares/public/index.html +66 -0
- package/lib/middlewares/public/index.js +98 -0
- package/lib/middlewares/public/serve-static.js +23 -0
- package/lib/middlewares/responseTime/defaults.json +5 -0
- package/lib/middlewares/responseTime/index.js +25 -0
- package/lib/middlewares/responses/defaults.json +5 -0
- package/lib/middlewares/responses/index.js +18 -0
- package/lib/middlewares/router/defaults.json +7 -0
- package/lib/middlewares/router/index.js +64 -0
- package/lib/middlewares/router/utils/composeEndpoint.js +25 -0
- package/lib/middlewares/router/utils/routerChecker.js +92 -0
- package/lib/middlewares/session/defaults.json +18 -0
- package/lib/middlewares/session/index.js +140 -0
- package/lib/middlewares/xframe/defaults.json +6 -0
- package/lib/middlewares/xframe/index.js +33 -0
- package/lib/middlewares/xss/defaults.json +6 -0
- package/lib/middlewares/xss/index.js +30 -0
- package/lib/services/core-store.js +144 -0
- package/lib/services/entity-service.js +260 -0
- package/lib/services/entity-validator/index.js +199 -0
- package/lib/services/entity-validator/validators.js +125 -0
- package/lib/services/event-hub.js +15 -0
- package/lib/services/metrics/index.js +103 -0
- package/lib/services/metrics/is-truthy.js +9 -0
- package/lib/services/metrics/middleware.js +33 -0
- package/lib/services/metrics/rate-limiter.js +27 -0
- package/lib/services/metrics/sender.js +76 -0
- package/lib/services/metrics/stringify-deep.js +22 -0
- package/lib/services/utils/upload-files.js +70 -0
- package/lib/services/webhook-runner.js +159 -0
- package/lib/services/webhook-store.js +97 -0
- package/lib/services/worker-queue.js +58 -0
- package/lib/utils/addSlash.js +10 -0
- package/lib/utils/ee.js +123 -0
- package/lib/utils/get-prefixed-dependencies.js +7 -0
- package/lib/utils/index.js +25 -0
- package/lib/utils/openBrowser.js +145 -0
- package/lib/utils/resources/key.pub +9 -0
- package/lib/utils/resources/openChrome.applescript +83 -0
- package/lib/utils/run-checks.js +37 -0
- package/lib/utils/success.js +31 -0
- package/lib/utils/update-notifier/index.js +96 -0
- package/lib/utils/url-from-segments.js +13 -0
- package/package.json +143 -0
|
Binary file
|
|
@@ -0,0 +1,66 @@
|
|
|
1
|
+
<!doctype html>
|
|
2
|
+
<html>
|
|
3
|
+
<head>
|
|
4
|
+
<meta charset="utf-8" />
|
|
5
|
+
<meta http-equiv="X-UA-Compatible" content="IE=edge,chrome=1" />
|
|
6
|
+
<title>Welcome to your Strapi app</title>
|
|
7
|
+
<meta name="viewport" content="width=device-width, initial-scale=1" />
|
|
8
|
+
<meta name="robots" content="noindex, nofollow">
|
|
9
|
+
<link href="https://cdnjs.cloudflare.com/ajax/libs/meyer-reset/2.0/reset.min.css" rel="stylesheet" />
|
|
10
|
+
<link href="https://cdnjs.cloudflare.com/ajax/libs/font-awesome/5.11.2/css/all.min.css" rel="stylesheet" />
|
|
11
|
+
<link href="https://fonts.googleapis.com/css?family=Lato:400,700&display=swap" rel="stylesheet" />
|
|
12
|
+
<style>
|
|
13
|
+
*{-webkit-box-sizing:border-box;text-decoration:none}body,html{margin:0;padding:0;font-size:62.5%;-webkit-font-smoothing:antialiased}body{font-size:1.3rem;font-family:Lato,Helvetica,Arial,Verdana,sans-serif;background:#fafafb;margin:0;padding:80px 0;color:#333740;line-height:1.8rem}strong{font-weight:700}.wrapper{width:684px;margin:auto}h1{text-align:center}h2{font-size:1.8rem;font-weight:700;margin-bottom:1px}.logo{height:40px;margin-bottom:74px}.informations{position:relative;overflow:hidden;display:flex;justify-content:space-between;width:100%;height:126px;margin-top:18px;padding:20px 30px;background:#fff;border-radius:2px;box-shadow:0 2px 4px 0 #e3e9f3}.informations:before{position:absolute;top:0;left:0;content:'';display:block;width:100%;height:2px;background:#007eff}.environment{display:inline-block;padding:0 10px;height:20px;margin-bottom:36px;background:#e6f0fb;border:1px solid #aed4fb;border-radius:2px;text-transform:uppercase;color:#007eff;font-size:1.2rem;font-weight:700;line-height:20px;letter-spacing:.05rem}.cta{display:inline-block;height:30px;padding:0 15px;margin-top:32px;border-radius:2px;color:#fff;font-weight:700;line-height:28px}.cta i{position:relative;display:inline-block;height:100%;vertical-align:middle;font-size:1rem;margin-right:20px}.cta i:before{position:absolute;top:8px}.cta-primary{background:#007eff}.cta-secondary{background:#6dbb1a}.text-align-right{text-align:right}.lets-started{position:relative;overflow:hidden;width:100%;height:144px;margin-top:18px;padding:20px 30px;background:#fff;border-radius:2px;box-shadow:0 2px 4px 0 #e3e9f3}.people-saying-hello{position:absolute;right:30px;bottom:-8px;width:113px;height:70px}.visible{opacity:1!important}.people-saying-hello img{position:absolute;max-width:100%;opacity:0;transition:opacity .2s ease-out}@media only screen and (max-width:768px){.wrapper{width:auto!important;margin:0 20px}.informations{flex-direction:column;height:auto}.environment{width:100%;text-align:center;margin-bottom:18px}.text-align-right{margin-top:18px;text-align:center}.cta{width:100%;text-align:center}.lets-started{height:auto}.people-saying-hello{display:none}}
|
|
14
|
+
</style>
|
|
15
|
+
</head>
|
|
16
|
+
<body lang="en">
|
|
17
|
+
<section class="wrapper">
|
|
18
|
+
<h1><img class="logo" src="<%= strapi.config.server.url %>/assets/images/logo_login.png" /></h1>
|
|
19
|
+
<% if (strapi.config.environment === 'development' && isInitialised) { %>
|
|
20
|
+
<div class="informations">
|
|
21
|
+
<div>
|
|
22
|
+
<span class="environment"><%= strapi.config.environment %></span>
|
|
23
|
+
<p>
|
|
24
|
+
The server is running successfully (<strong>v<%= strapi.config.info.version %>)</strong>
|
|
25
|
+
</p>
|
|
26
|
+
</div>
|
|
27
|
+
<div class="text-align-right">
|
|
28
|
+
<p><%= serverTime %></p>
|
|
29
|
+
<% if (strapi.config.serveAdminPanel) { %>
|
|
30
|
+
<a class="cta cta-primary" href="<%= strapi.config.admin.url %>" target="_blank" title="Click to open the administration" ><i class="fas fa-external-link-alt"></i>Open the administration</a>
|
|
31
|
+
<% } %>
|
|
32
|
+
</div>
|
|
33
|
+
</div>
|
|
34
|
+
<% } else if (strapi.config.environment === 'development' && !isInitialised) { %>
|
|
35
|
+
<div class="lets-started">
|
|
36
|
+
<h2>Let's get started!</h2>
|
|
37
|
+
<p>To discover the power provided by Strapi, you need to create an administrator.</p>
|
|
38
|
+
<a class="cta cta-secondary" href="<%= strapi.config.admin.url %>" target="_blank" title="Click to create the first administration" ><i class="fas fa-external-link-alt"></i>Create the first administrator</a>
|
|
39
|
+
<div class="people-saying-hello">
|
|
40
|
+
<img class="visible" src="<%= strapi.config.server.url %>/assets/images/group_people_1.png" alt="People saying hello" />
|
|
41
|
+
<img src="<%= strapi.config.server.url %>/assets/images/group_people_2.png" alt="People saying hello" />
|
|
42
|
+
<img src="<%= strapi.config.server.url %>/assets/images/group_people_3.png" alt="People saying hello" />
|
|
43
|
+
</div>
|
|
44
|
+
</div>
|
|
45
|
+
<% } else { %>
|
|
46
|
+
<div class="informations">
|
|
47
|
+
<div>
|
|
48
|
+
<span class="environment"><%= strapi.config.environment %></span>
|
|
49
|
+
<p>The server is running successfully.</p>
|
|
50
|
+
</div>
|
|
51
|
+
<div class="text-align-right">
|
|
52
|
+
<p><%= serverTime %></p>
|
|
53
|
+
</div>
|
|
54
|
+
</div>
|
|
55
|
+
<% } %>
|
|
56
|
+
</section>
|
|
57
|
+
|
|
58
|
+
<% if (strapi.config.environment === 'development' && !isInitialised) { %>
|
|
59
|
+
<script>
|
|
60
|
+
var images=document.querySelectorAll('.people-saying-hello img');var nextIndex=0;setInterval(function(){var currentIndex=0;images.forEach(function(image,index){if(image.className==='visible'){currentIndex=index}});nextIndex=currentIndex+1;if(nextIndex===images.length){nextIndex=0}
|
|
61
|
+
images.forEach(function(image){image.classList.remove('visible')})
|
|
62
|
+
images[nextIndex].classList.add('visible')},1500)
|
|
63
|
+
</script>
|
|
64
|
+
<% } %>
|
|
65
|
+
</body>
|
|
66
|
+
</html>
|
|
@@ -0,0 +1,98 @@
|
|
|
1
|
+
'use strict';
|
|
2
|
+
|
|
3
|
+
/**
|
|
4
|
+
* Module dependencies
|
|
5
|
+
*/
|
|
6
|
+
|
|
7
|
+
// Node.js core.
|
|
8
|
+
const fs = require('fs');
|
|
9
|
+
const path = require('path');
|
|
10
|
+
const stream = require('stream');
|
|
11
|
+
const _ = require('lodash');
|
|
12
|
+
const koaStatic = require('koa-static');
|
|
13
|
+
const utils = require('../../utils');
|
|
14
|
+
const serveStatic = require('./serve-static');
|
|
15
|
+
|
|
16
|
+
/**
|
|
17
|
+
* Public assets hook
|
|
18
|
+
*/
|
|
19
|
+
|
|
20
|
+
module.exports = strapi => {
|
|
21
|
+
return {
|
|
22
|
+
/**
|
|
23
|
+
* Initialize the hook
|
|
24
|
+
*/
|
|
25
|
+
|
|
26
|
+
async initialize() {
|
|
27
|
+
const { defaultIndex, maxAge, path: publicPath } = strapi.config.middleware.settings.public;
|
|
28
|
+
const staticDir = path.resolve(strapi.dir, publicPath || strapi.config.paths.static);
|
|
29
|
+
|
|
30
|
+
if (defaultIndex === true) {
|
|
31
|
+
const index = fs.readFileSync(path.join(__dirname, 'index.html'), 'utf8');
|
|
32
|
+
|
|
33
|
+
const serveIndexPage = async (ctx, next) => {
|
|
34
|
+
// defer rendering of strapi index page
|
|
35
|
+
await next();
|
|
36
|
+
if (ctx.body != null || ctx.status !== 404) return;
|
|
37
|
+
|
|
38
|
+
ctx.url = 'index.html';
|
|
39
|
+
const isInitialised = await utils.isInitialised(strapi);
|
|
40
|
+
const data = {
|
|
41
|
+
serverTime: new Date().toUTCString(),
|
|
42
|
+
isInitialised,
|
|
43
|
+
..._.pick(strapi, [
|
|
44
|
+
'config.info.version',
|
|
45
|
+
'config.info.name',
|
|
46
|
+
'config.admin.url',
|
|
47
|
+
'config.server.url',
|
|
48
|
+
'config.environment',
|
|
49
|
+
'config.serveAdminPanel',
|
|
50
|
+
]),
|
|
51
|
+
};
|
|
52
|
+
const content = _.template(index)(data);
|
|
53
|
+
const body = stream.Readable({
|
|
54
|
+
read() {
|
|
55
|
+
this.push(Buffer.from(content));
|
|
56
|
+
this.push(null);
|
|
57
|
+
},
|
|
58
|
+
});
|
|
59
|
+
// Serve static.
|
|
60
|
+
ctx.type = 'html';
|
|
61
|
+
ctx.body = body;
|
|
62
|
+
};
|
|
63
|
+
|
|
64
|
+
strapi.router.get('/', serveIndexPage);
|
|
65
|
+
strapi.router.get('/index.html', serveIndexPage);
|
|
66
|
+
strapi.router.get(
|
|
67
|
+
'/assets/images/(.*)',
|
|
68
|
+
serveStatic(path.resolve(__dirname, 'assets/images'), { maxage: maxAge, defer: true })
|
|
69
|
+
);
|
|
70
|
+
}
|
|
71
|
+
|
|
72
|
+
// serve files in public folder unless a sub router renders something else
|
|
73
|
+
strapi.router.get(
|
|
74
|
+
'/(.*)',
|
|
75
|
+
koaStatic(staticDir, {
|
|
76
|
+
maxage: maxAge,
|
|
77
|
+
defer: true,
|
|
78
|
+
})
|
|
79
|
+
);
|
|
80
|
+
|
|
81
|
+
if (!strapi.config.serveAdminPanel) return;
|
|
82
|
+
|
|
83
|
+
const buildDir = path.resolve(strapi.dir, 'build');
|
|
84
|
+
const serveAdmin = ctx => {
|
|
85
|
+
ctx.type = 'html';
|
|
86
|
+
ctx.body = fs.createReadStream(path.join(buildDir + '/index.html'));
|
|
87
|
+
};
|
|
88
|
+
|
|
89
|
+
strapi.router.get(
|
|
90
|
+
`${strapi.config.admin.path}/*`,
|
|
91
|
+
serveStatic(buildDir, { maxage: maxAge, defer: false, index: 'index.html' })
|
|
92
|
+
);
|
|
93
|
+
|
|
94
|
+
strapi.router.get(`${strapi.config.admin.path}`, serveAdmin);
|
|
95
|
+
strapi.router.get(`${strapi.config.admin.path}/*`, serveAdmin);
|
|
96
|
+
},
|
|
97
|
+
};
|
|
98
|
+
};
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
'use strict';
|
|
2
|
+
|
|
3
|
+
const path = require('path');
|
|
4
|
+
const koaStatic = require('koa-static');
|
|
5
|
+
|
|
6
|
+
// serveStatic is not supposed to be used to serve a folder that have sub-folders
|
|
7
|
+
const serveStatic = (filesDir, koaStaticOptions = {}) => {
|
|
8
|
+
const serve = koaStatic(filesDir, koaStaticOptions);
|
|
9
|
+
|
|
10
|
+
return async (ctx, next) => {
|
|
11
|
+
const prev = ctx.path;
|
|
12
|
+
const newPath = path.basename(ctx.path);
|
|
13
|
+
ctx.path = newPath;
|
|
14
|
+
await serve(ctx, async () => {
|
|
15
|
+
ctx.path = prev;
|
|
16
|
+
await next();
|
|
17
|
+
ctx.path = newPath;
|
|
18
|
+
});
|
|
19
|
+
ctx.path = prev;
|
|
20
|
+
};
|
|
21
|
+
};
|
|
22
|
+
|
|
23
|
+
module.exports = serveStatic;
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
'use strict';
|
|
2
|
+
|
|
3
|
+
/**
|
|
4
|
+
* X-Response-Time hook
|
|
5
|
+
*/
|
|
6
|
+
|
|
7
|
+
module.exports = strapi => {
|
|
8
|
+
return {
|
|
9
|
+
/**
|
|
10
|
+
* Initialize the hook
|
|
11
|
+
*/
|
|
12
|
+
|
|
13
|
+
initialize() {
|
|
14
|
+
strapi.app.use(async (ctx, next) => {
|
|
15
|
+
const start = Date.now();
|
|
16
|
+
|
|
17
|
+
await next();
|
|
18
|
+
|
|
19
|
+
const delta = Math.ceil(Date.now() - start);
|
|
20
|
+
|
|
21
|
+
ctx.set('X-Response-Time', delta + 'ms'); // eslint-disable-line prefer-template
|
|
22
|
+
});
|
|
23
|
+
},
|
|
24
|
+
};
|
|
25
|
+
};
|
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
'use strict';
|
|
2
|
+
|
|
3
|
+
const _ = require('lodash');
|
|
4
|
+
|
|
5
|
+
module.exports = strapi => {
|
|
6
|
+
return {
|
|
7
|
+
initialize() {
|
|
8
|
+
strapi.app.use(async (ctx, next) => {
|
|
9
|
+
await next();
|
|
10
|
+
|
|
11
|
+
const responseFn = strapi.config.get(['functions', 'responses', ctx.status]);
|
|
12
|
+
if (_.isFunction(responseFn)) {
|
|
13
|
+
await responseFn(ctx);
|
|
14
|
+
}
|
|
15
|
+
});
|
|
16
|
+
},
|
|
17
|
+
};
|
|
18
|
+
};
|
|
@@ -0,0 +1,64 @@
|
|
|
1
|
+
'use strict';
|
|
2
|
+
|
|
3
|
+
/**
|
|
4
|
+
* Module dependencies
|
|
5
|
+
*/
|
|
6
|
+
|
|
7
|
+
// Public node modules.
|
|
8
|
+
const _ = require('lodash');
|
|
9
|
+
const Router = require('koa-router');
|
|
10
|
+
const createEndpointComposer = require('./utils/composeEndpoint');
|
|
11
|
+
/**
|
|
12
|
+
* Router hook
|
|
13
|
+
*/
|
|
14
|
+
|
|
15
|
+
module.exports = strapi => {
|
|
16
|
+
const composeEndpoint = createEndpointComposer(strapi);
|
|
17
|
+
|
|
18
|
+
return {
|
|
19
|
+
/**
|
|
20
|
+
* Initialize the hook
|
|
21
|
+
*/
|
|
22
|
+
|
|
23
|
+
initialize() {
|
|
24
|
+
_.forEach(strapi.config.routes, value => {
|
|
25
|
+
composeEndpoint(value, { router: strapi.router });
|
|
26
|
+
});
|
|
27
|
+
|
|
28
|
+
strapi.router.prefix(strapi.config.get('middleware.settings.router.prefix', ''));
|
|
29
|
+
|
|
30
|
+
if (_.has(strapi.admin, 'config.routes')) {
|
|
31
|
+
const router = new Router({
|
|
32
|
+
prefix: '/admin',
|
|
33
|
+
});
|
|
34
|
+
|
|
35
|
+
_.get(strapi.admin, 'config.routes', []).forEach(route => {
|
|
36
|
+
composeEndpoint(route, { plugin: 'admin', router });
|
|
37
|
+
});
|
|
38
|
+
|
|
39
|
+
// Mount admin router on Strapi router
|
|
40
|
+
strapi.app.use(router.routes()).use(router.allowedMethods());
|
|
41
|
+
}
|
|
42
|
+
|
|
43
|
+
if (strapi.plugins) {
|
|
44
|
+
// Parse each plugin's routes.
|
|
45
|
+
_.forEach(strapi.plugins, (plugin, pluginName) => {
|
|
46
|
+
const router = new Router({
|
|
47
|
+
prefix: `/${pluginName}`,
|
|
48
|
+
});
|
|
49
|
+
|
|
50
|
+
(plugin.config.routes || []).forEach(route => {
|
|
51
|
+
const hasPrefix = _.has(route.config, 'prefix');
|
|
52
|
+
composeEndpoint(route, {
|
|
53
|
+
plugin: pluginName,
|
|
54
|
+
router: hasPrefix ? strapi.router : router,
|
|
55
|
+
});
|
|
56
|
+
});
|
|
57
|
+
|
|
58
|
+
// Mount plugin router
|
|
59
|
+
strapi.app.use(router.routes()).use(router.allowedMethods());
|
|
60
|
+
});
|
|
61
|
+
}
|
|
62
|
+
},
|
|
63
|
+
};
|
|
64
|
+
};
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
'use strict';
|
|
2
|
+
|
|
3
|
+
const _ = require('lodash');
|
|
4
|
+
const compose = require('koa-compose');
|
|
5
|
+
const createRouteChecker = require('./routerChecker');
|
|
6
|
+
|
|
7
|
+
module.exports = strapi => {
|
|
8
|
+
const routerChecker = createRouteChecker(strapi);
|
|
9
|
+
|
|
10
|
+
return (value, { plugin, router }) => {
|
|
11
|
+
if (_.isEmpty(_.get(value, 'method')) || _.isEmpty(_.get(value, 'path'))) {
|
|
12
|
+
return;
|
|
13
|
+
}
|
|
14
|
+
|
|
15
|
+
const { method, endpoint, policies, action } = routerChecker(value, plugin);
|
|
16
|
+
|
|
17
|
+
if (_.isUndefined(action) || !_.isFunction(action)) {
|
|
18
|
+
return strapi.log.warn(
|
|
19
|
+
`Ignored attempt to bind route '${value.method} ${value.path}' to unknown controller/action.`
|
|
20
|
+
);
|
|
21
|
+
}
|
|
22
|
+
|
|
23
|
+
router[method](endpoint, compose(policies), action);
|
|
24
|
+
};
|
|
25
|
+
};
|
|
@@ -0,0 +1,92 @@
|
|
|
1
|
+
'use strict';
|
|
2
|
+
|
|
3
|
+
/**
|
|
4
|
+
* Module dependencies
|
|
5
|
+
*/
|
|
6
|
+
|
|
7
|
+
// Public node modules.
|
|
8
|
+
const _ = require('lodash');
|
|
9
|
+
|
|
10
|
+
// Strapi utilities.
|
|
11
|
+
const { finder, policy: policyUtils } = require('@akemona-org/strapi-utils');
|
|
12
|
+
|
|
13
|
+
const getMethod = (route) => _.trim(_.toLower(route.method));
|
|
14
|
+
const getEndpoint = (route) => _.trim(route.path);
|
|
15
|
+
|
|
16
|
+
module.exports = (strapi) =>
|
|
17
|
+
function routerChecker(value, plugin) {
|
|
18
|
+
const method = getMethod(value);
|
|
19
|
+
const endpoint = getEndpoint(value);
|
|
20
|
+
|
|
21
|
+
// Define controller and action names.
|
|
22
|
+
const [controllerName, actionName] = _.trim(value.handler).split('.');
|
|
23
|
+
const controllerKey = _.toLower(controllerName);
|
|
24
|
+
|
|
25
|
+
let controller;
|
|
26
|
+
|
|
27
|
+
if (plugin) {
|
|
28
|
+
controller =
|
|
29
|
+
plugin === 'admin'
|
|
30
|
+
? strapi.admin.controllers[controllerKey]
|
|
31
|
+
: strapi.plugins[plugin].controllers[controllerKey];
|
|
32
|
+
} else {
|
|
33
|
+
controller = strapi.controllers[controllerKey];
|
|
34
|
+
}
|
|
35
|
+
|
|
36
|
+
if (!_.isFunction(controller[actionName])) {
|
|
37
|
+
strapi.stopWithError(
|
|
38
|
+
`Error creating endpoint ${method} ${endpoint}: handler not found "${controllerKey}.${actionName}"`
|
|
39
|
+
);
|
|
40
|
+
}
|
|
41
|
+
|
|
42
|
+
const action = controller[actionName].bind(controller);
|
|
43
|
+
|
|
44
|
+
// Retrieve the API's name where the controller is located
|
|
45
|
+
// to access to the right validators
|
|
46
|
+
const currentApiName = finder(strapi.plugins[plugin] || strapi.api || strapi.admin, controller);
|
|
47
|
+
|
|
48
|
+
// Add the `globalPolicy`.
|
|
49
|
+
const globalPolicy = policyUtils.globalPolicy({
|
|
50
|
+
controller: controllerKey,
|
|
51
|
+
action: actionName,
|
|
52
|
+
method,
|
|
53
|
+
endpoint,
|
|
54
|
+
plugin,
|
|
55
|
+
});
|
|
56
|
+
|
|
57
|
+
// Init policies array.
|
|
58
|
+
const policies = [globalPolicy];
|
|
59
|
+
|
|
60
|
+
let policyOption = _.get(value, 'config.policies');
|
|
61
|
+
|
|
62
|
+
// Allow string instead of array of policies.
|
|
63
|
+
if (_.isString(policyOption) && !_.isEmpty(policyOption)) {
|
|
64
|
+
policyOption = [policyOption];
|
|
65
|
+
}
|
|
66
|
+
|
|
67
|
+
if (_.isArray(policyOption)) {
|
|
68
|
+
policyOption.forEach((policyName) => {
|
|
69
|
+
try {
|
|
70
|
+
policies.push(policyUtils.get(policyName, plugin, currentApiName));
|
|
71
|
+
} catch (error) {
|
|
72
|
+
strapi.stopWithError(`Error creating endpoint ${method} ${endpoint}: ${error.message}`);
|
|
73
|
+
}
|
|
74
|
+
});
|
|
75
|
+
}
|
|
76
|
+
|
|
77
|
+
policies.push(async (ctx, next) => {
|
|
78
|
+
// Set body.
|
|
79
|
+
const values = await next();
|
|
80
|
+
|
|
81
|
+
if (_.isNil(ctx.body) && !_.isNil(values)) {
|
|
82
|
+
ctx.body = values;
|
|
83
|
+
}
|
|
84
|
+
});
|
|
85
|
+
|
|
86
|
+
return {
|
|
87
|
+
method,
|
|
88
|
+
endpoint,
|
|
89
|
+
policies,
|
|
90
|
+
action,
|
|
91
|
+
};
|
|
92
|
+
};
|
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
{
|
|
2
|
+
"session": {
|
|
3
|
+
"enabled": true,
|
|
4
|
+
"client": "cookie",
|
|
5
|
+
"key": "strapi.sid",
|
|
6
|
+
"prefix": "strapi:sess:",
|
|
7
|
+
"ttl": 864000000,
|
|
8
|
+
"rolling": false,
|
|
9
|
+
"secretKeys": ["mySecretKey1", "mySecretKey2"],
|
|
10
|
+
"cookie": {
|
|
11
|
+
"path": "/",
|
|
12
|
+
"httpOnly": true,
|
|
13
|
+
"maxAge": 864000000,
|
|
14
|
+
"rewrite": true,
|
|
15
|
+
"signed": false
|
|
16
|
+
}
|
|
17
|
+
}
|
|
18
|
+
}
|
|
@@ -0,0 +1,140 @@
|
|
|
1
|
+
'use strict';
|
|
2
|
+
|
|
3
|
+
const path = require('path');
|
|
4
|
+
const _ = require('lodash');
|
|
5
|
+
const session = require('koa-session');
|
|
6
|
+
|
|
7
|
+
/**
|
|
8
|
+
* Session middleware
|
|
9
|
+
*/
|
|
10
|
+
module.exports = strapi => {
|
|
11
|
+
const requireStore = store => {
|
|
12
|
+
return require(path.resolve(strapi.config.appPath, 'node_modules', 'koa-' + store));
|
|
13
|
+
};
|
|
14
|
+
|
|
15
|
+
const defineStore = session => {
|
|
16
|
+
if (_.isEmpty(_.get(session, 'client'))) {
|
|
17
|
+
return strapi.log.error(
|
|
18
|
+
'(middleware:session) please provide a valid client to store session'
|
|
19
|
+
);
|
|
20
|
+
} else if (_.isEmpty(_.get(session, 'connection'))) {
|
|
21
|
+
return strapi.log.error(
|
|
22
|
+
'(middleware:session) please provide connection for the session store'
|
|
23
|
+
);
|
|
24
|
+
} else if (!strapi.config.get(`database.connections.${session.connection}`)) {
|
|
25
|
+
return strapi.log.error(
|
|
26
|
+
'(middleware:session) please provide a valid connection for the session store'
|
|
27
|
+
);
|
|
28
|
+
}
|
|
29
|
+
|
|
30
|
+
session.settings = strapi.config.get(`database.connections.${session.connection}`);
|
|
31
|
+
|
|
32
|
+
// Define correct store name to avoid require to failed.
|
|
33
|
+
switch (session.client.toLowerCase()) {
|
|
34
|
+
case 'redis': {
|
|
35
|
+
const store = requireStore('redis');
|
|
36
|
+
|
|
37
|
+
session.settings.db = session.settings.database;
|
|
38
|
+
|
|
39
|
+
return store(session.settings);
|
|
40
|
+
}
|
|
41
|
+
case 'mysql': {
|
|
42
|
+
const Store = requireStore('mysql-session');
|
|
43
|
+
|
|
44
|
+
return new Store(session.settings);
|
|
45
|
+
}
|
|
46
|
+
case 'mongo': {
|
|
47
|
+
const Store = requireStore('generic-session-mongo');
|
|
48
|
+
|
|
49
|
+
session.settings.db = session.settings.database;
|
|
50
|
+
|
|
51
|
+
return new Store(session.settings);
|
|
52
|
+
}
|
|
53
|
+
case 'postgresql': {
|
|
54
|
+
const Store = requireStore('pg-session');
|
|
55
|
+
|
|
56
|
+
return new Store(session.settings, session.options);
|
|
57
|
+
}
|
|
58
|
+
case 'rethink': {
|
|
59
|
+
const Store = requireStore('generic-session-rethinkdb');
|
|
60
|
+
|
|
61
|
+
session.settings.dbName = session.settings.database;
|
|
62
|
+
session.settings.tableName = session.settings.table;
|
|
63
|
+
|
|
64
|
+
const sessionStore = new Store({
|
|
65
|
+
connection: session.settings,
|
|
66
|
+
});
|
|
67
|
+
|
|
68
|
+
// Create the DB, tables and indexes to store sessions.
|
|
69
|
+
sessionStore.setup();
|
|
70
|
+
|
|
71
|
+
return sessionStore;
|
|
72
|
+
}
|
|
73
|
+
case 'sqlite': {
|
|
74
|
+
const Store = requireStore('sqlite3-session');
|
|
75
|
+
|
|
76
|
+
return new Store(session.fileName, session.options);
|
|
77
|
+
}
|
|
78
|
+
case 'sequelize': {
|
|
79
|
+
const Store = requireStore('generic-session-sequelize');
|
|
80
|
+
|
|
81
|
+
// Sequelize needs to be instantiated.
|
|
82
|
+
if (!_.isObject(strapi.sequelize)) {
|
|
83
|
+
return null;
|
|
84
|
+
}
|
|
85
|
+
|
|
86
|
+
return new Store(strapi.sequelize, session.options);
|
|
87
|
+
}
|
|
88
|
+
default: {
|
|
89
|
+
return null;
|
|
90
|
+
}
|
|
91
|
+
}
|
|
92
|
+
};
|
|
93
|
+
|
|
94
|
+
return {
|
|
95
|
+
initialize() {
|
|
96
|
+
strapi.app.keys = strapi.config.get('middleware.settings.session.secretKeys');
|
|
97
|
+
|
|
98
|
+
if (
|
|
99
|
+
_.has(strapi.config.middleware.settings.session, 'client') &&
|
|
100
|
+
_.isString(strapi.config.middleware.settings.session.client) &&
|
|
101
|
+
strapi.config.middleware.settings.session.client !== 'cookie'
|
|
102
|
+
) {
|
|
103
|
+
const store = defineStore(strapi.config.middleware.settings.session);
|
|
104
|
+
|
|
105
|
+
if (!_.isEmpty(store)) {
|
|
106
|
+
// Options object contains the defined store, the custom middlewares configurations
|
|
107
|
+
// and also the function which are located to `./config/functions/session.js`
|
|
108
|
+
const options = _.assign(
|
|
109
|
+
{
|
|
110
|
+
store,
|
|
111
|
+
},
|
|
112
|
+
strapi.config.middleware.settings.session
|
|
113
|
+
);
|
|
114
|
+
|
|
115
|
+
strapi.app.use(session(options, strapi.app));
|
|
116
|
+
strapi.app.use((ctx, next) => {
|
|
117
|
+
ctx.state = ctx.state || {};
|
|
118
|
+
ctx.state.session = ctx.session || {};
|
|
119
|
+
|
|
120
|
+
return next();
|
|
121
|
+
});
|
|
122
|
+
}
|
|
123
|
+
} else if (
|
|
124
|
+
_.has(strapi.config.middleware.settings.session, 'client') &&
|
|
125
|
+
_.isString(strapi.config.middleware.settings.session.client) &&
|
|
126
|
+
strapi.config.middleware.settings.session.client === 'cookie'
|
|
127
|
+
) {
|
|
128
|
+
const options = _.assign(strapi.config.middleware.settings.session);
|
|
129
|
+
|
|
130
|
+
strapi.app.use(session(options, strapi.app));
|
|
131
|
+
strapi.app.use((ctx, next) => {
|
|
132
|
+
ctx.state = ctx.state || {};
|
|
133
|
+
ctx.state.session = ctx.session || {};
|
|
134
|
+
|
|
135
|
+
return next();
|
|
136
|
+
});
|
|
137
|
+
}
|
|
138
|
+
},
|
|
139
|
+
};
|
|
140
|
+
};
|
|
@@ -0,0 +1,33 @@
|
|
|
1
|
+
'use strict';
|
|
2
|
+
|
|
3
|
+
const convert = require('koa-convert');
|
|
4
|
+
const { xframe } = require('koa-lusca');
|
|
5
|
+
|
|
6
|
+
/**
|
|
7
|
+
* CRON hook
|
|
8
|
+
*/
|
|
9
|
+
|
|
10
|
+
module.exports = strapi => {
|
|
11
|
+
return {
|
|
12
|
+
/**
|
|
13
|
+
* Initialize the hook
|
|
14
|
+
*/
|
|
15
|
+
|
|
16
|
+
initialize() {
|
|
17
|
+
const defaults = require('./defaults.json');
|
|
18
|
+
|
|
19
|
+
strapi.app.use(async (ctx, next) => {
|
|
20
|
+
if (ctx.request.admin) {
|
|
21
|
+
return await convert(xframe(defaults.xframe))(ctx, next);
|
|
22
|
+
}
|
|
23
|
+
|
|
24
|
+
const { enabled, value } = strapi.config.get('middleware.settings.xframe', {});
|
|
25
|
+
if (enabled) {
|
|
26
|
+
return await convert(xframe(value))(ctx, next);
|
|
27
|
+
}
|
|
28
|
+
|
|
29
|
+
await next();
|
|
30
|
+
});
|
|
31
|
+
},
|
|
32
|
+
};
|
|
33
|
+
};
|