Я использую System.Linq.Dynamic.Core v1.0.8.18
Я сокращаю объект, который у меня есть - я удалил теги JSON для сериализации / десериализации, а такжеКонструктор. Ниже приведен сокращенный класс для позиции в заказе.Обратите внимание, что этот объект десериализован из JSON, и цель «другого» словаря состоит в том, чтобы захватить любую пару имя / значение, которая явно не определена в объекте (которая работает точно так же, как и при тестировании и производстве):
public partial class OrderRequestItem
{
public string line_number { get; set; }
public decimal quantity { get; set; }
public string supplier_id { get; set; }
public string supplier_aux_id { get; set; }
public decimal unitprice { get; set; }
public string description { get; set; }
public string uom { get; set; }
public IDictionary<string, object> other;
public decimal extension
{
get
{
return unitprice * quantity;
}
}
public bool validated { get; set; }
public bool rejected { get; set; }
}
Я пытаюсь «разделить» заказ, используя следующий код на основе записи файла конфигурации JSON, в которой указываются поля, на которые следует разделить заказ (параметр 2):
private List<OrderRequest> SplitOrder(OrderRequest originalOrder, string[] orderSplitLineItemFields = null)
{
var retval = new List<OrderRequest>();
if (null == orderSplitLineItemFields || originalOrder.items.Count < 2) //Can't return more than one order if we don't have fields to split by, and we don't have at least 2 line items.
{
retval.Add(originalOrder);
}
else
{
var bareOrderHeader = (OrderRequest)originalOrder.DeepClone();
bareOrderHeader.items.Clear();
var firstLineItem = originalOrder.items[0];
var validOrderSplitLineItemFields = new List<string>();
var dynamicQueryBase = new List<string>();
int validFieldCount = 0;
foreach (var field in orderSplitLineItemFields)
{
if (firstLineItem.HasProperty(field))
{
validOrderSplitLineItemFields.Add(field);
dynamicQueryBase.Add(field + " = @" + validFieldCount++);
}
else if (null != firstLineItem.other[field])
{
validOrderSplitLineItemFields.Add("other[\"" + field + "\"]");
dynamicQueryBase.Add("other[\"" + field + "\"]" + " = @" + validFieldCount++);
}
}
if(validOrderSplitLineItemFields.Count<1) //Can't return more than one order if we don't have valid fields to split by.
{
retval.Add(originalOrder);
}
else //We have valid fields to split the order, so we might be able to return more than one order.
{
string distinctFields = String.Join(",", validOrderSplitLineItemFields);
var distinctFieldValues = originalOrder.items.AsQueryable().Select(distinctFields).Distinct();
var dynamicWhere = string.Join(" and ", dynamicQueryBase);
var originalLineItems = originalOrder.items.AsQueryable();
foreach (var distinctResult in distinctFieldValues)
{
var newOrderSplit = (OrderRequest)bareOrderHeader.DeepClone();
var results = originalLineItems.Where(dynamicWhere, distinctResult);
foreach (var lineitem in results)
{
newOrderSplit.items.Add(lineitem);
}
retval.Add(newOrderSplit);
}
}
}
return retval;
}
Поле, на которое я пытаюсь разделить, называется «required_delivery_date», которое правильно передается в функцию SplitOrder.Поскольку это не фактическое свойство OrderRequestItem, разделенный код проверяет (и фактически успешно) просматривает / находит словарную запись в свойстве «other» и соответственно добавляет поле в список динамических полей, по которым запрашивается- (Я делаю это так, потому что определенные свойства являются «обязательными», и я не смогу предсказать, какие дополнительные поля мы можем отправить в будущих заказах с другими покупателями).
У меня есть образецфайл заказа, который содержит 4 позиции.Все строки 1, 2, 3 имеют другое определенное значение ["required_delivery_date"] = 2018-09-29, а строка 4 имеет другое значение ["required_delivery_date"] = 2018-09-30.
На основекод, я бы ожидал вернуть два заказа, один с позициями 1-3, а другой только с строкой 4. Однако я на самом деле получаю обратно два заказа, один с одной строкой #1, а другой только с позицией № 4.Кажется, что строка
var results = originalLineItems.Where(dynamicWhere, distinctResult);
только когда-либо возвращает единственный результат, когда я запрашиваю словарь, являющийся членом OrderRequestItem.
Я бью себя здесь головой об стенув лучшую часть дня, и я не понимаю, почему я получаю только один результат, когда отладчик показывает мне, что в исходном списке элементов, которые я запрашиваю, больше совпадений.Я начинаю думать, что это ошибка в текущей версии System.Linq.Dynamic.Core.
Любая помощь / предложения приветствуются!Имейте в виду, что мне нужно использовать динамический linq, так как я буду постоянно иметь дело с новыми или измененными дополнительными полями в позициях - поэтому возврат к «обычному linq» здесь не вариант.