diff --git a/src/apps/opportunities/src/components/ChallengeDetailHeader.spec.tsx b/src/apps/opportunities/src/components/ChallengeDetailHeader.spec.tsx index e6f38df13..ab8ae2403 100644 --- a/src/apps/opportunities/src/components/ChallengeDetailHeader.spec.tsx +++ b/src/apps/opportunities/src/components/ChallengeDetailHeader.spec.tsx @@ -672,22 +672,116 @@ describe('ChallengeDetailHeader actions and presentation', () => { }) }) - it('retains a future Iterative Review deadline in a Task timeline', () => { + it.each([ + { + challengeEnd: '2026-08-31T17:44:00.000Z', + challengeStart: '2026-08-10T17:44:00.000Z', + isOpen: true, + phaseEnd: '2026-08-15T17:44:00.000Z', + phaseStart: '2026-08-13T17:44:00.000Z', + state: 'current', + }, + { + challengeEnd: '2999-08-31T17:44:00.000Z', + challengeStart: '2999-08-10T17:44:00.000Z', + isOpen: false, + phaseEnd: '2999-08-21T17:44:00.000Z', + phaseStart: '2999-08-20T17:44:00.000Z', + state: 'future', + }, + ])('omits a $state Iterative Review phase from a Task timeline', ({ + challengeEnd, + challengeStart, + isOpen, + phaseEnd, + phaseStart, + }: { + challengeEnd: string + challengeStart: string + isOpen: boolean + phaseEnd: string + phaseStart: string + }) => { + const { container }: RenderResult = render( + + + , + ) + + fireEvent.click(screen.getByRole('button', { name: 'Show full timeline' })) + const timeline = screen.getByRole('region', { name: 'Challenge timeline' }) + const itemLabels = within(timeline) + .getAllByRole('listitem') + .map(item => item.querySelector('strong')?.textContent) + expect(itemLabels) + .toEqual(['Launch', 'Registration', 'Submission', 'Winners']) + expect(within(timeline) + .queryByText('Iterative Review')) + .not.toBeInTheDocument() + expect(container.querySelector('.timelineItems')) + .toHaveStyle({ + gridTemplateColumns: '88px minmax(0, 1fr) minmax(0, 1fr) 88px', + }) + }) + + it('retains Iterative Review for non-Task challenge timelines', () => { render( { - const phaseKey = challengeCatalogKey(item.name) - if (!taskChallenge || !phaseKey.includes('iterativereview')) return true - const phaseEnd = timelineTimestamp(item.actualEndDate ?? item.scheduledEndDate) - return phaseEnd !== undefined && phaseEnd > now - }) + const authoredPhases = (challenge.phases ?? []).filter(item => ( + !taskChallenge || !challengeCatalogKey(item.name) + .includes('iterativereview') + )) const phases = authoredPhases .map((item, index) => ({ index, item })) .sort((left: IndexedChallengePhase, right: IndexedChallengePhase) => {