![]() |
#1 |
Участник
|
Как сделать хитрый фильтр?
Для каждой записи из custTrans может быть 0 или 1 запись в таблице CustDispute
Есть отчет, построенный по custTrans. Пользователи хотят видеть в диалоге отчета перечисление custVendDisputeStatus и иметь возможность выбрать несколько значений для фильтрации - соответственно, простым добавлением комбобокса (перечисления) в диалог не отделаешься. Но, если я по outerJoin добавлю к custTrans таблицу CustDispute , то при наложении фильтра custVendDisputeStatus::None пользователь по сути ожидает увидеть все записи из custTrans , которых нет в CustDispute, но получает пустую выборку, тк записей с custVendDisputeStatus::None в таблице CustDispute нет. Вопрос: как такое реализовать? Естественно, если бы не было требования , чтобы можно было выбрать неск значений из списка, можно было бы динамически добавлть CustDispute таблицу к запросу, если в фильтре указано значение , отличное от custVendDisputeStatus::None, но это,к сожалению, не мой случай(. AX2012 R2 |
|
![]() |
#2 |
Участник
|
при наложении фильтра по значению CustVendDisputeStatus::None вместо фильтрации по CustDispute менять outer join на notexists join?..
Хотя нет, если None может быть одним из нескольких выбранных значений, то так не получится - тут скорее нужен union-запрос. Последний раз редактировалось gl00mie; 02.10.2014 в 19:17. |
|
![]() |
#3 |
северный Будда
|
вместо комбо добавьте в создание диалога цикл по значениям комбо, для каждого значения выводите чекбокс. потом соберите чекбоксы и рассчитайте кверю
P.S. ну или замените диалог на форму
__________________
С уважением, Вячеслав |
|
![]() |
#4 |
Участник
|
|
|
![]() |
#5 |
Участник
|
Именно так, как Kuskov сказал, поэтому not exisst не подойдет
можно самой парсить range , убирать DS, а потом , в зависимости от значений в range,там добавляь DS обратно, если есть только range, который не None, если нету, то union и для только None- по nonExixts уже. Но муторно как-то ради такой простой задачи Последний раз редактировалось IKA; 02.10.2014 в 19:37. |
|
![]() |
#6 |
Боец
|
Приходилось решать такую задачу.
- Делаете View custTransDisputeView на базе Query, в которой линкуете custTrans и CustDispute по outerJoin. [У view будут поля CustTransRecId, Status] - В форму где нужен фильтр добавляете custTransDisputeView как дополнительный датасорс и джоините его с custTrans по innerJoin. [линкуете по полям CustTrans.RecId == custTransDisputeView.CustTransRecId]. Вот вкратце и всё. Последний раз редактировалось DSPIC; 02.10.2014 в 19:56. |
|
|
За это сообщение автора поблагодарили: Logger (3), IKA (1). |
![]() |
#7 |
Участник
|
Спасибище, попробую
|
|
![]() |
#8 |
Участник
|
А в случае outer join какое значение в аксаптовском View будет иметь поле Status для несуществующих строк CustDispute? Это будет значение по умолчанию соответствующего типа? Т.е. в случае enum (int) - это будет ноль? Тогда принципиально (ну и это на самом деле логично) чтобы custVendDisputeStatus::None имел именно такое значение. Так?
|
|
![]() |
#9 |
Боец
|
Да, скорее всего так и будет.
Цитата:
Вообще, в AX2012 появилась возможность во вьюхи добавлять вычисляемые поля. Таким образом, можно расширить поле статус, в зависимости от того, есть запись или нет - скажем [-1, 1, 0], а потом фильтровать по желанию. |
|
|
За это сообщение автора поблагодарили: AndyD (2). |
![]() |
#10 |
Участник
|
Цитата:
Сообщение от DSPIC
![]() Приходилось решать такую задачу.
- Делаете View custTransDisputeView на базе Query, в которой линкуете custTrans и CustDispute по outerJoin. [У view будут поля CustTransRecId, Status] - В форму где нужен фильтр добавляете custTransDisputeView как дополнительный датасорс и джоините его с custTrans по innerJoin. [линкуете по полям CustTrans.RecId == custTransDisputeView.CustTransRecId]. Вот вкратце и всё. А рейнж по Status точно преобразовывает значение 0 в NULL?
__________________
Axapta v.3.0 sp5 kr2 |
|
![]() |
#11 |
Участник
|
Не выйдет, если я правильно понял идею
На одном уровне юниона должен быть одинаковый уровень связи Т.е. в обоих ветках юниона должны возвращаться курсоры CustTrans и CustDispute из запроса У меня, в частности, был случай с юнионами, когда пришлось отказываться от референсов в пользу дисплейных методов, поскольку ядро лепило подзапрос только к одной ветке юниона и валилась ошибка сиквела
__________________
Axapta v.3.0 sp5 kr2 |
|
![]() |
#12 |
Участник
|
Цитата:
Можно использовать такую функцию на View X++: public static server str isNullExpression(str _expression) { return strFmt('COALESCE(T2.STATUS, %1)', int2str(CustVendDisputeStatus::None)); }
__________________
Axapta v.3.0 sp5 kr2 |
|
|
За это сообщение автора поблагодарили: S.Kuskov (2). |
![]() |
#13 |
Участник
|
Цитата:
Сообщение от DSPIC
![]() Приходилось решать такую задачу.
- Делаете View custTransDisputeView на базе Query, в которой линкуете custTrans и CustDispute по outerJoin. [У view будут поля CustTransRecId, Status] - В форму где нужен фильтр добавляете custTransDisputeView как дополнительный датасорс и джоините его с custTrans по innerJoin. [линкуете по полям CustTrans.RecId == custTransDisputeView.CustTransRecId]. Вот вкратце и всё. Если этот VIew открыть, то оно отображает данные правильно. Но вот накладывать фильтр - по "Not disputed" (отображаемое значение, соответствующее Enum 0, т.е те строки View, где поля из custDispute отсутствуют) не позволяет. При этом, пробовала 0, null - тоже не получается, т.е возвращается просто пустая выборка. |
|
![]() |
#14 |
Боец
|
Тогда так:
1. Сделайте свой EDT как копию стандартного, но с дополнительным значением: 2. Сделайте во View вычисляемое поле: X++: display CustVendDisputeStatusExt disputeStatusExt() { if (this.CustDisputeRecId) { return this.CustDisputeStatus; } else { return CustVendDisputeStatusExt::TSTNotExist; } } - дополнительно нужно во view протянуть поле CustDisputeRecId |
|
|
![]() |
||||
Тема | Ответов | |||
Добавить хитрый фильтр в Query | 5 | |||
Фильтр. Как сделать? | 9 | |||
Как сделать фильтр по группе пользователей? | 12 | |||
Как сделать хитрый лукап | 11 | |||
Как сделать фильтр с "ИЛИ"? | 8 |
|