@paralect/hive 0.1.6 → 0.1.8

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/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@paralect/hive",
3
- "version": "0.1.6",
3
+ "version": "0.1.8",
4
4
  "description": "",
5
5
  "main": "index.js",
6
6
  "bin": {
@@ -1,3 +1,4 @@
1
+ import _ from 'lodash';
1
2
  import fs from "fs";
2
3
  import dotenv from "dotenv";
3
4
  import appConfig from "./app.js";
@@ -17,16 +18,21 @@ if (process.env.HIVE_SRC) {
17
18
  });
18
19
  }
19
20
 
20
- if (process.env.HIVE_SRC) {
21
- let pluginConfigPath = `${process.env.HIVE_SRC}/app-config/app.js`;
22
- // pluginConfig = (await import(pluginConfigPath)).default;
23
- if (fs.existsSync(pluginConfigPath)) {
24
- appConfig = { ...appConfig };
25
- }
26
- }
27
-
28
21
  const env = process.env.APP_ENV || "development";
29
- const config = {
22
+
23
+ let config = {
24
+ async init() {
25
+ if (process.env.HIVE_SRC) {
26
+ let pluginConfigPath = `${process.env.HIVE_SRC}/app-config/app.js`;
27
+
28
+ if (fs.existsSync(pluginConfigPath)) {
29
+ const { default: pluginConfig } = await (import(pluginConfigPath))
30
+ _.extend(config, pluginConfig);
31
+ }
32
+ }
33
+ },
34
+
35
+ _hive: {},
30
36
  env,
31
37
  port: process.env.PORT || 3001,
32
38
  domain:
@@ -52,4 +58,5 @@ const config = {
52
58
  }
53
59
  },
54
60
  };
61
+
55
62
  export default config;
@@ -23,34 +23,35 @@ import get from "resources/health/endpoints/get";
23
23
  import scheduler from "./scheduler";
24
24
 
25
25
  const main = async () => {
26
+ await config.init();
26
27
  await db.init();
27
28
 
28
29
  process.on("unhandledRejection", (reason, p) => {
29
30
  console.trace(reason.stack);
30
31
  logger.error(reason.stack);
31
32
  });
32
-
33
+
33
34
  const app = new Koa();
34
-
35
+
35
36
  app.use(cors({ credentials: true }));
36
37
  app.use(helmet());
37
-
38
+
38
39
  qs(app);
39
-
40
+
40
41
  app.use(bodyParser({ enableTypes: ["json", "form", "text"] }));
41
42
  app.use(mount("/health", get.handler));
42
43
  app.use(requestLogger());
43
-
44
+
44
45
  routes(app);
45
-
46
+
46
47
  const server = http.createServer(app.callback());
47
-
48
+
48
49
  server.listen(config.port, () => {
49
- console.log(`Api server listening on ${config.port}, in ${process.env.NODE_ENV} mode and ${process.env.APP_ENV} environment`);
50
+ console.log(`Api server listening on ${config.port}, in ${process.env.NODE_ENV} mode and ${process.env.APP_ENV} environment`);
50
51
  });
51
-
52
+
52
53
  scheduler();
53
-
54
+
54
55
  await socketIo(server);
55
56
  };
56
57
 
@@ -0,0 +1,38 @@
1
+ import _ from 'lodash';
2
+ import path from 'path';
3
+ import fs from 'fs';
4
+
5
+ const {
6
+ promises: { readdir },
7
+ } = fs;
8
+
9
+
10
+ const getFiles = async (source) => {
11
+ return (await readdir(source, { withFileTypes: true }))
12
+ .filter((file) => !file.isDirectory())
13
+ .map((file) => ({ fileName: file.name }));
14
+ };
15
+
16
+ export default async () => {
17
+ let middlewaresDirs = await getFiles(`${__dirname}/../middlewares`);
18
+
19
+ if (process.env.HIVE_SRC) {
20
+ let hiveMiddlewaresDirPath = `${process.env.HIVE_SRC}/middlewares`;
21
+
22
+ if (fs.existsSync(hiveMiddlewaresDirPath)) {
23
+ middlewaresDirs = _.uniqBy([...middlewaresDirs, ...((await getFiles(hiveMiddlewaresDirPath)).map(r => ({ fileName: r.fileName, isHive: true })))], r => r.fileName);
24
+ }
25
+ }
26
+
27
+ return Promise.all(middlewaresDirs
28
+ .map(({ fileName, isHive }) => ({
29
+ filePath: isHive ? path.resolve(`${process.env.HIVE_SRC}/middlewares/${fileName}`) : path.resolve(`${__dirname}/../middlewares/${fileName}`),
30
+ name: fileName.replace('.js', ''),
31
+ })).map(async ({ filePath, name }) => {
32
+ return {
33
+ name,
34
+ filePath,
35
+ fn: (await import(filePath)).default,
36
+ }
37
+ }));
38
+ };
@@ -4,7 +4,7 @@ export default z
4
4
  .object({
5
5
  _id: z.string(),
6
6
 
7
- createdOn: z.coerce.date(),
8
- updatedOn: z.coerce.date(),
7
+ createdOn: z.coerce.date().default(() => new Date()),
8
+ updatedOn: z.coerce.date().default(() => new Date()),
9
9
  })
