copilotkit 0.0.57 → 0.0.59

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 (66) hide show
  1. package/LICENSE +21 -0
  2. package/dist/commands/base-command.js +9 -6
  3. package/dist/commands/base-command.js.map +1 -1
  4. package/dist/commands/create.d.ts +1 -1
  5. package/dist/commands/create.js +234 -59
  6. package/dist/commands/create.js.map +1 -1
  7. package/dist/commands/dev.js +94 -35
  8. package/dist/commands/dev.js.map +1 -1
  9. package/dist/commands/init.d.ts +0 -20
  10. package/dist/commands/init.js +243 -209
  11. package/dist/commands/init.js.map +1 -1
  12. package/dist/commands/login.js +44 -20
  13. package/dist/commands/login.js.map +1 -1
  14. package/dist/commands/logout.js +44 -20
  15. package/dist/commands/logout.js.map +1 -1
  16. package/dist/index.js.map +1 -1
  17. package/dist/lib/init/ide-docs.d.ts +1 -1
  18. package/dist/lib/init/ide-docs.js +19 -5
  19. package/dist/lib/init/ide-docs.js.map +1 -1
  20. package/dist/lib/init/index.js +171 -67
  21. package/dist/lib/init/index.js.map +1 -1
  22. package/dist/lib/init/questions.d.ts +1 -1
  23. package/dist/lib/init/questions.js +77 -18
  24. package/dist/lib/init/questions.js.map +1 -1
  25. package/dist/lib/init/scaffold/agent.js +30 -23
  26. package/dist/lib/init/scaffold/agent.js.map +1 -1
  27. package/dist/lib/init/scaffold/crew-inputs.js +17 -4
  28. package/dist/lib/init/scaffold/crew-inputs.js.map +1 -1
  29. package/dist/lib/init/scaffold/env.js +14 -11
  30. package/dist/lib/init/scaffold/env.js.map +1 -1
  31. package/dist/lib/init/scaffold/github.js +27 -6
  32. package/dist/lib/init/scaffold/github.js.map +1 -1
  33. package/dist/lib/init/scaffold/index.js +152 -62
  34. package/dist/lib/init/scaffold/index.js.map +1 -1
  35. package/dist/lib/init/scaffold/langgraph-assistants.js +14 -11
  36. package/dist/lib/init/scaffold/langgraph-assistants.js.map +1 -1
  37. package/dist/lib/init/scaffold/packages.js +3 -1
  38. package/dist/lib/init/scaffold/packages.js.map +1 -1
  39. package/dist/lib/init/scaffold/shadcn.js +88 -23
  40. package/dist/lib/init/scaffold/shadcn.js.map +1 -1
  41. package/dist/lib/init/types/index.js +77 -18
  42. package/dist/lib/init/types/index.js.map +1 -1
  43. package/dist/lib/init/types/questions.d.ts +19 -19
  44. package/dist/lib/init/types/questions.js +73 -17
  45. package/dist/lib/init/types/questions.js.map +1 -1
  46. package/dist/lib/init/types/templates.d.ts +2 -2
  47. package/dist/lib/init/types/templates.js +4 -1
  48. package/dist/lib/init/types/templates.js.map +1 -1
  49. package/dist/lib/init/utils.js.map +1 -1
  50. package/dist/services/analytics.service.d.ts +1 -1
  51. package/dist/services/analytics.service.js +4 -1
  52. package/dist/services/analytics.service.js.map +1 -1
  53. package/dist/services/auth.service.d.ts +1 -1
  54. package/dist/services/auth.service.js +35 -14
  55. package/dist/services/auth.service.js.map +1 -1
  56. package/dist/services/events.d.ts +33 -33
  57. package/dist/services/tunnel.service.js.map +1 -1
  58. package/dist/utils/detect-endpoint-type.utils.d.ts +1 -1
  59. package/dist/utils/detect-endpoint-type.utils.js +11 -4
  60. package/dist/utils/detect-endpoint-type.utils.js.map +1 -1
  61. package/dist/utils/trpc.js.map +1 -1
  62. package/dist/utils/version.d.ts +1 -1
  63. package/dist/utils/version.js +1 -1
  64. package/dist/utils/version.js.map +1 -1
  65. package/oclif.manifest.json +6 -163
  66. package/package.json +8 -4
package/LICENSE ADDED
@@ -0,0 +1,21 @@
1
+ The MIT License
2
+
3
+ Copyright (c) Atai Barkai
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
13
+ all 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
21
+ THE SOFTWARE.
@@ -3,7 +3,7 @@ import { Command } from "@oclif/core";
3
3
  import Sentry, { consoleIntegration } from "@sentry/node";
4
4
 
5
5
  // src/utils/version.ts
6
- var LIB_VERSION = "0.0.57";
6
+ var LIB_VERSION = "0.0.59";
7
7
 
8
8
  // src/utils/trpc.ts
9
9
  import { createTRPCClient as trpcClient, httpBatchLink } from "@trpc/client";
