opencode-pollinations-plugin 6.4.9 → 6.4.10

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.de.md CHANGED
@@ -97,10 +97,11 @@ Das **Pollen 🌻** ist unser zentrales Kreditsystem (1$ ≈ 1 Pollen). Verbinde
97
97
 
98
98
  | Tier (Stufe) | Stündliche Aufladung ⏱️ | Schätzung Tag* | Voraussetzung |
99
99
  | :--- | :--- | :--- | :--- |
100
- | 🍄 **Spore** | **0.01 Pollen / Std.** | ~0.24 / Tag | Automatische Verifikation |
101
- | 🌱 **Seed** | **0.15 Pollen / Std.** | ~3.6 / Tag | Aktiver GitHub-Entwickler (8+ Punkte) |
102
- | 🌸 **Flower** | **0.40 Pollen / Std.** | ~9.6 / Tag | **Eine App veröffentlichen** (Wie dieses Plugin!) |
103
- | 🍯 **Nectar** | **0.80 Pollen / Std.** | ~19.2 / Tag | Demnächst 🔮 |
100
+ | 🍄 **Spore** | **0.01 Pollen / Std.** | ~0.24 / Tag | Neues Konto (Standard) |
101
+ | 🌱 **Seed** | **0.15 Pollen / Std.** | ~3.6 / Tag | Aktives Community-Mitglied |
102
+ | 🌸 **Flower** | **0.40 Pollen / Std.** | ~9.6 / Tag | Quests abschließen & beitragen |
103
+ | 🍯 **Nectar** | **0.80 Pollen / Std.** | ~19.2 / Tag | Top-Mitwirkender |
104
+ | 🐝 **Router** | **10 Pollen / Std.** | ~240 / Tag | Speziell / nur auf Einladung |
104
105
 
105
106
  _*Tägliche Schätzungen sind nur Näherungswerte (~24h × Stundenrate). Das Reset findet automatisch zur vollen Stunde (XX:00) statt._
106
107
 
package/README.es.md CHANGED
@@ -97,10 +97,11 @@ El **Pollen 🌻** dicta la ley unificada del crédito (1$ ≈ 1 Pollen). Sólo
97
97
 
98
98
  | Tier | Recarga Hora ⏱️ | Aprox Diario* | Requisito a Cumplir |
99
99
  | :--- | :--- | :--- | :--- |
100
- | 🍄 **Spore** | **0.01 Pollen / hora** | ~0.24 /día | Examen de perfil y verificación |
101
- | 🌱 **Seed** | **0.15 Pollen / hora** | ~3.6 /día | Desarrollador activo en Github (+8 pts) |
102
- | 🌸 **Flower** | **0.40 Pollen / hora** | ~9.6 /día | **Completar y Publicar una App** |
103
- | 🍯 **Nectar** | **0.80 Pollen / hora** | ~19.2 /día | Pendiente a futuras actualizaciones 🔮 |
100
+ | 🍄 **Spore** | **0.01 Pollen / hora** | ~0.24 /día | Cuenta nueva (predeterminado) |
101
+ | 🌱 **Seed** | **0.15 Pollen / hora** | ~3.6 /día | Miembro activo de la comunidad |
102
+ | 🌸 **Flower** | **0.40 Pollen / hora** | ~9.6 /día | Completa Misiones y contribuye |
103
+ | 🍯 **Nectar** | **0.80 Pollen / hora** | ~19.2 /día | Principal contribuidor |
104
+ | 🐝 **Router** | **10 Pollen / hora** | ~240 /día | Especial / solo por invitación |
104
105
 
105
106
  _*Los cálculos diarios solo son estimaciones teóricas (~24h × cuota/hora). El reinicio limpio sucede exacto en el minuto `:00` de las horas del reloj._
106
107
 
package/README.fr.md CHANGED
@@ -97,10 +97,11 @@ Le **Pollen 🌻** est notre système de crédit unifié (1$ ≈ 1 Pollen). En c
97
97
 
