miolo 3.0.0-beta.21 → 3.0.0-beta.210
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/bin/build/build.mjs +53 -0
- package/bin/build/build_bin.mjs +17 -0
- package/bin/build/cli/client.mjs +52 -0
- package/bin/build/cli/css.mjs +22 -0
- package/bin/build/cli/index.mjs +40 -0
- package/bin/build/cli/ssr.mjs +21 -0
- package/bin/build/server/aliases.mjs +112 -0
- package/bin/build/server/babel.config.js +24 -0
- package/bin/build/server/banner.mjs +20 -0
- package/bin/build/server/bundle.mjs +111 -0
- package/bin/build/server/fix.mjs +15 -0
- package/bin/build/server/index.mjs +69 -0
- package/bin/build/server/options.mjs +83 -0
- package/bin/create/auth.mjs +23 -0
- package/bin/create/copy.mjs +175 -0
- package/bin/create/docker.mjs +25 -0
- package/bin/create/index.mjs +137 -0
- package/bin/create/pkgjson.mjs +72 -0
- package/bin/create/prepare-template.mjs +158 -0
- package/bin/create/validation.mjs +27 -0
- package/bin/dev/dev.mjs +32 -23
- package/bin/dev/dev_start.mjs +6 -5
- package/bin/index.mjs +94 -52
- package/bin/prod-bin/create-bin.mjs +42 -27
- package/bin/prod-bin/run.mjs +13 -9
- package/bin/{prod-run → run}/pid.mjs +4 -4
- package/bin/run/restart.mjs +13 -0
- package/bin/run/start.mjs +18 -0
- package/bin/run/stop.mjs +20 -0
- package/bin/util.mjs +35 -11
- package/package.json +59 -39
- package/src/config/.env +34 -12
- package/src/config/defaults.mjs +253 -185
- package/src/config/env.mjs +40 -22
- package/src/config/index.mjs +19 -24
- package/src/config/util.mjs +25 -10
- package/src/db-conn.mjs +34 -0
- package/src/engines/cron/emails.mjs +10 -5
- package/src/engines/cron/index.mjs +45 -51
- package/src/engines/cron/init.mjs +16 -17
- package/src/engines/cron/ipsum.mjs +65 -60
- package/src/engines/cron/syscheck.mjs +30 -30
- package/src/engines/emailer/index.mjs +1 -2
- package/src/engines/emailer/queue.mjs +14 -20
- package/src/engines/emailer/transporter.mjs +86 -74
- package/src/engines/geoip/index.mjs +23 -28
- package/src/engines/http/index.mjs +26 -15
- package/src/engines/logger/buildErrorEmailBody.mjs +72 -0
- package/src/engines/logger/index.mjs +114 -122
- package/src/engines/logger/injectStackTrace.mjs +59 -0
- package/src/engines/logger/logger_mail.mjs +47 -61
- package/src/engines/logger/reopenTransportOnHupSignal.mjs +12 -13
- package/src/engines/parser/Parser.mjs +77 -60
- package/src/engines/parser/index.mjs +1 -1
- package/src/engines/schema/diffObjs.mjs +41 -0
- package/src/engines/schema/index.mjs +4 -0
- package/src/engines/schema/input.mjs +54 -0
- package/src/engines/schema/output.mjs +66 -0
- package/src/engines/socket/index.mjs +44 -46
- package/src/index.mjs +15 -10
- package/src/middleware/auth/basic.mjs +41 -40
- package/src/middleware/auth/custom.mjs +10 -13
- package/src/middleware/auth/guest.mjs +27 -27
- package/src/middleware/auth/passport/index.mjs +374 -0
- package/src/middleware/auth/passport/session/index.mjs +43 -0
- package/src/middleware/auth/{credentials → passport}/session/store.mjs +35 -15
- package/src/middleware/auth/passport/session/store_koa_redis.mjs +3 -0
- package/src/middleware/context/cache/index.mjs +78 -33
- package/src/middleware/context/cache/options.mjs +19 -21
- package/src/middleware/context/db.mjs +45 -20
- package/src/middleware/context/index.mjs +12 -12
- package/src/middleware/extra.mjs +4 -5
- package/src/middleware/http/body.mjs +25 -25
- package/src/middleware/http/catcher.mjs +81 -8
- package/src/middleware/http/custom_blacklist.mjs +19 -16
- package/src/middleware/http/headers.mjs +37 -34
- package/src/middleware/http/ratelimit.mjs +16 -23
- package/src/middleware/http/request.mjs +60 -65
- package/src/middleware/routes/catch_js_error.mjs +30 -23
- package/src/middleware/routes/robots.mjs +4 -7
- package/src/middleware/routes/router/crud/attachCrudRoutes.mjs +108 -90
- package/src/middleware/routes/router/crud/getCrudConfig.mjs +31 -55
- package/src/middleware/routes/router/defaults.mjs +6 -19
- package/src/middleware/routes/router/index.mjs +17 -21
- package/src/middleware/routes/router/queries/attachQueriesRoutes.mjs +227 -50
- package/src/middleware/routes/router/queries/getQueriesConfig.mjs +45 -55
- package/src/middleware/routes/router/utils.mjs +41 -26
- package/src/middleware/ssr/context.mjs +5 -7
- package/src/middleware/ssr/html.mjs +66 -43
- package/src/middleware/ssr/loader.mjs +11 -14
- package/src/middleware/ssr/ssr_render.mjs +39 -22
- package/src/middleware/static/index.mjs +33 -14
- package/src/middleware/vite/devserver.mjs +38 -22
- package/src/middleware/vite/watcher.mjs +12 -14
- package/src/server-cron.mjs +13 -8
- package/src/server-dev.mjs +13 -16
- package/src/server.mjs +49 -51
- package/template/.agent/skills/miolo-app-arch/SKILL.md +218 -0
- package/template/.agent/skills/miolo-auth/SKILL.md +450 -0
- package/template/.agent/skills/miolo-cli-router/SKILL.md +394 -0
- package/template/.agent/skills/miolo-database/SKILL.md +358 -0
- package/template/.agent/skills/miolo-react-patterns/SKILL.md +426 -0
- package/template/.agent/skills/miolo-routing/SKILL.md +326 -0
- package/template/.agent/skills/miolo-schemas/SKILL.md +329 -0
- package/template/.agent/skills/miolo-session-context/SKILL.md +397 -0
- package/template/.agent/skills/miolo-ssr/SKILL.md +433 -0
- package/template/.editorconfig +18 -0
- package/template/.env +120 -0
- package/template/biome.json +63 -0
- package/template/components.json +21 -0
- package/template/db/init.sh +89 -0
- package/template/db/sql/00_drop.sql +2 -0
- package/template/db/sql/01_users.sql +31 -0
- package/template/db/sql/02_todos.sql +20 -0
- package/template/docker/Dockerfile +13 -0
- package/template/docker/docker-compose.yaml +79 -0
- package/template/gitignore +42 -0
- package/template/jsconfig.json +18 -0
- package/template/package.json +88 -0
- package/template/postcss.config.js +9 -0
- package/template/src/cli/App.jsx +25 -0
- package/template/src/cli/components/JsonTreeViewer.jsx +128 -0
- package/template/src/cli/components/shadcn-io/spinner/index.jsx +232 -0
- package/template/src/cli/components/stepper.jsx +408 -0
- package/template/src/cli/components/ui/avatar.jsx +36 -0
- package/template/src/cli/components/ui/badge.jsx +31 -0
- package/template/src/cli/components/ui/breadcrumb.jsx +97 -0
- package/template/src/cli/components/ui/card.jsx +73 -0
- package/template/src/cli/components/ui/collapsible.jsx +16 -0
- package/template/src/cli/components/ui/dropdown-menu.jsx +179 -0
- package/template/src/cli/components/ui/field.jsx +217 -0
- package/template/src/cli/components/ui/input.jsx +19 -0
- package/template/src/cli/components/ui/label.jsx +17 -0
- package/template/src/cli/components/ui/pagination.jsx +99 -0
- package/template/src/cli/components/ui/patched/alert.jsx +56 -0
- package/template/src/cli/components/ui/patched/button.jsx +45 -0
- package/template/src/cli/components/ui/patched/dialog.jsx +114 -0
- package/template/src/cli/components/ui/patched/sidebar.jsx +660 -0
- package/template/src/cli/components/ui/select.jsx +141 -0
- package/template/src/cli/components/ui/separator.jsx +21 -0
- package/template/src/cli/components/ui/sheet.jsx +115 -0
- package/template/src/cli/components/ui/skeleton.jsx +13 -0
- package/template/src/cli/components/ui/sonner.jsx +22 -0
- package/template/src/cli/components/ui/switch.jsx +25 -0
- package/template/src/cli/components/ui/table.jsx +88 -0
- package/template/src/cli/components/ui/textarea.jsx +16 -0
- package/template/src/cli/components/ui/tooltip.jsx +45 -0
- package/template/src/cli/config/store_keys.mjs +2 -0
- package/template/src/cli/context/data/DataContext.jsx +5 -0
- package/template/src/cli/context/data/DataProvider.jsx +44 -0
- package/template/src/cli/context/data/useBreads.mjs +15 -0
- package/template/src/cli/context/data/useDataContext.mjs +4 -0
- package/template/src/cli/context/session/SessionContext.mjs +4 -0
- package/template/src/cli/context/session/SessionProvider.jsx +31 -0
- package/template/src/cli/context/session/makePermissioner.mjs +34 -0
- package/template/src/cli/context/session/useSessionContext.mjs +6 -0
- package/template/src/cli/context/theme/ThemeContext.mjs +4 -0
- package/template/src/cli/context/theme/ThemeProvider.jsx +49 -0
- package/template/src/cli/context/theme/useThemeContext.mjs +6 -0
- package/template/src/cli/context/ui/UIContext.jsx +5 -0
- package/template/src/cli/context/ui/UIProvider.jsx +16 -0
- package/template/src/cli/context/ui/useUIContext.mjs +4 -0
- package/template/src/cli/context/util.mjs +17 -0
- package/template/src/cli/entry-cli.jsx +33 -0
- package/template/src/cli/hooks/useIsMobile.mjs +19 -0
- package/template/src/cli/hooks/useStoragedState.mjs +63 -0
- package/template/src/cli/index.html +29 -0
- package/template/src/cli/layout/app-sidebar.jsx +25 -0
- package/template/src/cli/layout/main-layout.jsx +63 -0
- package/template/src/cli/layout/nav-last-todos.jsx +72 -0
- package/template/src/cli/layout/nav-main.jsx +39 -0
- package/template/src/cli/layout/nav-user.jsx +105 -0
- package/template/src/cli/layout/prop-switcher.jsx +93 -0
- package/template/src/cli/lib/utils.mjs +10 -0
- package/template/src/cli/pages/Index.jsx +13 -0
- package/template/src/cli/pages/IndexOffline.jsx +13 -0
- package/template/src/cli/pages/IndexOnline.jsx +18 -0
- package/template/src/cli/pages/dash/Dashboard.jsx +29 -0
- package/template/src/cli/pages/offline/Login.jsx +43 -0
- package/template/src/cli/pages/offline/LoginForm.jsx +115 -0
- package/template/src/cli/pages/security/Security.jsx +39 -0
- package/template/src/cli/pages/security/SecurityForm.jsx +106 -0
- package/template/src/cli/pages/todos/TodoActions.jsx +99 -0
- package/template/src/cli/pages/todos/TodoAdd.jsx +43 -0
- package/template/src/cli/pages/todos/TodoList.jsx +60 -0
- package/template/src/cli/pages/todos/Todos.jsx +23 -0
- package/template/src/cli/pages/todos/context/TodosContext.jsx +5 -0
- package/template/src/cli/pages/todos/context/TodosProvider.jsx +191 -0
- package/template/src/cli/pages/todos/context/useTodosContext.mjs +4 -0
- package/template/src/ns/models/Todo.mjs +29 -0
- package/template/src/ns/models/TodoList.mjs +8 -0
- package/template/src/ns/models/User.mjs +40 -0
- package/template/src/server/bot/check_today.mjs +10 -0
- package/template/src/server/io/cache/base.mjs +21 -0
- package/template/src/server/io/db/filter.mjs +92 -0
- package/template/src/server/io/db/todos/delete.mjs +29 -0
- package/template/src/server/io/db/todos/find.mjs +13 -0
- package/template/src/server/io/db/todos/read.mjs +83 -0
- package/template/src/server/io/db/todos/toggle.mjs +37 -0
- package/template/src/server/io/db/todos/upsave.mjs +32 -0
- package/template/src/server/io/db/triggers/user.mjs +13 -0
- package/template/src/server/io/db/users/auth.mjs +132 -0
- package/template/src/server/io/db/users/pwd.mjs +38 -0
- package/template/src/server/io/db/users/save.mjs +17 -0
- package/template/src/server/miolo/auth/basic.mjs +15 -0
- package/template/src/server/miolo/auth/guest.mjs +3 -0
- package/template/src/server/miolo/auth/passport.mjs +73 -0
- package/template/src/server/miolo/cache.mjs +11 -0
- package/template/src/server/miolo/cron/foo.mjs +7 -0
- package/template/src/server/miolo/cron/index.mjs +28 -0
- package/template/src/server/miolo/cron/invalidate.mjs +21 -0
- package/template/src/server/miolo/db.mjs +36 -0
- package/template/src/server/miolo/http.mjs +14 -0
- package/template/src/server/miolo/index.mjs +43 -0
- package/template/src/server/miolo/routes/crud.mjs +16 -0
- package/template/src/server/miolo/routes/index.mjs +8 -0
- package/template/src/server/miolo/ssr/entry-server.jsx +13 -0
- package/template/src/server/miolo/ssr/loader.mjs +18 -0
- package/template/src/server/routes/index.mjs +66 -0
- package/template/src/server/routes/todos/mod.mjs +52 -0
- package/template/src/server/routes/todos/read.mjs +45 -0
- package/template/src/server/routes/todos/special.mjs +47 -0
- package/template/src/server/routes/users/user.mjs +54 -0
- package/template/src/server/server.mjs +10 -0
- package/template/src/server/utils/crypt.mjs +38 -0
- package/template/src/server/utils/io.mjs +15 -0
- package/template/src/server/utils/pwdfor.mjs +25 -0
- package/template/src/server/utils/schema.mjs +22 -0
- package/template/src/static/img/default/profile.png +0 -0
- package/template/src/static/img/favicon.ico +0 -0
- package/template/src/static/img/miolo_logo.png +0 -0
- package/template/src/static/img/miolo_name.png +0 -0
- package/template/src/static/public/manifest.json +21 -0
- package/template/src/static/public/sw.js +79 -0
- package/template/src/static/style/globals.css +156 -0
- package/template/src/static/style/json-tree.css +54 -0
- package/template/src/static/style/skeleton.css +49 -0
- package/bin/prod-build/build-client.mjs +0 -67
- package/bin/prod-build/build-server.mjs +0 -58
- package/bin/prod-run/restart.mjs +0 -9
- package/bin/prod-run/start.mjs +0 -15
- package/bin/prod-run/stop.mjs +0 -20
- package/src/engines/logger/verify.mjs +0 -22
- package/src/middleware/auth/credentials/index.mjs +0 -151
- package/src/middleware/auth/credentials/session/index.mjs +0 -24
- package/src/middleware/auth/credentials/session/store_koa_redis.mjs +0 -3
|
@@ -1,12 +1,11 @@
|
|
|
1
|
-
import
|
|
2
|
-
import
|
|
3
|
-
import
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
const
|
|
8
|
-
const
|
|
9
|
-
const _IPSUM_REMOTE_FILE = 'https://raw.githubusercontent.com/stamparm/ipsum/master/ipsum.txt'
|
|
1
|
+
import fs from "node:fs"
|
|
2
|
+
import https from "node:https"
|
|
3
|
+
import path from "node:path"
|
|
4
|
+
import { cyan, green, yellow } from "tinguir"
|
|
5
|
+
|
|
6
|
+
const _IPSUM_DEF_FOLDER = "/var/ipsum"
|
|
7
|
+
const _IPSUM_FILE_NAME = "ipsum.txt"
|
|
8
|
+
const _IPSUM_REMOTE_FILE = "https://raw.githubusercontent.com/stamparm/ipsum/master/ipsum.txt"
|
|
10
9
|
const _IPSUM_NLISTS = 1
|
|
11
10
|
|
|
12
11
|
/*function ipsum_download_file(callback, remote_file = _IPSUM_REMOTE_FILE) {
|
|
@@ -17,118 +16,124 @@ const _IPSUM_NLISTS = 1
|
|
|
17
16
|
})
|
|
18
17
|
}*/
|
|
19
18
|
|
|
20
|
-
|
|
21
19
|
export function ipsum_download_file(callback, remote_file = _IPSUM_REMOTE_FILE, logger) {
|
|
22
20
|
const lerr = logger ? logger.error : console.error
|
|
23
21
|
|
|
24
|
-
https
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
22
|
+
https
|
|
23
|
+
.get(remote_file, (res) => {
|
|
24
|
+
const data = []
|
|
25
|
+
res
|
|
26
|
+
.on("data", (chunk) => {
|
|
27
|
+
data.push(chunk)
|
|
28
|
+
})
|
|
29
|
+
.on("end", () => {
|
|
30
|
+
const content = Buffer.concat(data).toString()
|
|
31
|
+
callback(content)
|
|
32
|
+
})
|
|
33
|
+
})
|
|
34
|
+
.on("error", (err) => {
|
|
35
|
+
lerr(`[cron][${cyan("IPsum")}] Error downloading remote file (${err.toString()})`)
|
|
36
|
+
callback("")
|
|
31
37
|
})
|
|
32
|
-
}).on('error', (err) => {
|
|
33
|
-
lerr(`[cron][${cyan('IPsum')}] Error downloading remote file (${err.toString()})`)
|
|
34
|
-
callback('')
|
|
35
|
-
})
|
|
36
|
-
|
|
37
38
|
}
|
|
38
39
|
|
|
39
40
|
function _ipsum_ips_from_content(content, logger) {
|
|
40
41
|
const lerr = logger ? logger.error : console.error
|
|
41
42
|
|
|
42
|
-
if (!
|
|
43
|
+
if (!content) {
|
|
43
44
|
return []
|
|
44
45
|
}
|
|
45
46
|
|
|
46
47
|
try {
|
|
47
|
-
|
|
48
|
+
const ips = []
|
|
48
49
|
content
|
|
49
|
-
.split(
|
|
50
|
-
.filter(line => line.indexOf(
|
|
51
|
-
.
|
|
52
|
-
const [ip, nlists] = line.split(
|
|
53
|
-
if (parseInt(nlists) >= _IPSUM_NLISTS) {
|
|
50
|
+
.split("\n")
|
|
51
|
+
.filter((line) => line.indexOf("#") < 0)
|
|
52
|
+
.forEach((line) => {
|
|
53
|
+
const [ip, nlists] = line.split("\t")
|
|
54
|
+
if (parseInt(nlists, 10) >= _IPSUM_NLISTS) {
|
|
54
55
|
ips.push(ip)
|
|
55
56
|
}
|
|
56
57
|
})
|
|
57
58
|
return ips
|
|
58
|
-
} catch(
|
|
59
|
-
lerr(`[cron][${cyan(
|
|
59
|
+
} catch (_) {
|
|
60
|
+
lerr(`[cron][${cyan("IPsum")}] Error getting IPs from content`)
|
|
60
61
|
return []
|
|
61
62
|
}
|
|
62
63
|
}
|
|
63
64
|
|
|
64
|
-
function _ipsum_ips_from_file(folder= _IPSUM_DEF_FOLDER, logger) {
|
|
65
|
+
function _ipsum_ips_from_file(folder = _IPSUM_DEF_FOLDER, logger) {
|
|
65
66
|
const lerr = logger ? logger.error : console.error
|
|
66
67
|
|
|
67
|
-
if (!
|
|
68
|
+
if (!fs.existsSync(folder)) {
|
|
68
69
|
if (logger) {
|
|
69
|
-
lerr(`[cron][${cyan(
|
|
70
|
+
lerr(`[cron][${cyan("IPsum")}] Folder ${folder} does not exist`)
|
|
70
71
|
}
|
|
71
72
|
return []
|
|
72
73
|
}
|
|
73
74
|
|
|
74
75
|
const local_path = path.join(folder, _IPSUM_FILE_NAME)
|
|
75
76
|
|
|
76
|
-
if (!
|
|
77
|
+
if (!fs.existsSync(local_path)) {
|
|
77
78
|
if (logger) {
|
|
78
|
-
lerr(`[cron][${cyan(
|
|
79
|
+
lerr(`[cron][${cyan("IPsum")}] File ${local_path} does not exist`)
|
|
79
80
|
}
|
|
80
81
|
return []
|
|
81
82
|
}
|
|
82
83
|
|
|
83
|
-
const content = fs.readFileSync(local_path, {encoding:
|
|
84
|
+
const content = fs.readFileSync(local_path, { encoding: "utf8" })
|
|
84
85
|
return _ipsum_ips_from_content(content, logger)
|
|
85
86
|
}
|
|
86
87
|
|
|
87
|
-
|
|
88
|
-
function ipsum_update(folder= _IPSUM_DEF_FOLDER, callback, logger) {
|
|
88
|
+
function ipsum_update(folder = _IPSUM_DEF_FOLDER, callback, logger) {
|
|
89
89
|
const lerr = logger ? logger.error : console.error
|
|
90
|
-
const
|
|
90
|
+
const linf = logger ? logger.info : console.log
|
|
91
91
|
|
|
92
|
-
if (!
|
|
93
|
-
lerr(`[cron][${cyan(
|
|
92
|
+
if (!fs.existsSync(folder)) {
|
|
93
|
+
lerr(`[cron][${cyan("IPsum")}] Folder ${folder} does not exist`)
|
|
94
94
|
return
|
|
95
95
|
}
|
|
96
96
|
|
|
97
97
|
try {
|
|
98
|
-
|
|
98
|
+
linf(`[cron][${cyan("IPsum")}] Updating file...`)
|
|
99
99
|
|
|
100
100
|
ipsum_download_file((content) => {
|
|
101
|
-
|
|
102
101
|
const local_path = path.join(folder, _IPSUM_FILE_NAME)
|
|
103
|
-
fs.writeFileSync(local_path, content, {encoding:
|
|
102
|
+
fs.writeFileSync(local_path, content, { encoding: "utf8", flag: "w" })
|
|
104
103
|
|
|
105
|
-
const ntot = content.split(
|
|
104
|
+
const ntot = content.split("\n").length
|
|
106
105
|
const ips = _ipsum_ips_from_content(content, logger)
|
|
107
106
|
const nfilt = ips.length
|
|
108
|
-
|
|
109
|
-
|
|
107
|
+
linf(
|
|
108
|
+
`[cron][${cyan("IPsum")}] File downloaded. ${ntot} ips on the list (${nfilt} appearing in ${_IPSUM_NLISTS} or more lists)`
|
|
109
|
+
)
|
|
110
|
+
|
|
110
111
|
if (callback) {
|
|
111
112
|
callback(ips)
|
|
112
113
|
}
|
|
113
114
|
})
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
lerr(`[cron][${cyan('IPsum')}] Error ${error} updating the file`)
|
|
115
|
+
} catch (error) {
|
|
116
|
+
lerr(`[cron][${cyan("IPsum")}] Error ${error} updating the file`)
|
|
117
117
|
}
|
|
118
118
|
}
|
|
119
119
|
|
|
120
|
-
|
|
121
120
|
export function ipsum_config() {
|
|
122
121
|
return {
|
|
123
|
-
name:
|
|
124
|
-
cronTime:
|
|
122
|
+
name: "IPsum",
|
|
123
|
+
cronTime: "0 0 * * *",
|
|
125
124
|
onTick: async (miolo, _onCompleted) => {
|
|
126
125
|
const folder = miolo.config.http.ratelimit.ipsum_folder || _IPSUM_DEF_FOLDER
|
|
127
|
-
ipsum_update(
|
|
128
|
-
|
|
129
|
-
|
|
126
|
+
ipsum_update(
|
|
127
|
+
folder,
|
|
128
|
+
(ips) => {
|
|
129
|
+
miolo.logger.debug(
|
|
130
|
+
`[cron][${cyan("IPsum")}] File downloaded. ${green(ips.length)} ips will be ${yellow("blacklisted")}!`
|
|
131
|
+
)
|
|
132
|
+
},
|
|
133
|
+
miolo.logger
|
|
134
|
+
)
|
|
130
135
|
},
|
|
131
|
-
start: true
|
|
136
|
+
start: true
|
|
132
137
|
}
|
|
133
138
|
}
|
|
134
139
|
|
|
@@ -141,10 +146,10 @@ export function ipsum_read_ips(folder = _IPSUM_DEF_FOLDER, callback, logger) {
|
|
|
141
146
|
if (callback) {
|
|
142
147
|
callback(ips)
|
|
143
148
|
}
|
|
144
|
-
ldbg(`[cron][${cyan(
|
|
149
|
+
ldbg(`[cron][${cyan("IPsum")}] File contains ${ips.length} ips`)
|
|
145
150
|
return ips
|
|
146
151
|
} else {
|
|
147
|
-
lwarn(`[cron][${cyan(
|
|
152
|
+
lwarn(`[cron][${cyan("IPsum")}] File is empty. Launching update...`)
|
|
148
153
|
ipsum_update(folder, callback, logger)
|
|
149
154
|
return []
|
|
150
155
|
}
|
|
@@ -1,56 +1,56 @@
|
|
|
1
|
-
import os from
|
|
2
|
-
import diskspace from
|
|
3
|
-
import { cyan, green, yellow } from
|
|
1
|
+
import os from "node:os"
|
|
2
|
+
import diskspace from "diskspace"
|
|
3
|
+
import { cyan, green, yellow } from "tinguir"
|
|
4
4
|
|
|
5
5
|
function _toMB(bytes) {
|
|
6
6
|
if (!bytes) return 0
|
|
7
|
-
return bytes/1000000
|
|
7
|
+
return bytes / 1000000
|
|
8
8
|
}
|
|
9
9
|
|
|
10
|
-
|
|
11
10
|
function _toGB(kbytes) {
|
|
12
11
|
if (!kbytes) return 0
|
|
13
|
-
return kbytes/1000000
|
|
12
|
+
return kbytes / 1000000
|
|
14
13
|
}
|
|
15
14
|
|
|
16
|
-
|
|
17
|
-
|
|
18
15
|
function _sys_check_and_log(logger) {
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
const
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
16
|
+
const used = Math.round(_toMB(os.freemem()), 2)
|
|
17
|
+
const total = Math.round(_toMB(os.totalmem()), 2)
|
|
18
|
+
const perc = Math.round((used * 100) / total, 2)
|
|
19
|
+
|
|
20
|
+
if (perc > 80) {
|
|
21
|
+
logger.warn(
|
|
22
|
+
`[cron][${cyan("SysCheck")}] RAM ${yellow(used)} MB used of ${green(total)} MB (${yellow(perc)} %)`
|
|
23
|
+
)
|
|
27
24
|
} else {
|
|
28
|
-
logger.info(
|
|
25
|
+
logger.info(
|
|
26
|
+
`[cron][${cyan("SysCheck")}] RAM ${yellow(used)} MB used of ${green(total)} MB (${yellow(perc)} %)`
|
|
27
|
+
)
|
|
29
28
|
}
|
|
30
|
-
|
|
31
29
|
|
|
32
|
-
diskspace.check(
|
|
33
|
-
{
|
|
30
|
+
diskspace.check("/", (_err, result) => {
|
|
34
31
|
const used = Math.round(_toGB(result.used), 2)
|
|
35
|
-
const total= Math.round(_toGB(result.total), 2)
|
|
32
|
+
const total = Math.round(_toGB(result.total), 2)
|
|
36
33
|
const free = Math.round(_toGB(result.free), 2)
|
|
37
34
|
|
|
38
|
-
if (free<1) {
|
|
39
|
-
logger.
|
|
35
|
+
if (free < 1) {
|
|
36
|
+
logger.warn(
|
|
37
|
+
`[cron][${cyan("SysCheck")}] DISK ${yellow(used)} GB used of ${green(total)} GB (${yellow(free)} GB free)`
|
|
38
|
+
)
|
|
40
39
|
} else {
|
|
41
|
-
logger.info(
|
|
40
|
+
logger.info(
|
|
41
|
+
`[cron][${cyan("SysCheck")}] DISK ${yellow(used)} GB used of ${green(total)} GB (${yellow(free)} GB free)`
|
|
42
|
+
)
|
|
42
43
|
}
|
|
43
|
-
})
|
|
44
|
+
})
|
|
44
45
|
}
|
|
45
46
|
|
|
46
|
-
|
|
47
47
|
export function sys_check_config() {
|
|
48
48
|
return {
|
|
49
|
-
name:
|
|
50
|
-
cronTime:
|
|
49
|
+
name: "SysCheck",
|
|
50
|
+
cronTime: "0,15,30,45 * * * *",
|
|
51
51
|
onTick: async (miolo, _onCompleted) => {
|
|
52
52
|
_sys_check_and_log(miolo.logger)
|
|
53
53
|
},
|
|
54
|
-
start: true
|
|
54
|
+
start: true
|
|
55
55
|
}
|
|
56
|
-
}
|
|
56
|
+
}
|
|
@@ -1,2 +1 @@
|
|
|
1
|
-
|
|
2
|
-
export {init_emailer_transporter} from './transporter.mjs'
|
|
1
|
+
export { init_emailer_transporter } from "./transporter.mjs"
|
|
@@ -1,9 +1,9 @@
|
|
|
1
|
-
import { v4 as uuidv4 } from
|
|
1
|
+
import { v4 as uuidv4 } from "uuid"
|
|
2
2
|
|
|
3
|
-
export
|
|
3
|
+
export const EMAIL_QUEUE = {}
|
|
4
4
|
|
|
5
|
-
export async function email_queue_an_email(email, logger= undefined) {
|
|
6
|
-
const _loge = logger?.
|
|
5
|
+
export async function email_queue_an_email(email, logger = undefined) {
|
|
6
|
+
const _loge = logger?.error || console.error
|
|
7
7
|
|
|
8
8
|
try {
|
|
9
9
|
const id = uuidv4()
|
|
@@ -11,24 +11,22 @@ export async function email_queue_an_email(email, logger= undefined) {
|
|
|
11
11
|
//await client.rPush('email_queue', JSON.stringify(emailData))
|
|
12
12
|
EMAIL_QUEUE[id] = emailData
|
|
13
13
|
return { ok: true, id }
|
|
14
|
-
|
|
15
14
|
} catch (error) {
|
|
16
15
|
_loge(`[emailer] Error al guardar en la cola: ${error}`)
|
|
17
16
|
return { ok: false, id: null, error }
|
|
18
17
|
}
|
|
19
18
|
}
|
|
20
19
|
|
|
21
|
-
export function email_queue_pop_pendings(
|
|
22
|
-
|
|
23
|
-
let grouped = {}
|
|
20
|
+
export function email_queue_pop_pendings(_logger = undefined) {
|
|
21
|
+
const grouped = {}
|
|
24
22
|
|
|
25
23
|
Object.values(EMAIL_QUEUE)
|
|
26
|
-
.filter(e => !e.sent)
|
|
27
|
-
.forEach(({ id: eid, from, to, subject }) => {
|
|
24
|
+
.filter((e) => !e.sent)
|
|
25
|
+
.forEach(({ id: eid, from, to, subject, text, html }) => {
|
|
28
26
|
const key = `${from}_${to}_${subject}`
|
|
29
|
-
|
|
27
|
+
|
|
30
28
|
if (!grouped[key]) {
|
|
31
|
-
grouped[key] = { to_subject_key: key, from, to, subject, count: 0, ids: [] }
|
|
29
|
+
grouped[key] = { to_subject_key: key, from, to, subject, text, html, count: 0, ids: [] }
|
|
32
30
|
}
|
|
33
31
|
|
|
34
32
|
grouped[key].count++
|
|
@@ -36,19 +34,15 @@ export function email_queue_pop_pendings(logger= undefined) {
|
|
|
36
34
|
|
|
37
35
|
// Mark as sent
|
|
38
36
|
try {
|
|
39
|
-
EMAIL_QUEUE[eid].sent= true
|
|
40
|
-
} catch(_) {}
|
|
41
|
-
|
|
37
|
+
EMAIL_QUEUE[eid].sent = true
|
|
38
|
+
} catch (_) {}
|
|
39
|
+
})
|
|
42
40
|
|
|
43
|
-
|
|
44
41
|
return Object.values(grouped)
|
|
45
42
|
}
|
|
46
43
|
|
|
47
|
-
export function email_queue_remove_ids(eids,
|
|
44
|
+
export function email_queue_remove_ids(eids, _logger = undefined) {
|
|
48
45
|
eids.forEach((eid) => {
|
|
49
|
-
|
|
50
46
|
delete EMAIL_QUEUE[eid]
|
|
51
47
|
})
|
|
52
48
|
}
|
|
53
|
-
|
|
54
|
-
|
|
@@ -1,37 +1,35 @@
|
|
|
1
|
-
import nodemailer from
|
|
2
|
-
import { email_queue_an_email, email_queue_pop_pendings, email_queue_remove_ids } from
|
|
1
|
+
import nodemailer from "nodemailer"
|
|
2
|
+
import { email_queue_an_email, email_queue_pop_pendings, email_queue_remove_ids } from "./queue.mjs"
|
|
3
3
|
|
|
4
|
+
const _logi = (logger, msg) => (logger?.info ? logger.info(msg) : console.log(msg))
|
|
5
|
+
const _logs = (logger, msg) => (logger?.silly ? logger.silly(msg) : console.log(msg))
|
|
6
|
+
const _loge = (logger, msg) => (logger?.error ? logger.error(msg) : console.error(msg))
|
|
4
7
|
|
|
5
|
-
|
|
6
|
-
const _loge = (logger, msg) => logger?.error ? logger.info(msg) : console.error(msg)
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
export function _init_emailer_transporter({options, defaults, silent}) {
|
|
10
|
-
|
|
8
|
+
export function _init_emailer_transporter({ options, defaults, silent }) {
|
|
11
9
|
const nmailer = nodemailer.createTransport(options, defaults)
|
|
12
10
|
|
|
13
|
-
function verify_emailer(logger= undefined) {
|
|
14
|
-
|
|
15
|
-
nmailer.verify(
|
|
11
|
+
function verify_emailer(logger = undefined) {
|
|
12
|
+
_logs(logger, "[emailer] Verifying...")
|
|
13
|
+
nmailer.verify((error, _success) => {
|
|
16
14
|
if (error) {
|
|
17
|
-
_loge(logger,
|
|
18
|
-
_loge(logger, error?.message || error?.stack || error ||
|
|
15
|
+
_loge(logger, "[emailer] Verifying ERROR")
|
|
16
|
+
_loge(logger, error?.message || error?.stack || error || "Unknown error")
|
|
19
17
|
} else {
|
|
20
|
-
|
|
18
|
+
_logs(logger, "[emailer] Verifyed OK: Server is ready to take our messages")
|
|
21
19
|
}
|
|
22
20
|
})
|
|
23
21
|
}
|
|
24
22
|
|
|
25
|
-
async function send_email(mail, logger= undefined) {
|
|
23
|
+
async function send_email(mail, logger = undefined) {
|
|
26
24
|
if (silent === true) {
|
|
27
|
-
_logi(logger,
|
|
28
|
-
_logi(logger,
|
|
29
|
-
_logi(logger, `[emailer] From: ${mail?.from ||
|
|
30
|
-
_logi(logger, `[emailer] To: ${mail?.to ||
|
|
31
|
-
_logi(logger, `[emailer] Subject: ${mail?.subject ||
|
|
32
|
-
_logi(logger,
|
|
33
|
-
_logi(logger, mail?.text || mail?.html ||
|
|
34
|
-
_logi(logger,
|
|
25
|
+
_logi(logger, "[emailer] *********************************")
|
|
26
|
+
_logi(logger, "[emailer] This mail will not be send (emailing is disabled):")
|
|
27
|
+
_logi(logger, `[emailer] From: ${mail?.from || "?"}`)
|
|
28
|
+
_logi(logger, `[emailer] To: ${mail?.to || "?"}`)
|
|
29
|
+
_logi(logger, `[emailer] Subject: ${mail?.subject || "?"}`)
|
|
30
|
+
_logi(logger, "[emailer] Mail body:")
|
|
31
|
+
_logi(logger, mail?.text || mail?.html || "--empty--")
|
|
32
|
+
_logi(logger, "[emailer] *********************************")
|
|
35
33
|
|
|
36
34
|
return {
|
|
37
35
|
ok: true,
|
|
@@ -41,12 +39,15 @@ export function _init_emailer_transporter({options, defaults, silent}) {
|
|
|
41
39
|
}
|
|
42
40
|
} else {
|
|
43
41
|
try {
|
|
44
|
-
|
|
45
|
-
info.ok = info?.messageId
|
|
42
|
+
const info = await nmailer.sendMail(mail)
|
|
43
|
+
info.ok = info?.messageId !== undefined
|
|
46
44
|
|
|
47
45
|
return info
|
|
48
|
-
} catch(error) {
|
|
49
|
-
_loge(
|
|
46
|
+
} catch (error) {
|
|
47
|
+
_loge(
|
|
48
|
+
logger,
|
|
49
|
+
`[emailer] Error sending email: ${mail?.from || ""} => ${mail?.to || ""} (${mail?.subject || ""})`
|
|
50
|
+
)
|
|
50
51
|
|
|
51
52
|
return {
|
|
52
53
|
ok: false,
|
|
@@ -58,16 +59,16 @@ export function _init_emailer_transporter({options, defaults, silent}) {
|
|
|
58
59
|
}
|
|
59
60
|
}
|
|
60
61
|
|
|
61
|
-
function queue_email(mail, logger= undefined) {
|
|
62
|
+
function queue_email(mail, logger = undefined) {
|
|
62
63
|
if (silent === true) {
|
|
63
|
-
_logi(logger,
|
|
64
|
-
_logi(logger,
|
|
65
|
-
_logi(logger, `[emailer] From: ${mail?.from ||
|
|
66
|
-
_logi(logger, `[emailer] To: ${mail?.to ||
|
|
67
|
-
_logi(logger, `[emailer] Subject: ${mail?.subject ||
|
|
68
|
-
_logi(logger,
|
|
69
|
-
_logi(logger, mail?.text || mail?.html ||
|
|
70
|
-
_logi(logger,
|
|
64
|
+
_logi(logger, "[emailer] *********************************")
|
|
65
|
+
_logi(logger, "[emailer] This mail will not be queued (emailing is disabled):")
|
|
66
|
+
_logi(logger, `[emailer] From: ${mail?.from || "?"}`)
|
|
67
|
+
_logi(logger, `[emailer] To: ${mail?.to || "?"}`)
|
|
68
|
+
_logi(logger, `[emailer] Subject: ${mail?.subject || "?"}`)
|
|
69
|
+
_logi(logger, "[emailer] Mail body:")
|
|
70
|
+
_logi(logger, mail?.text || mail?.html || "--empty--")
|
|
71
|
+
_logi(logger, "[emailer] *********************************")
|
|
71
72
|
|
|
72
73
|
return {
|
|
73
74
|
ok: true,
|
|
@@ -78,7 +79,10 @@ export function _init_emailer_transporter({options, defaults, silent}) {
|
|
|
78
79
|
} else {
|
|
79
80
|
try {
|
|
80
81
|
const q = email_queue_an_email(mail, logger)
|
|
81
|
-
|
|
82
|
+
_logs(
|
|
83
|
+
logger,
|
|
84
|
+
`[emailer] Queued email: ${mail?.from || ""} => ${mail?.to || ""} (${mail?.subject || ""})`
|
|
85
|
+
)
|
|
82
86
|
|
|
83
87
|
return {
|
|
84
88
|
ok: q.ok,
|
|
@@ -86,8 +90,11 @@ export function _init_emailer_transporter({options, defaults, silent}) {
|
|
|
86
90
|
error: q.error,
|
|
87
91
|
messageId: q.id
|
|
88
92
|
}
|
|
89
|
-
} catch(error) {
|
|
90
|
-
_loge(
|
|
93
|
+
} catch (error) {
|
|
94
|
+
_loge(
|
|
95
|
+
logger,
|
|
96
|
+
`[emailer] Error queueing email: ${mail?.from || ""} => ${mail?.to || ""} (${mail?.subject || ""})`
|
|
97
|
+
)
|
|
91
98
|
|
|
92
99
|
return {
|
|
93
100
|
ok: false,
|
|
@@ -99,59 +106,64 @@ export function _init_emailer_transporter({options, defaults, silent}) {
|
|
|
99
106
|
}
|
|
100
107
|
}
|
|
101
108
|
|
|
102
|
-
async function queue_send_emails(logger= undefined) {
|
|
109
|
+
async function queue_send_emails(logger = undefined) {
|
|
103
110
|
const pending = email_queue_pop_pendings(logger)
|
|
104
111
|
if (pending.length <= 0) {
|
|
105
|
-
return
|
|
112
|
+
return 0
|
|
106
113
|
}
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
if (res.ok) {
|
|
124
|
-
delete email_queue_remove_ids(email.ids, logger)
|
|
114
|
+
try {
|
|
115
|
+
_logi(logger, `[emailer] Sending emails queue (${pending.length} emails)`)
|
|
116
|
+
|
|
117
|
+
// const emailString = await client.lPop('email_queue')
|
|
118
|
+
// if (!emailString) break
|
|
119
|
+
// const email = JSON.parse(emailString)
|
|
120
|
+
|
|
121
|
+
for (const email of pending) {
|
|
122
|
+
if (email.count > 1) {
|
|
123
|
+
_logs(
|
|
124
|
+
logger,
|
|
125
|
+
`[emailer] Sending queued and stacked email [${email.subject}](x${email.count})...`
|
|
126
|
+
)
|
|
127
|
+
email.subject = `${email.subject} (x${email.count})`
|
|
128
|
+
} else {
|
|
129
|
+
_logs(logger, `[emailer] Sending queued email [${email.subject}]...`)
|
|
125
130
|
}
|
|
126
|
-
|
|
131
|
+
|
|
132
|
+
send_email(email).then((res) => {
|
|
133
|
+
_logs(logger, `[emailer] Queued email [${email.subject}]sent ${res.ok ? "OK" : "NOT OK"}`)
|
|
134
|
+
if (res.ok) {
|
|
135
|
+
delete email_queue_remove_ids(email.ids, logger)
|
|
136
|
+
}
|
|
137
|
+
})
|
|
138
|
+
}
|
|
139
|
+
_logs(logger, `[emailer] Sent emails ${pending.length} from queue`)
|
|
140
|
+
return pending.length
|
|
141
|
+
} catch (error) {
|
|
142
|
+
_loge(logger, `[emailer] Error sending emails queue: ${error}`)
|
|
143
|
+
return -1
|
|
127
144
|
}
|
|
128
|
-
_logi(logger, `[emailer] Sent emails ${pending.length} from queue`)
|
|
129
145
|
}
|
|
130
|
-
|
|
131
|
-
const emailer= {
|
|
132
|
-
send: send_email,
|
|
146
|
+
|
|
147
|
+
const emailer = {
|
|
148
|
+
send: send_email,
|
|
133
149
|
verify: verify_emailer,
|
|
134
150
|
queue_email,
|
|
135
151
|
queue_send_emails,
|
|
136
|
-
options,
|
|
137
|
-
defaults,
|
|
152
|
+
options,
|
|
153
|
+
defaults,
|
|
138
154
|
silent
|
|
139
155
|
}
|
|
140
156
|
return emailer
|
|
141
157
|
}
|
|
142
158
|
|
|
159
|
+
const _cache = {}
|
|
143
160
|
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
export function init_emailer_transporter({options, defaults, silent}, logger= undefined) {
|
|
148
|
-
|
|
149
|
-
const ckey = JSON.stringify({options, defaults, silent})
|
|
161
|
+
export function init_emailer_transporter({ options, defaults, silent }, logger = undefined) {
|
|
162
|
+
const ckey = JSON.stringify({ options, defaults, silent })
|
|
150
163
|
if (ckey in _cache) {
|
|
151
164
|
return _cache[ckey]
|
|
152
165
|
}
|
|
153
166
|
|
|
154
|
-
_cache[ckey] = _init_emailer_transporter({options, defaults, silent}, logger)
|
|
167
|
+
_cache[ckey] = _init_emailer_transporter({ options, defaults, silent }, logger)
|
|
155
168
|
return _cache[ckey]
|
|
156
|
-
|
|
157
169
|
}
|