am-i-vibing 0.0.2 → 0.0.4

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 CHANGED
@@ -1,6 +1,6 @@
1
1
  # am-i-vibing
2
2
 
3
- Detect agentic coding environments and AI assistant tools. This library allows CLI tools and applications to detect when they're being executed by AI agents (like Claude Code) and adapt their behavior accordingly.
3
+ Detect agentic coding environments and AI assistant tools. This library allows CLI tools and Node apps to detect when they're being executed by AI agents. This enables them to adapt by, for example, providing different output formats or logs.
4
4
 
5
5
  ## Installation
6
6
 
@@ -16,59 +16,61 @@ Run as CLI tool:
16
16
  npx am-i-vibing
17
17
  ```
18
18
 
19
+ ```ts
20
+ import { detectAgenticEnvironment } from "am-i-vibing";
21
+ const result = detectAgenticEnvironment();
22
+ console.log(`Detected: ${result.name} (${result.type})`);
23
+ ```
24
+
19
25
  ## Supported AI Tools
20
26
 
21
- - **Claude Code**
22
- - **GitHub Copilot Agent**
23
- - **Replit AI**
24
27
  - **Aider**
25
- - **Bolt.new**
28
+ - **Bolt**
29
+ - **Claude Code**
26
30
  - **Cursor**
27
- - **Windsurf/Codeium**
28
- - **Zed**
31
+ - **Gemini CLI**
32
+ - **GitHub Copilot Agent**
33
+ - **Jules**
34
+ - **Codex CLI**
35
+ - **Replit**
29
36
  - **Warp**
37
+ - **Windsurf**
38
+ - **Zed**
39
+ - **opencode**
30
40
 
31
- ## CLI Usage
32
-
33
- Use the CLI to quickly check if you're running in an agentic environment:
34
-
35
- ```bash
36
- # Basic detection
37
- npx am-i-vibing
38
- # ✓ Detected: Claude Code (agent)
39
-
40
- # JSON output
41
- npx am-i-vibing --format json
42
- # {"isAgentic": true, "id": "claude-code", "name": "Claude Code", "type": "agent"}
43
-
44
- # Check for specific environment type
45
- npx am-i-vibing --check agent
46
- # ✓ Running in agent environment: Claude Code
47
-
48
- npx am-i-vibing --check interactive
49
- # ✗ Not running in interactive environment
41
+ ## Example use case
50
42
 
51
- # Quiet mode (useful for scripts)
52
- npx am-i-vibing --quiet
53
- # Claude Code
43
+ Generating LLM-specific error messages or logs:
54
44
 
55
- # Debug mode (full diagnostic output)
56
- npx am-i-vibing --debug
57
- # {"detection": {"isAgentic": true, "id": "claude-code", "name": "Claude Code", "type": "agent"}, "environment": {...}, "processAncestry": [...]}
45
+ ```typescript
46
+ import { isAgent } from "am-i-vibing";
47
+ const agent = isAgent();
48
+
49
+ function handleError(error: Error) {
50
+ if (agent) {
51
+ console.info(`
52
+ # Error
53
+ <error_message>${error.message}</error_message>
54
+ <error_type>${error.name}</error_type>
55
+ <error_stack>${error.stack}</error_stack>
56
+ <note>Use the search_docs tool to find help for this error. If the tool is not available,
57
+ prompt the user to enable the MCP server followng the instructions at https://example.com/mcp</note>
58
+ `);
59
+ } else {
60
+ console.error("An error occurred:", error.message);
61
+ }
62
+ }
58
63
  ```
59
64
 
60
- ### CLI Options
65
+ ## Environment Types
61
66
 
62
- - `-f, --format <json|text>` - Output format (default: text)
63
- - `-c, --check <agent|interactive|hybrid>` - Check for specific environment type
64
- - `-q, --quiet` - Only output result, no labels
65
- - `-d, --debug` - Debug output with environment and process info
66
- - `-h, --help` - Show help message
67
+ The library detects three main types of environments:
67
68
 
68
- ### Exit Codes
69
+ - **Agent**: Command was directly run by an AI agent (e.g. Claude Code, Codex CLI, Jules)
70
+ - **Interactive**: Interactive commands run inside an AI environment (e.g. Cursor terminal, Replit shell)
71
+ - **Hybrid**: Environments that combine both agentic and interactive features in the same session (e.g. Warp)
69
72
 
70
- - `0` - Agentic environment detected (or specific check passed)
71
- - `1` - No agentic environment detected (or specific check failed)
73
+ There may be false positives, such as if a user directly runs a command in an terminal opened by an AI tool, such as a Copilot terminal in VS Code.
72
74
 
73
75
  ## Library Usage
74
76
 
@@ -115,13 +117,47 @@ interface DetectionResult {
115
117
  }
