【问题标题】:Custom Transformer for raw SQL query using NHibernate使用 NHibernate 进行原始 SQL 查询的自定义转换器
【发布时间】:2016-10-26 21:55:27
【问题描述】:

我有一个customerorders 的表,它与purchases 的表相关联。每个订单都可以有多次购买,这很奇怪,但想象一下,就好像您在结帐时分别为每件商品付款一样。每个订单都有客户姓名和日期,每次购买都有付款类型和总额。

我有一个很好的查询,只要您知道客户的姓名,您就可以找到他们最近的独特购买类型。

例如: 客户A一共下了3个订单,2个信用卡,1个现金。

我问数据库“A 的最新支付类型的唯一订单是什么?”数据库返回 2 个结果 - 最近的信用卡订单和 1 个现金订单。

这是查询:

String sqlQueryStr = $@"SELECT ee.PaymentType, ee.Total
FROM
(
            SELECT e.CustomerName, ee.PaymentType, ee.Total, MAX(e.Date) as MaxTimestamp
                FROM customerorders ee
                INNER JOIN purchases e ON e.Id=ee.OrderId WHERE CustomerName='{customerName}'
                GROUP BY 1, 2, 3
) AS sub
INNER JOIN purchases e ON e.Date = sub.MaxTimestamp AND e.CustomerName = sub.CustomerName
INNER JOIN customerorders ee ON ee.OrderId=e.Id AND ee.PaymentType = sub.PaymentType;"

ISQLQuery query = session.CreateSQLQuery(sqlQueryStr);
return query.SetResultTransformer(new AliasToBeanResultTransformer(typeof(Purchase)))
            .List<Purchase>();

这本身就很好用。客户 A 的结果如下,我得到了我想要的:

  1. 'PaymentType: Credit Total:100'
  2. 'PaymentType: Cash Total:50'

但是,现在我想做一些我不提供“customerName”的事情。我想以同样的方式获得每个人的

现在,如果您还记得我之前说过的话,Purchase 没有CustomerName。所以我不能只删除WHERE 并再使用变压器!

当我删除 'WHERE' 并为 e.CustomerName 添加额外的 SELECT 时,我使用查询在 MySQL 中获得此输出:

  1. 'CustomerName: A PaymentType: Credit Total:100'
  2. 'CustomerName: A PaymentType: Cash Total:50'
  3. 'CustomerName: B PaymentType: Credit Total:20'
  4. 'CustomerName: C PaymentType: Credit Total:15'

我正在考虑制作一个自定义转换器,但我不确定哪种转换器可以让我处理这种结果。它现在不仅仅是Purchase,它也有了名字。而且我可能希望它们正确组合在一起(而不是在不同的行上)?

【问题讨论】:

    标签: c# mysql nhibernate


    【解决方案1】:
    public sealed class CustomTransformer: IResultTransformer
        {
            public IList TransformList(IList collection)
            {
                return collection;
            }
    
            public object TransformTuple(object[] tuple, string[] aliases)
            {
                return new UniqueCustomerPurchase()
                {
                       CustomerName = (string)tuple[0],
                       PaymentType = (string)tuple[1],
                       Total = (uint)tuple[2]
                };
            }
        }
    

    这是我目前所拥有的。这似乎运作良好,但是,我希望有一种方法可以将 CustomerName 分组到 Purchases(paymentType & total) 列表中,而不必这样做。我最终不得不再次遍历该集合以将它们分组,如下所示:

    ISQLQuery query = session.CreateSQLQuery(sqlQueryStr);
    return query.SetResultTransformer(new CustomTransformer())
                .List<UniqueCustomerPurchase>()
                .GroupBy(cp => cp.CustomerName)
                .Select(g => new KeyValuePair(g.Key, g.Select(cp => cp));
    

    【讨论】:

      猜你喜欢
      • 2020-11-12
      • 2013-05-16
      • 2020-10-19
      • 2015-01-31
      • 2021-08-19
      • 1970-01-01
      • 2019-02-03
      • 2020-09-22
      • 1970-01-01
      相关资源
      最近更新 更多