98
98
  | Tier | Recharge Horaire ⏱️ | Estimation Jour* | Condition |
99
99
  | :--- | :--- | :--- | :--- |
100
- | 🍄 **Spore** | **0.01 Pollen / heure** | ~0.24 / jour | Vérification automatique |
101
- | 🌱 **Seed** | **0.15 Pollen / heure** | ~3.6 / jour | Développeur GitHub Actif (8+ points) |
102
- | 🌸 **Flower** | **0.40 Pollen / heure** | ~9.6 / jour | **Publier une App** (Comme ce plugin !) |
103
- | 🍯 **Nectar** | **0.80 Pollen / heure** | ~19.2 / jour | À venir 🔮 |
100
+ | 🍄 **Spore** | **0.01 Pollen / heure** | ~0.24 / jour | Nouveau compte (par défaut) |
101
+ | 🌱 **Seed** | **0.15 Pollen / heure** | ~3.6 / jour | Membre actif de la communauté |
102
+ | 🌸 **Flower** | **0.40 Pollen / heure** | ~9.6 / jour | Compléter des Quêtes et contribuer |
103
+ | 🍯 **Nectar** | **0.80 Pollen / heure** | ~19.2 / jour | Contributeur de premier plan |
104
+ | 🐝 **Router** | **10 Pollen / heure** | ~240 / jour | Spécial / sur invitation |
104
105
 
105
106
  _*Les estimations quotidiennes sont approximatives (~24h × taux horaire). La réinitialisation réelle s'effectue automatiquement au début de chaque heure (XX:00)._
106
107
 
package/README.it.md CHANGED
@@ -97,10 +97,11 @@ Il **Pollen 🌻** è un sistema universale (1$ ≈ 1 Pollen). Immettendo una pr
97
97
 
98
98
  | Tier (Livello) | Ricarica Oraria ⏱️ | Stima Giorno* | Requisito richiesto |
99
99
  | :--- | :--- | :--- | :--- |
100
- | 🍄 **Spore** | **0.01 Pollen / ora** | ~0.24 / giorno | Essendo verificato dal sistema |
101
- | 🌱 **Seed** | **0.15 Pollen / ora** | ~3.6 / giorno | Operazioni su Github valide (+8 pts) |
102
- | 🌸 **Flower** | **0.40 Pollen / ora** | ~9.6 / giorno | **Aver prodotto una applicazione** (Come questo Plugin) |
103
- | 🍯 **Nectar** | **0.80 Pollen / ora** | ~19.2 / giorno | Arriverà prossimamente 🔮 |
100
+ | 🍄 **Spore** | **0.01 Pollen / ora** | ~0.24 / giorno | Nuovo account (predefinito) |
101
+ | 🌱 **Seed** | **0.15 Pollen / ora** | ~3.6 / giorno | Membro attivo della community |
102
+ | 🌸 **Flower** | **0.40 Pollen / ora** | ~9.6 / giorno | Completa le Missioni e contribuisci |
103
+ | 🍯 **Nectar** | **0.80 Pollen / ora** | ~19.2 / giorno | Contributore di punta |
104
+ | 🐝 **Router** | **10 Pollen / ora** | ~240 / giorno | Speciale / solo su invito |
104
105
 
105
106
  _*La stima giornaliera è puramente teorica (~24h × quota oraria). I Pollen si rinfrescano in modo corretto all'istante di ogni cambio ora (`:00`)._
106
107
 
package/README.zh.md CHANGED
@@ -97,10 +97,11 @@
97
97
 
98
98
  | Tier (称号) | 每小时获取补贴量 ⏱️ | 无限循环参考值* | 达成条件 |
99
99
  | :--- | :--- | :--- | :--- |
