Script 'mail_helper' called by obssrc
Hello community,

here is the log from the commit of package kargo-cli for openSUSE:Factory 
checked in at 2026-04-22 17:00:15
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Comparing /work/SRC/openSUSE:Factory/kargo-cli (Old)
 and      /work/SRC/openSUSE:Factory/.kargo-cli.new.11940 (New)
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++

Package is "kargo-cli"

Wed Apr 22 17:00:15 2026 rev:49 rq:1348685 version:1.10.1

Changes:
--------
--- /work/SRC/openSUSE:Factory/kargo-cli/kargo-cli.changes      2026-04-18 
21:39:40.341681711 +0200
+++ /work/SRC/openSUSE:Factory/.kargo-cli.new.11940/kargo-cli.changes   
2026-04-22 17:01:23.540453303 +0200
@@ -1,0 +2,7 @@
+Wed Apr 22 05:59:30 UTC 2026 - Johannes Kastl 
<[email protected]>
+
+- Update to version 1.10.1:
+  * chore(backport release-1.10): fix: cli and server to match
+    openapi spec (#6136)
+
+-------------------------------------------------------------------

Old:
----
  kargo-cli-1.10.0.obscpio

New:
----
  kargo-cli-1.10.1.obscpio

++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++

Other differences:
------------------
++++++ kargo-cli.spec ++++++
--- /var/tmp/diff_new_pack.kbRpZ7/_old  2026-04-22 17:01:24.880508599 +0200
+++ /var/tmp/diff_new_pack.kbRpZ7/_new  2026-04-22 17:01:24.888508930 +0200
@@ -19,7 +19,7 @@
 %define executable_name kargo
 
 Name:           kargo-cli
-Version:        1.10.0
+Version:        1.10.1
 Release:        0
 Summary:        CLI for the Kubernetes Application lifecycle orchestration
 License:        Apache-2.0

++++++ _service ++++++
--- /var/tmp/diff_new_pack.kbRpZ7/_old  2026-04-22 17:01:24.956511736 +0200
+++ /var/tmp/diff_new_pack.kbRpZ7/_new  2026-04-22 17:01:24.960511901 +0200
@@ -3,7 +3,7 @@
     <param name="url">https://github.com/akuity/kargo</param>
     <param name="scm">git</param>
     <param name="exclude">.git</param>
-    <param name="revision">v1.10.0</param>
+    <param name="revision">v1.10.1</param>
     <param name="versionformat">@PARENT_TAG@</param>
     <param name="versionrewrite-pattern">v(.*)</param>
     <param name="changesgenerate">enable</param>

++++++ _servicedata ++++++
--- /var/tmp/diff_new_pack.kbRpZ7/_old  2026-04-22 17:01:24.996513386 +0200
+++ /var/tmp/diff_new_pack.kbRpZ7/_new  2026-04-22 17:01:25.004513717 +0200
@@ -1,6 +1,6 @@
 <servicedata>
 <service name="tar_scm">
                 <param name="url">https://github.com/akuity/kargo</param>
-              <param 
name="changesrevision">f5477e786aa4904425e9bbd547c7c05527b76237</param></service></servicedata>
+              <param 
name="changesrevision">6063d52de99ed5c26e5a01856ffe67434f8a9f23</param></service></servicedata>
 (No newline at EOF)
 

++++++ kargo-cli-1.10.0.obscpio -> kargo-cli-1.10.1.obscpio ++++++
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/kargo-cli-1.10.0/charts/kargo/templates/api/role-bindings.yaml 
new/kargo-cli-1.10.1/charts/kargo/templates/api/role-bindings.yaml
--- old/kargo-cli-1.10.0/charts/kargo/templates/api/role-bindings.yaml  
2026-04-16 22:35:17.000000000 +0200
+++ new/kargo-cli-1.10.1/charts/kargo/templates/api/role-bindings.yaml  
2026-04-21 23:14:06.000000000 +0200
@@ -3,6 +3,7 @@
 kind: RoleBinding
 metadata:
   name: kargo-api
+  namespace: {{ .Release.Namespace }}
   labels:
     {{- include "kargo.labels" . | nindent 4 }}
 roleRef:
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/kargo-cli-1.10.0/charts/kargo/templates/api/roles.yaml 
new/kargo-cli-1.10.1/charts/kargo/templates/api/roles.yaml
--- old/kargo-cli-1.10.0/charts/kargo/templates/api/roles.yaml  2026-04-16 
22:35:17.000000000 +0200
+++ new/kargo-cli-1.10.1/charts/kargo/templates/api/roles.yaml  2026-04-21 
23:14:06.000000000 +0200
@@ -3,6 +3,7 @@
 kind: Role
 metadata:
   name: kargo-api
+  namespace: {{ .Release.Namespace }}
   labels:
     {{- include "kargo.labels" . | nindent 4 }}
 rules:
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/kargo-cli-1.10.0/charts/kargo/templates/users/role-bindings.yaml 
new/kargo-cli-1.10.1/charts/kargo/templates/users/role-bindings.yaml
--- old/kargo-cli-1.10.0/charts/kargo/templates/users/role-bindings.yaml        
2026-04-16 22:35:17.000000000 +0200
+++ new/kargo-cli-1.10.1/charts/kargo/templates/users/role-bindings.yaml        
2026-04-21 23:14:06.000000000 +0200
@@ -2,6 +2,7 @@
 kind: RoleBinding
 metadata:
   name: kargo-admin
+  namespace: {{ .Release.Namespace }}
   labels:
     {{- include "kargo.labels" . | nindent 4 }}
 roleRef:
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/kargo-cli-1.10.0/charts/kargo/templates/users/roles.yaml 
new/kargo-cli-1.10.1/charts/kargo/templates/users/roles.yaml
--- old/kargo-cli-1.10.0/charts/kargo/templates/users/roles.yaml        
2026-04-16 22:35:17.000000000 +0200
+++ new/kargo-cli-1.10.1/charts/kargo/templates/users/roles.yaml        
2026-04-21 23:14:06.000000000 +0200
@@ -2,6 +2,7 @@
 kind: Role
 metadata:
   name: kargo-admin
+  namespace: {{ .Release.Namespace }}
   labels:
     {{- include "kargo.labels" . | nindent 4 }}
 rules:
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/kargo-cli-1.10.0/docs/docs/80-release-notes/100-deprecations.md 
new/kargo-cli-1.10.1/docs/docs/80-release-notes/100-deprecations.md
--- old/kargo-cli-1.10.0/docs/docs/80-release-notes/100-deprecations.md 
2026-04-16 22:35:17.000000000 +0200
+++ new/kargo-cli-1.10.1/docs/docs/80-release-notes/100-deprecations.md 
2026-04-21 23:14:06.000000000 +0200
@@ -16,11 +16,15 @@
 
 | Feature | Deprecated In | Removed In | Replacement/Notes |
 |---------|---------------|------------|-------------------|
+| `git-commit` step `author` field | [v1.10.0](./89-v1.10.0.md) | Scheduled 
for v1.12.0 | Configure authorship and signing in the `git-clone` step or via 
`ClusterConfig`. See [git-commit 
docs](https://docs.kargo.io/user-guide/reference-docs/promotion-steps/git-commit).
 |
+| `git-push` default integration policy (`AlwaysRebase`) | 
[v1.10.0](./89-v1.10.0.md) | Default changes in v1.12.0 | The default 
`git-push` push integration policy will change from `AlwaysRebase` to 
`RebaseOrMerge` in v1.12.0. Set 
[`controller.gitClient.pushIntegrationPolicy`](https://docs.kargo.io/operator-guide/advanced-installation/common-configurations#push-integration-policy)
 explicitly if you rely on unconditional rebase. |
 | SSH URLs and SSH private keys for Git repositories | v1.10.0 | Scheduled for 
v1.13.0 | Use HTTPS URLs with a personal access token or equivalent. SSH keys 
cannot authenticate to git provider APIs, forcing users to maintain two sets of 
credentials. See [#5858](https://github.com/akuity/kargo/issues/5858) for 
details. |
+| The `createTargetBranch` option in the `git-open-pr` promotion step | 
[v1.10.0](./89-v1.10.0.md) | Scheduled for v1.12.0 | The `createTargetBranch` 
option has been deprecated as the feature never worked. See 
[#5847](https://github.com/akuity/kargo/issues/5847) for details. |
 | The Connect-based API | [v1.9.0](./90-v1.9.0.md) | Scheduled for v1.12.0 | A 
new, RESTful API has been introduced. Most users will not be impacted beyond 
simply needing to upgrade their CLI when upgrading the back end to v1.9.0 or 
greater. |
 | "global credentials namespace(s)" | [v1.9.0](./90-v1.9.0.md) | Scheduled for 
v1.12.0 | Replaced with "shared secrets namespace." See [release 
notes](./90-v1.9.0.md#-the-secret-shuffle) and 
[docs](../40-operator-guide/40-security/40-managing-secrets.md#transitioning) 
for details. |
 | "cluster secrets namespace" | [v1.9.0](./90-v1.9.0.md) | Scheduled for 
v1.12.0 | Replaced with "system resources namespace." See [release 
notes](./90-v1.9.0.md#-the-secret-shuffle) and 
[docs](../40-operator-guide/40-security/40-managing-secrets.md#transitioning) 
for details. |
 | `Warehouse`'s container image subscription's `semverConstraint` field | 
[v1.7.0](./92-v1.7.0.md#new-deprecations) | [v1.9.0](./90-v1.9.0.md) | Users 
should migrate to using the 
[`constraint`](https://docs.kargo.io/user-guide/how-to-guides/working-with-warehouses/#image-selection-strategies)
 field which, accepts the same value but is named to better indicate it can 
also be used for tag selection (e.g. `latest`) when the image selection 
strategy is set to `Digest`. |
+| `freightMetadata` functions optional second argument for the key name | 
[v1.8.0](./91-v1.8.0.md#new-deprecations) | 
[v1.10.0](./89-v1.10.0.md#breaking-changes) | Users should migrate to either 
dot notation (`freightMetadata(freightName).keyName`) or map access syntax 
(`freightMetadata(freightName)['key-name']`) to access specific values instead 
of using the optional second argument. |
 | `Project` specification | [v1.5.0](./94-v1.5.0.md#new-deprecations) | 
[v1.7.0](./92-v1.7.0.md#breaking-changes) | Users should migrate to the 
dedicated [`ProjectConfig` 
resource](../50-user-guide/20-how-to-guides/20-working-with-projects.md#project-configuration).
 This resource kind accepts a `.spec` identitical to the `Project`, but allows 
for fine-grain permissions. |
 | `secrets` object in the Promotion variables | 
[v1.5.0](./94-v1.5.0.md#new-deprecations) | 
[v1.7.0](./92-v1.7.0.md#breaking-changes) | Users should migrate to the 
[`secret()` 
function](../50-user-guide/60-reference-docs/40-expressions.md#promotion-variables)
 which resolves Secrets on-demand, reducing overhead. |
 | `prNumber` field in `git-open-pr` Promotion Step output | 
[v1.5.0](./94-v1.5.0.md#new-deprecations) | 
[v1.7.0](./92-v1.7.0.md#breaking-changes) | Users should migrate to using [the 
`pr.id`](../50-user-guide/60-reference-docs/30-promotion-steps/git-open-pr.md#output)
 for referencing pull request IDs. |
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/kargo-cli-1.10.0/docs/docs/80-release-notes/89-v1.10.0.md 
new/kargo-cli-1.10.1/docs/docs/80-release-notes/89-v1.10.0.md
--- old/kargo-cli-1.10.0/docs/docs/80-release-notes/89-v1.10.0.md       
1970-01-01 01:00:00.000000000 +0100
+++ new/kargo-cli-1.10.1/docs/docs/80-release-notes/89-v1.10.0.md       
2026-04-21 23:14:06.000000000 +0200
@@ -0,0 +1,239 @@
+🧬 Kargo v1.10.0 is here! This release is packed with a host of UI and 
quality-of-life enhancements.
+The goal for this release was "evolution, not revolution." Highlights are below
+
+## 🚨 Breaking Changes {#breaking-changes}
+
+* The optional second arugment for `freightMetadata` that was deprecated in 
v1.8.0 has now been
+  removed. If you were using this argument before, use either dot notation
+  (`freightMetadata(freightName).keyName`) or map access syntax
+  (`freightMetadata(freightName)['key-name']`) to access specific values
+
+## ⚠️ New Deprecations {#new-deprecations}
+
+* **`git-push` Default Integration Policy Changing in v1.12.0**: The 
`git-push` step now supports
+  four configurable [push integration
+  
policies](https://docs.kargo.io/user-guide/reference-docs/promotion-steps/git-push)
 that control
+  how remote changes are integrated before pushing: `AlwaysRebase`, 
`RebaseOrMerge`, `RebaseOrFail`,
+  and `AlwaysMerge`. The current default remains `AlwaysRebase` (i.e. the 
current behavior), but
+  **the default will change to `RebaseOrMerge` in v1.12.0**. `RebaseOrMerge` 
uses signature-trust
+  analysis to prefer rebase when safe but falls back to a merge commit when a 
rebase would alter
+  commit signature semantics. If you rely on the current unconditional rebase 
behavior, set the
+  policy explicitly via the
+  
[`controller.gitClient.pushIntegrationPolicy`](https://docs.kargo.io/operator-guide/advanced-installation/common-configurations#push-integration-policy)
+  Helm value before upgrading to v1.12.0.
+
+* **SSH URLs and SSH Private Keys for Git Repositories**: SSH-based Git 
credentials are deprecated
+  and scheduled for removal in v1.13.0. SSH keys cannot authenticate to git 
provider APIs, forcing
+  users to maintain two sets of credentials. Use HTTPS URLs with a personal 
access token or
+  equivalent instead. See [#5858](https://github.com/akuity/kargo/issues/5858) 
for details.
+
+* **`createTargetBranch` Option in `git-open-pr` Promotion Step**: The 
`createTargetBranch` option has
+  been deprecated as the feature never worked. It is scheduled for removal in 
v1.12. See
+  [#5847](https://github.com/akuity/kargo/issues/5847) for details.
+
+* **`git-commit` Step `author` Field**: The `author` configuration block 
(including `name`, `email`,
+  and `signingKey`) on the `git-commit` step is deprecated and scheduled for 
removal in v1.12.0.
+  Authorship and signing configuration should be set in the
+  
[`git-clone`](https://docs.kargo.io/user-guide/reference-docs/promotion-steps/git-clone)
 step or
+  via `ClusterConfig` instead, as `git-clone` is the single authority for work 
tree identity and
+  signing configuration. All downstream steps inherit from it.
+
+## 🪜 New and Improved Promotion Steps {#promotion-steps}
+
+### New Steps
+
+* **`argocd-wait`**: Blocks a promotion until one or more Argo CD Applications 
reach desired health,
+  sync, and operation statuses. Unlike `argocd-update` (which can already 
wait), `argocd-wait` is
+  useful when you need to gate on Argo CD application health without 
triggering a sync -- for
+  example, waiting for a separate deployment tool to finish before proceeding.
+  
([docs](https://docs.kargo.io/user-guide/reference-docs/promotion-steps/argocd-wait))
+
+* **`oci-push`**: Copies or retags OCI artifacts (container images and Helm 
charts) between
+  registries, with support for single images, multi-arch image indexes, and 
OCI Helm charts.
+  Supports optional annotation injection and shares credential resolution with 
the existing
+  `oci-download` step.
+  
([docs](https://docs.kargo.io/user-guide/reference-docs/promotion-steps/oci-push))
+
+* **`git-tag`**: Creates annotated or lightweight Git tags, with optional GPG 
signing. Pair with
+  `git-push` (which now supports pushing tags) to tag a verified build only 
after it passes
+  promotion through a testing Stage.
+  
([docs](https://docs.kargo.io/user-guide/reference-docs/promotion-steps/git-tag))
+
+* **`github-push`**: An alternative to `git-push` that replays commits through 
the GitHub REST API,
+  enabling GitHub's native commit verification ("Verified" badge) when 
authenticating with a GitHub
+  App installation token. Trust is determined by GPG signature status: commits 
signed by a trusted
+  key are verified by GitHub, while untrusted commits preserve their original 
attribution. Supports
+  the same push integration policies as `git-push`.
+  
([docs](https://docs.kargo.io/user-guide/reference-docs/promotion-steps/github-push))
+
+* **`fail`**: Unconditionally fails the promotion with a configurable message. 
Combined with
+  conditional step execution (`if:` expressions), this provides a clean way to 
fail a promotion
+  pipeline based on evaluated conditions.
+  
([docs](https://docs.kargo.io/user-guide/reference-docs/promotion-steps/fail))
+
+* **`set-freight-alias`**: Assigns a custom, human-readable alias to a piece 
of Freight during a
+  promotion pipeline, improving visibility in the UI -- especially useful in 
pre-processing Stages
+  where a meaningful name can be set before downstream promotions begin.
+  
([docs](https://docs.kargo.io/user-guide/reference-docs/promotion-steps/set-freight-alias))
+
+* **`toml-parse` / `toml-update`**: Parse and update TOML files, complementing 
the existing JSON and
+  YAML equivalents. The update step modifies scalar values in-place while 
preserving all other
+  bytes. Useful for `kcl.mod` files or other TOML-based configuration.
+  
([toml-parse](https://docs.kargo.io/user-guide/reference-docs/promotion-steps/toml-parse),
+  
[toml-update](https://docs.kargo.io/user-guide/reference-docs/promotion-steps/toml-update))
+
+### Improvements to Existing Steps
+
+* **`git-merge-pr`**: Now supports a `mergeMethod` field, allowing you to 
choose between merge,
+  squash, and rebase strategies when merging pull requests.
+  
([docs](https://docs.kargo.io/user-guide/reference-docs/promotion-steps/git-merge-pr))
+
+* **`git-open-pr`**: Detects when there are no commits between source and 
target branches and skips
+  gracefully rather than failing the promotion. `git-wait-for-pr` is also 
skipped in that case. This
+  prevents promotions from failing unnecessarily in multi-stage pipelines 
where some Stages have no
+  effective diff to promote.
+  
([docs](https://docs.kargo.io/user-guide/reference-docs/promotion-steps/git-open-pr))
+
+## 📦 Warehouse Improvements {#warehouse-improvements}
+
+* **`since` Date Limiter for Git Subscriptions**: A new `since` field limits 
commit discovery to
+  commits newer than a specified date, directly addressing performance 
problems in monorepos with
+  large commit histories where unbounded `git log` operations were a primary 
source of slowness.
+  
([docs](https://docs.kargo.io/user-guide/how-to-guides/working-with-warehouses#git-commit-subscriptions))
+
+* **Chart Subscription TLS Skip**: Chart subscriptions now support 
`insecureSkipTLSVerify`, matching
+  the option already available on Git and image subscriptions. Useful for 
internal registries with
+  self-signed or custom CA certificates.
+  
([docs](https://docs.kargo.io/user-guide/how-to-guides/working-with-warehouses#helm-chart-repository-subscriptions))
+
+* **Webhook Path Filtering**: GitHub push-event webhooks now evaluate each 
Warehouse's
+  `includePaths`/`excludePaths` against the files changed in a push *before* 
marking it for refresh,
+  rather than refreshing all Warehouses and filtering later during 
reconciliation. This can
+  dramatically reduce unnecessary refresh traffic in monorepo environments 
with many Warehouses.
+  
([docs](https://docs.kargo.io/user-guide/reference-docs/webhook-receivers/github))
+
+## 🔄 Shared Resource Replication {#shared-resource-replication}
+
+`Secret`s and `ConfigMap`s in the shared resources namespace can now be 
automatically replicated to
+all Project namespaces by annotating them with `kargo.akuity.io/replicate-to: 
"*"`. This enables
+workloads in Project namespaces (such as Argo Rollouts `AnalysisTemplate` 
Jobs) to consume shared
+resources that would otherwise require cross-namespace references. Replicated 
resources are
+immutable and cleaned up automatically when the source is deleted or the 
annotation is removed.
+([docs](https://docs.kargo.io/operator-guide/security/managing-secrets))
+
+## 🖥️ UI Improvements {#ui-improvements}
+
+* **"My Projects" Filter**: The project list now defaults to showing only 
projects where you've been
+  explicitly mapped via OIDC claims, making it easier to find your projects in 
large organizations.
+
+* **Page Titles**: Browser tabs now reflect the current context (project name, 
Stage name, etc.) so
+  you can distinguish between multiple Kargo tabs at a glance.
+
+* **Version-Matched CLI Downloads**: The CLI download page now links to the 
specific version of
+  Kargo currently running rather than always pointing to "latest," preventing 
inadvertent version
+  mismatches.
+
+* **Git Commit Deep Links for Self-Hosted Providers**: Commit links now work 
correctly for
+  self-hosted GitHub Enterprise and GitLab instances, not just `github.com` 
and `gitlab.com`.
+
+* **Inline Promotion Step Errors**: Errors are now displayed directly beneath 
the failed step with
+  the step highlighted in red, rather than only in a disconnected banner. 
Skipped steps are visually
+  muted.
+
+* **Smooth Freight List Scrolling**: The freight list now scrolls smoothly 
rather than jumping
+  between positions.
+
+* **Improved Status Colors**: Non-failed, non-errored statuses now show a 
neutral color instead of
+  potentially misleading indicators.
+
+## ⎈ Helm Chart Improvements {#helm-chart}
+
+* **`priorityClassName` Configuration**: Operators can now assign scheduling 
priority to Kargo
+  components, preventing them from being evicted in favor of higher-priority 
workloads when
+  resources are constrained.
+
+* **Startup Probe for Large Clusters**: The API server now has a startup probe 
with a 5-minute
+  window, preventing the pod from being killed before its initial cache sync 
completes in large
+  clusters with many resources.
+
+* **Certificate Group Enforcement**: The `group` field on cert-manager 
`Certificate` resources is
+  now explicitly set, preventing renewal failures that could occur after 
approximately one year.
+
+## 🔧 API & Developer Experience {#api-developer}
+
+* **REST API Client Module**: The generated Go client for the Kargo REST API 
has been extracted into
+  its own Go module with minimal dependencies, making it easier for external 
consumers to import
+  without pulling in the full Kargo dependency tree.
+
+* **Swagger API Documentation**: Auto-generated OpenAPI documentation for the 
Kargo REST API is now
+  embedded in the documentation site.
+
+* **Port Numbers in OCI Image Refs**: The `oci-download` step now accepts 
image references with
+  explicit port numbers (e.g., `registry.internal:5000/image:tag`).
+
+## 🐛 Notable Bug Fixes {#bug-fixes}
+
+* **`yaml-update` escaping**: Dots in YAML key names can now be properly 
escaped using backslash
+  notation (e.g., `metadata.annotations.example\.com/version`).
+  
([docs](https://docs.kargo.io/user-guide/reference-docs/promotion-steps/yaml-update))
+
+* **Argo CD App Status Responsiveness** (#5995): Eliminated a 10-second 
cooldown that could cause
+  promotions to stall for minutes in "Unknown" health state. The controller 
now trusts health
+  immediately when Argo CD's `reconciledAt` timestamp confirms a fresh 
reconciliation, and forces a
+  hard refresh otherwise.
+
+* **Path Filtering on Merge Commits** (#5990, #5999): Fixed two related issues 
where
+  `includePaths`/`excludePaths` filtering on Warehouses could silently skip 
changes introduced via
+  merge commits. The `--first-parent` flag is now used to correctly identify 
files changed by a
+  merge.
+
+* **ClusterRole Permissions in Kargo Roles** (#5916): Fixed a bug since v1.4.4 
where `RoleBinding`s
+  referencing a `ClusterRole` (instead of a namespaced `Role`) caused "Role 
not found" errors,
+  breaking the RBAC UI for any namespace with such bindings.
+
+* **Promotion Working Directory Cleanup** (#5805): Temporary promotion working 
directories are now
+  cleaned up when a promotion reaches a terminal state or is deleted, 
preventing disk space leaks on
+  the controller.
+
+* **`git-commit` Custom Author** (#5857): Fixed a regression where using the 
`author` config block
+  in the `git-commit` step failed with "Author identity unknown."
+
+* **Promotion `Failed` vs `Errored` Status** (#5941): Steps that intentionally 
return `Failed`
+  status (such as the new `fail` step) are no longer incorrectly reported as 
`Errored`.
+
+* **Events Dropped on Shutdown** (#5943): Kubernetes events are no longer 
silently dropped when the
+  controller's context is cancelled during shutdown.
+
+* **API Delete Error Handling** (#5870): The API server no longer silently 
swallows errors when
+  deleting resources.
+
+* **UI: Invalid Metric Chart Date** (#5733): Fixed "Invalid date" display in 
verification metric
+  chart tooltips.
+
+* **UI: Freight Assembly Crash** (#5975): Fixed a crash on the freight 
assembly page when commits
+  were not found for a Git subscription.
+
+## 🙏 Special Thanks {#special-thanks}
+
+Thank you to community members who made their first contributions in this 
release or a recent v1.9
+patch release!
+
+@apt-itude
+@bafulton
+@bobdoah
+@cmontemuino
+@danielloader
+@edshin24
+@emilyxinyi
+@emirot
+@EronWright
+@evanndev
+@henrycatalinismith
+@neboman11
+@nikita-unity
+@olofsol
+@shamsalmon
+@ThreePinkApples
+@zoeyfyi
+
+**Full Changelog**: 
[v1.9.5...v1.10.0](https://github.com/akuity/kargo/compare/v1.9.5...v1.10.0)
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/kargo-cli-1.10.0/docs/docs/80-release-notes/91-v1.8.0.md 
new/kargo-cli-1.10.1/docs/docs/80-release-notes/91-v1.8.0.md
--- old/kargo-cli-1.10.0/docs/docs/80-release-notes/91-v1.8.0.md        
2026-04-16 22:35:17.000000000 +0200
+++ new/kargo-cli-1.10.1/docs/docs/80-release-notes/91-v1.8.0.md        
2026-04-21 23:14:06.000000000 +0200
@@ -6,7 +6,7 @@
 
 ## ⚠️ New Deprecations
 
-None
+* **`freightMetadata` function's optional second argument for the key name**: 
The optional second argument for `freightMetadata` is now scheduled for removal 
in v1.10.0. Users should migrate to either dot notation 
(`freightMetadata(freightName).keyName`) or map access syntax 
(`freightMetadata(freightName)['key-name']`) to access specific values instead 
of using the optional second argument.
 
 ## ✨ Noteworthy Features
 
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/kargo-cli-1.10.0/docs/src/components/VersionDropdown.js 
new/kargo-cli-1.10.1/docs/src/components/VersionDropdown.js
--- old/kargo-cli-1.10.0/docs/src/components/VersionDropdown.js 2026-04-16 
22:35:17.000000000 +0200
+++ new/kargo-cli-1.10.1/docs/src/components/VersionDropdown.js 2026-04-21 
23:14:06.000000000 +0200
@@ -24,10 +24,8 @@
 
   const fetchVersions = async () => {
     try {
-      console.log("Before fetching versions");
       const response = await fetch(githubApiUrl);
       const branches = await response.json();
-      console.log("Fetched branches are: ", branches);
 
       const releaseBranches = branches
         .map(branch => branch.name)
@@ -40,15 +38,10 @@
           };
         });
 
-      console.log("These are release branches before sorting and updating 0 
element: ", releaseBranches);
       releaseBranches.sort((a, b) => {
-        if (a.version > b.version) {
-          return -1;
-        }
-        if (a.version < b.version) {
-          return 1;
-        }
-        return 0;
+        const [aMajor, aMinor] = a.version.slice(1).split('.').map(Number);
+        const [bMajor, bMinor] = b.version.slice(1).split('.').map(Number);
+        return bMajor - aMajor || bMinor - aMinor;
       });
       // Overwrite the first element with the latest version
       releaseBranches[0] = {
@@ -69,7 +62,6 @@
           url: `${url.protocol}//${url.hostname}${url.port ? `:${url.port}` : 
''}`
         });
       }
-      console.log("These are release branches: ", releaseBranches);
       setVersions(releaseBranches);
       setLoading(false);
     } catch (error) {
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/kargo-cli-1.10.0/pkg/cli/cmd/promote/promote.go 
new/kargo-cli-1.10.1/pkg/cli/cmd/promote/promote.go
--- old/kargo-cli-1.10.0/pkg/cli/cmd/promote/promote.go 2026-04-16 
22:35:17.000000000 +0200
+++ new/kargo-cli-1.10.1/pkg/cli/cmd/promote/promote.go 2026-04-21 
23:14:06.000000000 +0200
@@ -212,14 +212,10 @@
                if err != nil {
                        return fmt.Errorf("marshal promotion: %w", err)
                }
-               // The response is {"promotion": {...}}
-               var result struct {
-                       Promotion *kargoapi.Promotion `json:"promotion"`
-               }
-               if err = json.Unmarshal(promoJSON, &result); err != nil {
+               promo := &kargoapi.Promotion{}
+               if err = json.Unmarshal(promoJSON, promo); err != nil {
                        return fmt.Errorf("unmarshal promotion: %w", err)
                }
-               promo := result.Promotion
                if o.Wait {
                        if err = o.waitForPromotion(ctx, nil, promo); err != 
nil {
                                return fmt.Errorf("wait for promotion: %w", err)
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/kargo-cli-1.10.0/pkg/server/promote_to_stage_v1alpha1.go 
new/kargo-cli-1.10.1/pkg/server/promote_to_stage_v1alpha1.go
--- old/kargo-cli-1.10.0/pkg/server/promote_to_stage_v1alpha1.go        
2026-04-16 22:35:17.000000000 +0200
+++ new/kargo-cli-1.10.1/pkg/server/promote_to_stage_v1alpha1.go        
2026-04-21 23:14:06.000000000 +0200
@@ -284,5 +284,5 @@
                s.recordPromotionCreatedEvent(ctx, promotion, freight)
        }
 
-       c.JSON(http.StatusCreated, gin.H{"promotion": promotion})
+       c.JSON(http.StatusCreated, promotion)
 }
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/kargo-cli-1.10.0/ui/src/features/project/pipelines/freight/freight-timeline-filters.tsx
 
new/kargo-cli-1.10.1/ui/src/features/project/pipelines/freight/freight-timeline-filters.tsx
--- 
old/kargo-cli-1.10.0/ui/src/features/project/pipelines/freight/freight-timeline-filters.tsx
 2026-04-16 22:35:17.000000000 +0200
+++ 
new/kargo-cli-1.10.1/ui/src/features/project/pipelines/freight/freight-timeline-filters.tsx
 2026-04-21 23:14:06.000000000 +0200
@@ -1,7 +1,7 @@
 import { faDocker, faGitAlt } from '@fortawesome/free-brands-svg-icons';
 import { faAnchor, faFilter, faTimes, IconDefinition } from 
'@fortawesome/free-solid-svg-icons';
 import { FontAwesomeIcon } from '@fortawesome/react-fontawesome';
-import { Button, Checkbox, Select, SelectProps } from 'antd';
+import { Badge, Button, Checkbox, Select, SelectProps } from 'antd';
 import classNames from 'classnames';
 import { useMemo } from 'react';
 
@@ -24,6 +24,11 @@
 };
 
 export const FreightTimelineFilters = (props: FreightTimelineFiltersProps) => {
+  const isFilterActive =
+    (props.preferredFilter?.sources?.length ?? 0) > 0 ||
+    props.preferredFilter?.timerange !== 'all-time' ||
+    props.preferredFilter?.hideUnusedFreights === true;
+
   const sourcesDropdownOptions: SelectProps['options'] = useMemo(() => {
     const freightSourcesCatalogue = catalogueFreights(props.freights);
 
@@ -63,9 +68,11 @@
           </div>
         )}
 
-        <Button size='small' className='ml-auto' 
onClick={props.onCollapseToggle}>
-          <FontAwesomeIcon icon={props.collapsed ? faFilter : faTimes} />
-        </Button>
+        <Badge dot={props.collapsed && isFilterActive} offset={[-2, 2]} 
className='ml-auto'>
+          <Button size='small' onClick={props.onCollapseToggle}>
+            <FontAwesomeIcon icon={props.collapsed ? faFilter : faTimes} />
+          </Button>
+        </Badge>
       </span>
 
       <div
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/kargo-cli-1.10.0/ui/src/features/project/pipelines/freight/freight-timeline.tsx
 
new/kargo-cli-1.10.1/ui/src/features/project/pipelines/freight/freight-timeline.tsx
--- 
old/kargo-cli-1.10.0/ui/src/features/project/pipelines/freight/freight-timeline.tsx
 2026-04-16 22:35:17.000000000 +0200
+++ 
new/kargo-cli-1.10.1/ui/src/features/project/pipelines/freight/freight-timeline.tsx
 2026-04-21 23:14:06.000000000 +0200
@@ -2,7 +2,7 @@
 import { faCaretLeft, faCaretRight } from '@fortawesome/free-solid-svg-icons';
 import { FontAwesomeIcon } from '@fortawesome/react-fontawesome';
 import classNames from 'classnames';
-import { useContext, useMemo, useRef, useState } from 'react';
+import { useCallback, useContext, useEffect, useMemo, useRef, useState } from 
'react';
 import { generatePath, useNavigate } from 'react-router-dom';
 
 import { paths } from '@ui/config/paths';
@@ -129,8 +129,26 @@
     actionContext
   ]);
 
+  const PAGE_SIZE = 20;
+  const [visibleCount, setVisibleCount] = useState(PAGE_SIZE);
+
+  // Reset visible count and scroll position when filters change
+  useEffect(() => {
+    setVisibleCount(PAGE_SIZE);
+    freightListStyleRef.current?.style.setProperty('right', '0px');
+  }, [
+    freightTimelineControllerContext.preferredFilter.sources,
+    freightTimelineControllerContext.preferredFilter.timerange,
+    freightTimelineControllerContext.preferredFilter.warehouses,
+    freightTimelineControllerContext.preferredFilter.hideUnusedFreights
+  ]);
+
   const freightListStyleRef = useRef<HTMLDivElement>(null);
 
+  const loadMore = useCallback(() => {
+    setVisibleCount((prev) => Math.min(prev + PAGE_SIZE, 
filteredFreights.length));
+  }, [filteredFreights.length]);
+
   const scrollCarouselLeft = () => {
     const right = freightListStyleRef.current?.style.right || '0px';
 
@@ -149,6 +167,10 @@
     const nextRight = +right.slice(0, -2) + 160;
 
     if (nextRight >= (freightListStyleRef.current?.clientWidth || 0) / 2) {
+      // At the edge — load more items if available
+      if (visibleCount < filteredFreights.length) {
+        loadMore();
+      }
       return;
     }
 
@@ -203,7 +225,7 @@
             className='flex gap-1 relative right-0 transition-[right] 
duration-300 ease-out'
             ref={freightListStyleRef}
           >
-            {filteredFreights.map((freight) => {
+            {filteredFreights.slice(0, visibleCount).map((freight) => {
               const freightSoakTime = soakTime?.[freight?.metadata?.name || 
''];
 
               const promotionEligible = Boolean(
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/kargo-cli-1.10.0/ui/src/features/project/pipelines/graph/graph.tsx 
new/kargo-cli-1.10.1/ui/src/features/project/pipelines/graph/graph.tsx
--- old/kargo-cli-1.10.0/ui/src/features/project/pipelines/graph/graph.tsx      
2026-04-16 22:35:17.000000000 +0200
+++ new/kargo-cli-1.10.1/ui/src/features/project/pipelines/graph/graph.tsx      
2026-04-21 23:14:06.000000000 +0200
@@ -171,7 +171,7 @@
           nodes: nodesExcludingSubscriptionNodes
         }}
         proOptions={{ hideAttribution: true }}
-        minZoom={0}
+        minZoom={nodes.length > 100 ? 0.6 : 0.1}
         onlyRenderVisibleElements
         panOnDrag
         onInit={(inst) => (reactFlowInstance.current = inst)}
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/kargo-cli-1.10.0/ui/src/features/project/pipelines/graph/use-pipeline-graph.ts
 
new/kargo-cli-1.10.1/ui/src/features/project/pipelines/graph/use-pipeline-graph.ts
--- 
old/kargo-cli-1.10.0/ui/src/features/project/pipelines/graph/use-pipeline-graph.ts
  2026-04-16 22:35:17.000000000 +0200
+++ 
new/kargo-cli-1.10.1/ui/src/features/project/pipelines/graph/use-pipeline-graph.ts
  2026-04-21 23:14:06.000000000 +0200
@@ -1,6 +1,6 @@
 import { layout } from '@dagrejs/dagre';
 import { Edge, MarkerType, Node } from '@xyflow/react';
-import { useContext, useMemo } from 'react';
+import { useContext, useEffect, useRef, useState } from 'react';
 
 import { ColorContext } from '@ui/context/colors';
 import { WarehouseExpanded } from '@ui/extend/types';
@@ -32,121 +32,140 @@
 ) => {
   const { warehouseColorMap } = useContext(ColorContext);
 
-  return useMemo(() => {
+  const [result, setResult] = useState<{ nodes: Node[]; edges: Edge[] }>({
+    nodes: [],
+    edges: []
+  });
+  const lastRunRef = useRef(0);
+  const functionCalled = useRef(false);
+
+  useEffect(() => {
     if (Object.keys(dimensionState).length === 0) {
-      return {
-        nodes: [],
-        edges: []
-      };
+      setResult({ nodes: [], edges: [] });
+      return;
     }
 
-    // eslint-disable-next-line prefer-const
-    let { graph, stageByName, maxStageHeight } = layoutGraph(
-      {
-        stages,
-        ignore(s) {
-          return (
-            !!pipeline.length &&
-            !s.spec?.requestedFreight?.find((f) => 
pipeline.includes(f?.origin?.name || ''))
-          );
-        }
-      },
-      {
-        warehouses,
-        ignore(w) {
-          return !!pipeline.length && !pipeline.includes(w?.metadata?.name || 
'');
-        }
-      },
-      dimensionState,
-      warehouseColorMap,
-      hideSubscriptions
-    );
-
-    graph = stackNodes(stack?.afterNodes || [], graph, stageByName, 
maxStageHeight);
-
-    layout(graph, { disableOptimalOrderHeuristic: true });
+    const compute = () => {
+      lastRunRef.current = Date.now();
 
-    const reactFlowNodes: Node[] = [];
-    const reactFlowEdges: Edge[] = [];
+      // eslint-disable-next-line prefer-const
+      let { graph, stageByName, maxStageHeight } = layoutGraph(
+        {
+          stages,
+          ignore(s) {
+            return (
+              !!pipeline.length &&
+              !s.spec?.requestedFreight?.find((f) => 
pipeline.includes(f?.origin?.name || ''))
+            );
+          }
+        },
+        {
+          warehouses,
+          ignore(w) {
+            return !!pipeline.length && !pipeline.includes(w?.metadata?.name 
|| '');
+          }
+        },
+        dimensionState,
+        warehouseColorMap,
+        hideSubscriptions
+      );
+
+      graph = stackNodes(stack?.afterNodes || [], graph, stageByName, 
maxStageHeight);
+
+      layout(graph, { disableOptimalOrderHeuristic: true });
+
+      const reactFlowNodes: Node[] = [];
+      const reactFlowEdges: Edge[] = [];
+
+      for (const node of graph.nodes()) {
+        const dagreNode = graph.node(node);
+
+        if (stackedIndexer.is(node)) {
+          const stackedActualHeight =
+            dimensionState[STACKED_NODE_DUMMY_KEY]?.height || 
stackSizer.size().height;
+          reactFlowNodes.push({
+            id: node,
+            type: reactFlowNodeConstants.STACKED_NODE,
+            position: {
+              x: dagreNode?.x - dagreNode?.width / 2,
+              y: dagreNode?.y - stackedActualHeight / 2
+            },
+            data: {
+              value: dagreNode?.value,
+              id: dagreNode?.id,
+              parentNodeId: dagreNode?.parentNodeId
+            }
+          });
+          continue;
+        }
 
-    for (const node of graph.nodes()) {
-      const dagreNode = graph.node(node);
+        // All nodes share a uniform virtual height in dagre (= max stage 
height)
+        // so edges connect at the same center. Use the actual measured height 
to
+        // visually center each node within its virtual slot.
+        const actualHeight = dimensionState[node]?.height || dagreNode?.height;
 
-      if (stackedIndexer.is(node)) {
-        const stackedActualHeight =
-          dimensionState[STACKED_NODE_DUMMY_KEY]?.height || 
stackSizer.size().height;
         reactFlowNodes.push({
           id: node,
-          type: reactFlowNodeConstants.STACKED_NODE,
+          type: reactFlowNodeConstants.CUSTOM_NODE,
           position: {
             x: dagreNode?.x - dagreNode?.width / 2,
-            y: dagreNode?.y - stackedActualHeight / 2
+            y: dagreNode?.y - actualHeight / 2
           },
           data: {
-            value: dagreNode?.value,
-            id: dagreNode?.id,
-            parentNodeId: dagreNode?.parentNodeId
+            label: node,
+            value: dagreNode?.warehouse || dagreNode?.subscription || 
dagreNode?.stage,
+            subscriptionParent: dagreNode?.subscriptionParent,
+            // Fixed pixel offset from the node's top to the dagre center 
point.
+            // Stored at layout time so handles stay anchored even when node 
content
+            // grows and the rendered height changes (node position is not 
updated).
+            handleOffsetY: actualHeight / 2
           }
         });
-        continue;
       }
 
-      // All nodes share a uniform virtual height in dagre (= max stage height)
-      // so edges connect at the same center. Use the actual measured height to
-      // visually center each node within its virtual slot.
-      const actualHeight = dimensionState[node]?.height || dagreNode?.height;
-
-      reactFlowNodes.push({
-        id: node,
-        type: reactFlowNodeConstants.CUSTOM_NODE,
-        position: {
-          x: dagreNode?.x - dagreNode?.width / 2,
-          y: dagreNode?.y - actualHeight / 2
-        },
-        data: {
-          label: node,
-          value: dagreNode?.warehouse || dagreNode?.subscription || 
dagreNode?.stage,
-          subscriptionParent: dagreNode?.subscriptionParent,
-          // Fixed pixel offset from the node's top to the dagre center point.
-          // Stored at layout time so handles stay anchored even when node 
content
-          // grows and the rendered height changes (node position is not 
updated).
-          handleOffsetY: actualHeight / 2
-        }
-      });
-    }
+      for (const edge of graph.edges()) {
+        const belongsToWarehouse = warehouseIndexer.getWarehouseName(edge.name 
|| '');
 
-    for (const edge of graph.edges()) {
-      const belongsToWarehouse = warehouseIndexer.getWarehouseName(edge.name 
|| '');
+        const dagreEdge = graph.edge(edge);
 
-      const dagreEdge = graph.edge(edge);
+        reactFlowEdges.push({
+          id: edgeIndexer.index(belongsToWarehouse, edge.v, edge.w),
+          source: edge.v,
+          target: edge.w,
+          animated: false,
+          type:
+            (graph.successors(edge.v)?.length || 0) > 1 ||
+            (graph.predecessors(edge.w)?.length || 0) > 1
+              ? 'step'
+              : '',
+          sourceHandle: belongsToWarehouse,
+          targetHandle: belongsToWarehouse,
+          markerEnd: {
+            type: MarkerType.ArrowClosed,
+            color: dagreEdge.edgeColor || ''
+          },
+          style: {
+            strokeWidth: 2,
+            stroke: dagreEdge.edgeColor || '',
+            transition: 'd 0.3s ease'
+          }
+        });
+      }
 
-      reactFlowEdges.push({
-        id: edgeIndexer.index(belongsToWarehouse, edge.v, edge.w),
-        source: edge.v,
-        target: edge.w,
-        animated: false,
-        type:
-          (graph.successors(edge.v)?.length || 0) > 1 ||
-          (graph.predecessors(edge.w)?.length || 0) > 1
-            ? 'step'
-            : '',
-        sourceHandle: belongsToWarehouse,
-        targetHandle: belongsToWarehouse,
-        markerEnd: {
-          type: MarkerType.ArrowClosed,
-          color: dagreEdge.edgeColor || ''
-        },
-        style: {
-          strokeWidth: 2,
-          stroke: dagreEdge.edgeColor || '',
-          transition: 'd 0.3s ease'
-        }
-      });
+      setResult({ nodes: reactFlowNodes, edges: reactFlowEdges });
+    };
+
+    if (!functionCalled.current) {
+      functionCalled.current = true;
+      compute();
+      return;
     }
 
-    return {
-      nodes: reactFlowNodes,
-      edges: reactFlowEdges
-    };
+    const elapsed = Date.now() - lastRunRef.current;
+    const delay = Math.max(0, 3000 - elapsed);
+    const id = setTimeout(compute, delay);
+    return () => clearTimeout(id);
   }, [stack?.afterNodes, pipeline, redraw, warehouseColorMap, 
hideSubscriptions, dimensionState]);
+
+  return result;
 };
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/kargo-cli-1.10.0/ui/src/features/project/pipelines/nodes/stage-node.tsx 
new/kargo-cli-1.10.1/ui/src/features/project/pipelines/nodes/stage-node.tsx
--- old/kargo-cli-1.10.0/ui/src/features/project/pipelines/nodes/stage-node.tsx 
2026-04-16 22:35:17.000000000 +0200
+++ new/kargo-cli-1.10.1/ui/src/features/project/pipelines/nodes/stage-node.tsx 
2026-04-21 23:14:06.000000000 +0200
@@ -191,7 +191,7 @@
           'postiion-relative'
         )}
         size='small'
-        variant='borderless'
+        // variant='borderless'
       >
         <DropOverlay isOver={isOver} stage={props.stage} />
         {controlFlow && (
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/kargo-cli-1.10.0/ui/src/features/project/pipelines/pipelines.tsx 
new/kargo-cli-1.10.1/ui/src/features/project/pipelines/pipelines.tsx
--- old/kargo-cli-1.10.0/ui/src/features/project/pipelines/pipelines.tsx        
2026-04-16 22:35:17.000000000 +0200
+++ new/kargo-cli-1.10.1/ui/src/features/project/pipelines/pipelines.tsx        
2026-04-21 23:14:06.000000000 +0200
@@ -97,7 +97,6 @@
     projectQuery.isLoading ||
     getFreightQuery.isLoading ||
     listWarehousesQuery.isLoading ||
-    listStagesQuery.isLoading ||
     getConfigQuery.isLoading;
 
   const promote = freight && stage ? { freight, stage } : undefined;
@@ -301,14 +300,19 @@
                       />
                     </div>
                   )}
-                  {pipelineView === 'graph' && (
+                  {listStagesQuery.isLoading && (
+                    <div className='mt-20'>
+                      <LoadingState />
+                    </div>
+                  )}
+                  {pipelineView === 'graph' && listStagesQuery.data?.stages && 
(
                     <Graph
                       project={project.metadata?.name || ''}
                       warehouses={listWarehousesQuery.data?.warehouses || []}
                       stages={listStagesQuery.data?.stages || []}
                     />
                   )}
-                  {pipelineView === 'list' && (
+                  {pipelineView === 'list' && listStagesQuery.data?.stages && (
                     <PipelineListView
                       stages={listStagesQuery.data?.stages || []}
                       warehouses={listWarehousesQuery.data?.warehouses || []}
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/kargo-cli-1.10.0/ui/src/features/project/pipelines/url-params/use-freight-timeline-controller-store.ts
 
new/kargo-cli-1.10.1/ui/src/features/project/pipelines/url-params/use-freight-timeline-controller-store.ts
--- 
old/kargo-cli-1.10.0/ui/src/features/project/pipelines/url-params/use-freight-timeline-controller-store.ts
  2026-04-16 22:35:17.000000000 +0200
+++ 
new/kargo-cli-1.10.1/ui/src/features/project/pipelines/url-params/use-freight-timeline-controller-store.ts
  2026-04-21 23:14:06.000000000 +0200
@@ -24,7 +24,9 @@
       showMinimap: true
     };
 
-    if (searchParams.size === 0) {
+    const hasFilterParams = Object.keys(filters).some((name) => 
searchParams.has(name));
+
+    if (!hasFilterParams) {
       return { ...filters, ...getFreightTimelineFiltersLocalStorage(project) };
     }
 
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/kargo-cli-1.10.0/ui/src/features/project/pipelines/use-watch-freight.ts 
new/kargo-cli-1.10.1/ui/src/features/project/pipelines/use-watch-freight.ts
--- old/kargo-cli-1.10.0/ui/src/features/project/pipelines/use-watch-freight.ts 
2026-04-16 22:35:17.000000000 +0200
+++ new/kargo-cli-1.10.1/ui/src/features/project/pipelines/use-watch-freight.ts 
2026-04-21 23:14:06.000000000 +0200
@@ -68,6 +68,17 @@
         }
 
         const currentFreight = queryCache.freight.get(project);
+
+        // Skip ADDED events for freight that already exists in the cache.
+        // Kubernetes watches replay all existing objects as ADDED on connect,
+        // which duplicates the initial GET and causes unnecessary re-renders.
+        if (e.type === 'ADDED') {
+          const existing = currentFreight?.groups?.['']?.freight || [];
+          if (existing.some((f) => f?.metadata?.name === 
freight?.metadata?.name)) {
+            continue;
+          }
+        }
+
         const updatedFreight =
           e.type === 'DELETED'
             ? deleteFreight(currentFreight, freight)
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/kargo-cli-1.10.0/ui/src/features/project/pipelines/watcher.ts 
new/kargo-cli-1.10.1/ui/src/features/project/pipelines/watcher.ts
--- old/kargo-cli-1.10.0/ui/src/features/project/pipelines/watcher.ts   
2026-04-16 22:35:17.000000000 +0200
+++ new/kargo-cli-1.10.1/ui/src/features/project/pipelines/watcher.ts   
2026-04-21 23:14:06.000000000 +0200
@@ -30,6 +30,7 @@
   getter: (e: T) => S,
   callback: (item: S, data: S[]) => void
 ) {
+  let timer: ReturnType<typeof setTimeout> | undefined;
   for await (const e of stream) {
     let data = getData();
     const index = data.findIndex((item) => item.metadata?.name === 
getter(e).metadata?.name);
@@ -45,7 +46,8 @@
       }
     }
 
-    callback(getter(e), data);
+    clearTimeout(timer);
+    timer = setTimeout(() => callback(getter(e), data));
   }
 }
 

++++++ kargo-cli.obsinfo ++++++
--- /var/tmp/diff_new_pack.kbRpZ7/_old  2026-04-22 17:01:33.128848964 +0200
+++ /var/tmp/diff_new_pack.kbRpZ7/_new  2026-04-22 17:01:33.180851110 +0200
@@ -1,5 +1,5 @@
 name: kargo-cli
-version: 1.10.0
-mtime: 1776371717
-commit: f5477e786aa4904425e9bbd547c7c05527b76237
+version: 1.10.1
+mtime: 1776806046
+commit: 6063d52de99ed5c26e5a01856ffe67434f8a9f23
 

++++++ vendor.tar.gz ++++++
/work/SRC/openSUSE:Factory/kargo-cli/vendor.tar.gz 
/work/SRC/openSUSE:Factory/.kargo-cli.new.11940/vendor.tar.gz differ: char 13, 
line 1

Reply via email to