10
10
  .strict();
@@ -1,13 +1,16 @@
1
1
  import _ from "lodash";
2
2
  import getResources from "helpers/getResources";
3
+ import getMiddlewares from "helpers/getMiddlewares";
3
4
  import getResourceEndpoints from "helpers/getResourceEndpoints";
4
5
  import mount from "koa-mount";
5
6
  import Router from "@koa/router";
6
7
  import validate from "middlewares/validate";
7
8
  import db from "db";
8
9
  import tryToAttachUser from "middlewares/global/tryToAttachUser";
9
- import attachCustomErrors from "./middlewares/attachCustomErrors.js";
10
- import routeErrorHandler from "./middlewares/routeErrorHandler.js";
10
+ import attachCustomErrors from "./middlewares/attachCustomErrors";
11
+ import routeErrorHandler from "./middlewares/routeErrorHandler";
12
+ import isAuthorized from "middlewares/isAuthorized";
13
+ import config from 'app-config';
11
14
 
12
15
  const requestLogService = db.createService("_request_logs");
13
16
 
@@ -59,8 +62,10 @@ const defineRoutes = async (app) => {
59
62
  app.use(attachCustomErrors);
60
63
  app.use(routeErrorHandler);
61
64
  app.use(tryToAttachUser);
62
-
63
- const resources = await getResources();
65
+
66
+
67
+
68
+ const [resources, allMiddlewares] = await Promise.all([getResources(), getMiddlewares()]);
64
69
 
65
70
  _.each(resources, async ({ name: resourceName }) => {
66
71
  const resourceRouter = new Router();
@@ -68,7 +73,7 @@ const defineRoutes = async (app) => {
68
73
  const endpoints = await Promise.all((await getResourceEndpoints(resourceName))
69
74
  .map(async ({ file: endpointFile, name }) => {
70
75
  let endpointDef = (await import(endpointFile));
71
-
76
+
72
77
  if (!endpointDef.endpoint) {
73
78
  console.log('missing endpoint for', name);
74
79
  }
@@ -92,15 +97,15 @@ const defineRoutes = async (app) => {
92
97
 
93
98
  endpoints.forEach(({ endpoint, requestSchema, middlewares = [], handler }) => {
94
99
  const additionalMiddlewares = [];
95
-
100
+
96
101
  if (requestSchema) {
97
102
  additionalMiddlewares.push(validate(requestSchema));
98
103
  }
99
-
104
+
100
105
  let targetRouter;
101
106
 
102
107
  let url = endpoint.absoluteUrl || endpoint.url;
103
-
108
+
104
109
  if (url.startsWith("$HOST/")) {
105
110
  url = url.replace("$HOST", "");
106
111
  targetRouter = globalRouter;
@@ -110,6 +115,30 @@ const defineRoutes = async (app) => {
110
115
  targetRouter = resourceRouter;
111
116
  }
112
117
 
118
+ middlewares = middlewares.map(middleware => {
119
+ if (_.isString(middleware)) {
120
+ if (!allMiddlewares.find(m => m.name === middleware)) {
121
+ throw new Error(`Middleware ${middleware} not found`);
122
+ }
123
+
124
+ middleware = allMiddlewares.find(m => m.name === middleware).fn;
125
+ } else if (_.isArray(middleware)) {
126
+ const [middlewareName, ...middlewareParams] = middleware;
127
+
128
+ if (!allMiddlewares.find(m => m.name === middlewareName)) {
129
+ throw new Error(`Middleware ${middlewareName} not found`);
130
+ }
131
+
132
+ middleware = allMiddlewares.find(m => m.name === middlewareName).fn(...middlewareParams);
133
+ }
134
+
135
+ return middleware;
136
+ });
137
+
138
+ if (config._hive.isRequireAuthAllEndpoints && !endpoint.isNoAuthRequired) {
139
+ app.use(isAuthorized);
140
+ }
141
+
113
142
  targetRouter[endpoint.method?.toLowerCase() || "get"](
114
143
  url,
115
144
  async (ctx, next) => {