Общие затраты на рабочую силу и общие затраты на материалы MAximo workorder

Я работаю со своим администратором баз данных, чтобы попытаться найти способ свести все расходы, связанные с заказом на работу. Поскольку любое рабочее задание может иметь несколько дочерних рабочих заданий (через несколько «поколений»), а также связанных рабочих заданий (через таблицу RELATEDRECORDS), мне нужно иметь возможность получить общее количество полей ACTLABORCOST и ACTMATERIALCOST для всех дочерних и связанных рабочие задания (а также каждый из их дочерних и связанных рабочих заданий). Я работал с иерархическим запросом (используя CONNECT BY PRIOR), чтобы получить всех детей, внуков и т. д., но я застрял на связанных рабочих заданиях. Поскольку каждое рабочее задание может иметь связанное рабочее задание со своими дочерними элементами и связанными рабочими заданиями, мне нужна функция Oracle, которая детализирует дочерние элементы и связанные рабочие задания, а также их дочерние элементы и связанные рабочие задания. Поскольку я думаю, что это должно быть довольно распространенным явлением, я надеюсь, что есть кто-то, кто сделал это и может поделиться тем, что они сделали.


person Frank Ball    schedule 17.07.2019    source источник
comment
В Oracle есть 2 варианта решения этой проблемы. Один с использованием Oracle Connect by (о котором вы уже упоминали), а другой с использованием рекурсивного факторинга подзапросов. Чтобы предоставить вам лучшую помощь, было бы здорово, если бы вы могли предоставить упрощенную версию вашей структуры данных, образцы данных и ожидаемые результаты. Таким образом, кто-то, вероятно, сможет адаптировать решение, которое работает для вашей проблемы, а не делать предложения, которые могут или не могут относиться к тому, что вам нужно.   -  person Francisco Sitja    schedule 17.07.2019
comment
Подключение по: docs.oracle.com/en/database/oracle/oracle-database/12.2/sqlrf/ Рекурсивный факторинг подзапросов: docs.oracle.com/en/database/oracle/oracle -база данных/12.2/sqlrf/   -  person Francisco Sitja    schedule 17.07.2019
comment
Планируете ли вы использовать результаты внутри или вне Maximo?   -  person Preacher    schedule 18.07.2019


Ответы (3)


Другим вариантом может быть рекурсивный запрос, предложенный Франсиско Ситья. Поскольку мой Oracle не допускал 2 UNION ALL, мне пришлось присоединиться к таблице WOANCESTOR в обоих дочерних запросах вместо того, чтобы выделить UNION ALL для выполнения иерархии WO. Затем я смог использовать один разрешенный UNION ALL для выполнения иерархии RELATEDRECORD. И, кажется, работает довольно быстро.

with mywos (wonum, parent, taskid, worktype, description, origrecordid, woclass, siteid) as (
    -- normal WO hierarchy
    select wo.wonum, wo.parent, wo.taskid, wo.worktype, wo.description, wo.origrecordid, wo.woclass, wo.siteid
    from woancestor a
        join workorder wo
            on a.wonum = wo.wonum
            and a.siteid = wo.siteid
    where a.ancestor = 'MY-STARTING-WONUM'
    union all
    -- WO hierarchy associated via RELATEDRECORD
    select wo.wonum, wo.parent, wo.taskid, wo.worktype, wo.description, wo.origrecordid, wo.woclass, wo.siteid
    from mywos
        join relatedrecord rr
            on mywos.woclass = rr.class
            and mywos.siteid = rr.siteid
            and mywos.wonum = rr.recordkey
            -- prevent cycle / going back up the hierarchy
            and rr.relatetype not in ('ORIGINATOR')
        join woancestor a
            on rr.relatedrecsiteid = a.siteid
            and rr.relatedreckey = a.ancestor 
        join workorder wo
            on a.siteid = wo.siteid
            and a.wonum = wo.wonum
)
select * from mywos
;
person Preacher    schedule 18.07.2019
comment
Мы пришли к похожему (и более простому) подходу. Наша кривая обучения заключалась в том, чтобы выяснить, как заставить WITH работать. - person Frank Ball; 19.07.2019
comment
Я внимательно изучил ваше утверждение и вижу, где ваше выводит все уровни. Во-первых, оба наших оператора могут возвращать дубликаты, поэтому ваш последний оператор должен быть SELECT DISTINCT. - person Frank Ball; 22.07.2019
comment
Кроме того, зачем использовать таблицу WOANCESTOR вместо CONNECT BY PRIOR? (просто пытаюсь лучше понять) - person Frank Ball; 22.07.2019
comment
Я просматривал некоторые из своих ранних попыток сделать это и получил много ошибок CYCLE. Второй, который я пробовал, был почти идентичен вашему, но без типа отношения не в предложении ('ORIGINATOR') и ​​с использованием CONNECT BY PRIOR. вместо ВОАНСТОР. - person Frank Ball; 22.07.2019
comment
Спасибо, что нашли проблему DISTINCT. Таблицы ANCESTOR (WOANCESTOR, LOCANCESTOR и т. д.) в основном представляют собой сохраненные результаты CONNECT BY. Это узкие таблицы, которые обычно индексируются, поэтому они должны работать лучше, чем CONNECT BY PRIOR, который каждый раз должен вычислять все заново. - person Preacher; 23.07.2019

