依赖注入新手,但到目前为止,我喜欢它。使用接口设置我的所有服务,这样我就可以模拟单元测试的服务,这一切都很好。
我已经来到了一个部分,我在一个服务中有一个功能,我需要从另一个服务访问。注入整个服务只是为了访问那个函数吗?
我的模块服务中有删除功能(标记为删除),我还需要删除该模块的所有相关页面。由于用户也可以删除页面,我已将所有页面代码放在PageService中,并将任何内容放入ModuleService中的模块中。这是在一个地方,我不必重新键入每个服务中的代码。我在实际代码中提供的不仅仅是这两项服务。
所以这是我的例子
public interface IModuleService
{
Task<int> DeleteAsync(Module entity);
Task<int> DeleteAsync(Module entity, bool saveChanges);
}
public interface IPageService
{
Task<int> DeleteAsync(Page entity);
Task<int> DeleteAsync(Page entity, bool saveChanges);
}
public ModuleService : IModuleService
{
public Task<int> DeleteAsync(Module entity)
{
return DeleteAsync(entity, true);
}
public async Task<int> DeleteAsync(Module entity, bool saveChanges)
{
foreach (var page in entity.Pages)
await _pageService.DeleteAsync(page);
entity.IsDeleted = true;
if (saveChanges)
return await _context.SaveChangesAsync();
else
return await Task.FromResult<int>(1);
}
private IDbContext _context;
private IPageService _pageService;
public ModuleService(IDbContext context, IPageService pageService)
{
_context = context;
_pageService = pageService;
}
}
public PageService : IPageService
{
public Task<int> DeleteAsync(Page entity)
{
return DeleteAsync(entity, true);
}
public async Task<int> DeleteAsync(Page entity, bool saveChanges)
{
// you can see that i have injected yet another service into this
foreach (var item in entity.Children)
await _itemService.DeleteAsync(item);
entity.IsDeleted = true;
if (saveChanges)
return await _context.SaveChangesAsync();
else
return await Task.FromResult<int>(1);
}
private IDbContext _context;
private IItemService _itemService;
public PageService(IDbContext context, IItemService itemService)
{
_context = context;
_itemService = itemService;
}
}
现在,用户可以通过调用
删除模块_moduleService.DeleteAsync(myModule);
它还将删除所有相关页面,并且每个页面都相关项目并调用SaveChangesAsync一次,所以它全部在1个事务中。
用户还可以通过调用
删除页面_pageService.DeleteAsync(myPage);
它还会删除所有相关项目,并再次调用SaveChangesAsync。
这是使用依赖注入的正确方法吗?注入整个服务,以便我可以访问1个方法?
答案 0 :(得分:1)
至于我,你可以为一个函数注入整个(但很少)的服务。但我建议你设置cascade delete = true如果可能的话。在这种情况下,您可以删除大量代码,也许在这个示例中根本不需要依赖注入。
<强>更新强>
如果将模块和页面存储在数据库中,则可以为module-&gt;页面外键设置CascadeDelete = true选项。在这种情况下,如果删除适当的模块,数据库将自动删除所有页面。页面和它的孩子也一样。至少你可以删除这段代码
foreach (var page in entity.Pages) await _pageService.DeleteAsync(page);
这foreach (var item in entity.Children) await _itemService.DeleteAsync(item);
因此,您不再需要_pageService
和_itemService
个变量,因此根本不需要依赖注入