cap-copilot-widget 0.1.7 → 0.1.9

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.
Files changed (2) hide show
  1. package/package.json +1 -1
  2. package/postinstall.js +72 -95
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "cap-copilot-widget",
3
- "version": "0.1.7",
3
+ "version": "0.1.9",
4
4
  "description": "BTP Copilot floating chat widget — Web Component (iframe launcher)",
5
5
  "main": "dist/btp-copilot.js",
6
6
  "module": "dist/btp-copilot.esm.js",
package/postinstall.js CHANGED
@@ -23,116 +23,93 @@ function findAppRoot() {
23
23
  const appRoot = findAppRoot();
24
24
  if (!appRoot) process.exit(0);
25
25
 
26
- const HTML_CANDIDATES = [
27
- "index.html",
28
- "app/index.html",
29
- "public/index.html",
30
- "webapp/index.html",
31
- "src/index.html",
32
- ];
33
-
34
- let htmlPath = null;
35
- for (const rel of HTML_CANDIDATES) {
36
- const candidate = path.join(appRoot, rel);
37
- if (fs.existsSync(candidate)) {
38
- htmlPath = candidate;
39
- break;
40
- }
41
- }
42
-
43
- if (!htmlPath) {
44
- try {
45
- const appDir = path.join(appRoot, "app");
46
- if (fs.existsSync(appDir)) {
47
- for (const entry of fs.readdirSync(appDir, { withFileTypes: true })) {
48
- if (!entry.isDirectory()) continue;
49
- const candidate = path.join(appDir, entry.name, "webapp", "index.html");
50
- if (fs.existsSync(candidate)) {
51
- htmlPath = candidate;
52
- break;
53
- }
54
- }
55
- }
56
- } catch { /* ignore */ }
57
- }
58
-
59
- if (!htmlPath) {
60
- process.exit(0);
61
- }
62
26
 
63
- const staticDir = path.dirname(htmlPath);
64
-
65
- const bundleSrc = path.join(__dirname, "dist", "btp-copilot.js");
66
- const bundleDest = path.join(staticDir, "btp-copilot.js");
67
-
68
- if (!fs.existsSync(bundleSrc)) {
69
- console.warn("\x1b[33m[cap-copilot-widget]\x1b[0m Warning: dist/btp-copilot.js not found — run `npm run build` in the widget package first.");
70
- process.exit(0);
71
- }
27
+ const htmlPaths = [];
72
28
 
29
+ const appDir = path.join(appRoot, "app");
73
30
  try {
74
- fs.copyFileSync(bundleSrc, bundleDest);
75
- } catch (e) {
76
- console.warn(`\x1b[33m[cap-copilot-widget]\x1b[0m Warning: Could not copy bundle to ${path.relative(appRoot, bundleDest)}: ${e.message}`);
77
- process.exit(0);
78
- }
79
-
80
- let html;
81
- try {
82
- html = fs.readFileSync(htmlPath, "utf8");
83
- } catch (e) {
84
- console.warn(`\x1b[33m[cap-copilot-widget]\x1b[0m Warning: Could not read ${path.relative(appRoot, htmlPath)}: ${e.message}`);
85
- process.exit(0);
86
- }
31
+ if (fs.existsSync(appDir)) {
32
+ for (const entry of fs.readdirSync(appDir, { withFileTypes: true })) {
33
+ if (!entry.isDirectory()) continue;
34
+ const candidate = path.join(appDir, entry.name, "webapp", "index.html");
35
+ if (fs.existsSync(candidate)) htmlPaths.push(candidate);
36
+ }
37
+ }
38
+ } catch { /* ignore */ }
87
39
 
88
- const alreadyHasScript = html.includes("btp-copilot.js");
89
- const alreadyHasElement = html.includes("<btp-copilot");
90
40
 
