我们在数据库开发中,一般会运用软删除 (soft delete)模式 ,即不直接从数据库删除数据 ,而是标记这笔数据为已删除。因此 ,如果实体被软删除了,那么它就应该不会在应用程序中被检索到。要达到这种效果 ,我们需要在每次检索实体的查询语句上添加 SQL的 Where条件 IsDeleted = false 。这是个乏味的工作 。但它是个容易被忘掉的事情。因此 ,我们应该要有个自动的机制来处理这些问题 。
ABP 提供数据过滤器 (Data filters),它使用 自动化的,基于规则的过滤查询。
 
ABP已做好的过滤器
ISoftDelete
publicclass Person : Entity, ISoftDelete
{
publicvirtualstring Name { get; set; } publicvirtualbool IsDeleted { get; set; }
}

如上面的Person类,实现了ISoftDelete接口,当我们使用IRepository.Delete方法删除一个Person时,该Person并不真的从数据库删除,仅仅是IsDeleted属性被设置为true。

publicclass MyService
{
privatereadonly IRepository<Person> _personRepository; publicMyService(IRepository<Person> personRepository)
{
_personRepository = personRepository;
} public List<Person> GetPeople()
{
return _personRepository.GetAllList();
}
}
GetPeople method only gets Person entities which has IsDeleted = false (not deleted). All repository methods and also navigation properties properly works. We could add some other Where conditions, joins.. etc. It will automatically add IsDeleted = false condition properly to the generated SQL query.

如上面代码,如果某个Person已经被软删除,那么使用IRepository获取所有Person数据时,过滤器会自动过滤掉已经软删除的Person,也就是说,GetAll不是获取实际上数据库还存有的所用Person数据,而是排除了之前被软删除的数据了。

A side note: If you implement IDeletionAudited (which extends ISoftDelete) then deletion time and deleter user id are also automatically set by ASP.NET Boilerplate.
 
IMustHaveTenant
publicclass Product : IMustHaveTenant
{
publicvirtualint TenantId { get; set; } publicvirtualstring Name { get; set; }
}

如果你创建了一个多租户的应用程序(储存所有租户的数据于单一一个数据库中),你肯定不会希望某个租户看到其他租户的资料,此时你可以实现IMustHaveTenant接口。

ABP会使用IABPSession来取得当前TenantId并且自动地替当前租户进行过滤查询处理。
If current user is not logged in to the system or current user is a host user (Host user is an upper level user that can manage tenants and tenant datas), ASP.NET Boilerplate automatically disables IMustHaveTenant filter. Thus, all data of all tenant's can be retrieved to the application. Notice that this is not about security, you should always authorize sensitive data.
 
IMayHaveTenant
publicclass Product : IMayHaveTenant
{
publicvirtualint? TenantId { get; set; } publicvirtualstring Name { get; set; }
}
If an entity class shared by tenants and the host (that means an entity object may be owned by a tenant or the host), you can use IMayHaveTenant filter.

IMayHaveTenant接口定义了TenantId,但是注意它是int?类型,可为空。

null value means this is a host entity, a non-null value means this entity owned by a tenant which's Id is the TenantId. ASP.NET Boilerplate uses IAbpSession to get current TenantId. IMayHaveTenant filter is not common as much as IMustHaveTenant. But you may need it for common structures used by host and tenants.
 
禁用过滤器
var people1 = _personRepository.GetAllList();

using (_unitOfWorkManager.Current.DisableFilter(AbpDataFilters.SoftDelete))
{
var people2 = _personRepository.GetAllList();
} var people3 = _personRepository.GetAllList();
启用过滤器
也就是使用_unitOfWorkManager.Current.EnableFilter方法
 
设定过滤器参数
CurrentUnitOfWork.SetFilterParameter("PersonFilter", "personId", 42);
CurrentUnitOfWork.SetFilterParameter(AbpDataFilters.MayHaveTenant, AbpDataFilters.Parameters.TenantId, 42);
自定义过滤器
 

首先定义一个接口:

publicinterface IHasPerson
{
int PersonId { get; set; }
}

实现接口:

publicclass Phone : Entity, IHasPerson
{
[ForeignKey("PersonId")]
publicvirtual Person Person { get; set; }
publicvirtualint PersonId { get; set; } publicvirtualstring Number { get; set; }
}