100
- | 🍄 **Spore (孢子)** | **0.01 Pollen / 小时** | 每天约 ~0.24 | 自动安全审核激活系统 |
101
- | 🌱 **Seed (树种)** | **0.15 Pollen / 小时** | 每天约 ~3.6 | GitHub 活跃开发成员 (总分达 8+) |
102
- | 🌸 **Flower (花朵)** | **0.40 Pollen / 小时** | 每天约 ~9.6 | **至少有完成并首发过一款应用在市场!** |
103
- | 🍯 **Nectar (花蜜)** | **0.80 Pollen / 小时** | 每天约 ~19.2 | 🔮 等待解锁中... |
100
+ | 🍄 **Spore (孢子)** | **0.01 Pollen / 小时** | 每天约 ~0.24 | 新账户(默认) |
101
+ | 🌱 **Seed (树种)** | **0.15 Pollen / 小时** | 每天约 ~3.6 | 活跃的社区成员 |
102
+ | 🌸 **Flower (花朵)** | **0.40 Pollen / 小时** | 每天约 ~9.6 | 完成任务并贡献 |
103
+ | 🍯 **Nectar (花蜜)** | **0.80 Pollen / 小时** | 每天约 ~19.2 | 顶级贡献者 |
104
+ | 🐝 **Router (路由)** | **10 Pollen / 小时** | 每天约 ~240 | 特殊 / 仅限邀请 |
104
105
 
105
106
  _*所列出每天近似最大总额建立在前置满消(~24h × hourly rate)为理论上限。真实的花粉量都会准时在零点过的一分钟 (XX:00) 统一灌满池子里。_
106
107
 