116
118
  ```
117
119
 
118
- ## Environment Types
120
+ ## CLI Usage
119
121
 
120
- The library detects three main types of environments:
122
+ Use the CLI to quickly check if you're running in an agentic environment:
123
+
124
+ ```bash
125
+ # Basic detection
126
+ npx am-i-vibing
127
+ # ✓ Detected: Claude Code (agent)
128
+
129
+ # JSON output
130
+ npx am-i-vibing --format json
131
+ # {"isAgentic": true, "id": "claude-code", "name": "Claude Code", "type": "agent"}
132
+
133
+ # Check for specific environment type
134
+ npx am-i-vibing --check agent
135
+ # ✓ Running in agent environment: Claude Code
136
+
137
+ npx am-i-vibing --check interactive
138
+ # ✗ Not running in interactive environment
139
+
140
+ # Quiet mode (useful for scripts)
141
+ npx am-i-vibing --quiet
142
+ # Claude Code
143
+
144
+ # Debug mode (full diagnostic output)
145
+ npx am-i-vibing --debug
146
+ # {"detection": {"isAgentic": true, "id": "claude-code", "name": "Claude Code", "type": "agent"}, "environment": {...}, "processAncestry": [...]}
147
+ ```
148
+
149
+ ### CLI Options
121
150
 
122
- - **Agent**: Command was run by an AI agent (e.g., Claude Code, GitHub Copilot Agent)
123
- - **Interactive**: Interactive commands run inside an AI environment (e.g., Cursor Terminal)
124
- - **Hybrid**: Environments that combine both agentic and interactive features in the same session (e.g., Warp)
151
+ - `-f, --format <json|text>` - Output format (default: text)
152
+ - `-c, --check <agent|interactive|hybrid>` - Check for specific environment type
153
+ - `-q, --quiet` - Only output result, no labels
154
+ - `-d, --debug` - Debug output with environment and process info
155
+ - `-h, --help` - Show help message
156
+
157
+ ### Exit Codes
158
+
159
+ - `0` - Agentic environment detected (or specific check passed)
160
+ - `1` - No agentic environment detected (or specific check failed)
125
161
 
126
162
  ## Debug Output
127
163
 
package/dist/cli.d.ts CHANGED
@@ -1 +1 @@
1
- #!/usr/bin/env node
1
+ export { };
package/dist/cli.js CHANGED
@@ -1,67 +1,62 @@
1
1
  #!/usr/bin/env node
2
- import {
3
- detectAgenticEnvironment,
4
- isAgent,
5
- isHybrid,
6
- isInteractive
7
- } from "./chunk-EFLDW3WY.js";
8
-
9
- // src/cli.ts
10
- import { parseArgs } from "util";
2
+ import { detectAgenticEnvironment, isAgent, isHybrid, isInteractive } from "./detector-BEnp3d4c.js";
3
+ import { parseArgs } from "node:util";
11
4
  import { getProcessAncestry } from "process-ancestry";
5
+
6
+ //#region src/cli.ts
12
7
  function parseCliArgs() {
13
- const { values } = parseArgs({
14
- args: process.argv.slice(2),
15
- options: {
16
- format: {
17
- type: "string",
18
- short: "f",
19
- default: "text"
20
- },
21
- check: {
22
- type: "string",
23
- short: "c"
24
- },
25
- quiet: {
26
- type: "boolean",
27
- short: "q",
28
- default: false
29
- },
30
- help: {
31
- type: "boolean",
32
- short: "h",
33
- default: false
34
- },
35
- debug: {
36
- type: "boolean",
37
- short: "d",
38
- default: false
39
- }
40
- },
41
- allowPositionals: false
42
- });
43
- if (values.format && !["json", "text"].includes(values.format)) {
44
- console.error(
45
- `Error: Invalid format '${values.format}'. Must be 'json' or 'text'.`
46
- );
47
- process.exit(1);
48
- }
49
- if (values.check && !["agent", "interactive", "hybrid"].includes(values.check)) {
50
- console.error(
51
- `Error: Invalid check type '${values.check}'. Must be 'agent', 'interactive', or 'hybrid'.`
52
- );
53
- process.exit(1);
54
- }
55
- return {
56
- format: values.format,
57
- check: values.check,
58
- quiet: values.quiet,
59
- help: values.help,
60
- debug: values.debug
61
- };
8
+ const { values } = parseArgs({
9
+ args: process.argv.slice(2),
10
+ options: {
11
+ format: {
12
+ type: "string",
13
+ short: "f",
14
+ default: "text"
15
+ },
16
+ check: {
17
+ type: "string",
18
+ short: "c"
19
+ },
20
+ quiet: {
21
+ type: "boolean",
22
+ short: "q",
23
+ default: false
24
+ },
25
+ help: {
26
+ type: "boolean",
27
+ short: "h",
28
+ default: false
29
+ },
30
+ debug: {
31
+ type: "boolean",
32
+ short: "d",
33
+ default: false
34
+ }
35
+ },
36
+ allowPositionals: false
37
+ });
38
+ if (values.format && !["json", "text"].includes(values.format)) {
39
+ console.error(`Error: Invalid format '${values.format}'. Must be 'json' or 'text'.`);
40
+ process.exit(1);
41
+ }
42
+ if (values.check && ![
43
+ "agent",
44
+ "interactive",
45
+ "hybrid"
46
+ ].includes(values.check)) {
47
+ console.error(`Error: Invalid check type '${values.check}'. Must be 'agent', 'interactive', or 'hybrid'.`);
48
+ process.exit(1);
49
+ }
50
+ return {
51
+ format: values.format,
52
+ check: values.check,
53
+ quiet: values.quiet,
54
+ help: values.help,
55
+ debug: values.debug
56
+ };
62
57
  }
63
58
  function showHelp() {
64
- console.log(`
59
+ console.log(`
65
60
  am-i-vibing - Detect agentic coding environments
66
61
 
67
62
  USAGE:
@@ -88,65 +83,55 @@ EXIT CODES:
88
83
  `);
89
84
  }
90
85
  function checkEnvironmentType(checkType) {
91
- switch (checkType) {
92
- case "agent":
93
- return isAgent();
94
- case "interactive":
95
- return isInteractive();
96
- case "hybrid":
97
- return isHybrid();
98
- default:
99
- return false;
100
- }
86
+ switch (checkType) {
87
+ case "agent": return isAgent();
88
+ case "interactive": return isInteractive();
89
+ case "hybrid": return isHybrid();
90
+ default: return false;
91
+ }
101
92
  }
102
93
  function formatOutput(result, options) {
103
- if (options.debug) {
104
- let processAncestry = [];
105
- try {
106
- processAncestry = getProcessAncestry();
107
- } catch (error) {
108
- processAncestry = [{ error: "Failed to get process ancestry" }];
109
- }
110
- const debugOutput = {
111
- detection: result,
112
- environment: process.env,
113
- processAncestry
114
- };
115
- return JSON.stringify(debugOutput, null, 2);
116
- }
117
- if (options.format === "json") {
118
- return JSON.stringify(result, null, 2);
119
- }
120
- if (options.quiet) {
121
- if (options.check) {
122
- return checkEnvironmentType(options.check) ? "true" : "false";
123
- }
124
- return result.isAgentic ? `${result.name}` : "none";
125
- }
126
- if (options.check) {
127
- const matches = checkEnvironmentType(options.check);
128
- return matches ? `\u2713 Running in ${options.check} environment: ${result.name}` : `\u2717 Not running in ${options.check} environment`;
129
- }
130
- if (!result.isAgentic) {
131
- return "\u2717 No agentic environment detected";
132
- }
133
- return `\u2713 Detected: [${result.id}] ${result.name} (${result.type})`;
94
+ if (options.debug) {
95
+ let processAncestry = [];
96
+ try {
97
+ processAncestry = getProcessAncestry();
98
+ } catch (error) {
99
+ processAncestry = [{ error: "Failed to get process ancestry" }];
100
+ }
101
+ const debugOutput = {
102
+ detection: result,
103
+ environment: process.env,
104
+ processAncestry
105
+ };
106
+ return JSON.stringify(debugOutput, null, 2);
107
+ }
108
+ if (options.format === "json") return JSON.stringify(result, null, 2);
109
+ if (options.quiet) {
110
+ if (options.check) return checkEnvironmentType(options.check) ? "true" : "false";
111
+ return result.isAgentic ? `${result.name}` : "none";
112
+ }
113
+ if (options.check) {
114
+ const matches = checkEnvironmentType(options.check);
115
+ return matches ? `✓ Running in ${options.check} environment: ${result.name}` : `✗ Not running in ${options.check} environment`;
116
+ }
117
+ if (!result.isAgentic) return "✗ No agentic environment detected";
118
+ return `✓ Detected: [${result.id}] ${result.name} (${result.type})`;
134
119
  }
135
120
  function main() {
136
- const options = parseCliArgs();
137
- if (options.help) {
138
- showHelp();
139
- process.exit(0);
140
- }
141
- const result = detectAgenticEnvironment();
142
- let exitCode = 1;
143
- if (options.check) {
144
- exitCode = checkEnvironmentType(options.check) ? 0 : 1;
145
- } else {
146
- exitCode = result.isAgentic ? 0 : 1;
147
- }
148
- const output = formatOutput(result, options);
149
- console.log(output);
150
- process.exit(exitCode);
121
+ const options = parseCliArgs();
122
+ if (options.help) {
123
+ showHelp();
124
+ process.exit(0);
125
+ }
126
+ const result = detectAgenticEnvironment();
127
+ let exitCode = 1;
128
+ if (options.check) exitCode = checkEnvironmentType(options.check) ? 0 : 1;
129
+ else exitCode = result.isAgentic ? 0 : 1;
130
+ const output = formatOutput(result, options);
131
+ console.log(output);
132
+ process.exit(exitCode);
151
133
  }
152
134
  main();
