|
19.08.2009, 21:16 | #1 |
Участник
|
DAX4 Интеркомпани, ошибка разноски внутрихолдинговой накладной
Для информации, может быть кому понадобится.
Совместно с rINT обнаружили ошибку расчета количества при разноске внутрихолдинговой накладной. При разноске накладной по внутрихолдинговому заказу на продажу автоматически разносится накладная по внутрихолдинговому заказу на покупку. При этом определяется количество, которое нужно разносить. В классе SalesFormLetter в методе createParmLine есть следующий код: X++: [newSalesParmLine.DeliverNow, newSalesParmLine.RemainBefore , newSalesParmLine.RemainAfter] = this.qtySales (_salesLineOrig, this.interCompanyParmLineQty(_salesLineOrig)); [newSalesParmLine.InventNow , newSalesParmLine.RemainBeforeInvent, newSalesParmLine.RemainAfterInvent] = this.qtyInvent (_salesLineOrig, this.interCompanyParmLineQty(_salesLineOrig)); Решение проблемы: для второго вызова interCompanyParmLineQty результат необходимо пересчитать в складские единицы. |
|
|
За это сообщение автора поблагодарили: kashperuk (5). |
20.08.2009, 10:23 | #2 |
Участник
|
Есть такое дело. Тоже исправлял. Вообще в Intercompany я много косяков в свое время нарыл. Такое ощущение, что эту функциональность плохо тестировали.
|
|
21.08.2009, 13:04 | #3 |
Участник
|
Raven, а расскажите плз, как именно вы исправляли эту ошибку. Передачей true при втором вызове метода interCompanyParmLineQty?
И, если будет время, было бы здорово привести сценарий, с помощью которого можно воспроизвести это поведение в стандартном функционале. Спасибо Последний раз редактировалось kashperuk; 21.08.2009 в 13:07. |
|
|
За это сообщение автора поблагодарили: Raven Melancholic (4). |
21.08.2009, 15:08 | #4 |
Участник
|
Лично я исправлял как Вы сказали:
Цитата:
Передачей true при втором вызове метода interCompanyParmLineQty
создать цепочку заказов (внутрихолд заказ продажи - внутрихолд заказ покупки - исходный заказ) типа прямая поставка. И разнести ее. |
|
|
За это сообщение автора поблагодарили: Raven Melancholic (2). |
21.08.2009, 15:33 | #5 |
Участник
|
Тогда уже исправили. Спасибо
|
|
|
За это сообщение автора поблагодарили: mazzy (2). |
21.08.2009, 17:17 | #6 |
Участник
|
Ну тогда, позвольте я еще про одну ошибку изложу. Скажу сразу, что толком не помню как ее воспроизвести (давненько это было). Кроется она в классе IntercompanyTransferInventDim метод transfer:
X++: ... while (qr.next()) { fromInventTrans = qr.get(tablenum(InventTrans)); fromInventDim = qr.get(tablenum(InventDim)); ... fromQty = -fromInventTrans.Qty; if (inventDimParm.InventLocationIdFlag && fromInventDim.InventLocationId) { convInventLocation = new TradeInterCompanyConv(); salesInventLocationId = fromInventDim.InventLocationId; convInventLocation.axInventLocationId(fromValueMap, fromInventDim.InventLocationId); } ... changecompany(_toDataAreaId) { toInventTrans = null; select forceplaceholders sum(Qty) from toInventTrans where toInventTrans.InventTransId == _toInventTransId && (toInventTrans.StatusReceipt <= StatusReceipt::Registered || toInventTrans.InterCompanyInventDimTransferred == true) && toInventTrans.StatusIssue == StatusIssue::None #inventDimJoin(toInventTrans.InventDimId,toInventDim,fromInventDim,inventDimParm); fromQty -= toInventTrans.Qty; .... P.S.: надеюсь понятно пояснил, как-то сумбурно получилось, млин |
|
21.08.2009, 17:20 | #7 |
Участник
|
Забыл добавить: DAX 4.0 SP2
|
|
21.08.2009, 21:30 | #8 |
Участник
|
Цитата:
Поэтому лучше получить данные методом interCompanyParmLineQty для единиц закупки/продажи и приводить к складским уже в компании-покупателе. |
|
24.08.2009, 10:11 | #9 |
Участник
|
В предыдущем сообщении, где приводил пример кода, я допустил ошибку. Исправляюсь. Код в базовой функциональности должен выглядеть так:
X++: while (fromInventTrans) { ... fromQty = -fromInventTrans.Qty; if (inventDimParm.InventLocationIdFlag && fromInventDim.InventLocationId) { convInventLocation = new TradeInterCompanyConv(); salesInventLocationId = fromInventDim.InventLocationId; convInventLocation.axInventLocationId(fromValueMap, fromInventDim.InventLocationId); } ... changecompany(_toDataAreaId) { toInventTrans = null; select forceplaceholders sum(Qty) from toInventTrans where toInventTrans.InventTransId == _toInventTransId && (toInventTrans.StatusReceipt <= StatusReceipt::Registered || toInventTrans.InterCompanyInventDimTransferred == true) && toInventTrans.StatusIssue == StatusIssue::None #inventDimJoin(toInventTrans.InventDimId,toInventDim,fromInventDim,inventDimParm); fromQty -= toInventTrans.Qty; .... Кстати непонятно зачем нужно было писать такую "этажерку" в этом методе до вышеописанного цикла: X++: if (inventDimParm.InventLocationIdFlag && inventDimParm.InventBatchIdFlag && inventDimParm.InventSerialIdFlag) { select forceplaceholders sum(Qty) from fromInventTrans where fromInventTrans.InventTransId == _fromInventTransId && fromInventTrans.StatusIssue <= _statusIssue && fromInventTrans.StatusReceipt == StatusReceipt::None join InventLocationId, InventBatchId, InventSerialId from fromInventDim group by InventLocationId, InventBatchId, InventSerialId where fromInventDim.InventDimId == fromInventTrans.InventDimId; } else if (inventDimParm.InventLocationIdFlag && inventDimParm.InventBatchIdFlag) { select forceplaceholders sum(Qty) from fromInventTrans where fromInventTrans.InventTransId == _fromInventTransId && fromInventTrans.StatusIssue <= _statusIssue && fromInventTrans.StatusReceipt == StatusReceipt::None join InventLocationId, InventBatchId from fromInventDim group by InventLocationId, InventBatchId where fromInventDim.InventDimId == fromInventTrans.InventDimId; } else if (inventDimParm.InventLocationIdFlag && inventDimParm.InventSerialIdFlag) { ... |
|
24.08.2009, 10:20 | #10 |
Участник
|
to Raven
Цитата:
К сожалению это не одна ошибка в этом методе
Цитата:
даже если отбросить тот факт, что про ГТД в этом методе ничего нет
|
|
29.08.2009, 21:08 | #11 |
Участник
|
Еще наткнулись. Ка-то странно работает кэш (я про это уже писал, но тогда было только тестирование и как-то не зациклились на этой теме).
У нас в разных компаниях номенклатура ведет себя по разному (например, в производственной это спецификация с номенклатурной группой "Готовая продукция", в торговых домах это номенклатура с номенклатурной группой Товар, ну и т.п.). Поэтому справочник не общий, а в каждой компании свой (есть доработка по вводу и синхронизации определенных номенклатур, но суть не в этом). Так вот, простой код джоба: X++: itemId = 'ВентиляторWRW50/40'; intentTable = InventTable::find(itemId); changeCompany('TRD') { inventTableChg = null; select firstOnly inventTableChg where inventTableChg == itemId; ... } То же происходит если в разных компаниях номера складских лотов совпадают. Если после переключения компании искать складские операции по номеру лота, совпадающему с тем, что был выполнен ранее, то вернется ранее найденный лот. Помогает включения в код запрет кэша: X++: itemId = 'ВентиляторWRW50/40'; intentTable = InventTable::find(itemId); changeCompany('TRD') { inventTableChg = null; inventTableChg.disableCash(true); select firstOnly inventTableChg where inventTableChg == itemId; ... } Такое впечатление, то кэш игнорирует компании. вобщем-то можно было бы отключить кэш DAX для всех таблиц (кэш MS SQL хорошо справляется со своей работой), но InventTrans не кэшируется DAX! Так же понятно, что из-за этой проблемы следует стараться иметь для одних и тех же таблиц в разных компаниях разные уникальные идентификаторы. Но, в нашем случае, это возможно для InventTrans, но не интересно для InvntTable. Можно всегда добавлять disableCach, но в наших разработках мы так и делаем, но есть стандартный код! PS: кстати, без использования disableCash Trasert MS SQL показывает, что к базе данных было только оно обращение, то есть цепочка: поиск в одной компании, changeCompany, поиск в другой компании того же значения обрабатывает DAx независимо от типа кэширования. Последний раз редактировалось Raven Melancholic; 29.08.2009 в 21:16. |
|
|
За это сообщение автора поблагодарили: JeS (1), Kabardian (3). |