01.09.2021, 18:09 | #1 |
Участник
|
ax2009+: как получить Query из QueryRun формы
На форме есть несколько датасорсов, у которых LinkType= Delayed
Как на основе запросов из формы создать один Query? Подробнее: Для определенности возьмем стандартную форму SalesTable. Для определенности обратим внимание на датасорсы SalesTable и SalesLine - они связаны LinkType= Delayed ядро аксапты внутри формы работает с отдельными запросами. Предположим, я хочу как-то обработать все выбранные строки всех выбранных заказов. Как на основе запросов из формы создать один Query? со всеми критериями на всех датасорсах (в том числе пользовательскими), сортировками, вложенными датасорсами, и пр. можно без диналинков. Есть ли какой-нибудь штатный метод создания одного запроса на основании запросов из формы? Спасибо. ======================= upd: 2. как можно вывернуть решение, чтобы таки реализовать хотелку: обрабатывать записи, которые пользователь видит в форме после наложения фильтров/сортировок? upd:: 3. подскажите, реализована ли где-нибудь в стандартном функционале такая хотелка? Последний раз редактировалось mazzy; 01.09.2021 в 18:18. |
|
08.09.2021, 07:28 | #2 |
Мрачный тип
|
Штатный для таких изысков - слишком хорошего мнения о вендоре
А у формы есть свой QueryRun ? Он есть у каждого DS, его тек. состояние можно клонировать в отдельный запрос и далее над ним творить потребное - чем собственно и занимались тут Единственный вариант - прошерстить список DS формы, выстроив цепочку связи, и воспроизвести в аналогичной последовательности и структуре (Query каждого DS может включать в себя не только таблицу DS и быть построенным не только по имеющимся в AOT relations м-ду таблицами - что справедливо и для связи м-ду самими DS на форме) запрос, где таблицы DS будут залинкованы по OuterJoin
__________________
Мы летаем, кружимся, нагоняем ужасы ... Последний раз редактировалось TasmanianDevil; 08.09.2021 в 07:45. |
|
|
За это сообщение автора поблагодарили: mazzy (10). |
08.09.2021, 09:26 | #3 |
Участник
|
упрек принят.
вопрос к единственному числу принят. это то понятно. учесть что один может быть с группировкой и/или агрегатными функциями, а другой без один может быть union запрос, а другой нет и прочие радости... вдруг кто-нибудь это уже делал... А вот точно ли единственный вариант? Может кто копал в сторону dataSet, которые появились в 2009? Делал ли кто-нибудь код, который эмулирует dataSet и автоматом делает выполняет вложенные запросы? Есть ли перспективы в этих направлениях? Последний раз редактировалось mazzy; 08.09.2021 в 09:28. |
|
08.09.2021, 11:41 | #4 |
Участник
|
У меня в подписи ссылка на мультипаспорт. Он такие вещи умеет делать. Например, сначала стандартным способом пользователь через CTRL + F3 может отфильтровать заказы по конкретному клиенту, в строках которого есть конкретная номенклатура .
А потом запустить мультипаспорт, поставить в нем галку "Выполнить для всех записей, отображаемых на форме". Встать на поле "Цена" и поставить для всех строк всех выбранных заказов одинаковую цену 100 рублей. Правда он поставит цену 100 рублей для всех строк выбранных заказов, а не только в той, для которой задали фильтр по коду номенклатуры. Но это только потому, что сама Аксапта выбирает такие строки через Exists Join. Сама Аксапта тоже показывает на форме все строки заказов. Но шапки заказов фильтрует только те, в которых есть хотя бы одна строка с заданной номенклатурой. И мультипаспорт генерирует запросы вида SELECT * FROM SalesTable WHERE ((CustAccount = 54321)) EXISTS JOIN * FROM SalesLine WHERE SalesTable.SalesId = SalesLine.SalesId AND ((ItemId = 12345)) Я этим мультипаспортом пользуюсь активно, и несмотря на некоторые глюки, он мне сильно облегчает жизнь. Правда опасно ошибаться.
__________________
Мои утилиты для Аксапты версий 3.0-2012: http://aceofdatabase.blogspot.com/ Последний раз редактировалось Ace of Database; 08.09.2021 в 11:44. |
|
|
За это сообщение автора поблагодарили: mazzy (2). |
08.09.2021, 11:58 | #5 |
Участник
|
Вот такой страшный запрос мультипаспорт генерирует для формы EсoResProductDetailsExtended в AX2012
Я иногда копи-пастю такие запросы для всяких нужд. SELECT * FROM InventTable(InventTable) OUTER JOIN * FROM S_InventTable(S_InventTable) ON InventTable.RecId = S_InventTable.RefRecId OUTER JOIN * FROM InventModelGroupItem(InventModelGroupItem) ON InventTable.dataAreaId = InventModelGroupItem.ItemDataAreaId AND InventTable.ItemId = InventModelGroupItem.ItemId OUTER JOIN * FROM InventItemGroupItem(InventItemGroupItem) ON InventTable.dataAreaId = InventItemGroupItem.ItemDataAreaId AND InventTable.ItemId = InventItemGroupItem.ItemId OUTER JOIN * FROM EcoResTrackingDimensionGroupItem(EcoResTrackingDimensionGroupItem) ON InventTable.dataAreaId = EcoResTrackingDimensionGroupItem.ItemDataAreaId AND InventTable.ItemId = EcoResTrackingDimensionGroupItem.ItemId OUTER JOIN * FROM EcoResStorageDimensionGroupItem(EcoResStorageDimensionGroupItem) ON InventTable.dataAreaId = EcoResStorageDimensionGroupItem.ItemDataAreaId AND InventTable.ItemId = EcoResStorageDimensionGroupItem.ItemId JOIN * FROM EcoResProduct(EcoResProduct) ON InventTable.Product = EcoResProduct.RecId OUTER JOIN * FROM EcoResProductDimensionGroupProduct(EcoResProductDimensionGroupProduct) ON EcoResProductMaster.RecId = EcoResProductDimensionGroupProduct.Product OUTER JOIN * FROM EcoResProductTranslation(EcoResProductTranslation) ON EcoResProduct.RecId = EcoResProductTranslation.Product AND ((LanguageId = N'ru') OR (LanguageId = N'ru')) OUTER JOIN * FROM EcoResProductMasterModelingPolicy(EcoResProductMasterModelingPolicy) ON EcoResProductMaster.RecId = EcoResProductMasterModelingPolicy.ProductMaster JOIN * FROM InventTableModule(Purch) ON InventTable.ItemId = InventTableModule.ItemId AND ((ModuleType = 1)) JOIN * FROM InventTableModule(Invent) ON InventTable.ItemId = InventTableModule.ItemId AND ((ModuleType = 0)) JOIN * FROM InventTableModule(Sales) ON InventTable.ItemId = InventTableModule.ItemId AND ((ModuleType = 2)) JOIN * FROM InventItemLocation(InventItemLocation) ON InventTable.ItemId = InventItemLocation.ItemId AND ((inventDimId = N'AllBlank')) WHERE ((InventModelGroupItem(InventModelGroupItem).)) AND ((InventItemGroupItem(InventItemGroupItem).))
__________________
Мои утилиты для Аксапты версий 3.0-2012: http://aceofdatabase.blogspot.com/ |
|
09.09.2021, 00:23 | #6 |
Administrator
|
Цитата:
И потом...А как интересно можно создать единый Query, если его на форме в принципе нет? Я имею в виду пример SalesTable, где датасорсы SalesTable и SalesLine связаны между собой по Delayed? Да, если связка по Inner / Exists / Outer Join - там все понятно и в этом случае все датасорсы сидят в корневом датасорсе, а значит весь запрос вытаскивается через метод FormDataSource.query(). Ведь даже на форме SalesTable (AX2009) видно, что строки подгружаются позже шапок, т.е. отдельным запросом к БД.
__________________
Возможно сделать все. Вопрос времени |
|
09.09.2021, 11:23 | #7 |
Участник
|
Цитата:
очередной объект для конкретного случая... но вдруг? Цитата:
я неправильно сформулировал вопрос. в исходном сообщении я писал "Предположим, я хочу как-то обработать все выбранные строки всех выбранных заказов." правильный вопрос: "как обработать все строки, которые может увидеть пользователь на форме, с учётом наложенных на форму фильтров" Последний раз редактировалось mazzy; 09.09.2021 в 11:32. |
|
10.09.2021, 01:28 | #8 |
Administrator
|
Цитата:
Напрашивается решение - обратиться к датасорсу, к которому привязаны строки и посмотреть у него _ds.queryRun().query() (ну если в явном виде не перебирать все строки текущего датасорса) Т.е. подразумевается, что есть форма (условно - SalesTable), в ней есть строки (SalesLine), которые подчинены главному датасорсу по Delayed. Я хочу обработать все строки (SalesLine) с учетом пользовательского фильтра. Я делаю кнопку на форме, к ней привязываю тот датасорс, строки которого я хочу обработать, а дальше в коде обращаюсь к _ds.queryRun().query() Но это все хорошо, если мой датасорс является либо корневым, либо подчиненным по Delayed / Active / Passive - в общем не join Если же мой датасорс подчинен кому-то по *Join, то получается, что надо обращаться к его родителю (его датасорсу) и уже там искать _ds.queryRun().query() Т.е. грубо говоря, если на форме SalesTable под строками я подразумеваю не SalesLine, а InventDim, то мне нужно от датасорса InventDim "подняться" до SalesLine и взять его queryRun.query()
__________________
Возможно сделать все. Вопрос времени |
|