91
- if (alreadyHasScript && alreadyHasElement) {
92
- console.log(`\x1b[36m[cap-copilot-widget]\x1b[0m \u2714 Widget bundle updated in ${path.relative(appRoot, bundleDest)}`);
93
- process.exit(0);
41
+ if (htmlPaths.length === 0) {
42
+ for (const rel of ["webapp/index.html", "public/index.html", "src/index.html", "index.html"]) {
43
+ const candidate = path.join(appRoot, rel);
44
+ if (fs.existsSync(candidate)) { htmlPaths.push(candidate); break; }
45
+ }
94
46
  }
95
47
 
48
+ if (htmlPaths.length === 0) process.exit(0);
49
+
96
50
  let appId = "my-app";
97
51
  let appName = "My App";
98
52
  try {
99
53
  const pkg = JSON.parse(fs.readFileSync(path.join(appRoot, "package.json"), "utf8"));
100
- appId = (pkg.name ?? "my-app").replace(/[^a-zA-Z0-9_-]/g, "-");
101
- appName = pkg.description ?? pkg.name ?? "My App";
54
+ const cdsSection = pkg.cds ?? {};
55
+ const btpCfg = cdsSection.requires?.["btp-copilot"] ?? {};
56
+ appId = btpCfg.appId ?? (pkg.name ?? "my-app").replace(/[^a-zA-Z0-9_-]/g, "-");
57
+ appName = btpCfg.appName ?? pkg.description ?? pkg.name ?? "My App";
102
58
  } catch { /* ignore */ }
103
59
 
104
- if (!alreadyHasScript) {
105
60
 
106
- const scriptTag =
107
- ` <!-- injected by cap-copilot-widget -->\n` +
108
- ` <script src="btp-copilot.js" defer></script>`;
109
- html = html.replace("</head>", `${scriptTag}\n</head>`);
110
- }
61
+ const SCRIPT_SRC = "/__btp-copilot-widget/btp-copilot.js";
62
+
63
+ const scriptTag = [
64
+ ` <!-- injected by cap-copilot-widget -->`,
65
+ ` <script src="${SCRIPT_SRC}" defer></script>`,
66
+ ].join("\n");
111
67
 
112
- if (!alreadyHasElement) {
113
-
114
- const widgetElement = [
115
- ` <!-- injected by cap-copilot-widget -->`,
116
- ` <btp-copilot`,
117
- ` app-id="${appId}"`,
118
- ` app-name="${appName}"`,
119
- ` position="bottom-right">`,
120
- ` </btp-copilot>`,
121
- ].join("\n");
122
-
123
- if (html.includes("</body>")) {
124
- html = html.replace("</body>", `${widgetElement}\n</body>`);
125
- } else {
126
- html += `\n${widgetElement}\n`;
68
+ const widgetElement = [
69
+ ` <!-- injected by cap-copilot-widget -->`,
70
+ ` <btp-copilot`,
71
+ ` app-id="${appId}"`,
72
+ ` app-name="${appName}"`,
73
+ ` position="bottom-right">`,
74
+ ` </btp-copilot>`,
75
+ ].join("\n");
76
+
77
+ for (const htmlPath of htmlPaths) {
78
+ let html;
79
+ try {
80
+ html = fs.readFileSync(htmlPath, "utf8");
81
+ } catch (e) {
82
+ console.warn(`\x1b[33m[cap-copilot-widget]\x1b[0m Warning: Could not read ${path.relative(appRoot, htmlPath)}: ${e.message}`);
83
+ continue;
127
84
  }
128
- }
129
85
 
130
- try {
131
- fs.writeFileSync(htmlPath, html, "utf8");
132
- console.log(`\x1b[36m[cap-copilot-widget]\x1b[0m \u2714 Copied widget bundle \u2192 ${path.relative(appRoot, bundleDest)}`);
133
- console.log(`\x1b[36m[cap-copilot-widget]\x1b[0m \u2714 Injected <btp-copilot> into ${path.relative(appRoot, htmlPath)}`);
134
- console.log(`\x1b[36m[cap-copilot-widget]\x1b[0m URLs are auto-configured from the CDS plugin (/__btp-copilot/config).`);
135
- console.log(`\x1b[36m[cap-copilot-widget]\x1b[0m Override: add iframe-url and/or backend-url attributes to <btp-copilot> if needed.`);
136
- } catch (e) {
137
- console.warn(`\x1b[33m[cap-copilot-widget]\x1b[0m Warning: Could not write ${path.relative(appRoot, htmlPath)}: ${e.message}`);
86
+ const alreadyHasScript = html.includes(SCRIPT_SRC) || html.includes("btp-copilot-widget");
87
+ const alreadyHasElement = html.includes("<btp-copilot");
88
+
89
+ if (alreadyHasScript && alreadyHasElement) {
90
+ console.log(`\x1b[36m[cap-copilot-widget]\x1b[0m \u2714 Already configured: ${path.relative(appRoot, htmlPath)}`);
91
+ continue;
92
+ }
93
+
94
+ if (!alreadyHasScript) {
95
+ html = html.replace("</head>", `${scriptTag}\n</head>`);
96
+ }
97
+
98
+ if (!alreadyHasElement) {
99
+ if (html.includes("</body>")) {
100
+ html = html.replace("</body>", `${widgetElement}\n</body>`);
101
+ } else {
102
+ html += `\n${widgetElement}\n`;
103
+ }
104
+ }
105
+
106
+ try {
107
+ fs.writeFileSync(htmlPath, html, "utf8");
108
+ console.log(`\x1b[36m[cap-copilot-widget]\x1b[0m \u2714 Injected <btp-copilot> into ${path.relative(appRoot, htmlPath)}`);
109
+ } catch (e) {
110
+ console.warn(`\x1b[33m[cap-copilot-widget]\x1b[0m Warning: Could not write ${path.relative(appRoot, htmlPath)}: ${e.message}`);
111
+ }
138
112
  }
113
+
114
+ console.log(`\x1b[36m[cap-copilot-widget]\x1b[0m Widget JS served by CAP at ${SCRIPT_SRC} (no file copies needed).`);
115
+ console.log(`\x1b[36m[cap-copilot-widget]\x1b[0m URLs are auto-configured from the CDS plugin (/__btp-copilot/config).`);