chopratejas commited on
Commit
fb4eade
·
2 Parent(s): 0a80b5286d3d6d

Merge pull request #106 from JerrettDavis/fix/openclaw-local-install-hook

Browse files
plugins/openclaw/README.md CHANGED
@@ -21,23 +21,40 @@ This plugin can auto-start a local `headroom proxy` when needed. OpenClaw treats
21
 
22
  ## Local Development Install (Detection-Friendly)
23
 
24
- If you are testing from this repo, run npm install/build from the plugin directory so local launcher detection aligns with runtime paths:
25
 
26
  ```bash
27
  cd plugins/openclaw
28
  npm install
29
  npm run build
30
  openclaw plugins install --dangerously-force-unsafe-install --link .
 
 
 
 
 
 
 
 
 
 
 
 
 
 
31
  ```
32
 
33
  Why this matters:
34
  - The plugin checks launchers in this order: PATH -> local npm bin -> global npm -> python.
35
- - "local npm bin" means `plugins/openclaw/node_modules/.bin/headroom` relative to the installed plugin root.
36
- - Using `--link .` from `plugins/openclaw` keeps that local path aligned for detection.
 
37
  - If you install from a `.tgz`, local npm bin may not exist in the installed extension and detection will fall back to PATH/global/python.
38
 
39
  ## Configure
40
 
 
 
41
  ```json
42
  {
43
  "plugins": {
 
21
 
22
  ## Local Development Install (Detection-Friendly)
23
 
24
+ If you are testing from this repo, run npm install/build from the plugin directory so local launcher detection aligns with runtime paths. These linked installs are supported:
25
 
26
  ```bash
27
  cd plugins/openclaw
28
  npm install
29
  npm run build
30
  openclaw plugins install --dangerously-force-unsafe-install --link .
31
+ openclaw plugins install --dangerously-force-unsafe-install --link dist
32
+ ```
33
+
34
+ From the repo root, install the plugin directory explicitly:
35
+
36
+ ```bash
37
+ openclaw plugins install --dangerously-force-unsafe-install --link ./plugins/openclaw
38
+ ```
39
+
40
+ Or, from inside `dist/`:
41
+
42
+ ```bash
43
+ cd plugins/openclaw/dist
44
+ openclaw plugins install --dangerously-force-unsafe-install --link .
45
  ```
46
 
47
  Why this matters:
48
  - The plugin checks launchers in this order: PATH -> local npm bin -> global npm -> python.
49
+ - "local npm bin" means `plugins/openclaw/node_modules/.bin/headroom` relative to the source checkout.
50
+ - Using `--link dist` (or `--link .` from `dist/`) still keeps runtime code adjacent to the checkout, and launcher detection falls back to PATH/global/python if a local npm bin is not present under the installed root.
51
+ - `plugins/openclaw` also carries a no-op hook shim so OpenClaw's hook-pack fallback treats the path as valid instead of emitting a misleading `package.json missing openclaw.hooks` warning.
52
  - If you install from a `.tgz`, local npm bin may not exist in the installed extension and detection will fall back to PATH/global/python.
53
 
54
  ## Configure
55
 
56
+ Install automatically selects the `contextEngine` slot for `headroom` on current OpenClaw releases. If you need to switch back manually, set `plugins.slots.contextEngine` to `"legacy"` or another engine id.
57
+
58
  ```json
