架构中的服务层 - DLL?

时间:2015-11-28 19:06:15

标签: c# .net wcf dll architecture

我们处于.Net的中型/大型应用程序的早期设计阶段,对于一个内部有三个不同客户端(站点)(一个在单独的域中)连接的系统,以及作为很多外部服务。

我们现在专注于连接的内部网站,我正在提出一个经典的分层应用,包括接口层,服务层,业务逻辑层和数据访问层。

enter image description here

在图像中,我们有一个连接到MVC应用程序的浏览器。控制器具有对服务项目的引用(将为每个"业务区"可能。例如," PersonService")。 MVC将直接引用此服务项目。在服务层中,还会有一些WCF项目,将某些功能暴露给外部源,其他内部站点和服务等。

但是,WCF项目将连接到主服务DLL以从中获取共享功能。

然后,Service项目直接引用Business项目,其中包含所有业务逻辑。然后它引用了数据访问项目,该项目具有/某些实体框架模型作为SQL Server数据库的ORM。

SharedLib只是一个所有图层引用的项目,包含任何共享逻辑,但主要用于DTO(数据传输对象)。 EF模型被转换为数据层中的DTO,因为没有其他层参考EF模型。

但MVC应用程序,通过应用程序中的直接引用连接到服务层,以及将WCF服务暴露给外部源和跨域内部站点。

我们遇到的问题是服务层。我认为这应该是一个DLL,其他人说,如果没有WCF,那么表示应该直接连接到业务逻辑层。他们问,为什么在这里添加服务DLL的额外层和复杂性?'。

消除演示文稿所能提供的服务层是一种好习惯吗?直接连接到逻辑?我看到服务层的好处是增加了业务和表示的明确隔离,允许扩展。它确实看起来像是通过dll,但直接连接到BL看起来很奇怪。

是否存在使用DLL的pro / con,这样可以保持/不保留它?

2 个答案:

答案 0 :(得分:5)

当我看到图片中MVVM模式的提示时,我会认为是这种情况,但它不应该对答案产生真正的影响。

我不会得到完美的答案,但不要认为应该直接访问业务层。

我认为界面所需的任何功能都应该可以通过视图模型中的命令访问,这些命令使用可用的服务来执行他们的任务。

我看到它的方式,业务层将是业务规则,例如创建发票时的公式和预算映射。产生P.O.的另一个例子。号。

另一方面,发票服务将负责应用您拥有的不同业务规则,以生成,修改等(管理)您的发票。

当不需要太复杂时,我经常看到的是业务层将隐式包含在服务层中。

将服务层编译为DLL的最大优点是它们可以由应用程序的不同部分共享(例如前端和后端)。例如,如果你使用ASP.net来构建前端,那么能够共享服务将是一个优势,但如果你使用像angular.js这样的东西,那么很明显它们将无法使用合乎需要的。

我还看到了一些WebAPI的暗示,这是将客户端接口与基于服务器的后端分离的最新趋势。此模式通常意味着客户端不了解您的业务逻辑或您的后端。发送HTTP请求以执行操作,API根据操作(GET与POST)以确认或数据进行响应。

至于WCF部分,我对它不太熟悉,我个人使用RabbitMQ。

总而言之,我希望我的咆哮能给你一些思考并帮助你做出决定。

由于这是一个C#.net问题,我想我可以放心地认为你的解决方案将在visual studio中创建。就个人而言,如果有足够的目的将服务与业务逻辑分开,我会毫不犹豫地向我的解决方案添加一个额外的库项目,并添加对需要它的项目的引用。它根本不会增加很多开销,因为大部分都是由visual studio管理的(或者在自动构建时在命令行中使用msbuild)。

如前一段所述,我将在我的解决方案中创建库项目,因为管理它并不太复杂。它实际上将促进适当的名称空间管理作为一个小额奖金。

我不认为你们应该害怕拥有更多的dll(再次取决于项目的规模)。如果您考虑一下,每次在项目中添加nuget包时,您实际上都依赖于另一个dll。

答案 1 :(得分:1)

我不打算解决服务交付层之上的任何问题;如何将服务结果传递给浏览器应该在服务层的设计中保持中立。我们目前使用AngularJS完全使用客户端UI,效果非常好。

对我而言,拥有图层主要是为了允许抽象并允许用其他东西替换图层,或修改图层的实现方式而不重写所有内容。所以在我的设计中,彼此叠加的层次;所以服务层应该只使用存储库,存储库是唯一引用域模型/核心业务逻辑的地方。

在过去的4年里,我一直在研究一个相当大的系统。我们开始使用Windows Worfklow,WCF和MVC.Net。我们在第一次修订(大约6个月)之后就停止使用Workflow和WCF - WCF只添加了编码的复杂性和乏味。一旦我们弄清楚如何正确实施它,工作流程仍然在我们的重新包装列表中。我们在每个DLL中使用我的Emesary消息传递系统,并使用EmesaryMSMQ桥接器允许多台机器提供服务。 Emesary允许您在项目中拥有基于接口的通知系统 - 并且该桥允许您将某些通知(可靠地通过MSMQ)桥接到其他进程。无论使用何种方法,正确设计协议都非常重要。

我们拥有自己的私人nuget存储库 - 我希望我们这样开始只是因为它真正关注设计过程并确保可替换性。目前,我们有一个由IUnitOfWorkManager和IAuthorisationMediator提供的IUnitOfWork,它提供基于Reference Monitor的对象级安全性。我花了一天左右的时间习惯使用NuGet,但这是一项很好的投资。

最后我建议不要使用EF。虽然额外的费用,我建议使用dataobjects.net(我不是以任何方式附属,除非作为一个非常快乐的用户)。 最初我们选择了dataobjects.net,因为它首先是代码。我在2012年重新评估了EF(代码优先),NHibernate和其他一些ORM - 我们继续使用dataobjects.net,因为它是最容易编码并具有最佳性能(对我们而言)。我不想过多地讨论ORM的主题,所以我最后会说我们最近将EF用于另一个项目 - 我们都希望我们不会使用它。

Standard service design

1当时我们确实认识到它是由dataobjects.net的创建者部分推广的,但我们的测试结果在很大程度上与他们一致。