Регистрация модели из списка объектов, ЕИ в выборке класса оборудования, доработки режимов обновления закладок

This commit is contained in:
Mikhail Chechnev 2024-08-14 14:10:10 +03:00
parent 6f69658ac2
commit b9a925d0d1
14 changed files with 884 additions and 243 deletions

View File

@ -20,6 +20,25 @@ create or replace package UDO_PKG_EQUIPDS as
NRN in number -- Регистрационный номер
);
/* Клиентское формирование "Выборки данных оборудования" по классу технического объекта */
procedure MAKE
(
SEQUIPDS in varchar2, -- Выборка данных оборудования
SEQOBJKIND in varchar2, -- Класс оборудования
SDICMUNTS in varchar2, -- Единица измерения выборки
SUSERPROCS_DATA in varchar2, -- Процедура формирования
SEXSSERVICE_UPLOAD in varchar2, -- Сервис обмена для выгрузки данных
SEXSSERVICEFN_UPLOAD in varchar2, -- Функция обмена для выгрузки данных
SEXSSERVICE_SEND_MD in varchar2, -- Сервис обмена для передачи внешней системе
SEXSSERVICEFN_SEND_MD in varchar2, -- Функция обмена для передачи внешней системе
SEXSSERVICE_SEND_RQ in varchar2, -- Сервис обмена для обработки внешней системой
SEXSSERVICEFN_SEND_RQ in varchar2, -- Функция обмена для обработки внешней системой
STASK in varchar2, -- Задача (TCF - оценка технического состояния (Technical Condition Forecast), RUL - прогнозирование остаточного ресурса (Remaining Useful Life), FP - Прогнозирование отказа (Failure Predict))
NPRECISION_P in number, -- Точность (план)
NEQUIPDS out number, -- Регистрационный номер выборки данных оборудования
NEQUIPDSCM out number -- Регистрационный номер класса оборудования выборки данных
);
/* Карточка "Выборки данных оборудования (классы оборудования)" */
procedure CM_CARD
(
@ -39,6 +58,7 @@ create or replace package UDO_PKG_EQUIPDS as
(
NPRN in number, -- Родитель
SEQOBJKIND in varchar2, -- Класс оборудования
SDICMUNTS in varchar2, -- Единица измерения выборки
SUSERPROCS_DATA in varchar2, -- Процедура формирования
SEXSSERVICE_UPLOAD in varchar2, -- Сервис обмена для выгрузки данных
SEXSSERVICEFN_UPLOAD in varchar2, -- Функция обмена для выгрузки данных
@ -153,6 +173,7 @@ text="Проверка прав доступа на работу с ""Выбор
NCUR := PKG_XMAKE.OPEN_CURSOR();
/* Обходим выборки данных */
for C in (select T.RN NRN,
T.CODE SCODE,
T.NAME SNAME
from UDO_T_EQUIPDS T
where T.COMPANY = NCOMPANY
@ -167,6 +188,9 @@ text="Проверка прав доступа на работу с ""Выбор
SNAME => 'NRN',
SVALUE => C.NRN),
RATTRIBUTE01 => PKG_XMAKE.ATTRIBUTE(ICURSOR => NCUR,
SNAME => 'SCODE',
SVALUE => C.SCODE),
RATTRIBUTE02 => PKG_XMAKE.ATTRIBUTE(ICURSOR => NCUR,
SNAME => 'SNAME',
SVALUE => C.SNAME))));
end loop;
@ -209,6 +233,69 @@ text="Проверка прав доступа на работу с ""Выбор
UDO_PKG_EQUIPDS_BASE.DEL(NRN => NRN, NCOMPANY => NCOMPANY);
end DEL;
/* Клиентское формирование "Выборки данных оборудования" по классу технического объекта */
procedure MAKE
(
SEQUIPDS in varchar2, -- Выборка данных оборудования
SEQOBJKIND in varchar2, -- Класс оборудования
SDICMUNTS in varchar2, -- Единица измерения выборки
SUSERPROCS_DATA in varchar2, -- Процедура формирования
SEXSSERVICE_UPLOAD in varchar2, -- Сервис обмена для выгрузки данных
SEXSSERVICEFN_UPLOAD in varchar2, -- Функция обмена для выгрузки данных
SEXSSERVICE_SEND_MD in varchar2, -- Сервис обмена для передачи внешней системе
SEXSSERVICEFN_SEND_MD in varchar2, -- Функция обмена для передачи внешней системе
SEXSSERVICE_SEND_RQ in varchar2, -- Сервис обмена для обработки внешней системой
SEXSSERVICEFN_SEND_RQ in varchar2, -- Функция обмена для обработки внешней системой
STASK in varchar2, -- Задача (TCF - оценка технического состояния (Technical Condition Forecast), RUL - прогнозирование остаточного ресурса (Remaining Useful Life), FP - Прогнозирование отказа (Failure Predict))
NPRECISION_P in number, -- Точность (план)
NEQUIPDS out number, -- Регистрационный номер выборки данных оборудования
NEQUIPDSCM out number -- Регистрационный номер класса оборудования выборки данных
)
is
NCOMPANY PKG_STD.TREF := GET_SESSION_COMPANY(); -- Организация
NEQUIPDSCMML PKG_STD.TREF; -- Рег. номер модели
begin
/* Проверим наличие такой выборки */
UDO_PKG_EQUIPDS_BASE.FIND_BY_CODE(NFLAG_SMART => 1, NCOMPANY => NCOMPANY, SCODE => SEQUIPDS, NRN => NEQUIPDS);
/* Выборки нет */
if (NEQUIPDS is null) then
/* Добавим выборку данных */
INS(SCODE => SEQUIPDS, SNAME => SEQUIPDS, NRN => NEQUIPDS);
else
/* Выборка есть - надо проверить в ней наличие класса оборудования */
UDO_PKG_EQUIPDS_BASE.CM_FIND_BY_EQOBJKIND(NFLAG_SMART => 1,
NPRN => NEQUIPDS,
SEQOBJKIND => SEQOBJKIND,
NRN => NEQUIPDSCM);
end if;
/* Класса оборудования в выборке нет */
if (NEQUIPDSCM is null) then
/* Добавляем запись класса оборудования */
CM_INS(NPRN => NEQUIPDS,
SEQOBJKIND => SEQOBJKIND,
SDICMUNTS => SDICMUNTS,
SUSERPROCS_DATA => SUSERPROCS_DATA,
SEXSSERVICE_UPLOAD => SEXSSERVICE_UPLOAD,
SEXSSERVICEFN_UPLOAD => SEXSSERVICEFN_UPLOAD,
SEXSSERVICE_SEND_MD => SEXSSERVICE_SEND_MD,
SEXSSERVICEFN_SEND_MD => SEXSSERVICEFN_SEND_MD,
SEXSSERVICE_SEND_RQ => SEXSSERVICE_SEND_RQ,
SEXSSERVICEFN_SEND_RQ => SEXSSERVICEFN_SEND_RQ,
NRN => NEQUIPDSCM);
end if;
/* Проверим наличие такой модели */
UDO_PKG_EQUIPDS_BASE.CMML_FIND_BY_TASK(NFLAG_SMART => 1,
NPRN => NEQUIPDSCM,
STASK => STASK,
NPRECISION_P => NPRECISION_P,
NRN => NEQUIPDSCMML);
/* Модели нет */
if (NEQUIPDSCMML is null) then
/* Добавим модель */
CMML_INS(NPRN => NEQUIPDSCM, STASK => STASK, NPRECISION_P => NPRECISION_P, NRN => NEQUIPDSCMML);
end if;
end MAKE;
/* Карточка "Выборки данных оборудования (классы оборудования)" */
procedure CM_CARD
(
@ -300,11 +387,26 @@ text="Проверка прав доступа на работу с ""Выбор
/* Обходим классы оборудования заданной выборки данных */
for C in (select T.RN NRN,
OK.CODE SCODE,
OK.NAME SNAME
OK.NAME SNAME,
DM.MEAS_MNEMO SDICMUNTS,
UPD.CODE SUSERPROCS_DATA,
UPL.CODE SEXSSERVICEFN_UPLOAD,
SMD.CODE SEXSSERVICEFN_SEND_MD,
SRQ.CODE SEXSSERVICEFN_SEND_RQ
from UDO_T_EQUIPDSCM T,
EQOBJKIND OK
EQOBJKIND OK,
DICMUNTS DM,
USERPROCS UPD,
EXSSERVICEFN UPL,
EXSSERVICEFN SMD,
EXSSERVICEFN SRQ
where T.PRN = NEQUIPDS
and T.EQOBJKIND = OK.RN
and T.DICMUNTS = DM.RN
and T.USERPROCS_DATA = UPD.RN
and T.EXSSERVICEFN_UPLOAD = UPL.RN
and T.EXSSERVICEFN_SEND_MD = SMD.RN
and T.EXSSERVICEFN_SEND_RQ = SRQ.RN
order by OK.CODE)
loop
XDSCM := PKG_XMAKE.CONCAT(ICURSOR => NCUR,
@ -320,7 +422,22 @@ text="Проверка прав доступа на работу с ""Выбор
SVALUE => C.SCODE),
RATTRIBUTE02 => PKG_XMAKE.ATTRIBUTE(ICURSOR => NCUR,
SNAME => 'SNAME',
SVALUE => C.SNAME))));
SVALUE => C.SNAME),
RATTRIBUTE03 => PKG_XMAKE.ATTRIBUTE(ICURSOR => NCUR,
SNAME => 'SDICMUNTS',
SVALUE => C.SDICMUNTS),
RATTRIBUTE04 => PKG_XMAKE.ATTRIBUTE(ICURSOR => NCUR,
SNAME => 'SUSERPROCS_DATA',
SVALUE => C.SUSERPROCS_DATA),
RATTRIBUTE05 => PKG_XMAKE.ATTRIBUTE(ICURSOR => NCUR,
SNAME => 'SEXSSERVICEFN_UPLOAD',
SVALUE => C.SEXSSERVICEFN_UPLOAD),
RATTRIBUTE06 => PKG_XMAKE.ATTRIBUTE(ICURSOR => NCUR,
SNAME => 'SEXSSERVICEFN_SEND_MD',
SVALUE => C.SEXSSERVICEFN_SEND_MD),
RATTRIBUTE07 => PKG_XMAKE.ATTRIBUTE(ICURSOR => NCUR,
SNAME => 'SEXSSERVICEFN_SEND_RQ',
SVALUE => C.SEXSSERVICEFN_SEND_RQ))));
end loop;
/* Формируем XML-представление ответа */
XDOC := PKG_XMAKE.ELEMENT(ICURSOR => NCUR, SNAME => 'XDATA', RNODE00 => XDSCM);
@ -340,6 +457,7 @@ text="Проверка прав доступа на работу с ""Выбор
(
NPRN in number, -- Родитель
SEQOBJKIND in varchar2, -- Класс оборудования
SDICMUNTS in varchar2, -- Единица измерения выборки
SUSERPROCS_DATA in varchar2, -- Процедура формирования
SEXSSERVICE_UPLOAD in varchar2, -- Сервис обмена для выгрузки данных
SEXSSERVICEFN_UPLOAD in varchar2, -- Функция обмена для выгрузки данных
@ -352,6 +470,7 @@ text="Проверка прав доступа на работу с ""Выбор
is
NCOMPANY PKG_STD.TREF := GET_SESSION_COMPANY(); -- Организация
NEQOBJKIND PKG_STD.TREF; -- Рег. номер класса оборудования
NDICMUNTS PKG_STD.TREF; -- Рег. номер единицы измерения выборки
NUSERPROCS_DATA PKG_STD.TREF; -- Рег. номер процедуры формирования
NEXSSERVICEFN_UPLOAD PKG_STD.TREF; -- Рег. номер функции обмена для выгрузки данных
NEXSSERVICEFN_SEND_MD PKG_STD.TREF; -- Рег. номер Функции обмена для передачи внешней системе
@ -360,6 +479,7 @@ text="Проверка прав доступа на работу с ""Выбор
/* Разыменуем ссылки */
UDO_PKG_EQUIPDS_BASE.CM_JOINS(NCOMPANY => NCOMPANY,
SEQOBJKIND => SEQOBJKIND,
SDICMUNTS => SDICMUNTS,
SUSERPROCS_DATA => SUSERPROCS_DATA,
SEXSSERVICE_UPLOAD => SEXSSERVICE_UPLOAD,
SEXSSERVICEFN_UPLOAD => SEXSSERVICEFN_UPLOAD,
@ -368,6 +488,7 @@ text="Проверка прав доступа на работу с ""Выбор
SEXSSERVICE_SEND_RQ => SEXSSERVICE_SEND_RQ,
SEXSSERVICEFN_SEND_RQ => SEXSSERVICEFN_SEND_RQ,
NEQOBJKIND => NEQOBJKIND,
NDICMUNTS => NDICMUNTS,
NUSERPROCS_DATA => NUSERPROCS_DATA,
NEXSSERVICEFN_UPLOAD => NEXSSERVICEFN_UPLOAD,
NEXSSERVICEFN_SEND_MD => NEXSSERVICEFN_SEND_MD,
@ -375,6 +496,7 @@ text="Проверка прав доступа на работу с ""Выбор
/* Добавляем запись */
UDO_PKG_EQUIPDS_BASE.CM_INS(NPRN => NPRN,
NEQOBJKIND => NEQOBJKIND,
NDICMUNTS => NDICMUNTS,
NUSERPROCS_DATA => NUSERPROCS_DATA,
NEXSSERVICEFN_UPLOAD => NEXSSERVICEFN_UPLOAD,
NEXSSERVICEFN_SEND_MD => NEXSSERVICEFN_SEND_MD,
@ -624,7 +746,9 @@ text="Проверка прав доступа на работу с ""Выбор
and CM.RN = ML.PRN)
loop
/* Модель есть */
if (NRES < 2) then
NRES := 1;
end if;
/* Если она уже обучена */
if (C.STATUS = 2) then
NRES := 2;

View File

@ -1,5 +1,21 @@
create or replace package UDO_PKG_EQUIPDS_BASE as
/* Считывание записи "Выборки данных оборудования" по регистрационному номеру */
function GET
(
NFLAG_SMART in number, -- Признак выдачи сообщения об ошибке (0 - выдавать, 1 - не выдавать)
NRN in number -- Регистрационный номер
) return UDO_T_EQUIPDS%rowtype; -- Запись выборки данных оборудования
/* Поиск "Выборки данных оборудования" по мнемокоду */
procedure FIND_BY_CODE
(
NFLAG_SMART in number, -- Признак выдачи сообщения об ошибке (0 - выдавать, 1 - не выдавать)
NCOMPANY in number, -- Организация
SCODE in varchar2, -- Мнемокод
NRN out number -- Регистрационный номер
);
/* Базовое добавление "Выборки данных оборудования" */
procedure INS
(
@ -25,11 +41,28 @@ create or replace package UDO_PKG_EQUIPDS_BASE as
NCOMPANY in number -- Организация
);
/* Считывание записи "Выборки данных оборудования (классы оборудования)" по регистрационному номеру */
function CM_GET
(
NFLAG_SMART in number, -- Признак выдачи сообщения об ошибке (0 - выдавать, 1 - не выдавать)
NRN in number -- Регистрационный номер
) return UDO_T_EQUIPDSCM%rowtype; -- Запись класса оборудования выборки данных
/* Поиск "Выборки данных оборудования (классы оборудования)" по классу оборудования */
procedure CM_FIND_BY_EQOBJKIND
(
NFLAG_SMART in number, -- Признак выдачи сообщения об ошибке (0 - выдавать, 1 - не выдавать)
NPRN in number, -- Родитель
SEQOBJKIND in varchar2, -- Класс оборудования
NRN out number -- Регистрационный номер
);
/* Разыменование словарей "Выборки данных оборудования (классы оборудования)" */
procedure CM_JOINS
(
NCOMPANY in number, -- Организация
SEQOBJKIND in varchar2, -- Класс оборудования
SDICMUNTS in varchar2, -- Единица измерения выборки
SUSERPROCS_DATA in varchar2, -- Процедура формирования
SEXSSERVICE_UPLOAD in varchar2, -- Сервис обмена для выгрузки данных
SEXSSERVICEFN_UPLOAD in varchar2, -- Функция обмена для выгрузки данных
@ -38,6 +71,7 @@ create or replace package UDO_PKG_EQUIPDS_BASE as
SEXSSERVICE_SEND_RQ in varchar2, -- Сервис обмена для обработки внешней системой
SEXSSERVICEFN_SEND_RQ in varchar2, -- Функция обмена для обработки внешней системой
NEQOBJKIND out number, -- Рег. номер класса оборудования
NDICMUNTS out number, -- Рег. номер единицы измерения выборки
NUSERPROCS_DATA out number, -- Рег. номер процедуры формирования
NEXSSERVICEFN_UPLOAD out number, -- Рег. номер функции обмена для выгрузки данных
NEXSSERVICEFN_SEND_MD out number, -- Рег. номер Функции обмена для передачи внешней системе
@ -49,6 +83,7 @@ create or replace package UDO_PKG_EQUIPDS_BASE as
(
NPRN in number, -- Родитель
NEQOBJKIND in number, -- Класс оборудования
NDICMUNTS in number, -- Единица измерения выборки
NUSERPROCS_DATA in number, -- Процедура формирования
NEXSSERVICEFN_UPLOAD in number, -- Функция обмена для выгрузки данных
NEXSSERVICEFN_SEND_MD in number, -- Функция обмена для передачи внешней системе
@ -61,6 +96,7 @@ create or replace package UDO_PKG_EQUIPDS_BASE as
(
NRN in number, -- Регистрационный номер
NEQOBJKIND in number, -- Класс оборудования
NDICMUNTS in number, -- Единица измерения выборки
NUSERPROCS_DATA in number, -- Процедура формирования
NEXSSERVICEFN_UPLOAD in number, -- Функция обмена для выгрузки данных
NEXSSERVICEFN_SEND_MD in number, -- Функция обмена для передачи внешней системе
@ -104,6 +140,16 @@ create or replace package UDO_PKG_EQUIPDS_BASE as
SERR in varchar2 -- Сообщение об ошибке
);
/* Поиск "Выборки данных оборудования (классы оборудования, модели)" по задаче */
procedure CMML_FIND_BY_TASK
(
NFLAG_SMART in number, -- Признак выдачи сообщения об ошибке (0 - выдавать, 1 - не выдавать)
NPRN in number, -- Родитель
STASK in varchar2, -- Задача (TCF - оценка технического состояния (Technical Condition Forecast), RUL - прогнозирование остаточного ресурса (Remaining Useful Life), FP - Прогнозирование отказа (Failure Predict)) */
NPRECISION_P in number, -- Точность (план)
NRN out number -- Регистрационный номер
);
/* Базовое добавление "Выборки данных оборудования (классы оборудования, модели)" */
procedure CMML_INS
(
@ -182,6 +228,51 @@ end UDO_PKG_EQUIPDS_BASE;
/
create or replace package body UDO_PKG_EQUIPDS_BASE as
/* Считывание записи "Выборки данных оборудования" по регистрационному номеру */
function GET
(
NFLAG_SMART in number, -- Признак выдачи сообщения об ошибке (0 - выдавать, 1 - не выдавать)
NRN in number -- Регистрационный номер
) return UDO_T_EQUIPDS%rowtype -- Запись выборки данных оборудования
is
RES UDO_T_EQUIPDS%rowtype; -- Буфер для результата
begin
/* Считывание записи */
begin
select T.* into RES from UDO_T_EQUIPDS T where T.RN = NRN;
exception
when NO_DATA_FOUND then
PKG_MSG.RECORD_NOT_FOUND(NFLAG_SMART => NFLAG_SMART, NDOCUMENT => NRN, SUNIT_TABLE => 'UDO_T_EQUIPDS');
end;
/* Возврат результата */
return RES;
end GET;
/* Поиск "Выборки данных оборудования" по мнемокоду */
procedure FIND_BY_CODE
(
NFLAG_SMART in number, -- Признак выдачи сообщения об ошибке (0 - выдавать, 1 - не выдавать)
NCOMPANY in number, -- Организация
SCODE in varchar2, -- Мнемокод
NRN out number -- Регистрационный номер
)
is
begin
/* Поиск записи */
begin
select RN
into NRN
from UDO_T_EQUIPDS T
where T.COMPANY = NCOMPANY
and T.CODE = SCODE;
exception
when NO_DATA_FOUND then
P_EXCEPTION(NFLAG_SMART,
'Выборка данных оборудования "%s" не определёна.',
SCODE);
end;
end FIND_BY_CODE;
/* Базовое добавление "Выборки данных оборудования" */
procedure INS
(
@ -230,11 +321,60 @@ create or replace package body UDO_PKG_EQUIPDS_BASE as
and T.COMPANY = NCOMPANY;
end DEL;
/* Считывание записи "Выборки данных оборудования (классы оборудования)" по регистрационному номеру */
function CM_GET
(
NFLAG_SMART in number, -- Признак выдачи сообщения об ошибке (0 - выдавать, 1 - не выдавать)
NRN in number -- Регистрационный номер
) return UDO_T_EQUIPDSCM%rowtype -- Запись класса оборудования выборки данных
is
RES UDO_T_EQUIPDSCM%rowtype; -- Буфер для результата
begin
/* Считывание записи */
begin
select T.* into RES from UDO_T_EQUIPDSCM T where T.RN = NRN;
exception
when NO_DATA_FOUND then
PKG_MSG.RECORD_NOT_FOUND(NFLAG_SMART => NFLAG_SMART, NDOCUMENT => NRN, SUNIT_TABLE => 'UDO_T_EQUIPDSCM');
end;
/* Возврат результата */
return RES;
end CM_GET;
/* Поиск "Выборки данных оборудования (классы оборудования)" по классу оборудования */
procedure CM_FIND_BY_EQOBJKIND
(
NFLAG_SMART in number, -- Признак выдачи сообщения об ошибке (0 - выдавать, 1 - не выдавать)
NPRN in number, -- Родитель
SEQOBJKIND in varchar2, -- Класс оборудования
NRN out number -- Регистрационный номер
)
is
begin
/* Поиск записи */
begin
select T.RN
into NRN
from UDO_T_EQUIPDSCM T,
EQOBJKIND OK
where T.PRN = NPRN
and T.EQOBJKIND = OK.RN
and OK.CODE = SEQOBJKIND;
exception
when NO_DATA_FOUND then
P_EXCEPTION(NFLAG_SMART,
'Класс оборудования "%s" в выборке данных "%s" не определён.',
SEQOBJKIND,
TO_CHAR(NPRN));
end;
end CM_FIND_BY_EQOBJKIND;
/* Разыменование словарей "Выборки данных оборудования (классы оборудования)" */
procedure CM_JOINS
(
NCOMPANY in number, -- Организация
SEQOBJKIND in varchar2, -- Класс оборудования
SDICMUNTS in varchar2, -- Единица измерения выборки
SUSERPROCS_DATA in varchar2, -- Процедура формирования
SEXSSERVICE_UPLOAD in varchar2, -- Сервис обмена для выгрузки данных
SEXSSERVICEFN_UPLOAD in varchar2, -- Функция обмена для выгрузки данных
@ -243,6 +383,7 @@ create or replace package body UDO_PKG_EQUIPDS_BASE as
SEXSSERVICE_SEND_RQ in varchar2, -- Сервис обмена для обработки внешней системой
SEXSSERVICEFN_SEND_RQ in varchar2, -- Функция обмена для обработки внешней системой
NEQOBJKIND out number, -- Рег. номер класса оборудования
NDICMUNTS out number, -- Рег. номер единицы измерения выборки
NUSERPROCS_DATA out number, -- Рег. номер процедуры формирования
NEXSSERVICEFN_UPLOAD out number, -- Рег. номер функции обмена для выгрузки данных
NEXSSERVICEFN_SEND_MD out number, -- Рег. номер Функции обмена для передачи внешней системе
@ -257,6 +398,12 @@ create or replace package body UDO_PKG_EQUIPDS_BASE as
NCOMPANY => NCOMPANY,
SCODE => SEQOBJKIND,
NRN => NEQOBJKIND);
/* Единица измерения */
FIND_DICMUNTS_CODE(NFLAG_SMART => 0,
NFLAG_OPTION => 0,
NCOMPANY => NCOMPANY,
SMEAS_MNEMO => SDICMUNTS,
NRN => NDICMUNTS);
/* Процедура формирования */
if (SUSERPROCS_DATA is not null) then
FIND_USERPROCS_CODE(NFLAG_SMART => 0, SCODE => SUSERPROCS_DATA, NRN => NUSERPROCS_DATA);
@ -291,6 +438,7 @@ create or replace package body UDO_PKG_EQUIPDS_BASE as
(
NPRN in number, -- Родитель
NEQOBJKIND in number, -- Класс оборудования
NDICMUNTS in number, -- Единица измерения выборки
NUSERPROCS_DATA in number, -- Процедура формирования
NEXSSERVICEFN_UPLOAD in number, -- Функция обмена для выгрузки данных
NEXSSERVICEFN_SEND_MD in number, -- Функция обмена для передачи внешней системе
@ -306,6 +454,7 @@ create or replace package body UDO_PKG_EQUIPDS_BASE as
(RN,
PRN,
EQOBJKIND,
DICMUNTS,
DATA_CONFIG,
USERPROCS_DATA,
EXSSERVICEFN_UPLOAD,
@ -315,6 +464,7 @@ create or replace package body UDO_PKG_EQUIPDS_BASE as
(NRN,
NPRN,
NEQOBJKIND,
NDICMUNTS,
null,
NUSERPROCS_DATA,
NEXSSERVICEFN_UPLOAD,
@ -327,6 +477,7 @@ create or replace package body UDO_PKG_EQUIPDS_BASE as
(
NRN in number, -- Регистрационный номер
NEQOBJKIND in number, -- Класс оборудования
NDICMUNTS in number, -- Единица измерения выборки
NUSERPROCS_DATA in number, -- Процедура формирования
NEXSSERVICEFN_UPLOAD in number, -- Функция обмена для выгрузки данных
NEXSSERVICEFN_SEND_MD in number, -- Функция обмена для передачи внешней системе
@ -337,6 +488,7 @@ create or replace package body UDO_PKG_EQUIPDS_BASE as
/* Исправим данные */
update UDO_T_EQUIPDSCM T
set T.EQOBJKIND = NEQOBJKIND,
T.DICMUNTS = NDICMUNTS,
T.USERPROCS_DATA = NUSERPROCS_DATA,
T.EXSSERVICEFN_UPLOAD = NEXSSERVICEFN_UPLOAD,
T.EXSSERVICEFN_SEND_MD = NEXSSERVICEFN_SEND_MD,
@ -425,6 +577,35 @@ create or replace package body UDO_PKG_EQUIPDS_BASE as
where T.RN = NRN;
end CMFL_SET_STATUS;
/* Поиск "Выборки данных оборудования (классы оборудования, модели)" по задаче */
procedure CMML_FIND_BY_TASK
(
NFLAG_SMART in number, -- Признак выдачи сообщения об ошибке (0 - выдавать, 1 - не выдавать)
NPRN in number, -- Родитель
STASK in varchar2, -- Задача (TCF - оценка технического состояния (Technical Condition Forecast), RUL - прогнозирование остаточного ресурса (Remaining Useful Life), FP - Прогнозирование отказа (Failure Predict)) */
NPRECISION_P in number, -- Точность (план)
NRN out number -- Регистрационный номер
)
is
begin
/* Поиск записи */
begin
select T.RN
into NRN
from UDO_T_EQUIPDSCMML T
where T.PRN = NPRN
and T.TASK = STASK
and T.PRECISION_P = NPRECISION_P;
exception
when NO_DATA_FOUND then
P_EXCEPTION(NFLAG_SMART,
'Модель с задачей "%s" и точностью "%s" в классе оборудования "%s" не определёна.',
STASK,
TO_CHAR(NPRECISION_P),
TO_CHAR(NPRN));
end;
end CMML_FIND_BY_TASK;
/* Базовое добавление "Выборки данных оборудования (классы оборудования, модели)" */
procedure CMML_INS
(

View File

@ -258,6 +258,16 @@ text="Проверка прав доступа при формировании
SDATA_TYPE => PKG_P8PANELS_VISUAL.SDATA_TYPE_STR,
BORDER => true,
BFILTER => true);
PKG_P8PANELS_VISUAL.TDATA_GRID_ADD_COL_DEF(RDATA_GRID => RDG,
SNAME => 'SOBJ_KIND_FULL_CODE',
SCAPTION => 'Класс (полный иерархический код)',
SDATA_TYPE => PKG_P8PANELS_VISUAL.SDATA_TYPE_STR,
BVISIBLE => false);
PKG_P8PANELS_VISUAL.TDATA_GRID_ADD_COL_DEF(RDATA_GRID => RDG,
SNAME => 'SUMEAS_RES',
SCAPTION => 'Единица измерения ресурса',
SDATA_TYPE => PKG_P8PANELS_VISUAL.SDATA_TYPE_STR,
BVISIBLE => false);
PKG_P8PANELS_VISUAL.TCOL_VALS_ADD(RCOL_VALS => RCOL_VALS, NVALUE => 0, BCLEAR => true);
PKG_P8PANELS_VISUAL.TCOL_VALS_ADD(RCOL_VALS => RCOL_VALS, NVALUE => 1);
PKG_P8PANELS_VISUAL.TCOL_VALS_ADD(RCOL_VALS => RCOL_VALS, NVALUE => 2);
@ -283,9 +293,12 @@ text="Проверка прав доступа при формировании
PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' ST.CODE SUSE_KIND,');
PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' C.OBJ_KIND NOBJ_KIND,');
PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' OK.NAME SOBJ_KIND,');
PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' FORMAT_HIER_NAME(OK.COMPANY, null, OK.FULLCODE) SOBJ_KIND_FULL_CODE,');
PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' DM.MEAS_MNEMO SUMEAS_RES,');
PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => PKG_SQL_BUILD.PKG_NAME(SNAME => 'UDO_PKG_EQUIPDS.CMML_STATUS_BY_EQCONFIG') || '(C.RN) NCMML_STATUS');
PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' from EQCONFIG C');
PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' left outer join HLSTATETYPES ST on C.HLSTATETYPES = ST.RN,');
PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' left outer join HLSTATETYPES ST on C.HLSTATETYPES = ST.RN');
PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' left outer join DICMUNTS DM on C.UMEAS_RES = DM.RN,');
PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' EQOBJKIND OK');
PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' where C.EQPARENT = :NEQPARENT');
PKG_SQL_BUILD.APPEND(SSQL => CSQL, SELEMENT1 => ' and C.OBJ_KIND = OK.RN');
@ -316,8 +329,10 @@ text="Проверка прав доступа при формировании
PKG_SQL_DML.DEFINE_COLUMN_STR(ICURSOR => ICURSOR, IPOSITION => 5);
PKG_SQL_DML.DEFINE_COLUMN_NUM(ICURSOR => ICURSOR, IPOSITION => 6);
PKG_SQL_DML.DEFINE_COLUMN_STR(ICURSOR => ICURSOR, IPOSITION => 7);
PKG_SQL_DML.DEFINE_COLUMN_NUM(ICURSOR => ICURSOR, IPOSITION => 8);
PKG_SQL_DML.DEFINE_COLUMN_NUM(ICURSOR => ICURSOR, IPOSITION => 9);
PKG_SQL_DML.DEFINE_COLUMN_STR(ICURSOR => ICURSOR, IPOSITION => 8);
PKG_SQL_DML.DEFINE_COLUMN_STR(ICURSOR => ICURSOR, IPOSITION => 9);
PKG_SQL_DML.DEFINE_COLUMN_NUM(ICURSOR => ICURSOR, IPOSITION => 10);
PKG_SQL_DML.DEFINE_COLUMN_NUM(ICURSOR => ICURSOR, IPOSITION => 11);
/* Делаем выборку */
if (PKG_SQL_DML.EXECUTE(ICURSOR => ICURSOR) = 0) then
null;
@ -349,10 +364,18 @@ text="Проверка прав доступа при формировании
SNAME => 'SOBJ_KIND',
ICURSOR => ICURSOR,
NPOSITION => 7);
PKG_P8PANELS_VISUAL.TROW_ADD_CUR_COLS(RROW => RDG_ROW,
SNAME => 'SOBJ_KIND_FULL_CODE',
ICURSOR => ICURSOR,
NPOSITION => 8);
PKG_P8PANELS_VISUAL.TROW_ADD_CUR_COLS(RROW => RDG_ROW,
SNAME => 'SUMEAS_RES',
ICURSOR => ICURSOR,
NPOSITION => 9);
PKG_P8PANELS_VISUAL.TROW_ADD_CUR_COLN(RROW => RDG_ROW,
SNAME => 'NCMML_STATUS',
ICURSOR => ICURSOR,
NPOSITION => 8);
NPOSITION => 10);
/* Добавляем строку в таблицу */
PKG_P8PANELS_VISUAL.TDATA_GRID_ADD_ROW(RDATA_GRID => RDG, RROW => RDG_ROW);
end loop;

