0

我目前正在尝试选择一个 C# ORM 与我的 PostgreSQL 数据库一起使用,并且我对 micro-ORM 很感兴趣,因为它们让我能够更好地利用 Postgres 的强大功能(而且由于成熟的 ORM 很难配置。虽然 Dapper 可以正常工作,但尝试处理 NHibernate 却在我的屏幕上留下了前额形状的凹痕......)

无论如何,目前 PetaPoco 处于领先地位,但是我需要一个功能并且无法确定它是否具有(公平地说 - 我在其他 ORM 中也找不到它) - 自定义类型的映射。

我的 PostgreSQL 数据库使用定义自定义类型的 hstore 和 Postgis 扩展。我不希望任何 ORM 支持这些类型(很难找到支持 PostgreSQL 的类型!)但我希望能够为它们提供我自己的映射器,所以当我将它们作为列获取或作为参数发送时 PetaPoco将自动使用我的映射器。

这甚至可能吗?我能找到的最接近的是IDbParameter support,但这些是内置类型,我需要为不属于列表的扩展类型编写映射器......

4

1 回答 1

2

根据 Schotime 的评论,我提出了一半的解决方案 - 如何hstore将查询结果解析为对象。如果有人想获得其他解决方案,我将保留这个问题。

我需要定义自己的映射器。显然我想对常规类型使用 PetaPoco 的默认映射,所以继承是很自然的PetaPoco.StandardMapper——但这不起作用,因为StandardMapperimplementsPetaPoco.IMapper的字段没有virtual属性——所以我不能覆盖它们(我只能掩盖它们,但是这并没有真正的帮助)。

我所做的是IMapper直接实现,并将常规类型委托给以下实例PetaPoco.IMapper

public class MyMapper:PetaPoco.IMapper{
    private PetaPoco.StandardMapper standardMapper=new PetaPoco.StandardMapper();
    public PetaPoco.TableInfo GetTableInfo(Type pocoType){
        return standardMapper.GetTableInfo(pocoType);
    }
    public PetaPoco.ColumnInfo GetColumnInfo(PropertyInfo pocoProperty){
        return standardMapper.GetColumnInfo(pocoProperty);
    }
    public Func<object, object> GetFromDbConverter(PropertyInfo TargetProperty, Type SourceType){
        if(TargetProperty.PropertyType==typeof(HStore)){
            return (x)=>HStore.Create((string)x);
        }
        return standardMapper.GetFromDbConverter(TargetProperty,SourceType);
    }
    public Func<object, object> GetToDbConverter(PropertyInfo SourceProperty){
        if(SourceProperty.PropertyType==typeof(HStore)){
            return (x)=>((HStore)x).ToSqlString();
        }
        return standardMapper.GetToDbConverter(SourceProperty);
    }
}

HStore对象的构造类似于Schotime 的 gist中的对象。

我还需要注册映射器:

PetaPoco.Mappers.Register(Assembly.GetAssembly(typeof(MainClass)),new MyMapper());
PetaPoco.Mappers.Register(typeof(HStore),new MyMapper());

现在,当我从查询中读取时,所有这些都可以完美运行 - 但在我编写查询参数时(即使我定义GetToDbConverter了 . ?

于 2013-09-04T19:45:37.513 回答