@@ -44,11 +44,14 @@ var BaseCommand = class extends Command {
44
44
  async run() {
45
45
  }
46
46
  async checkCLIVersion() {
47
- const response = await fetch(`${COPILOT_CLOUD_BASE_URL}/api/healthz`);
48
- const data = await response.json();
49
- const cloudVersion = data.cliVersion;
50
- if (!cloudVersion || cloudVersion === LIB_VERSION) {
51
- return;
47
+ try {
48
+ const response = await fetch(`${COPILOT_CLOUD_BASE_URL}/api/healthz`);
49
+ const data = await response.json();
50
+ const cloudVersion = data.cliVersion;
51
+ if (!cloudVersion || cloudVersion === LIB_VERSION) {
52
+ return;
53
+ }
54
+ } catch {
52
55
  }
53
56
  }
54
57
  async gracefulError(message) {
@@ -1 +1 @@
1
- {"version":3,"sources":["../../src/commands/base-command.ts","../../src/utils/version.ts","../../src/utils/trpc.ts"],"sourcesContent":["import {Command} from '@oclif/core'\nimport Sentry, {consoleIntegration} from '@sentry/node'\nimport {LIB_VERSION} from '../utils/version.js'\nimport {COPILOT_CLOUD_BASE_URL} from '../utils/trpc.js'\nimport chalk from 'chalk'\n\nexport class BaseCommand extends Command {\n async init() {\n await this.checkCLIVersion()\n\n if (process.env.SENTRY_DISABLED === 'true') {\n return\n }\n\n Sentry.init({\n dsn:\n process.env.SENTRY_DSN ||\n 'https://1eea15d32e2eacb0456a77db5e39aeeb@o4507288195170304.ingest.us.sentry.io/4508581448581120',\n integrations: [consoleIntegration()],\n // Tracing\n tracesSampleRate: 1.0, // Capture 100% of the transactions\n })\n }\n\n async catch(err: any) {\n if (process.env.SENTRY_DISABLED !== 'true') {\n Sentry.captureException(err)\n }\n\n const message = err?.message ?? 'Unknown error'\n\n this.log('\\n' + chalk.red(message) + '\\n')\n\n const exitCode = err?.oclif?.exit ?? 1\n this.exit(exitCode)\n }\n\n async finally() {\n if (process.env.SENTRY_DISABLED === 'true') {\n return\n }\n\n Sentry.close()\n }\n\n async run() {}\n\n async checkCLIVersion() {\n const response = await fetch(`${COPILOT_CLOUD_BASE_URL}/api/healthz`)\n\n const data = await response.json()\n const cloudVersion = data.cliVersion\n\n if (!cloudVersion || cloudVersion === LIB_VERSION) {\n return\n }\n\n // TODO: add this back in, removed for crew ai launch since we don't want to keep releasing cloud\n // this.log(chalk.yellow('================ New version available! =================\\n'))\n // this.log(`You are using CopilotKit CLI v${LIB_VERSION}.`)\n // this.log(`A new CopilotKit CLI version is available (v${cloudVersion}).\\n`)\n // this.log('Please update your CLI to the latest version:\\n\\n')\n // this.log(`${chalk.cyan(chalk.underline(chalk.bold('npm:')))}\\t npm install -g copilotkit@${cloudVersion}\\n`)\n // this.log(`${chalk.cyan(chalk.underline(chalk.bold('pnpm:')))}\\t pnpm install -g copilotkit@${cloudVersion}\\n`)\n // this.log(`${chalk.cyan(chalk.underline(chalk.bold('yarn:')))}\\t yarn global add copilotkit@${cloudVersion}\\n`)\n // this.log(chalk.yellow('============================================================\\n\\n'))\n }\n\n async gracefulError(message: string) {\n this.log('\\n' + chalk.red(message))\n process.exit(1)\n }\n}\n","// This is auto generated!\nexport const LIB_VERSION = \"0.0.57\";\n","import {createTRPCClient as trpcClient, httpBatchLink} from '@trpc/client'\nimport superjson from 'superjson'\n\nexport const COPILOT_CLOUD_BASE_URL = process.env.COPILOT_CLOUD_BASE_URL || 'https://cloud.copilotkit.ai'\n\nexport function createTRPCClient(cliToken: string): any {\n return trpcClient({\n links: [\n httpBatchLink({\n url: `${COPILOT_CLOUD_BASE_URL}/api/trpc-cli`,\n transformer: superjson,\n headers: () => {\n return {\n 'x-trpc-source': 'cli',\n 'x-cli-token': cliToken,\n }\n },\n }),\n ],\n })\n}\n"],"mappings":";AAAA,SAAQ,eAAc;AACtB,OAAO,UAAS,0BAAyB;;;ACAlC,IAAM,cAAc;;;ACD3B,SAAQ,oBAAoB,YAAY,qBAAoB;AAC5D,OAAO,eAAe;AAEf,IAAM,yBAAyB,QAAQ,IAAI,0BAA0B;;;AFC5E,OAAO,WAAW;AAEX,IAAM,cAAN,cAA0B,QAAQ;AAAA,EACvC,MAAM,OAAO;AACX,UAAM,KAAK,gBAAgB;AAE3B,QAAI,QAAQ,IAAI,oBAAoB,QAAQ;AAC1C;AAAA,IACF;AAEA,WAAO,KAAK;AAAA,MACV,KACE,QAAQ,IAAI,cACZ;AAAA,MACF,cAAc,CAAC,mBAAmB,CAAC;AAAA;AAAA,MAEnC,kBAAkB;AAAA;AAAA,IACpB,CAAC;AAAA,EACH;AAAA,EAEA,MAAM,MAAM,KAAU;AACpB,QAAI,QAAQ,IAAI,oBAAoB,QAAQ;AAC1C,aAAO,iBAAiB,GAAG;AAAA,IAC7B;AAEA,UAAM,UAAU,KAAK,WAAW;AAEhC,SAAK,IAAI,OAAO,MAAM,IAAI,OAAO,IAAI,IAAI;AAEzC,UAAM,WAAW,KAAK,OAAO,QAAQ;AACrC,SAAK,KAAK,QAAQ;AAAA,EACpB;AAAA,EAEA,MAAM,UAAU;AACd,QAAI,QAAQ,IAAI,oBAAoB,QAAQ;AAC1C;AAAA,IACF;AAEA,WAAO,MAAM;AAAA,EACf;AAAA,EAEA,MAAM,MAAM;AAAA,EAAC;AAAA,EAEb,MAAM,kBAAkB;AACtB,UAAM,WAAW,MAAM,MAAM,GAAG,sBAAsB,cAAc;AAEpE,UAAM,OAAO,MAAM,SAAS,KAAK;AACjC,UAAM,eAAe,KAAK;AAE1B,QAAI,CAAC,gBAAgB,iBAAiB,aAAa;AACjD;AAAA,IACF;AAAA,EAWF;AAAA,EAEA,MAAM,cAAc,SAAiB;AACnC,SAAK,IAAI,OAAO,MAAM,IAAI,OAAO,CAAC;AAClC,YAAQ,KAAK,CAAC;AAAA,EAChB;AACF;","names":[]}
1
+ {"version":3,"sources":["../../src/commands/base-command.ts","../../src/utils/version.ts","../../src/utils/trpc.ts"],"sourcesContent":["import { Command } from \"@oclif/core\";\nimport Sentry, { consoleIntegration } from \"@sentry/node\";\nimport { LIB_VERSION } from \"../utils/version.js\";\nimport { COPILOT_CLOUD_BASE_URL } from \"../utils/trpc.js\";\nimport chalk from \"chalk\";\n\nexport class BaseCommand extends Command {\n async init() {\n await this.checkCLIVersion();\n\n if (process.env.SENTRY_DISABLED === \"true\") {\n return;\n }\n\n Sentry.init({\n dsn:\n process.env.SENTRY_DSN ||\n \"https://1eea15d32e2eacb0456a77db5e39aeeb@o4507288195170304.ingest.us.sentry.io/4508581448581120\",\n integrations: [consoleIntegration()],\n // Tracing\n tracesSampleRate: 1.0, // Capture 100% of the transactions\n });\n }\n\n async catch(err: any) {\n if (process.env.SENTRY_DISABLED !== \"true\") {\n Sentry.captureException(err);\n }\n\n const message = err?.message ?? \"Unknown error\";\n\n this.log(\"\\n\" + chalk.red(message) + \"\\n\");\n\n const exitCode = err?.oclif?.exit ?? 1;\n this.exit(exitCode);\n }\n\n async finally() {\n if (process.env.SENTRY_DISABLED === \"true\") {\n return;\n }\n\n Sentry.close();\n }\n\n async run() {}\n\n async checkCLIVersion() {\n try {\n const response = await fetch(`${COPILOT_CLOUD_BASE_URL}/api/healthz`);\n\n const data = await response.json();\n const cloudVersion = data.cliVersion;\n\n if (!cloudVersion || cloudVersion === LIB_VERSION) {\n return;\n }\n\n // TODO: add this back in, removed for crew ai launch since we don't want to keep releasing cloud\n // this.log(chalk.yellow('================ New version available! =================\\n'))\n // this.log(`You are using CopilotKit CLI v${LIB_VERSION}.`)\n // this.log(`A new CopilotKit CLI version is available (v${cloudVersion}).\\n`)\n // this.log('Please update your CLI to the latest version:\\n\\n')\n // this.log(`${chalk.cyan(chalk.underline(chalk.bold('npm:')))}\\t npm install -g copilotkit@${cloudVersion}\\n`)\n // this.log(`${chalk.cyan(chalk.underline(chalk.bold('pnpm:')))}\\t pnpm install -g copilotkit@${cloudVersion}\\n`)\n // this.log(`${chalk.cyan(chalk.underline(chalk.bold('yarn:')))}\\t yarn global add copilotkit@${cloudVersion}\\n`)\n // this.log(chalk.yellow('============================================================\\n\\n'))\n } catch {\n // Version check is non-critical — don't crash the CLI when offline\n }\n }\n\n async gracefulError(message: string) {\n this.log(\"\\n\" + chalk.red(message));\n process.exit(1);\n }\n}\n","// This is auto generated!\nexport const LIB_VERSION = \"0.0.59\";\n","import { createTRPCClient as trpcClient, httpBatchLink } from \"@trpc/client\";\nimport superjson from \"superjson\";\n\nexport const COPILOT_CLOUD_BASE_URL =\n process.env.COPILOT_CLOUD_BASE_URL || \"https://cloud.copilotkit.ai\";\n\nexport function createTRPCClient(cliToken: string): any {\n return trpcClient({\n links: [\n httpBatchLink({\n url: `${COPILOT_CLOUD_BASE_URL}/api/trpc-cli`,\n transformer: superjson,\n headers: () => {\n return {\n \"x-trpc-source\": \"cli\",\n \"x-cli-token\": cliToken,\n };\n },\n }),\n ],\n });\n}\n"],"mappings":";AAAA,SAAS,eAAe;AACxB,OAAO,UAAU,0BAA0B;;;ACApC,IAAM,cAAc;;;ACD3B,SAAS,oBAAoB,YAAY,qBAAqB;AAC9D,OAAO,eAAe;AAEf,IAAM,yBACX,QAAQ,IAAI,0BAA0B;;;AFAxC,OAAO,WAAW;AAEX,IAAM,cAAN,cAA0B,QAAQ;AAAA,EACvC,MAAM,OAAO;AACX,UAAM,KAAK,gBAAgB;AAE3B,QAAI,QAAQ,IAAI,oBAAoB,QAAQ;AAC1C;AAAA,IACF;AAEA,WAAO,KAAK;AAAA,MACV,KACE,QAAQ,IAAI,cACZ;AAAA,MACF,cAAc,CAAC,mBAAmB,CAAC;AAAA;AAAA,MAEnC,kBAAkB;AAAA;AAAA,IACpB,CAAC;AAAA,EACH;AAAA,EAEA,MAAM,MAAM,KAAU;AACpB,QAAI,QAAQ,IAAI,oBAAoB,QAAQ;AAC1C,aAAO,iBAAiB,GAAG;AAAA,IAC7B;AAEA,UAAM,UAAU,KAAK,WAAW;AAEhC,SAAK,IAAI,OAAO,MAAM,IAAI,OAAO,IAAI,IAAI;AAEzC,UAAM,WAAW,KAAK,OAAO,QAAQ;AACrC,SAAK,KAAK,QAAQ;AAAA,EACpB;AAAA,EAEA,MAAM,UAAU;AACd,QAAI,QAAQ,IAAI,oBAAoB,QAAQ;AAC1C;AAAA,IACF;AAEA,WAAO,MAAM;AAAA,EACf;AAAA,EAEA,MAAM,MAAM;AAAA,EAAC;AAAA,EAEb,MAAM,kBAAkB;AACtB,QAAI;AACF,YAAM,WAAW,MAAM,MAAM,GAAG,sBAAsB,cAAc;AAEpE,YAAM,OAAO,MAAM,SAAS,KAAK;AACjC,YAAM,eAAe,KAAK;AAE1B,UAAI,CAAC,gBAAgB,iBAAiB,aAAa;AACjD;AAAA,MACF;AAAA,IAWF,QAAQ;AAAA,IAER;AAAA,EACF;AAAA,EAEA,MAAM,cAAc,SAAiB;AACnC,SAAK,IAAI,OAAO,MAAM,IAAI,OAAO,CAAC;AAClC,YAAQ,KAAK,CAAC;AAAA,EAChB;AACF;","names":[]}
@@ -8,7 +8,7 @@ declare class Create extends BaseCommand {
8
8
  static flags: {
9
9
  framework: _oclif_core_interfaces.OptionFlag<string | undefined, _oclif_core_interfaces.CustomOptions>;
10
10
  name: _oclif_core_interfaces.OptionFlag<string | undefined, _oclif_core_interfaces.CustomOptions>;
11
- 'no-banner': _oclif_core_interfaces.BooleanFlag<boolean>;
11
+ "no-banner": _oclif_core_interfaces.BooleanFlag<boolean>;
12
12
  project: _oclif_core_interfaces.OptionFlag<string | undefined, _oclif_core_interfaces.CustomOptions>;
13
13
  };
14
14
  static args: {
@@ -1,9 +1,9 @@
1
1
  // src/commands/create.ts
2
2
  import { Flags, Args } from "@oclif/core";
3
3
  import inquirer from "inquirer";
4
- import chalk2 from "chalk";
5
- import fs from "fs-extra";
6
- import path from "path";
4
+ import chalk3 from "chalk";
5
+ import fs2 from "fs-extra";
6
+ import path2 from "path";
7
7
  import { promisify } from "util";
8
8
  import { pipeline } from "stream";
9
9
  import { createWriteStream } from "fs";
@@ -15,7 +15,7 @@ import { Command } from "@oclif/core";
15
15
  import Sentry, { consoleIntegration } from "@sentry/node";
16
16
 
17
17
  // src/utils/version.ts
18
- var LIB_VERSION = "0.0.57";
18
+ var LIB_VERSION = "0.0.59";
19
19
 
20
20
  // src/utils/trpc.ts
21
21
  import { createTRPCClient as trpcClient, httpBatchLink } from "@trpc/client";
@@ -56,11 +56,14 @@ var BaseCommand = class extends Command {
56
56
  async run() {
57
57
  }
58
58
  async checkCLIVersion() {
59
- const response = await fetch(`${COPILOT_CLOUD_BASE_URL}/api/healthz`);
60
- const data = await response.json();
61
- const cloudVersion = data.cliVersion;
62
- if (!cloudVersion || cloudVersion === LIB_VERSION) {
63
- return;
59
+ try {
60
+ const response = await fetch(`${COPILOT_CLOUD_BASE_URL}/api/healthz`);
61
+ const data = await response.json();
62
+ const cloudVersion = data.cliVersion;
63
+ if (!cloudVersion || cloudVersion === LIB_VERSION) {
64
+ return;
65
+ }
66
+ } catch {
64
67
  }
65
68
  }
66
69
  async gracefulError(message) {
@@ -69,33 +72,144 @@ var BaseCommand = class extends Command {
69
72
  }
70
73
  };
71
74
 
75
+ // src/lib/init/scaffold/github.ts
76
+ import { execSync } from "child_process";
77
+ import * as fs from "fs";
78
+ import * as path from "path";
79
+ import * as os from "os";
80
+ import chalk2 from "chalk";
81
+ async function cloneGitHubSubdirectory(githubUrl, destinationPath, spinner) {
82
+ try {
83
+ const { owner, repo, branch, subdirectoryPath } = parseGitHubUrl(githubUrl);
84
+ spinner.text = chalk2.cyan(`Cloning from ${owner}/${repo}...`);
85
+ return await sparseCheckout(
86
+ owner,
87
+ repo,
88
+ branch,
89
+ subdirectoryPath,
90
+ destinationPath,
91
+ spinner
92
+ );
93
+ } catch (error) {
94
+ spinner.text = chalk2.red(`Failed to clone from GitHub: ${error}`);
95
+ return false;
96
+ }
97
+ }
98
+ async function sparseCheckout(owner, repo, branch, subdirectoryPath, destinationPath, spinner) {
99
+ const tempDir = fs.mkdtempSync(path.join(os.tmpdir(), "copilotkit-sparse-"));
100
+ try {
101
+ spinner.text = chalk2.cyan("Creating temporary workspace...");
102
+ execSync("git init", { cwd: tempDir, stdio: "pipe" });
103
+ spinner.text = chalk2.cyan("Connecting to repository...");
104
+ execSync(`git remote add origin https://github.com/${owner}/${repo}.git`, {
105
+ cwd: tempDir,
106
+ stdio: "pipe"
107
+ });
108
+ execSync("git config core.sparseCheckout true", {
109
+ cwd: tempDir,
110
+ stdio: "pipe"
111
+ });
112
+ fs.writeFileSync(
113
+ path.join(tempDir, ".git/info/sparse-checkout"),
114
+ subdirectoryPath
115
+ );
116
+ spinner.text = chalk2.cyan("Downloading agent files...");
117
+ execSync(`git pull origin ${branch} --depth=1`, {
118
+ cwd: tempDir,
119
+ stdio: "pipe"
120
+ });
121
+ const sourcePath = path.join(tempDir, subdirectoryPath);
122
+ if (!fs.existsSync(sourcePath)) {
123
+ throw new Error(
124
+ `Subdirectory '${subdirectoryPath}' not found in the repository.`
125
+ );
126
+ }
127
+ fs.mkdirSync(destinationPath, { recursive: true });
128
+ spinner.text = chalk2.cyan("Installing agent files...");
129
+ await copyDirectoryAsync(sourcePath, destinationPath);
130
+ return true;
131
+ } finally {
132
+ try {
133
+ fs.rmSync(tempDir, { recursive: true, force: true });
134
+ } catch (error) {
135
+ console.warn(`Failed to clean up temporary directory: ${error}`);
136
+ }
137
+ }
138
+ }
139
+ async function copyDirectoryAsync(source, destination) {
140
+ if (!fs.existsSync(destination)) {
141
+ fs.mkdirSync(destination, { recursive: true });
142
+ }
143
+ const entries = fs.readdirSync(source, { withFileTypes: true });
144
+ for (const entry of entries) {
145
+ const srcPath = path.join(source, entry.name);
146
+ const destPath = path.join(destination, entry.name);
147
+ if (entry.isDirectory()) {
148
+ await copyDirectoryAsync(srcPath, destPath);
149
+ } else {
150
+ fs.copyFileSync(srcPath, destPath);
151
+ }
152
+ if (entries.length > 10) {
153
+ await new Promise((resolve) => setTimeout(resolve, 1));
154
+ }
155
+ }
156
+ }
157
+ function parseGitHubUrl(githubUrl) {
158
+ const url = new URL(githubUrl);
159
+ if (url.hostname !== "github.com") {
160
+ throw new Error("Only GitHub URLs are supported");
161
+ }
162
+ const pathParts = url.pathname.split("/").filter(Boolean);
163
+ if (pathParts.length < 2) {
164
+ throw new Error("Invalid GitHub URL format");
165
+ }
166
+ const owner = pathParts[0];
167
+ const repo = pathParts[1];
168
+ let branch = "main";
169
+ let subdirectoryPath = "";
170
+ if (pathParts.length > 3 && (pathParts[2] === "tree" || pathParts[2] === "blob")) {
171
+ branch = pathParts[3];
172
+ subdirectoryPath = pathParts.slice(4).join("/");
173
+ }
174
+ return { owner, repo, branch, subdirectoryPath };
175
+ }
176
+ function isValidGitHubUrl(url) {
177
+ try {
178
+ const parsedUrl = new URL(url);
179
+ return parsedUrl.hostname === "github.com" && parsedUrl.pathname.split("/").filter(Boolean).length >= 2;
180
+ } catch {
181
+ return false;
182
+ }
183
+ }
184
+
72
185
  // src/commands/create.ts
73
186
  var streamPipeline = promisify(pipeline);
74
187
  var theme = {
75
- primary: chalk2.magenta,
76
- secondary: chalk2.gray,
77
- tertiary: chalk2.gray,
78
- error: chalk2.red,
79
- command: chalk2.blue,
80
- success: chalk2.green,
81
- warning: chalk2.yellow,
82
- divider: chalk2.gray("\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501"),
188
+ primary: chalk3.magenta,
189
+ secondary: chalk3.gray,
190
+ tertiary: chalk3.gray,
191
+ error: chalk3.red,
192
+ command: chalk3.blue,
193
+ success: chalk3.green,
194
+ warning: chalk3.yellow,
195
+ divider: chalk3.gray("\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501"),
83
196
  bottomPadding: ""
84
197
  };
85
198
  var TEMPLATE_REPOS = {
86
- "langgraph-py": "copilotkit/with-langgraph-python",
87
- "langgraph-js": "copilotkit/with-langgraph-js",
88
- mastra: "copilotkit/with-mastra",
89
- flows: "copilotkit/with-crewai-flows",
90
- llamaindex: "copilotkit/with-llamaindex",
91
- agno: "copilotkit/with-agno",
92
- "pydantic-ai": "copilotkit/with-pydantic-ai",
199
+ "langgraph-py": "https://github.com/CopilotKit/CopilotKit/tree/main/examples/integrations/langgraph-python",
200
+ "langgraph-js": "https://github.com/CopilotKit/CopilotKit/tree/main/examples/integrations/langgraph-js",
201
+ mastra: "https://github.com/CopilotKit/CopilotKit/tree/main/examples/integrations/mastra",
202
+ flows: "https://github.com/CopilotKit/CopilotKit/tree/main/examples/integrations/crewai-flows",
203
+ llamaindex: "https://github.com/CopilotKit/CopilotKit/tree/main/examples/integrations/llamaindex",
204
+ agno: "https://github.com/CopilotKit/CopilotKit/tree/main/examples/integrations/agno",
205
+ "pydantic-ai": "https://github.com/CopilotKit/CopilotKit/tree/main/examples/integrations/pydantic-ai",
93
206
  ag2: "ag2ai/ag2-copilotkit-starter",
94
- adk: "copilotkit/with-adk",
95
- "aws-strands-py": "copilotkit/with-strands-python",
96
- a2a: "copilotkit/with-a2a-middleware",
97
- "microsoft-agent-framework-dotnet": "copilotkit/with-microsoft-agent-framework-dotnet",
98
- "microsoft-agent-framework-py": "copilotkit/with-microsoft-agent-framework-python"
207
+ adk: "https://github.com/CopilotKit/CopilotKit/tree/main/examples/integrations/adk",
208
+ "aws-strands-py": "https://github.com/CopilotKit/CopilotKit/tree/main/examples/integrations/strands-python",
209
+ a2a: "https://github.com/CopilotKit/CopilotKit/tree/main/examples/integrations/a2a-middleware",
210
+ "microsoft-agent-framework-dotnet": "https://github.com/CopilotKit/CopilotKit/tree/main/examples/integrations/ms-agent-framework-dotnet",
211
+ "microsoft-agent-framework-py": "https://github.com/CopilotKit/CopilotKit/tree/main/examples/integrations/ms-agent-framework-python",
212
+ "mcp-apps": "https://github.com/CopilotKit/CopilotKit/tree/main/examples/integrations/mcp-apps"
99
213
  };
100
214
  var FRAMEWORK_DOCUMENTATION = {
101
215
  "langgraph-py": "https://langchain-ai.github.io/langgraph/concepts/why-langgraph",
@@ -110,7 +224,8 @@ var FRAMEWORK_DOCUMENTATION = {
110
224
  "aws-strands-py": "https://strandsagents.com/latest/documentation/docs/",
111
225
  a2a: "https://a2a-protocol.org/latest/",
112
226
  "microsoft-agent-framework-dotnet": "https://learn.microsoft.com/en-us/agent-framework/",
113
- "microsoft-agent-framework-py": "https://learn.microsoft.com/en-us/agent-framework/"
227
+ "microsoft-agent-framework-py": "https://learn.microsoft.com/en-us/agent-framework/",
228
+ "mcp-apps": "https://modelcontextprotocol.github.io/ext-apps"
114
229
  };
115
230
  var FRAMEWORK_EMOJI = {
116
231
  "langgraph-js": "\u{1F99C}",
@@ -125,7 +240,8 @@ var FRAMEWORK_EMOJI = {
125
240
  a2a: "\u{1F916}",
126
241
  "aws-strands-py": "\u{1F9EC}",
127
242
  "microsoft-agent-framework-dotnet": "\u{1F7E6}",
128
- "microsoft-agent-framework-py": "\u{1F7E6}"
243
+ "microsoft-agent-framework-py": "\u{1F7E6}",
244
+ "mcp-apps": "\u264D"
129
245
  };
130
246
  var KITE = `
131
247
  \u28FF\u28FF\u28FF\u28FF\u28FF\u28FF\u28FF\u28FF\u28FF\u28FF\u28FF\u28FF\u28FF\u28FF\u28FF\u28FF\u28FF\u28FF\u28FF\u28FF\u28FF\u28FF\u28FF\u28FF\u28FF\u28FF\u28FF\u28FF\u28FF\u28FF
@@ -189,30 +305,42 @@ var Create = class _Create extends BaseCommand {
189
305
  this.log(theme.primary(KITE));
190
306
  this.log(theme.primary("~ Welcome to CopilotKit! ~\n"));
191
307
  this.log(theme.divider);
192
- if ((!flags.name || flags.projectName) && !flags.framework) {
193
- this.log("\n" + theme.secondary("Just a few questions to get started!\n"));
308
+ if (!flags.name && !args.projectName && !flags.framework) {
309
+ this.log(
310
+ "\n" + theme.secondary("Just a few questions to get started!\n")
311
+ );
194
312
  }
195
313
  }
196
314
  const projectNameInput = flags.name || args.projectName || await this.promptProjectName();
197
315
  const projectName = projectNameInput.trim();
198
316
  const usingCurrentDir = projectName === "." || projectName === "./";
199
317
  const agentFramework = flags.framework || await this.promptAgentFramework();
200
- const projectDir = usingCurrentDir ? process.cwd() : path.resolve(process.cwd(), projectName);
318
+ const projectDir = usingCurrentDir ? process.cwd() : path2.resolve(process.cwd(), projectName);
201
319
  if (usingCurrentDir) {
202
320
  const allowedEntries = /* @__PURE__ */ new Set([".git", ".gitignore", ".DS_Store"]);
203
- const existingEntries = await fs.readdir(projectDir);
204
- const blockingEntries = existingEntries.filter((entry) => !allowedEntries.has(entry));
321
+ const existingEntries = await fs2.readdir(projectDir);
322
+ const blockingEntries = existingEntries.filter(
323
+ (entry) => !allowedEntries.has(entry)
324
+ );
205
325
  if (blockingEntries.length > 0) {
206
326
  this.log(theme.error("\nCurrent directory is not empty."));
207
- this.log(theme.secondary("\nPlease run create in an empty directory or specify a new project name."));
327
+ this.log(
328
+ theme.secondary(
329
+ "\nPlease run create in an empty directory or specify a new project name."
330
+ )
331
+ );
208
332
  this.exit(1);
209
333
  }
210
- } else if (await fs.pathExists(projectDir)) {
334
+ } else if (await fs2.pathExists(projectDir)) {
211
335
  this.log(theme.error(`
212
336
  Directory "${projectName}" already exists.`));
213
337
  this.log(theme.secondary("\nYou can:"));
214
338
  this.log(theme.secondary(" 1. Choose a different project name"));
215
- this.log(theme.secondary(" 2. Remove the existing directory manually if you want to use this name\n"));
339
+ this.log(
340
+ theme.secondary(
341
+ " 2. Remove the existing directory manually if you want to use this name\n"
342
+ )
343
+ );
216
344
  this.exit(1);
217
345
  }
218
346
  const options = {
@@ -225,11 +353,13 @@ Directory "${projectName}" already exists.`));
225
353
  spinner: "dots"
226
354
  }).start();
227
355
  try {
228
- await fs.ensureDir(projectDir);
356
+ await fs2.ensureDir(projectDir);
229
357
  spinner.text = theme.secondary.bold("Downloading template...");
230
- await this.downloadTemplate(projectDir, options.agentFramework);
358
+ await this.downloadTemplate(projectDir, options.agentFramework, spinner);
231
359
  const displayName = usingCurrentDir ? "current directory" : `"${projectName}"`;
232
- spinner.succeed(theme.secondary.bold(`Project ${displayName} created successfully!`));
360
+ spinner.succeed(
361
+ theme.secondary.bold(`Project ${displayName} created successfully!`)
362
+ );
233
363
  } catch (error) {
234
364
  spinner.fail(theme.error(`Failed to create project: ${error.message}`));
235
365
  this.exit(1);
@@ -244,14 +374,24 @@ Your project is ready to explore CopilotKit locally.`
244
374
  );
245
375
  this.log("\n" + theme.secondary("Next steps:"));
246
376
  if (usingCurrentDir) {
247
- this.log(theme.secondary(" \u2022 You are already inside your new project directory"));
377
+ this.log(
378
+ theme.secondary(
379
+ " \u2022 You are already inside your new project directory"
380
+ )
381
+ );
248
382
  } else {
249
383
  this.log(theme.secondary(` \u2022 ${theme.command(`cd ${projectName}`)}`));
250
384
  }
251
- this.log(theme.secondary(" \u2022 Follow the setup instructions in the README.md"));
385
+ this.log(
386
+ theme.secondary(" \u2022 Follow the setup instructions in the README.md")
387
+ );
252
388
  this.log("\n" + theme.secondary("Documentation:"));
253
- this.log(theme.secondary(" \u2022 ") + theme.command("https://docs.copilotkit.ai"));
254
- this.log(theme.secondary(" \u2022 ") + theme.command(FRAMEWORK_DOCUMENTATION[options.agentFramework]));
389
+ this.log(
390
+ theme.secondary(" \u2022 ") + theme.command("https://docs.copilotkit.ai")
391
+ );
392
+ this.log(
393
+ theme.secondary(" \u2022 ") + theme.command(FRAMEWORK_DOCUMENTATION[options.agentFramework])
394
+ );
255
395
  this.log(theme.bottomPadding);
256
396
  }
257
397
  async promptProjectName() {
@@ -263,7 +403,9 @@ Your project is ready to explore CopilotKit locally.`
263
403
  validate: (input) => {
264
404
  if (!input) return theme.error("Project name is required");
265
405
  if (!/^[a-z0-9-]+$/.test(input)) {
266
- return theme.error("Project name can only contain lowercase letters, numbers, and hyphens");
406
+ return theme.error(
407
+ "Project name can only contain lowercase letters, numbers, and hyphens"
408
+ );
267
409
  }
268
410
  if (input.length > 30) {
269
411
  return theme.error("Project name must be less than 30 characters");
@@ -279,13 +421,27 @@ Your project is ready to explore CopilotKit locally.`
279
421
  {
280
422
  type: "list",
281
423
  name: "framework",
282
- message: theme.secondary("Which agent framework would you like to use?"),
424
+ message: theme.secondary(
425
+ "Which agent framework would you like to use?"
426
+ ),
283
427
  choices: [
284
- { name: `${FRAMEWORK_EMOJI["langgraph-py"]} LangGraph (Python)`, value: "langgraph-py" },
285
- { name: `${FRAMEWORK_EMOJI["langgraph-js"]} LangGraph (JavaScript)`, value: "langgraph-js" },
428
+ {
429
+ name: `${FRAMEWORK_EMOJI["langgraph-py"]} LangGraph (Python)`,
430
+ value: "langgraph-py"
431
+ },
432
+ {
433
+ name: `${FRAMEWORK_EMOJI["langgraph-js"]} LangGraph (JavaScript)`,
434
+ value: "langgraph-js"
435
+ },
286
436
  { name: `${FRAMEWORK_EMOJI.mastra} Mastra`, value: "mastra" },
287
- { name: `${FRAMEWORK_EMOJI["pydantic-ai"]} Pydantic AI`, value: "pydantic-ai" },
288
- { name: `${FRAMEWORK_EMOJI["aws-strands-py"]} AWS Strands (Python)`, value: "aws-strands-py" },
437
+ {
438
+ name: `${FRAMEWORK_EMOJI["pydantic-ai"]} Pydantic AI`,
439
+ value: "pydantic-ai"
440
+ },
441
+ {
442
+ name: `${FRAMEWORK_EMOJI["aws-strands-py"]} AWS Strands (Python)`,
443
+ value: "aws-strands-py"
444
+ },
289
445
  { name: `${FRAMEWORK_EMOJI.adk} ADK`, value: "adk" },
290
446
  {
291
447
  name: `${FRAMEWORK_EMOJI["microsoft-agent-framework-dotnet"]} Microsoft Agent Framework (.NET)`,
@@ -295,8 +451,15 @@ Your project is ready to explore CopilotKit locally.`
295
451
  name: `${FRAMEWORK_EMOJI["microsoft-agent-framework-py"]} Microsoft Agent Framework (Python)`,
296
452
  value: "microsoft-agent-framework-py"
297
453
  },
454
+ {
455
+ name: `${FRAMEWORK_EMOJI["mcp-apps"]} MCP Apps`,
456
+ value: "mcp-apps"
457
+ },
298
458
  { name: `${FRAMEWORK_EMOJI.flows} CrewAI Flows`, value: "flows" },
299
- { name: `${FRAMEWORK_EMOJI.llamaindex} LlamaIndex`, value: "llamaindex" },
459
+ {
460
+ name: `${FRAMEWORK_EMOJI.llamaindex} LlamaIndex`,
461
+ value: "llamaindex"
462
+ },
300
463
  { name: `${FRAMEWORK_EMOJI.agno} Agno`, value: "agno" },
301
464
  { name: `${FRAMEWORK_EMOJI.ag2} AG2`, value: "ag2" },
302
465
  { name: `${FRAMEWORK_EMOJI.a2a} A2A`, value: "a2a" }
@@ -305,13 +468,25 @@ Your project is ready to explore CopilotKit locally.`
305
468
  ]);
306
469
  return framework;
307
470
  }
308
- async downloadTemplate(projectDir, framework) {
309
- const repo = TEMPLATE_REPOS[framework];
310
- const url = `https://github.com/${repo}/archive/refs/heads/main.tar.gz`;
471
+ async downloadTemplate(projectDir, framework, spinner) {
472
+ const templateRef = TEMPLATE_REPOS[framework];
473
+ if (isValidGitHubUrl(templateRef)) {
474
+ const success = await cloneGitHubSubdirectory(
475
+ templateRef,
476
+ projectDir,
477
+ spinner
478
+ );
479
+ if (!success) {
480
+ throw new Error(`Failed to clone template from ${templateRef}`);
481
+ }
482
+ return;
483
+ }
484
+ const url = `https://github.com/${templateRef}/archive/refs/heads/main.tar.gz`;
311
485
  try {
312
486
  const response = await fetch(url);
313
- if (!response.ok) throw new Error(`Failed to download template: ${response.statusText}`);
314
- const tempFile = path.join(projectDir, "template.tar.gz");
487
+ if (!response.ok)
488
+ throw new Error(`Failed to download template: ${response.statusText}`);
489
+ const tempFile = path2.join(projectDir, "template.tar.gz");
315
490
  const fileStream = createWriteStream(tempFile);
316
491
  if (!response.body) throw new Error("Failed to get response body");
317
492
  await streamPipeline(response.body, fileStream);
@@ -320,7 +495,7 @@ Your project is ready to explore CopilotKit locally.`
320
495
  cwd: projectDir,
321
496
  strip: 1
322
497
  });
323
- await fs.remove(tempFile);
498
+ await fs2.remove(tempFile);
324
499
  } catch (error) {
325
500
  throw new Error(`Failed to download template: ${error.message}`);
326
501
  }