Warning: file_get_contents(/data/phpspider/zhask/data//catemap/0/mercurial/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# MessageBox.偶尔显示don';捕获异常时不显示_C#_Visual Studio Extensions - Fatal编程技术网

C# MessageBox.偶尔显示don';捕获异常时不显示

C# MessageBox.偶尔显示don';捕获异常时不显示,c#,visual-studio-extensions,C#,Visual Studio Extensions,我正在用C#编写一个visualstudio扩展,在管理异常和显示错误消息方面出现了一种奇怪的行为。基本上,我只想在异常消息中添加一些细节,以帮助我在出现问题时进行调查 这一切都是从上下文菜单项上的一个命令开始的,我怀疑这可能与异步/等待机制背后的线程管理有关。但我不确定我的猜测是否正确,也无法找到任何解决方案。救命啊 它从我的菜单项回调开始: internal sealed class My_RunAnalysis { //... public static async Tas

我正在用C#编写一个visualstudio扩展,在管理异常和显示错误消息方面出现了一种奇怪的行为。基本上,我只想在异常消息中添加一些细节,以帮助我在出现问题时进行调查

这一切都是从上下文菜单项上的一个命令开始的,我怀疑这可能与异步/等待机制背后的线程管理有关。但我不确定我的猜测是否正确,也无法找到任何解决方案。救命啊

它从我的菜单项回调开始:

internal sealed class My_RunAnalysis
{
    //...
    public static async Task InitializeAsync(AsyncPackage package)
    {
        // Switch to the main thread - the call to AddCommand in PS_RunAnalysis's constructor requires
        // the UI thread.
        await ThreadHelper.JoinableTaskFactory.SwitchToMainThreadAsync(package.DisposalToken);

        OleMenuCommandService commandService = await package.GetServiceAsync((typeof(IMenuCommandService))) as OleMenuCommandService;
        Instance = new My_RunAnalysis(package, commandService);
    }

    //...
    private async void ExecuteAsync(object sender, EventArgs e)
    {
        try
        {
            await My_ViewModel.RunAnalysisAsync();
        }
        catch (Exception exc)
        {
            await ThreadHelper.JoinableTaskFactory.SwitchToMainThreadAsync(package.DisposalToken);

            MessageBox.Show(exc.Message, "Error", MessageBoxButtons.OK, MessageBoxIcon.Warning);
        }
    }
}

//...

class My_ViewModel
{
    async public static Task RunAnalysisAsync()
    {
        await My_Model.GetResultsListAsync();
    }
}

//...

class My_Model
    async public static Task GetResultsListAsync()
    {
        ResultsList = new My_ResultsList();

        var rawResultsList = await QueryServerAsync<RawResultsListResponse>("GET", My_Request.GetResults());

        //...
    }

    async public static Task<JsonResponse> QueryServerAsync<JsonResponse>(string method, 
        string request)
    {
        try
        {
            HttpResponseMessage response;

            switch (method)
            {
                case "GET":
                    response = await _httpClient.GetAsync(request);
                    break;
                case "POST":
                default:
                    StringContent httpContent = new StringContent("", Encoding.UTF8, "application/json");
                    response = await _httpClient.PostAsync(request, httpContent);
                    break;
            }

            if (!response.IsSuccessStatusCode) //<<<<<<CASE #1
            {
                throw new My_Exception(
                response.ReasonPhrase,
                "Exception while querying server for " + request);
            }

            string serializedJson = await response.Content.ReadAsStringAsync();
            // CASE #2>>>>>
            var jsonResponse = serializer.Deserialize<JsonResponse>(serializedJson); 

            return jsonResponse;
        }
        catch (Exception e)
        {
            throw new My_Exception(
                e.Message,
                "Exception while querying server for " + request);
        }
    }
内部密封类My\u运行分析
{
//...
公共静态异步任务InitializeAsync(异步包)
{
//切换到主线程-在PS_RunAnalysis的构造函数中调用AddCommand需要
//用户界面线程。
等待ThreadHelper.JoinableTaskFactory.SwitchToMainThreadAsync(package.DisposalToken);
OleMenuCommandService commandService=await package.GetServiceAsync((typeof(IMenuCommandService)))作为OleMenuCommandService;
实例=新的My_RunAnalysis(包、commandService);
}
//...
私有异步void ExecuteAsync(对象发送方,事件参数e)
{
尝试
{
等待My_ViewModel.RunAnalysisAsync();
}
捕获(异常exc)
{
等待ThreadHelper.JoinableTaskFactory.SwitchToMainThreadAsync(package.DisposalToken);
MessageBox.Show(exc.Message,“Error”,MessageBoxButtons.OK,MessageBoxIcon.Warning);
}
}
}
//...
将My_ViewModel分类
{
异步公共静态任务RunAnalysisAsync()
{
等待My_Model.GetResultsListAsync();
}
}
//...
我的课堂教学模式
异步公共静态任务GetResultsListAsync()
{
ResultsList=新建My_ResultsList();
var rawResultsList=await queryserver async(“GET”,My_Request.GetResults());
//...
}
异步公共静态任务QueryServerAsync(字符串方法,
字符串请求)
{
尝试
{
HttpResponseMessage响应;
开关(方法)
{
案例“GET”:
response=wait\u httpClient.GetAsync(请求);
打破
案例“职位”:
违约:
StringContent httpContent=newStringContent(“,Encoding.UTF8,“application/json”);
response=wait_httpClient.PostAsync(请求,httpContent);
打破
}

如果(!response.issucessStatusCode)/使用
等待JoinableTaskFactory.SwitchToMainThreadAsync();
切换到主线程
JoinableTaskFactory
异步包的成员。
如果仍然不起作用,试试看

public static void ShowMessageBox(string title, string text)
        {
            Microsoft.VisualStudio.Shell.ThreadHelper.ThrowIfNotOnUIThread();

            IVsUIShell uiShell = Microsoft.VisualStudio.Shell.ServiceProvider.GlobalProvider.GetService(typeof(SVsUIShell)) as IVsUIShell;
            Guid clsid = Guid.Empty;
            int result;
            Microsoft.VisualStudio.ErrorHandler.ThrowOnFailure(uiShell.ShowMessageBox(
                       0,
                       ref clsid,
                       title,
                       text,
                       string.Empty,
                       0,
                       OLEMSGBUTTON.OLEMSGBUTTON_OK,
                       OLEMSGDEFBUTTON.OLEMSGDEFBUTTON_FIRST,
                       OLEMSGICON.OLEMSGICON_INFO,
                       0,        // false
                       out result));
        }

我找不到任何关于MessageBox处理一个案例而不是另一个案例的解释。我最终使用FileStream.WriteAsync找到了一些日志解决方案。因此,所有内容都保持异步,我不必再使用MessageBox了。

您是否正在逐步完成创建
我的\u异常
的捕获过程,以及创建
My_Exception
?MessageBox与任何对话框一样,需要一个所有者窗口。该窗口保证位于其顶部,因此始终可见。如果不强制您指定所有者,则会有点太有用,它会在当前线程上拾取活动窗口。在该代码中,它会在当前线程上落下。调用是在线程池线程不拥有任何窗口。这使得桌面窗口成为所有者。它现在出现在VS主窗口后面的几率总是很高。嗨,Ed!谢谢你的回复。是的,我确认在这两种情况下我都可以单步执行捕获,在这两种情况下我也可以单步执行My_Exception构造函数。我不明白它为什么会工作!response.IsSuccessStatusCode而非序列化程序。反序列化异常。代码的相同部分与相同的上下文相同。有什么想法吗?嗨,Hans!谢谢你的回复。我了解你关于设置对话框所有者的详细信息。但它如何在!response.IsSuccessStatusCode而不是序列化程序上工作。反序列化异常?嗨!谢谢你的回复。我这两个都已初始化,没有更改:仍然失败,serializer.Deserialize上出现异常。UI将挂起10到15秒,MessageBox最终不会显示。还有其他想法吗?顺便说一句,使用ThrowifNotNuithRead()时,编译器失败,并显示以下消息:错误VSTHRD109:在异步或任务返回方法中,避免在不在主线程上时引发。请改为切换到所需的线程。我必须删除此行…已替换为Wait ThreadHelper.JoinableTaskFactory.SwitchToMainThreadAsync(package.DisposalToken)。是否与我的问题“在异步或任务返回方法中避免在不在主线程上时引发”有关?那么在异步或任务返回方法中处理异常的最佳实践是什么?因为我需要的方法确实会引发异常(serializer.Deserialize)…关于我发现的:,。我可以确认我确实在catch块中获取了异常,但问题仍然是,当从serializer.Deserialize获取异常时,我无法可靠地获取MessageBox显示。为什么它在case#1而不是case#2下工作?为什么我在case#1而不是case#2上的线程正确?