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

C#中如何禁止外部创建子类实例同时允许跨程序集测试?

解决方案

1. 调整核心类型定义,消除基类与子类的耦合

保留Result的internal构造函数,禁止外部程序集随意继承或实例化子类,不在基类中添加任何直接创建子类的静态方法:

public abstract class Result
{
    internal Result() { }
}

internal class SuccessResult : Result { }

internal class FailureResult<TError> : Result
{
    public TError Error { get; init; }
}

2. 保留原有工厂权限控制逻辑

工厂接口保持不变,你自己的内部代码实现工厂逻辑,根据业务场景给用户返回对应权限的工厂实例,生产环境下用户只能通过你提供的工厂创建Result实例:

public interface IPartialResultFactory
{
    Result Success();
}

public interface IResultFactory : IPartialResultFactory
{
    Result Error<TError>(TError error);
}

// 内部实现,不对外暴露
internal class ResultFactory : IResultFactory
{
    public Result Success() => new SuccessResult();
    public Result Error<TError>(TError error) => new FailureResult<TError> { Error = error };
}

这个设计下,如果你给用户返回的是IPartialResultFactory实例,用户只能调用Success方法,完全无法创建错误类型的Result,符合你限制创建权限的需求。

3. 单独提供测试专用创建入口

在你的类库中新增独立的YourLibrary.Testing命名空间,在该命名空间下提供仅用于测试的工厂,明确标注生产环境禁用:

namespace YourLibrary.Testing
{
    /// <summary>
    /// 仅用于单元/集成测试的Result创建工具,生产代码禁止使用
    /// </summary>
    [Obsolete("此类型仅用于测试场景,生产代码使用会触发编译警告/错误", false)]
    public static class TestResultFactory
    {
        public static Result CreateSuccess() => new SuccessResult();
        public static Result CreateFailure<TError>(TError error) => new FailureResult<TError> { Error = error };
    }
}

如果需要完全阻断生产环境误用,可以给方法加上[Conditional("TEST")]特性,只有测试项目定义了TEST常量时,方法才会生效,生产代码调用会直接编译报错。

方案优势

  • 完全消除了Result基类和子类的耦合,后续新增子类只需要修改对应工厂实现即可,基类不需要做任何调整
  • 生产环境下公开API没有额外的创建入口,用户无法绕开你提供的工厂权限限制
  • 测试代码只要引用YourLibrary.Testing命名空间,就能自由创建需要的Result实例完成集成测试

内容的提问来源于stack exchange,提问作者Jake Conkerton-Darby

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.10.06 08:24:02