在DoWork Backgroundworker方法结束时未处理TargetInvocationException



这里是DoWork:

private void uploadWorker_DoWork(object sender, DoWorkEventArgs e)
        {
            uploadWorker.ReportProgress(20);
            int tiffError = 0;
            finalFiles = Directory.GetFiles(AppVars.FinalPolicyImagesFolder);
            foreach (string file in finalFiles)
            {
                if (!file.EndsWith(".tiff"))
                {
                    tiffError = 1;
                    break;
                }
            }
            uploadWorker.ReportProgress(50);
            if (tiffError == 1)
            {
                MessageBox.Show("There are files in this folder that are not .tiff. Please ensure only .tiff files are in this folder.", "Error!", MessageBoxButtons.OK, MessageBoxIcon.Error);
            }
            else
            {
                if (finalFiles.Length == 0)
                {
                    MessageBox.Show("There are no TIFF files to be uploaded. Please generate files first.", "Error!", MessageBoxButtons.OK, MessageBoxIcon.Error);
                    pbUpload.Value = 0;
                    EnableAllButtons();
                }
                else
                {
                    double count = finalFiles.Length;
                    int current = 0;
                    int pbValue = 0;
                    uploadWorker.ReportProgress(70);
                    foreach (string file in finalFiles)
                    {
                        current = current + 2;
                        if (file.Contains(".tiff") == true)
                        {
                            PolicyNumber = Path.GetFileName(file).Split('_')[0];
                            basePolicyNumber = PolicyNumber.Remove(PolicyNumber.Length - 2);
                            basePolicyNumber = basePolicyNumber + "00";
                            finalPolicyName = Path.GetFileName(file);
                            PolicyUUID = Transporter.GetPolicyUUID(AppVars.pxCentralRootURL, basePolicyNumber);
                            if (PolicyUUID == "")
                            {
                                MessageBox.Show("The InsightPolicyID for the policy you are trying to upload does not exist in ixLibrary. Please ensure the policy number is correct. If you are sure it should be in ixLibray, please contact IT.", "Error!", MessageBoxButtons.OK, MessageBoxIcon.Error);
                            }
                            else
                            {
                                ixLibrarySourceFileURL = AppVars.ixLibraryPolicyAttachmentsURL + finalPolicyName;
                                UploadToixLibraryErrorCode = Transporter.UploadFileToixLibrary(AppVars.ixLibraryPolicyAttachmentsURL, file);
                                if (UploadToixLibraryErrorCode != 0)
                                {
                                    MessageBox.Show("There was an error uploading the file to ixLibrary. Please contact IT about this problem.", "Error!", MessageBoxButtons.OK, MessageBoxIcon.Error);
                                }
                                else
                                {
                                    GeneratePayLoadErrorCode = Transformer.GeneratePayLoad(ixLibrarySourceFileURL, finalPolicyName);
                                    if (GeneratePayLoadErrorCode != 0)
                                    {
                                        MessageBox.Show("There was an error generating the XML for pxCentral. Please contact IT about this problem.", "Error!", MessageBoxButtons.OK, MessageBoxIcon.Error);
                                    }
                                    else
                                    {
                                        pxCentralPOSTErrorCode = Transporter.pxCentralPOST(AppVars.pxCentralRootURL + PolicyUUID, AppVars.pxCentralXMLPayloadFilePath);
                                        pbValue = Convert.ToInt32(((current / count) * 30) + 70);
                                        uploadWorker.ReportProgress(pbValue);
                                    }
                                }
                            }
                        } 
                    }
                }
            }
        }

当它到达最后一个}时,我在这里得到TargetInvocationException是未处理的错误(请参阅代码中的注释):

static class Program
    {
        [STAThread]
        static void Main()
        {
            Application.EnableVisualStyles();
            Application.SetCompatibleTextRenderingDefault(false);
            bool createdNew = false;
            Mutex mutex = new Mutex(true, "MyApplicationMutex", out createdNew);
            if (createdNew == true)
            {
                //error happens here
                Application.Run(new frmMain());
            }
            else
            {
                MessageBox.Show("The application is already running.", Application.ProductName, MessageBoxButtons.OK, MessageBoxIcon.Exclamation);
            }
        }
    }

