0

序言

本人从事分布式计算机系统,使用C#和.Net Remoting作为进程间通信技术编写,基本部署到客户内网环境。系统负责执行可能涉及多台物理计算机(一台或多台)的预配置任务。该系统是用Interfaces描述的,并且在任务代码中使用它们是透明的,因此它们中的一些是代理对象还是本地对象都没有关系 - 代码库位于单一位置。此外,该接口的实现在代码中的单一位置。这种方法的优点是,当您以某种方式更改接口时- 您可以在代码中反映这种更改。

要点是:

在单一代码库1中拥有服务合同及其实施很重要。

问题

至于现在,我需要以 REST 方式公开我们的服务,并使用它进行进程间通信。根据WCF 和 ASP.NET Web API(以及可能的其他原因),选择使用ASP.NET Web API。使用它,我们需要创建从 ApiController 继承的类。控制器将使用合约(接口),但不会实现它

public class ContractsController : ApiController
{
    private IContracts contractsRepository;

    public ContractsController(IContracts contractsRepository)
    {
        this.contractsRepository= contractsRepository;
    }
}

做出这个决定是因为我不希望合约包含 Http 特定的,比如IHttpActionResult,HttpResponseMessage等。同时我的控制器必须与它使用的合约兼容,因此对代理合约的调用必须正确路由到正确的另一端控制器的操作,它将调用合同的相同方法。这让我编写代码(实际上是单元测试)来验证合约和控制器是否同步。

我曾尝试通过 API 规范使用一些代码生成器,如swaggerraml,但生成的代码是……你知道,它适用于 hello-world 示例,而不适用于复杂的应用程序。即使使用模板驱动——生成优质代码也并不简单。

如果它是 WCF 服务 - 一切都会很棒,因为我们有[ServiceContract],服务器和客户端都是一样的。

例子

这里的示例可以演示 ApiController 和它使用的合约(接口)的同步问题(为简单起见,此处使用 if 语句)

private void LongRunningAction()
{
    IContract1 c1;
    IContract2 c2;
    if (/* contract1 belongs to local computer */)
    {
        c1 = container.Resolve<IContract1>();
    }
    else /* contract1 belongs to remote computer */
    {
        c1 = container.Resolve<IRemoteFactory>("RemoteComputerName").Resolve<IContract1>;
    }

    if (/* contract2 belongs to local computer */)
    {
        c2 = container.Resolve<IContract2>();
    }
    else /* contract2 belongs to remote computer */
    {
        c2 = container.Resolve<IRemoteFactory>("RemoteComputerName2").Resolve<IContract2>;
    }

    // Rest of the code will be the same because we operate with
    // interfaces, which could be either local objects or
    // proxy to the remote computer. Proxy objects will generate
    // the Http request, and it will be passed to the remote ApiController,
    // so the contracts and ApiControllers must be in sync.
}

问题

如何确保他们使用的控制器和合同(接口)是同步的?

使用哪种方法来避免这种不确定性?


1单一代码库并不意味着单一项目或单一程序集。

4

0 回答 0