Feature: Added SSH support for Git and progress reporting in Status Center #18063
Feature: Added SSH support for Git and progress reporting in Status Center #18063NyanHeart wants to merge 2 commits intofiles-community:mainfrom
Conversation
…unity#17692) - Implemented SSH key authentication by integrating with the system OpenSSH Agent, resolving compatibility issues with LibGit2Sharp 0.31.0 and enabling support for passphrase-protected keys. - Integrated Git Push, Fetch, and Pull operations with the Status Center to provide real-time progress feedback (items processed, transfer bytes). - Fixed the issue where the Git Status Bar (commits ahead/behind) would not refresh automatically after remote operations. - Refactored FetchOrigin and PullOriginAsync to use async/await and perform operations on background threads, preventing UI freezes. - Removed the obsolete GitPassphraseDialog and custom SSH credential handling logic in favor of the native agent. - Added GitFetch and GitPull to FileOperationType and updated Resources.resw with localized strings for these operations. Closes files-community#17692
There was a problem hiding this comment.
Auto-fetch on folder navigation silently fails due to being called from a background thread in BaseShellPage.cs.
There was a problem hiding this comment.
This is no longer used after the refactoring.
There was a problem hiding this comment.
The older code used Prune = true in _fetchOptions, but that appears to have been removed. Is this intentional?
|
I am able to successfully pull and push using an SSH URL (and HTTPS). However, I encountered the following problems,
|
- Threading: Wrapped Status Center UI updates and dialogs in `DispatcherQueue.TryEnqueue` to prevent `COMException` (RPC_E_WRONG_THREAD) during background fetches. - Cleanup: Removed unused `_fetchOptions` field and restored `Prune = true` for fetch operations. - Error Handling: - Catch `CheckoutConflictException` specifically for uncommitted changes during pull, providing a helpful localized error message. - Catch generic `LibGit2SharpException` to surface authentic underlying errors (e.g. ssh-agent failures, missing files) to the user via dialog. - Localization: Added `GitError_UncommittedChanges` resource string.
| { | ||
| Username = signature.Name, | ||
| Password = token | ||
| fsProgress.ItemsCount = total; | ||
| fsProgress.SetProcessedSize(bytes); | ||
| fsProgress.AddProcessedItemsCount(1); // Not accurate but shows activity |
There was a problem hiding this comment.
Bug: The OnPushTransferProgress callback in PushToOriginAsync updates UI-bound properties from a background thread without using the dispatcher, which will cause a crash.
Severity: CRITICAL
Suggested Fix
Wrap the property updates on the fsProgress object inside the OnPushTransferProgress callback with a MainWindow.Instance.DispatcherQueue.TryEnqueue call, similar to the implementation in FetchOrigin and PullOriginAsync.
Prompt for AI Agent
Review the code at the location below. A potential bug has been identified by an AI
agent.
Verify if this is a real issue. If it is, propose a fix; if not, explain why it's not
valid.
Location: src/Files.App/Utils/Git/GitHelpers.cs#L623-L626
Potential issue: The `OnPushTransferProgress` callback within `PushToOriginAsync`
directly updates properties of the `fsProgress` object, which is an instance of
`StatusCenterItemProgressModel`. This model raises `PropertyChanged` events, which must
occur on the UI thread. Since the operation runs on a background thread, updating these
properties without dispatching to the UI thread will cause a `COMException
(RPC_E_WRONG_THREAD)` and crash the application during a git push operation. Other git
operations in the same file, like `FetchOrigin` and `PullOriginAsync`, correctly wrap
these UI updates using `DispatcherQueue.TryEnqueue`.
Did we get this right? 👍 / 👎 to inform future reviews.
|
@workbysaran Thanks for the detailed review! I've pushed a fix that addresses your feedback:
Could you please take another look? Thanks! |
| var remoteName = repository.Network.Remotes.FirstOrDefault()?.Name ?? "origin"; | ||
|
|
||
| // Add Status Center Card | ||
| var banner = StatusCenterHelper.AddCard_GitFetch(remoteName, ReturnResult.InProgress); |
There was a problem hiding this comment.
The call to StatusCenterHelper.AddCard_GitFetch needs to be dispatched to the UI thread. An exception is thrown during auto-fetch.
|
Thanks for the update. I tested again, and here are my findings.
It appears that the LibGit2Sharp library hides transport-level errors, so only the generic message "could not read refs from remote repository" is returned. We may need to investigate and address this in a separate PR. The Git CLI shows the following error: git@github.com: Permission denied (publickey). I think we should accept this behavior with the current limitation.
Now it shows, "Please commit or stash your changes before pulling," which is good! |
Does this fix #18024 ? |
|
@NyanHeart fyi |
Resolved / Related Issues
Closes #17692
Changes
async/awaitand run on background threads, preventing UI freezes during network operations.GitPassphraseDialogand custom SSH credential logic.Steps used to test these changes
git@github.com:...).git pushandgit pullwork seamlessly using the system SSH Agent (with both passphrase-protected and standard keys).