Skip to content

Commit cb698d6

Browse files
authored
[O2B-1536] Add lastEditiedBy name to EOR reason section of the run-details page (#2090)
* [O2B-1536] Show lastEditedName for EOR reasons and display the lastEditedName for EOR reasons on `run-detail` page. * `formatEorReason` also renders a tooltip above the `lastEditedName` to make clear who it refers to. * [O2B-1536] Drop lastEditedName in addNewEorReason * [O2B-1532] Extract eorReasonComponent and revert formatter * [O2B-1536] Keep EOR lastEditedName out of patch; preserve for UI * [O2B-1536] Pass EOR lastEditedName through RunPatch * Stop keeping a separate `eorReasonLastEditedNames` list on RunDetailsModel and instead include `lastEditedName` on each eorReason within RunPatch.
1 parent ecbbda0 commit cb698d6

5 files changed

Lines changed: 72 additions & 14 deletions

File tree

lib/public/views/Runs/Details/RunPatch.js

Lines changed: 9 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,7 @@ import { RunQualities } from '../../../domain/enums/RunQualities.js';
99
* @property {string} category
1010
* @property {string} title
1111
* @property {string} description
12+
* @property {string|null} [lastEditedName]
1213
*/
1314

1415
/**
@@ -75,7 +76,8 @@ export class RunPatch extends Observable {
7576
}
7677

7778
if (this._eorReasons.length !== this._run.eorReasons.length || this._eorReasons.some(({ id }) => id === undefined)) {
78-
ret.eorReasons = this._eorReasons;
79+
// Strip lastEditedName — the server's EorReasonDto only accepts id, reasonTypeId, and description
80+
ret.eorReasons = this._eorReasons.map(({ id, reasonTypeId, description }) => ({ id, reasonTypeId, description }));
7981
}
8082

8183
if (this._hasRunQualityChange()) {
@@ -126,7 +128,12 @@ export class RunPatch extends Observable {
126128
} = this._run || {};
127129

128130
this._runQuality = runQuality;
129-
this._eorReasons = eorReasons.map(({ id, description, reasonTypeId }) => ({ id, description, reasonTypeId }));
131+
this._eorReasons = eorReasons.map(({ id, description, reasonTypeId, lastEditedName }) => ({
132+
id,
133+
description,
134+
reasonTypeId,
135+
lastEditedName,
136+
}));
130137
this._tags = tags.map(({ text }) => text);
131138

132139
this.formData = {

lib/public/views/Runs/Details/runDetailsComponent.js

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -40,7 +40,7 @@ import { RunDefinition } from '../../../domain/enums/RunDefinition.js';
4040
import { formatFloat } from '../../../utilities/formatting/formatFloat.js';
4141
import { formatEditableNumber } from '../format/formatEditableNumber.js';
4242
import { editRunEorReasons } from '../format/editRunEorReasons.js';
43-
import { formatEorReason } from '../format/formatEorReason.mjs';
43+
import { formatRunEorReason } from '../format/formatRunEorReason.js';
4444
import { selectionDropdown } from '../../../components/common/selection/dropdown/selectionDropdown.js';
4545
import { formatRunCalibrationStatus } from '../format/formatRunCalibrationStatus.js';
4646
import { BeamModes } from '../../../domain/enums/BeamModes.js';
@@ -533,7 +533,10 @@ export const runDetailsComponent = (runDetailsModel, router) => runDetailsModel.
533533
h('#eor-reasons.flex-row', [
534534
runDetailsModel.isEditModeEnabled
535535
? editRunEorReasons(runDetailsModel)
536-
: h('.flex-column.g2', run.eorReasons.map((eorReason) => h('.eor-reason', formatEorReason(eorReason)))),
536+
: h(
537+
'.flex-column.g2.w-100',
538+
run.eorReasons.map((eorReason) => h('.eor-reason', formatRunEorReason(eorReason))),
539+
),
537540
]),
538541
]),
539542
]),

lib/public/views/Runs/format/editRunEorReasons.js

Lines changed: 9 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -94,20 +94,23 @@ export const editRunEorReasons = (runDetailsModel) => {
9494
*/
9595
runDetailsModel.runPatch.eorReasons.length > 0
9696
? runDetailsModel.runPatch.eorReasons.map((eorReason) => {
97-
const { reasonTypeId, description } = eorReason;
97+
const { reasonTypeId, description, lastEditedName } = eorReason;
9898
const { category = '-', title } = eorReasonTypes.find((eorReasonType) => eorReasonType.id === reasonTypeId) || {};
9999
const titleString = title ? ` - ${title}` : '';
100100
const descriptionString = description ? ` - ${description}` : '';
101101
return h(
102-
'.flex-row.items-center',
102+
'.flex-row.justify-between',
103103
{
104104
key: `${category} ${titleString} ${descriptionString}`,
105105
},
106106
[
107-
h('label.remove-eor-reason.danger.ph1.actionable-icon', {
108-
onclick: () => runDetailsModel.runPatch.removeEorReason(eorReason),
109-
}, iconTrash()),
110-
h('.w-wrapped', `${category} ${titleString} ${descriptionString}`),
107+
h('.flex-row.items-center', [
108+
h('label.remove-eor-reason.danger.ph1.actionable-icon', {
109+
onclick: () => runDetailsModel.runPatch.removeEorReason(eorReason),
110+
}, iconTrash()),
111+
h('.w-wrapped', `${category} ${titleString} ${descriptionString}`),
112+
]),
113+
h('.w-wrapped', lastEditedName || null),
111114
],
112115
);
113116
})
Lines changed: 36 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,36 @@
1+
/**
2+
* @license
3+
* Copyright CERN and copyright holders of ALICE O2. This software is
4+
* distributed under the terms of the GNU General Public License v3 (GPL
5+
* Version 3), copied verbatim in the file "COPYING".
6+
*
7+
* See http://alice-o2.web.cern.ch/license for full licensing information.
8+
*
9+
* In applying this license CERN does not waive the privileges and immunities
10+
* granted to it by virtue of its status as an Intergovernmental Organization
11+
* or submit itself to any jurisdiction.
12+
*/
13+
14+
import { h } from '/js/src/index.js';
15+
import { tooltip } from '../../../../components/common/popover/tooltip.js';
16+
import { formatEorReason } from './formatEorReason.mjs';
17+
18+
/**
19+
* Display the given EoR reason as a vnode component with lastEditedName tooltip
20+
*
21+
* @param {Partial<{
22+
* category: string,
23+
* title: string,
24+
* description: string,
25+
* lastEditedName: string,
26+
* }>} eorReason the EoR reason to display
27+
* @return {VNode} the vnode component
28+
*/
29+
export const formatRunEorReason = (eorReason) => {
30+
const { lastEditedName } = eorReason;
31+
const reasonText = formatEorReason(eorReason);
32+
return h('.w-100.flex-row.justify-between', [
33+
h('', reasonText),
34+
lastEditedName ? tooltip(h('.w-wrapped', lastEditedName), 'Last edited by') : null,
35+
]);
36+
};

test/public/runs/detail.test.js

Lines changed: 13 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -208,10 +208,10 @@ module.exports = () => {
208208

209209
expect(eorReasons).to.lengthOf(2);
210210
expect(await eorReasons[0].evaluate((element) => element.innerText))
211-
.to.equal('DETECTORS - TPC - Some Reason other than selected plus one');
211+
.to.equal('DETECTORS - TPC - Some Reason other than selected plus one\nAnonymous');
212212

213213
expect(await eorReasons[1].evaluate((element) => element.innerText))
214-
.to.equal('DETECTORS - CPV - A new EOR reason');
214+
.to.equal('DETECTORS - CPV - A new EOR reason\nAnonymous');
215215
});
216216

