onecontext-ai 0.7.10

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/README.md ADDED
@@ -0,0 +1,65 @@
1
+ # onecontext-ai
2
+
3
+ npm wrapper for [OneContext AI](https://pypi.org/project/aline-ai/) (the `aline-ai` Python package).
4
+
5
+ ## Installation
6
+
7
+ ```bash
8
+ npm install -g onecontext-ai
9
+ ```
10
+
11
+ This will automatically install the latest `aline-ai` Python package using the best available Python package manager (`uv` > `pipx` > `pip3` > `pip`).
12
+
13
+ ### Prerequisites
14
+
15
+ - Node.js >= 16
16
+ - Python 3.8+ with one of: `uv`, `pipx`, `pip3`, or `pip`
17
+
18
+ ## Usage
19
+
20
+ After installation, the following commands are available:
21
+
22
+ ```bash
23
+ onecontext-ai <command> [args...]
24
+ onecontext <command> [args...]
25
+ oc <command> [args...]
26
+ ```
27
+
28
+ All three commands are equivalent and proxy to the underlying Python CLI.
29
+
30
+ ### Examples
31
+
32
+ ```bash
33
+ # Check version
34
+ onecontext version
35
+
36
+ # Show help
37
+ onecontext --help
38
+
39
+ # Short alias
40
+ oc version
41
+ ```
42
+
43
+ ## Updating the Python Package
44
+
45
+ The npm wrapper installs the latest `aline-ai` on `npm install`. To update the Python package independently:
46
+
47
+ ```bash
48
+ # Using pip
49
+ pip install --upgrade aline-ai
50
+
51
+ # Or rebuild the npm package to re-trigger postinstall
52
+ npm rebuild onecontext-ai
53
+ ```
54
+
55
+ ## Troubleshooting
56
+
57
+ If the commands aren't found after installation:
58
+
59
+ 1. Ensure the Python package is installed: `pip install aline-ai`
60
+ 2. Rebuild to re-discover paths: `npm rebuild onecontext-ai`
61
+ 3. Check that `onecontext` is on your PATH: `which onecontext`
62
+
63
+ ## License
64
+
65
+ MIT
package/bin/default.js ADDED
@@ -0,0 +1,4 @@
1
+ #!/usr/bin/env node
2
+ "use strict";
3
+ const { run } = require("../run.js");
4
+ run("onecontext");
package/bin/oc.js ADDED
@@ -0,0 +1,4 @@
1
+ #!/usr/bin/env node
2
+ "use strict";
3
+ const { run } = require("../run.js");
4
+ run("oc");
@@ -0,0 +1,4 @@
1
+ #!/usr/bin/env node
2
+ "use strict";
3
+ const { run } = require("../run.js");
4
+ run("onecontext");
package/package.json ADDED
@@ -0,0 +1,33 @@
1
+ {
2
+ "name": "onecontext-ai",
3
+ "version": "0.7.10",
4
+ "description": "OneContext AI - npm wrapper for the aline-ai Python package",
5
+ "bin": {
6
+ "onecontext-ai": "./bin/default.js",
7
+ "onecontext": "./bin/onecontext.js",
8
+ "oc": "./bin/oc.js"
9
+ },
10
+ "scripts": {
11
+ "postinstall": "node postinstall.js"
12
+ },
13
+ "engines": {
14
+ "node": ">=16"
15
+ },
16
+ "files": [
17
+ "bin/",
18
+ "postinstall.js",
19
+ "run.js",
20
+ "README.md"
21
+ ],
22
+ "keywords": [
23
+ "onecontext",
24
+ "aline",
25
+ "ai",
26
+ "cli"
27
+ ],
28
+ "license": "MIT",
29
+ "repository": {
30
+ "type": "git",
31
+ "url": "https://github.com/Loke-60000/ReAlign"
32
+ }
33
+ }
package/postinstall.js ADDED
@@ -0,0 +1,140 @@
1
+ #!/usr/bin/env node
2
+ "use strict";
3
+
4
+ const { execSync, execFileSync } = require("child_process");
5
+ const fs = require("fs");
6
+ const path = require("path");
7
+
8
+ const PACKAGE = "aline-ai";
9
+ const COMMANDS = ["onecontext", "oc"];
10
+ const PATHS_FILE = path.join(__dirname, ".paths.json");
11
+
12
+ function log(msg) {
13
+ console.log(`[onecontext-ai] ${msg}`);
14
+ }
15
+
16
+ function warn(msg) {
17
+ console.warn(`[onecontext-ai] WARNING: ${msg}`);
18
+ }
19
+
20
+ // Detect available Python package manager: uv > pipx > pip3 > pip
21
+ function detectPkgManager() {
22
+ const candidates = ["uv", "pipx", "pip3", "pip"];
23
+ for (const cmd of candidates) {
24
+ try {
25
+ execFileSync(cmd, ["--version"], { stdio: "ignore" });
26
+ return cmd;
27
+ } catch {
28
+ // not found, try next
29
+ }
30
+ }
31
+ return null;
32
+ }
33
+
34
+ // Build install args for the given package manager
35
+ function installArgs(mgr) {
36
+ switch (mgr) {
37
+ case "uv":
38
+ return [["uv", "tool", "install", PACKAGE], ["uv", "tool", "install", "--force", PACKAGE]];
39
+ case "pipx":
40
+ return [["pipx", "install", PACKAGE], ["pipx", "install", "--force", PACKAGE]];
41
+ case "pip3":
42
+ return [["pip3", "install", PACKAGE], ["pip3", "install", "--upgrade", PACKAGE]];
43
+ case "pip":
44
+ return [["pip", "install", PACKAGE], ["pip", "install", "--upgrade", PACKAGE]];
45
+ default:
46
+ return [];
47
+ }
48
+ }
49
+
50
+ // Run install, retry with force/upgrade on failure
51
+ function install(mgr) {
52
+ const [primary, fallback] = installArgs(mgr);
53
+ log(`Installing ${PACKAGE} via ${mgr}...`);
54
+ try {
55
+ execFileSync(primary[0], primary.slice(1), { stdio: "inherit" });
56
+ return true;
57
+ } catch {
58
+ log(`Retrying with ${fallback.slice(-1)[0]}...`);
59
+ try {
60
+ execFileSync(fallback[0], fallback.slice(1), { stdio: "inherit" });
61
+ return true;
62
+ } catch {
63
+ return false;
64
+ }
65
+ }
66
+ }
67
+
68
+ // Get npm global/local bin directories to exclude from search (avoid recursion)
69
+ function npmBinDirs() {
70
+ const dirs = new Set();
71
+ try {
72
+ dirs.add(execSync("npm bin -g", { encoding: "utf8" }).trim());
73
+ } catch { /* ignore */ }
74
+ try {
75
+ dirs.add(execSync("npm bin", { encoding: "utf8" }).trim());
76
+ } catch { /* ignore */ }
77
+ // Also add the directory where this package's bins will be linked
78
+ try {
79
+ dirs.add(execSync("npm prefix -g", { encoding: "utf8" }).trim() + "/bin");
80
+ } catch { /* ignore */ }
81
+ return dirs;
82
+ }
83
+
84
+ // Discover absolute path for a command, filtering out npm bin directories
85
+ function discoverPath(cmd, excludeDirs) {
86
+ const whichCmd = process.platform === "win32" ? "where" : "which";
87
+ const whichArgs = process.platform === "win32" ? [cmd] : ["-a", cmd];
88
+ try {
89
+ const output = execFileSync(whichCmd, whichArgs, { encoding: "utf8" });
90
+ const paths = output.split(/\r?\n/).map((p) => p.trim()).filter(Boolean);
91
+ for (const p of paths) {
92
+ const dir = path.dirname(p);
93
+ let skip = false;
94
+ for (const excl of excludeDirs) {
95
+ if (dir === excl || p.startsWith(excl + path.sep)) {
96
+ skip = true;
97
+ break;
98
+ }
99
+ }
100
+ if (!skip) return p;
101
+ }
102
+ } catch {
103
+ // command not found
104
+ }
105
+ return null;
106
+ }
107
+
108
+ function main() {
109
+ const mgr = detectPkgManager();
110
+ if (!mgr) {
111
+ warn("No Python package manager found (uv, pipx, pip3, pip).");
112
+ warn(`Please install ${PACKAGE} manually and re-run: npm rebuild onecontext-ai`);
113
+ fs.writeFileSync(PATHS_FILE, JSON.stringify({}, null, 2));
114
+ return; // don't exit(1) — report error at runtime instead
115
+ }
116
+
117
+ const ok = install(mgr);
118
+ if (!ok) {
119
+ warn(`Failed to install ${PACKAGE} via ${mgr}.`);
120
+ warn(`Please install ${PACKAGE} manually and re-run: npm rebuild onecontext-ai`);
121
+ }
122
+
123
+ // Discover command paths
124
+ const excludeDirs = npmBinDirs();
125
+ const paths = {};
126
+ for (const cmd of COMMANDS) {
127
+ const resolved = discoverPath(cmd, excludeDirs);
128
+ if (resolved) {
129
+ paths[cmd] = resolved;
130
+ log(`Found ${cmd} at ${resolved}`);
131
+ } else {
132
+ warn(`Could not find ${cmd} in PATH`);
133
+ }
134
+ }
135
+
136
+ fs.writeFileSync(PATHS_FILE, JSON.stringify(paths, null, 2));
137
+ log("Installation complete.");
138
+ }
139
+
140
+ main();
package/run.js ADDED
@@ -0,0 +1,101 @@
1
+ #!/usr/bin/env node
2
+ "use strict";
3
+
4
+ const { spawn, execFileSync } = require("child_process");
5
+ const fs = require("fs");
6
+ const path = require("path");
7
+
8
+ const PATHS_FILE = path.join(__dirname, ".paths.json");
9
+
10
+ // Get npm bin directories to exclude (avoid recursion)
11
+ function npmBinDirs() {
12
+ const dirs = new Set();
13
+ try {
14
+ dirs.add(require("child_process").execSync("npm bin -g", { encoding: "utf8" }).trim());
15
+ } catch { /* ignore */ }
16
+ try {
17
+ dirs.add(require("child_process").execSync("npm bin", { encoding: "utf8" }).trim());
18
+ } catch { /* ignore */ }
19
+ try {
20
+ dirs.add(require("child_process").execSync("npm prefix -g", { encoding: "utf8" }).trim() + "/bin");
21
+ } catch { /* ignore */ }
22
+ return dirs;
23
+ }
24
+
25
+ // Fallback: search PATH for command, excluding npm bin dirs
26
+ function searchPath(cmd) {
27
+ const whichCmd = process.platform === "win32" ? "where" : "which";
28
+ const whichArgs = process.platform === "win32" ? [cmd] : ["-a", cmd];
29
+ const excludeDirs = npmBinDirs();
30
+ try {
31
+ const output = execFileSync(whichCmd, whichArgs, { encoding: "utf8" });
32
+ const paths = output.split(/\r?\n/).map((p) => p.trim()).filter(Boolean);
33
+ for (const p of paths) {
34
+ const dir = path.dirname(p);
35
+ let skip = false;
36
+ for (const excl of excludeDirs) {
37
+ if (dir === excl || p.startsWith(excl + path.sep)) {
38
+ skip = true;
39
+ break;
40
+ }
41
+ }
42
+ if (!skip) return p;
43
+ }
44
+ } catch {
45
+ // not found
46
+ }
47
+ return null;
48
+ }
49
+
50
+ function resolve(cmd) {
51
+ // 1. Try .paths.json
52
+ if (fs.existsSync(PATHS_FILE)) {
53
+ try {
54
+ const data = JSON.parse(fs.readFileSync(PATHS_FILE, "utf8"));
55
+ if (data[cmd]) return data[cmd];
56
+ } catch {
57
+ // corrupted file, fall through
58
+ }
59
+ }
60
+
61
+ // 2. Fallback: search PATH
62
+ const found = searchPath(cmd);
63
+ if (found) return found;
64
+
65
+ // 3. Not found
66
+ console.error(
67
+ `[onecontext-ai] ERROR: Could not find "${cmd}" command.\n` +
68
+ `Please install the Python package first:\n` +
69
+ ` pip install aline-ai\n` +
70
+ `Then re-run: npm rebuild onecontext-ai`
71
+ );
72
+ process.exit(1);
73
+ }
74
+
75
+ function run(cmd) {
76
+ const binPath = resolve(cmd);
77
+ const args = process.argv.slice(2);
78
+ const child = spawn(binPath, args, { stdio: "inherit" });
79
+
80
+ // Forward signals to child process
81
+ for (const sig of ["SIGINT", "SIGTERM", "SIGHUP"]) {
82
+ process.on(sig, () => {
83
+ child.kill(sig);
84
+ });
85
+ }
86
+
87
+ child.on("error", (err) => {
88
+ console.error(`[onecontext-ai] Failed to start ${cmd}: ${err.message}`);
89
+ process.exit(1);
90
+ });
91
+
92
+ child.on("exit", (code, signal) => {
93
+ if (signal) {
94
+ process.kill(process.pid, signal);
95
+ } else {
96
+ process.exit(code ?? 1);
97
+ }
98
+ });
99
+ }
100
+
101
+ module.exports = { run };