使用依赖型产生编译错误

问题描述:

用例:编写一个通用的功能像使用依赖型产生编译错误

def tenantFilterQuery[T, Q <: Table[T]](t: Q, e: TableQuery[Q], id: Int)(implicit s: Session) :Query[Q,Q#TableElementType,Seq] = { 
    e.filter(_.tenantId === id) 
} 

我想补充编译时情报,e.filter(_.tenantId === id)过滤器应只应用于如果通过T有一个名为tenantId属性否则它不会应用该过滤器,如果T没有该属性。

这可以解决与依赖路径类型有或没有使用无形?

第二步试图拿出其中,当最后Query由一种方式,如果T一直属性命名tenantId它会在编译时失败,如果没有filtertenantId它。想一想第一个问题,我应该为这个问题创建一个单独的问题。

第二个问题是更容易的一个:你可以使用结构类型T <: {def tenantId: Int},然后只能用这样的T来调用它。

如果你想过滤器发生这些类型,而不是发生另一种类型,我想你可以通过提供一个隐式助手做到这一点?喜欢的东西:

sealed trait Helper[T]{ 
    def applyToQuery[Q <: Table[T]](e: TableQuery[Q]): TableQuery[Q] 
} 
trait LowPriorityHelper { 
    implicit def withoutTenantId[T] = new Helper[T] { 
    def applyToQuery[Q <: Table[T]](e: TableQuery[Q]): TableQuery[Q] = e 
    } 
} 
object Helper extends LowPriorityHelper { 
    implicit def withTenantId[T <: {def tenantId: Int}] = 
    new Helper[T] { 
     def applyToQuery[Q <: Table[T]](e: TableQuery[Q]): TableQuery[Q] = 
     e.filter(_.tenantId === id) 
    } 
} 

def doQuery[T: Helper] = { val e = ...; implicitly[Helper[T]].applyToQuery(e)...} 

withTenantIdHelperT具有tenantIdwithoutTenantId一个,否则将被传递。

+0

我不知道你正在使用这个数据库库,但它看起来像你需要'Q'包含'tenantId'。相同的技术应该可以工作。 – lmm 2014-11-25 08:01:21