135
+
136
+ //#endregion
137
+ //# sourceMappingURL=cli.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"cli.js","names":["checkType: string","result: ReturnType<typeof detectAgenticEnvironment>","options: CliOptions","processAncestry: any[]"],"sources":["../src/cli.ts"],"sourcesContent":["#!/usr/bin/env node\n\nimport { parseArgs } from \"node:util\";\nimport { getProcessAncestry } from \"process-ancestry\";\nimport {\n detectAgenticEnvironment,\n isAgent,\n isInteractive,\n isHybrid,\n} from \"./detector.js\";\n\ninterface CliOptions {\n format?: \"json\" | \"text\";\n check?: \"agent\" | \"interactive\" | \"hybrid\";\n quiet?: boolean;\n help?: boolean;\n debug?: boolean;\n}\n\nfunction parseCliArgs(): CliOptions {\n const { values } = parseArgs({\n args: process.argv.slice(2),\n options: {\n format: {\n type: \"string\",\n short: \"f\",\n default: \"text\",\n },\n check: {\n type: \"string\",\n short: \"c\",\n },\n quiet: {\n type: \"boolean\",\n short: \"q\",\n default: false,\n },\n help: {\n type: \"boolean\",\n short: \"h\",\n default: false,\n },\n debug: {\n type: \"boolean\",\n short: \"d\",\n default: false,\n },\n },\n allowPositionals: false,\n });\n\n // Validate format option\n if (values.format && ![\"json\", \"text\"].includes(values.format)) {\n console.error(\n `Error: Invalid format '${values.format}'. Must be 'json' or 'text'.`,\n );\n process.exit(1);\n }\n\n // Validate check option\n if (values.check && ![\"agent\", \"interactive\", \"hybrid\"].includes(values.check)) {\n console.error(\n `Error: Invalid check type '${values.check}'. Must be 'agent', 'interactive', or 'hybrid'.`,\n );\n process.exit(1);\n }\n\n return {\n format: values.format as \"json\" | \"text\",\n check: values.check as \"agent\" | \"interactive\" | \"hybrid\",\n quiet: values.quiet,\n help: values.help,\n debug: values.debug,\n };\n}\n\nfunction showHelp(): void {\n console.log(`\nam-i-vibing - Detect agentic coding environments\n\nUSAGE:\n npx am-i-vibing [OPTIONS]\n\nOPTIONS:\n -f, --format <json|text> Output format (default: text)\n -c, --check <agent|interactive|hybrid> Check for specific environment type\n -q, --quiet Only output result, no labels\n -d, --debug Debug output with environment and process info\n -h, --help Show this help message\n\nEXAMPLES:\n npx am-i-vibing # Detect current environment\n npx am-i-vibing --format json # JSON output\n npx am-i-vibing --check agent # Check if running under agent\n npx am-i-vibing --check hybrid # Check if running under hybrid\n npx am-i-vibing --quiet # Minimal output\n npx am-i-vibing --debug # Debug with full environment info\n\nEXIT CODES:\n 0 Agentic environment detected (or specific check passed)\n 1 No agentic environment detected (or specific check failed)\n`);\n}\n\nfunction checkEnvironmentType(checkType: string): boolean {\n switch (checkType) {\n case \"agent\":\n return isAgent();\n case \"interactive\":\n return isInteractive();\n case \"hybrid\":\n return isHybrid();\n default:\n return false;\n }\n}\n\nfunction formatOutput(\n result: ReturnType<typeof detectAgenticEnvironment>,\n options: CliOptions,\n): string {\n if (options.debug) {\n let processAncestry: any[] = [];\n try {\n processAncestry = getProcessAncestry();\n } catch (error) {\n processAncestry = [{ error: \"Failed to get process ancestry\" }];\n }\n\n const debugOutput = {\n detection: result,\n environment: process.env,\n processAncestry,\n };\n return JSON.stringify(debugOutput, null, 2);\n }\n\n if (options.format === \"json\") {\n return JSON.stringify(result, null, 2);\n }\n\n if (options.quiet) {\n if (options.check) {\n return checkEnvironmentType(options.check) ? \"true\" : \"false\";\n }\n return result.isAgentic ? `${result.name}` : \"none\";\n }\n\n if (options.check) {\n const matches = checkEnvironmentType(options.check);\n return matches\n ? `✓ Running in ${options.check} environment: ${result.name}`\n : `✗ Not running in ${options.check} environment`;\n }\n\n if (!result.isAgentic) {\n return \"✗ No agentic environment detected\";\n }\n\n return `✓ Detected: [${result.id}] ${result.name} (${result.type})`;\n}\n\nfunction main(): void {\n const options = parseCliArgs();\n\n if (options.help) {\n showHelp();\n process.exit(0);\n }\n\n const result = detectAgenticEnvironment();\n let exitCode = 1;\n\n if (options.check) {\n exitCode = checkEnvironmentType(options.check) ? 0 : 1;\n } else {\n exitCode = result.isAgentic ? 0 : 1;\n }\n\n const output = formatOutput(result, options);\n console.log(output);\n\n process.exit(exitCode);\n}\n\nmain();\n"],"mappings":";;;;;;AAmBA,SAAS,eAA2B;CAClC,MAAM,EAAE,QAAQ,GAAG,UAAU;EAC3B,MAAM,QAAQ,KAAK,MAAM,EAAE;EAC3B,SAAS;GACP,QAAQ;IACN,MAAM;IACN,OAAO;IACP,SAAS;GACV;GACD,OAAO;IACL,MAAM;IACN,OAAO;GACR;GACD,OAAO;IACL,MAAM;IACN,OAAO;IACP,SAAS;GACV;GACD,MAAM;IACJ,MAAM;IACN,OAAO;IACP,SAAS;GACV;GACD,OAAO;IACL,MAAM;IACN,OAAO;IACP,SAAS;GACV;EACF;EACD,kBAAkB;CACnB,EAAC;AAGF,KAAI,OAAO,WAAW,CAAC,QAAQ,MAAO,EAAC,SAAS,OAAO,OAAO,EAAE;AAC9D,UAAQ,MACN,CAAC,uBAAuB,EAAE,OAAO,OAAO,4BAA4B,CAAC,CACtE;AACD,UAAQ,KAAK,EAAE;CAChB;AAGD,KAAI,OAAO,UAAU;EAAC;EAAS;EAAe;CAAS,EAAC,SAAS,OAAO,MAAM,EAAE;AAC9E,UAAQ,MACN,CAAC,2BAA2B,EAAE,OAAO,MAAM,+CAA+C,CAAC,CAC5F;AACD,UAAQ,KAAK,EAAE;CAChB;AAED,QAAO;EACL,QAAQ,OAAO;EACf,OAAO,OAAO;EACd,OAAO,OAAO;EACd,MAAM,OAAO;EACb,OAAO,OAAO;CACf;AACF;AAED,SAAS,WAAiB;AACxB,SAAQ,IAAI,CAAC;;;;;;;;;;;;;;;;;;;;;;;;AAwBf,CAAC,CAAC;AACD;AAED,SAAS,qBAAqBA,WAA4B;AACxD,SAAQ,WAAR;EACE,KAAK,QACH,QAAO,SAAS;EAClB,KAAK,cACH,QAAO,eAAe;EACxB,KAAK,SACH,QAAO,UAAU;EACnB,QACE,QAAO;CACV;AACF;AAED,SAAS,aACPC,QACAC,SACQ;AACR,KAAI,QAAQ,OAAO;EACjB,IAAIC,kBAAyB,CAAE;AAC/B,MAAI;AACF,qBAAkB,oBAAoB;EACvC,SAAQ,OAAO;AACd,qBAAkB,CAAC,EAAE,OAAO,iCAAkC,CAAC;EAChE;EAED,MAAM,cAAc;GAClB,WAAW;GACX,aAAa,QAAQ;GACrB;EACD;AACD,SAAO,KAAK,UAAU,aAAa,MAAM,EAAE;CAC5C;AAED,KAAI,QAAQ,WAAW,OACrB,QAAO,KAAK,UAAU,QAAQ,MAAM,EAAE;AAGxC,KAAI,QAAQ,OAAO;AACjB,MAAI,QAAQ,MACV,QAAO,qBAAqB,QAAQ,MAAM,GAAG,SAAS;AAExD,SAAO,OAAO,YAAY,GAAG,OAAO,MAAM,GAAG;CAC9C;AAED,KAAI,QAAQ,OAAO;EACjB,MAAM,UAAU,qBAAqB,QAAQ,MAAM;AACnD,SAAO,UACH,CAAC,aAAa,EAAE,QAAQ,MAAM,cAAc,EAAE,OAAO,MAAM,GAC3D,CAAC,iBAAiB,EAAE,QAAQ,MAAM,YAAY,CAAC;CACpD;AAED,MAAK,OAAO,UACV,QAAO;AAGT,QAAO,CAAC,aAAa,EAAE,OAAO,GAAG,EAAE,EAAE,OAAO,KAAK,EAAE,EAAE,OAAO,KAAK,CAAC,CAAC;AACpE;AAED,SAAS,OAAa;CACpB,MAAM,UAAU,cAAc;AAE9B,KAAI,QAAQ,MAAM;AAChB,YAAU;AACV,UAAQ,KAAK,EAAE;CAChB;CAED,MAAM,SAAS,0BAA0B;CACzC,IAAI,WAAW;AAEf,KAAI,QAAQ,MACV,YAAW,qBAAqB,QAAQ,MAAM,GAAG,IAAI;KAErD,YAAW,OAAO,YAAY,IAAI;CAGpC,MAAM,SAAS,aAAa,QAAQ,QAAQ;AAC5C,SAAQ,IAAI,OAAO;AAEnB,SAAQ,KAAK,SAAS;AACvB;AAED,MAAM"}
@@ -0,0 +1,239 @@
1
+ import { getProcessAncestry } from "process-ancestry";
2
+
3
+ //#region src/providers.ts
4
+ /**
5
+ * Provider configurations for major AI coding tools
6
+ */
7
+ const providers = [
8
+ {
9
+ id: "sst-opencode",
10
+ name: "SST OpenCode",
11
+ type: "agent",
12
+ envVars: [{ any: [
13
+ "OPENCODE_BIN_PATH",
14
+ "OPENCODE_SERVER",
15
+ "OPENCODE_APP_INFO",
16
+ "OPENCODE_MODES"
17
+ ] }]
18
+ },
19
+ {
20
+ id: "jules",
21
+ name: "Jules",
22
+ type: "agent",
23
+ envVars: [{ all: [["HOME", "/home/jules"], ["USER", "swebot"]] }]
24
+ },
25
+ {
26
+ id: "claude-code",
27
+ name: "Claude Code",
28
+ type: "agent",
29
+ envVars: ["CLAUDECODE"]
30
+ },
31
+ {
32
+ id: "cursor-agent",
33
+ name: "Cursor Agent",
34
+ type: "agent",
35
+ envVars: [{ all: ["CURSOR_TRACE_ID", ["PAGER", "head -n 10000 | cat"]] }]
36
+ },
37
+ {
38
+ id: "cursor",
39
+ name: "Cursor",
40
+ type: "interactive",
41
+ envVars: ["CURSOR_TRACE_ID"]
42
+ },
43
+ {
44
+ id: "gemini-agent",
45
+ name: "Gemini Agent",
46
+ type: "agent",
47
+ processChecks: ["gemini"]
48
+ },
49
+ {
50
+ id: "codex",
51
+ name: "OpenAI Codex",
52
+ type: "agent",
53
+ processChecks: ["codex"]
54
+ },
55
+ {
56
+ id: "replit",
57
+ name: "Replit",
58
+ type: "agent",
59
+ envVars: ["REPL_ID"]
60
+ },
61
+ {
62
+ id: "aider",
63
+ name: "Aider",
64
+ type: "agent",
65
+ envVars: ["AIDER_API_KEY"],
66
+ processChecks: ["aider"]
67
+ },
68
+ {
69
+ id: "bolt-agent",
70
+ name: "Bolt.new Agent",
71
+ type: "agent",
72
+ envVars: [{ all: [["SHELL", "/bin/jsh"], "npm_config_yes"] }]
73
+ },
74
+ {
75
+ id: "bolt",
76
+ name: "Bolt.new",
77
+ type: "interactive",
78
+ envVars: [{
79
+ all: [["SHELL", "/bin/jsh"]],
80
+ none: ["npm_config_yes"]
81
+ }]
82
+ },
83
+ {
84
+ id: "zed-agent",
85
+ name: "Zed Agent",
86
+ type: "agent",
87
+ envVars: [{ all: [["TERM_PROGRAM", "zed"], ["PAGER", "cat"]] }]
88
+ },
89
+ {
90
+ id: "zed",
91
+ name: "Zed",
92
+ type: "interactive",
93
+ envVars: [{
94
+ all: [["TERM_PROGRAM", "zed"]],
95
+ none: [["PAGER", "cat"]]
96
+ }]
97
+ },
98
+ {
99
+ id: "replit-assistant",
100
+ name: "Replit Assistant",
101
+ type: "agent",
102
+ envVars: [{ all: ["REPL_ID", ["REPLIT_MODE", "assistant"]] }]
103
+ },
104
+ {
105
+ id: "replit",
106
+ name: "Replit",
107
+ type: "interactive",
108
+ envVars: [{
109
+ all: ["REPL_ID"],
110
+ none: [["REPLIT_MODE", "assistant"]]
111
+ }]
112
+ },
113
+ {
114
+ id: "windsurf",
115
+ name: "Windsurf",
116
+ type: "agent",
117
+ envVars: ["CODEIUM_EDITOR_APP_ROOT"]
118
+ },
119
+ {
120
+ id: "vscode-copilot-agent",
121
+ name: "GitHub Copilot in VS Code",
122
+ type: "agent",
123
+ envVars: [{ all: [["TERM_PROGRAM", "vscode"], ["GIT_PAGER", "cat"]] }]
124
+ },
125
+ {
126
+ id: "warp",
127
+ name: "Warp Terminal",
128
+ type: "hybrid",
129
+ envVars: [{ all: [["TERM_PROGRAM", "WarpTerminal"]] }]
130
+ }
131
+ ];
132
+ /**
133
+ * Get provider configuration by name
134
+ */
135
+ function getProvider(name) {
136
+ return providers.find((p) => p.name === name);
137
+ }
138
+ /**
139
+ * Get all providers of a specific type
140
+ */
141
+ function getProvidersByType(type) {
142
+ return providers.filter((p) => p.type === type);
143
+ }
144
+
145
+ //#endregion
146
+ //#region src/detector.ts
147
+ /**
148
+ * Check if a specific environment variable exists (handles both strings and tuples)
149
+ */
150
+ function checkEnvVar(envVarDef, env = process.env) {
151
+ const [envVar, expectedValue] = typeof envVarDef === "string" ? [envVarDef, void 0] : envVarDef;
152
+ const actualValue = env[envVar];
153
+ return Boolean(actualValue && (!expectedValue || actualValue === expectedValue));
154
+ }
155
+ /**
156
+ * Check if a process is running in the process tree
157
+ */
158
+ function checkProcess(processName) {
159
+ try {
160
+ const ancestry = getProcessAncestry();
161
+ for (const ancestorProcess of ancestry) if (ancestorProcess.command?.includes(processName)) return true;
162
+ } catch (error) {}
163
+ return false;
164
+ }
165
+ /**
166
+ * Check if an environment variable group matches based on its properties
167
+ */
168
+ function checkEnvVars(definition, env = process.env) {
169
+ if (typeof definition === "string" || Array.isArray(definition)) return checkEnvVar(definition, env);
170
+ const { any, all, none } = definition;
171
+ const anyResult = !any?.length || any.some((envVar) => checkEnvVar(envVar, env));
172
+ const allResult = !all?.length || all.every((envVar) => checkEnvVar(envVar, env));
173
+ const noneResult = !none?.length || !none.some((envVar) => checkEnvVar(envVar, env));
174
+ return anyResult && allResult && noneResult;
175
+ }
176
+ /**
177
+ * Run custom detectors for a provider
178
+ */
179
+ function runCustomDetectors(provider) {
180
+ return provider.customDetectors?.some((detector) => {
181
+ try {
182
+ return detector();
183
+ } catch {
184
+ return false;
185
+ }
186
+ }) ?? false;
187
+ }
188
+ /**
189
+ * Create a positive detection result
190
+ */
191
+ function createDetectedResult(provider) {
192
+ return {
193
+ isAgentic: true,
194
+ id: provider.id,
195
+ name: provider.name,
196
+ type: provider.type
197
+ };
198
+ }
199
+ /**
200
+ * Detect agentic coding environment
201
+ */
202
+ function detectAgenticEnvironment(env = process.env) {
203
+ for (const provider of providers) {
204
+ if (provider.envVars?.some((group) => checkEnvVars(group, env))) return createDetectedResult(provider);
205
+ if (provider.processChecks?.some(checkProcess)) return createDetectedResult(provider);
206
+ if (runCustomDetectors(provider)) return createDetectedResult(provider);
207
+ }
208
+ return {
209
+ isAgentic: false,
210
+ id: null,
211
+ name: null,
212
+ type: null
213
+ };
214
+ }
215
+ /**
216
+ * Check if currently running in any agent environment
217
+ */
218
+ function isAgent(env = process.env) {
219
+ const result = detectAgenticEnvironment(env);
220
+ return result.type === "agent" || result.type === "hybrid";
221
+ }
222
+ /**
223
+ * Check if currently running in any interactive AI environment
224
+ */
225
+ function isInteractive(env = process.env) {
226
+ const result = detectAgenticEnvironment(env);
227
+ return result.type === "interactive" || result.type === "hybrid";
228
+ }
229
+ /**
230
+ * Check if currently running in any hybrid AI environment
231
+ */
232
+ function isHybrid(env = process.env) {
233
+ const result = detectAgenticEnvironment(env);
234
+ return result.type === "hybrid";
235
+ }
236
+
237
+ //#endregion
238
+ export { detectAgenticEnvironment, getProvider, getProvidersByType, isAgent, isHybrid, isInteractive, providers };
239
+ //# sourceMappingURL=detector-BEnp3d4c.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"detector-BEnp3d4c.js","names":["providers: ProviderConfig[]","name: string","type: \"agent\" | \"interactive\" | \"hybrid\"","envVarDef: EnvVarDefinition","env: Record<string, string | undefined>","processName: string","definition: EnvVarGroup | EnvVarDefinition","provider: ProviderConfig"],"sources":["../src/providers.ts","../src/detector.ts"],"sourcesContent":["import type { ProviderConfig } from \"./types.js\";\n\n/**\n * Provider configurations for major AI coding tools\n */\nexport const providers: ProviderConfig[] = [\n {\n id: \"sst-opencode\",\n name: \"SST OpenCode\",\n type: \"agent\",\n envVars: [\n {\n any: [\n \"OPENCODE_BIN_PATH\",\n \"OPENCODE_SERVER\",\n \"OPENCODE_APP_INFO\",\n \"OPENCODE_MODES\",\n ],\n },\n ],\n },\n {\n id: \"jules\",\n name: \"Jules\",\n type: \"agent\",\n envVars: [{ all: [[\"HOME\", \"/home/jules\"], [\"USER\", \"swebot\"]] }],\n },\n {\n id: \"claude-code\",\n name: \"Claude Code\",\n type: \"agent\",\n envVars: [\"CLAUDECODE\"],\n },\n {\n id: \"cursor-agent\",\n name: \"Cursor Agent\",\n type: \"agent\",\n envVars: [\n {\n all: [\"CURSOR_TRACE_ID\", [\"PAGER\", \"head -n 10000 | cat\"]],\n },\n ],\n },\n {\n id: \"cursor\",\n name: \"Cursor\",\n type: \"interactive\",\n envVars: [\"CURSOR_TRACE_ID\"],\n },\n {\n id: \"gemini-agent\",\n name: \"Gemini Agent\",\n type: \"agent\",\n processChecks: [\"gemini\"],\n },\n {\n id: \"codex\",\n name: \"OpenAI Codex\",\n type: \"agent\",\n processChecks: [\"codex\"],\n },\n {\n id: \"replit\",\n name: \"Replit\",\n type: \"agent\",\n envVars: [\"REPL_ID\"],\n },\n {\n id: \"aider\",\n name: \"Aider\",\n type: \"agent\",\n envVars: [\"AIDER_API_KEY\"],\n processChecks: [\"aider\"],\n },\n {\n id: \"bolt-agent\",\n name: \"Bolt.new Agent\",\n type: \"agent\",\n envVars: [\n {\n all: [[\"SHELL\", \"/bin/jsh\"], \"npm_config_yes\"],\n },\n ],\n },\n {\n id: \"bolt\",\n name: \"Bolt.new\",\n type: \"interactive\",\n envVars: [\n {\n all: [[\"SHELL\", \"/bin/jsh\"]],\n none: [\"npm_config_yes\"],\n },\n ],\n },\n {\n id: \"zed-agent\",\n name: \"Zed Agent\",\n type: \"agent\",\n envVars: [\n {\n all: [\n [\"TERM_PROGRAM\", \"zed\"],\n [\"PAGER\", \"cat\"],\n ],\n },\n ],\n },\n {\n id: \"zed\",\n name: \"Zed\",\n type: \"interactive\",\n envVars: [\n {\n all: [[\"TERM_PROGRAM\", \"zed\"]],\n none: [[\"PAGER\", \"cat\"]],\n },\n ],\n },\n {\n id: \"replit-assistant\",\n name: \"Replit Assistant\",\n type: \"agent\",\n envVars: [\n {\n all: [\"REPL_ID\", [\"REPLIT_MODE\", \"assistant\"]],\n },\n ],\n },\n {\n id: \"replit\",\n name: \"Replit\",\n type: \"interactive\",\n envVars: [\n {\n all: [\"REPL_ID\"],\n none: [[\"REPLIT_MODE\", \"assistant\"]],\n },\n ],\n },\n {\n id: \"windsurf\",\n name: \"Windsurf\",\n type: \"agent\",\n envVars: [\"CODEIUM_EDITOR_APP_ROOT\"],\n },\n {\n id: \"vscode-copilot-agent\",\n name: \"GitHub Copilot in VS Code\",\n type: \"agent\",\n envVars: [\n {\n all: [\n [\"TERM_PROGRAM\", \"vscode\"],\n [\"GIT_PAGER\", \"cat\"],\n ],\n },\n ],\n },\n {\n id: \"warp\",\n name: \"Warp Terminal\",\n type: \"hybrid\",\n envVars: [\n {\n all: [\n [\"TERM_PROGRAM\", \"WarpTerminal\"],\n ],\n },\n ],\n },\n];\n\n/**\n * Get provider configuration by name\n */\nexport function getProvider(name: string): ProviderConfig | undefined {\n return providers.find((p) => p.name === name);\n}\n\n/**\n * Get all providers of a specific type\n */\nexport function getProvidersByType(\n type: \"agent\" | \"interactive\" | \"hybrid\",\n): ProviderConfig[] {\n return providers.filter((p) => p.type === type);\n}\n","import type {\n DetectionResult,\n ProviderConfig,\n EnvVarDefinition,\n EnvVarGroup,\n} from \"./types.js\";\nimport { providers } from \"./providers.js\";\nimport { getProcessAncestry } from \"process-ancestry\";\n\n/**\n * Check if a specific environment variable exists (handles both strings and tuples)\n */\nfunction checkEnvVar(\n envVarDef: EnvVarDefinition,\n env: Record<string, string | undefined> = process.env,\n): boolean {\n const [envVar, expectedValue] =\n typeof envVarDef === \"string\" ? [envVarDef, undefined] : envVarDef;\n\n const actualValue = env[envVar];\n return Boolean(\n actualValue && (!expectedValue || actualValue === expectedValue),\n );\n}\n\n/**\n * Check if a process is running in the process tree\n */\nfunction checkProcess(processName: string): boolean {\n try {\n const ancestry = getProcessAncestry();\n for (const ancestorProcess of ancestry) {\n if (ancestorProcess.command?.includes(processName)) {\n return true;\n }\n }\n } catch (error) {\n // Ignore process check errors\n }\n return false;\n}\n\n/**\n * Check if an environment variable group matches based on its properties\n */\nfunction checkEnvVars(\n definition: EnvVarGroup | EnvVarDefinition,\n env: Record<string, string | undefined> = process.env,\n): boolean {\n if (typeof definition === \"string\" || Array.isArray(definition)) {\n return checkEnvVar(definition, env);\n }\n\n const { any, all, none } = definition;\n\n // Check ANY conditions (OR logic) - at least one must pass\n const anyResult =\n !any?.length || any.some((envVar) => checkEnvVar(envVar, env));\n\n // Check ALL conditions (AND logic) - all must pass\n const allResult =\n !all?.length || all.every((envVar) => checkEnvVar(envVar, env));\n\n // Check NONE conditions (NOT logic) - none should pass\n const noneResult =\n !none?.length || !none.some((envVar) => checkEnvVar(envVar, env));\n\n return anyResult && allResult && noneResult;\n}\n\n/**\n * Run custom detectors for a provider\n */\nfunction runCustomDetectors(provider: ProviderConfig): boolean {\n return (\n provider.customDetectors?.some((detector) => {\n try {\n return detector();\n } catch {\n return false;\n }\n }) ?? false\n );\n}\n\n/**\n * Create a positive detection result\n */\nfunction createDetectedResult(provider: ProviderConfig): DetectionResult {\n return {\n isAgentic: true,\n id: provider.id,\n name: provider.name,\n type: provider.type,\n };\n}\n\n/**\n * Detect agentic coding environment\n */\nexport function detectAgenticEnvironment(\n env: Record<string, string | undefined> = process.env,\n): DetectionResult {\n for (const provider of providers) {\n // Check environment variables\n if (provider.envVars?.some((group) => checkEnvVars(group, env))) {\n return createDetectedResult(provider);\n }\n\n // Check processes\n if (provider.processChecks?.some(checkProcess)) {\n return createDetectedResult(provider);\n }\n\n // Run custom detectors\n if (runCustomDetectors(provider)) {\n return createDetectedResult(provider);\n }\n }\n\n // No provider detected\n return {\n isAgentic: false,\n id: null,\n name: null,\n type: null,\n };\n}\n\n/**\n * Check if currently running in a specific provider\n */\nexport function isProvider(\n providerName: string,\n env: Record<string, string | undefined> = process.env,\n): boolean {\n const result = detectAgenticEnvironment(env);\n return result.name === providerName;\n}\n\n/**\n * Check if currently running in any agent environment\n */\nexport function isAgent(\n env: Record<string, string | undefined> = process.env,\n): boolean {\n const result = detectAgenticEnvironment(env);\n return result.type === \"agent\" || result.type === \"hybrid\";\n}\n\n/**\n * Check if currently running in any interactive AI environment\n */\nexport function isInteractive(\n env: Record<string, string | undefined> = process.env,\n): boolean {\n const result = detectAgenticEnvironment(env);\n return result.type === \"interactive\" || result.type === \"hybrid\";\n}\n\n/**\n * Check if currently running in any hybrid AI environment\n */\nexport function isHybrid(\n env: Record<string, string | undefined> = process.env,\n): boolean {\n const result = detectAgenticEnvironment(env);\n return result.type === \"hybrid\";\n}\n"],"mappings":"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"}
package/dist/index.d.ts CHANGED
@@ -1,3 +1,4 @@
1
+ //#region src/types.d.ts
1
2
  /**
2
3
  * The type of AI coding environment detected
3
4
  */
