針對代理服務進行疑難解答
適用於: Visual Studio 2019 和更新版本
本文介紹疑難解答建議,以及當您嘗試在Visual Studio SDK中取得 代理服務 時,可能會發生的數個常見問題解決方案。
代理服務可能會以各種方式失敗。 開始調查的實用技巧是檢查 Visual Studio 活動記錄,當代理服務發生問題時,通常會記錄錯誤或警告。
要求服務時的問題
代理服務最常見的挑戰可能是瞭解呼叫 或 所得到 IServiceBroker.GetProxyAsync 的結果或 IServiceBroker.GetPipeAsync例外狀況。 刻 IServiceBroker 意將代理服務啟用位置和方式的疑慮抽象化。 但是,當發生錯誤時,就必須深入鑽研以診斷並更正問題。
無服務
當下列任一條件成立時,服務要求的結果可能是 null
:
- 要求的服務未註冊。 代理服務作者應該向 或手動撰寫的 .pkgdef 檔案註冊它ProvideBrokeredServiceAttribute。
- 要求的服務會向不會向此客戶端公開服務的組態註冊。 默認範圍是 ServiceAudience.Process,這表示代理服務只能在從與用戶端相同的進程產生時啟動。 如果用戶端在另一個進程中,且意圖是要讓代理服務可供其使用,請變更服務註冊以展開其 ServiceAudience。
- 要求的服務已向 ServiceAudience.LiveShareGuest註冊,Live Share 連線存在,但主機未提供該代理服務,或 ProvideBrokeredServiceAttribute.AllowTransitiveGuestClients 屬性未設定為
true
。 透過 Live Share 公開代理服務時,請檢閱 如何保護代理服務。 - 要求的服務已註冊,但缺少要初始化以提供其處理站之套件的相關信息。 屬性 ProvideBrokeredServiceAttribute 會自動產生註冊,指出已套用屬性的套件,讓Visual Studio可以視需要載入該套件。 如果屬性套用至錯誤的套件,或 .pkgdef 檔案是手動撰寫的,則此資訊可能會遺失或不正確。
- 負責提供代理服務的Visual Studio套件會在初始化期間擲回,否則無法實際提供該服務處理站。 檢查 Visual Studio 活動記錄 檔,以取得封裝載入失敗的辨識項。
- 服務處理站本身會傳回
null
。
服務要求擲回例外狀況
當服務處理站擲回例外狀況時,服務要求可能會擲 ServiceCompositionException 回 。 這表示上述所有會導致 null
結果的問題都不適用。 查看例外狀況詳細數據 (包括內部例外狀況) 瞭解發生什麼錯誤,以及對用戶端或服務處理站進行任何必要的更正。
您會在預期遠端服務時取得本地服務
視服務註冊和 Visual Studio 的目前狀態而定,要求可能會在本機或遠端完成。 默認範圍是 ServiceAudience.Process,這表示代理服務只能在從與用戶端相同的進程產生時啟動。
當代理服務應該從 Live Share 主機公開至已連線的來賓, ServiceAudience 但 僅限於本機範圍時,來自 Live Share 來賓的要求會從該相同電腦而不是主機啟動代理服務。 更新註冊以包含 ServiceAudience.LiveShareGuest ,以透過 Live Share 公開您的代理服務。 您可能也需要設定 ProvideBrokeredServiceAttribute.AllowTransitiveGuestClients 為 true
。
提供服務時的問題
除非透過MEF匯出代理服務,否則必須從 AsyncPackage 類別提供代理服務,如 如何提供代理服務中所述。
如果上述任何條件成立,嘗試提供代理服務將會擲回例外狀況:
- 所提供服務的Moniker與已註冊服務) (名稱和版本並不完全相符。
- 已針對相同的服務 Moniker 提供處理站。
通話 IBrokeredServiceContainer.Proffer 的結果是 IDisposable。 處置此值之後,新的要求將無法使用代理服務。 當您的代理服務對某些內容具有特定的親和性,例如開放式解決方案時,可能只適合在該內容處於作用中狀態時才提供代理服務。 當您的套件處置時,不需要保留和處置此值。
追蹤客戶端與服務之間的 RPC
建立客戶端與服務之間的連線之後,追蹤其通訊會很有用,特別是當它們位於不同的程式時。
根據預設,跨進程之代理服務之間的通訊追蹤會 (RPC 套用) 會記錄在目錄中找到 的 .svclog 檔案中 %TEMP%\VSLogs
。 這些 xml 檔案最適合使用 服務追蹤查看器來檢視。 此工具可以一次開啟許多 .svclog 檔案,並將它們拼接在一起以形成多方圖形,讓您更容易瞭解用戶端與服務之間的 RPC。
代理服務本身可以直接追蹤,以新增至這些 .svclog 追蹤檔案,進一步協助診斷代理服務行為。 叫用 [回報問題] 命令,且使用者選擇共享記錄時,可能會收集儲存到 %TEMP%\VSLogs
的任何追蹤。
若要追蹤您自己的訊息,以便輕鬆地探索並結合其他 .svclog 追蹤,您的程式代碼 (代理服務是否) 可以執行如下的動作:
// Define your log's ID, a namespace-like fully qualified name.
// In general it is expected that you follow you team's assembly namespace.
// Also an optional parameter, the ServiceMoniker for your service
var myLogId = new LogId("Microsoft.SomeTeam.MyLogName", serviceId: null);
var requestedLevel = new LoggingLevelSettings(SourceLevels.Warning | SourceLevels.ActivityTracing);
var myLogOptions = new LoggerOptions(requestedLevel, PrivacyFlags.MayContainPrivateInformation);
TraceSource myTraceSource;
using (TraceConfiguration traceConfig = await TraceConfiguration.CreateTraceConfigurationInstanceAsync(serviceBroker, ownsServiceBroker: false, cancellationToken))
{
myTraceSource = await traceConfig.RegisterLogSourceAsync(myLogId, myLogOptions, traceSource: null, cancellationToken);
}
myTraceSource
現在可用於追蹤,因為它已新增適當的接聽程式,以將追蹤寫入 .svclog 檔案。 如果您已經有 TraceSource 想要使用的 ,請將它傳遞至 RegisterLogSourceAsync 方法,並捨棄結果,因為接聽程式會新增至現有的 TraceSource。
從服務遠端用戶端的代理服務進行追蹤時,系統會自動將活動指派給 ExecutionContext 程式代碼執行所在的 ,讓 svclog 與用戶端的 svclog 一起拼接,以便使用 服務追蹤查看器查看整體檢視。