View File

@ -7,11 +7,13 @@ create table UDO_T_EQUIPDSCM
PRN number(17) not null,
/* Класс оборудования */
EQOBJKIND number(17) not null,
/* Единица измерения выборки */
DICMUNTS number(17) not null,
/* Описание структуры выборки */
DATA_CONFIG clob,
/* Процедура формирования */
USERPROCS_DATA number(17) not null,
/* Функция обмена для выгрузки на FTP */
/* Функция обмена для выгрузки на внешний сервер */
EXSSERVICEFN_UPLOAD number(17) not null,
/* Функция обмена для передачи внешней системе */
EXSSERVICEFN_SEND_MD number(17) not null,
@ -21,6 +23,7 @@ create table UDO_T_EQUIPDSCM
constraint UDO_C_EQUIPDSCM_RN_PK primary key (RN),
constraint UDO_C_EQUIPDSCM_PRN_FK foreign key (PRN) references UDO_T_EQUIPDS(RN),
constraint UDO_C_EQUIPDSCM_EQOBJKIND_FK foreign key (EQOBJKIND) references EQOBJKIND(RN),
constraint UDO_C_EQUIPDSCM_DICMUNTS_FK foreign key (DICMUNTS) references DICMUNTS(RN),
constraint UDO_C_EQUIPDSCM_USRPD_FK foreign key (USERPROCS_DATA) references USERPROCS(RN),
constraint UDO_C_EQUIPDSCM_EXSFNUPLD_FK foreign key (EXSSERVICEFN_UPLOAD) references EXSSERVICEFN(RN),
constraint UDO_C_EQUIPDSCM_EXSFNSDMD_FK foreign key (EXSSERVICEFN_SEND_MD) references EXSSERVICEFN(RN),

