@saptools/cf-live-trace 0.1.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/LICENSE ADDED
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2026 Dong Tran
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
package/README.md ADDED
@@ -0,0 +1,219 @@
1
+ <div align="center">
2
+
3
+ # `@saptools/cf-live-trace`
4
+
5
+ **Inject a bounded HTTP trace hook into a running SAP BTP Cloud Foundry Node.js app and stream request/response events from the CLI.**
6
+
7
+ [![npm version](https://img.shields.io/npm/v/@saptools/cf-live-trace.svg?style=flat&color=CB3837&logo=npm)](https://www.npmjs.com/package/@saptools/cf-live-trace)
8
+ [![license](https://img.shields.io/npm/l/@saptools/cf-live-trace.svg?style=flat&color=blue)](./LICENSE)
9
+ [![node](https://img.shields.io/node/v/@saptools/cf-live-trace.svg?style=flat&color=339933&logo=node.js&logoColor=white)](https://nodejs.org)
10
+ [![types](https://img.shields.io/npm/types/@saptools/cf-live-trace.svg?style=flat&color=3178C6&logo=typescript&logoColor=white)](https://www.typescriptlang.org)
11
+
12
+ [Install](#install) - [Quick Start](#quick-start) - [CLI](#cli) - [API](#programmatic-usage) - [Security](#security-notes)
13
+
14
+ </div>
15
+
16
+ ---
17
+
18
+ ## Features
19
+
20
+ - Runtime HTTP tracing for Node.js apps already running on Cloud Foundry.
21
+ - Automatic CF session setup, SSH enablement check, Node inspector startup, and SSH port forwarding.
22
+ - CDP-based JavaScript injection derived from the SAP Tools VS Code Live Trace flow.
23
+ - Request and response header capture, body previews, status, duration, byte counts, correlation id, and bounded queue drops.
24
+ - `ndjson`, human summary, and final JSON output modes for scripts and agents.
25
+ - Strict TypeScript, ESLint, unit coverage, and fake-backed E2E tests without live SAP access.
26
+
27
+ ---
28
+
29
+ ## Install
30
+
31
+ ```bash
32
+ npm install -g @saptools/cf-live-trace
33
+
34
+ # or as a library
35
+ npm install @saptools/cf-live-trace
36
+ ```
37
+
38
+ Requires Node.js >= 20 and the official `cf` CLI on `PATH`.
39
+
40
+ The target Cloud Foundry app must be a Node.js process where `cf ssh` can reach `127.0.0.1:9229` after Node inspector startup. If SSH is disabled, the CLI enables SSH and restarts the app before opening the tunnel.
41
+
42
+ ---
43
+
44
+ ## Quick Start
45
+
46
+ ```bash
47
+ export SAP_EMAIL="sample@example.com"
48
+ export SAP_PASSWORD="<password>"
49
+
50
+ cf-live-trace \
51
+ --region ap10 \
52
+ --org sample-org \
53
+ --space dev \
54
+ --app orders-api \
55
+ --instance 0 \
56
+ --format ndjson
57
+ ```
58
+
59
+ If you already know the CF API endpoint, replace `--region ap10` with `--api-endpoint https://api.cf.ap10.hana.ondemand.com`.
60
+
61
+ By default the command streams one JSON object per captured HTTP request and runs until `Ctrl+C`.
62
+
63
+ ```json
64
+ {"id":"1","method":"POST","normalizedUrl":"/orders","status":201,"durationMs":24}
65
+ ```
66
+
67
+ ---
68
+
69
+ ## CLI
70
+
71
+ ```bash
72
+ cf-live-trace --help
73
+ ```
74
+
75
+ Targeting flags:
76
+
77
+ | Flag | Description |
78
+ | --- | --- |
79
+ | `--region <key>` | CF region key resolved through `@saptools/cf-sync` |
80
+ | `--api-endpoint <url>` | Explicit CF API endpoint instead of a region key |
81
+ | `--org <name>` | CF org name |
82
+ | `--space <name>` | CF space name |
83
+ | `--app <name>` | CF app name |
84
+ | `--instance <index>` | CF app instance index, default `0` |
85
+ | `--email <value>` | Override `SAP_EMAIL` |
86
+ | `--password <value>` | Override `SAP_PASSWORD` |
87
+ | `--cf-home <dir>` | Reuse an existing CF home instead of a temporary one |
88
+ | `--cf-command <path>` | CF CLI executable or test shim |
89
+
90
+ Trace flags:
91
+
92
+ | Flag | Description |
93
+ | --- | --- |
94
+ | `--duration <seconds>` | Stop after N seconds |
95
+ | `--max-events <count>` | Stop after N captured trace events |
96
+ | `--max-body-bytes <bytes>` | Maximum request/response preview bytes, default `4096`; `0` keeps unlimited local previews |
97
+ | `--no-capture-headers` | Do not capture request/response headers |
98
+ | `--no-capture-request-body` | Do not capture request body previews |
99
+ | `--no-capture-response-body` | Do not capture response body previews |
100
+ | `--no-uninstall-on-exit` | Disable the injected hook instead of uninstalling it |
101
+ | `--format <format>` | `ndjson`, `summary`, or `json` |
102
+ | `--quiet` | Suppress progress lines on stderr |
103
+
104
+ Prefer `SAP_EMAIL` and `SAP_PASSWORD` over inline credential flags. Process arguments can be visible to other users on the same machine.
105
+
106
+ ---
107
+
108
+ ## Examples
109
+
110
+ Stop after the first five requests and print a compact text stream:
111
+
112
+ ```bash
113
+ cf-live-trace \
114
+ --api-endpoint https://api.cf.ap10.hana.ondemand.com \
115
+ --org sample-org \
116
+ --space dev \
117
+ --app orders-api \
118
+ --max-events 5 \
119
+ --format summary
120
+ ```
121
+
122
+ Capture headers only, without body previews:
123
+
124
+ ```bash
125
+ cf-live-trace \
126
+ --region ap10 \
127
+ --org sample-org \
128
+ --space dev \
129
+ --app orders-api \
130
+ --no-capture-request-body \
131
+ --no-capture-response-body
132
+ ```
133
+
134
+ Emit one final JSON document for downstream processing:
135
+
136
+ ```bash
137
+ cf-live-trace \
138
+ --region ap10 \
139
+ --org sample-org \
140
+ --space dev \
141
+ --app orders-api \
142
+ --duration 30 \
143
+ --format json
144
+ ```
145
+
146
+ ---
147
+
148
+ ## How It Works
149
+
150
+ `cf-live-trace` follows the same high-level route as the SAP Tools VS Code Live Trace feature:
151
+
152
+ 1. Prepare an isolated CF session with `cf api`, `cf auth`, and `cf target`.
153
+ 2. Ensure SSH is enabled for the app.
154
+ 3. Run a robust `/proc` scan inside the app container and send `SIGUSR1` to the best Node.js process candidate.
155
+ 4. Open `cf ssh -L <local>:127.0.0.1:9229` for the selected app instance.
156
+ 5. Attach to the Node inspector over CDP using `@saptools/cf-inspector`.
157
+ 6. Evaluate a runtime hook that patches Node's `http` and `https` server prototypes.
158
+ 7. Poll a bounded in-process queue and stream drained trace events back to stdout.
159
+ 8. Disable or uninstall the hook and close the tunnel on exit.
160
+
161
+ The injected global is named `__SAPTOOLS_CF_LIVE_TRACE__` so CLI sessions do not collide with the VS Code extension's Live Trace runtime global.
162
+
163
+ ---
164
+
165
+ ## Programmatic Usage
166
+
167
+ ```ts
168
+ import { LiveTraceSession } from "@saptools/cf-live-trace";
169
+
170
+ const session = new LiveTraceSession({
171
+ target: {
172
+ region: "ap10",
173
+ email: process.env["SAP_EMAIL"] ?? "",
174
+ password: process.env["SAP_PASSWORD"] ?? "",
175
+ org: "sample-org",
176
+ space: "dev",
177
+ app: "orders-api",
178
+ instanceIndex: 0,
179
+ },
180
+ onEvents(events) {
181
+ for (const event of events) {
182
+ process.stdout.write(`${event.method} ${event.normalizedUrl} ${String(event.status)}\n`);
183
+ }
184
+ },
185
+ });
186
+
187
+ await session.start({ maxBodyBytes: 4096 });
188
+
189
+ process.once("SIGINT", () => {
190
+ void session.stop({ uninstallRuntimeHook: true, reason: "user" });
191
+ });
192
+ ```
193
+
194
+ The public API also exports helpers for payload parsing, runtime expression construction, CF SSH argument construction, and URL summaries.
195
+
196
+ ---
197
+
198
+ ## Security Notes
199
+
200
+ - This tool injects JavaScript into a running Node.js process through the Node inspector. Use it only for apps and spaces you are authorized to inspect.
201
+ - Captured headers and bodies can contain credentials, tokens, cookies, or personal data. Keep output streams and CI artifacts protected.
202
+ - `--max-body-bytes` bounds previews transported back from the app. Set it lower for sensitive or high-throughput services.
203
+ - The CLI avoids putting credentials in `cf auth` arguments; credentials are passed to the CF CLI through `CF_USERNAME` and `CF_PASSWORD`.
204
+ - If cleanup fails, the runtime hook can remain disabled or installed until the app process restarts. Progress events report this state.
205
+
206
+ ---
207
+
208
+ ## Development
209
+
210
+ ```bash
211
+ pnpm install
212
+ pnpm --filter @saptools/cf-live-trace build
213
+ pnpm --filter @saptools/cf-live-trace lint
214
+ pnpm --filter @saptools/cf-live-trace typecheck
215
+ pnpm --filter @saptools/cf-live-trace test:unit
216
+ pnpm --filter @saptools/cf-live-trace test:e2e
217
+ ```
218
+
219
+ The E2E test starts a local inspectable Node.js app and a fake `cf` executable that opens a real TCP proxy to the app inspector. No live SAP account is required.