@@ -488,7 +488,10 @@
488
488
  "condition": {
489
489
  "signup": "Einfach registrieren!",
490
490
  "auto_verify": "Automatische Verifizierung",
491
+ "under_review": "Konto wird überprüft",
492
+ "default": "Neues Konto (Standard)",
491
493
  "community": "Aktives Community-Mitglied",
494
+ "quests": "Quests abschließen & beitragen",
492
495
  "publish_app": "Eine App veröffentlichen",
493
496
  "top_contributor": "Top-Mitwirkender",
494
497
  "special": "Speziell / nur auf Einladung"
@@ -488,7 +488,10 @@
488
488
  "condition": {
489
489
  "signup": "Just register",
490
490
  "auto_verify": "Automatic verification",
491
+ "under_review": "Account under review",
492
+ "default": "New account (default)",
491
493
  "community": "Active community member",
494
+ "quests": "Complete Quests & contribute",
492
495
  "publish_app": "Publish an app",
493
496
  "top_contributor": "Top contributor",
494
497
  "special": "Special / invite-only"
@@ -488,7 +488,10 @@
488
488
  "condition": {
489
489
  "signup": "¡Solo regístrate!",
490
490
  "auto_verify": "Verificación automática",
491
+ "under_review": "Cuenta en revisión",
492
+ "default": "Cuenta nueva (predeterminado)",
491
493
  "community": "Miembro activo de la comunidad",
494
+ "quests": "Completa Misiones y contribuye",
492
495
  "publish_app": "Publica una app",
493
496
  "top_contributor": "Principal contribuidor",
494
497
  "special": "Especial / solo por invitación"
@@ -488,7 +488,10 @@
488
488
  "condition": {
489
489
  "signup": "Inscrivez-vous, c'est tout !",
490
490
  "auto_verify": "Vérification automatique",
491
+ "under_review": "Compte en cours d'examen",
492
+ "default": "Nouveau compte (par défaut)",
491
493
  "community": "Membre actif de la communauté",
494
+ "quests": "Compléter des Quêtes et contribuer",
492
495
  "publish_app": "Publier une app",
493
496
  "top_contributor": "Contributeur de premier plan",
494
497
  "special": "Spécial / sur invitation"
@@ -488,7 +488,10 @@
488
488
  "condition": {
489
489
  "signup": "Basta registrarsi!",
490
490
  "auto_verify": "Verifica automatica",
491
+ "under_review": "Account in revisione",
492
+ "default": "Nuovo account (predefinito)",
491
493
  "community": "Membro attivo della community",
494
+ "quests": "Completa le Missioni e contribuisci",
492
495
  "publish_app": "Pubblica un'app",
493
496
  "top_contributor": "Contributore di punta",
494
497
  "special": "Speciale / solo su invito"
@@ -488,7 +488,10 @@
488
488
  "condition": {
489
489
  "signup": "只需注册",
490
490
  "auto_verify": "自动验证",
491
+ "under_review": "账户审核中",
492
+ "default": "新账户(默认)",
491
493
  "community": "活跃的社区成员",
494
+ "quests": "完成任务并贡献",
492
495
  "publish_app": "发布一个应用",
493
496
  "top_contributor": "顶级贡献者",
494
497
  "special": "特殊 / 仅限邀请"
@@ -7,27 +7,6 @@ import { ModelRegistry } from './models/index.js';
7
7
  import { t } from '../locales/index.js';
8
8
  import { formatTierTable } from './tier-info.js';
9
9
  import { buildQuestsReport } from '../tools/pollinations/polli_quests.js';
10
- // GET helper for /account/* JSON endpoints (used for quest-reward reconstruction).
11
- function fetchAccountJson(path, apiKey) {
12
- return new Promise((resolve, reject) => {
13
- const req = https.request({
14
- hostname: 'gen.pollinations.ai', path, method: 'GET',
15
- headers: { 'Authorization': `Bearer ${apiKey}`, 'User-Agent': 'opencode-pollinations-plugin' },
16
- }, (res) => {
17
- let data = '';
18
- res.on('data', c => data += c);
19
- res.on('end', () => { try {
20
- resolve(JSON.parse(data));
21
- }
22
- catch (e) {
23
- reject(e);
24
- } });
25
- });
26
- req.on('error', reject);
27
- req.setTimeout(10000, () => { req.destroy(); reject(new Error('Timeout')); });
28
- req.end();
29
- });
30
- }
31
10
  function checkEndpoint(ep, key) {
32
11
  return new Promise((resolve) => {
33
12
  const req = https.request({
@@ -262,43 +241,9 @@ export async function handleUsageCommand(args) {
262
241
  response += t('commands.usage.tier', { emoji: quota.tierEmoji, tier: quota.tier.toUpperCase(), limit: quota.tierLimit });
263
242
  response += t('commands.usage.quota', { remaining: formatPollen(quota.tierLimit - quota.tierRemaining), limit: formatPollen(quota.tierLimit) });
264
243
  response += t('commands.usage.usage_bar', { bar: progressBar(quota.tierLimit - quota.tierRemaining, quota.tierLimit) });
265
- // Reconstructed Quest/Paid split by CROSS-REFERENCING exact data (no magic field needed):
266
- // • claimed quest rewards (tier bucket) ← /account/quests (exact)
267
- // • tier consumption since the first claim ← /account/usage meter_source=='tier' (exact)
268
- // • current-hour floor remaining (≤ tierLimit) ← quota (the only fuzzy term, ignored)
269
- // Quest remaining ≈ claimedQuestTier − tierConsumedSinceClaim (+ floor); Paid = Total − Quest.
270
- const total = quota.tierRemaining + quota.walletBalance; // true balance
271
- let claimedQuestTier = 0;
272
- let firstClaimMs = Infinity;
273
- let tierConsumedSinceClaim = 0;
274
- if (config.apiKey && config.keyHasAccessToProfile !== false) {
275
- try {
276
- const qres = await fetchAccountJson('/account/quests', config.apiKey);
277
- for (const q of (qres?.quests || [])) {
278
- const r = q.reward;
279
- if (r && r.claimedAt && r.balanceBucket === 'tier') {
280
- claimedQuestTier += (r.pollenAmount || 0);
281
- const cms = new Date(r.claimedAt).getTime();
282
- if (!isNaN(cms) && cms < firstClaimMs)
283
- firstClaimMs = cms;
284
- }
285
- }
286
- // Sum tier-metered spend since the first claim (what actually ate the Quest stash).
287
- if (claimedQuestTier > 0 && isFinite(firstClaimMs)) {
288
- const ures = await fetchAccountJson('/account/usage?limit=100', config.apiKey);
289
- for (const e of (ures?.usage || [])) {
290
- const ts = new Date(String(e.timestamp).replace(' ', 'T') + (String(e.timestamp).includes('Z') ? '' : 'Z')).getTime();
291
- if (e.meter_source === 'tier' && !isNaN(ts) && ts >= firstClaimMs) {
292
- tierConsumedSinceClaim += (e.cost_usd || 0);
293
- }
294
- }
295
- }
296
- }
297
- catch { /* fall back gracefully if unreachable */ }
298
- }
299
- // Quest stash = claimed − consumed, plus the current hourly floor still available.
300
- const questPollen = Math.max(0, claimedQuestTier - tierConsumedSinceClaim) + quota.tierRemaining;
301
- const paidPollen = Math.max(0, total - questPollen);
244
+ const total = quota.tierRemaining + quota.questStash + quota.walletBalance;
245
+ const questPollen = quota.tierRemaining + quota.questStash;
246
+ const paidPollen = quota.walletBalance;
302
247
  response += t('commands.usage.split', {
303
248
  quest: questPollen.toFixed(2),
304
249
  paid: paidPollen.toFixed(2),
@@ -810,12 +755,16 @@ ${t('commands.help.models_pricing')}
810
755
  }
811
756
  // === MODELS & PRICING COMMANDS ===
812
757
  function parseNameDesc(m) {
758
+ const displayName = m.title || m.description || m.name;
813
759
  const fullDesc = m.description || m.name;
814
- const parts = fullDesc.split(" - ");
760
+ if (m.title && m.description) {
761
+ return { nom: m.title, desc: m.description };
762
+ }
763
+ const parts = displayName.split(" - ");
815
764
  if (parts.length > 1) {
816
765
  return { nom: parts[0].trim(), desc: parts.slice(1).join(" - ").trim() };
817
766
  }
818
- return { nom: fullDesc, desc: "" };
767
+ return { nom: displayName, desc: "" };
819
768
  }
820
769
  export async function handleModelsCommand(args) {
821
770
  const filter = args[0]; // optional: image, video, audio, text
@@ -956,17 +905,7 @@ function buildOutputCost(m) {
956
905
  export async function handleInfosCommand() {
957
906
  const config = loadConfig();
958
907
  let name = "Developer";
959
- let tier = "anonymous";
960
- let tierEmoji = '👤';
961
908
  if (config.apiKey) {
962
- try {
963
- const quota = await getQuotaStatus(true);
964
- tier = quota.tier || 'anonymous';
965
- tierEmoji = quota.tierEmoji || '👤';
966
- }
967
- catch (e) {
968
- // Ignorer l'erreur réseau et garder les valeurs par défaut
969
- }
970
909
  try {
971
910
  const res = await fetch('https://gen.pollinations.ai/account/profile', {
972
911
  headers: { 'Authorization': `Bearer ${config.apiKey}` }
@@ -992,7 +931,6 @@ ${t('commands.infos.features_pro')}
992
931
 
993
932
  ${t('commands.infos.features_config')}
994
933
 
995
- ${t('commands.infos.tiers_title', { emoji: tierEmoji, tier: tier.toUpperCase() })}
996
934
  ${t('commands.infos.get_started')}
997
935
 
998
936
  ${t('commands.infos.about')}
@@ -73,7 +73,7 @@ const DEFAULT_CONFIG_V5 = {
73
73
  gui: { status: 'alert', logs: 'none' },
74
74
  thresholds: { tier: 10, wallet: 5 },
75
75
  fallbacks: {
76
- free: { main: 'free/mistral', agent: 'free/openai-fast' },
76
+ free: { main: 'free/openai-fast', agent: 'free/openai-fast' },
77
77
  enter: { agent: 'free/openai-fast' }
78
78
  },
79
79
  enablePaidTools: false,
@@ -71,7 +71,7 @@ export async function generatePollinationsConfig(forceApiKey, forceStrict = fals
71
71
  catch (e) {
72
72
  log(`Error fetching Free models: ${e}`);
73
73
  // Fallback Robust (Offline support)
74
- modelsOutput.push({ id: "free/mistral", name: "Mistral Nemo (Fallback)", object: "model", variants: {} });
74
+ modelsOutput.push({ id: "free/openai-fast", name: "GPT-5 Nano (Fallback)", object: "model", variants: {} });
75
75
  modelsOutput.push({ id: "free/openai", name: "OpenAI (Fallback)", object: "model", variants: {} });
76
76
  modelsOutput.push({ id: "free/gemini", name: "Gemini Flash (Fallback)", object: "model", variants: {} });
77
77
  }
@@ -152,7 +152,7 @@ function getCapabilityIcons(raw) {
152
152
  function mapModel(raw, prefix, namePrefix) {
153
153
  const rawId = raw.id || raw.name;
154
154
  const fullId = prefix + rawId; // ex: "free/gemini" or "enter/nomnom" (prefix passed is "enter/")
155
- let baseName = raw.description;
155
+ let baseName = raw.title || raw.description;
156
156
  if (!baseName || baseName === rawId) {
157
157
  baseName = formatName(rawId, raw.censored !== false);
158
158
  }
@@ -79,6 +79,8 @@ function mapRawToModel(raw, fallbackCategory, averageCost) {
79
79
  };
80
80
  const model = {
81
81
  name: raw.name || raw.id || 'unknown',
82
+ title: raw.title || undefined,
83
+ brand: raw.brand || undefined,
82
84
  description: raw.description || raw.name || '',
83
85
  category,
84
86
  aliases: raw.aliases || [],
@@ -21,6 +21,8 @@ export interface ModelPricing {
21
21
  }
22
22
  export interface PollinationsModel {
23
23
  name: string;
24
+ title?: string;
25
+ brand?: string;
24
26
  description: string;
25
27
  category: ModelCategory;
26
28
  aliases: string[];
@@ -338,13 +338,7 @@ export async function handleChatCompletion(req, res, bodyRaw) {
338
338
  // Check dynamic list saved by generate-config.ts
339
339
  if (isEnterprise) {
340
340
  try {
341
- const paidListPath = path.join(config.gui ? path.dirname(path.join(process.env.HOME || '/tmp', '.config/opencode/pollinations-signature.json')) : '/tmp', 'pollinations-paid-models.json');
342
- // Wait, logic above for config path is messy. Let's use standard path logic:
343
- // config.ts uses ~/.pollinations/config.json usually.
344
- // generate-config uses path.join(config.gui ? path.dirname(CONFIG_FILE) : '/tmp')
345
- // Let's rely on standard ~/.pollinations location if possible, or try both.
346
- const homedir = process.env.HOME || '/tmp';
347
- const standardPaidPath = path.join(homedir, '.pollinations', 'pollinations-paid-models.json');
341
+ const standardPaidPath = path.join(getConfigDir(), 'pollinations-paid-models.json');
348
342
  if (fs.existsSync(standardPaidPath)) {
349
343
  const paidModels = JSON.parse(fs.readFileSync(standardPaidPath, 'utf-8'));
350
344
  if (paidModels.includes(actualModel)) {
@@ -389,8 +383,7 @@ export async function handleChatCompletion(req, res, bodyRaw) {
389
383
  if (isEnterprise) {
390
384
  // Paid Only Check: BLOCK (not fallback) in AlwaysFree mode
391
385
  try {
392
- const homedir = process.env.HOME || '/tmp';
393
- const standardPaidPath = path.join(homedir, '.pollinations', 'pollinations-paid-models.json');
386
+ const standardPaidPath = path.join(getConfigDir(), 'pollinations-paid-models.json');
394
387
  if (fs.existsSync(standardPaidPath)) {
395
388
  const paidModels = JSON.parse(fs.readFileSync(standardPaidPath, 'utf-8'));
396
389
  if (paidModels.includes(actualModel)) {
@@ -561,6 +554,10 @@ export async function handleChatCompletion(req, res, bodyRaw) {
561
554
  if (actualModel.includes("gpt") || actualModel.includes("openai") || actualModel.includes("azure") || actualModel.includes("midijourney") || actualModel.includes("grok")) {
562
555
  const limit = (actualModel.includes("midijourney") || actualModel.includes("grok")) ? 128 : 120;
563
556
  proxyBody.tools = truncateTools(proxyBody.tools, limit);
557
+ if (proxyBody.reasoning_effort)
558
+ delete proxyBody.reasoning_effort;
559
+ if (proxyBody.reasoningEffort)
560
+ delete proxyBody.reasoningEffort;
564
561
  if (proxyBody.messages) {
565
562
  proxyBody.messages.forEach((m) => {
566
563
  if (m.tool_calls) {
@@ -702,7 +699,7 @@ export async function handleChatCompletion(req, res, bodyRaw) {
702
699
  // TRANSPARENT FALLBACK LOGIC
703
700
  // 1. Enterprise Safety Net (Quota/Auth/RateLimit)
704
701
  // 2. Gemini Tools Fix (Gemini + Tools -> 401 -> Fallback to OpenAI)
705
- const isEnterpriseFallback = (fetchRes.status === 402 || fetchRes.status === 429 || fetchRes.status === 401 || fetchRes.status === 403) && isEnterprise;
702
+ const isEnterpriseFallback = (fetchRes.status === 402 || fetchRes.status === 429 || fetchRes.status === 502 || fetchRes.status === 401 || fetchRes.status === 403) && isEnterprise;
706
703
  const isGeminiToolsFallback = fetchRes.status === 401 && actualModel.includes('gemini') && !isEnterprise && proxyBody.tools && proxyBody.tools.length > 0;
707
704
  // STRICT MANUAL MODE: Disable "Magic" Fallbacks
708
705
  if ((isEnterpriseFallback || isGeminiToolsFallback) && config.mode !== 'manual') {
@@ -109,12 +109,15 @@ function getCost(m, type) {
109
109
  }
110
110
  // ─── RENDU VISUEL ────────────────────────────────────────────────────────────
111
111
  function parseNameDesc(m) {
112
- const fullDesc = m.description || m.name;
113
- const parts = fullDesc.split(" - ");
112
+ if (m.title && m.description) {
113
+ return { nom: m.title, desc: m.description };
114
+ }
115
+ const displayName = m.title || m.description || m.name;
116
+ const parts = displayName.split(" - ");
114
117
  if (parts.length > 1) {
115
118
  return { nom: parts[0].trim(), desc: parts.slice(1).join(" - ").trim() };
116
119
  }
117
- return { nom: fullDesc, desc: "" };
120
+ return { nom: displayName, desc: "" };
118
121
  }
119
122
  function flags(m, overrides = []) {
120
123
  const f = [];
package/package.json CHANGED
@@ -1,65 +1,65 @@
1
1
  {
2
- "name": "opencode-pollinations-plugin",
3
- "displayName": "Pollinations",
4
- "version": "6.4.9",
5
- "description": "Native Pollinations.ai Provider Plugin for OpenCode — free & premium AI models, media tools, quests, cost guards",
6
- "author": "fkom13",
7
- "license": "MIT",
8
- "keywords": [
9
- "opencode",
10
- "pollinations",
11
- "ai",
12
- "plugin",
13
- "image-generation",
14
- "video-generation",
15
- "llm",
16
- "pollen"
17
- ],
18
- "repository": {
19
- "type": "git",
20
- "url": "git+https://github.com/fkom13/opencode-pollinations-plugin.git"
21
- },
22
- "bugs": {
23
- "url": "https://github.com/fkom13/opencode-pollinations-plugin/issues"
24
- },
25
- "homepage": "https://github.com/fkom13/opencode-pollinations-plugin#readme",
26
- "type": "module",
27
- "exports": {
28
- ".": {
29
- "types": "./dist/index.d.ts",
30
- "default": "./dist/index.js"
31
- }
32
- },
33
- "bin": {
34
- "opencode-pollinations-plugin": "./bin/setup.js"
35
- },
36
- "main": "./dist/index.js",
37
- "types": "./dist/index.d.ts",
38
- "engines": {
39
- "node": ">=18"
40
- },
41
- "scripts": {
42
- "build": "tsc",
43
- "test": "npm run build && node scripts/tests/test-suite.cjs",
44
- "test:unit": "node scripts/tests/test-suite.cjs",
45
- "test:i18n": "node scripts/tests/test-i18n.cjs",
46
- "prepare": "npm run build",
47
- "prepublishOnly": "npm run build && npm run test:unit && npm run test:i18n"
48
- },
49
- "files": [
50
- "dist",
51
- "bin",
52
- "README.md",
53
- "LICENSE.md"
54
- ],
55
- "dependencies": {
56
- "@opencode-ai/plugin": "^1.0.85",
57
- "qrcode": "^1.5.4",
58
- "zod": "^3.25.76"
59
- },
60
- "devDependencies": {
61
- "@types/node": "^20.0.0",
62
- "@types/qrcode": "^1.5.6",
63
- "typescript": "^5.0.0"
2
+ "name": "opencode-pollinations-plugin",
3
+ "displayName": "Pollinations",
4
+ "version": "6.4.10",
5
+ "description": "Native Pollinations.ai Provider Plugin for OpenCode — free & premium AI models, media tools, quests, cost guards",
6
+ "author": "fkom13",
7
+ "license": "MIT",
8
+ "keywords": [
9
+ "opencode",
10
+ "pollinations",
11
+ "ai",
12
+ "plugin",
13
+ "image-generation",
14
+ "video-generation",
15
+ "llm",
16
+ "pollen"
17
+ ],
18
+ "repository": {
19
+ "type": "git",
20
+ "url": "git+https://github.com/fkom13/opencode-pollinations-plugin.git"
21
+ },
22
+ "bugs": {
23
+ "url": "https://github.com/fkom13/opencode-pollinations-plugin/issues"
24
+ },
25
+ "homepage": "https://github.com/fkom13/opencode-pollinations-plugin#readme",
26
+ "type": "module",
27
+ "exports": {
28
+ ".": {
29
+ "types": "./dist/index.d.ts",
30
+ "default": "./dist/index.js"
64
31
  }
32
+ },
33
+ "bin": {
34
+ "opencode-pollinations-plugin": "./bin/setup.js"
35
+ },
36
+ "main": "./dist/index.js",
37
+ "types": "./dist/index.d.ts",
38
+ "engines": {
39
+ "node": ">=18"
40
+ },
41
+ "scripts": {
42
+ "build": "tsc",
43
+ "test": "npm run build && node scripts/tests/test-suite.cjs",
44
+ "test:unit": "node scripts/tests/test-suite.cjs",
45
+ "test:i18n": "node scripts/tests/test-i18n.cjs",
46
+ "prepare": "npm run build",
47
+ "prepublishOnly": "npm run build && npm run test:unit && npm run test:i18n"
48
+ },
49
+ "files": [
50
+ "dist",
51
+ "bin",
52
+ "README.md",
53
+ "LICENSE.md"
54
+ ],
55
+ "dependencies": {
56
+ "@opencode-ai/plugin": "^1.0.85",
57
+ "qrcode": "^1.5.4",
58
+ "zod": "^3.25.76"
59
+ },
60
+ "devDependencies": {
61
+ "@types/node": "^20.0.0",
62
+ "@types/qrcode": "^1.5.6",
63
+ "typescript": "^5.0.0"
64
+ }
65
65
  }