@gxp-dev/tools 2.0.12 → 2.0.14

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.
@@ -186,11 +186,20 @@ async function checkCodexAvailable() {
186
186
  }
187
187
 
188
188
  /**
189
- * Check if Gemini is available (API key or gcloud)
189
+ * Check if Gemini is available (CLI, API key, or gcloud)
190
190
  * @returns {Promise<{available: boolean, reason?: string, method?: string}>}
191
191
  */
192
192
  async function checkGeminiAvailable() {
193
- // Check for API key first
193
+ // Check for Gemini CLI first (preferred - uses logged-in account)
194
+ try {
195
+ execSync("which gemini", { stdio: "pipe" });
196
+ // Gemini CLI is installed - it handles its own auth
197
+ return { available: true, method: "cli" };
198
+ } catch (error) {
199
+ // Gemini CLI not installed
200
+ }
201
+
202
+ // Check for API key
194
203
  const apiKey = process.env.GEMINI_API_KEY || process.env.GOOGLE_API_KEY;
195
204
  if (apiKey) {
196
205
  return { available: true, method: "api_key" };
@@ -212,7 +221,8 @@ async function checkGeminiAvailable() {
212
221
  return {
213
222
  available: false,
214
223
  reason:
215
- "Gemini requires either:\n" +
224
+ "Gemini requires one of:\n" +
225
+ " • Gemini CLI logged in (npm i -g @google/gemini-cli && gemini), or\n" +
216
226
  " • GEMINI_API_KEY environment variable, or\n" +
217
227
  " • gcloud CLI logged in (gcloud auth login)",
218
228
  };
@@ -371,11 +381,11 @@ async function generateWithCodex(userPrompt, projectName, description) {
371
381
  }
372
382
 
373
383
  /**
374
- * Generate scaffold using Gemini (API key or gcloud)
384
+ * Generate scaffold using Gemini (CLI, API key, or gcloud)
375
385
  * @param {string} userPrompt - User's description
376
386
  * @param {string} projectName - Project name
377
387
  * @param {string} description - Project description
378
- * @param {string} method - 'api_key' or 'gcloud'
388
+ * @param {string} method - 'cli', 'api_key', or 'gcloud'
379
389
  * @returns {Promise<object|null>}
380
390
  */
381
391
  async function generateWithGemini(
@@ -386,15 +396,76 @@ async function generateWithGemini(
386
396
  ) {
387
397
  const fullPrompt = buildFullPrompt(userPrompt, projectName, description);
388
398
 
389
- // Determine authentication method
390
- const apiKey = process.env.GEMINI_API_KEY || process.env.GOOGLE_API_KEY;
391
- const useApiKey = method === "api_key" || apiKey;
399
+ // Use the appropriate method
400
+ if (method === "cli") {
401
+ return generateWithGeminiCli(fullPrompt);
402
+ }
392
403
 
393
- if (useApiKey && apiKey) {
404
+ const apiKey = process.env.GEMINI_API_KEY || process.env.GOOGLE_API_KEY;
405
+ if (method === "api_key" && apiKey) {
394
406
  return generateWithGeminiApiKey(fullPrompt, apiKey);
395
- } else {
396
- return generateWithGeminiGcloud(fullPrompt);
397
407
  }
408
+
409
+ return generateWithGeminiGcloud(fullPrompt);
410
+ }
411
+
412
+ /**
413
+ * Generate using Gemini CLI
414
+ */
415
+ async function generateWithGeminiCli(fullPrompt) {
416
+ return new Promise((resolve) => {
417
+ console.log("\n🤖 Generating plugin scaffold with Gemini CLI...\n");
418
+
419
+ let output = "";
420
+ let errorOutput = "";
421
+
422
+ // Use gemini CLI with -p for prompt mode
423
+ const gemini = spawn(
424
+ "gemini",
425
+ ["-p", `${SCAFFOLD_SYSTEM_PROMPT}\n\n${fullPrompt}`],
426
+ {
427
+ stdio: ["pipe", "pipe", "pipe"],
428
+ shell: true,
429
+ }
430
+ );
431
+
432
+ gemini.stdout.on("data", (data) => {
433
+ output += data.toString();
434
+ });
435
+
436
+ gemini.stderr.on("data", (data) => {
437
+ errorOutput += data.toString();
438
+ });
439
+
440
+ gemini.on("close", (code) => {
441
+ if (code !== 0) {
442
+ console.error(`❌ Gemini CLI error: ${errorOutput}`);
443
+ resolve(null);
444
+ return;
445
+ }
446
+
447
+ const scaffoldData = parseAIResponse(output);
448
+ if (!scaffoldData) {
449
+ console.error("❌ Could not parse Gemini response");
450
+ console.log("Raw response:", output.slice(0, 500));
451
+ resolve(null);
452
+ return;
453
+ }
454
+
455
+ if (scaffoldData.explanation) {
456
+ console.log("📝 AI Explanation:");
457
+ console.log(` ${scaffoldData.explanation}`);
458
+ console.log("");
459
+ }
460
+
461
+ resolve(scaffoldData);
462
+ });
463
+
464
+ gemini.on("error", (err) => {
465
+ console.error(`❌ Failed to run Gemini CLI: ${err.message}`);
466
+ resolve(null);
467
+ });
468
+ });
398
469
  }
399
470
 
400
471
  /**
@@ -56,7 +56,7 @@
56
56
  },
57
57
 
58
58
  "web_accessible_resources": [{
59
- "resources": ["content.js", "inspector.js", "panel.html", "panel.js"],
59
+ "resources": ["content.js", "inspector.js", "panel.html", "panel.js", "defaults.json"],
60
60
  "matches": ["<all_urls>"]
61
61
  }],
62
62