pinokiod 3.19.0 → 3.19.4
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/api/filepicker/index.js +5 -21
- package/kernel/api/index.js +0 -2
- package/kernel/api/push/index.js +21 -0
- package/kernel/bin/cli.js +31 -0
- package/kernel/bin/git.js +34 -0
- package/kernel/bin/index.js +36 -44
- package/kernel/bin/setup.js +3 -0
- package/kernel/environment.js +0 -3
- package/kernel/git.js +64 -0
- package/kernel/index.js +2 -0
- package/kernel/router/index.js +13 -11
- package/kernel/scripts/git/commit +21 -0
- package/kernel/scripts/git/create +12 -0
- package/kernel/scripts/git/push +22 -0
- package/kernel/shell.js +17 -1
- package/kernel/shells.js +47 -22
- package/kernel/util.js +258 -1
- package/package.json +5 -2
- package/server/index.js +214 -5
- package/server/public/RobotoMono-Regular.ttf +0 -0
- package/server/public/install.js +4 -0
- package/server/public/style.css +11 -1
- package/server/socket.js +89 -2
- package/server/views/app.ejs +46 -9
- package/server/views/file_explorer.ejs +3 -4
- package/server/views/git.ejs +149 -0
- package/server/views/install.ejs +3 -0
- package/server/views/mini.ejs +1542 -0
- package/server/views/partials/dynamic.ejs +10 -9
- package/server/views/prototype/init.ejs +22 -8
- package/server/views/shell.ejs +4 -5
- package/server/views/terminal.ejs +4 -18
|
@@ -1,5 +1,3 @@
|
|
|
1
|
-
const path = require('path')
|
|
2
|
-
const { spawn } = require("child_process");
|
|
3
1
|
/*
|
|
4
2
|
{
|
|
5
3
|
method: "filepicker.open",
|
|
@@ -7,6 +5,7 @@ const { spawn } = require("child_process");
|
|
|
7
5
|
title, := <dialog title>
|
|
8
6
|
type, := folder | file (default)
|
|
9
7
|
path, := <cwd to open from>
|
|
8
|
+
filetype, := <file types to accept> can be an array or string (example: `image/*.png,*.jpg` or `["image/*.png", "docs/*.pdf"]`)
|
|
10
9
|
filetypes, := <file types to accept> (example: [["Images", "*.png *.jpg *.jpeg"]] )
|
|
11
10
|
multiple, := True | False (allow multiple)
|
|
12
11
|
save, := True | False ('save as' dialog, which lets the user select a file name)
|
|
@@ -26,6 +25,8 @@ returns: {
|
|
|
26
25
|
}
|
|
27
26
|
|
|
28
27
|
*/
|
|
28
|
+
const path = require('path')
|
|
29
|
+
const Util = require("../../util")
|
|
29
30
|
class Filepicker {
|
|
30
31
|
async open(req, ondata, kernel) {
|
|
31
32
|
if (req.params.cwd) {
|
|
@@ -35,27 +36,10 @@ class Filepicker {
|
|
|
35
36
|
} else {
|
|
36
37
|
req.params.cwd = req.cwd
|
|
37
38
|
}
|
|
38
|
-
let response = await new Promise((resolve, reject) => {
|
|
39
|
-
let picker_path = kernel.path("bin/py/picker.py")
|
|
40
|
-
const proc = spawn("python", [picker_path])
|
|
41
39
|
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
proc.stderr.on("data", (err) => console.error("Python error:", err.toString()));
|
|
45
|
-
proc.on("close", () => {
|
|
46
|
-
try {
|
|
47
|
-
const result = JSON.parse(output);
|
|
48
|
-
if (result.error) return reject(result.error);
|
|
49
|
-
resolve(result.paths); // Always an array
|
|
50
|
-
} catch (e) {
|
|
51
|
-
reject("Failed to parse Python output: " + output);
|
|
52
|
-
}
|
|
53
|
-
});
|
|
40
|
+
let res = await Util.filepicker(req, ondata, kernel)
|
|
41
|
+
return res
|
|
54
42
|
|
|
55
|
-
proc.stdin.write(JSON.stringify(req.params));
|
|
56
|
-
proc.stdin.end();
|
|
57
|
-
});
|
|
58
|
-
return { paths: response }
|
|
59
43
|
}
|
|
60
44
|
}
|
|
61
45
|
module.exports = Filepicker
|
package/kernel/api/index.js
CHANGED
|
@@ -1321,7 +1321,6 @@ class Api {
|
|
|
1321
1321
|
// look for pinokio.js
|
|
1322
1322
|
let p = path.resolve(request.path, "pinokio.js")
|
|
1323
1323
|
let exists = await this.exists(p)
|
|
1324
|
-
console.log({ p, exists })
|
|
1325
1324
|
if (exists) {
|
|
1326
1325
|
await this.launch(request, p)
|
|
1327
1326
|
} else {
|
|
@@ -1332,7 +1331,6 @@ class Api {
|
|
|
1332
1331
|
})
|
|
1333
1332
|
}
|
|
1334
1333
|
} else {
|
|
1335
|
-
console.log({ request })
|
|
1336
1334
|
let { cwd, script } = await this.resolveScript(request.path)
|
|
1337
1335
|
|
|
1338
1336
|
if (!script) {
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
/*
|
|
2
|
+
{
|
|
3
|
+
method: "push",
|
|
4
|
+
params: {
|
|
5
|
+
title: <string>,
|
|
6
|
+
subtitle: <string>,
|
|
7
|
+
message: <string>,
|
|
8
|
+
image: <image path>,
|
|
9
|
+
sound: true|false,
|
|
10
|
+
}
|
|
11
|
+
}
|
|
12
|
+
(*/
|
|
13
|
+
const util = require('../../util')
|
|
14
|
+
const path = require('path');
|
|
15
|
+
module.exports = async (req, ondata, kernel) => {
|
|
16
|
+
let params = req.params
|
|
17
|
+
if (params.image) {
|
|
18
|
+
params.image = path.resolve(req.cwd, params.image)
|
|
19
|
+
}
|
|
20
|
+
util.push(params)
|
|
21
|
+
}
|
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
const path = require('path')
|
|
2
|
+
class CLI {
|
|
3
|
+
async install(req, ondata) {
|
|
4
|
+
await this.kernel.exec({
|
|
5
|
+
message: "npm install -g pinokio-cli@latest",
|
|
6
|
+
}, ondata)
|
|
7
|
+
}
|
|
8
|
+
async installed(req, ondata) {
|
|
9
|
+
console.log("Check installed")
|
|
10
|
+
if (this.kernel.which('pinokio')) {
|
|
11
|
+
let res = await this.kernel.exec({
|
|
12
|
+
message: "pinokio version"
|
|
13
|
+
}, ondata)
|
|
14
|
+
if (/.*v0\.0\.4.*/.test(res.stdout)) {
|
|
15
|
+
console.log("Installed")
|
|
16
|
+
return true
|
|
17
|
+
} else {
|
|
18
|
+
console.log("Not Installed")
|
|
19
|
+
return false
|
|
20
|
+
}
|
|
21
|
+
} else {
|
|
22
|
+
return false
|
|
23
|
+
}
|
|
24
|
+
}
|
|
25
|
+
async uninstall(req, ondata) {
|
|
26
|
+
await this.kernel.exec({
|
|
27
|
+
message: "npm uninstall -g pinokio-cli",
|
|
28
|
+
}, ondata)
|
|
29
|
+
}
|
|
30
|
+
}
|
|
31
|
+
module.exports = CLI
|
package/kernel/bin/git.js
CHANGED
|
@@ -45,6 +45,25 @@ class Git {
|
|
|
45
45
|
gitconfig_path
|
|
46
46
|
)
|
|
47
47
|
}
|
|
48
|
+
|
|
49
|
+
await fs.promises.mkdir(this.kernel.path("scripts/git"), { recursive: true }).catch((e) => { })
|
|
50
|
+
let gitpush_path = path.resolve(this.kernel.homedir, "scripts/git/push.json")
|
|
51
|
+
await fs.promises.copyFile(
|
|
52
|
+
path.resolve(__dirname, "..", "scripts/git/push"),
|
|
53
|
+
gitpush_path
|
|
54
|
+
)
|
|
55
|
+
|
|
56
|
+
let gitcreate_path = path.resolve(this.kernel.homedir, "scripts/git/create.json")
|
|
57
|
+
await fs.promises.copyFile(
|
|
58
|
+
path.resolve(__dirname, "..", "scripts/git/create"),
|
|
59
|
+
gitcreate_path
|
|
60
|
+
)
|
|
61
|
+
|
|
62
|
+
let gitcommit_path = path.resolve(this.kernel.homedir, "scripts/git/commit.json")
|
|
63
|
+
await fs.promises.copyFile(
|
|
64
|
+
path.resolve(__dirname, "..", "scripts/git/commit"),
|
|
65
|
+
gitcommit_path
|
|
66
|
+
)
|
|
48
67
|
}
|
|
49
68
|
async installed() {
|
|
50
69
|
let gitconfig_path = path.resolve(this.kernel.homedir, "gitconfig")
|
|
@@ -52,6 +71,21 @@ class Git {
|
|
|
52
71
|
if (!exists) {
|
|
53
72
|
return false;
|
|
54
73
|
}
|
|
74
|
+
let gitpush_path = path.resolve(this.kernel.homedir, "scripts/git/push.json")
|
|
75
|
+
let exists2 = await this.kernel.api.exists(gitpush_path)
|
|
76
|
+
if (!exists2) {
|
|
77
|
+
return false;
|
|
78
|
+
}
|
|
79
|
+
let gitcreate_path = path.resolve(this.kernel.homedir, "scripts/git/create.json")
|
|
80
|
+
let exists3 = await this.kernel.api.exists(gitcreate_path)
|
|
81
|
+
if (!exists3) {
|
|
82
|
+
return false;
|
|
83
|
+
}
|
|
84
|
+
let gitcommit_path = path.resolve(this.kernel.homedir, "scripts/git/commit.json")
|
|
85
|
+
let exists4 = await this.kernel.api.exists(gitcommit_path)
|
|
86
|
+
if (!exists4) {
|
|
87
|
+
return false;
|
|
88
|
+
}
|
|
55
89
|
|
|
56
90
|
if (this.kernel.platform === "darwin") {
|
|
57
91
|
let gh_config_exists = await this.kernel.exists("config/gh")
|
package/kernel/bin/index.js
CHANGED
|
@@ -4,13 +4,13 @@ const _ = require('lodash')
|
|
|
4
4
|
const path = require('path')
|
|
5
5
|
const { rimraf } = require('rimraf')
|
|
6
6
|
const { DownloaderHelper } = require('node-downloader-helper');
|
|
7
|
-
const { spawn } = require('child_process')
|
|
8
7
|
const { ProxyAgent } = require('proxy-agent');
|
|
9
8
|
|
|
10
9
|
//const Cmake = require("./cmake")
|
|
11
10
|
const Python = require('./python')
|
|
12
11
|
const Git = require('./git')
|
|
13
12
|
const Node = require('./node')
|
|
13
|
+
const CLI = require('./cli')
|
|
14
14
|
const Brew = require("./brew")
|
|
15
15
|
const Conda = require("./conda")
|
|
16
16
|
const Win = require("./win")
|
|
@@ -27,6 +27,7 @@ const fse = require('fs-extra')
|
|
|
27
27
|
const semver = require('semver')
|
|
28
28
|
//const { bootstrap } = require('global-agent')
|
|
29
29
|
const Environment = require('../environment')
|
|
30
|
+
const Util = require("../util")
|
|
30
31
|
//const imageToAscii = require("image-to-ascii");
|
|
31
32
|
|
|
32
33
|
const Setup = require('./setup')
|
|
@@ -198,6 +199,7 @@ class Bin {
|
|
|
198
199
|
return e
|
|
199
200
|
}
|
|
200
201
|
async init() {
|
|
202
|
+
this.requirements_cache = {}
|
|
201
203
|
this.mods = []
|
|
202
204
|
if (this.kernel.homedir) {
|
|
203
205
|
const bin_folder = this.path()
|
|
@@ -658,32 +660,8 @@ class Bin {
|
|
|
658
660
|
}
|
|
659
661
|
}
|
|
660
662
|
async filepicker(req, ondata) {
|
|
661
|
-
|
|
662
|
-
|
|
663
|
-
cwd: cwd
|
|
664
|
-
}
|
|
665
|
-
*/
|
|
666
|
-
let response = await new Promise((resolve, reject) => {
|
|
667
|
-
let picker_path = this.kernel.path("bin/py/picker.py")
|
|
668
|
-
const proc = spawn("python", [picker_path])
|
|
669
|
-
|
|
670
|
-
let output = "";
|
|
671
|
-
proc.stdout.on("data", (chunk) => output += chunk);
|
|
672
|
-
proc.stderr.on("data", (err) => console.error("Python error:", err.toString()));
|
|
673
|
-
proc.on("close", () => {
|
|
674
|
-
try {
|
|
675
|
-
const result = JSON.parse(output);
|
|
676
|
-
if (result.error) return reject(result.error);
|
|
677
|
-
resolve(result.paths); // Always an array
|
|
678
|
-
} catch (e) {
|
|
679
|
-
reject("Failed to parse Python output: " + output);
|
|
680
|
-
}
|
|
681
|
-
});
|
|
682
|
-
|
|
683
|
-
proc.stdin.write(JSON.stringify(req.params));
|
|
684
|
-
proc.stdin.end();
|
|
685
|
-
});
|
|
686
|
-
return { paths: response }
|
|
663
|
+
let res = await Util.filepicker(req, ondata, this.kernel)
|
|
664
|
+
return res
|
|
687
665
|
}
|
|
688
666
|
async install(req, ondata) {
|
|
689
667
|
/*
|
|
@@ -703,6 +681,7 @@ class Bin {
|
|
|
703
681
|
} else {
|
|
704
682
|
this.client = null
|
|
705
683
|
}
|
|
684
|
+
console.log("Client", this.client)
|
|
706
685
|
let requirements = JSON.parse(req.params)
|
|
707
686
|
for(let x=0; x<10; x++) {
|
|
708
687
|
console.log(`## Install Attempt ${x}`)
|
|
@@ -1000,27 +979,40 @@ class Bin {
|
|
|
1000
979
|
let install_required = true
|
|
1001
980
|
if (!requirements_pending) {
|
|
1002
981
|
install_required = false
|
|
982
|
+
console.log("requirements", requirements)
|
|
1003
983
|
for(let i=0; i<requirements.length; i++) {
|
|
1004
984
|
let r = requirements[i]
|
|
1005
|
-
|
|
1006
|
-
|
|
1007
|
-
|
|
1008
|
-
|
|
1009
|
-
|
|
1010
|
-
|
|
1011
|
-
|
|
1012
|
-
|
|
1013
|
-
|
|
1014
|
-
if (
|
|
1015
|
-
|
|
1016
|
-
|
|
1017
|
-
|
|
1018
|
-
|
|
1019
|
-
|
|
1020
|
-
|
|
1021
|
-
|
|
985
|
+
let fingerprint = JSON.stringify(r)
|
|
986
|
+
let installed
|
|
987
|
+
if (this.requirements_cache[fingerprint]) {
|
|
988
|
+
console.log("USE CACHED", fingerprint)
|
|
989
|
+
installed = true
|
|
990
|
+
requirements[i].installed = true
|
|
991
|
+
} else {
|
|
992
|
+
//let installed = await this.installed(r)
|
|
993
|
+
//requirements[i].installed = installed
|
|
994
|
+
//if (!installed) {
|
|
995
|
+
// install_required = true
|
|
996
|
+
//}
|
|
997
|
+
let relevant = this.relevant(r)
|
|
998
|
+
requirements[i].relevant = relevant
|
|
999
|
+
if (relevant) {
|
|
1000
|
+
let dependencies
|
|
1001
|
+
if (r.name === "conda") {
|
|
1002
|
+
dependencies = config.bin.conda_requirements
|
|
1003
|
+
requirements[i].dependencies = dependencies
|
|
1004
|
+
}
|
|
1005
|
+
installed = await this.check_installed(r, dependencies)
|
|
1006
|
+
if (installed) {
|
|
1007
|
+
// cache if true
|
|
1008
|
+
this.requirements_cache[fingerprint] = true
|
|
1009
|
+
}
|
|
1010
|
+
requirements[i].installed = installed
|
|
1022
1011
|
}
|
|
1023
1012
|
}
|
|
1013
|
+
if (!installed) {
|
|
1014
|
+
install_required = true
|
|
1015
|
+
}
|
|
1024
1016
|
}
|
|
1025
1017
|
}
|
|
1026
1018
|
|
package/kernel/bin/setup.js
CHANGED
|
@@ -27,6 +27,7 @@ module.exports = {
|
|
|
27
27
|
requirements = requirements.concat([
|
|
28
28
|
{ name: "git", },
|
|
29
29
|
{ name: "node", },
|
|
30
|
+
{ name: "cli", },
|
|
30
31
|
{ name: "ffmpeg", },
|
|
31
32
|
// { name: "caddy", }
|
|
32
33
|
])
|
|
@@ -68,6 +69,7 @@ module.exports = {
|
|
|
68
69
|
requirements = requirements.concat([
|
|
69
70
|
{ name: "git", },
|
|
70
71
|
{ name: "node", },
|
|
72
|
+
{ name: "cli", },
|
|
71
73
|
{ name: "py" },
|
|
72
74
|
])
|
|
73
75
|
return {
|
|
@@ -118,6 +120,7 @@ module.exports = {
|
|
|
118
120
|
requirements = requirements.concat([
|
|
119
121
|
{ name: "git", },
|
|
120
122
|
{ name: "node", },
|
|
123
|
+
{ name: "cli", },
|
|
121
124
|
{ name: "uv", },
|
|
122
125
|
])
|
|
123
126
|
let conda_requirements = [
|
package/kernel/environment.js
CHANGED
package/kernel/git.js
ADDED
|
@@ -0,0 +1,64 @@
|
|
|
1
|
+
const git = require('isomorphic-git')
|
|
2
|
+
const fs = require('fs')
|
|
3
|
+
const path = require('path')
|
|
4
|
+
const { glob, sync, hasMagic } = require('glob-gitignore')
|
|
5
|
+
const http = require('isomorphic-git/http/node')
|
|
6
|
+
const ini = require('ini')
|
|
7
|
+
class Git {
|
|
8
|
+
constructor(kernel) {
|
|
9
|
+
this.kernel = kernel
|
|
10
|
+
}
|
|
11
|
+
async repos (root) {
|
|
12
|
+
let _repos = await glob('**/.git/', {
|
|
13
|
+
cwd: root,
|
|
14
|
+
onlyDirectories: true,
|
|
15
|
+
dot: true,
|
|
16
|
+
ignore: ['**/node_modules/**', "**/venv/**"], // optional
|
|
17
|
+
});
|
|
18
|
+
|
|
19
|
+
let repos = []
|
|
20
|
+
for(let r of _repos) {
|
|
21
|
+
const gitPath = path.resolve(root, r)
|
|
22
|
+
const gitRelPath = path.relative(root, gitPath)
|
|
23
|
+
const gitParentPath = path.dirname(gitPath)
|
|
24
|
+
const gitParentRelPath = path.relative(this.kernel.path("api"), gitParentPath)
|
|
25
|
+
let dir = path.dirname(gitPath)
|
|
26
|
+
try {
|
|
27
|
+
let gitRemote = await git.getConfig({
|
|
28
|
+
fs,
|
|
29
|
+
http,
|
|
30
|
+
dir,
|
|
31
|
+
path: 'remote.origin.url'
|
|
32
|
+
})
|
|
33
|
+
repos.push({
|
|
34
|
+
gitPath,
|
|
35
|
+
gitRelPath,
|
|
36
|
+
gitParentPath,
|
|
37
|
+
gitParentRelPath,
|
|
38
|
+
dir,
|
|
39
|
+
url: gitRemote
|
|
40
|
+
})
|
|
41
|
+
} catch (e) {
|
|
42
|
+
repos.push({
|
|
43
|
+
gitPath,
|
|
44
|
+
gitRelPath,
|
|
45
|
+
gitParentPath,
|
|
46
|
+
gitParentRelPath,
|
|
47
|
+
dir,
|
|
48
|
+
})
|
|
49
|
+
}
|
|
50
|
+
}
|
|
51
|
+
return repos
|
|
52
|
+
}
|
|
53
|
+
async config (dir) {
|
|
54
|
+
try {
|
|
55
|
+
const gitConfigPath = path.resolve(dir, ".git/config")
|
|
56
|
+
const content = await fs.promises.readFile(gitConfigPath, 'utf-8');
|
|
57
|
+
const gitconfig = ini.parse(content);
|
|
58
|
+
return gitconfig
|
|
59
|
+
} catch (e) {
|
|
60
|
+
return null
|
|
61
|
+
}
|
|
62
|
+
}
|
|
63
|
+
}
|
|
64
|
+
module.exports = Git
|
package/kernel/index.js
CHANGED
|
@@ -35,6 +35,7 @@ const Plugin = require('./plugin')
|
|
|
35
35
|
const Router = require("./router")
|
|
36
36
|
const Procs = require('./procs')
|
|
37
37
|
const Peer = require('./peer')
|
|
38
|
+
const Git = require('./git')
|
|
38
39
|
const Connect = require('./connect')
|
|
39
40
|
const { DownloaderHelper } = require('node-downloader-helper');
|
|
40
41
|
const { ProxyAgent } = require('proxy-agent');
|
|
@@ -658,6 +659,7 @@ class Kernel {
|
|
|
658
659
|
this.kv = new KV(this)
|
|
659
660
|
this.cloudflare = new Cloudflare()
|
|
660
661
|
this.peer = new Peer()
|
|
662
|
+
this.git = new Git(this)
|
|
661
663
|
|
|
662
664
|
this.homedir = home
|
|
663
665
|
|
package/kernel/router/index.js
CHANGED
|
@@ -200,19 +200,21 @@ class Router {
|
|
|
200
200
|
this._mapping = {}
|
|
201
201
|
this.localhost_home_router.handle()
|
|
202
202
|
this.localhost_variable_router.handle(this.kernel.memory.local)
|
|
203
|
-
|
|
204
|
-
this.
|
|
205
|
-
|
|
206
|
-
|
|
207
|
-
|
|
208
|
-
let
|
|
209
|
-
|
|
210
|
-
this.
|
|
211
|
-
|
|
212
|
-
|
|
203
|
+
if (this.kernel.processes && this.kernel.processes.info) {
|
|
204
|
+
for(let proc of this.kernel.processes.info) {
|
|
205
|
+
this.localhost_port_router.handle(proc)
|
|
206
|
+
}
|
|
207
|
+
if (this.kernel.peer.active) {
|
|
208
|
+
for(let host in this.kernel.peer.info) {
|
|
209
|
+
let peer = this.kernel.peer.info[host]
|
|
210
|
+
if (peer.host === this.kernel.peer.host) {
|
|
211
|
+
this.peer_home_router.handle(peer)
|
|
212
|
+
this.peer_variable_router.handle(peer)
|
|
213
|
+
this.peer_port_router.handle(peer)
|
|
214
|
+
}
|
|
213
215
|
}
|
|
216
|
+
await this.fill()
|
|
214
217
|
}
|
|
215
|
-
await this.fill()
|
|
216
218
|
}
|
|
217
219
|
this.mapping = this._mapping
|
|
218
220
|
}
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
{
|
|
2
|
+
"run": [{
|
|
3
|
+
"method": "input",
|
|
4
|
+
"params": {
|
|
5
|
+
"form": [{
|
|
6
|
+
"key": "commit",
|
|
7
|
+
"title": "Commit message"
|
|
8
|
+
}]
|
|
9
|
+
}
|
|
10
|
+
}, {
|
|
11
|
+
"method": "shell.run",
|
|
12
|
+
"params": {
|
|
13
|
+
"chain": true,
|
|
14
|
+
"path": "{{args.cwd}}",
|
|
15
|
+
"message": [
|
|
16
|
+
"git add .",
|
|
17
|
+
"git commit -am {{input.commit}}"
|
|
18
|
+
]
|
|
19
|
+
}
|
|
20
|
+
}]
|
|
21
|
+
}
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
{
|
|
2
|
+
"run": [{
|
|
3
|
+
"method": "input",
|
|
4
|
+
"params": {
|
|
5
|
+
"form": [{
|
|
6
|
+
"key": "commit",
|
|
7
|
+
"title": "Commit message"
|
|
8
|
+
}]
|
|
9
|
+
}
|
|
10
|
+
}, {
|
|
11
|
+
"method": "shell.run",
|
|
12
|
+
"params": {
|
|
13
|
+
"chain": true,
|
|
14
|
+
"path": "{{args.cwd}}",
|
|
15
|
+
"message": [
|
|
16
|
+
"git add .",
|
|
17
|
+
"git commit -am {{input.commit}}",
|
|
18
|
+
"git push"
|
|
19
|
+
]
|
|
20
|
+
}
|
|
21
|
+
}]
|
|
22
|
+
}
|
package/kernel/shell.js
CHANGED
|
@@ -252,6 +252,7 @@ class Shell {
|
|
|
252
252
|
this.ondata({ raw: `\r\n████\r\n██ Starting Shell ${this.id}\r\n` })
|
|
253
253
|
|
|
254
254
|
|
|
255
|
+
this.start_time = Date.now()
|
|
255
256
|
this.params = params
|
|
256
257
|
|
|
257
258
|
// 3. path => path can be http, relative, absolute
|
|
@@ -969,8 +970,22 @@ class Shell {
|
|
|
969
970
|
this.done = false
|
|
970
971
|
this.ptyProcess = pty.spawn(this.shell, this.args, config)
|
|
971
972
|
this.ptyProcess.onData((data) => {
|
|
972
|
-
|
|
973
|
+
if (!this.monitor) {
|
|
974
|
+
this.monitor = ""
|
|
975
|
+
}
|
|
976
|
+
this.monitor = this.monitor + data
|
|
977
|
+
this.monitor = this.monitor.slice(-300) // last 300
|
|
973
978
|
if (!this.done) {
|
|
979
|
+
|
|
980
|
+
// "request cursor position" handling: https://github.com/microsoft/node-pty/issues/535
|
|
981
|
+
if (data.includes('\x1b[6n')) {
|
|
982
|
+
const row = this.vt.buffer.active.cursorY + 1;
|
|
983
|
+
const col = this.vt.buffer.active.cursorX + 1;
|
|
984
|
+
const response = `\x1b[${row};${col}R`;
|
|
985
|
+
this.ptyProcess.write(response);
|
|
986
|
+
data = data.replace(/\x1b\[6n/g, ''); // remove the code
|
|
987
|
+
}
|
|
988
|
+
|
|
974
989
|
this.queue.push(data)
|
|
975
990
|
}
|
|
976
991
|
});
|
|
@@ -1151,6 +1166,7 @@ ${cleaned}
|
|
|
1151
1166
|
raw: msg,
|
|
1152
1167
|
cleaned,
|
|
1153
1168
|
state: cleaned,
|
|
1169
|
+
buf,
|
|
1154
1170
|
shell_id: this.id
|
|
1155
1171
|
}
|
|
1156
1172
|
this.state = cleaned
|
package/kernel/shells.js
CHANGED
|
@@ -2,6 +2,7 @@ const os = require('os')
|
|
|
2
2
|
const _ = require('lodash')
|
|
3
3
|
const fs = require('fs')
|
|
4
4
|
const set = require("./api/set")
|
|
5
|
+
const Util = require('./util')
|
|
5
6
|
const {
|
|
6
7
|
glob
|
|
7
8
|
} = require('glob')
|
|
@@ -117,8 +118,16 @@ class Shells {
|
|
|
117
118
|
message,
|
|
118
119
|
on: [{
|
|
119
120
|
event: <regex>,
|
|
120
|
-
|
|
121
|
-
|
|
121
|
+
done: true|false,
|
|
122
|
+
kill: true|false,
|
|
123
|
+
debug: true|false,
|
|
124
|
+
notify: {
|
|
125
|
+
title,
|
|
126
|
+
sound,
|
|
127
|
+
message,
|
|
128
|
+
image
|
|
129
|
+
}
|
|
130
|
+
}]
|
|
122
131
|
}
|
|
123
132
|
}
|
|
124
133
|
*/
|
|
@@ -127,27 +136,43 @@ class Shells {
|
|
|
127
136
|
// regexify
|
|
128
137
|
//let matches = /^\/([^\/]+)\/([dgimsuy]*)$/.exec(handler.event)
|
|
129
138
|
if (handler.event) {
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
matches
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
let
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
if (handler.kill) {
|
|
145
|
-
m = rendered_event[0]
|
|
146
|
-
sh.kill()
|
|
139
|
+
if (handler.notify) {
|
|
140
|
+
// notify is a special case. check by line
|
|
141
|
+
let matches = /^\/(.+)\/([dgimsuy]*)$/gs.exec(handler.event)
|
|
142
|
+
if (!/g/.test(matches[2])) {
|
|
143
|
+
matches[2] += "g" // if g option is not included, include it (need it for matchAll)
|
|
144
|
+
}
|
|
145
|
+
let re = new RegExp(matches[1], matches[2])
|
|
146
|
+
let test = re.exec(sh.monitor)
|
|
147
|
+
if (test && test.length > 0) {
|
|
148
|
+
// reset monitor
|
|
149
|
+
sh.monitor = ""
|
|
150
|
+
let params = this.kernel.template.render(handler.notify, { event: test })
|
|
151
|
+
if (params.image) {
|
|
152
|
+
params.contentImage = path.resolve(req.cwd, params.image)
|
|
147
153
|
}
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
154
|
+
Util.push(params)
|
|
155
|
+
}
|
|
156
|
+
} else {
|
|
157
|
+
let matches = /^\/(.+)\/([dgimsuy]*)$/gs.exec(handler.event)
|
|
158
|
+
if (!/g/.test(matches[2])) {
|
|
159
|
+
matches[2] += "g" // if g option is not included, include it (need it for matchAll)
|
|
160
|
+
}
|
|
161
|
+
let re = new RegExp(matches[1], matches[2])
|
|
162
|
+
if (stream.cleaned) {
|
|
163
|
+
let line = stream.cleaned.replaceAll(/[\r\n]/g, "")
|
|
164
|
+
let rendered_event = [...line.matchAll(re)]
|
|
165
|
+
// 3. if the rendered expression is truthy, run the "run" script
|
|
166
|
+
if (rendered_event.length > 0) {
|
|
167
|
+
stream.matches = rendered_event
|
|
168
|
+
if (handler.kill) {
|
|
169
|
+
m = rendered_event[0]
|
|
170
|
+
sh.kill()
|
|
171
|
+
}
|
|
172
|
+
if (handler.done) {
|
|
173
|
+
m = rendered_event[0]
|
|
174
|
+
sh.continue()
|
|
175
|
+
}
|
|
151
176
|
}
|
|
152
177
|
}
|
|
153
178
|
}
|