[DURACOM-282] fix issue with removing duplicated json patch operations, which in some case changed the order in the queue

This commit is contained in:
Giuseppe Digilio
2024-06-19 13:11:40 +02:00
committed by Tim Donohue
parent fbb97167d6
commit 4eacdfb113
2 changed files with 387 additions and 3 deletions

View File

@@ -339,4 +339,384 @@ describe('jsonPatchOperationsReducer test suite', () => {
}); });
}); });
describe('dedupeOperationEntries', () => {
it('should not remove duplicated keys if operations are not sequential', () => {
initState = {
sections: {
children: {
publicationStep: {
body: [
{
operation: {
op: 'add',
path: '/sections/publicationStep/dc.date.issued',
value: [
{
value: '2024-06',
language: null,
authority: null,
display: '2024-06',
confidence: -1,
place: 0,
otherInformation: null,
},
],
},
timeCompleted: timestampBeforeStart,
},
{
operation: {
op: 'replace',
path: '/sections/publicationStep/dc.date.issued/0',
value: {
value: '2023-06-19',
language: null,
authority: null,
display: '2023-06-19',
confidence: -1,
place: 0,
otherInformation: null,
},
},
timeCompleted: timestampBeforeStart,
},
],
} as JsonPatchOperationsEntry,
},
transactionStartTime: null,
commitPending: false,
} as JsonPatchOperationsResourceEntry,
};
const value = [
{
value: '2024-06-19',
language: null,
authority: null,
display: '2024-06-19',
confidence: -1,
place: 0,
otherInformation: null,
},
];
const action = new NewPatchAddOperationAction(
'sections',
'publicationStep',
'/sections/publicationStep/dc.date.issued',
value);
const newState = jsonPatchOperationsReducer(initState, action);
const expectedBody: any = [
{
'operation': {
'op': 'add',
'path': '/sections/publicationStep/dc.date.issued',
'value': [
{
'value': '2024-06',
'language': null,
'authority': null,
'display': '2024-06',
'confidence': -1,
'place': 0,
'otherInformation': null,
},
],
},
'timeCompleted': timestampBeforeStart,
},
{
'operation': {
'op': 'replace',
'path': '/sections/publicationStep/dc.date.issued/0',
'value': {
'value': '2023-06-19',
'language': null,
'authority': null,
'display': '2023-06-19',
'confidence': -1,
'place': 0,
'otherInformation': null,
},
},
'timeCompleted': timestampBeforeStart,
},
{
'operation': {
'op': 'add',
'path': '/sections/publicationStep/dc.date.issued',
'value': [
{
'value': '2024-06-19',
'language': null,
'authority': null,
'display': '2024-06-19',
'confidence': -1,
'place': 0,
'otherInformation': null,
},
],
},
'timeCompleted': timestampBeforeStart,
},
];
expect(newState.sections.children.publicationStep.body).toEqual(expectedBody);
});
it('should remove duplicated keys if operations are sequential', () => {
initState = {
sections: {
children: {
publicationStep: {
body: [
{
operation: {
op: 'add',
path: '/sections/publicationStep/dc.date.issued',
value: [
{
value: '2024-06',
language: null,
authority: null,
display: '2024-06',
confidence: -1,
place: 0,
otherInformation: null,
},
],
},
timeCompleted: timestampBeforeStart,
},
{
operation: {
op: 'replace',
path: '/sections/publicationStep/dc.date.issued/0',
value: {
value: '2023-06-19',
language: null,
authority: null,
display: '2023-06-19',
confidence: -1,
place: 0,
otherInformation: null,
},
},
timeCompleted: timestampBeforeStart,
},
{
'operation': {
'op': 'add',
'path': '/sections/publicationStep/dc.date.issued',
'value': [
{
'value': '2024-06-19',
'language': null,
'authority': null,
'display': '2024-06-19',
'confidence': -1,
'place': 0,
'otherInformation': null,
},
],
},
'timeCompleted': timestampBeforeStart,
},
],
} as JsonPatchOperationsEntry,
},
transactionStartTime: null,
commitPending: false,
} as JsonPatchOperationsResourceEntry,
};
const value = [
{
value: '2024-06-20',
language: null,
authority: null,
display: '2024-06-20',
confidence: -1,
place: 0,
otherInformation: null,
},
];
const action = new NewPatchAddOperationAction(
'sections',
'publicationStep',
'/sections/publicationStep/dc.date.issued',
value);
const newState = jsonPatchOperationsReducer(initState, action);
const expectedBody: any = [
{
'operation': {
'op': 'add',
'path': '/sections/publicationStep/dc.date.issued',
'value': [
{
'value': '2024-06',
'language': null,
'authority': null,
'display': '2024-06',
'confidence': -1,
'place': 0,
'otherInformation': null,
},
],
},
'timeCompleted': timestampBeforeStart,
},
{
'operation': {
'op': 'replace',
'path': '/sections/publicationStep/dc.date.issued/0',
'value': {
'value': '2023-06-19',
'language': null,
'authority': null,
'display': '2023-06-19',
'confidence': -1,
'place': 0,
'otherInformation': null,
},
},
'timeCompleted': timestampBeforeStart,
},
{
'operation': {
'op': 'add',
'path': '/sections/publicationStep/dc.date.issued',
'value': [
{
'value': '2024-06-20',
'language': null,
'authority': null,
'display': '2024-06-20',
'confidence': -1,
'place': 0,
'otherInformation': null,
},
],
},
'timeCompleted': timestampBeforeStart,
},
];
expect(newState.sections.children.publicationStep.body).toEqual(expectedBody);
});
it('should remove duplicated keys if all operations have same key', () => {
initState = {
sections: {
children: {
publicationStep: {
body: [
{
operation: {
op: 'add',
path: '/sections/publicationStep/dc.date.issued',
value: [
{
value: '2024',
language: null,
authority: null,
display: '2024-06',
confidence: -1,
place: 0,
otherInformation: null,
},
],
},
timeCompleted: timestampBeforeStart,
},
{
'operation': {
'op': 'add',
'path': '/sections/publicationStep/dc.date.issued',
'value': [
{
'value': '2024-06',
'language': null,
'authority': null,
'display': '2024-06',
'confidence': -1,
'place': 0,
'otherInformation': null,
},
],
},
'timeCompleted': timestampBeforeStart,
},
{
'operation': {
'op': 'add',
'path': '/sections/publicationStep/dc.date.issued',
'value': [
{
'value': '2024-06-19',
'language': null,
'authority': null,
'display': '2024-06-19',
'confidence': -1,
'place': 0,
'otherInformation': null,
},
],
},
'timeCompleted': timestampBeforeStart,
},
],
} as JsonPatchOperationsEntry,
},
transactionStartTime: null,
commitPending: false,
} as JsonPatchOperationsResourceEntry,
};
const value = [
{
value: '2024-06-20',
language: null,
authority: null,
display: '2024-06-20',
confidence: -1,
place: 0,
otherInformation: null,
},
];
const action = new NewPatchAddOperationAction(
'sections',
'publicationStep',
'/sections/publicationStep/dc.date.issued',
value);
const newState = jsonPatchOperationsReducer(initState, action);
const expectedBody: any = [
{
'operation': {
'op': 'add',
'path': '/sections/publicationStep/dc.date.issued',
'value': [
{
'value': '2024-06-20',
'language': null,
'authority': null,
'display': '2024-06-20',
'confidence': -1,
'place': 0,
'otherInformation': null,
},
],
},
'timeCompleted': timestampBeforeStart,
},
];
expect(newState.sections.children.publicationStep.body).toEqual(expectedBody);
});
});
}); });

View File

@@ -361,14 +361,18 @@ function addOperationToList(body: JsonPatchOperationObject[], actionType, target
* @returns deduped JSON patch operation object entries * @returns deduped JSON patch operation object entries
*/ */
function dedupeOperationEntries(body: JsonPatchOperationObject[]): JsonPatchOperationObject[] { function dedupeOperationEntries(body: JsonPatchOperationObject[]): JsonPatchOperationObject[] {
const ops = new Map<string, any>(); const ops = new Map<string, number>();
for (let i = body.length - 1; i >= 0; i--) { for (let i = body.length - 1; i >= 0; i--) {
const patch = body[i].operation; const patch = body[i].operation;
const key = `${patch.op}-${patch.path}`; const key = `${patch.op}-${patch.path}`;
if (!ops.has(key)) { if (!ops.has(key)) {
ops.set(key, patch); ops.set(key, i);
} else { } else {
body.splice(i, 1); const entry = ops.get(key);
if (entry - 1 === i) {
body.splice(i, 1);
ops.set(key, i);
}
} }
} }