我不知道为什么会突然发生这种事。有人知道为什么吗?

最后,这里是RunWorkerCompleted:

private void uploadWorker_RunWorkerCompleted(object sender, RunWorkerCompletedEventArgs e)
        {
            if (e.Error == null)
            {
                DeleteFinalFiles(finalFiles);
                MessageBox.Show("Upload process complete.", "Complete!", MessageBoxButtons.OK, MessageBoxIcon.Information);
            }
            EnableAllButtons();
        }

您正在DoWork处理程序中调用EnableAllButtons。据推测,这会更改表单上按钮的Enabled状态。这对于UI线程之外的任何其他线程都是不合法的。您应该在ProgressChanged事件处理程序或RunWorkerCompleted事件处理程序中调用EnableAllButtons。您还在DoWork中调用ProgressBar.Value,代码为pbUpload.Value = 0

此外,您应该从UI线程(即在ProgressChangedRunworkerCompleted处理程序中)调用MessageBox.Show,以便MessageBox可以与表单消息泵属性关联。您应该将一个表单对象传递给MessageBox.Show以将消息框与表单关联起来,这样在显示消息框时就不能将表单带到前台。例如:

MessageBox.Show(this, 
    "There are files in this folder that are not .tiff. Please ensure only .tiff files are in this folder.", 
    "Error!", MessageBoxButtons.OK, MessageBoxIcon.Error);

在WinForms中,您只能访问创建控件的线程上的控件。您的DoWork事件处理程序没有在创建表单的线程上运行(这当然是重点)。因此,您不能在DoWork处理程序中访问表单上的任何控件。这样做可能会产生不可预测的结果。

我在后台进程完成后遇到了与TargetInvocation Exception完全相同的问题。在backgroundWorker ProgressChanges事件中,我引用了如下所示的控件`private void m_oWorker_ProgressChanged(object sender,ProgressChangedEventArgs e){

       // This function fires on the UI thread so it's safe to edit
       // the UI control directly, no funny business with Control.Invoke :)
       CurrentState state =
               (CurrentState)e.UserState;
       txtProgress.Text = state.CrawlStatus;
       lblStatus2.Text = state.sStatus;
       txtItemsStored.Text = state.TotItems.ToString() + " items";
       txtLastRunTime.Text = state.MostRecentGatherDate.ToString();
       AppNameKey.SetValue("LastCrawlTime", txtLastRunTime.Text);
   }`

DoWork事件从控制读取

private  void m_oWorker_DoWork(object sender, DoWorkEventArgs e)
   {
       DateTime LastCrawlTime;
       try
       {
         LastCrawlTime = Convert.ToDateTime(txtLastRunTime.Text);
        if (lblStatus2.Text != "Status: Running" || (!cmdRunNow.Enabled && cmdStopRun.Enabled)) // run is not currently running or cmdRunNow clicked
        {
            //lblStatus2.Text = "Status: Running";
            GetUpdated(LastCrawlTime,e);
        }
       }
       catch (Exception Ex)
       {
           MessageBox.Show(Ex.Message);
       }
   }

RunWorkedrCompleted事件写入控件:

void m_oWorker_RunWorkerCompleted(object sender, RunWorkerCompletedEventArgs e)
   {
        if (e.Cancelled)
       {
           lblStatus2.Text = "Status: Stopped";
           cmdStopRun.Enabled = false;
       }
       // Check to see if an error occurred in the background process.
       else if (e.Error != null)
       {
           lblStatus2.Text = "Fatal Error while processing.";
       }
       else
       {
           // Everything completed normally.
           //CurrentState state = (CurrentState)e.UserState;
           lblStatus2.Text = "Status: Finished";            
       }
   }

这些都没有造成问题。导致问题的原因是试图在RunWorker_Completed事件中引用e.UserState(如上所述)

我发现了这个问题。

进度条超过了允许的最大值(100)。

问题是,在代码中,我增加了进度条:

current = current + 2;

我将其替换为:

current++;

我之所以增加2只是为了测试的目的。

相关内容

  • 没有找到相关文章

最新更新