59
  {
60
  "plugins": {
plugins/openclaw/hook-shim/HOOK.md ADDED
@@ -0,0 +1,21 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ ---
2
+ name: headroom-link-shim
3
+ description: "No-op hook shim so local plugin source paths are also valid OpenClaw hook-pack paths."
4
+ metadata:
5
+ {
6
+ "openclaw":
7
+ {
8
+ "emoji": "🪝",
9
+ "events": ["command"],
10
+ },
11
+ }
12
+ ---
13
+
14
+ # Headroom Link Shim
15
+
16
+ This hook intentionally does nothing.
17
+
18
+ OpenClaw currently falls back to validating local plugin paths as hook packs when a
19
+ plugin install cannot proceed, such as when the plugin is already installed.
20
+ Including this no-op hook keeps `--link` installs from reporting a misleading
21
+ `package.json missing openclaw.hooks` error for valid Headroom plugin paths.
plugins/openclaw/hook-shim/handler.js ADDED
@@ -0,0 +1,3 @@
 
 
 
 
1
+ export default async function headroomLinkShim() {
2
+ return undefined;
3
+ }
plugins/openclaw/openclaw.plugin.json CHANGED
@@ -1,5 +1,6 @@
1
  {
2
  "id": "headroom",
 
3
  "uiHints": {
4
  "proxyUrl": {
5
  "label": "Proxy URL",
 
1
  {
2
  "id": "headroom",
3
+ "kind": "context-engine",
4
  "uiHints": {
5
  "proxyUrl": {
6
  "label": "Proxy URL",
plugins/openclaw/package.json CHANGED
@@ -7,11 +7,12 @@
7
  "types": "./dist/index.d.ts",
8
  "files": [
9
  "dist",
 
10
  "openclaw.plugin.json",
11
  "README.md"
12
  ],
13
  "scripts": {
14
- "build": "tsup",
15
  "test": "vitest run",
16
  "test:watch": "vitest",
17
  "typecheck": "tsc --noEmit"
@@ -34,12 +35,9 @@
34
  "vitest": "^2.0.0"
35
  },
36
  "openclaw": {
37
- "hooks": {
38
- "contextEngine": "dist/index.js",
39
- "tools": [
40
- "dist/index.js"
41
- ]
42
- },
43
  "extensions": [
44
  "./dist/index.js"
45
  ],
 
7
  "types": "./dist/index.d.ts",
8
  "files": [
9
  "dist",
10
+ "hook-shim",
11
  "openclaw.plugin.json",
12
  "README.md"
13
  ],
14
  "scripts": {
15
+ "build": "tsup && node prepare-dist.mjs",
16
  "test": "vitest run",
17
  "test:watch": "vitest",
18
  "typecheck": "tsc --noEmit"
 
35
  "vitest": "^2.0.0"
36
  },
37
  "openclaw": {
38
+ "hooks": [
39
+ "./hook-shim"
40
+ ],
 
 
 
41
  "extensions": [
42
  "./dist/index.js"
43
  ],
plugins/openclaw/prepare-dist.mjs ADDED
@@ -0,0 +1,56 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ import fs from "node:fs/promises";
2
+ import path from "node:path";
3
+ import { fileURLToPath } from "node:url";
4
+
5
+ const __dirname = path.dirname(fileURLToPath(import.meta.url));
6
+ const rootDir = __dirname;
7
+ const distDir = path.join(rootDir, "dist");
8
+
9
+ const rootPackage = JSON.parse(
10
+ await fs.readFile(path.join(rootDir, "package.json"), "utf8"),
11
+ );
12
+
13
+ const distPackage = {
14
+ name: rootPackage.name,
15
+ version: rootPackage.version,
16
+ description: rootPackage.description,
17
+ type: rootPackage.type,
18
+ main: "./index.js",
19
+ types: "./index.d.ts",
20
+ license: rootPackage.license,
21
+ dependencies: rootPackage.dependencies,
22
+ peerDependencies: rootPackage.peerDependencies,
23
+ peerDependenciesMeta: rootPackage.peerDependenciesMeta,
24
+ openclaw: {
25
+ hooks: ["./hook-shim"],
26
+ extensions: ["./index.js"],
27
+ capabilities: rootPackage.openclaw?.capabilities ?? {},
28
+ },
29
+ };
30
+
31
+ await fs.mkdir(distDir, { recursive: true });
32
+ await fs.writeFile(
33
+ path.join(distDir, "package.json"),
34
+ `${JSON.stringify(distPackage, null, 2)}\n`,
35
+ "utf8",
36
+ );
37
+
38
+ await Promise.all([
39
+ fs.copyFile(
40
+ path.join(rootDir, "openclaw.plugin.json"),
41
+ path.join(distDir, "openclaw.plugin.json"),
42
+ ),
43
+ fs.copyFile(path.join(rootDir, "README.md"), path.join(distDir, "README.md")),
44
+ fs.mkdir(path.join(distDir, "hook-shim"), { recursive: true }),
45
+ ]);
46
+
47
+ await Promise.all([
48
+ fs.copyFile(
49
+ path.join(rootDir, "hook-shim", "HOOK.md"),
50
+ path.join(distDir, "hook-shim", "HOOK.md"),
51
+ ),
52
+ fs.copyFile(
53
+ path.join(rootDir, "hook-shim", "handler.js"),
54
+ path.join(distDir, "hook-shim", "handler.js"),
55
+ ),
56
+ ]);