diff --git a/src/renderer/locales/de/messages.po b/src/renderer/locales/de/messages.po index 0aaaa5e8c..14094d343 100644 --- a/src/renderer/locales/de/messages.po +++ b/src/renderer/locales/de/messages.po @@ -316,9 +316,12 @@ msgstr "{0}-Token" msgid "{0} tokens - {when}" msgstr "{0} Tokens - {when}" +#. placeholder {0}: agent.label #. placeholder {0}: agent.name #. placeholder {1}: agent.version +#. placeholder {1}: entry.targetVersion #: src/renderer/views/SettingsOverlay/parts/AcpRegistrySettings.tsx +#: src/renderer/views/SettingsOverlay/parts/useProviderUpdates.ts msgid "{0} updated to v{1}." msgstr "{0} auf Version {1} aktualisiert." @@ -7122,8 +7125,8 @@ msgstr "Modellbeschriftung" #: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx #: src/renderer/views/SettingsOverlay/parts/settingsSearchIndex.ts -msgid "Model order" -msgstr "Modellreihenfolge" +#~ msgid "Model order" +#~ msgstr "Modellreihenfolge" #: src/renderer/commands/registry.ts msgid "Model removed from favorites" @@ -9297,7 +9300,9 @@ msgstr "Anbieternutzung" msgid "providers" msgstr "Anbieter" +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx #: src/renderer/views/SettingsOverlay/parts/ProfileSettings.tsx +#: src/renderer/views/SettingsOverlay/parts/settingsSearchIndex.ts #: src/renderer/views/SettingsOverlay/parts/UsageSettings.tsx msgid "Providers" msgstr "Anbieter" @@ -13020,9 +13025,11 @@ msgstr "{0} ({envName}) kann nicht aktualisiert werden." msgid "Unable to update {0} hooks." msgstr "{0}-Hooks können nicht aktualisiert werden." +#. placeholder {0}: agent.label #. placeholder {0}: agentStatus.label #. placeholder {1}: detail.slice(0, 240) #: src/renderer/components/thread/ThreadAgentUpdateDock.tsx +#: src/renderer/views/SettingsOverlay/parts/useProviderUpdates.ts msgid "Unable to update {0}: {1}" msgstr "{0} kann nicht aktualisiert werden: {1}" @@ -13035,6 +13042,7 @@ msgstr "{0} kann nicht aktualisiert werden: {detailText}" #. placeholder {0}: agentStatus.label #: src/renderer/components/thread/ThreadAgentUpdateDock.tsx #: src/renderer/views/SettingsOverlay/parts/SingleAgentSettings/SingleAgentSettings.tsx +#: src/renderer/views/SettingsOverlay/parts/useProviderUpdates.ts msgid "Unable to update {0}." msgstr "{0} kann nicht aktualisiert werden." @@ -13228,11 +13236,17 @@ msgstr "Aktualisierung" msgid "Update" msgstr "Aktualisieren" +#. placeholder {0}: agent.label #. placeholder {0}: props.agentLabel +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx #: src/renderer/views/SettingsOverlay/parts/SingleAgentSettings/parts/AgentEnvironmentRow.tsx msgid "Update {0} to {updateLabel}" msgstr "Aktualisieren Sie {0} auf {updateLabel}" +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx +msgid "Update all" +msgstr "Alle aktualisieren" + #: src/renderer/components/thread/ThreadAgentUpdateDock.tsx msgid "Update available" msgstr "Update verfügbar" @@ -13289,7 +13303,9 @@ msgid "Update to {updateLabel} for {0} ({env})" msgstr "Update auf {updateLabel} für {0} ({env})" #. placeholder {0}: agent.version +#. placeholder {0}: update.targetVersion #: src/renderer/views/SettingsOverlay/parts/AcpRegistrySettings.tsx +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx msgid "Update to v{0}" msgstr "Update auf v{0}" @@ -13315,10 +13331,13 @@ msgid "Updated {0}" msgstr "{0} aktualisiert" #: src/renderer/views/SettingsOverlay/parts/AcpRegistrySettings.tsx +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx msgid "Updating" msgstr "Wird aktualisiert …" +#. placeholder {0}: agent.label #. placeholder {0}: props.agentLabel +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx #: src/renderer/views/SettingsOverlay/parts/SingleAgentSettings/parts/AgentEnvironmentRow.tsx msgid "Updating {0}" msgstr "{0} wird aktualisiert" diff --git a/src/renderer/locales/en/messages.po b/src/renderer/locales/en/messages.po index 8e61d83d8..434f1b537 100644 --- a/src/renderer/locales/en/messages.po +++ b/src/renderer/locales/en/messages.po @@ -316,9 +316,12 @@ msgstr "{0} tokens" msgid "{0} tokens - {when}" msgstr "{0} tokens - {when}" +#. placeholder {0}: agent.label #. placeholder {0}: agent.name #. placeholder {1}: agent.version +#. placeholder {1}: entry.targetVersion #: src/renderer/views/SettingsOverlay/parts/AcpRegistrySettings.tsx +#: src/renderer/views/SettingsOverlay/parts/useProviderUpdates.ts msgid "{0} updated to v{1}." msgstr "{0} updated to v{1}." @@ -7122,8 +7125,8 @@ msgstr "Model label" #: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx #: src/renderer/views/SettingsOverlay/parts/settingsSearchIndex.ts -msgid "Model order" -msgstr "Model order" +#~ msgid "Model order" +#~ msgstr "Model order" #: src/renderer/commands/registry.ts msgid "Model removed from favorites" @@ -9297,7 +9300,9 @@ msgstr "Provider Usage" msgid "providers" msgstr "providers" +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx #: src/renderer/views/SettingsOverlay/parts/ProfileSettings.tsx +#: src/renderer/views/SettingsOverlay/parts/settingsSearchIndex.ts #: src/renderer/views/SettingsOverlay/parts/UsageSettings.tsx msgid "Providers" msgstr "Providers" @@ -13020,9 +13025,11 @@ msgstr "Unable to update {0} ({envName})." msgid "Unable to update {0} hooks." msgstr "Unable to update {0} hooks." +#. placeholder {0}: agent.label #. placeholder {0}: agentStatus.label #. placeholder {1}: detail.slice(0, 240) #: src/renderer/components/thread/ThreadAgentUpdateDock.tsx +#: src/renderer/views/SettingsOverlay/parts/useProviderUpdates.ts msgid "Unable to update {0}: {1}" msgstr "Unable to update {0}: {1}" @@ -13035,6 +13042,7 @@ msgstr "Unable to update {0}: {detailText}" #. placeholder {0}: agentStatus.label #: src/renderer/components/thread/ThreadAgentUpdateDock.tsx #: src/renderer/views/SettingsOverlay/parts/SingleAgentSettings/SingleAgentSettings.tsx +#: src/renderer/views/SettingsOverlay/parts/useProviderUpdates.ts msgid "Unable to update {0}." msgstr "Unable to update {0}." @@ -13228,11 +13236,17 @@ msgstr "update" msgid "Update" msgstr "Update" +#. placeholder {0}: agent.label #. placeholder {0}: props.agentLabel +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx #: src/renderer/views/SettingsOverlay/parts/SingleAgentSettings/parts/AgentEnvironmentRow.tsx msgid "Update {0} to {updateLabel}" msgstr "Update {0} to {updateLabel}" +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx +msgid "Update all" +msgstr "Update all" + #: src/renderer/components/thread/ThreadAgentUpdateDock.tsx msgid "Update available" msgstr "Update available" @@ -13289,7 +13303,9 @@ msgid "Update to {updateLabel} for {0} ({env})" msgstr "Update to {updateLabel} for {0} ({env})" #. placeholder {0}: agent.version +#. placeholder {0}: update.targetVersion #: src/renderer/views/SettingsOverlay/parts/AcpRegistrySettings.tsx +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx msgid "Update to v{0}" msgstr "Update to v{0}" @@ -13315,10 +13331,13 @@ msgid "Updated {0}" msgstr "Updated {0}" #: src/renderer/views/SettingsOverlay/parts/AcpRegistrySettings.tsx +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx msgid "Updating" msgstr "Updating" +#. placeholder {0}: agent.label #. placeholder {0}: props.agentLabel +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx #: src/renderer/views/SettingsOverlay/parts/SingleAgentSettings/parts/AgentEnvironmentRow.tsx msgid "Updating {0}" msgstr "Updating {0}" diff --git a/src/renderer/locales/es/messages.po b/src/renderer/locales/es/messages.po index 90275dbcb..701c9e944 100644 --- a/src/renderer/locales/es/messages.po +++ b/src/renderer/locales/es/messages.po @@ -316,9 +316,12 @@ msgstr "{0} tokens" msgid "{0} tokens - {when}" msgstr "{0} tokens - {when}" +#. placeholder {0}: agent.label #. placeholder {0}: agent.name #. placeholder {1}: agent.version +#. placeholder {1}: entry.targetVersion #: src/renderer/views/SettingsOverlay/parts/AcpRegistrySettings.tsx +#: src/renderer/views/SettingsOverlay/parts/useProviderUpdates.ts msgid "{0} updated to v{1}." msgstr "{0} actualizado a v{1}." @@ -7122,8 +7125,8 @@ msgstr "Etiqueta del modelo" #: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx #: src/renderer/views/SettingsOverlay/parts/settingsSearchIndex.ts -msgid "Model order" -msgstr "Orden de modelos" +#~ msgid "Model order" +#~ msgstr "Orden de modelos" #: src/renderer/commands/registry.ts msgid "Model removed from favorites" @@ -9297,7 +9300,9 @@ msgstr "Uso de proveedores" msgid "providers" msgstr "proveedores" +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx #: src/renderer/views/SettingsOverlay/parts/ProfileSettings.tsx +#: src/renderer/views/SettingsOverlay/parts/settingsSearchIndex.ts #: src/renderer/views/SettingsOverlay/parts/UsageSettings.tsx msgid "Providers" msgstr "Proveedores" @@ -13020,9 +13025,11 @@ msgstr "No se puede actualizar {0} ({envName})." msgid "Unable to update {0} hooks." msgstr "No se pueden actualizar los hooks de {0}." +#. placeholder {0}: agent.label #. placeholder {0}: agentStatus.label #. placeholder {1}: detail.slice(0, 240) #: src/renderer/components/thread/ThreadAgentUpdateDock.tsx +#: src/renderer/views/SettingsOverlay/parts/useProviderUpdates.ts msgid "Unable to update {0}: {1}" msgstr "No se puede actualizar {0}: {1}" @@ -13035,6 +13042,7 @@ msgstr "No se puede actualizar {0}: {detailText}" #. placeholder {0}: agentStatus.label #: src/renderer/components/thread/ThreadAgentUpdateDock.tsx #: src/renderer/views/SettingsOverlay/parts/SingleAgentSettings/SingleAgentSettings.tsx +#: src/renderer/views/SettingsOverlay/parts/useProviderUpdates.ts msgid "Unable to update {0}." msgstr "No se puede actualizar {0}." @@ -13228,11 +13236,17 @@ msgstr "actualización" msgid "Update" msgstr "Actualizar" +#. placeholder {0}: agent.label #. placeholder {0}: props.agentLabel +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx #: src/renderer/views/SettingsOverlay/parts/SingleAgentSettings/parts/AgentEnvironmentRow.tsx msgid "Update {0} to {updateLabel}" msgstr "Actualizar {0} a {updateLabel}" +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx +msgid "Update all" +msgstr "Actualizar todo" + #: src/renderer/components/thread/ThreadAgentUpdateDock.tsx msgid "Update available" msgstr "Actualización disponible" @@ -13289,7 +13303,9 @@ msgid "Update to {updateLabel} for {0} ({env})" msgstr "Actualizar a {updateLabel} para {0} ({env})" #. placeholder {0}: agent.version +#. placeholder {0}: update.targetVersion #: src/renderer/views/SettingsOverlay/parts/AcpRegistrySettings.tsx +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx msgid "Update to v{0}" msgstr "Actualizar a v{0}" @@ -13315,10 +13331,13 @@ msgid "Updated {0}" msgstr "Actualizado {0}" #: src/renderer/views/SettingsOverlay/parts/AcpRegistrySettings.tsx +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx msgid "Updating" msgstr "Actualizando" +#. placeholder {0}: agent.label #. placeholder {0}: props.agentLabel +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx #: src/renderer/views/SettingsOverlay/parts/SingleAgentSettings/parts/AgentEnvironmentRow.tsx msgid "Updating {0}" msgstr "Actualizando {0}" diff --git a/src/renderer/locales/fr/messages.po b/src/renderer/locales/fr/messages.po index ccd43ac7f..05e20268b 100644 --- a/src/renderer/locales/fr/messages.po +++ b/src/renderer/locales/fr/messages.po @@ -316,9 +316,12 @@ msgstr "{0} jetons" msgid "{0} tokens - {when}" msgstr "{0} tokens - {when}" +#. placeholder {0}: agent.label #. placeholder {0}: agent.name #. placeholder {1}: agent.version +#. placeholder {1}: entry.targetVersion #: src/renderer/views/SettingsOverlay/parts/AcpRegistrySettings.tsx +#: src/renderer/views/SettingsOverlay/parts/useProviderUpdates.ts msgid "{0} updated to v{1}." msgstr "{0} mis à jour vers v{1}." @@ -7121,8 +7124,8 @@ msgstr "Libellé du modèle" #: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx #: src/renderer/views/SettingsOverlay/parts/settingsSearchIndex.ts -msgid "Model order" -msgstr "Ordre des modèles" +#~ msgid "Model order" +#~ msgstr "Ordre des modèles" #: src/renderer/commands/registry.ts msgid "Model removed from favorites" @@ -9296,7 +9299,9 @@ msgstr "Utilisation des fournisseurs" msgid "providers" msgstr "fournisseurs" +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx #: src/renderer/views/SettingsOverlay/parts/ProfileSettings.tsx +#: src/renderer/views/SettingsOverlay/parts/settingsSearchIndex.ts #: src/renderer/views/SettingsOverlay/parts/UsageSettings.tsx msgid "Providers" msgstr "Fournisseurs" @@ -13019,9 +13024,11 @@ msgstr "Impossible de mettre à jour {0} ({envName})." msgid "Unable to update {0} hooks." msgstr "Impossible de mettre à jour les hooks {0}." +#. placeholder {0}: agent.label #. placeholder {0}: agentStatus.label #. placeholder {1}: detail.slice(0, 240) #: src/renderer/components/thread/ThreadAgentUpdateDock.tsx +#: src/renderer/views/SettingsOverlay/parts/useProviderUpdates.ts msgid "Unable to update {0}: {1}" msgstr "Impossible de mettre à jour {0} : {1}" @@ -13034,6 +13041,7 @@ msgstr "Impossible de mettre à jour {0} : {detailText}" #. placeholder {0}: agentStatus.label #: src/renderer/components/thread/ThreadAgentUpdateDock.tsx #: src/renderer/views/SettingsOverlay/parts/SingleAgentSettings/SingleAgentSettings.tsx +#: src/renderer/views/SettingsOverlay/parts/useProviderUpdates.ts msgid "Unable to update {0}." msgstr "Impossible de mettre à jour {0}." @@ -13227,11 +13235,17 @@ msgstr "mise à jour" msgid "Update" msgstr "Mise à jour" +#. placeholder {0}: agent.label #. placeholder {0}: props.agentLabel +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx #: src/renderer/views/SettingsOverlay/parts/SingleAgentSettings/parts/AgentEnvironmentRow.tsx msgid "Update {0} to {updateLabel}" msgstr "Mettre à jour {0} vers {updateLabel}" +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx +msgid "Update all" +msgstr "Tout mettre à jour" + #: src/renderer/components/thread/ThreadAgentUpdateDock.tsx msgid "Update available" msgstr "Mise à jour disponible" @@ -13288,7 +13302,9 @@ msgid "Update to {updateLabel} for {0} ({env})" msgstr "Mise à jour vers {updateLabel} pour {0} ({env})" #. placeholder {0}: agent.version +#. placeholder {0}: update.targetVersion #: src/renderer/views/SettingsOverlay/parts/AcpRegistrySettings.tsx +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx msgid "Update to v{0}" msgstr "Mise à jour vers v{0}" @@ -13314,10 +13330,13 @@ msgid "Updated {0}" msgstr "{0} mis à jour" #: src/renderer/views/SettingsOverlay/parts/AcpRegistrySettings.tsx +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx msgid "Updating" msgstr "Mise à jour" +#. placeholder {0}: agent.label #. placeholder {0}: props.agentLabel +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx #: src/renderer/views/SettingsOverlay/parts/SingleAgentSettings/parts/AgentEnvironmentRow.tsx msgid "Updating {0}" msgstr "Mise à jour de {0}" diff --git a/src/renderer/locales/ja/messages.po b/src/renderer/locales/ja/messages.po index a839d9a4f..b1a99008a 100644 --- a/src/renderer/locales/ja/messages.po +++ b/src/renderer/locales/ja/messages.po @@ -316,9 +316,12 @@ msgstr "{0}トークン" msgid "{0} tokens - {when}" msgstr "{0}トークン - {when}" +#. placeholder {0}: agent.label #. placeholder {0}: agent.name #. placeholder {1}: agent.version +#. placeholder {1}: entry.targetVersion #: src/renderer/views/SettingsOverlay/parts/AcpRegistrySettings.tsx +#: src/renderer/views/SettingsOverlay/parts/useProviderUpdates.ts msgid "{0} updated to v{1}." msgstr "{0}が v{1}に更新されました。" @@ -7120,8 +7123,8 @@ msgstr "モデルラベル" #: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx #: src/renderer/views/SettingsOverlay/parts/settingsSearchIndex.ts -msgid "Model order" -msgstr "モデルオーダー" +#~ msgid "Model order" +#~ msgstr "モデルオーダー" #: src/renderer/commands/registry.ts msgid "Model removed from favorites" @@ -9295,7 +9298,9 @@ msgstr "プロバイダーの使用量" msgid "providers" msgstr "プロバイダー" +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx #: src/renderer/views/SettingsOverlay/parts/ProfileSettings.tsx +#: src/renderer/views/SettingsOverlay/parts/settingsSearchIndex.ts #: src/renderer/views/SettingsOverlay/parts/UsageSettings.tsx msgid "Providers" msgstr "プロバイダー" @@ -13018,9 +13023,11 @@ msgstr "{0}({envName}) を更新できません。" msgid "Unable to update {0} hooks." msgstr "{0}フックを更新できません。" +#. placeholder {0}: agent.label #. placeholder {0}: agentStatus.label #. placeholder {1}: detail.slice(0, 240) #: src/renderer/components/thread/ThreadAgentUpdateDock.tsx +#: src/renderer/views/SettingsOverlay/parts/useProviderUpdates.ts msgid "Unable to update {0}: {1}" msgstr "{0}を更新できません:{1}" @@ -13033,6 +13040,7 @@ msgstr "{0}を更新できません:{detailText}" #. placeholder {0}: agentStatus.label #: src/renderer/components/thread/ThreadAgentUpdateDock.tsx #: src/renderer/views/SettingsOverlay/parts/SingleAgentSettings/SingleAgentSettings.tsx +#: src/renderer/views/SettingsOverlay/parts/useProviderUpdates.ts msgid "Unable to update {0}." msgstr "{0}を更新できません。" @@ -13226,11 +13234,17 @@ msgstr "更新" msgid "Update" msgstr "アップデート" +#. placeholder {0}: agent.label #. placeholder {0}: props.agentLabel +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx #: src/renderer/views/SettingsOverlay/parts/SingleAgentSettings/parts/AgentEnvironmentRow.tsx msgid "Update {0} to {updateLabel}" msgstr "{0}を{updateLabel}に更新します" +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx +msgid "Update all" +msgstr "すべて更新" + #: src/renderer/components/thread/ThreadAgentUpdateDock.tsx msgid "Update available" msgstr "利用可能なアップデート" @@ -13287,7 +13301,9 @@ msgid "Update to {updateLabel} for {0} ({env})" msgstr "{0}({env}) の{updateLabel}への更新" #. placeholder {0}: agent.version +#. placeholder {0}: update.targetVersion #: src/renderer/views/SettingsOverlay/parts/AcpRegistrySettings.tsx +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx msgid "Update to v{0}" msgstr "v{0}に更新" @@ -13313,10 +13329,13 @@ msgid "Updated {0}" msgstr "{0}を更新しました" #: src/renderer/views/SettingsOverlay/parts/AcpRegistrySettings.tsx +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx msgid "Updating" msgstr "更新中" +#. placeholder {0}: agent.label #. placeholder {0}: props.agentLabel +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx #: src/renderer/views/SettingsOverlay/parts/SingleAgentSettings/parts/AgentEnvironmentRow.tsx msgid "Updating {0}" msgstr "{0}を更新しています" diff --git a/src/renderer/locales/ko/messages.po b/src/renderer/locales/ko/messages.po index c36c20024..f7d5807af 100644 --- a/src/renderer/locales/ko/messages.po +++ b/src/renderer/locales/ko/messages.po @@ -316,9 +316,12 @@ msgstr "{0} 토큰" msgid "{0} tokens - {when}" msgstr "토큰 {0} - {when}" +#. placeholder {0}: agent.label #. placeholder {0}: agent.name #. placeholder {1}: agent.version +#. placeholder {1}: entry.targetVersion #: src/renderer/views/SettingsOverlay/parts/AcpRegistrySettings.tsx +#: src/renderer/views/SettingsOverlay/parts/useProviderUpdates.ts msgid "{0} updated to v{1}." msgstr "{0}이 v{1}로 업데이트되었습니다." @@ -7122,8 +7125,8 @@ msgstr "모델 레이블" #: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx #: src/renderer/views/SettingsOverlay/parts/settingsSearchIndex.ts -msgid "Model order" -msgstr "모델 순서" +#~ msgid "Model order" +#~ msgstr "모델 순서" #: src/renderer/commands/registry.ts msgid "Model removed from favorites" @@ -9297,7 +9300,9 @@ msgstr "공급자 사용량" msgid "providers" msgstr "공급자" +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx #: src/renderer/views/SettingsOverlay/parts/ProfileSettings.tsx +#: src/renderer/views/SettingsOverlay/parts/settingsSearchIndex.ts #: src/renderer/views/SettingsOverlay/parts/UsageSettings.tsx msgid "Providers" msgstr "공급자" @@ -13020,9 +13025,11 @@ msgstr "{0}({envName})을 업데이트할 수 없습니다." msgid "Unable to update {0} hooks." msgstr "{0} 후크를 업데이트할 수 없습니다." +#. placeholder {0}: agent.label #. placeholder {0}: agentStatus.label #. placeholder {1}: detail.slice(0, 240) #: src/renderer/components/thread/ThreadAgentUpdateDock.tsx +#: src/renderer/views/SettingsOverlay/parts/useProviderUpdates.ts msgid "Unable to update {0}: {1}" msgstr "{0}을(를) 업데이트할 수 없습니다: {1}" @@ -13035,6 +13042,7 @@ msgstr "{0}을(를) 업데이트할 수 없습니다: {detailText}" #. placeholder {0}: agentStatus.label #: src/renderer/components/thread/ThreadAgentUpdateDock.tsx #: src/renderer/views/SettingsOverlay/parts/SingleAgentSettings/SingleAgentSettings.tsx +#: src/renderer/views/SettingsOverlay/parts/useProviderUpdates.ts msgid "Unable to update {0}." msgstr "{0}을(를) 업데이트할 수 없습니다." @@ -13228,11 +13236,17 @@ msgstr "업데이트" msgid "Update" msgstr "업데이트" +#. placeholder {0}: agent.label #. placeholder {0}: props.agentLabel +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx #: src/renderer/views/SettingsOverlay/parts/SingleAgentSettings/parts/AgentEnvironmentRow.tsx msgid "Update {0} to {updateLabel}" msgstr "{0}을(를) {updateLabel}(으)로 업데이트" +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx +msgid "Update all" +msgstr "모두 업데이트" + #: src/renderer/components/thread/ThreadAgentUpdateDock.tsx msgid "Update available" msgstr "업데이트 가능" @@ -13289,7 +13303,9 @@ msgid "Update to {updateLabel} for {0} ({env})" msgstr "{0}({env})에 대한 {updateLabel}(으)로 업데이트" #. placeholder {0}: agent.version +#. placeholder {0}: update.targetVersion #: src/renderer/views/SettingsOverlay/parts/AcpRegistrySettings.tsx +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx msgid "Update to v{0}" msgstr "v{0}(으)로 업데이트" @@ -13315,10 +13331,13 @@ msgid "Updated {0}" msgstr "{0} 업데이트됨" #: src/renderer/views/SettingsOverlay/parts/AcpRegistrySettings.tsx +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx msgid "Updating" msgstr "업데이트 중" +#. placeholder {0}: agent.label #. placeholder {0}: props.agentLabel +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx #: src/renderer/views/SettingsOverlay/parts/SingleAgentSettings/parts/AgentEnvironmentRow.tsx msgid "Updating {0}" msgstr "{0} 업데이트 중" diff --git a/src/renderer/locales/pl/messages.po b/src/renderer/locales/pl/messages.po index 230b25abf..60467d94b 100644 --- a/src/renderer/locales/pl/messages.po +++ b/src/renderer/locales/pl/messages.po @@ -316,9 +316,12 @@ msgstr "{0} tokenów" msgid "{0} tokens - {when}" msgstr "{0} tokenów - {when}" +#. placeholder {0}: agent.label #. placeholder {0}: agent.name #. placeholder {1}: agent.version +#. placeholder {1}: entry.targetVersion #: src/renderer/views/SettingsOverlay/parts/AcpRegistrySettings.tsx +#: src/renderer/views/SettingsOverlay/parts/useProviderUpdates.ts msgid "{0} updated to v{1}." msgstr "{0} zaktualizowano do wersji {1}." @@ -7122,8 +7125,8 @@ msgstr "Etykieta modelu" #: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx #: src/renderer/views/SettingsOverlay/parts/settingsSearchIndex.ts -msgid "Model order" -msgstr "Kolejność modeli" +#~ msgid "Model order" +#~ msgstr "Kolejność modeli" #: src/renderer/commands/registry.ts msgid "Model removed from favorites" @@ -9297,7 +9300,9 @@ msgstr "Użycie dostawców" msgid "providers" msgstr "dostawcy" +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx #: src/renderer/views/SettingsOverlay/parts/ProfileSettings.tsx +#: src/renderer/views/SettingsOverlay/parts/settingsSearchIndex.ts #: src/renderer/views/SettingsOverlay/parts/UsageSettings.tsx msgid "Providers" msgstr "Dostawcy" @@ -13020,9 +13025,11 @@ msgstr "Nie można zaktualizować {0} ({envName})." msgid "Unable to update {0} hooks." msgstr "Nie można zaktualizować haków {0}." +#. placeholder {0}: agent.label #. placeholder {0}: agentStatus.label #. placeholder {1}: detail.slice(0, 240) #: src/renderer/components/thread/ThreadAgentUpdateDock.tsx +#: src/renderer/views/SettingsOverlay/parts/useProviderUpdates.ts msgid "Unable to update {0}: {1}" msgstr "Nie można zaktualizować {0}: {1}" @@ -13035,6 +13042,7 @@ msgstr "Nie można zaktualizować {0}: {detailText}" #. placeholder {0}: agentStatus.label #: src/renderer/components/thread/ThreadAgentUpdateDock.tsx #: src/renderer/views/SettingsOverlay/parts/SingleAgentSettings/SingleAgentSettings.tsx +#: src/renderer/views/SettingsOverlay/parts/useProviderUpdates.ts msgid "Unable to update {0}." msgstr "Nie można zaktualizować {0}." @@ -13228,11 +13236,17 @@ msgstr "aktualizacja" msgid "Update" msgstr "Aktualizacja" +#. placeholder {0}: agent.label #. placeholder {0}: props.agentLabel +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx #: src/renderer/views/SettingsOverlay/parts/SingleAgentSettings/parts/AgentEnvironmentRow.tsx msgid "Update {0} to {updateLabel}" msgstr "Zaktualizuj {0} do {updateLabel}" +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx +msgid "Update all" +msgstr "Zaktualizuj wszystko" + #: src/renderer/components/thread/ThreadAgentUpdateDock.tsx msgid "Update available" msgstr "Dostępna aktualizacja" @@ -13289,7 +13303,9 @@ msgid "Update to {updateLabel} for {0} ({env})" msgstr "Aktualizacja do {updateLabel} dla {0} ({env})" #. placeholder {0}: agent.version +#. placeholder {0}: update.targetVersion #: src/renderer/views/SettingsOverlay/parts/AcpRegistrySettings.tsx +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx msgid "Update to v{0}" msgstr "Aktualizacja do wersji {0}" @@ -13315,10 +13331,13 @@ msgid "Updated {0}" msgstr "Zaktualizowano {0}" #: src/renderer/views/SettingsOverlay/parts/AcpRegistrySettings.tsx +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx msgid "Updating" msgstr "Aktualizowanie" +#. placeholder {0}: agent.label #. placeholder {0}: props.agentLabel +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx #: src/renderer/views/SettingsOverlay/parts/SingleAgentSettings/parts/AgentEnvironmentRow.tsx msgid "Updating {0}" msgstr "Aktualizowanie {0}" diff --git a/src/renderer/locales/pt-BR/messages.po b/src/renderer/locales/pt-BR/messages.po index 3841aff4c..93b62458c 100644 --- a/src/renderer/locales/pt-BR/messages.po +++ b/src/renderer/locales/pt-BR/messages.po @@ -316,9 +316,12 @@ msgstr "{0} tokens" msgid "{0} tokens - {when}" msgstr "{0} tokens - {when}" +#. placeholder {0}: agent.label #. placeholder {0}: agent.name #. placeholder {1}: agent.version +#. placeholder {1}: entry.targetVersion #: src/renderer/views/SettingsOverlay/parts/AcpRegistrySettings.tsx +#: src/renderer/views/SettingsOverlay/parts/useProviderUpdates.ts msgid "{0} updated to v{1}." msgstr "{0} atualizado para v{1}." @@ -7122,8 +7125,8 @@ msgstr "Rótulo do modelo" #: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx #: src/renderer/views/SettingsOverlay/parts/settingsSearchIndex.ts -msgid "Model order" -msgstr "Ordem do modelo" +#~ msgid "Model order" +#~ msgstr "Ordem do modelo" #: src/renderer/commands/registry.ts msgid "Model removed from favorites" @@ -9297,7 +9300,9 @@ msgstr "Uso de provedores" msgid "providers" msgstr "provedores" +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx #: src/renderer/views/SettingsOverlay/parts/ProfileSettings.tsx +#: src/renderer/views/SettingsOverlay/parts/settingsSearchIndex.ts #: src/renderer/views/SettingsOverlay/parts/UsageSettings.tsx msgid "Providers" msgstr "Provedores" @@ -13020,9 +13025,11 @@ msgstr "Não foi possível atualizar {0} ({envName})." msgid "Unable to update {0} hooks." msgstr "Não foi possível atualizar os ganchos do {0}." +#. placeholder {0}: agent.label #. placeholder {0}: agentStatus.label #. placeholder {1}: detail.slice(0, 240) #: src/renderer/components/thread/ThreadAgentUpdateDock.tsx +#: src/renderer/views/SettingsOverlay/parts/useProviderUpdates.ts msgid "Unable to update {0}: {1}" msgstr "Não foi possível atualizar {0}: {1}" @@ -13035,6 +13042,7 @@ msgstr "Não foi possível atualizar {0}: {detailText}" #. placeholder {0}: agentStatus.label #: src/renderer/components/thread/ThreadAgentUpdateDock.tsx #: src/renderer/views/SettingsOverlay/parts/SingleAgentSettings/SingleAgentSettings.tsx +#: src/renderer/views/SettingsOverlay/parts/useProviderUpdates.ts msgid "Unable to update {0}." msgstr "Não foi possível atualizar {0}." @@ -13228,11 +13236,17 @@ msgstr "atualização" msgid "Update" msgstr "Atualizar" +#. placeholder {0}: agent.label #. placeholder {0}: props.agentLabel +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx #: src/renderer/views/SettingsOverlay/parts/SingleAgentSettings/parts/AgentEnvironmentRow.tsx msgid "Update {0} to {updateLabel}" msgstr "Atualizar {0} para {updateLabel}" +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx +msgid "Update all" +msgstr "Atualizar tudo" + #: src/renderer/components/thread/ThreadAgentUpdateDock.tsx msgid "Update available" msgstr "Atualização disponível" @@ -13289,7 +13303,9 @@ msgid "Update to {updateLabel} for {0} ({env})" msgstr "Atualizar para {updateLabel} para {0} ({env})" #. placeholder {0}: agent.version +#. placeholder {0}: update.targetVersion #: src/renderer/views/SettingsOverlay/parts/AcpRegistrySettings.tsx +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx msgid "Update to v{0}" msgstr "Atualizar para v{0}" @@ -13315,10 +13331,13 @@ msgid "Updated {0}" msgstr "Atualizado {0}" #: src/renderer/views/SettingsOverlay/parts/AcpRegistrySettings.tsx +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx msgid "Updating" msgstr "Atualizando" +#. placeholder {0}: agent.label #. placeholder {0}: props.agentLabel +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx #: src/renderer/views/SettingsOverlay/parts/SingleAgentSettings/parts/AgentEnvironmentRow.tsx msgid "Updating {0}" msgstr "Atualizando {0}" diff --git a/src/renderer/locales/ru/messages.po b/src/renderer/locales/ru/messages.po index e16b3255e..01b744291 100644 --- a/src/renderer/locales/ru/messages.po +++ b/src/renderer/locales/ru/messages.po @@ -316,9 +316,12 @@ msgstr "{0} токенов" msgid "{0} tokens - {when}" msgstr "{0} токенов - {when}" +#. placeholder {0}: agent.label #. placeholder {0}: agent.name #. placeholder {1}: agent.version +#. placeholder {1}: entry.targetVersion #: src/renderer/views/SettingsOverlay/parts/AcpRegistrySettings.tsx +#: src/renderer/views/SettingsOverlay/parts/useProviderUpdates.ts msgid "{0} updated to v{1}." msgstr "{0} обновлён до v{1}." @@ -7122,8 +7125,8 @@ msgstr "Метка модели" #: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx #: src/renderer/views/SettingsOverlay/parts/settingsSearchIndex.ts -msgid "Model order" -msgstr "Порядок моделей" +#~ msgid "Model order" +#~ msgstr "Порядок моделей" #: src/renderer/commands/registry.ts msgid "Model removed from favorites" @@ -9297,7 +9300,9 @@ msgstr "Использование провайдеров" msgid "providers" msgstr "провайдеры" +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx #: src/renderer/views/SettingsOverlay/parts/ProfileSettings.tsx +#: src/renderer/views/SettingsOverlay/parts/settingsSearchIndex.ts #: src/renderer/views/SettingsOverlay/parts/UsageSettings.tsx msgid "Providers" msgstr "Провайдеры" @@ -13020,9 +13025,11 @@ msgstr "Не удалось обновить {0} ({envName})." msgid "Unable to update {0} hooks." msgstr "Не удалось обновить хуки {0}." +#. placeholder {0}: agent.label #. placeholder {0}: agentStatus.label #. placeholder {1}: detail.slice(0, 240) #: src/renderer/components/thread/ThreadAgentUpdateDock.tsx +#: src/renderer/views/SettingsOverlay/parts/useProviderUpdates.ts msgid "Unable to update {0}: {1}" msgstr "Не удалось обновить {0}: {1}" @@ -13035,6 +13042,7 @@ msgstr "Не удалось обновить {0}: {detailText}" #. placeholder {0}: agentStatus.label #: src/renderer/components/thread/ThreadAgentUpdateDock.tsx #: src/renderer/views/SettingsOverlay/parts/SingleAgentSettings/SingleAgentSettings.tsx +#: src/renderer/views/SettingsOverlay/parts/useProviderUpdates.ts msgid "Unable to update {0}." msgstr "Не удалось обновить {0}." @@ -13228,11 +13236,17 @@ msgstr "обновление" msgid "Update" msgstr "Обновить" +#. placeholder {0}: agent.label #. placeholder {0}: props.agentLabel +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx #: src/renderer/views/SettingsOverlay/parts/SingleAgentSettings/parts/AgentEnvironmentRow.tsx msgid "Update {0} to {updateLabel}" msgstr "Обновить {0} до {updateLabel}" +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx +msgid "Update all" +msgstr "Обновить все" + #: src/renderer/components/thread/ThreadAgentUpdateDock.tsx msgid "Update available" msgstr "Доступно обновление" @@ -13289,7 +13303,9 @@ msgid "Update to {updateLabel} for {0} ({env})" msgstr "Обновить до {updateLabel} для {0} ({env})" #. placeholder {0}: agent.version +#. placeholder {0}: update.targetVersion #: src/renderer/views/SettingsOverlay/parts/AcpRegistrySettings.tsx +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx msgid "Update to v{0}" msgstr "Обновить до v{0}" @@ -13315,10 +13331,13 @@ msgid "Updated {0}" msgstr "Обновлено {0}" #: src/renderer/views/SettingsOverlay/parts/AcpRegistrySettings.tsx +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx msgid "Updating" msgstr "Обновление" +#. placeholder {0}: agent.label #. placeholder {0}: props.agentLabel +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx #: src/renderer/views/SettingsOverlay/parts/SingleAgentSettings/parts/AgentEnvironmentRow.tsx msgid "Updating {0}" msgstr "Обновление {0}" diff --git a/src/renderer/locales/tr/messages.po b/src/renderer/locales/tr/messages.po index 3f70d1b5a..9dfdc17d3 100644 --- a/src/renderer/locales/tr/messages.po +++ b/src/renderer/locales/tr/messages.po @@ -316,9 +316,12 @@ msgstr "{0} jeton" msgid "{0} tokens - {when}" msgstr "{0} token - {when}" +#. placeholder {0}: agent.label #. placeholder {0}: agent.name #. placeholder {1}: agent.version +#. placeholder {1}: entry.targetVersion #: src/renderer/views/SettingsOverlay/parts/AcpRegistrySettings.tsx +#: src/renderer/views/SettingsOverlay/parts/useProviderUpdates.ts msgid "{0} updated to v{1}." msgstr "{0} v{1} sürümüne güncellendi." @@ -7122,8 +7125,8 @@ msgstr "Model etiketi" #: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx #: src/renderer/views/SettingsOverlay/parts/settingsSearchIndex.ts -msgid "Model order" -msgstr "Model sırası" +#~ msgid "Model order" +#~ msgstr "Model sırası" #: src/renderer/commands/registry.ts msgid "Model removed from favorites" @@ -9297,7 +9300,9 @@ msgstr "Sağlayıcı kullanımı" msgid "providers" msgstr "sağlayıcılar" +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx #: src/renderer/views/SettingsOverlay/parts/ProfileSettings.tsx +#: src/renderer/views/SettingsOverlay/parts/settingsSearchIndex.ts #: src/renderer/views/SettingsOverlay/parts/UsageSettings.tsx msgid "Providers" msgstr "Sağlayıcılar" @@ -13020,9 +13025,11 @@ msgstr "{0} ({envName}) güncellenemiyor." msgid "Unable to update {0} hooks." msgstr "{0} kancaları güncellenemiyor." +#. placeholder {0}: agent.label #. placeholder {0}: agentStatus.label #. placeholder {1}: detail.slice(0, 240) #: src/renderer/components/thread/ThreadAgentUpdateDock.tsx +#: src/renderer/views/SettingsOverlay/parts/useProviderUpdates.ts msgid "Unable to update {0}: {1}" msgstr "{0} güncellenemiyor: {1}" @@ -13035,6 +13042,7 @@ msgstr "{0} güncellenemiyor: {detailText}" #. placeholder {0}: agentStatus.label #: src/renderer/components/thread/ThreadAgentUpdateDock.tsx #: src/renderer/views/SettingsOverlay/parts/SingleAgentSettings/SingleAgentSettings.tsx +#: src/renderer/views/SettingsOverlay/parts/useProviderUpdates.ts msgid "Unable to update {0}." msgstr "{0} güncellenemiyor." @@ -13228,11 +13236,17 @@ msgstr "güncelleme" msgid "Update" msgstr "Güncelleme" +#. placeholder {0}: agent.label #. placeholder {0}: props.agentLabel +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx #: src/renderer/views/SettingsOverlay/parts/SingleAgentSettings/parts/AgentEnvironmentRow.tsx msgid "Update {0} to {updateLabel}" msgstr "{0} öğesini {updateLabel} olarak güncelleyin" +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx +msgid "Update all" +msgstr "Tümünü güncelle" + #: src/renderer/components/thread/ThreadAgentUpdateDock.tsx msgid "Update available" msgstr "Güncelleme mevcut" @@ -13289,7 +13303,9 @@ msgid "Update to {updateLabel} for {0} ({env})" msgstr "{0} ({env}) için {updateLabel} güncellemesi" #. placeholder {0}: agent.version +#. placeholder {0}: update.targetVersion #: src/renderer/views/SettingsOverlay/parts/AcpRegistrySettings.tsx +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx msgid "Update to v{0}" msgstr "v{0}'ye güncelleme" @@ -13315,10 +13331,13 @@ msgid "Updated {0}" msgstr "{0} güncellendi" #: src/renderer/views/SettingsOverlay/parts/AcpRegistrySettings.tsx +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx msgid "Updating" msgstr "Güncelleniyor" +#. placeholder {0}: agent.label #. placeholder {0}: props.agentLabel +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx #: src/renderer/views/SettingsOverlay/parts/SingleAgentSettings/parts/AgentEnvironmentRow.tsx msgid "Updating {0}" msgstr "{0} güncelleniyor" diff --git a/src/renderer/locales/uk/messages.po b/src/renderer/locales/uk/messages.po index a70fc6f49..e912ca6dd 100644 --- a/src/renderer/locales/uk/messages.po +++ b/src/renderer/locales/uk/messages.po @@ -316,9 +316,12 @@ msgstr "{0} токенів" msgid "{0} tokens - {when}" msgstr "{0} токенів - {when}" +#. placeholder {0}: agent.label #. placeholder {0}: agent.name #. placeholder {1}: agent.version +#. placeholder {1}: entry.targetVersion #: src/renderer/views/SettingsOverlay/parts/AcpRegistrySettings.tsx +#: src/renderer/views/SettingsOverlay/parts/useProviderUpdates.ts msgid "{0} updated to v{1}." msgstr "{0} оновлено до v{1}." @@ -7122,8 +7125,8 @@ msgstr "Мітка моделі" #: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx #: src/renderer/views/SettingsOverlay/parts/settingsSearchIndex.ts -msgid "Model order" -msgstr "Порядок моделей" +#~ msgid "Model order" +#~ msgstr "Порядок моделей" #: src/renderer/commands/registry.ts msgid "Model removed from favorites" @@ -9297,7 +9300,9 @@ msgstr "Використання провайдерів" msgid "providers" msgstr "провайдери" +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx #: src/renderer/views/SettingsOverlay/parts/ProfileSettings.tsx +#: src/renderer/views/SettingsOverlay/parts/settingsSearchIndex.ts #: src/renderer/views/SettingsOverlay/parts/UsageSettings.tsx msgid "Providers" msgstr "Постачальники" @@ -13020,9 +13025,11 @@ msgstr "Не вдалося оновити {0} ({envName})." msgid "Unable to update {0} hooks." msgstr "Не вдалося оновити хуки {0}." +#. placeholder {0}: agent.label #. placeholder {0}: agentStatus.label #. placeholder {1}: detail.slice(0, 240) #: src/renderer/components/thread/ThreadAgentUpdateDock.tsx +#: src/renderer/views/SettingsOverlay/parts/useProviderUpdates.ts msgid "Unable to update {0}: {1}" msgstr "Не вдалося оновити {0}: {1}" @@ -13035,6 +13042,7 @@ msgstr "Не вдалося оновити {0}: {detailText}" #. placeholder {0}: agentStatus.label #: src/renderer/components/thread/ThreadAgentUpdateDock.tsx #: src/renderer/views/SettingsOverlay/parts/SingleAgentSettings/SingleAgentSettings.tsx +#: src/renderer/views/SettingsOverlay/parts/useProviderUpdates.ts msgid "Unable to update {0}." msgstr "Не вдалося оновити {0}." @@ -13228,11 +13236,17 @@ msgstr "оновлення" msgid "Update" msgstr "Оновити" +#. placeholder {0}: agent.label #. placeholder {0}: props.agentLabel +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx #: src/renderer/views/SettingsOverlay/parts/SingleAgentSettings/parts/AgentEnvironmentRow.tsx msgid "Update {0} to {updateLabel}" msgstr "Оновити {0} до {updateLabel}" +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx +msgid "Update all" +msgstr "Оновити все" + #: src/renderer/components/thread/ThreadAgentUpdateDock.tsx msgid "Update available" msgstr "Доступне оновлення" @@ -13289,7 +13303,9 @@ msgid "Update to {updateLabel} for {0} ({env})" msgstr "Оновити до {updateLabel} для {0} ({env})" #. placeholder {0}: agent.version +#. placeholder {0}: update.targetVersion #: src/renderer/views/SettingsOverlay/parts/AcpRegistrySettings.tsx +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx msgid "Update to v{0}" msgstr "Оновити до v{0}" @@ -13315,10 +13331,13 @@ msgid "Updated {0}" msgstr "Оновлено {0}" #: src/renderer/views/SettingsOverlay/parts/AcpRegistrySettings.tsx +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx msgid "Updating" msgstr "Оновлення" +#. placeholder {0}: agent.label #. placeholder {0}: props.agentLabel +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx #: src/renderer/views/SettingsOverlay/parts/SingleAgentSettings/parts/AgentEnvironmentRow.tsx msgid "Updating {0}" msgstr "Оновлення {0}" diff --git a/src/renderer/locales/vi/messages.po b/src/renderer/locales/vi/messages.po index 2d145e51a..2308f1c19 100644 --- a/src/renderer/locales/vi/messages.po +++ b/src/renderer/locales/vi/messages.po @@ -316,9 +316,12 @@ msgstr "{0} mã thông báo" msgid "{0} tokens - {when}" msgstr "{0} tokens - {when}" +#. placeholder {0}: agent.label #. placeholder {0}: agent.name #. placeholder {1}: agent.version +#. placeholder {1}: entry.targetVersion #: src/renderer/views/SettingsOverlay/parts/AcpRegistrySettings.tsx +#: src/renderer/views/SettingsOverlay/parts/useProviderUpdates.ts msgid "{0} updated to v{1}." msgstr "{0} đã cập nhật lên v{1}." @@ -7122,8 +7125,8 @@ msgstr "Nhãn mô hình" #: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx #: src/renderer/views/SettingsOverlay/parts/settingsSearchIndex.ts -msgid "Model order" -msgstr "Thứ tự mô hình" +#~ msgid "Model order" +#~ msgstr "Thứ tự mô hình" #: src/renderer/commands/registry.ts msgid "Model removed from favorites" @@ -9297,7 +9300,9 @@ msgstr "Mức sử dụng nhà cung cấp" msgid "providers" msgstr "nhà cung cấp" +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx #: src/renderer/views/SettingsOverlay/parts/ProfileSettings.tsx +#: src/renderer/views/SettingsOverlay/parts/settingsSearchIndex.ts #: src/renderer/views/SettingsOverlay/parts/UsageSettings.tsx msgid "Providers" msgstr "Nhà cung cấp" @@ -13020,9 +13025,11 @@ msgstr "Không thể cập nhật {0} ({envName})." msgid "Unable to update {0} hooks." msgstr "Không thể cập nhật hook {0}." +#. placeholder {0}: agent.label #. placeholder {0}: agentStatus.label #. placeholder {1}: detail.slice(0, 240) #: src/renderer/components/thread/ThreadAgentUpdateDock.tsx +#: src/renderer/views/SettingsOverlay/parts/useProviderUpdates.ts msgid "Unable to update {0}: {1}" msgstr "Không thể cập nhật {0}: {1}" @@ -13035,6 +13042,7 @@ msgstr "Không thể cập nhật {0}: {detailText}" #. placeholder {0}: agentStatus.label #: src/renderer/components/thread/ThreadAgentUpdateDock.tsx #: src/renderer/views/SettingsOverlay/parts/SingleAgentSettings/SingleAgentSettings.tsx +#: src/renderer/views/SettingsOverlay/parts/useProviderUpdates.ts msgid "Unable to update {0}." msgstr "Không thể cập nhật {0}." @@ -13228,11 +13236,17 @@ msgstr "cập nhật" msgid "Update" msgstr "cập nhật" +#. placeholder {0}: agent.label #. placeholder {0}: props.agentLabel +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx #: src/renderer/views/SettingsOverlay/parts/SingleAgentSettings/parts/AgentEnvironmentRow.tsx msgid "Update {0} to {updateLabel}" msgstr "Cập nhật {0} lên {updateLabel}" +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx +msgid "Update all" +msgstr "Cập nhật tất cả" + #: src/renderer/components/thread/ThreadAgentUpdateDock.tsx msgid "Update available" msgstr "Đã có bản cập nhật" @@ -13289,7 +13303,9 @@ msgid "Update to {updateLabel} for {0} ({env})" msgstr "Cập nhật lên {updateLabel} cho {0} ({env})" #. placeholder {0}: agent.version +#. placeholder {0}: update.targetVersion #: src/renderer/views/SettingsOverlay/parts/AcpRegistrySettings.tsx +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx msgid "Update to v{0}" msgstr "Cập nhật lên v{0}" @@ -13315,10 +13331,13 @@ msgid "Updated {0}" msgstr "Đã cập nhật {0}" #: src/renderer/views/SettingsOverlay/parts/AcpRegistrySettings.tsx +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx msgid "Updating" msgstr "Đang cập nhật" +#. placeholder {0}: agent.label #. placeholder {0}: props.agentLabel +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx #: src/renderer/views/SettingsOverlay/parts/SingleAgentSettings/parts/AgentEnvironmentRow.tsx msgid "Updating {0}" msgstr "Đang cập nhật {0}" diff --git a/src/renderer/locales/zh-CN/messages.po b/src/renderer/locales/zh-CN/messages.po index aaacd5085..cc3c762a3 100644 --- a/src/renderer/locales/zh-CN/messages.po +++ b/src/renderer/locales/zh-CN/messages.po @@ -316,9 +316,12 @@ msgstr "{0} 令牌" msgid "{0} tokens - {when}" msgstr "{0}个token - {when}" +#. placeholder {0}: agent.label #. placeholder {0}: agent.name #. placeholder {1}: agent.version +#. placeholder {1}: entry.targetVersion #: src/renderer/views/SettingsOverlay/parts/AcpRegistrySettings.tsx +#: src/renderer/views/SettingsOverlay/parts/useProviderUpdates.ts msgid "{0} updated to v{1}." msgstr "{0}更新为 v{1}。" @@ -7121,8 +7124,8 @@ msgstr "模型标签" #: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx #: src/renderer/views/SettingsOverlay/parts/settingsSearchIndex.ts -msgid "Model order" -msgstr "模型排序" +#~ msgid "Model order" +#~ msgstr "模型排序" #: src/renderer/commands/registry.ts msgid "Model removed from favorites" @@ -9296,7 +9299,9 @@ msgstr "提供商用量" msgid "providers" msgstr "提供商" +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx #: src/renderer/views/SettingsOverlay/parts/ProfileSettings.tsx +#: src/renderer/views/SettingsOverlay/parts/settingsSearchIndex.ts #: src/renderer/views/SettingsOverlay/parts/UsageSettings.tsx msgid "Providers" msgstr "提供商" @@ -13019,9 +13024,11 @@ msgstr "无法更新{0}({envName})。" msgid "Unable to update {0} hooks." msgstr "无法更新{0}挂钩。" +#. placeholder {0}: agent.label #. placeholder {0}: agentStatus.label #. placeholder {1}: detail.slice(0, 240) #: src/renderer/components/thread/ThreadAgentUpdateDock.tsx +#: src/renderer/views/SettingsOverlay/parts/useProviderUpdates.ts msgid "Unable to update {0}: {1}" msgstr "无法更新{0}:{1}" @@ -13034,6 +13041,7 @@ msgstr "无法更新{0}:{detailText}" #. placeholder {0}: agentStatus.label #: src/renderer/components/thread/ThreadAgentUpdateDock.tsx #: src/renderer/views/SettingsOverlay/parts/SingleAgentSettings/SingleAgentSettings.tsx +#: src/renderer/views/SettingsOverlay/parts/useProviderUpdates.ts msgid "Unable to update {0}." msgstr "无法更新{0}。" @@ -13227,11 +13235,17 @@ msgstr "更新" msgid "Update" msgstr "更新" +#. placeholder {0}: agent.label #. placeholder {0}: props.agentLabel +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx #: src/renderer/views/SettingsOverlay/parts/SingleAgentSettings/parts/AgentEnvironmentRow.tsx msgid "Update {0} to {updateLabel}" msgstr "将{0}更新为{updateLabel}" +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx +msgid "Update all" +msgstr "全部更新" + #: src/renderer/components/thread/ThreadAgentUpdateDock.tsx msgid "Update available" msgstr "可用更新" @@ -13288,7 +13302,9 @@ msgid "Update to {updateLabel} for {0} ({env})" msgstr "将{0}({env})更新到{updateLabel}" #. placeholder {0}: agent.version +#. placeholder {0}: update.targetVersion #: src/renderer/views/SettingsOverlay/parts/AcpRegistrySettings.tsx +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx msgid "Update to v{0}" msgstr "更新到 v{0}" @@ -13314,10 +13330,13 @@ msgid "Updated {0}" msgstr "更新了{0}" #: src/renderer/views/SettingsOverlay/parts/AcpRegistrySettings.tsx +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx msgid "Updating" msgstr "更新中" +#. placeholder {0}: agent.label #. placeholder {0}: props.agentLabel +#: src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx #: src/renderer/views/SettingsOverlay/parts/SingleAgentSettings/parts/AgentEnvironmentRow.tsx msgid "Updating {0}" msgstr "正在更新{0}" diff --git a/src/renderer/views/SettingsOverlay/parts/ModelOrderSection.test.tsx b/src/renderer/views/SettingsOverlay/parts/ModelOrderSection.test.tsx new file mode 100644 index 000000000..9be136167 --- /dev/null +++ b/src/renderer/views/SettingsOverlay/parts/ModelOrderSection.test.tsx @@ -0,0 +1,375 @@ +import type { ReactNode } from "react"; +import { act, fireEvent, screen, waitFor } from "@testing-library/react"; +import { beforeEach, describe, expect, it, vi } from "vitest"; +import type { + AcpRegistryListResult, + AgentStatus, + AgentStatusesResponse, + InstalledAcpRegistryAgent, + Project, +} from "@/shared/contracts"; +import { renderWithI18n as render } from "@/renderer/testUtils/i18n"; + +const statusesState = { + agentStatuses: [] as AgentStatus[], + wslAgentStatuses: [] as AgentStatus[], +}; + +const settingsState = { + providerOrder: [] as string[], + setProviderOrder: vi.fn<(order: string[]) => void>(), + acpRegistryInstalledAgents: {} as Record, + syncAcpRegistryInstalledAgents: vi.fn<(installed: InstalledAcpRegistryAgent[]) => void>(), +}; + +const appState = { projects: [] as Project[] }; + +const bridge = { + getLatestAgentVersion: + vi.fn<(payload: { agentKind: string }) => Promise<{ source: string; version?: string }>>(), + updateAgentBinary: vi.fn< + (payload: { agentKind: string; envKind: string; wslDistro?: string }) => Promise<{ + ok: boolean; + output?: string; + }> + >(), + updateAcpRegistryAgent: + vi.fn<(payload: { agentId: string }) => Promise<{ installed: InstalledAcpRegistryAgent[] }>>(), + refreshAgentStatuses: vi.fn<() => Promise>(), + listAcpRegistry: vi.fn<() => Promise>(), +}; + +const toastMock = vi.hoisted(() => ({ + success: vi.fn<(message: string) => void>(), + danger: vi.fn<(message: string) => void>(), +})); + +vi.mock("@/renderer/state/agentStatusesStore", () => ({ + useAgentStatusesStore: (selector: (state: typeof statusesState) => unknown) => + selector(statusesState), +})); + +vi.mock("@/renderer/state/sharedSettingsStore", () => ({ + useSharedSettings: (selector: (state: typeof settingsState) => unknown) => + selector(settingsState), +})); + +vi.mock("@/renderer/state/appStore", () => ({ + useAppStore: Object.assign( + (selector: (state: typeof appState) => unknown) => selector(appState), + { + getState: () => appState, + }, + ), +})); + +vi.mock("@/renderer/bridge", () => ({ + readBridge: () => bridge, +})); + +vi.mock("@heroui/react", () => ({ + toast: toastMock, + Button: (props: { + children?: ReactNode; + "aria-label"?: string; + isPending?: boolean; + isDisabled?: boolean; + onPress?: () => void; + }) => ( + + ), +})); + +vi.mock("@dnd-kit/react", () => ({ + DragDropProvider: (props: { children?: ReactNode }) =>
{props.children}
, +})); + +vi.mock("@dnd-kit/react/sortable", () => ({ + isSortable: () => false, + useSortable: () => ({ ref: () => {}, handleRef: () => {}, isDragging: false }), +})); + +vi.mock("@/renderer/components/common", () => ({ + PixelLoader: () => , +})); + +vi.mock("@/renderer/components/providers/ProviderIcon", () => ({ + ProviderIcon: (props: { fallbackLabel?: string }) => {props.fallbackLabel}, +})); + +import { ModelOrderSection } from "./ModelOrderSection"; + +function makeStatus(overrides: Partial & { kind: string }): AgentStatus { + return { + label: overrides.kind, + installed: true, + envKind: "posix", + capabilities: {}, + ...overrides, + } as AgentStatus; +} + +describe("ModelOrderSection provider updates", () => { + beforeEach(() => { + statusesState.agentStatuses = []; + statusesState.wslAgentStatuses = []; + settingsState.providerOrder = []; + settingsState.acpRegistryInstalledAgents = {}; + toastMock.success.mockReset(); + toastMock.danger.mockReset(); + bridge.getLatestAgentVersion.mockReset().mockResolvedValue({ source: "unknown" }); + bridge.updateAgentBinary.mockReset().mockResolvedValue({ ok: true }); + bridge.updateAcpRegistryAgent.mockReset().mockResolvedValue({ installed: [] }); + bridge.refreshAgentStatuses + .mockReset() + .mockResolvedValue({ windows: [], wsl: [] } as unknown as AgentStatusesResponse); + bridge.listAcpRegistry.mockReset().mockResolvedValue({ version: "1", agents: [] }); + }); + + it("shows the installed version of every provider", async () => { + statusesState.agentStatuses = [ + makeStatus({ kind: "claude", label: "Claude Code", version: "1.2.3" }), + makeStatus({ kind: "codex", label: "Codex" }), + ]; + + render(); + + expect(await screen.findByText("v1.2.3")).toBeTruthy(); + expect(screen.getByText("—")).toBeTruthy(); + }); + + it("breaks the version out per environment only when they disagree", async () => { + statusesState.agentStatuses = [ + makeStatus({ kind: "claude", label: "Claude Code", version: "1.2.3", envKind: "windows" }), + makeStatus({ kind: "codex", label: "Codex", version: "1.0.0", envKind: "windows" }), + ]; + statusesState.wslAgentStatuses = [ + makeStatus({ + kind: "claude", + label: "Claude Code", + version: "1.1.0", + envKind: "wsl", + envDistro: "Ubuntu", + }), + makeStatus({ + kind: "codex", + label: "Codex", + version: "1.0.0", + envKind: "wsl", + envDistro: "Ubuntu", + }), + ]; + + render(); + + expect(await screen.findByText("Windows v1.2.3 · WSL (Ubuntu) v1.1.0")).toBeTruthy(); + expect(screen.getByText("v1.0.0")).toBeTruthy(); + }); + + it("offers a per-provider update when the published version is newer", async () => { + statusesState.agentStatuses = [ + makeStatus({ kind: "claude", label: "Claude Code", version: "1.2.3" }), + ]; + bridge.getLatestAgentVersion.mockResolvedValue({ source: "npm", version: "1.3.0" }); + + render(); + + fireEvent.click(await screen.findByRole("button", { name: "Update Claude Code to v1.3.0" })); + + await waitFor(() => + expect(bridge.updateAgentBinary).toHaveBeenCalledWith({ + agentKind: "claude", + envKind: "posix", + }), + ); + await waitFor(() => + expect(toastMock.success).toHaveBeenCalledWith("Claude Code updated to v1.3.0."), + ); + }); + + it("hides the update control while the provider is current", async () => { + statusesState.agentStatuses = [ + makeStatus({ kind: "claude", label: "Claude Code", version: "1.3.0" }), + ]; + bridge.getLatestAgentVersion.mockResolvedValue({ source: "npm", version: "1.3.0" }); + + render(); + + await waitFor(() => expect(bridge.getLatestAgentVersion).toHaveBeenCalled()); + expect(screen.queryByRole("button", { name: /^Update/u })).toBeNull(); + expect(screen.queryByRole("button", { name: "Update all" })).toBeNull(); + }); + + it("updates every outdated provider from the Update all control", async () => { + statusesState.agentStatuses = [ + makeStatus({ kind: "claude", label: "Claude Code", version: "1.2.3" }), + makeStatus({ kind: "codex", label: "Codex", version: "0.9.0" }), + makeStatus({ kind: "gemini", label: "Gemini", version: "2.0.0" }), + ]; + bridge.getLatestAgentVersion.mockImplementation(({ agentKind }) => + Promise.resolve( + agentKind === "gemini" + ? { source: "npm", version: "2.0.0" } + : { source: "npm", version: agentKind === "claude" ? "1.3.0" : "1.0.0" }, + ), + ); + + render(); + + fireEvent.click(await screen.findByRole("button", { name: "Update all" })); + + await waitFor(() => expect(bridge.updateAgentBinary).toHaveBeenCalledTimes(2)); + expect(bridge.updateAgentBinary.mock.calls.map(([payload]) => payload.agentKind)).toEqual([ + "claude", + "codex", + ]); + }); + + it("updates each outdated environment of a provider once", async () => { + statusesState.agentStatuses = [ + makeStatus({ kind: "claude", label: "Claude Code", version: "1.2.3", envKind: "windows" }), + ]; + statusesState.wslAgentStatuses = [ + makeStatus({ + kind: "claude", + label: "Claude Code", + version: "1.1.0", + envKind: "wsl", + envDistro: "Ubuntu", + }), + ]; + bridge.getLatestAgentVersion.mockResolvedValue({ source: "npm", version: "1.3.0" }); + + render(); + + fireEvent.click(await screen.findByRole("button", { name: "Update all" })); + + await waitFor(() => expect(bridge.updateAgentBinary).toHaveBeenCalledTimes(2)); + expect(bridge.updateAgentBinary.mock.calls.map(([payload]) => payload)).toEqual([ + { agentKind: "claude", envKind: "windows" }, + { agentKind: "claude", envKind: "wsl", wslDistro: "Ubuntu" }, + ]); + }); + + it("reports a failed update without claiming success", async () => { + statusesState.agentStatuses = [ + makeStatus({ kind: "claude", label: "Claude Code", version: "1.2.3" }), + ]; + bridge.getLatestAgentVersion.mockResolvedValue({ source: "npm", version: "1.3.0" }); + bridge.updateAgentBinary.mockResolvedValue({ ok: false, output: "npm ERR! EACCES" }); + + render(); + + fireEvent.click(await screen.findByRole("button", { name: "Update Claude Code to v1.3.0" })); + + await waitFor(() => + expect(toastMock.danger).toHaveBeenCalledWith( + "Unable to update Claude Code: npm ERR! EACCES", + ), + ); + expect(toastMock.success).not.toHaveBeenCalled(); + }); + + it("still updates the remaining environments when one environment fails", async () => { + statusesState.agentStatuses = [ + makeStatus({ kind: "claude", label: "Claude Code", version: "1.2.3", envKind: "windows" }), + ]; + statusesState.wslAgentStatuses = [ + makeStatus({ + kind: "claude", + label: "Claude Code", + version: "1.1.0", + envKind: "wsl", + envDistro: "Ubuntu", + }), + ]; + bridge.getLatestAgentVersion.mockResolvedValue({ source: "npm", version: "1.3.0" }); + bridge.updateAgentBinary.mockImplementation(({ envKind }) => + Promise.resolve( + envKind === "windows" ? { ok: true } : { ok: false, output: "npm ERR! EACCES" }, + ), + ); + + render(); + + fireEvent.click(await screen.findByRole("button", { name: "Update Claude Code to v1.3.0" })); + + await waitFor(() => expect(bridge.updateAgentBinary).toHaveBeenCalledTimes(2)); + expect(bridge.updateAgentBinary.mock.calls.map(([payload]) => payload)).toEqual([ + { agentKind: "claude", envKind: "windows" }, + { agentKind: "claude", envKind: "wsl", wslDistro: "Ubuntu" }, + ]); + expect(toastMock.danger).toHaveBeenCalledWith("Unable to update Claude Code: npm ERR! EACCES"); + expect(toastMock.success).not.toHaveBeenCalled(); + }); + + it("disables per-provider updates while an update-all run is active", async () => { + statusesState.agentStatuses = [ + makeStatus({ kind: "claude", label: "Claude Code", version: "1.2.3" }), + makeStatus({ kind: "codex", label: "Codex", version: "0.9.0" }), + ]; + let resolveCodexProbe!: (value: { source: string; version?: string }) => void; + bridge.getLatestAgentVersion.mockImplementation(({ agentKind }) => + agentKind === "claude" + ? Promise.resolve({ source: "npm", version: "1.3.0" }) + : new Promise((resolve) => { + resolveCodexProbe = resolve; + }), + ); + let resolveClaudeUpdate!: (value: { ok: boolean; output?: string }) => void; + bridge.updateAgentBinary.mockImplementation( + () => + new Promise((resolve) => { + resolveClaudeUpdate = resolve; + }), + ); + + render(); + fireEvent.click(await screen.findByRole("button", { name: "Update all" })); + + await act(async () => { + resolveCodexProbe({ source: "npm", version: "1.0.0" }); + }); + const codexButton = screen.getByRole("button", { + name: "Update Codex to v1.0.0", + }) as HTMLButtonElement; + expect(codexButton.disabled).toBe(true); + + await act(async () => { + resolveClaudeUpdate({ ok: true }); + }); + await waitFor(() => expect(codexButton.disabled).toBe(false)); + await waitFor(() => + expect(toastMock.success).toHaveBeenCalledWith("Claude Code updated to v1.3.0."), + ); + }); + + it("routes ACP registry instances through the registry update", async () => { + statusesState.agentStatuses = [ + makeStatus({ kind: "acp-generic:pi-acp", label: "Pi", version: "0.1.0" }), + ]; + settingsState.acpRegistryInstalledAgents = { + "pi-acp": { id: "pi-acp", version: "0.1.0" } as InstalledAcpRegistryAgent, + }; + bridge.listAcpRegistry.mockResolvedValue({ + version: "1", + agents: [{ id: "pi-acp", version: "0.2.0" }], + } as unknown as AcpRegistryListResult); + + render(); + + fireEvent.click(await screen.findByRole("button", { name: "Update Pi to v0.2.0" })); + + await waitFor(() => + expect(bridge.updateAcpRegistryAgent).toHaveBeenCalledWith({ agentId: "pi-acp" }), + ); + expect(bridge.updateAgentBinary).not.toHaveBeenCalled(); + }); +}); diff --git a/src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx b/src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx index ec20be70d..84a299b1d 100644 --- a/src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx +++ b/src/renderer/views/SettingsOverlay/parts/ModelOrderSection.tsx @@ -1,13 +1,16 @@ import { DragDropProvider, type DragEndEvent } from "@dnd-kit/react"; import { isSortable, useSortable } from "@dnd-kit/react/sortable"; -import { GripVertical, RotateCcw } from "lucide-react"; +import { Button } from "@heroui/react"; +import { ArrowUpCircle, GripVertical, RotateCcw } from "lucide-react"; import { Trans, useLingui } from "@lingui/react/macro"; import type { AgentStatus } from "@/shared/contracts"; import { useSharedSettings } from "@/renderer/state/sharedSettingsStore"; import { useAgentStatusesStore } from "@/renderer/state/agentStatusesStore"; import { getSettingsInstalledAgents } from "@/shared/agentStatus"; +import { PixelLoader } from "@/renderer/components/common"; import { ProviderIcon } from "@/renderer/components/providers/ProviderIcon"; import { getProviderModelPickerRank } from "@/renderer/components/providers/providerManifest"; +import { useProviderUpdates, type ProviderUpdateEntry } from "./useProviderUpdates"; function resolveDisplayedKinds( installed: readonly AgentStatus[], @@ -37,8 +40,14 @@ function resolveDisplayedKinds( return ordered; } -function SortableProviderRow(props: { agent: AgentStatus; index: number }) { - const { agent, index } = props; +function SortableProviderRow(props: { + agent: AgentStatus; + index: number; + update: ProviderUpdateEntry; + isBulkUpdating: boolean; + onUpdate: (kind: string) => void; +}) { + const { agent, index, update, isBulkUpdating, onUpdate } = props; const { t } = useLingui(); const { ref, handleRef, isDragging } = useSortable({ id: `provider-order:${agent.kind}`, @@ -48,6 +57,7 @@ function SortableProviderRow(props: { agent: AgentStatus; index: number }) { group: "provider-order", data: { kind: agent.kind }, }); + const updateLabel = update.targetVersion ? `v${update.targetVersion}` : ""; return (
{agent.label} + + {update.environments.length > 0 + ? update.environments + .map((env) => `${env.label} ${env.version ? `v${env.version}` : "—"}`.trim()) + .join(" · ") + : update.installedVersion + ? `v${update.installedVersion}` + : "—"} + + {update.isPending ? ( +
+ +
+ ) : update.targetVersion ? ( + + ) : null}
); } @@ -90,6 +130,7 @@ export function ModelOrderSection() { .filter((a): a is AgentStatus => a !== undefined); const isCustomized = providerOrder.length > 0; + const updates = useProviderUpdates(orderedAgents); function handleDragEnd(event: DragEndEvent) { if (event.canceled) return; @@ -115,7 +156,7 @@ export function ModelOrderSection() { >

- Model order + Providers

{isCustomized ? ( ) : null} + {updates.outdatedKinds.length > 0 ? ( + + ) : null}

Drag to reorder how providers appear in the model picker. @@ -134,7 +191,14 @@ export function ModelOrderSection() {

{orderedAgents.map((agent, index) => ( - + ))}
diff --git a/src/renderer/views/SettingsOverlay/parts/settingsSearchIndex.ts b/src/renderer/views/SettingsOverlay/parts/settingsSearchIndex.ts index 0ea085c99..1d1a092d4 100644 --- a/src/renderer/views/SettingsOverlay/parts/settingsSearchIndex.ts +++ b/src/renderer/views/SettingsOverlay/parts/settingsSearchIndex.ts @@ -582,9 +582,10 @@ export const SETTINGS_SEARCH_INDEX: readonly SettingsSearchEntry[] = [ { section: "agentsGeneral", anchor: "agentsGeneral.modelOrder", - title: msg`Model order`, + title: msg`Providers`, description: msg`Drag to reorder how providers appear in the model picker.`, - keywords: "reorder rearrange sort providers drag model picker sequence position", + keywords: + "reorder rearrange sort providers drag model picker sequence position model order version update upgrade outdated latest agents", conditional: true, }, // Dev (only in dev builds) diff --git a/src/renderer/views/SettingsOverlay/parts/useProviderUpdates.ts b/src/renderer/views/SettingsOverlay/parts/useProviderUpdates.ts new file mode 100644 index 000000000..5fc50b08b --- /dev/null +++ b/src/renderer/views/SettingsOverlay/parts/useProviderUpdates.ts @@ -0,0 +1,309 @@ +import { useEffect, useState } from "react"; +import { toast } from "@heroui/react"; +import { useLingui } from "@lingui/react/macro"; +import { extractAcpGenericInstanceId, type AgentStatus } from "@/shared/contracts"; +import { isNewerVersion } from "@/shared/agents/updateResolver"; +import { readBridge } from "@/renderer/bridge"; +import { useAgentStatusesStore } from "@/renderer/state/agentStatusesStore"; +import { useSharedSettings } from "@/renderer/state/sharedSettingsStore"; +import { + currentWslDistros, + envLabelForStatus, + scopeEnvForStatus, + statusUpdateScope, +} from "@/renderer/utils/acpRegistryAuth"; + +export interface ProviderEnvironmentVersion { + /** Environment name, e.g. `Windows` or `WSL (Ubuntu)`. */ + label: string; + version: string | undefined; +} + +export interface ProviderUpdateEntry { + /** Newest version detected across the provider's environments. */ + installedVersion: string | undefined; + /** + * Per-environment versions, native first — only populated when the provider + * is installed in several environments that disagree on the version, so the + * common single-environment case stays a bare version string. + */ + environments: readonly ProviderEnvironmentVersion[]; + /** Version to update to; `undefined` when the provider is current. */ + targetVersion: string | undefined; + /** An update is running for this provider (all of its environments). */ + isPending: boolean; +} + +export interface ProviderUpdatesModel { + entryFor: (kind: string) => ProviderUpdateEntry; + /** Kinds with an available update, in the order they were passed in. */ + outdatedKinds: readonly string[]; + isUpdatingAll: boolean; + updateKind: (kind: string) => void; + updateAll: () => void; +} + +const EMPTY_ENTRY: ProviderUpdateEntry = { + installedVersion: undefined, + environments: [], + targetVersion: undefined, + isPending: false, +}; + +function newerOf(left: string | undefined, right: string | undefined): string | undefined { + if (!left) return right; + if (!right) return left; + return isNewerVersion(right, left) ? right : left; +} + +function splitKinds(kindsKey: string): string[] { + return kindsKey ? kindsKey.split("\0") : []; +} + +/** + * Version and update state for a list of provider kinds, so the agents list can + * offer per-provider and "update all" upgrades in one place instead of one + * settings page per provider. + * + * Both update channels of the per-agent settings page are covered: ACP registry + * instances update through the registry, every other provider updates its + * binary once per environment it is installed in (Windows and each WSL distro). + */ +export function useProviderUpdates(agents: readonly AgentStatus[]): ProviderUpdatesModel { + const { t } = useLingui(); + const agentStatuses = useAgentStatusesStore((s) => s.agentStatuses); + const wslAgentStatuses = useAgentStatusesStore((s) => s.wslAgentStatuses); + const registryInstalled = useSharedSettings((s) => s.acpRegistryInstalledAgents); + const syncInstalledAgents = useSharedSettings((s) => s.syncAcpRegistryInstalledAgents); + const [latestByKind, setLatestByKind] = useState>>({}); + const [registryLatestById, setRegistryLatestById] = useState>>( + {}, + ); + const [pendingKinds, setPendingKinds] = useState>(() => new Set()); + const [isUpdatingAll, setIsUpdatingAll] = useState(false); + + const kindsKey = agents.map((agent) => agent.kind).join("\0"); + const kinds = splitKinds(kindsKey); + const hasRegistryKinds = kinds.some((kind) => extractAcpGenericInstanceId(kind) !== undefined); + + // One upstream probe per binary-channel kind. The supervisor caches latest + // versions for 30 minutes, so reopening the page does not re-hit registries. + useEffect(() => { + const probeKinds = splitKinds(kindsKey).filter( + (kind) => extractAcpGenericInstanceId(kind) === undefined, + ); + if (probeKinds.length === 0) return; + let cancelled = false; + for (const kind of probeKinds) { + readBridge() + .getLatestAgentVersion({ agentKind: kind }) + .then((result) => { + const version = result.version; + if (cancelled || !version) return; + setLatestByKind((current) => + current[kind] === version ? current : { ...current, [kind]: version }, + ); + }) + .catch((error) => { + console.warn( + `[useProviderUpdates] getLatestAgentVersion(${kind}) failed:`, + error instanceof Error ? error.message : error, + ); + }); + } + return () => { + cancelled = true; + }; + }, [kindsKey]); + + useEffect(() => { + if (!hasRegistryKinds) return; + let cancelled = false; + readBridge() + .listAcpRegistry() + .then((result) => { + if (cancelled) return; + setRegistryLatestById( + Object.fromEntries(result.agents.map((entry) => [entry.id, entry.version])), + ); + }) + .catch((error) => { + console.warn( + "[useProviderUpdates] listAcpRegistry failed:", + error instanceof Error ? error.message : error, + ); + }); + return () => { + cancelled = true; + }; + }, [hasRegistryKinds]); + + function installedStatusesFor(kind: string): AgentStatus[] { + return [...agentStatuses, ...wslAgentStatuses].filter( + (status) => status.kind === kind && status.installed, + ); + } + + function newestVersionOf(statuses: readonly AgentStatus[]): string | undefined { + return statuses.reduce( + (newest, status) => newerOf(newest, status.version), + undefined, + ); + } + + /** + * Environments of a binary-channel provider that are behind. A peer + * environment counts as a target too: with no upstream version available, a + * WSL install lagging the Windows one is still a known-good upgrade. + */ + function outdatedStatusesFor(kind: string): AgentStatus[] { + const statuses = installedStatusesFor(kind); + const target = newerOf(latestByKind[kind], newestVersionOf(statuses)); + if (!target) return []; + return statuses.filter( + (status) => status.version !== undefined && isNewerVersion(target, status.version), + ); + } + + /** + * Per-environment breakdown, native first — empty unless the environments + * disagree, so a provider that is consistent everywhere renders as one + * version instead of repeating it per environment. + */ + function environmentsOf(statuses: readonly AgentStatus[]): ProviderEnvironmentVersion[] { + if (new Set(statuses.map((status) => status.version)).size < 2) return []; + const ordered = [ + ...statuses.filter((status) => status.envKind !== "wsl"), + ...statuses.filter((status) => status.envKind === "wsl"), + ]; + return ordered.map((status) => ({ + label: envLabelForStatus(status), + version: status.version, + })); + } + + function entryFor(kind: string): ProviderUpdateEntry { + const statuses = installedStatusesFor(kind); + if (statuses.length === 0) return EMPTY_ENTRY; + const isPending = pendingKinds.has(kind); + const registryId = extractAcpGenericInstanceId(kind); + if (registryId !== undefined) { + const installedVersion = registryInstalled[registryId]?.version ?? newestVersionOf(statuses); + const latest = registryLatestById[registryId]; + const isOutdated = + latest !== undefined && + installedVersion !== undefined && + isNewerVersion(latest, installedVersion); + return { + installedVersion, + // A registry instance is installed once, under the app's own base dir. + environments: [], + targetVersion: isOutdated ? latest : undefined, + isPending, + }; + } + const installedVersion = newestVersionOf(statuses); + const hasOutdatedEnv = outdatedStatusesFor(kind).length > 0; + return { + installedVersion, + environments: environmentsOf(statuses), + targetVersion: hasOutdatedEnv ? newerOf(latestByKind[kind], installedVersion) : undefined, + isPending, + }; + } + + const outdatedKinds = kinds.filter((kind) => entryFor(kind).targetVersion !== undefined); + + async function runBinaryUpdate(agent: AgentStatus): Promise { + // Attempt every outdated environment even when one fails, so a flaky + // Windows or WSL install never leaves the others silently stale; the + // first failure is surfaced after the loop. + let failure: Error | undefined; + for (const status of outdatedStatusesFor(agent.kind)) { + const scope = statusUpdateScope(status); + try { + const result = await readBridge().updateAgentBinary({ + agentKind: agent.kind, + envKind: scope.envKind, + ...(scope.wslDistro ? { wslDistro: scope.wslDistro } : {}), + }); + if (!result.ok) { + const detail = result.output?.trim(); + throw new Error( + detail + ? t`Unable to update ${agent.label}: ${detail.slice(0, 240)}` + : t`Unable to update ${agent.label}.`, + ); + } + await readBridge().refreshAgentStatuses(currentWslDistros(), { + agentKinds: [agent.kind], + envs: [scopeEnvForStatus(status)], + }); + } catch (error) { + failure ??= error instanceof Error ? error : new Error(t`Unable to update ${agent.label}.`); + } + } + if (failure) throw failure; + } + + async function runUpdate(agent: AgentStatus): Promise { + const entry = entryFor(agent.kind); + if (!entry.targetVersion) return; + const registryId = extractAcpGenericInstanceId(agent.kind); + try { + if (registryId === undefined) { + await runBinaryUpdate(agent); + } else { + const result = await readBridge().updateAcpRegistryAgent({ agentId: registryId }); + syncInstalledAgents(result.installed); + await readBridge().refreshAgentStatuses(currentWslDistros(), { agentKinds: [agent.kind] }); + } + toast.success(t`${agent.label} updated to v${entry.targetVersion}.`); + } catch (error) { + toast.danger(error instanceof Error ? error.message : t`Unable to update ${agent.label}.`); + } + } + + function withPending(pending: readonly string[], run: () => Promise): void { + setPendingKinds((current) => { + const next = new Set(current); + for (const kind of pending) next.add(kind); + return next; + }); + void run().finally(() => { + setPendingKinds((current) => { + const next = new Set(current); + for (const kind of pending) next.delete(kind); + return next; + }); + }); + } + + function updateKind(kind: string): void { + const agent = agents.find((candidate) => candidate.kind === kind); + if (!agent || pendingKinds.has(kind)) return; + withPending([kind], () => runUpdate(agent)); + } + + function updateAll(): void { + const targets = agents.filter( + (agent) => outdatedKinds.includes(agent.kind) && !pendingKinds.has(agent.kind), + ); + if (targets.length === 0) return; + setIsUpdatingAll(true); + withPending( + targets.map((agent) => agent.kind), + async () => { + try { + // Sequential: concurrent installs contend for the same package + // manager prefix (and the same WSL distro) and fail unpredictably. + for (const agent of targets) await runUpdate(agent); + } finally { + setIsUpdatingAll(false); + } + }, + ); + } + + return { entryFor, outdatedKinds, isUpdatingAll, updateKind, updateAll }; +}