如何干净地编写抽象以与RESTful资源进行交互?

时间:2012-02-29 14:56:34

标签: oop design-patterns rest

我有一个运行良好的简单REST客户端。在我的应用程序代码中,我做了类似这样的事情:

restClient = new RestClient(configurationData)
restClient.get('/person/1') //Get Person
restClient.get('/equipment/auto/3') //Get an Auto
restClient.get('/house/7') //Get a House

效果很好,但事情变得越来越复杂,我想将应用程序代码与特定的资源位置分开。

我希望能够在服务周围编写一个包装器,它将存储资源位置,而不需要我将它们放在我的应用程序代码中。我希望我的代码看起来更像这样:

restClient = new RestClient(configurationData)
restClient.getPerson(1) //Get Person
restClient.getAuto(3) //Get an Auto
restClient.getHouse(7) //Get a House

我开始在我的RestClient类中添加这些包装器,但是它非常快速地膨胀,并且它认为抽象应该处于更高的级别。将资源特定信息与我的客户混合也感觉不对。

因此,我将RestClient子类化,并且每个资源都有自己的类。问题是现在我必须为每种不同的资源类型实例化一个新的客户端:

personRestClient = new PersonRestClient(configurationData)
personRestClient.get(1);
autoRestClient = new AutoRestClient(configurationData)
autoRestClient.get(3);
housesRestClient = new HousesRestClient(configurationData)
housesRestClient.get(7);

但现在我为每个Client创建了一个新的Resource类,我相当确定这是一件非常糟糕的事情。这也是一个痛苦,因为我必须将我的连接配置数据绑定到每个,当这应该只发生一次。

当我想为我的资源编写抽象时,我应该遵循一个好的示例或模式吗?我的基础RestClient工作正常,但我不喜欢将服务器端API位置放在我的应用程序代码中。但我也不想为每个想与之交互的资源实例化一个专门的客户端类。

2 个答案:

答案 0 :(得分:1)

我处于类似情况,并且我认为通过适当的抽象实现了良好的实现。无论我的解决方案是否是最佳实践,我都无法保证,但它相当轻巧。以下是我设计它的方法:

我的UI层需要调用我的REST服务,所以我创建了一个名为ServiceManagers.Interfaces.IAccountManager的抽象。该接口具有名为GetAccounts(Int64 userId)的方法。

然后我创建了一个实现此接口的Rest.AccountManager,并将其注入我的AccountController。 Rest.AccountManager包含REST细节(URL,get / post / put ...,参数等)。

所以,现在我的UI代码只需要调用accountManager.GetAccounts(userId)。你可以创建一个包罗万象的界面,这样你只有一个Get,但我觉得它不那么富有表现力。每个组件都有很多不同的接口(例如:PersonManager,HouseManager,AutoManager),因为每个组件都是一个返回不同数据的独立关注点。只要您的名字具有表现力,就不要害怕拥有大量的接口和类。

在我的示例中,我的UI为每个控制器都有一个不同的管理器,并且调用适当地适合每个控制器(即,AccountController的GetAccounts,PeopleController的GetPeople)。

此外,对于根配置数据,您可以使用configurationCreationFactory类等。这样,所有实现都具有适当的配置,核心逻辑在一个位置。

这可能很难解释,我知道我没有完成一份完美的工作,但希望这有点帮助。我会稍后再回过头来清理它,特别是如果你不明白我的观点:)

答案 1 :(得分:1)

我正在考虑这样的事情,再次将你的终点映射到客户端。您可以将映射作为xml或属性文件,可以在应用程序启动期间加载和缓存。该文件应具有键值对 PERSON_ENDPOINT = /人/ AUTO_ENDPOINT = /设备/汽车/ ... 客户端应该将此密钥传递给工厂可能是ClientFactory,它具有此xml缓存并从缓存文件中检索端点。参数可以作为自定义对象或地图传递给工厂。工厂给出了完整的结束点“/ person / 1”,您可以将其传递给您的客户。这样您就不需要为客户端提供不同的类。如果您不喜欢xml或文件,可以将其作为具有键值对的静态地图。如果它是一个xml或文件,那么每次这样做都不需要更改代码。 希望这会对你有所帮助。