@@ -10,44 +11,46 @@ type EnvVarDefinition = string | [string, string];
10
11
  * Environment variable group with logical operators
11
12
  */
12
13
  interface EnvVarGroup {
13
- /** ANY of these environment variables can match (OR logic) */
14
- any?: EnvVarDefinition[];
15
- /** ALL of these environment variables must match (AND logic) */
16
- all?: EnvVarDefinition[];
17
- /** NONE of these environment variables should be present (NOT logic) */
18
- none?: EnvVarDefinition[];
14
+ /** ANY of these environment variables can match (OR logic) */
15
+ any?: EnvVarDefinition[];
16
+ /** ALL of these environment variables must match (AND logic) */
17
+ all?: EnvVarDefinition[];
18
+ /** NONE of these environment variables should be present (NOT logic) */
19
+ none?: EnvVarDefinition[];
19
20
  }
20
21
  /**
21
22
  * Configuration for detecting a specific AI coding provider
22
23
  */
23
24
  interface ProviderConfig {
24
- /** Unique identifier for the provider */
25
- id: string;
26
- /** Human-readable name of the provider */
27
- name: string;
28
- /** Type of AI coding environment */
29
- type: AgenticType;
30
- /** Environment variables */
31
- envVars?: Array<EnvVarGroup | EnvVarDefinition>;
32
- /** Process names to check for in the process tree */
33
- processChecks?: string[];
34
- /** Custom detection functions for complex logic */
35
- customDetectors?: (() => boolean)[];
25
+ /** Unique identifier for the provider */
26
+ id: string;
27
+ /** Human-readable name of the provider */
28
+ name: string;
29
+ /** Type of AI coding environment */
30
+ type: AgenticType;
31
+ /** Environment variables */
32
+ envVars?: Array<EnvVarGroup | EnvVarDefinition>;
33
+ /** Process names to check for in the process tree */
34
+ processChecks?: string[];
35
+ /** Custom detection functions for complex logic */
36
+ customDetectors?: (() => boolean)[];
36
37
  }