重写DbContext类中的OnModelCreating 方法(用的EntityFramework.DynamicFilters,参考https://github.com/jcachat/EntityFramework.DynamicFilters):

protectedoverridevoidOnModelCreating(DbModelBuilder modelBuilder)
{
base.OnModelCreating(modelBuilder); modelBuilder.Filter("PersonFilter", (IHasPerson entity, int personId) => entity.PersonId == personId, 0);
}

"PersonFilter" is the unique name of the filter here. Second parameter defines filter interface and personId filter parameter (not needed if filter is not parametric), last parameter is the default value of the personId.

最后,我们要把过滤器注册到ABP的工作单元系统中,以下代码需要写在模块的Preinitialize方法里:

Configuration.UnitOfWork.RegisterFilter("PersonFilter", false);

First parameter is same unique name we defined before. Second parameter indicates whether this filter is enabled or disabled by default. After declaring such a parametric filter, we can use it by supplying it's value on runtime.

using (CurrentUnitOfWork.EnableFilter("PersonFilter"))
{
CurrentUnitOfWork.SetFilterParameter("PersonFilter", "personId", 42);
var phones = _phoneRepository.GetAllList();
//...
}
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

ABP的数据过滤器(Data Filters)的更多相关文章

  1. ABP(现代ASP.NET样板开发框架)系列之13、ABP领域层——数据过滤器(Data filters)

    点这里进入ABP系列文章总目录 基于DDD的现代ASP.NET开发框架--ABP系列之13.ABP领域层——数据过滤器(Data filters) ABP是“ASP.NET Boilerplate P ...

  2. ABP中的数据过滤器

      本文首先介绍了ABP内置的软删除过滤器(ISoftDelete)和多租户过滤器(IMultiTenant),然后介绍了如何实现一个自定义过滤器,最后介绍了在软件开发过程中遇到的实际问题,同时给出了 ...

  3. ABP理论学习之数据过滤器

    返回总目录 本篇目录 介绍 预定义过滤器 关闭过滤器 开启过滤器 设置过滤器参数 定义自定义过滤器 其他ORM 介绍 软删除模式通常用于不会真正从数据库删除一个实体而是仅仅将它标记为"已删除 ...

  4. ABP官方文档翻译 3.8 数据过滤器

    数据过滤器 介绍 预定义过滤器 ISoftDelete 何时使用? IMustHaveTenant 何时使用? IMayHaveTenant 何时使用 禁用过滤器 关于using语句 关于多租户 全局 ...

  5. ABP 配置全局数据过滤器

    ABP官方数据过滤的地址:https://aspnetboilerplate.com/Pages/Documents/Data-Filters 中文可以看这个:https://aspnetboiler ...

  6. 文章翻译:ABP如何在EF core中添加数据过滤器

    原文地址:https://aspnetboilerplate.com/Pages/Documents/Articles%5CHow-To%5Cadd-custom-data-filter-ef-cor ...

  7. 第一章、VUE-挂载点-实例成员-数据-过滤器-文本指令-事件指令-属性指令-表单指令-01

    目录 路飞项目 vue vue 导读 vue 的优势 渐进式框架 引入 vue 实例成员 - 挂载点 el js 对象(字典)补充 实例成员 - 数据 data 实例成员 - 过滤器 filters ...

  8. VUE-挂载点-实例成员-数据-过滤器-文本指令-事件指令-属性指令-表单指令-01

    目录 路飞项目 vue vue 导读 vue 的优势 渐进式框架 引入 vue 实例成员 - 挂载点 el js 对象(字典)补充 实例成员 - 数据 data 实例成员 - 过滤器 filters ...

  9. C# Web 数据注解Data Annotations、模型状态ModelState、数据验证

    C#中的模型状态与数据注解,为我们提供了很便利的请求数据的验证. 1. ModelState ModelState在进行数据验证的时候很有用的,它是: 1)验证数据,以及保存数据对应的错误信息. 2) ...

随机推荐

  1. ZooKeeper程序员指南(转)

    译自http://zookeeper.apache.org/doc/trunk/zookeeperProgrammers.html 1 简介 本文是为想要创建使用ZooKeeper协调服务优势的分布式 ...

  2. RabbitMQ介绍6 - 其它

    深入话题 Exchange实现路由的方法 http://www.rabbitmq.com/blog/2010/09/14/very-fast-and-scalable-topic-routing-pa ...

  3. .net 中生成二维码的组件

    http://qrcodenet.codeplex.com/

  4. Blackfin DSP(三):BF533 的EBIU接口之flash

    上一节谈了GPIO问题,是用BF561 ezkit进行说明的,这是因为561 ezkit上的GPIO是与LED直连的,讲解GPIO时不会涉及到其它问题,降低了复杂性.对于533,也采取同样的操作即可. ...

  5. 华为OJ题目:刷题

    题目描述: 新入职华为的小伙伴们都有在oj上面刷题的任务,共需要刷100道初级题,45道中级题,5道高级题,其中,做出来的高级题如果超标可以当初级或者中级题,做出来的中级题如果超标可以当初级题.每天, ...

  6. CSS3属性transition

    CSS3 Transitions 指定过渡 语法: transition: property duration timing-function delay;     参数一: transition-p ...

  7. host DNS 访问规则

    昨天站点一直出现302循环重定向问题,捣鼓了半天才解决,原来是hosts和dns配置问题. 注:当你的站点出现循环重定向时,首先应该关注的hosts以及dns配置,确保无误. 下面记录下相关知识点: ...

  8. lua 面向对象

    对象的特点是: 对象拥有自己的数据,两个对象即使数据完全相同,他们也是相互独立的: 对象之间可以共享对象的行为,也就是他们的方法是一致的: lua中的table就非常适合作为一个对象,可以在table ...

  9. 百度地图API示例之添加/删除工具条、比例尺控件

    代码 <!DOCTYPE html> <html> <head> <meta http-equiv="Content-Type" cont ...

  10. cs11_c++_lab1

    lab1.cpp #include "Point.hh" #include <iostream> #include <cmath> using namesp ...