ActiveX控件无法实例化,因为当前线程不在WebBrowser的单线程单元中

本文关键字:WebBrowser 单线程 单元 线程 前线 控件 实例化 因为 ActiveX | 更新日期: 2023-09-27 18:00:14

我想在Resharper test runner中的单元测试中调用以下代码。

    /// <summary>
    /// Function to return the OAuth code
    /// </summary>
    /// <param name="config">Contains the API configuration such as ClientId and Redirect URL</param>
    /// <returns>OAuth code</returns>
    /// <remarks></remarks>
    [STAThread]
    public static string GetAuthorizationCode(IApiConfiguration config)
    {
        //Format the URL so  User can login to OAuth server
        string url =
            $"{CsOAuthServer}?client_id={config.ClientId}&redirect_uri={HttpUtility.UrlEncode(config.RedirectUrl)}&scope={CsOAuthScope}&response_type=code";
        // Create a new form with a web browser to display OAuth login page
        var frm = new Form();
        var webB = new WebBrowser();
        frm.Controls.Add(webB);
        webB.Dock = DockStyle.Fill;
        // Add a handler for the web browser to capture content change 
        webB.DocumentTitleChanged += WebBDocumentTitleChanged;
        // navigat to url and display form
        webB.Navigate(url);
        frm.Size = new Size(800, 600);
        frm.ShowDialog();
        //Retrieve the code from the returned HTML
        return ExtractSubstring(webB.DocumentText, "code=", "<");
    }

当我这样做时,我得到以下错误

System.Threading.ThreadStateException : ActiveX control '8856f961-340a-11d0-a96b-00c04fd705a2' cannot be instantiated because the current thread is not in a single-threaded apartment.
   at System.Windows.Forms.WebBrowserBase..ctor(String clsidString)
   at System.Windows.Forms.WebBrowser..ctor()

ActiveX控件无法实例化,因为当前线程不在WebBrowser的单线程单元中

当我们在非UI线程上创建新Form时,会出现此问题。(线程可以从调试->Windows->线程部分进行验证)

我也遇到了同样的问题,经过分析,发现新表单是在一个新线程上创建的,而不是在邮件STA线程上。

为了解决这个问题,我调用了使用.NET System.Windows.Threading命名空间中的Dispatcher类创建新表单的方法,如下所示:

  var dispatcher = Dispatcher.CurrentDispatcher;
  dispatcher.Invoke(new Action(() =>
  {
  isConnectedSuccessfully = UserInfoService.Login();
  }));

从调度器调用您的方法,它将确保在同一个主UI线程上创建表单。

这为我解决了问题。:-)