You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

C#中如何将捕获的异常存入List并继续执行?(Selenium测试场景)

没问题!刚好我之前做Selenium自动化测试时也遇到过一模一样的需求——希望单个步骤出错不中断整个流程,最后统一查看所有异常。我来帮你把这个实现捋清楚,包括完善你的异常存储类、捕获示例,以及如何让程序继续执行的关键点。

实现捕获异常并存储到List的方案

1. 先完善你的ExceptionsList类

你最初的静态List思路是对的,但为了更安全、更符合编码规范,建议做一点封装,尤其是考虑到Selenium测试可能涉及多线程的情况,加个线程锁很有必要。这里给你一个更健壮的版本:

public static class ExceptionsList
{
    // 用私有字段封装列表,避免外部直接修改
    private static readonly List<Exception> _exceptionList = new List<Exception>();
    // 线程锁:如果你的测试是多线程执行,防止并发操作列表导致异常
    private static readonly object _lockObj = new object();

    // 添加异常的公共方法
    public static void AddException(Exception ex)
    {
        lock (_lockObj)
        {
            _exceptionList.Add(ex);
            // 不管是系统异常还是你自己的自定义异常,都能直接加进来,因为自定义异常继承自Exception
        }
    }

    // 获取所有异常的方法(返回新列表,避免外部篡改原数据)
    public static List<Exception> GetAllExceptions()
    {
        lock (_lockObj)
        {
            return new List<Exception>(_exceptionList);
        }
    }

    // 可选:清空列表的方法,比如每个测试用例执行前重置
    public static void ClearExceptions()
    {
        lock (_lockObj)
        {
            _exceptionList.Clear();
        }
    }
}

2. 捕获异常并存储的具体示例(适配Selenium场景)

单个测试步骤的捕获

比如你要执行一个Selenium操作,担心找不到元素或者超时,就用try-catch包裹,捕获后只存异常不抛出:

IWebDriver driver = new ChromeDriver();

try
{
    // 你的Selenium操作:比如查找并点击按钮
    IWebElement submitBtn = driver.FindElement(By.Id("submit-btn"));
    submitBtn.Click();
}
catch (NoSuchElementException ex) // 可以先捕获Selenium特定异常,更精准
{
    ExceptionsList.AddException(ex);
    Console.WriteLine($"找不到元素:{ex.Message}"); // 可选:加日志方便实时排查
}
catch (Exception ex) // 兜底捕获其他所有异常
{
    ExceptionsList.AddException(ex);
    Console.WriteLine($"执行出错:{ex.Message}");
}

// 这里的代码会继续执行,不会因为上面的异常中断
Console.WriteLine("继续执行下一个测试步骤...");

批量测试步骤的循环处理

如果有一堆测试步骤要执行,循环里给每个步骤都套try-catch,这样一个步骤失败不影响其他:

// 假设这是你的测试步骤集合,每个步骤都是一个Action
var testSteps = new List<Action>
{
    () => driver.FindElement(By.Id("username")).SendKeys("test-user"),
    () => driver.FindElement(By.Id("password")).SendKeys("wrong-password"),
    () => driver.FindElement(By.Id("login")).Click(),
    () => driver.FindElement(By.Id("dashboard-header")).Displayed
};

foreach (var step in testSteps)
{
    try
    {
        step.Invoke(); // 执行当前测试步骤
    }
    catch (Exception ex)
    {
        ExceptionsList.AddException(ex);
        Console.WriteLine($"步骤执行失败:{ex.Message}");
    }
}

// 所有步骤执行完后,统一查看捕获的异常
var allExceptions = ExceptionsList.GetAllExceptions();
if (allExceptions.Any())
{
    Console.WriteLine($"\n总共捕获到 {allExceptions.Count} 个异常:");
    foreach (var ex in allExceptions)
    {
        Console.WriteLine($"- 异常类型:{ex.GetType().Name},消息:{ex.Message}");
        // 要是需要看堆栈信息排查问题,可以加一行:Console.WriteLine(ex.StackTrace);
    }
}

3. 如何阻止异常抛出,让程序继续执行?

核心非常简单:在catch块里不要写throw相关的语句!

  • 不要写throw;(这会重新抛出原异常,保留堆栈信息,程序会中断)
  • 不要写throw ex;(这会抛出异常但丢失原堆栈信息,同样会中断)
  • 只要在catch里只做存储异常、打日志这类操作,不抛出异常,程序就会自动继续执行后续代码。

4. 自定义异常的处理

你已经创建了自定义异常类,那存储起来和普通Exception完全一样,因为自定义异常肯定是继承自Exception的。比如你的自定义异常是这样的:

public class CustomTestException : Exception
{
    public CustomTestException(string message) : base(message) { }
    public CustomTestException(string message, Exception innerException) : base(message, innerException) { }
}

捕获并存储的代码和普通异常没有区别:

try
{
    // 模拟抛出自定义异常
    throw new CustomTestException("自定义测试异常:用户名格式不正确");
}
catch (CustomTestException ex)
{
    ExceptionsList.AddException(ex);
}

这样所有类型的异常都能被统一存储到列表里,最后统一分析。

内容的提问来源于stack exchange,提问作者user5199

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.28 09:58:55