Co-authored-by: gorbenko.pavel <gorbenko.pavel@tansu.kz> Reviewed-on: http://git.tnsu.kz/timur.gorodetskiy/request-portal/pulls/6
This commit was merged in pull request #6.
This commit is contained in:
@@ -32,6 +32,8 @@ const FIELDS = {
|
||||
allowReassign: 'AllowReassignToOtherApprovers', // «Можно перепоручать» (Да/Нет)
|
||||
phase: 'Phase', // «Фаза» (Choice): Согласование | Исполнение
|
||||
delegatedBy: 'DelegatedBy', // «Кем переназначено» (User) → DelegatedById
|
||||
slaHours: 'SLAhours', // «SLA, часов» (Number) — пусто значит «взять у типа заявки»
|
||||
askOverdueReason: 'AskOverdueReason', // «Опрос причины просрочки» (Да/Нет)
|
||||
};
|
||||
|
||||
// Согласующий для записи в список.
|
||||
@@ -45,6 +47,18 @@ export interface IApproverToWrite {
|
||||
* (ApprovalMatrix/useMatrixEditor) всегда даёт уникальный order по позиции —
|
||||
* это поле для параллельных шагов, приходящих из внешнего маршрута напрямую. */
|
||||
order?: number;
|
||||
/**
|
||||
* SLA шага в часах и признак опроса причины просрочки — приходят из resolve
|
||||
* с уже применённым наследованием «шаг перекрывает тип заявки» (см. бэкенд
|
||||
* ResolveStepAsync). Портал их не вычисляет, только переносит в строку.
|
||||
*
|
||||
* undefined/null — «в строке не задано»: тогда напоминания используют SLA
|
||||
* типа заявки. Ноль — это НЕ пусто, а «напоминать сразу».
|
||||
*/
|
||||
// eslint-disable-next-line @rushstack/no-new-null -- null = «не задано» (в SharePoint пустая колонка)
|
||||
slaHours?: number | null;
|
||||
// eslint-disable-next-line @rushstack/no-new-null -- см. slaHours
|
||||
askOverdueReason?: boolean | null;
|
||||
}
|
||||
|
||||
// Все запросы к списку «<форма> — согласование». listTitle задаётся формой.
|
||||
@@ -101,6 +115,9 @@ export class ApprovalListService {
|
||||
[FIELDS.order]: order,
|
||||
[FIELDS.allowReassign]: a.allowReassign,
|
||||
[FIELDS.phase]: phase,
|
||||
// ?? null, а не || null: ноль часов — значимое значение.
|
||||
[FIELDS.slaHours]: a.slaHours ?? null,
|
||||
[FIELDS.askOverdueReason]: a.askOverdueReason ?? null,
|
||||
});
|
||||
}
|
||||
}
|
||||
@@ -222,6 +239,8 @@ export class ApprovalListService {
|
||||
FIELDS.order,
|
||||
FIELDS.allowReassign,
|
||||
FIELDS.phase,
|
||||
FIELDS.slaHours,
|
||||
FIELDS.askOverdueReason,
|
||||
`${FIELDS.approver}/Title`,
|
||||
`${FIELDS.approver}/EMail`
|
||||
)
|
||||
@@ -240,6 +259,11 @@ export class ApprovalListService {
|
||||
comment: (r[FIELDS.comment] as string) || '',
|
||||
allowReassign: (r[FIELDS.allowReassign] as boolean) ?? false,
|
||||
phase: (r[FIELDS.phase] as string) || APPROVAL_PHASE.approval,
|
||||
// Читаем, чтобы не потерять при пересохранении: writeRoute удаляет
|
||||
// строки и создаёт их заново из матрицы, и без этих полей SLA,
|
||||
// проставленный при первой отправке, обнулился бы у черновика.
|
||||
slaHours: (r[FIELDS.slaHours] as number | null) ?? null,
|
||||
askOverdueReason: (r[FIELDS.askOverdueReason] as boolean | null) ?? null,
|
||||
};
|
||||
});
|
||||
}
|
||||
|
||||
@@ -33,6 +33,8 @@ export async function getPlannedMatrix(
|
||||
comment: '',
|
||||
allowReassign: s.allowReassignToOtherApprovers,
|
||||
phase,
|
||||
slaHours: s.slaHours,
|
||||
askOverdueReason: s.askOverdueReason,
|
||||
}))
|
||||
);
|
||||
}
|
||||
|
||||
@@ -47,4 +47,12 @@ export interface IResolvedRouteStep {
|
||||
// Предупреждение маршрута по этому шагу (например, роль не разрешилась в
|
||||
// конкретного человека) — приходит от API, показываем автору при желании.
|
||||
warning: string | null;
|
||||
// SLA шага в часах и признак опроса причины просрочки. Наследование
|
||||
// «шаг перекрывает тип заявки» бэкенд уже применил — здесь итоговое значение,
|
||||
// его достаточно записать в строку списка согласования.
|
||||
// null — SLA не настроен, напоминаний по шагу не будет.
|
||||
// eslint-disable-next-line @rushstack/no-new-null -- зеркалит nullable-контракт бэкенда
|
||||
slaHours: number | null;
|
||||
// eslint-disable-next-line @rushstack/no-new-null -- см. slaHours
|
||||
askOverdueReason: boolean | null;
|
||||
}
|
||||
|
||||
@@ -15,4 +15,16 @@ export interface IMatrixRow {
|
||||
// редактировании — переключается кнопкой и заново раздаёт order (см.
|
||||
// useMatrixEditor/withOrders).
|
||||
parallelWithPrev?: boolean;
|
||||
/**
|
||||
* SLA шага и признак опроса причины просрочки. Матрица здесь — транзитное
|
||||
* звено: значения приходят из resolve (или читаются из уже записанных строк)
|
||||
* и уходят обратно в список при сохранении. На форме они не показываются и
|
||||
* не редактируются — правятся в админке.
|
||||
*
|
||||
* null/undefined — «не задано», работает SLA типа заявки. Ноль — «сразу».
|
||||
*/
|
||||
// eslint-disable-next-line @rushstack/no-new-null -- null приходит из SharePoint и значит «не задано»
|
||||
slaHours?: number | null;
|
||||
// eslint-disable-next-line @rushstack/no-new-null -- см. slaHours
|
||||
askOverdueReason?: boolean | null;
|
||||
}
|
||||
|
||||
@@ -79,6 +79,12 @@ export const ApprovalMatrix: React.FC<IApprovalMatrixProps> = ({
|
||||
// Пустые колонки не показываем — столбец из одних прочерков только шумит.
|
||||
const hasStatuses = rows.some((r) => r.status && r.status !== '—');
|
||||
const hasDates = rows.some((r) => !!r.date);
|
||||
// slaHours на строке — уже ИТОГОВОЕ значение с применённым наследованием
|
||||
// (шаг перекрывает тип заявки): для черновика его так отдаёт resolve
|
||||
// (getPlannedMatrix), для поданной заявки — то, что записали в строку при
|
||||
// отправке (см. writeRoute). Здесь его достаточно просто показать, повторно
|
||||
// резолвить нечего.
|
||||
const hasSla = rows.some((r) => r.slaHours !== undefined && r.slaHours !== null);
|
||||
|
||||
// Число колонок (для colSpan) — на случай будущих нужд не используется: комментарий
|
||||
// выводим внутри ячейки согласующего, чтобы не ломать rowSpan колонки «Шаг».
|
||||
@@ -101,6 +107,7 @@ export const ApprovalMatrix: React.FC<IApprovalMatrixProps> = ({
|
||||
<th>Должность</th>
|
||||
{hasStatuses && <th>Статус</th>}
|
||||
{hasDates && <th>Дата</th>}
|
||||
{hasSla && <th>SLA</th>}
|
||||
{editable && <th />}
|
||||
{editable && <th />}
|
||||
</tr>
|
||||
@@ -137,6 +144,9 @@ export const ApprovalMatrix: React.FC<IApprovalMatrixProps> = ({
|
||||
</td>
|
||||
)}
|
||||
{hasDates && <td data-label="Дата">{r.date}</td>}
|
||||
{hasSla && (
|
||||
<td data-label="SLA">{r.slaHours || r.slaHours === 0 ? `${r.slaHours} ч` : '—'}</td>
|
||||
)}
|
||||
{/* Перемещение действует на ШАГ целиком (параллельные строки
|
||||
переезжают вместе): одна пара стрелок на весь шаг. */}
|
||||
{editable && isBlockStart && (
|
||||
|
||||
Reference in New Issue
Block a user