37
38
  /**
38
39
  * Result of agentic environment detection
39
40
  */
40
41
  interface DetectionResult {
41
- /** Whether an agentic environment was detected */
42
- isAgentic: boolean;
43
- /** ID of the detected provider, if any */
44
- id: string | null;
45
- /** Name of the detected provider, if any */
46
- name: string | null;
47
- /** Type of agentic environment, if detected */
48
- type: AgenticType | null;
42
+ /** Whether an agentic environment was detected */
43
+ isAgentic: boolean;
44
+ /** ID of the detected provider, if any */
45
+ id: string | null;
46
+ /** Name of the detected provider, if any */
47
+ name: string | null;
48
+ /** Type of agentic environment, if detected */
49
+ type: AgenticType | null;
49
50
  }
50
-
51
+ //# sourceMappingURL=types.d.ts.map
52
+ //#endregion
53
+ //#region src/providers.d.ts
51
54
  /**
52
55
  * Provider configurations for major AI coding tools
53
56
  */
@@ -60,11 +63,17 @@ declare function getProvider(name: string): ProviderConfig | undefined;
60
63
  * Get all providers of a specific type
61
64
  */
62
65
  declare function getProvidersByType(type: "agent" | "interactive" | "hybrid"): ProviderConfig[];
63
-
66
+ //# sourceMappingURL=providers.d.ts.map
67
+ //#endregion
68
+ //#region src/detector.d.ts
64
69
  /**
65
70
  * Detect agentic coding environment
66
71
  */
