koishi-plugin-aka-ai-generator 0.4.0 → 0.4.1

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/lib/index.js +50 -2
  2. package/package.json +1 -1
package/lib/index.js CHANGED
@@ -598,6 +598,39 @@ function parseGeminiResponse(response, logger) {
598
598
  logger?.error("Gemini API 返回错误", { error: response.error });
599
599
  throw new Error(`Gemini API 错误: ${response.error.message || JSON.stringify(response.error)}`);
600
600
  }
601
+ if (response.promptFeedback) {
602
+ const blockReason = response.promptFeedback.blockReason;
603
+ const safetyRatings = response.promptFeedback.safetyRatings;
604
+ if (blockReason) {
605
+ logger?.error("Gemini API 请求被阻止", {
606
+ blockReason,
607
+ safetyRatings,
608
+ blockReasonMessage: response.promptFeedback.blockReasonMessage
609
+ });
610
+ let errorMessage = "请求被 Gemini API 阻止";
611
+ switch (blockReason) {
612
+ case "SAFETY":
613
+ errorMessage = "内容被安全策略阻止,可能包含不安全的内容";
614
+ break;
615
+ case "OTHER":
616
+ errorMessage = "请求被阻止(原因:OTHER),可能是内容不符合使用政策或模型无法处理";
617
+ if (response.promptFeedback.blockReasonMessage) {
618
+ errorMessage += `:${response.promptFeedback.blockReasonMessage}`;
619
+ }
620
+ break;
621
+ case "RECITATION":
622
+ errorMessage = "内容包含受版权保护的内容";
623
+ break;
624
+ default:
625
+ errorMessage = `请求被阻止(原因:${blockReason})`;
626
+ }
627
+ if (safetyRatings && Array.isArray(safetyRatings) && safetyRatings.length > 0) {
628
+ const ratings = safetyRatings.map((r) => `${r.category}:${r.probability}`).join(", ");
629
+ errorMessage += ` [安全评分: ${ratings}]`;
630
+ }
631
+ throw new Error(errorMessage);
632
+ }
633
+ }
601
634
  if (response.candidates && response.candidates.length > 0) {
602
635
  for (const candidate of response.candidates) {
603
636
  if (candidate.finishReason && candidate.finishReason !== "STOP") {
@@ -638,14 +671,29 @@ function parseGeminiResponse(response, logger) {
638
671
  }
639
672
  }
640
673
  } else {
641
- logger?.warn("Gemini API 响应中没有 candidates", { response: JSON.stringify(response).substring(0, 500) });
674
+ const hasPromptFeedback = !!response.promptFeedback;
675
+ const responseKeys = Object.keys(response);
676
+ logger?.error("Gemini API 响应中没有 candidates", {
677
+ response: JSON.stringify(response).substring(0, 500),
678
+ hasPromptFeedback,
679
+ responseKeys
680
+ });
681
+ if (!hasPromptFeedback) {
682
+ throw new Error("Gemini API 响应格式异常:既没有生成内容也没有反馈信息");
683
+ }
684
+ if (hasPromptFeedback && !response.promptFeedback.blockReason) {
685
+ logger?.warn("有 promptFeedback 但没有 blockReason,也没有 candidates", {
686
+ promptFeedback: response.promptFeedback
687
+ });
688
+ }
642
689
  }
643
690
  if (images.length === 0) {
644
691
  logger?.error("未能从 Gemini API 响应中提取到任何图片", {
645
692
  hasCandidates: !!response.candidates,
646
693
  candidatesCount: response.candidates?.length || 0,
647
694
  responseKeys: Object.keys(response),
648
- firstCandidate: response.candidates?.[0] ? JSON.stringify(response.candidates[0]).substring(0, 300) : null
695
+ firstCandidate: response.candidates?.[0] ? JSON.stringify(response.candidates[0]).substring(0, 300) : null,
696
+ promptFeedback: response.promptFeedback ? JSON.stringify(response.promptFeedback) : null
649
697
  });
650
698
  }
651
699
  return images;
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "koishi-plugin-aka-ai-generator",
3
3
  "description": "自用AI生成插件(GPTGod & Yunwu)",
4
- "version": "0.4.0",
4
+ "version": "0.4.1",
5
5
  "main": "lib/index.js",
6
6
  "typings": "lib/index.d.ts",
7
7
  "files": [