Рассматривали ли вы объект WOGRANDTOTAL? Его описание в MAXOBJECT: «Непостоянная таблица для отображения общих итогов WO». В приложении «Отслеживание заказов на работу» есть диалоговое окно, доступ к которому можно получить из меню «Выбрать действие» / «Дополнительные действия». Поскольку вы неоднократно упоминали об этом, я должен отметить, что значения WOGRANDTOTAL не включают соединения через RELATEDRECORDS с другими иерархиями рабочих заданий.

Вы также можете избавить себя от сложностей с CONNECT BY PRIOR, присоединившись к WOANCESTOR, который фактически является дампом из запроса CONNECT BY PRIOR. (Есть другие таблицы %ANCESTOR для других иерархий.)

Я думаю, что рекурсивный сценарий автоматизации был бы лучшим способом сделать то, что вы хотите, если вам нужны результаты в Maximo. Если вам нужна общая стоимость за пределами Maximo, возможно, сработает рекурсивная функция.

person Preacher    schedule 18.07.2019
comment
Вся картина заключается в том, что у нас есть какое-то внутреннее программное обеспечение, которое мы используем для отслеживания инцидентов безопасности, и нам нужно знать полную стоимость инцидента для компании (это связано с повреждением имущества). Мы работаем над рекурсивной функцией для этого, но я надеюсь, что есть кто-то, кто уже изобрел это колесо, и может поделиться этой работой. Я просмотрел функцию WOGRANDTOTAL, и, поскольку она не обрабатывает RELATEDRECORDS, сама по себе она нам не подойдет. - person Frank Ball; 18.07.2019
comment
Насколько я видел за 14 лет, люди не заботятся о суммировании по RELATEDRECORDS / по иерархиям. Так что, возможно, не многие изобрели это колесо раньше. - person Preacher; 18.07.2019

Наконец-то мы поняли, как это осуществить.

WITH WO(WONUM,
PARENT) AS
((SELECT X.WONUM,
                  X.PARENT
        FROM (SELECT R.RECORDKEY WONUM,
                                    R.RELATEDRECKEY PARENT
                        FROM MAXIMO.RELATEDRECORD R
                        WHERE R.RELATEDRECKEY = '382418'
                    UNION ALL
                    SELECT W.WONUM,
                                    W.PARENT
                        FROM MAXIMO.WORKORDER W
                        START WITH W.PARENT = '382418'
                    CONNECT BY PRIOR W.WONUM = W.PARENT) X) 
           UNION ALL 
  SELECT W.WONUM, W.PARENT FROM MAXIMO.WORKORDER W, WO WHERE W.WONUM = WO.PARENT)
SELECT DISTINCT WONUM FROM WO;

Это возвращает список всех дочерних и связанных рабочих заданий для данного рабочего задания.

person Frank Ball    schedule 19.07.2019
comment
Он найдет их только в том случае, если ваш начальный заказ на работу имеет продолжение, и будет искать (через RELATEDRECORD) только один раз. - person Preacher; 19.07.2019
comment
Я пересматриваю свое мнение. Ваш встроенный вид возвращает 1 уровень вниз плюс все уровни вниз. Затем ваш with использует это, чтобы снова спуститься. Таким образом, вы получите от '382418' и вниз плюс один уровень вниз и вниз. Но ваше первоначальное требование состояло в том, чтобы пройти весь путь (сколь угодно много уровней) и все вниз, что, я думаю, достигает мой запрос. - person Preacher; 19.07.2019