67
72
  declare function detectAgenticEnvironment(env?: Record<string, string | undefined>): DetectionResult;
73
+ /**
74
+ * Check if currently running in a specific provider
75
+ */
76
+
68
77
  /**
69
78
  * Check if currently running in any agent environment
70
79
  */
@@ -77,9 +86,8 @@ declare function isInteractive(env?: Record<string, string | undefined>): boolea
77
86
  * Check if currently running in any hybrid AI environment
78
87
  */
79
88
  declare function isHybrid(env?: Record<string, string | undefined>): boolean;
89
+ //# sourceMappingURL=detector.d.ts.map
80
90
 
81
- /**
82
- * am-i-vibing - Detect agentic coding environments and AI assistant tools
83
- */
84
-
91
+ //#endregion
85
92
  export { type AgenticType, type DetectionResult, type ProviderConfig, detectAgenticEnvironment as default, detectAgenticEnvironment, getProvider, getProvidersByType, isAgent, isHybrid, isInteractive, providers };
93
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","names":[],"sources":["../src/types.ts","../src/providers.ts","../src/detector.ts"],"sourcesContent":[],"mappings":";;AAGA;AAKA;AAKiB,KAVL,WAAA,GAUgB,OAAA,GAAA,aAAA,GAAA,QAAA;;;;AAQnB,KAbG,gBAAA,GAaH,MAAA,GAAA,CAAA,MAAA,EAAA,MAAA,CAAA;AAAgB;AAMzB;;AAQQ,UAtBS,WAAA,CAsBT;EAAW;EAGU,GAAG,CAAA,EAvBxB,gBAuBwB,EAAA;EAAgB;EAA/B,GAAA,CAAA,EApBT,gBAoBS,EAAA;EAYA;SA7BR;;;AChBT;AA2KA;AAOgB,UD5JC,cAAA,CC4JiB;;;;ECnFlB,IAAA,EAAA,MAAA;EAAwB;EAAA,IACjC,EFlEC,WEkED;EAAM;EACK,OAAA,CAAA,EFhEN,KEgEM,CFhEA,WEgEA,GFhEc,gBEgEd,CAAA;EAyCF;EAUA,aAAA,CAAA,EAAa,MAAA,EAAA;EAUb;;;;;;UFjHC,eAAA;;;;;;;;QAWT;;;;;AA1DR;AAKA;AAKA;AAA4B,cCRf,SDQe,ECRJ,cDQI,EAAA;;;;AAQH,iBC2JT,WAAA,CD3JS,IAAA,EAAA,MAAA,CAAA,EC2JkB,cD3JlB,GAAA,SAAA;AAMzB;;;AAWkB,iBCiJF,kBAAA,CDjJE,IAAA,EAAA,OAAA,GAAA,aAAA,GAAA,QAAA,CAAA,ECmJf,cDnJe,EAAA;;;;AAnClB;AAKA;AAKA;AAA4B,iBEuFZ,wBAAA,CFvFY,GAAA,CAAA,EEwFrB,MFxFqB,CAAA,MAAA,EAAA,MAAA,GAAA,SAAA,CAAA,CAAA,EEyFzB,eFzFyB;;;;;AAc5B;;;AAWkB,iBEyGF,OAAA,CFzGE,GAAA,CAAA,EE0GX,MF1GW,CAAA,MAAA,EAAA,MAAA,GAAA,SAAA,CAAA,CAAA,EAAA,OAAA;;;AAAD;AAYA,iBEuGD,aAAA,CF5FR,GAAW,CAAX,EE6FD,MF7FY,CAAA,MAAA,EAAA,MAAA,GAAA,SAAA,CAAA,CAAA,EAAA,OAAA;;;;ACxDN,iBC8JG,QAAA,CD9JQ,GAAc,CAAd,EC+JjB,MD/J+B,CAAA,MAAA,EAAA,MAAA,GAAA,SAAA,CAAA,CAAA,EAAA,OAAA;AA2KtC"}
package/dist/index.js CHANGED
@@ -1,22 +1,8 @@
1
- import {
2
- detectAgenticEnvironment,
3
- getProvider,
4
- getProvidersByType,
5
- isAgent,
6
- isHybrid,
7
- isInteractive,
8
- providers
9
- } from "./chunk-EFLDW3WY.js";
1
+ import { detectAgenticEnvironment, getProvider, getProvidersByType, isAgent, isHybrid, isInteractive, providers } from "./detector-BEnp3d4c.js";
10
2
 
