pinokiod 3.148.0 → 3.151.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/kernel/prototype.js +0 -1
- package/kernel/router/common.js +1 -0
- package/kernel/router/connector.js +2 -0
- package/kernel/shell.js +14 -14
- package/kernel/util.js +0 -1
- package/package.json +1 -1
- package/server/index.js +187 -53
- package/server/public/files-app/app.css +317 -0
- package/server/public/files-app/app.js +686 -0
- package/server/public/style.css +5 -5
- package/server/public/tab-idle-notifier.js +48 -6
- package/server/public/urldropdown.css +59 -0
- package/server/public/urldropdown.js +140 -90
- package/server/routes/files.js +284 -0
- package/server/views/app.ejs +75 -33
- package/server/views/file_browser.ejs +130 -0
- package/server/views/net.ejs +3 -4
package/kernel/prototype.js
CHANGED
package/kernel/router/common.js
CHANGED
|
@@ -16,6 +16,7 @@ class Connector extends Processor {
|
|
|
16
16
|
"headers": {
|
|
17
17
|
"request": {
|
|
18
18
|
"set": {
|
|
19
|
+
"Host": ["{http.request.header.X-Forwarded-Host}"],
|
|
19
20
|
"X-Forwarded-Proto": ["{http.request.header.X-Forwarded-Proto}"],
|
|
20
21
|
//"X-Forwarded-Proto": ["{http.request.scheme}"],
|
|
21
22
|
//"X-Forwarded-Proto": ["https"],
|
|
@@ -55,6 +56,7 @@ class Connector extends Processor {
|
|
|
55
56
|
"headers": {
|
|
56
57
|
"request": {
|
|
57
58
|
"set": {
|
|
59
|
+
"Host": ["{http.request.host}"],
|
|
58
60
|
//"X-Forwarded-Proto": ["https"],
|
|
59
61
|
//"Origin": "localhost",
|
|
60
62
|
"X-Forwarded-Proto": ["{http.request.scheme}"],
|
package/kernel/shell.js
CHANGED
|
@@ -1061,20 +1061,20 @@ class Shell {
|
|
|
1061
1061
|
this.monitor = this.monitor + data
|
|
1062
1062
|
this.monitor = this.monitor.slice(-300) // last 300
|
|
1063
1063
|
|
|
1064
|
-
let notifications = this.parser.processData(data)
|
|
1065
|
-
if (notifications.length > 0) {
|
|
1066
|
-
console.log({ notifications })
|
|
1067
|
-
for(let notif of notifications) {
|
|
1068
|
-
if (notif.type !== "bell") {
|
|
1069
|
-
Util.push({
|
|
1070
|
-
image: path.resolve(__dirname, "../server/public/pinokio-black.png"),
|
|
1071
|
-
message: notif.title,
|
|
1072
|
-
sound: true,
|
|
1073
|
-
timeout: 30,
|
|
1074
|
-
})
|
|
1075
|
-
}
|
|
1076
|
-
}
|
|
1077
|
-
}
|
|
1064
|
+
// let notifications = this.parser.processData(data)
|
|
1065
|
+
// if (notifications.length > 0) {
|
|
1066
|
+
// console.log({ notifications })
|
|
1067
|
+
// for(let notif of notifications) {
|
|
1068
|
+
// if (notif.type !== "bell") {
|
|
1069
|
+
// Util.push({
|
|
1070
|
+
// image: path.resolve(__dirname, "../server/public/pinokio-black.png"),
|
|
1071
|
+
// message: notif.title,
|
|
1072
|
+
// sound: true,
|
|
1073
|
+
// timeout: 30,
|
|
1074
|
+
// })
|
|
1075
|
+
// }
|
|
1076
|
+
// }
|
|
1077
|
+
// }
|
|
1078
1078
|
|
|
1079
1079
|
if (!this.done) {
|
|
1080
1080
|
|
package/kernel/util.js
CHANGED
package/package.json
CHANGED
package/server/index.js
CHANGED
|
@@ -25,6 +25,7 @@ const QRCode = require('qrcode')
|
|
|
25
25
|
const axios = require('axios')
|
|
26
26
|
const crypto = require('crypto')
|
|
27
27
|
const serveIndex = require('./serveIndex')
|
|
28
|
+
const registerFileRoutes = require('./routes/files')
|
|
28
29
|
|
|
29
30
|
const git = require('isomorphic-git')
|
|
30
31
|
const http = require('isomorphic-git/http/node')
|
|
@@ -812,6 +813,12 @@ class Server {
|
|
|
812
813
|
let dev_tab = "/p/" + name + "/dev"
|
|
813
814
|
let review_tab = "/p/" + name + "/review"
|
|
814
815
|
|
|
816
|
+
let editor_tab = `/pinokio/fileview/${encodeURIComponent(name)}`
|
|
817
|
+
let savedTabs = []
|
|
818
|
+
if (Array.isArray(this.tabs[name])) {
|
|
819
|
+
savedTabs = this.tabs[name].filter((url) => url !== editor_tab)
|
|
820
|
+
}
|
|
821
|
+
|
|
815
822
|
let dynamic_url = "/pinokio/dynamic/" + name;
|
|
816
823
|
if (Object.values(req.query).length > 0) {
|
|
817
824
|
let index = 0
|
|
@@ -852,7 +859,8 @@ class Server {
|
|
|
852
859
|
name,
|
|
853
860
|
// profile,
|
|
854
861
|
// feed,
|
|
855
|
-
tabs:
|
|
862
|
+
tabs: savedTabs,
|
|
863
|
+
editor_tab: editor_tab,
|
|
856
864
|
config,
|
|
857
865
|
// sidebar_url: "/pinokio/sidebar/" + name,
|
|
858
866
|
home: req.originalUrl,
|
|
@@ -3182,61 +3190,180 @@ class Server {
|
|
|
3182
3190
|
}
|
|
3183
3191
|
}
|
|
3184
3192
|
add_extra_urls(info) {
|
|
3185
|
-
|
|
3186
|
-
|
|
3187
|
-
|
|
3193
|
+
if (!this.kernel.peer || !this.kernel.peer.info) {
|
|
3194
|
+
return
|
|
3195
|
+
}
|
|
3188
3196
|
|
|
3189
|
-
|
|
3190
|
-
|
|
3191
|
-
|
|
3192
|
-
|
|
3193
|
-
|
|
3194
|
-
|
|
3195
|
-
|
|
3196
|
-
|
|
3197
|
-
|
|
3198
|
-
|
|
3199
|
-
|
|
3200
|
-
name: `[Files] ${host_rewrites[key].name}`,
|
|
3201
|
-
ip: host_rewrites[key].external_ip
|
|
3202
|
-
})
|
|
3197
|
+
const ensureArray = (value) => {
|
|
3198
|
+
if (!value) return []
|
|
3199
|
+
return Array.isArray(value) ? value.filter(Boolean) : [value].filter(Boolean)
|
|
3200
|
+
}
|
|
3201
|
+
|
|
3202
|
+
const normalizeHttpUrl = (value) => {
|
|
3203
|
+
if (!value) return null
|
|
3204
|
+
const str = String(value).trim()
|
|
3205
|
+
if (!str) return null
|
|
3206
|
+
if (/^https?:\/\//i.test(str)) {
|
|
3207
|
+
return str.replace(/^https:/i, 'http:')
|
|
3203
3208
|
}
|
|
3204
|
-
|
|
3205
|
-
|
|
3206
|
-
|
|
3207
|
-
|
|
3208
|
-
|
|
3209
|
-
|
|
3210
|
-
|
|
3211
|
-
|
|
3212
|
-
|
|
3213
|
-
|
|
3209
|
+
return `http://${str}`
|
|
3210
|
+
}
|
|
3211
|
+
|
|
3212
|
+
const normalizeHttpsUrl = (value) => {
|
|
3213
|
+
if (!value) return null
|
|
3214
|
+
const str = String(value).trim()
|
|
3215
|
+
if (!str) return null
|
|
3216
|
+
if (/^https?:\/\//i.test(str)) {
|
|
3217
|
+
return str.replace(/^http:/i, 'https:')
|
|
3218
|
+
}
|
|
3219
|
+
return `https://${str}`
|
|
3220
|
+
}
|
|
3221
|
+
|
|
3222
|
+
const seen = new Set()
|
|
3223
|
+
|
|
3224
|
+
const pushEntry = ({ host, name, ip, httpUrl, httpsUrls, description, icon, online = true }) => {
|
|
3225
|
+
const normalizedHttp = normalizeHttpUrl(httpUrl)
|
|
3226
|
+
const hostNameForAlias = host && host.name ? String(host.name).trim() : ''
|
|
3227
|
+
const peerSuffix = hostNameForAlias ? `.${hostNameForAlias}.localhost` : null
|
|
3228
|
+
|
|
3229
|
+
const normalizedHttpsSet = new Set(
|
|
3230
|
+
ensureArray(httpsUrls)
|
|
3231
|
+
.map(normalizeHttpsUrl)
|
|
3232
|
+
.filter(Boolean)
|
|
3233
|
+
)
|
|
3234
|
+
|
|
3235
|
+
if (host && host.local && peerSuffix) {
|
|
3236
|
+
for (const originalUrl of normalizedHttpsSet) {
|
|
3237
|
+
try {
|
|
3238
|
+
const parsed = new URL(originalUrl)
|
|
3239
|
+
if (parsed.hostname.endsWith(peerSuffix)) {
|
|
3240
|
+
const aliasHost = `${parsed.hostname.slice(0, -peerSuffix.length)}.localhost`
|
|
3241
|
+
if (aliasHost && aliasHost !== parsed.hostname) {
|
|
3242
|
+
let pathname = parsed.pathname || ''
|
|
3243
|
+
if (pathname === '/' || pathname === '') {
|
|
3244
|
+
pathname = ''
|
|
3245
|
+
}
|
|
3246
|
+
const aliasUrl = `${parsed.protocol}//${aliasHost}${pathname}${parsed.search}${parsed.hash}`
|
|
3247
|
+
normalizedHttpsSet.add(aliasUrl)
|
|
3248
|
+
}
|
|
3249
|
+
}
|
|
3250
|
+
} catch (_) {
|
|
3251
|
+
// continue
|
|
3214
3252
|
}
|
|
3215
|
-
|
|
3216
|
-
|
|
3217
|
-
|
|
3218
|
-
|
|
3219
|
-
|
|
3220
|
-
|
|
3221
|
-
|
|
3222
|
-
|
|
3223
|
-
|
|
3224
|
-
|
|
3253
|
+
}
|
|
3254
|
+
}
|
|
3255
|
+
|
|
3256
|
+
const normalizedHttps = Array.from(normalizedHttpsSet)
|
|
3257
|
+
const ipValue = typeof ip === 'string' ? ip : (normalizedHttp ? normalizedHttp.replace(/^https?:\/\//i, '') : null)
|
|
3258
|
+
const selectedUrl = normalizedHttps[0] || normalizedHttp || null
|
|
3259
|
+
const protocol = normalizedHttps.length > 0 ? 'https' : (normalizedHttp ? 'http' : undefined)
|
|
3260
|
+
const hostKey = host && (host.ip || host.name) ? `${host.ip || host.name}` : 'unknown'
|
|
3261
|
+
const uniquenessKey = `${hostKey}|${name}|${ipValue || ''}|${selectedUrl || ''}`
|
|
3262
|
+
if (seen.has(uniquenessKey)) {
|
|
3263
|
+
return
|
|
3264
|
+
}
|
|
3265
|
+
seen.add(uniquenessKey)
|
|
3266
|
+
|
|
3267
|
+
const entry = {
|
|
3268
|
+
online,
|
|
3269
|
+
host: { ...host },
|
|
3270
|
+
name,
|
|
3271
|
+
ip: ipValue,
|
|
3272
|
+
url: selectedUrl,
|
|
3273
|
+
protocol,
|
|
3274
|
+
urls: {
|
|
3275
|
+
http: normalizedHttp,
|
|
3276
|
+
https: normalizedHttps
|
|
3277
|
+
}
|
|
3278
|
+
}
|
|
3279
|
+
if (description) {
|
|
3280
|
+
entry.description = description
|
|
3281
|
+
}
|
|
3282
|
+
if (icon) {
|
|
3283
|
+
entry.icon = icon
|
|
3284
|
+
}
|
|
3285
|
+
info.push(entry)
|
|
3286
|
+
}
|
|
3287
|
+
|
|
3288
|
+
for (const host of Object.keys(this.kernel.peer.info)) {
|
|
3289
|
+
const hostInfo = this.kernel.peer.info[host]
|
|
3290
|
+
if (!hostInfo) {
|
|
3291
|
+
continue
|
|
3292
|
+
}
|
|
3293
|
+
|
|
3294
|
+
const hostMeta = {
|
|
3295
|
+
ip: host,
|
|
3296
|
+
local: this.kernel.peer.host === host,
|
|
3297
|
+
name: hostInfo.name,
|
|
3298
|
+
platform: hostInfo.platform,
|
|
3299
|
+
arch: hostInfo.arch
|
|
3300
|
+
}
|
|
3301
|
+
|
|
3302
|
+
const rewrites = hostInfo.rewrite_mapping
|
|
3303
|
+
if (rewrites && typeof rewrites === 'object') {
|
|
3304
|
+
for (const key of Object.keys(rewrites)) {
|
|
3305
|
+
const rewrite = rewrites[key]
|
|
3306
|
+
if (!rewrite) {
|
|
3307
|
+
continue
|
|
3308
|
+
}
|
|
3309
|
+
const externalIp = Array.isArray(rewrite.external_ip) ? rewrite.external_ip[0] : rewrite.external_ip
|
|
3310
|
+
const httpsSources = [
|
|
3311
|
+
...ensureArray(rewrite.external_router),
|
|
3312
|
+
...ensureArray(rewrite.internal_router)
|
|
3313
|
+
]
|
|
3314
|
+
pushEntry({
|
|
3315
|
+
host: hostMeta,
|
|
3316
|
+
name: `[Files] ${rewrite.name || key}`,
|
|
3317
|
+
ip: externalIp || null,
|
|
3318
|
+
httpUrl: externalIp,
|
|
3319
|
+
httpsUrls: Array.from(new Set(httpsSources))
|
|
3225
3320
|
})
|
|
3226
3321
|
}
|
|
3227
3322
|
}
|
|
3228
3323
|
|
|
3229
|
-
|
|
3230
|
-
|
|
3231
|
-
|
|
3232
|
-
|
|
3233
|
-
|
|
3234
|
-
|
|
3235
|
-
|
|
3236
|
-
|
|
3237
|
-
|
|
3238
|
-
|
|
3239
|
-
|
|
3324
|
+
const hostRouters = Array.isArray(hostInfo.router_info) ? hostInfo.router_info : []
|
|
3325
|
+
for (const route of hostRouters) {
|
|
3326
|
+
if (!route) {
|
|
3327
|
+
continue
|
|
3328
|
+
}
|
|
3329
|
+
const externalIp = Array.isArray(route.external_ip) ? route.external_ip[0] : route.external_ip
|
|
3330
|
+
const httpUrl = externalIp || null
|
|
3331
|
+
const httpsCandidates = Array.from(new Set([
|
|
3332
|
+
...ensureArray(route.external_router),
|
|
3333
|
+
...ensureArray(route.internal_router)
|
|
3334
|
+
]))
|
|
3335
|
+
if (httpsCandidates.length === 0 && !httpUrl) {
|
|
3336
|
+
continue
|
|
3337
|
+
}
|
|
3338
|
+
pushEntry({
|
|
3339
|
+
host: hostMeta,
|
|
3340
|
+
name: route.title || route.name,
|
|
3341
|
+
ip: externalIp || null,
|
|
3342
|
+
httpUrl,
|
|
3343
|
+
httpsUrls: httpsCandidates,
|
|
3344
|
+
description: route.description,
|
|
3345
|
+
icon: route.icon || route.https_icon || route.http_icon
|
|
3346
|
+
})
|
|
3347
|
+
}
|
|
3348
|
+
|
|
3349
|
+
const installedApps = Array.isArray(hostInfo.installed) ? hostInfo.installed : []
|
|
3350
|
+
for (const app of installedApps) {
|
|
3351
|
+
if (!app) {
|
|
3352
|
+
continue
|
|
3353
|
+
}
|
|
3354
|
+
const httpHref = Array.isArray(app.http_href) ? app.http_href[0] : app.http_href
|
|
3355
|
+
const httpsCandidates = Array.from(new Set([
|
|
3356
|
+
...ensureArray(app.app_href),
|
|
3357
|
+
...ensureArray(app.https_href)
|
|
3358
|
+
]))
|
|
3359
|
+
pushEntry({
|
|
3360
|
+
host: hostMeta,
|
|
3361
|
+
name: app.title || app.name || app.folder,
|
|
3362
|
+
ip: httpHref ? httpHref.replace(/^https?:\/\//i, '') : null,
|
|
3363
|
+
httpUrl: httpHref || null,
|
|
3364
|
+
httpsUrls: httpsCandidates,
|
|
3365
|
+
description: app.description,
|
|
3366
|
+
icon: app.https_icon || app.http_icon || app.icon
|
|
3240
3367
|
})
|
|
3241
3368
|
}
|
|
3242
3369
|
}
|
|
@@ -3267,14 +3394,14 @@ class Server {
|
|
|
3267
3394
|
}
|
|
3268
3395
|
terminal = {
|
|
3269
3396
|
icon: "fa-solid fa-terminal",
|
|
3270
|
-
title: "Terminal",
|
|
3397
|
+
title: "User Terminal",
|
|
3271
3398
|
subtitle: "Open the terminal in the browser",
|
|
3272
3399
|
menu: terminals
|
|
3273
3400
|
}
|
|
3274
3401
|
} else {
|
|
3275
3402
|
terminal = {
|
|
3276
3403
|
icon: "fa-solid fa-terminal",
|
|
3277
|
-
title: "Terminal",
|
|
3404
|
+
title: "User Terminal",
|
|
3278
3405
|
subtitle: "Work with the terminal directly in the browser",
|
|
3279
3406
|
menu: [this.renderShell(filepath, 0, 0, {
|
|
3280
3407
|
icon: "fa-solid fa-terminal",
|
|
@@ -3730,6 +3857,11 @@ class Server {
|
|
|
3730
3857
|
};
|
|
3731
3858
|
next();
|
|
3732
3859
|
});
|
|
3860
|
+
registerFileRoutes(this.app, {
|
|
3861
|
+
kernel: this.kernel,
|
|
3862
|
+
getTheme: () => this.theme,
|
|
3863
|
+
exists: (target) => this.exists(target),
|
|
3864
|
+
});
|
|
3733
3865
|
/*
|
|
3734
3866
|
this.app.get("/asset/*", ex((req, res) => {
|
|
3735
3867
|
let pathComponents = req.params[0].split("/")
|
|
@@ -4527,7 +4659,6 @@ class Server {
|
|
|
4527
4659
|
}
|
|
4528
4660
|
}))
|
|
4529
4661
|
this.app.post("/push", ex(async (req, res) => {
|
|
4530
|
-
console.log("Push", req.body)
|
|
4531
4662
|
try {
|
|
4532
4663
|
const payload = { ...(req.body || {}) }
|
|
4533
4664
|
const resolveAssetPath = (raw) => {
|
|
@@ -6222,6 +6353,7 @@ class Server {
|
|
|
6222
6353
|
menu: exec_menus
|
|
6223
6354
|
},
|
|
6224
6355
|
]
|
|
6356
|
+
|
|
6225
6357
|
let spec = ""
|
|
6226
6358
|
try {
|
|
6227
6359
|
spec = await fs.promises.readFile(path.resolve(filepath, "SPEC.md"), "utf8")
|
|
@@ -6610,6 +6742,7 @@ class Server {
|
|
|
6610
6742
|
if (preferHttps) {
|
|
6611
6743
|
httpsHosts = resolveHttpsHosts(item)
|
|
6612
6744
|
}
|
|
6745
|
+
console.log("httpsHosts", httpsHosts)
|
|
6613
6746
|
const httpsUrls = httpsHosts.map((host) => {
|
|
6614
6747
|
if (!host) {
|
|
6615
6748
|
return null
|
|
@@ -6620,6 +6753,7 @@ class Server {
|
|
|
6620
6753
|
}
|
|
6621
6754
|
return `https://${trimmed}`
|
|
6622
6755
|
}).filter(Boolean)
|
|
6756
|
+
console.log("httpsUrls", httpsUrls)
|
|
6623
6757
|
|
|
6624
6758
|
const preferredHttpsUrl = preferFriendlyHost(httpsHosts)
|
|
6625
6759
|
const displayHttpsUrl = preferredHttpsUrl
|
|
@@ -6648,7 +6782,7 @@ class Server {
|
|
|
6648
6782
|
}
|
|
6649
6783
|
})
|
|
6650
6784
|
|
|
6651
|
-
|
|
6785
|
+
this.add_extra_urls(info)
|
|
6652
6786
|
res.json({
|
|
6653
6787
|
info
|
|
6654
6788
|
})
|