217217
it('should successfully revert the update end of run reasons', async () => {
@@ -234,10 +234,19 @@ module.exports = () => {
234234

235235
expect(eorReasons).to.lengthOf(2);
236236
expect(await eorReasons[0].evaluate((element) => element.innerText))
237-
.to.equal('DETECTORS - TPC - Some Reason other than selected plus one');
237+
.to.equal('DETECTORS - TPC - Some Reason other than selected plus one\nAnonymous');
238238

239239
expect(await eorReasons[1].evaluate((element) => element.innerText))
240-
.to.equal('DETECTORS - CPV - A new EOR reason');
240+
.to.equal('DETECTORS - CPV - A new EOR reason\nAnonymous');
241+
});
242+
243+
it('should display lastEditedName tooltip with "Last edited by" on formatRunEorReason', async () => {
244+
const eorReasonElement = await page.$('#eor-reasons .eor-reason');
245+
const popoverTrigger = await eorReasonElement.$('.popover-trigger');
246+
expect(popoverTrigger).to.not.be.null;
247+
248+
const popoverContent = await getPopoverContent(popoverTrigger);
249+
expect(popoverContent).to.equal('Last edited by');
241250
});
242251

243252
it('should successfully update inelasticInteractionRate values of PbPb run', async () => {

0 commit comments

Comments
 (0)