11
- // src/index.ts
12
- var index_default = detectAgenticEnvironment;
13
- export {
14
- index_default as default,
15
- detectAgenticEnvironment,
16
- getProvider,
17
- getProvidersByType,
18
- isAgent,
19
- isHybrid,
20
- isInteractive,
21
- providers
22
- };
3
+ //#region src/index.ts
4
+ var src_default = detectAgenticEnvironment;
5
+
6
+ //#endregion
7
+ export { src_default as default, detectAgenticEnvironment, getProvider, getProvidersByType, isAgent, isHybrid, isInteractive, providers };
8
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","names":[],"sources":["../src/index.ts"],"sourcesContent":["/**\n * am-i-vibing - Detect agentic coding environments and AI assistant tools\n */\n\n// Export types\nexport type { AgenticType, ProviderConfig, DetectionResult } from \"./types.js\";\n\n// Export providers\nexport { providers, getProvider, getProvidersByType } from \"./providers.js\";\n\n// Export detection functions\nexport {\n detectAgenticEnvironment,\n isAgent,\n isInteractive,\n isHybrid,\n} from \"./detector.js\";\n\n// Import for default export\nimport { detectAgenticEnvironment } from \"./detector.js\";\n\n// Convenience export for the main function\nexport default detectAgenticEnvironment;\n"],"mappings":";;;AAsBA,kBAAe"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "am-i-vibing",
3
- "version": "0.0.2",
3
+ "version": "0.0.4",
4
4
  "description": "Detect agentic coding environments and AI assistant tools",
5
5
  "type": "module",
6
6
  "main": "dist/index.js",
@@ -15,11 +15,11 @@
15
15
  },
16
16
  "devDependencies": {
17
17
  "@arethetypeswrong/cli": "^0.18.2",
18
- "@types/node": "^20.0.0",
18
+ "@types/node": "^22.16.5",
19
19
  "publint": "^0.3.12",
20
- "tsup": "^8.5.0",
20
+ "tsdown": "^0.12.9",
21
21
  "typescript": "^5.8.3",
22
- "vitest": "^2.0.0"
22
+ "vitest": "^3.2.4"
23
23
  },
24
24
  "repository": {
25
25
  "type": "git",
@@ -41,8 +41,8 @@
41
41
  "process-ancestry": "^0.0.2"
42
42
  },
