@anonymilyhq/cli 1.0.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.
Files changed (2) hide show
  1. package/bin/cli.js +73 -0
  2. package/package.json +29 -0
package/bin/cli.js ADDED
@@ -0,0 +1,73 @@
1
+ #!/usr/bin/env node
2
+
3
+ import { EventSource as EventSourceConstructor } from 'eventsource';
4
+
5
+ import { program } from 'commander';
6
+ import pc from 'picocolors';
7
+
8
+ // Point this to your live production backend URL
9
+ const API_URL = process.env.ANONYMILY_API_URL || 'https://api.anonymily.com';
10
+
11
+ program
12
+ .name('anonymily')
13
+ .description('Forward webhooks from Anonymily directly to your local machine.')
14
+ .version('1.0.0');
15
+
16
+ program
17
+ .command('listen')
18
+ .description('Listen for incoming webhooks and forward them to a local port')
19
+ .argument('<port>', 'Local port to forward to (e.g., 8080)')
20
+ .action((port) => {
21
+ startListening(port);
22
+ });
23
+
24
+ program.parse();
25
+
26
+ async function startListening(port) {
27
+ // 1. Generate a random Hook ID
28
+ const hookId = Math.random().toString(36).substring(2, 10);
29
+ const webhookUrl = `${API_URL}/h/${hookId}`;
30
+ const localUrl = `http://localhost:${port}`;
31
+
32
+ console.log(pc.green(pc.bold(`\nšŸš€ Anonymily CLI is running!`)));
33
+ console.log(`\nForwarding: ${pc.cyan(webhookUrl)} āž” ${pc.cyan(localUrl)}`);
34
+ console.log(pc.dim(`Waiting for requests to arrive...\n`));
35
+
36
+ // 2. Connect to the Server-Sent Events stream using the safe constructor
37
+ const es = new EventSourceConstructor(`${API_URL}/stream/${hookId}`);
38
+
39
+ es.onmessage = async (event) => {
40
+ const reqData = JSON.parse(event.data);
41
+ const { method, headers, query, body } = reqData;
42
+
43
+ // 3. Clean up headers before forwarding
44
+ const forwardHeaders = { ...headers };
45
+ delete forwardHeaders.host;
46
+ delete forwardHeaders.connection;
47
+
48
+ // Reconstruct query parameters
49
+ const queryString = new URLSearchParams(query).toString();
50
+ const fullLocalUrl = queryString ? `${localUrl}?${queryString}` : localUrl;
51
+
52
+ console.log(pc.yellow(`[${new Date().toLocaleTimeString()}] ⚔ Incoming ${method} request...`));
53
+
54
+ try {
55
+ // 4. Forward the exact payload to localhost
56
+ const response = await fetch(fullLocalUrl, {
57
+ method: method,
58
+ headers: forwardHeaders,
59
+ body: ['GET', 'HEAD'].includes(method) ? undefined : JSON.stringify(body)
60
+ });
61
+
62
+ const statusColor = response.ok ? pc.green : pc.red;
63
+ console.log(` └─ Forwarded to localhost | Status: ${statusColor(response.status)}\n`);
64
+ } catch (err) {
65
+ console.log(pc.red(` └─ Error forwarding: ${err.message}`));
66
+ console.log(pc.dim(` Make sure your local server is actually running on port ${port}\n`));
67
+ }
68
+ };
69
+
70
+ es.onerror = () => {
71
+ console.error(pc.red(`\nConnection error. Attempting to reconnect...`));
72
+ };
73
+ }
package/package.json ADDED
@@ -0,0 +1,29 @@
1
+ {
2
+ "name": "@anonymilyhq/cli",
3
+ "version": "1.0.0",
4
+ "description": "CLI for Anonymily platform",
5
+ "type": "module",
6
+ "bin": {
7
+ "anonymily": "./bin/cli.js"
8
+ },
9
+ "scripts": {
10
+ "start": "node ./bin/cli.js"
11
+ },
12
+ "keywords": [
13
+ "cli",
14
+ "anonymily",
15
+ "webhook",
16
+ "devtools",
17
+ "api-client"
18
+ ],
19
+ "files": [
20
+ "bin",
21
+ "index.js",
22
+ "README.md"
23
+ ],
24
+ "dependencies": {
25
+ "commander": "^14.0.3",
26
+ "eventsource": "^4.1.0",
27
+ "picocolors": "^1.1.1"
28
+ }
29
+ }