diff --git a/src/lib/mappers/tests/content-item-mapper.test.ts b/src/lib/mappers/tests/content-item-mapper.test.ts index 2cdd43e..2aac435 100644 --- a/src/lib/mappers/tests/content-item-mapper.test.ts +++ b/src/lib/mappers/tests/content-item-mapper.test.ts @@ -179,6 +179,16 @@ describe('ContentItemMapper.addMapping', () => { mapper.addMapping(makeItem({ contentID: 10 }), makeItem({ contentID: 21 })) ).toThrow('Invalid Mappings detected'); }); + + it('throws when source already has a mapping but a different unmapped target is provided (duplicate mapping attempt)', () => { + const mapper = makeMapper(); + // source 10 is already mapped to target 20 + mapper.addMapping(makeItem({ contentID: 10 }), makeItem({ contentID: 20 })); + // now try to map source 10 to target 99 — target 99 has no mapping, but source already points to 20 + expect(() => + mapper.addMapping(makeItem({ contentID: 10 }), makeItem({ contentID: 99 })) + ).toThrow('Aborting a duplicate mapping attempt'); + }); }); // ─── hasSourceChanged ───────────────────────────────────────────────────────── diff --git a/src/lib/pushers/content-pusher/util/tests/get-content-item-types.test.ts b/src/lib/pushers/content-pusher/util/tests/get-content-item-types.test.ts index b8ac3b0..96d4c34 100644 --- a/src/lib/pushers/content-pusher/util/tests/get-content-item-types.test.ts +++ b/src/lib/pushers/content-pusher/util/tests/get-content-item-types.test.ts @@ -191,6 +191,23 @@ describe('getContentItemTypes — linked items', () => { expect(result.linkedContentItems[0]).toBe(linkedItem); }); + it('item already in linkedSet is not re-added to normalSet when its own loop iteration runs', () => { + // parent is first in the array — when processed, it marks linkedItem as linked + // linkedItem comes second — without the fix, its loop iteration would add it back to normalSet + const linkedItem = makeItem('linked-ref', 'ModelLinked'); + const parentItem = makeItem('parent-ref', 'ModelParent', { + items: { referenceName: 'linked-ref', fullList: true }, + }); + + const result = getContentItemTypes([parentItem, linkedItem], makeValidOpts()); + expect(result.linkedContentItems).toHaveLength(1); + expect(result.linkedContentItems[0]).toBe(linkedItem); + expect(result.normalContentItems).toHaveLength(1); + expect(result.normalContentItems[0]).toBe(parentItem); + // linkedItem must not appear in normalContentItems + expect(result.normalContentItems).not.toContain(linkedItem); + }); + it('item referenced by multiple parents ends up as linked only once', () => { const sharedItem = makeItem('shared-ref', 'ModelShared'); const parent1 = makeItem('parent-1', 'ModelParent', {