43
43
  "scripts": {
44
- "build": "tsup src/index.ts src/cli.ts --format esm --dts --clean",
45
- "dev": "tsup src/index.ts src/cli.ts --format esm --dts --watch",
44
+ "build": "tsdown src/index.ts src/cli.ts --format esm --dts --clean",
45
+ "dev": "tsdown src/index.ts src/cli.ts --format esm --dts --watch",
46
46
  "check": "publint && attw --pack --ignore-rules=cjs-resolves-to-esm",
47
47
  "test": "vitest run",
48
48
  "whoami": "tsx scripts/whoami.ts"
@@ -1,243 +0,0 @@
1
- // src/providers.ts
2
- var providers = [
3
- {
4
- id: "claude-code",
5
- name: "Claude Code",
6
- type: "agent",
7
- envVars: ["CLAUDECODE"]
8
- },
9
- {
10
- id: "cursor-agent",
11
- name: "Cursor Agent",
12
- type: "agent",
13
- envVars: [
14
- {
15
- all: ["CURSOR_TRACE_ID", ["PAGER", "head -n 10000 | cat"]]
16
- }
17
- ]
18
- },
19
- {
20
- id: "cursor",
21
- name: "Cursor",
22
- type: "interactive",
23
- envVars: ["CURSOR_TRACE_ID"]
24
- },
25
- {
26
- id: "gemini-agent",
27
- name: "Gemini Agent",
28
- type: "agent",
29
- processChecks: ["gemini"]
30
- },
31
- {
32
- id: "codex",
33
- name: "OpenAI Codex",
34
- type: "agent",
35
- processChecks: ["codex"]
36
- },
37
- {
38
- id: "replit",
39
- name: "Replit",
40
- type: "agent",
41
- envVars: ["REPL_ID"]
42
- },
43
- {
44
- id: "aider",
45
- name: "Aider",
46
- type: "agent",
47
- envVars: ["AIDER_API_KEY"],
48
- processChecks: ["aider"]
49
- },
50
- {
51
- id: "bolt-agent",
52
- name: "Bolt.new Agent",
53
- type: "agent",
54
- envVars: [
55
- {
56
- all: [["SHELL", "/bin/jsh"], "npm_config_yes"]
57
- }
58
- ]
59
- },
60
- {
61
- id: "bolt",
62
- name: "Bolt.new",
63
- type: "interactive",
64
- envVars: [
65
- {
66
- all: [["SHELL", "/bin/jsh"]],
67
- none: ["npm_config_yes"]
68
- }
69
- ]
70
- },
71
- {
72
- id: "zed-agent",
73
- name: "Zed Agent",
74
- type: "agent",
75
- envVars: [
76
- {
77
- all: [
78
- ["TERM_PROGRAM", "zed"],
79
- ["PAGER", "cat"]
80
- ]
81
- }
82
- ]
83
- },
84
- {
85
- id: "zed",
86
- name: "Zed",
87
- type: "interactive",
88
- envVars: [
89
- {
90
- all: [["TERM_PROGRAM", "zed"]],
91
- none: [["PAGER", "cat"]]
92
- }
93
- ]
94
- },
95
- {
96
- id: "replit-assistant",
97
- name: "Replit Assistant",
98
- type: "agent",
99
- envVars: [
100
- {
101
- all: ["REPL_ID", ["REPLIT_MODE", "assistant"]]
102
- }
103
- ]
104
- },
105
- {
106
- id: "replit",
107
- name: "Replit",
108
- type: "interactive",
109
- envVars: [
110
- {
111
- all: ["REPL_ID"],
112
- none: [["REPLIT_MODE", "assistant"]]
113
- }
114
- ]
115
- },
116
- {
117
- id: "windsurf",
118
- name: "Windsurf",
119
- type: "agent",
120
- envVars: ["CODEIUM_EDITOR_APP_ROOT"]
121
- },
122
- {
123
- id: "vscode-copilot-agent",
124
- name: "GitHub Copilot in VS Code",
125
- type: "agent",
126
- envVars: [
127
- {
128
- all: [
129
- ["TERM_PROGRAM", "vscode"],
130
- ["GIT_PAGER", "cat"]
131
- ]
132
- }
133
- ]
134
- },
135
- {
136
- id: "warp",
137
- name: "Warp Terminal",
138
- type: "hybrid",
139
- envVars: [
140
- {
141
- all: [
142
- ["TERM_PROGRAM", "WarpTerminal"]
143
- ]
144
- }
145
- ]
146
- }
147
- ];
148
- function getProvider(name) {
149
- return providers.find((p) => p.name === name);
150
- }
151
- function getProvidersByType(type) {
152
- return providers.filter((p) => p.type === type);
153
- }
154
-
155
- // src/detector.ts
156
- import { getProcessAncestry } from "process-ancestry";
157
- function checkEnvVar(envVarDef, env = process.env) {
158
- const [envVar, expectedValue] = typeof envVarDef === "string" ? [envVarDef, void 0] : envVarDef;
159
- const actualValue = env[envVar];
160
- return Boolean(
161
- actualValue && (!expectedValue || actualValue === expectedValue)
162
- );
163
- }
164
- function checkProcess(processName) {
165
- try {
166
- const ancestry = getProcessAncestry();
167
- for (const ancestorProcess of ancestry) {
168
- if (ancestorProcess.command?.includes(processName)) {
169
- return true;
170
- }
171
- }
172
- } catch (error) {
173
- }
174
- return false;
175
- }
176
- function checkEnvVars(definition, env = process.env) {
177
- if (typeof definition === "string" || Array.isArray(definition)) {
178
- return checkEnvVar(definition, env);
179
- }
180
- const { any, all, none } = definition;
181
- const anyResult = !any?.length || any.some((envVar) => checkEnvVar(envVar, env));
182
- const allResult = !all?.length || all.every((envVar) => checkEnvVar(envVar, env));
183
- const noneResult = !none?.length || !none.some((envVar) => checkEnvVar(envVar, env));
184
- return anyResult && allResult && noneResult;
185
- }
186
- function runCustomDetectors(provider) {
187
- return provider.customDetectors?.some((detector) => {
188
- try {
189
- return detector();
190
- } catch {
191
- return false;
192
- }
193
- }) ?? false;
194
- }
195
- function createDetectedResult(provider) {
196
- return {
197
- isAgentic: true,
198
- id: provider.id,
199
- name: provider.name,
200
- type: provider.type
201
- };
202
- }
203
- function detectAgenticEnvironment(env = process.env) {
204
- for (const provider of providers) {
205
- if (provider.envVars?.some((group) => checkEnvVars(group, env))) {
206
- return createDetectedResult(provider);
207
- }
208
- if (provider.processChecks?.some(checkProcess)) {
209
- return createDetectedResult(provider);
210
- }
211
- if (runCustomDetectors(provider)) {
212
- return createDetectedResult(provider);
213
- }
214
- }
215
- return {
216
- isAgentic: false,
217
- id: null,
218
- name: null,
219
- type: null
220
- };
221
- }
222
- function isAgent(env = process.env) {
223
- const result = detectAgenticEnvironment(env);
224
- return result.type === "agent" || result.type === "hybrid";
225
- }
226
- function isInteractive(env = process.env) {
227
- const result = detectAgenticEnvironment(env);
228
- return result.type === "interactive" || result.type === "hybrid";
229
- }
230
- function isHybrid(env = process.env) {
231
- const result = detectAgenticEnvironment(env);
232
- return result.type === "hybrid";
233
- }
234
-
235
- export {
236
- providers,
237
- getProvider,
238
- getProvidersByType,
239
- detectAgenticEnvironment,
240
- isAgent,
241
- isInteractive,
242
- isHybrid
243
- };