View File

@ -29,6 +29,6 @@ create table UDO_T_EQUIPDSCMML
constraint UDO_C_EQUIPDSCMML_STATUS_CH check (STATUS in (0, 1, 2, 3)),
constraint UDO_C_EQUIPDSCMML_ERR_NB check ((ERR is null) or (rtrim(ERR) is not null)),
constraint UDO_C_EQUIPDSCMML_ERR_CH check (((STATUS in (3)) and (ERR is not null)) or (STATUS not in (3))),
constraint UDO_C_EQUIPDSCMML_UN unique (PRN, TASK, PRECISION_P, QUEUE_ID),
constraint UDO_C_EQUIPDSCMML_UN unique (PRN, TASK, PRECISION_P),
constraint UDO_C_EQUIPDSCMML_QID_UN unique (QUEUE_ID)
);

View File

@ -12,6 +12,7 @@ import PropTypes from "prop-types"; //Контроль свойств компо
import { Box, Grid, Stack, Icon, Button, IconButton } from "@mui/material"; //Интерфейсные компоненты
import { ApplicationСtx } from "../../context/application"; //Контекст приложения
import { BackEndСtx } from "../../context/backend"; //Контекст взаимодействия с серверомs
import { DS_RN_DEFAULT, useEquipDataSelectionList } from "./eqs_tech_cond_forecast_hooks"; //Общие вспомогательные хуки
import {
EquipDataSelectionIU,
EquipDataSelectionList,
@ -21,8 +22,6 @@ import {
EquipDataSelectionClassMachineModelIU
} from "./admin_tab_layout"; //Вспомогательные компоненты и вёрстка
import {
DS_RN_DEFAULT,
useEquipDataSelectionList,
useEquipDataSelectionClassMachineList,
useEquipDataSelectionClassMachineCard,
useEquipDataSelectionClassMachineFilesList,
@ -35,9 +34,8 @@ import {
//Начальное состояние флагов обновления
const REFRESH_INITIAL = {
action: null,
dataSelection: null,
dataSelectionClassMachine: null,
dataSelection: 0,
dataSelectionClassMachine: 0,
dataSelectionClassMachineCard: 0,
dataSelectionClassMachineFilesList: 0,
dataSelectionClassMachineModelsList: 0
@ -113,7 +111,7 @@ const AdminTab = ({ dataSelection = DS_RN_DEFAULT, dataSelectionClassMachine = n
//При нажатии на "Удалить выборку"
const handleDeleteEquipDataSelection = async () => {
await executeStored({ stored: "UDO_PKG_EQUIPDS.DEL", args: { NRN: equipDataSelection } });
setRefresh(pv => ({ ...pv, dataSelection: equipDataSelection * 2, action: "DEL" }));
setRefresh(pv => ({ ...pv, dataSelection: pv.dataSelection + 1 }));
setDataSelection(DS_RN_DEFAULT);
};
@ -124,7 +122,8 @@ const AdminTab = ({ dataSelection = DS_RN_DEFAULT, dataSelectionClassMachine = n
const handleEquipDataSelectionIUOk = async values => {
const data = await executeStored({ stored: "UDO_PKG_EQUIPDS.INS", args: { SCODE: values.code, SNAME: values.name } });
setDialogs(pv => ({ ...pv, dataSelectionIU: false }));
setRefresh(pv => ({ ...pv, dataSelection: data.NRN, action: "INS" }));
setRefresh(pv => ({ ...pv, dataSelection: pv.dataSelection + 1 }));
setDataSelection(data.NRN);
};
//При нажатии на класс оборудования
@ -136,7 +135,7 @@ const AdminTab = ({ dataSelection = DS_RN_DEFAULT, dataSelectionClassMachine = n
//При нажатии на "Удалить класс оборудования"
const handleDeleteEquipDataSelectionClassMachine = async equipDSCM => {
await executeStored({ stored: "UDO_PKG_EQUIPDS.CM_DEL", args: { NRN: equipDSCM } });
setRefresh(pv => ({ ...pv, dataSelectionClassMachine: equipDSCM * 2, action: "DEL" }));
setRefresh(pv => ({ ...pv, dataSelectionClassMachine: pv.dataSelectionClassMachine + 1 }));
setDataSelectionClassMachine(null);
};
@ -150,6 +149,7 @@ const AdminTab = ({ dataSelection = DS_RN_DEFAULT, dataSelectionClassMachine = n
args: {
NPRN: equipDataSelection,
SEQOBJKIND: values.eqobjKind,
SDICMUNTS: values.measureUnit,
SUSERPROCS_DATA: values.userprocsData,
SEXSSERVICE_UPLOAD: values.exsServiceUpload,
SEXSSERVICEFN_UPLOAD: values.exsServiceFnUpload,
@ -160,7 +160,8 @@ const AdminTab = ({ dataSelection = DS_RN_DEFAULT, dataSelectionClassMachine = n
}
});
setDialogs(pv => ({ ...pv, dataSelectionClassMachineIU: false }));
setRefresh(pv => ({ ...pv, dataSelectionClassMachine: data.NRN, action: "INS" }));
setRefresh(pv => ({ ...pv, dataSelectionClassMachine: pv.dataSelectionClassMachine + 1 }));
setDataSelectionClassMachine(data.NRN);
};
//При нажатии "Сформировать" в списке файлов карточки класса оборудования
@ -220,28 +221,15 @@ const AdminTab = ({ dataSelection = DS_RN_DEFAULT, dataSelectionClassMachine = n
//При измении выборки данных через свойства
useEffect(() => {
setDataSelection(dataSelection);
setRefresh(pv => ({ ...pv, dataSelection: pv.dataSelection + 1 }));
}, [dataSelection]);
//При изменеии класса оборудования через свойства
useEffect(() => {
setDataSelectionClassMachine(dataSelectionClassMachine);
setRefresh(pv => ({ ...pv, dataSelectionClassMachine: pv.dataSelectionClassMachine + 1 }));
}, [dataSelectionClassMachine]);
//При изменении списка выборок данных
useEffect(() => {
if (refresh.action == "INS" && refresh.dataSelection) {
setDataSelection(refresh.dataSelection);
setDataSelectionClassMachine(null);
}
// eslint-disable-next-line react-hooks/exhaustive-deps
}, [equipDataSelectionList]);
//При изменении списка классов оборудования выборки данных
useEffect(() => {
if (refresh.action == "INS" && refresh.dataSelectionClassMachine) setDataSelectionClassMachine(refresh.dataSelectionClassMachine);
// eslint-disable-next-line react-hooks/exhaustive-deps
}, [equipDataSelectionClassMachineList]);
//Генерация содержимого
return (
<Box>
@ -278,7 +266,7 @@ const AdminTab = ({ dataSelection = DS_RN_DEFAULT, dataSelectionClassMachine = n
</Grid>
<Grid item xs={12}>
<Grid container>
<Grid item xs={2} hidden={equipDataSelection == DS_RN_DEFAULT}>
<Grid item xs={3} hidden={equipDataSelection == DS_RN_DEFAULT}>
<Button
fullWidth
startIcon={<Icon>add</Icon>}
@ -293,7 +281,7 @@ const AdminTab = ({ dataSelection = DS_RN_DEFAULT, dataSelectionClassMachine = n
onClick={handleDataSelectionClassMachineClick}
/>
</Grid>
<Grid item xs={10} hidden={equipDataSelectionClassMachine == null}>
<Grid item xs={9} hidden={equipDataSelectionClassMachine == null}>
<EquipDataSelectionClassMachineCard
card={equipDataSelectionClassMachineCard}
filesList={equipDataSelectionClassMachineFilesList}

View File

@ -9,59 +9,12 @@
import { useState, useEffect, useContext } from "react"; //Классы React
import { BackEndСtx } from "../../context/backend"; //Контекст взаимодействия с сервером
//---------
//Константы
//---------
//Рег. номер выборки данных по умолчанию
const DS_RN_DEFAULT = -1;
//Наименование выборки данных по умолчанию
const DS_NAME_DEFAULT = "Не указана";
//Выборка данных по умолчанию
const DS_DEFAULT = { NRN: DS_RN_DEFAULT, SNAME: DS_NAME_DEFAULT };
import { DS_RN_DEFAULT } from "./eqs_tech_cond_forecast_hooks"; //Общие вспомогательные хуки
//-----------
//Тело модуля
//-----------
//Загрузка списка выборок данных
const useEquipDataSelectionList = refresh => {
//Собственное состояние - флаг загрузки
const [isLoading, setLoading] = useState(false);
//Собственное состояние - данные
const [data, setData] = useState([DS_DEFAULT]);
//Подключение к контексту взаимодействия с сервером
const { executeStored } = useContext(BackEndСtx);
//Загрузка данных при изменении зависимостей
useEffect(() => {
const loadData = async () => {
try {
setLoading(true);
const data = await executeStored({
stored: "UDO_PKG_EQUIPDS.LIST",
respArg: "COUT",
isArray: name => ["XDS"].includes(name),
attributeValueProcessor: (name, val) => (["SNAME"].includes(name) ? undefined : val),
loader: false
});
setData([DS_DEFAULT, ...(data?.XDS ? data.XDS : [])]);
} finally {
setLoading(false);
}
};
loadData();
}, [refresh, executeStored]);
//Вернём данные
return { equipDataSelectionList: data, equipDataSelectionListIsLoading: isLoading };
};
//Загрузка классов оборудования выбороки данных
const useEquipDataSelectionClassMachineList = (dataSelection, refresh) => {
//Собственное состояние - флаг загрузки
@ -223,8 +176,6 @@ const useEquipDataSelectionClassMachineModelsList = (classMachine, refresh) => {
//----------------
export {
DS_RN_DEFAULT,
useEquipDataSelectionList,
useEquipDataSelectionClassMachineList,
useEquipDataSelectionClassMachineCard,
useEquipDataSelectionClassMachineFilesList,

View File

@ -34,10 +34,20 @@ import {
import { useTheme } from "@mui/material/styles"; //Темы оформления
import { ApplicationСtx } from "../../context/application"; //Контекст приложения
import { BUTTONS } from "../../../app.text"; //Текстовые ресурсы и константы
import { APP_BAR_HEIGHT, TABS_HEIGHT, SCROLL_STYLES, formatModelStateValue, IUDFormTextField } from "./eqs_tech_cond_forecast_lyaout"; //Общие вспомогательные компоненты и вёрстка
import {
APP_BAR_HEIGHT,
TABS_HEIGHT,
SCROLL_STYLES,
formatModelStateValue,
selectEqobjKind,
selectMeasureUnit,
selectUserProcsData,
selectServiceFn,
IUDFormTextField
} from "./eqs_tech_cond_forecast_layout"; //Общие вспомогательные компоненты и вёрстка
import { P8PDataGrid, P8P_DATA_GRID_SIZE } from "../../components/p8p_data_grid"; //Таблица данных
import { P8P_DATA_GRID_CONFIG_PROPS } from "../../config_wrapper"; //Подключение компонентов к настройкам приложения
import { DS_RN_DEFAULT } from "./admin_tab_hooks"; //Вспомогательные хуки
import { DS_RN_DEFAULT, TASK_LIST } from "./eqs_tech_cond_forecast_hooks"; //Общие вспомогательные хуки
//---------
//Константы
@ -74,6 +84,7 @@ const STYLES = {
paddingRight: "15px",
...SCROLL_STYLES
},
EQUIP_DSCM_LIST_ITEM_SECONDARY_TEXT: { display: "block", wordBreak: "break-all" },
EQUIP_DSCM_CARD: {
minHeight: `calc(100vh - ${APP_BAR_HEIGHT} - ${TABS_HEIGHT} - ${DS_SELECTOR_HEIGHT})`,
maxHeight: `calc(100vh - ${APP_BAR_HEIGHT} - ${TABS_HEIGHT} - ${DS_SELECTOR_HEIGHT})`,
@ -216,6 +227,7 @@ const EquipDataSelectionClassMachineIU = ({ onOk, onCancel }) => {
//Собственное состояние - значения формы
const [values, setValues] = useState({
eqobjKind: "",
measureUnit: "",
userprocsData: "",
exsServiceUpload: "",
exsServiceFnUpload: "",
@ -228,46 +240,6 @@ const EquipDataSelectionClassMachineIU = ({ onOk, onCancel }) => {
//Отработка воода значения в форму
const handleValueChanged = (name, value) => setValues(pv => ({ ...pv, [name]: value }));
//Выбор класса оборудования из словаря
const selectEqobjKind = (name, callBack) => {
pOnlineShowDictionary({
unitCode: "EquipObjectKinds",
callBack: res => callBack(res.success ? [{ name, value: res.outParameters.out_FULLCODE }] : null)
});
};
//Выбор процедуры формирования из словаря
const selectUserProcsData = (name, callBack) => {
pOnlineShowDictionary({
unitCode: "UserProcedures",
callBack: res => callBack(res.success ? [{ name, value: res.outParameters.out_CODE }] : null)
});
};
//Выбор функции обмена для выгрузки данных
const selectServiceFn = (name, callBack) => {
pOnlineShowDictionary({
unitCode: "EXSService",
callBack: res =>
callBack(
res.success
? [
{ name, value: res.outParameters.out_FN_CODE },
{
name:
name == "exsServiceFnUpload"
? "exsServiceUpload"
: name == "exsServiceFnSendMd"
? "exsServiceSendMd"
: "exsServiceSendRq",
value: res.outParameters.out_CODE
}
]
: null
)
});
};
//Генерация содержимого
return (
<Dialog open={true} onClose={() => (onOk ? onCancel() : null)}>
@ -278,14 +250,21 @@ const EquipDataSelectionClassMachineIU = ({ onOk, onCancel }) => {
elementValue={values.eqobjKind}
labelText={"Класс оборудования"}
onChange={handleValueChanged}
dictionary={callBack => selectEqobjKind("eqobjKind", callBack)}
dictionary={callBack => selectEqobjKind(pOnlineShowDictionary, "eqobjKind", callBack)}
/>
<IUDFormTextField
elementCode={"measureUnit"}
elementValue={values.measureUnit}
labelText={"Едница измерения выборки"}
onChange={handleValueChanged}
dictionary={callBack => selectMeasureUnit(pOnlineShowDictionary, "measureUnit", callBack)}
/>
<IUDFormTextField
elementCode={"userprocsData"}
elementValue={values.userprocsData}
labelText={"Процедура формирования"}
onChange={handleValueChanged}
dictionary={callBack => selectUserProcsData("userprocsData", callBack)}
dictionary={callBack => selectUserProcsData(pOnlineShowDictionary, "userprocsData", callBack)}
/>
<IUDFormTextField
elementCode={"exsServiceUpload"}
@ -299,7 +278,7 @@ const EquipDataSelectionClassMachineIU = ({ onOk, onCancel }) => {
elementValue={values.exsServiceFnUpload}
labelText={"Функция обмена для выгрузки данных"}
onChange={handleValueChanged}
dictionary={callBack => selectServiceFn("exsServiceFnUpload", callBack)}
dictionary={callBack => selectServiceFn(pOnlineShowDictionary, "exsServiceFnUpload", callBack)}
/>
<IUDFormTextField
elementCode={"exsServiceSendMd"}
@ -313,7 +292,7 @@ const EquipDataSelectionClassMachineIU = ({ onOk, onCancel }) => {
elementValue={values.exsServiceFnSendMd}
labelText={"Функция обмена для передачи внешней системе"}
onChange={handleValueChanged}
dictionary={callBack => selectServiceFn("exsServiceFnSendMd", callBack)}
dictionary={callBack => selectServiceFn(pOnlineShowDictionary, "exsServiceFnSendMd", callBack)}
/>
<IUDFormTextField
elementCode={"exsServiceSendRq"}
@ -327,7 +306,7 @@ const EquipDataSelectionClassMachineIU = ({ onOk, onCancel }) => {
elementValue={values.exsServiceFnSendRq}
labelText={"Функция обмена для обработки внешней системой"}
onChange={handleValueChanged}
dictionary={callBack => selectServiceFn("exsServiceFnSendRq", callBack)}
dictionary={callBack => selectServiceFn(pOnlineShowDictionary, "exsServiceFnSendRq", callBack)}
/>
</DialogContent>
<DialogActions>
@ -349,7 +328,7 @@ const EquipDataSelectionClassMachineModelIU = ({ onOk, onCancel }) => {
//Собственное состояние - значения формы
const [values, setValues] = useState({
task: "RUL",
precisionP: ""
precisionP: null
});
//Отработка воода значения в форму
@ -365,14 +344,15 @@ const EquipDataSelectionClassMachineModelIU = ({ onOk, onCancel }) => {
elementValue={values.task}
labelText={"Задача"}
onChange={handleValueChanged}
list={[
{ value: null, name: "Не указана" },
{ value: "TCF", name: "TCF - оценка технического состояния (Technical Condition Forecast)" },
{ value: "RUL", name: "RUL - прогнозирование остаточного ресурса (Remaining Useful Life)" },
{ value: "FP", name: "FP - Прогнозирование отказа (Failure Predict)" }
]}
list={TASK_LIST}
/>
<IUDFormTextField
elementCode={"precisionP"}
elementValue={values.precisionP}
labelText={"Точность"}
onChange={handleValueChanged}
type={"number"}
/>
<IUDFormTextField elementCode={"precisionP"} elementValue={values.precisionP} labelText={"Точность"} onChange={handleValueChanged} />
</DialogContent>
<DialogActions>
<Button onClick={() => (onOk ? onOk(values) : null)}>{BUTTONS.OK}</Button>
@ -401,7 +381,7 @@ const EquipDataSelectionList = ({ list, value, onChange }) => {
labelId="equipDSlabel"
id="equipDS"
label="Выборка данных оборудования"
value={list.length == 1 ? DS_RN_DEFAULT : value}
value={list.find(i => i.NRN == value) ? value : DS_RN_DEFAULT}
onChange={handleChange}
displayEmpty
>
@ -433,7 +413,24 @@ const EquipDataSelectionClassMachineList = ({ list, value, onClick }) => {
{list.map((item, i) => (
<ListItem disablePadding key={i}>
<ListItemButton selected={value == item.NRN} onClick={() => handleClick(item.NRN)}>
<ListItemText primary={item.SCODE} secondary={item.SNAME} />
<ListItemText
primary={
<>
<b>{item.SCODE}</b> - <Typography component="span">{item.SNAME}</Typography>
</>
}
secondary={
<Typography
component="span"
variant="caption"
color={"text.secondary"}
sx={STYLES.EQUIP_DSCM_LIST_ITEM_SECONDARY_TEXT}
>
(<b>ЕИ:</b> {item.SDICMUNTS}; <b>ПФ:</b> {item.SUSERPROCS_DATA}; <b>Обмен:</b> {item.SEXSSERVICEFN_UPLOAD},{" "}
{item.SEXSSERVICEFN_SEND_MD}, {item.SEXSSERVICEFN_SEND_RQ})
</Typography>
}
/>
</ListItemButton>
</ListItem>
))}

View File

@ -9,7 +9,7 @@
import React, { useState } from "react"; //Классы React
import { Box, Tabs, Tab } from "@mui/material"; //Интерфейсные компоненты
import { MODES, TabPanel } from "./eqs_tech_cond_forecast_lyaout"; //Вспомогательные компоненты и вёрстка
import { MODES, TabPanel } from "./eqs_tech_cond_forecast_layout"; //Вспомогательные компоненты и вёрстка
import { AdminTab } from "./admin_tab"; //Интерфейс администрирования
import { ForecastTab } from "./forecast_tab"; //Интерфейс прогнозирования

View File

@ -0,0 +1,80 @@
/*
Парус 8 - Панели мониторинга - ТОиР - Прогнозирование технического состояния
Корневая панель прогнозирования технического состояния: кастомные хуки
*/
//---------------------
//Подключение библиотек
//---------------------
import { useState, useEffect, useContext } from "react"; //Классы React
import { BackEndСtx } from "../../context/backend"; //Контекст взаимодействия с сервером
//---------
//Константы
//---------
//Рег. номер выборки данных по умолчанию
const DS_RN_DEFAULT = -1;
//Код выборки данных по умолчанию
const DS_CODE_DEFAULT = "Не указана";
//Наименование выборки данных по умолчанию
const DS_NAME_DEFAULT = "Не указана";
//Выборка данных по умолчанию
const DS_DEFAULT = { NRN: DS_RN_DEFAULT, SCODE: DS_CODE_DEFAULT, SNAME: DS_NAME_DEFAULT };
//Список типовых задач
const TASK_LIST = [
{ value: null, name: "Не указана" },
{ value: "TCF", name: "TCF - оценка технического состояния (Technical Condition Forecast)" },
{ value: "RUL", name: "RUL - прогнозирование остаточного ресурса (Remaining Useful Life)" },
{ value: "FP", name: "FP - Прогнозирование отказа (Failure Predict)" }
];
//-----------
//Тело модуля
//-----------
//Загрузка списка выборок данных
const useEquipDataSelectionList = refresh => {
//Собственное состояние - флаг загрузки
const [isLoading, setLoading] = useState(false);
//Собственное состояние - данные
const [data, setData] = useState([DS_DEFAULT]);
//Подключение к контексту взаимодействия с сервером
const { executeStored } = useContext(BackEndСtx);
//Загрузка данных при изменении зависимостей
useEffect(() => {
const loadData = async () => {
try {
setLoading(true);
const data = await executeStored({
stored: "UDO_PKG_EQUIPDS.LIST",
respArg: "COUT",
isArray: name => ["XDS"].includes(name),
attributeValueProcessor: (name, val) => (["SNAME"].includes(name) ? undefined : val),
loader: false
});
setData([DS_DEFAULT, ...(data?.XDS ? data.XDS : [])]);
} finally {
setLoading(false);
}
};
loadData();
}, [refresh, executeStored]);
//Вернём данные
return { equipDataSelectionList: data, equipDataSelectionListIsLoading: isLoading };
};
//----------------
//Интерфейс модуля
//----------------
export { DS_RN_DEFAULT, TASK_LIST, useEquipDataSelectionList };

View File

@ -9,7 +9,20 @@
import React, { useState, useEffect } from "react"; //Классы React
import PropTypes from "prop-types"; //Контроль свойств компонента
import { Box, Stack, Icon, Input, InputAdornment, FormControl, Select, InputLabel, MenuItem, IconButton } from "@mui/material"; //Интерфейсные компоненты
import {
Box,
Stack,
Icon,
Input,
InputAdornment,
FormControl,
Select,
InputLabel,
MenuItem,
IconButton,
Autocomplete,
TextField
} from "@mui/material"; //Интерфейсные компоненты
//---------
//Константы
@ -74,6 +87,54 @@ const formatModelStateValue = (theme, value, err) => {
);
};
//Выбор класса оборудования из словаря
const selectEqobjKind = (showDictionary, name, callBack) => {
showDictionary({
unitCode: "EquipObjectKinds",
callBack: res => callBack(res.success ? [{ name, value: res.outParameters.out_FULLCODE }] : null)
});
};
//Выбор единица измерения из словаря
const selectMeasureUnit = (showDictionary, name, callBack) => {
showDictionary({
unitCode: "MeasureUnits",
callBack: res => callBack(res.success ? [{ name, value: res.outParameters.out_MEAS_MNEMO }] : null)
});
};
//Выбор процедуры формирования из словаря
const selectUserProcsData = (showDictionary, name, callBack) => {
showDictionary({
unitCode: "UserProcedures",
callBack: res => callBack(res.success ? [{ name, value: res.outParameters.out_CODE }] : null)
});
};
//Выбор функции обмена для выгрузки данных
const selectServiceFn = (showDictionary, name, callBack) => {
showDictionary({
unitCode: "EXSService",
callBack: res =>
callBack(
res.success
? [
{ name, value: res.outParameters.out_FN_CODE },
{
name:
name == "exsServiceFnUpload"
? "exsServiceUpload"
: name == "exsServiceFnSendMd"
? "exsServiceSendMd"
: "exsServiceSendRq",
value: res.outParameters.out_CODE
}
]
: null
)
});
};
//Закладка
const TabPanel = ({ mode, value, children }) => <Box hidden={mode != value}>{children}</Box>;
@ -85,7 +146,7 @@ TabPanel.propTypes = {
};
//Поле ввода формы
const IUDFormTextField = ({ elementCode, elementValue, labelText, onChange, dictionary, list, type, ...other }) => {
const IUDFormTextField = ({ elementCode, elementValue, labelText, onChange, dictionary, list, type, freeSolo = false, ...other }) => {
//Значение элемента
const [value, setValue] = useState(elementValue);
@ -98,19 +159,39 @@ const IUDFormTextField = ({ elementCode, elementValue, labelText, onChange, dict
const handleDictionaryClick = () =>
dictionary ? dictionary(res => (res ? res.map(i => handleChange({ target: { name: i.name, value: i.value } })) : null)) : null;
//Изменение значения элемента
//Изменение значения элемента (по событию)
const handleChange = e => {
setValue(e.target.value);
if (onChange) onChange(e.target.name, e.target.value);
};
//Изменение значения элемента (по имени и значению)
const handleChangeByName = (name, value) => {
setValue(value);
if (onChange) onChange(name, value);
};
//Генерация содержимого
return (
<Box p={1}>
<FormControl variant="standard" fullWidth {...other}>
{list ? (
freeSolo ? (
<Autocomplete
id={elementCode}
name={elementCode}
freeSolo
inputValue={value ? value : ""}
onChange={(event, newValue) => handleChangeByName(elementCode, newValue)}
onInputChange={(event, newInputValue) => handleChangeByName(elementCode, newInputValue)}
options={list}
renderInput={params => <TextField {...params} label={labelText} name={elementCode} variant={"standard"} />}
/>
) : (
<>
<InputLabel id={`${elementCode}Lable`}>{labelText}</InputLabel>
<InputLabel id={`${elementCode}Lable`} shrink>
{labelText}
</InputLabel>
<Select
labelId={`${elementCode}Lable`}
id={elementCode}
@ -127,9 +208,12 @@ const IUDFormTextField = ({ elementCode, elementValue, labelText, onChange, dict
))}
</Select>
</>
)
) : (
<>
<InputLabel htmlFor={elementCode}>{labelText}</InputLabel>
<InputLabel {...(type == "date" ? { shrink: true } : {})} htmlFor={elementCode}>
{labelText}
</InputLabel>
<Input
id={elementCode}
name={elementCode}
@ -161,7 +245,8 @@ IUDFormTextField.propTypes = {
onChange: PropTypes.func,
dictionary: PropTypes.func,
list: PropTypes.array,
type: PropTypes.string
type: PropTypes.string,
freeSolo: PropTypes.bool
};
//----------------
@ -176,6 +261,10 @@ export {
TABLE_FILTERS_HEIGHT,
SCROLL_STYLES,
formatModelStateValue,
selectEqobjKind,
selectMeasureUnit,
selectUserProcsData,
selectServiceFn,
TabPanel,
IUDFormTextField
};

View File

@ -16,8 +16,14 @@ import { BackEndСtx } from "../../context/backend"; //Контекст взаи
import { ApplicationСtx } from "../../context/application"; //Контекст приложения
import { P8PDataGrid, P8P_DATA_GRID_SIZE } from "../../components/p8p_data_grid"; //Таблица данных
import { P8P_DATA_GRID_CONFIG_PROPS } from "../../config_wrapper"; //Подключение компонентов к настройкам приложения
import { APP_BAR_HEIGHT, TABS_HEIGHT, TABLE_FILTERS_HEIGHT, TABLE_MORE_HEIGHT, SCROLL_STYLES } from "./eqs_tech_cond_forecast_lyaout"; //Общие Вспомогательные компоненты и вёрстка
import { TechObjCard, eqConfigTechObjTableValueFormatter, eqConfigTechObjTableDataCellRender, TechObjMakeEqRpSheet } from "./forecast_tab_layout"; //Вспомогательные компоненты и вёрстка
import { APP_BAR_HEIGHT, TABS_HEIGHT, TABLE_FILTERS_HEIGHT, TABLE_MORE_HEIGHT, SCROLL_STYLES } from "./eqs_tech_cond_forecast_layout"; //Общие Вспомогательные компоненты и вёрстка
import {
TechObjCard,
eqConfigTechObjTableValueFormatter,
eqConfigTechObjTableDataCellRender,
TechObjMakeEqRpSheet,
TechObjMakeDataSet
} from "./forecast_tab_layout"; //Вспомогательные компоненты и вёрстка
import {
useEqConfigTree,
useEqConfigTechObjTable,
@ -33,11 +39,23 @@ import {
//Начальное состояние флагов обновления
const REFRESH_INITIAL = {
techObjSpec: 0,
techObjForecastHistList: 0
};
//Начальное состояние диалогов
const DIALOGS_INITIAL = { makeEqRpSheet: false };
const DIALOGS_INITIAL = { makeEqRpSheet: false, makeEqDataSet: false, techObjCard: false };
//Начальное состояние спецификации технических объектов
const TECH_OBJ_SPEC_INITIAL = {
parent: null,
filters: [],
orders: [],
pageNumber: 1
};
//Начальное состояние выбранного технического объекта
const TECH_OBJ_INITIAL = { id: null, objKind: null, measureUnit: null };
//Стили
const STYLES = {
@ -59,9 +77,6 @@ const STYLES = {
})
};
//Начальное состояние спецификации техничких объектов
const TECH_OBJ_SPEC_INIT = { parent: null, filters: [], orders: [], pageNumber: 1 };
//-----------
//Тело модуля
//-----------
@ -81,10 +96,10 @@ const ForecastTab = ({ onGoToAdmin }) => {
const [loadingTreeItem, setLoadingTreeItem] = useState(0);
//Собственное состояние - спецификация технических объектов
const [techObjSpec, setTechObjSpec] = useState({ ...TECH_OBJ_SPEC_INIT });
const [techObjSpec, setTechObjSpec] = useState(TECH_OBJ_SPEC_INITIAL);
//Собственное состояния - карточка технического объекта - 11984229
const [techObjCardId, setTechObjCardId] = useState(null);
//Собственное состояния - карточка технического объекта
const [techObj, setTechObj] = useState(TECH_OBJ_INITIAL);
//Собственное состояние - отображаемые диалоги
const [dialogs, setDialogs] = useState(DIALOGS_INITIAL);
@ -100,24 +115,25 @@ const ForecastTab = ({ onGoToAdmin }) => {
techObjSpec.parent,
techObjSpec.filters,
techObjSpec.orders,
techObjSpec.pageNumber
techObjSpec.pageNumber,
refresh.techObjSpec
);
//Загрузчик карточки выбранного технического объекта
const { techObjCard, techObjCardIsLoading } = useEqConfigTechObjCard(techObjCardId);
const { techObjCard, techObjCardIsLoading } = useEqConfigTechObjCard(techObj.id);
//Загрузчик моделей выбранного технического объекта
const { techObjModelsList } = useTechObjModelsList(techObjCardId);
const { techObjModelsList } = useTechObjModelsList(techObj.id);
//
const { techObjForecastHistList } = useTechObjForecastHistList(techObjCardId, refresh.techObjForecastHistList);
//Загрузчик истории прогнозов выбранного технического объекта
const { techObjForecastHistList } = useTechObjForecastHistList(techObj.id, refresh.techObjForecastHistList);
//Обработка развёртывания/свёртывания уровня дерева
const handleTreeItemExpansionToggle = (event, itemId, isExpanded) =>
isExpanded && needLoadLevel(eQconfigTree, itemId) ? setLoadingTreeItem(parseInt(itemId)) : null;
//Обработка фокусировки на элементе дерева
const handleTreeItemFocus = (event, itemId) => setTechObjSpec({ ...TECH_OBJ_SPEC_INIT, parent: parseInt(itemId) });
const handleTreeItemFocus = (event, itemId) => setTechObjSpec({ ...TECH_OBJ_SPEC_INITIAL, parent: parseInt(itemId) });
//При изменении состояния фильтров спецификации технических объектов
const handleTechObjSpecFilterChanged = ({ filters }) => setTechObjSpec(pv => ({ ...pv, filters: [...filters], pageNumber: 1 }));
@ -131,8 +147,12 @@ const ForecastTab = ({ onGoToAdmin }) => {
//При выполнении действия в колоке "Модели" таблицы технических объектов
const handleCMMLStatusClick = (event, row) => {
if (row.NCMML_STATUS == 0) {
if (onGoToAdmin) onGoToAdmin();
} else setTechObjCardId(parseInt(row.NRN));
setTechObj(pv => ({ ...pv, objKind: String(row.SOBJ_KIND_FULL_CODE), measureUnit: String(row.SUMEAS_RES) }));
setDialogs(pv => ({ ...pv, makeEqDataSet: true }));
} else {
setTechObj(pv => ({ ...pv, id: parseInt(row.NRN) }));
setDialogs(pv => ({ ...pv, techObjCard: true }));
}
};
//При переходе к закладке администрирования из карточки технического объекта
@ -143,12 +163,15 @@ const ForecastTab = ({ onGoToAdmin }) => {
//При запросе прогноза по модели из карточки технического объекта
const handleTechObjeCardGetPrediction = async model => {
await executeStored({ stored: "UDO_PKG_EQUIPTCF.EQCONFIG_THOBJ_FORECAST", args: { NEQCONFIG: techObjCardId, NEQUIPDSCMML: model.NRN } });
await executeStored({ stored: "UDO_PKG_EQUIPTCF.EQCONFIG_THOBJ_FORECAST", args: { NEQCONFIG: techObj.id, NEQUIPDSCMML: model.NRN } });
setRefresh(pv => ({ ...pv, techObjForecastHistList: pv.techObjForecastHistList + 1 }));
};
//При закрытии карточки технического объекта
const handleTechObjeCardClose = () => setTechObjCardId(null);
const handleTechObjeCardClose = () => {
setDialogs(pv => ({ ...pv, techObjCard: false }));
setTechObj(TECH_OBJ_INITIAL);
};
//При нажатии на "Ремонтировать" в карточке технического объекта
const handleTechObjeCardMakeEqRpSheet = () => setDialogs(pv => ({ ...pv, makeEqRpSheet: true }));
@ -158,7 +181,7 @@ const ForecastTab = ({ onGoToAdmin }) => {
const data = await executeStored({
stored: "UDO_PKG_EQUIPTCF.EQCONFIG_THOBJ_MAKE_EQRPSHEET",
args: {
NEQCONFIG: techObjCardId,
NEQCONFIG: techObj.id,
SACATALOG: values.acatalog,
SEQTECSRVKIND: values.eQTecSrvKind,
DPLANDATE_FROM: new Date(values.planDateFrom)
@ -171,6 +194,34 @@ const ForecastTab = ({ onGoToAdmin }) => {
//При нажитии "Отмена" в диалоге формирования ремонтной ведомости
const handleTechObjMakeEqRpSheetCancel = () => setDialogs(pv => ({ ...pv, makeEqRpSheet: false }));
//При нажатии "ОК" в диалоге формирования выборки данных
const handleTechObjMakeDataSetOk = async values => {
const data = await executeStored({
stored: "UDO_PKG_EQUIPDS.MAKE",
args: {
SEQUIPDS: values.dataSet,
SEQOBJKIND: values.eqobjKind,
SDICMUNTS: values.measureUnit,
SUSERPROCS_DATA: values.userprocsData,
SEXSSERVICE_UPLOAD: values.exsServiceUpload,
SEXSSERVICEFN_UPLOAD: values.exsServiceFnUpload,
SEXSSERVICE_SEND_MD: values.exsServiceSendMd,
SEXSSERVICEFN_SEND_MD: values.exsServiceFnSendMd,
SEXSSERVICE_SEND_RQ: values.exsServiceSendRq,
SEXSSERVICEFN_SEND_RQ: values.exsServiceFnSendRq,
STASK: values.task,
NPRECISION_P: parseFloat(values.precisionP)
}
});
setDialogs(pv => ({ ...pv, makeEqDataSet: false }));
if (onGoToAdmin) onGoToAdmin(data.NEQUIPDS, data.NEQUIPDSCM);
if (techObjSpec.pageNumber == 1) setRefresh(pv => ({ ...pv, techObjSpec: pv.techObjSpec + 1 }));
else setTechObjSpec(pv => ({ ...pv, pageNumber: 1 }));
};
//При нажитии "Отмена" в диалоге формирования выборки данных
const handleTechObjMakeDataSetCancel = () => setDialogs(pv => ({ ...pv, makeEqDataSet: false }));
//Текст при отсутствии данных в списке технических объектов
const noDataFoundText =
techObjsDataGridIsLoading || !techObjsDataGrid.init
@ -182,15 +233,8 @@ const ForecastTab = ({ onGoToAdmin }) => {
//Генерация содержимого
return (
<div>
{dialogs.makeEqRpSheet ? <TechObjMakeEqRpSheet onCancel={handleTechObjMakeEqRpSheetCancel} onOk={handleTechObjMakeEqRpSheetOk} /> : null}
<Grid container>
<Grid item xs={3} sx={STYLES.LEFT_SIDE_GRID}>
<Box sx={STYLES.TREE_BOX}>
<RichTreeView items={eQconfigTree} onItemExpansionToggle={handleTreeItemExpansionToggle} onItemFocus={handleTreeItemFocus} />
</Box>
</Grid>
<Grid item xs={9} sx={STYLES.RIGHT_SIDE_GRID}>
{techObjCardId && !techObjCardIsLoading && techObjCard?.SCODE ? (
{dialogs.techObjCard ? (
techObj.id && !techObjCardIsLoading && techObjCard?.SCODE ? (
<TechObjCard
cardData={techObjCard}
modelsList={techObjModelsList}
@ -200,7 +244,24 @@ const ForecastTab = ({ onGoToAdmin }) => {
onGetPrediction={handleTechObjeCardGetPrediction}
onMakeEqRpSheet={handleTechObjeCardMakeEqRpSheet}
/>
) : null
) : null}
{dialogs.makeEqRpSheet ? <TechObjMakeEqRpSheet onCancel={handleTechObjMakeEqRpSheetCancel} onOk={handleTechObjMakeEqRpSheetOk} /> : null}
{dialogs.makeEqDataSet ? (
<TechObjMakeDataSet
eqobjKind={techObj.objKind}
measureUnit={techObj.measureUnit}
onCancel={handleTechObjMakeDataSetCancel}
onOk={handleTechObjMakeDataSetOk}
/>
) : null}
<Grid container>
<Grid item xs={3} sx={STYLES.LEFT_SIDE_GRID}>
<Box sx={STYLES.TREE_BOX}>
<RichTreeView items={eQconfigTree} onItemExpansionToggle={handleTreeItemExpansionToggle} onItemFocus={handleTreeItemFocus} />
</Box>
</Grid>
<Grid item xs={9} sx={STYLES.RIGHT_SIDE_GRID}>
{techObjsDataGrid.init ? (
<P8PDataGrid
{...{ ...P8P_DATA_GRID_CONFIG_PROPS, noDataFoundText }}

View File

@ -95,7 +95,7 @@ const useEqConfigTree = parent => {
};
//Загрузка списка технических объектов
const useEqConfigTechObjTable = (parent, filters, orders, pageNumber) => {
const useEqConfigTechObjTable = (parent, filters, orders, pageNumber, refresh) => {
//Собственное состояние - флаг загрузки
const [isLoading, setLoading] = useState(false);
@ -140,7 +140,7 @@ const useEqConfigTechObjTable = (parent, filters, orders, pageNumber) => {
}
};
if (parent) loadData();
}, [parent, filters, orders, pageNumber, executeStored, SERV_DATA_TYPE_CLOB]);
}, [parent, filters, orders, pageNumber, refresh, executeStored, SERV_DATA_TYPE_CLOB]);
//Вернём данные
return { techObjsDataGrid: data, techObjsDataGridIsLoading: isLoading };

View File

@ -16,7 +16,15 @@ import { BUTTONS } from "../../../app.text"; //Текстовые ресурсы
import { P8PDataGrid, P8P_DATA_GRID_SIZE } from "../../components/p8p_data_grid"; //Таблица данных
import { P8P_DATA_GRID_CONFIG_PROPS } from "../../config_wrapper"; //Подключение компонентов к настройкам приложения
import { formatDateRF, xml2JSON } from "../../core/utils"; //Вспомогательные функции
import { SCROLL_STYLES, formatModelStateValue, IUDFormTextField } from "./eqs_tech_cond_forecast_lyaout"; //Общие вспомогательные компоненты и вёрстка
import {
SCROLL_STYLES,
formatModelStateValue,
selectMeasureUnit,
selectUserProcsData,
selectServiceFn,
IUDFormTextField
} from "./eqs_tech_cond_forecast_layout"; //Общие вспомогательные компоненты и вёрстка
import { DS_RN_DEFAULT, TASK_LIST, useEquipDataSelectionList } from "./eqs_tech_cond_forecast_hooks"; //Общие вспомогательные хуки
import { P8PChart } from "../../components/p8p_chart"; //График
//---------
@ -26,16 +34,18 @@ import { P8PChart } from "../../components/p8p_chart"; //График
//Стили
const STYLES = {
TECH_OBJ_CARD_DIALOG: { maxWidth: "800px" },
TECH_OBJ_CARD_DIALOG_CONTENT: { ...SCROLL_STYLES },
TECH_OBJ_CARD_ML_TABLE: {
maxHeight: "300px",
maxHeight: "200px",
...SCROLL_STYLES
},
TECH_OBJ_CARD_FORECAST_TABLE: {
maxHeight: "300px",
maxHeight: "200px",
...SCROLL_STYLES
},
TECH_OBJ_FORECAST_DETAIL_DIALOG: { maxWidth: "600px" },
TECH_OBJ_FORECAST_DETAIL_CHART: { width: "550px", display: "flex", justifyContent: "center" }
TECH_OBJ_FORECAST_DETAIL_CHART: { width: "550px", display: "flex", justifyContent: "center" },
TECH_OBJ_MAKE_DATASET_DIALOG_CONTENT: { ...SCROLL_STYLES }
};
//------------------------------------
@ -143,6 +153,41 @@ ForecastDetail.propTypes = {
//Тело модуля
//-----------
//Формирование значения для колонки "Модель" таблицы технических объектов
const formatTechObjCMMLStatusValue = value => (value == 0 ? "Обучить" : value == 1 ? "Обучается" : "Прогнозировать");
//Формирование цвета для колонки "Модель" таблицы технических объектов
const formatTechObjCMMLStatusColor = value => (value == 0 ? "primary" : value == 1 ? "warning" : "success");
//Форматирование значений колонок таблицы технических объектов
const eqConfigTechObjTableValueFormatter = ({ value, columnDef }) => {
switch (columnDef.name) {
case "DOPER_DATE":
return formatDateRF(value);
case "NCMML_STATUS":
return formatTechObjCMMLStatusValue(value);
}
return value;
};
//Форматирование колонок таблицы технических объектов
const eqConfigTechObjTableDataCellRender = ({ row, columnDef, onCMMLStatus }) => {
switch (columnDef.name) {
case "NCMML_STATUS":
return {
data: (
<Button
variant="outlined"
color={formatTechObjCMMLStatusColor(row[columnDef.name])}
onClick={event => (onCMMLStatus ? onCMMLStatus(event, row) : null)}
>
{formatTechObjCMMLStatusValue(row[columnDef.name])}
</Button>
)
};
}
};
//Карточка технического объекта
const TechObjCard = ({ cardData, modelsList, forecastHistList, onClose, onGoToModel, onGetPrediction, onMakeEqRpSheet }) => {
//Подключаемся к теме
@ -179,7 +224,7 @@ const TechObjCard = ({ cardData, modelsList, forecastHistList, onClose, onGoToMo
) : null}
<Dialog open={true} onClose={handleClose} {...STYLES.TECH_OBJ_CARD_DIALOG}>
<DialogTitle>{cardData.SCODE}</DialogTitle>
<DialogContent>
<DialogContent sx={STYLES.TECH_OBJ_CARD_DIALOG_CONTENT}>
<Typography variant="h6">{cardData.SNAME}</Typography>
<Stack spacing={2}>
<Typography color="text.secondary" variant="caption" gutterBottom>
@ -263,42 +308,7 @@ TechObjCard.propTypes = {
onMakeEqRpSheet: PropTypes.func
};
//Формирование значения для колонки "Медель" таблицы технических объектов
const formatTechObjCMMLStatusValue = value => (value == 0 ? "Обучить" : value == 1 ? "Обучается" : "Прогнозировать");
//Формирование цвета для колонки "Медель" таблицы технических объектов
const formatTechObjCMMLStatusColor = value => (value == 0 ? "primary" : value == 1 ? "warning" : "success");
//Форматирование значений колонок таблицы технических объектов
const eqConfigTechObjTableValueFormatter = ({ value, columnDef }) => {
switch (columnDef.name) {
case "DOPER_DATE":
return formatDateRF(value);
case "NCMML_STATUS":
return formatTechObjCMMLStatusValue(value);
}
return value;
};
//Форматирование колонок таблицы технических объектов
const eqConfigTechObjTableDataCellRender = ({ row, columnDef, onCMMLStatus }) => {
switch (columnDef.name) {
case "NCMML_STATUS":
return {
data: (
<Button
variant="outlined"
color={formatTechObjCMMLStatusColor(row[columnDef.name])}
onClick={event => (onCMMLStatus ? onCMMLStatus(event, row) : null)}
>
{formatTechObjCMMLStatusValue(row[columnDef.name])}
</Button>
)
};
}
};
//Диалог формирование ремонтной ведомости
//Диалог формирования ремонтной ведомости
const TechObjMakeEqRpSheet = ({ onOk, onCancel }) => {
//Подключение к контексту приложения
const { pOnlineShowDictionary } = useContext(ApplicationСtx);
@ -365,14 +375,148 @@ const TechObjMakeEqRpSheet = ({ onOk, onCancel }) => {
);
};
//Контроль свойств - Диалог формирование ремонтной ведомости
//Контроль свойств - Диалог формирования ремонтной ведомости
TechObjMakeEqRpSheet.propTypes = {
onOk: PropTypes.func,
onCancel: PropTypes.func
};
//Диалог формирования выборки данных для единицы оборудования
const TechObjMakeDataSet = ({ eqobjKind, measureUnit, onOk, onCancel }) => {
//Подключение к контексту приложения
const { pOnlineShowDictionary } = useContext(ApplicationСtx);
//Загрузка списка выборок данных
const { equipDataSelectionList } = useEquipDataSelectionList(true);
//Собственное состояние - значения формы
const [values, setValues] = useState({
dataSet: "",
eqobjKind: eqobjKind,
measureUnit: measureUnit || "",
userprocsData: "",
exsServiceUpload: "",
exsServiceFnUpload: "",
exsServiceSendMd: "",
exsServiceFnSendMd: "",
exsServiceSendRq: "",
exsServiceFnSendRq: "",
task: "RUL",
precisionP: null
});
//Отработка воода значения в форму
const handleValueChanged = (name, value) => setValues(pv => ({ ...pv, [name]: value }));
//Генерация содержимого
return (
<Dialog open={true} onClose={() => (onOk ? onCancel() : null)}>
<DialogTitle>Регистрация выборки данных класса технического объекта</DialogTitle>
<DialogContent sx={STYLES.TECH_OBJ_MAKE_DATASET_DIALOG_CONTENT}>
<IUDFormTextField
elementCode={"dataSet"}
elementValue={values.dataSet}
labelText={"Выборка данных"}
onChange={handleValueChanged}
list={equipDataSelectionList.filter(item => item.NRN != DS_RN_DEFAULT).map(item => item.SCODE)}
freeSolo={true}
/>
<IUDFormTextField
elementCode={"eqobjKind"}
elementValue={values.eqobjKind}
labelText={"Класс оборудования"}
onChange={handleValueChanged}
disabled
/>
<IUDFormTextField
elementCode={"measureUnit"}
elementValue={values.measureUnit}
labelText={"Едница измерения выборки"}
onChange={handleValueChanged}
dictionary={callBack => selectMeasureUnit(pOnlineShowDictionary, "measureUnit", callBack)}
/>
<IUDFormTextField
elementCode={"userprocsData"}
elementValue={values.userprocsData}
labelText={"Процедура формирования"}
onChange={handleValueChanged}
dictionary={callBack => selectUserProcsData(pOnlineShowDictionary, "userprocsData", callBack)}
/>
<IUDFormTextField
elementCode={"exsServiceUpload"}
elementValue={values.exsServiceUpload}
labelText={"Сервис обмена для выгрузки данных"}
onChange={handleValueChanged}
disabled
/>
<IUDFormTextField
elementCode={"exsServiceFnUpload"}
elementValue={values.exsServiceFnUpload}
labelText={"Функция обмена для выгрузки данных"}
onChange={handleValueChanged}
dictionary={callBack => selectServiceFn(pOnlineShowDictionary, "exsServiceFnUpload", callBack)}
/>
<IUDFormTextField
elementCode={"exsServiceSendMd"}
elementValue={values.exsServiceSendMd}
labelText={"Сервис обмена для передачи внешней системе"}
onChange={handleValueChanged}
disabled
/>
<IUDFormTextField
elementCode={"exsServiceFnSendMd"}
elementValue={values.exsServiceFnSendMd}
labelText={"Функция обмена для передачи внешней системе"}
onChange={handleValueChanged}
dictionary={callBack => selectServiceFn(pOnlineShowDictionary, "exsServiceFnSendMd", callBack)}
/>
<IUDFormTextField
elementCode={"exsServiceSendRq"}
elementValue={values.exsServiceSendRq}
labelText={"Сервис обмена для обработки внешней системой"}
onChange={handleValueChanged}
disabled
/>
<IUDFormTextField
elementCode={"exsServiceFnSendRq"}
elementValue={values.exsServiceFnSendRq}
labelText={"Функция обмена для обработки внешней системой"}
onChange={handleValueChanged}
dictionary={callBack => selectServiceFn(pOnlineShowDictionary, "exsServiceFnSendRq", callBack)}
/>
<IUDFormTextField
elementCode={"task"}
elementValue={values.task}
labelText={"Задача"}
onChange={handleValueChanged}
list={TASK_LIST}
/>
<IUDFormTextField
elementCode={"precisionP"}
elementValue={values.precisionP}
labelText={"Точность"}
onChange={handleValueChanged}
type={"number"}
/>
</DialogContent>
<DialogActions>
<Button onClick={() => (onOk ? onOk(values) : null)}>{BUTTONS.OK}</Button>
<Button onClick={() => (onOk ? onCancel() : null)}>{BUTTONS.CANCEL}</Button>
</DialogActions>
</Dialog>
);
};
//Контроль свойств - Диалог формирования выборки данных для единицы оборудования
TechObjMakeDataSet.propTypes = {
eqobjKind: PropTypes.string.isRequired,
measureUnit: PropTypes.string,
onOk: PropTypes.func,
onCancel: PropTypes.func
};
//----------------
//Интерфейс модуля
//----------------
export { TechObjCard, eqConfigTechObjTableValueFormatter, eqConfigTechObjTableDataCellRender, TechObjMakeEqRpSheet };
export { eqConfigTechObjTableValueFormatter, eqConfigTechObjTableDataCellRender, TechObjCard, TechObjMakeEqRpSheet, TechObjMakeDataSet };