tods-competition-factory 7.26.0 → 7.28.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/esm/acquire/findStructure.mjs +2 -2
- package/dist/esm/assemblies/engines/async/public.mjs +8 -0
- package/dist/esm/assemblies/engines/parts/engineStart.mjs +1 -1
- package/dist/esm/assemblies/engines/parts/stateMethods.mjs +1 -1
- package/dist/esm/assemblies/engines/scoring/v2/actions.mjs +2 -0
- package/dist/esm/assemblies/engines/scoring/v2/decide.mjs +34 -0
- package/dist/esm/assemblies/engines/scoring/v2/engine.mjs +72 -9
- package/dist/esm/assemblies/engines/scoring/v2/format.mjs +30 -2
- package/dist/esm/assemblies/engines/scoring/v2/overtime.mjs +30 -0
- package/dist/esm/assemblies/engines/scoring/v2/record.mjs +6 -0
- package/dist/esm/assemblies/engines/scoring/v2/reduce.mjs +73 -12
- package/dist/esm/assemblies/engines/scoring/v2/score.mjs +7 -2
- package/dist/esm/assemblies/engines/scoring/v2/view.mjs +3 -0
- package/dist/esm/assemblies/generators/drawDefinitions/drawTypes/adHoc/drawMatic/generateDrawMaticRound.mjs +1 -1
- package/dist/esm/assemblies/generators/drawDefinitions/drawTypes/adHoc/swiss/generateSwissRound.mjs +1 -1
- package/dist/esm/assemblies/generators/drawDefinitions/drawTypes/generateVoluntaryConsolation.mjs +1 -1
- package/dist/esm/assemblies/generators/drawDefinitions/generateAndPopulatePlayoffStructures.mjs +1 -1
- package/dist/esm/assemblies/generators/drawDefinitions/generateDrawDefinition/checkQualifyingEntriesFit.mjs +40 -0
- package/dist/esm/assemblies/generators/drawDefinitions/generateDrawDefinition/entriesNotPlaced.mjs +35 -0
- package/dist/esm/assemblies/generators/drawDefinitions/generateDrawDefinition/generateDrawDefinition.mjs +5 -2
- package/dist/esm/assemblies/generators/drawDefinitions/generateDrawDefinition/generateNewDrawDefinition.mjs +29 -7
- package/dist/esm/assemblies/generators/drawDefinitions/generateDrawDefinition/generateOrGetExisting.mjs +24 -2
- package/dist/esm/assemblies/generators/drawDefinitions/generateDrawDefinition/processExistingDrawDefinition.mjs +33 -5
- package/dist/esm/assemblies/generators/drawDefinitions/generateDrawStructuresAndLinks.mjs +1 -1
- package/dist/esm/assemblies/generators/drawDefinitions/generateDrawTypeAndModifyDrawDefinition.mjs +1 -1
- package/dist/esm/assemblies/generators/drawDefinitions/generateFlightProfile.mjs +59 -8
- package/dist/esm/assemblies/generators/drawDefinitions/getDrawFormat.mjs +2 -0
- package/dist/esm/assemblies/generators/drawDefinitions/validateAndDeriveDrawValues.mjs +4 -2
- package/dist/esm/assemblies/generators/mocks/generateSeason.mjs +97 -0
- package/dist/esm/assemblies/generators/mocks/modifyTournamentRecord.mjs +1 -1
- package/dist/esm/assemblies/generators/mocks/processLeagueProfiles.mjs +2 -1
- package/dist/esm/assemblies/generators/scheduling/utils/defaultPeriodLength.mjs +33 -0
- package/dist/esm/assemblies/generators/scheduling/utils/generateBookings.mjs +2 -0
- package/dist/esm/assemblies/generators/scheduling/utils/generateScheduleTimes.mjs +2 -0
- package/dist/esm/assemblies/generators/tournamentRecords/anonymizeTournamentRecord.mjs +259 -242
- package/dist/esm/assemblies/generators/tournamentRecords/generateStatCrew.mjs +51 -19
- package/dist/esm/assemblies/generators/venues/generateCourts.mjs +1 -1
- package/dist/esm/assemblies/governors/drawsGovernor/index.mjs +1 -0
- package/dist/esm/assemblies/governors/drawsGovernor/mutate.mjs +1 -0
- package/dist/esm/assemblies/governors/entriesGovernor/index.mjs +2 -0
- package/dist/esm/assemblies/governors/entriesGovernor/query.mjs +2 -0
- package/dist/esm/assemblies/governors/index.mjs +10 -8
- package/dist/esm/assemblies/governors/matchUpFormatGovernor/index.mjs +1 -1
- package/dist/esm/assemblies/governors/matchUpGovernor/index.mjs +2 -0
- package/dist/esm/assemblies/governors/matchUpGovernor/query.mjs +2 -0
- package/dist/esm/assemblies/governors/mocksGovernor/generate.mjs +1 -0
- package/dist/esm/assemblies/governors/mocksGovernor/index.mjs +1 -0
- package/dist/esm/assemblies/governors/queryGovernor/index.mjs +6 -0
- package/dist/esm/assemblies/governors/scheduleGovernor/index.mjs +2 -0
- package/dist/esm/assemblies/governors/scheduleGovernor/query.mjs +2 -0
- package/dist/esm/assemblies/governors/seasonGovernor/index.mjs +7 -0
- package/dist/esm/assemblies/governors/seasonGovernor/query.mjs +5 -0
- package/dist/esm/assemblies/governors/tournamentGovernor/index.mjs +1 -0
- package/dist/esm/assemblies/governors/tournamentGovernor/mutate.mjs +1 -0
- package/dist/esm/constants/dualIssueConstants.mjs +22 -0
- package/dist/esm/constants/entryStatusConstants.mjs +1 -1
- package/dist/esm/constants/errorConditionConstants.mjs +26 -1
- package/dist/esm/constants/flightConstants.mjs +7 -1
- package/dist/esm/constants/homeParticipantConstants.mjs +12 -0
- package/dist/esm/constants/index.mjs +3 -0
- package/dist/esm/constants/matchUpFormatConstants.mjs +1 -0
- package/dist/esm/constants/mutationLockScopeMap.mjs +1 -0
- package/dist/esm/constants/policyConstants.mjs +1 -0
- package/dist/esm/constants/seasonConstants.mjs +27 -0
- package/dist/esm/fixtures/policies/POLICY_ROUND_ROBIN_TALLY_FIBA.mjs +28 -0
- package/dist/esm/fixtures/policies/POLICY_ROUND_ROBIN_TALLY_USTA_LEAGUE.mjs +21 -0
- package/dist/esm/fixtures/policies/index.mjs +4 -0
- package/dist/esm/functions/sorters/structureSort.mjs +1 -1
- package/dist/esm/global/state/globalState.mjs +3 -3
- package/dist/esm/helpers/matchUpFormatCode/aggregateDecider.mjs +8 -0
- package/dist/esm/helpers/matchUpFormatCode/overtimeContext.mjs +67 -0
- package/dist/esm/helpers/matchUpFormatCode/overtimeFormat.mjs +40 -0
- package/dist/esm/helpers/matchUpFormatCode/parse.mjs +36 -8
- package/dist/esm/helpers/matchUpFormatCode/stringify.mjs +15 -3
- package/dist/esm/helpers/matchUpTypeOptions.mjs +30 -0
- package/dist/esm/helpers/parameters/checkRequiredParameters.mjs +3 -1
- package/dist/esm/index.mjs +17 -13
- package/dist/esm/mutate/drawDefinitions/addDrawDefinition.mjs +22 -7
- package/dist/esm/mutate/drawDefinitions/addDrawEntries.mjs +2 -0
- package/dist/esm/mutate/drawDefinitions/addLinkedConsolationStructure.mjs +1 -1
- package/dist/esm/mutate/drawDefinitions/competition/processCompetitionMatchUp.mjs +5 -79
- package/dist/esm/mutate/drawDefinitions/competition/processCompetitionRound.mjs +13 -24
- package/dist/esm/mutate/drawDefinitions/entryGovernor/addDrawEntries.mjs +6 -2
- package/dist/esm/mutate/drawDefinitions/entryGovernor/modifySeedAssignment.mjs +8 -1
- package/dist/esm/mutate/drawDefinitions/links/repairMalformedLinks.mjs +1 -1
- package/dist/esm/mutate/drawDefinitions/matchUpGovernor/attemptToSetWinningSide.mjs +1 -1
- package/dist/esm/mutate/drawDefinitions/matchUpGovernor/noDownstreamDependencies.mjs +19 -9
- package/dist/esm/mutate/drawDefinitions/matchUpGovernor/setDelegatedOutcome.mjs +4 -0
- package/dist/esm/mutate/drawDefinitions/matchUpGovernor/setOrderOfFinish.mjs +23 -4
- package/dist/esm/mutate/drawDefinitions/modifyDrawName.mjs +1 -1
- package/dist/esm/mutate/drawDefinitions/modifyPairAssignment.mjs +1 -1
- package/dist/esm/mutate/drawDefinitions/positionGovernor/qualifierProgression.mjs +18 -3
- package/dist/esm/mutate/drawDefinitions/removeSeededParticipant.mjs +9 -1
- package/dist/esm/mutate/drawDefinitions/resetDrawDefinition.mjs +10 -8
- package/dist/esm/mutate/drawDefinitions/resetQualifyingStructure.mjs +1 -1
- package/dist/esm/mutate/drawDefinitions/resetStructure.mjs +66 -0
- package/dist/esm/mutate/entries/addEventEntries.mjs +2 -2
- package/dist/esm/mutate/entries/modifyEntriesStatus.mjs +22 -10
- package/dist/esm/mutate/entries/moveEntryToGroup.mjs +38 -0
- package/dist/esm/mutate/entries/promoteAlternate.mjs +88 -63
- package/dist/esm/mutate/entries/refreshEntryPositions.mjs +2 -1
- package/dist/esm/mutate/events/addFlight.mjs +10 -1
- package/dist/esm/mutate/events/deleteDrawDefinitions.mjs +1 -1
- package/dist/esm/mutate/events/deleteEvent.mjs +1 -1
- package/dist/esm/mutate/events/deleteFlightAndFlightDraw.mjs +14 -14
- package/dist/esm/mutate/events/modifyEvent.mjs +30 -1
- package/dist/esm/mutate/events/refreshEventDrawOrder.mjs +6 -4
- package/dist/esm/mutate/events/setEventDates.mjs +37 -2
- package/dist/esm/mutate/events/updateDrawIdsOrder.mjs +2 -1
- package/dist/esm/mutate/extensions/events/modifyEventMatchUpFormatTiming.mjs +2 -2
- package/dist/esm/mutate/extensions/policies/attachPolicies.mjs +49 -25
- package/dist/esm/mutate/extensions/policies/removePolicy.mjs +11 -12
- package/dist/esm/mutate/matchUps/drawPositions/adHocPositionSwap.mjs +1 -1
- package/dist/esm/mutate/matchUps/drawPositions/assignDrawPositionBye.mjs +1 -1
- package/dist/esm/mutate/matchUps/drawPositions/assignMatchUpSideParticipant.mjs +5 -1
- package/dist/esm/mutate/matchUps/drawPositions/removeDirectedParticipants.mjs +6 -3
- package/dist/esm/mutate/matchUps/lineUps/applyLineUps.mjs +15 -0
- package/dist/esm/mutate/matchUps/lineUps/assignTieMatchUpParticipant.mjs +3 -3
- package/dist/esm/mutate/matchUps/lineUps/removeTieMatchUpParticipant.mjs +1 -1
- package/dist/esm/mutate/matchUps/lineUps/replaceTieMatchUpParticipant.mjs +2 -2
- package/dist/esm/mutate/matchUps/matchUpFormat/applyMatchUpFormat.mjs +8 -6
- package/dist/esm/mutate/matchUps/matchUpFormat/setMatchUpFormat.mjs +30 -18
- package/dist/esm/mutate/matchUps/matchUpStatus/setMatchUpState.mjs +29 -11
- package/dist/esm/mutate/matchUps/matchUpStatus/setMatchUpStatus.mjs +9 -5
- package/dist/esm/mutate/matchUps/outcome/apply.mjs +39 -6
- package/dist/esm/mutate/matchUps/outcome/decide.mjs +42 -7
- package/dist/esm/mutate/matchUps/outcome/differential.mjs +1 -11
- package/dist/esm/mutate/matchUps/outcome/finishingOrderOps.mjs +57 -0
- package/dist/esm/mutate/matchUps/outcome/ops.mjs +32 -1
- package/dist/esm/mutate/matchUps/outcome/plan.mjs +718 -185
- package/dist/esm/mutate/matchUps/outcome/refusals.mjs +34 -6
- package/dist/esm/mutate/matchUps/outcome/shadow.mjs +2 -2
- package/dist/esm/mutate/matchUps/outcome/unwindWalk.mjs +378 -0
- package/dist/esm/mutate/matchUps/outcome/view.mjs +281 -19
- package/dist/esm/mutate/matchUps/resetScorecard.mjs +19 -1
- package/dist/esm/mutate/matchUps/schedule/addSchedulingProfileRound.mjs +19 -2
- package/dist/esm/mutate/matchUps/schedule/bulkRescheduleMatchUps.mjs +15 -5
- package/dist/esm/mutate/matchUps/schedule/bulkScheduleMatchUps.mjs +1 -1
- package/dist/esm/mutate/matchUps/schedule/bulkUpdateCourtAssignments.mjs +1 -1
- package/dist/esm/mutate/matchUps/schedule/pipeline/periodStages.mjs +49 -0
- package/dist/esm/mutate/matchUps/schedule/pipeline/plan.mjs +13 -2
- package/dist/esm/mutate/matchUps/schedule/pipeline/scheduleProfile.mjs +30 -1
- package/dist/esm/mutate/matchUps/schedule/pipeline/view.mjs +43 -5
- package/dist/esm/mutate/matchUps/schedule/pipeline/write.mjs +14 -6
- package/dist/esm/mutate/matchUps/schedule/reorderUpcomingMatchUps.mjs +1 -1
- package/dist/esm/mutate/matchUps/schedule/scheduleItems/addMatchUpScheduledDate.mjs +7 -2
- package/dist/esm/mutate/matchUps/schedule/scheduleItems/scheduleItems.mjs +45 -7
- package/dist/esm/mutate/matchUps/schedule/scheduleItems/setMatchUpHomeParticipantId.mjs +1 -1
- package/dist/esm/mutate/matchUps/schedule/scheduleMatchUps/calculateScheduleTimes.mjs +2 -0
- package/dist/esm/mutate/matchUps/schedule/scheduleMatchUps/resolveScheduleMatchUpsTiming.mjs +2 -1
- package/dist/esm/mutate/matchUps/schedule/scheduleMatchUps/scheduleMatchUps.mjs +42 -4
- package/dist/esm/mutate/matchUps/schedule/scheduleProfileGrid.mjs +44 -3
- package/dist/esm/mutate/matchUps/schedule/scheduledTime.mjs +5 -2
- package/dist/esm/mutate/matchUps/schedule/schedulers/auditAutoScheduling.mjs +3 -0
- package/dist/esm/mutate/matchUps/schedule/schedulers/proScheduler/proAutoSchedule.mjs +31 -3
- package/dist/esm/mutate/matchUps/schedule/schedulers/processAlreadyScheduledMatchUps.mjs +2 -1
- package/dist/esm/mutate/matchUps/score/modifyMatchUpScore.mjs +42 -3
- package/dist/esm/mutate/notifications/drawNotifications.mjs +1 -1
- package/dist/esm/mutate/participants/addParticipant.mjs +2 -2
- package/dist/esm/mutate/participants/createTeamsFromAttributes.mjs +3 -2
- package/dist/esm/mutate/participants/deleteParticipants.mjs +1 -1
- package/dist/esm/mutate/participants/modifyParticipant.mjs +235 -150
- package/dist/esm/mutate/participants/modifyPersonFields.mjs +159 -0
- package/dist/esm/mutate/participants/participantSetterFields.mjs +148 -0
- package/dist/esm/mutate/participants/personAttributeShapes.mjs +139 -0
- package/dist/esm/mutate/participants/removeIndividualParticipantIds.mjs +1 -1
- package/dist/esm/mutate/participants/scaleItems/addScaleItems.mjs +1 -1
- package/dist/esm/mutate/sanctioning/activateFromSanctioning.mjs +10 -0
- package/dist/esm/mutate/scoring/addPoint.mjs +4 -3
- package/dist/esm/mutate/simulation/completeDrawMatchUps.mjs +2 -2
- package/dist/esm/mutate/structures/deleteAdHocMatchUps.mjs +1 -1
- package/dist/esm/mutate/structures/removeRoundMatchUps.mjs +1 -1
- package/dist/esm/mutate/tieFormat/addCollectionDefinition.mjs +6 -1
- package/dist/esm/mutate/tieFormat/checkTieFormat.mjs +1 -0
- package/dist/esm/mutate/tieFormat/collectionGroupUpdate.mjs +1 -1
- package/dist/esm/mutate/tieFormat/collectionTypeChange.mjs +147 -0
- package/dist/esm/mutate/tieFormat/modifyCollectionDefinition.mjs +95 -27
- package/dist/esm/mutate/tieFormat/modifyTieFormat.mjs +26 -2
- package/dist/esm/mutate/tieFormat/orderCollectionDefinitions.mjs +1 -1
- package/dist/esm/mutate/tieFormat/removeCollectionDefinition.mjs +1 -1
- package/dist/esm/mutate/tieFormat/resetTieFormat.mjs +5 -2
- package/dist/esm/mutate/timeItems/matchUps/checkInParticipant.mjs +1 -1
- package/dist/esm/mutate/timeItems/matchUps/checkOutParticipant.mjs +1 -1
- package/dist/esm/mutate/timeItems/matchUps/matchUpTimeItems.mjs +6 -0
- package/dist/esm/mutate/tournaments/migrateTournamentRecord.mjs +44 -7
- package/dist/esm/mutate/tournaments/schedulingProfile.mjs +20 -3
- package/dist/esm/mutate/tournaments/setSanctionConstraints.mjs +118 -0
- package/dist/esm/mutate/tournaments/setTournamentDates.mjs +76 -32
- package/dist/esm/mutate/tournaments/tournamentDateTrims.mjs +117 -0
- package/dist/esm/mutate/venues/addCourtGridBooking.mjs +1 -1
- package/dist/esm/mutate/venues/removeCourtGridBooking.mjs +1 -1
- package/dist/esm/package.json.mjs +1 -1
- package/dist/esm/query/base/timeItems.mjs +1 -1
- package/dist/esm/query/drawDefinition/checkSanctionedEntryLimits.mjs +57 -0
- package/dist/esm/query/drawDefinition/competition/deriveCompetitionState.mjs +124 -0
- package/dist/esm/query/drawDefinition/competition/getCompetitionLeaderboard.mjs +84 -71
- package/dist/esm/query/drawDefinition/competition/getCompetitionParticipantState.mjs +2 -2
- package/dist/esm/query/drawDefinition/competition/getCompetitionState.mjs +15 -8
- package/dist/esm/query/drawDefinition/getBestFinishers.mjs +11 -0
- package/dist/esm/query/drawDefinition/getDrawCompositionConstraints.mjs +28 -10
- package/dist/esm/query/drawDefinition/getEntryProfileQualifiers.mjs +17 -0
- package/dist/esm/query/drawDefinition/getSeedsCount.mjs +1 -1
- package/dist/esm/query/drawDefinition/getStageDrawPositions.mjs +53 -16
- package/dist/esm/query/drawDefinition/getStageSpace.mjs +36 -17
- package/dist/esm/query/drawDefinition/linkGetter.mjs +1 -1
- package/dist/esm/query/drawDefinition/linkTraversal.mjs +1 -1
- package/dist/esm/query/drawDefinition/stageGetter.mjs +18 -5
- package/dist/esm/query/entries/entryPositionGroup.mjs +17 -0
- package/dist/esm/query/entries/entryStatusReport.mjs +3 -3
- package/dist/esm/query/entries/getEntryStatusOrdinals.mjs +28 -0
- package/dist/esm/query/entries/getEventEntrySpace.mjs +44 -0
- package/dist/esm/query/event/extractEventInfo.mjs +10 -2
- package/dist/esm/query/event/getAllEventData.mjs +1 -1
- package/dist/esm/query/event/getEventData.mjs +19 -1
- package/dist/esm/query/event/getEventInconsistencies.mjs +30 -3
- package/dist/esm/query/event/getEveryDrawFlight.mjs +20 -0
- package/dist/esm/query/event/timingCategoryName.mjs +6 -0
- package/dist/esm/query/events/eventDateWarning.mjs +28 -0
- package/dist/esm/query/events/eventPlaysOnDate.mjs +126 -0
- package/dist/esm/query/extensions/getAppliedPolicies.mjs +1 -1
- package/dist/esm/query/extensions/matchUpFormatTiming/getEventMatchUpFormatTiming.mjs +3 -2
- package/dist/esm/query/extensions/matchUpFormatTiming/getMatchUpFormatTiming.mjs +12 -11
- package/dist/esm/query/extensions/matchUpFormatTiming/getScheduleTiming.mjs +2 -1
- package/dist/esm/query/hierarchical/getCompetitionFormat.mjs +1 -1
- package/dist/esm/query/hierarchical/getMatchUpFormat.mjs +1 -1
- package/dist/esm/query/hierarchical/getTieFormat.mjs +1 -1
- package/dist/esm/query/hierarchical/tieFormats/getTieFormatDescription.mjs +9 -3
- package/dist/esm/query/hierarchical/tieFormats/getTieMatchUpContext.mjs +7 -1
- package/dist/esm/query/matchUp/calculateWinCriteria.mjs +9 -5
- package/dist/esm/query/matchUp/collectionChoice.mjs +51 -0
- package/dist/esm/query/matchUp/finishingOrder.mjs +63 -0
- package/dist/esm/query/matchUp/getDualIssues.mjs +171 -0
- package/dist/esm/query/matchUp/getMatchUpCheckInHistory.mjs +1 -1
- package/dist/esm/query/matchUp/getMatchUpScheduleDetails.mjs +1 -0
- package/dist/esm/query/matchUp/resolveDeltaBand.mjs +1 -1
- package/dist/esm/query/matchUp/resolveHomeParticipantId.mjs +60 -0
- package/dist/esm/query/matchUps/addGoesTo.mjs +1 -1
- package/dist/esm/query/matchUps/addMatchUpContext.mjs +23 -13
- package/dist/esm/query/matchUps/getCollectionAssignment.mjs +2 -2
- package/dist/esm/query/matchUps/roundRobinTally/calculatePercentages.mjs +13 -17
- package/dist/esm/query/matchUps/roundRobinTally/getGroupOrder.mjs +25 -211
- package/dist/esm/query/matchUps/roundRobinTally/getParticipantResults.mjs +64 -44
- package/dist/esm/query/matchUps/roundRobinTally/tallyParticipantResults.mjs +25 -4
- package/dist/esm/query/matchUps/scheduling/getEventDateIssues.mjs +38 -0
- package/dist/esm/query/matchUps/scheduling/getOvernightRestWarnings.mjs +2 -1
- package/dist/esm/query/matchUps/scheduling/getRounds.mjs +22 -6
- package/dist/esm/query/matchUps/scheduling/getScheduledRoundsDetails.mjs +2 -2
- package/dist/esm/query/matchUps/scheduling/getSchedulingProfileIssues.mjs +30 -3
- package/dist/esm/query/matchUps/scheduling/schedulingTiming.mjs +2 -1
- package/dist/esm/query/matchUps/scheduling/schedulingUtils.mjs +3 -3
- package/dist/esm/query/matchUps/structuralIndex.mjs +28 -7
- package/dist/esm/query/participant/participantRoleOf.mjs +10 -0
- package/dist/esm/query/participant/paymentStatus.mjs +1 -1
- package/dist/esm/query/participant/presencePolicy.mjs +2 -2
- package/dist/esm/query/participants/filterParticipants.mjs +5 -7
- package/dist/esm/query/readModel/publicParticipant.mjs +2 -2
- package/dist/esm/query/reports/recoveryTimeline.mjs +2 -1
- package/dist/esm/query/reports/wrappers/wrapParticipantResultsReport.mjs +1 -1
- package/dist/esm/query/scoring/getScore.mjs +5 -1
- package/dist/esm/query/scoring/getScoreboard.mjs +5 -0
- package/dist/esm/query/scoring/overtimeScore.mjs +35 -0
- package/dist/esm/query/season/getSeasonAdvancement.mjs +40 -0
- package/dist/esm/query/season/getSeasonMovement.mjs +110 -0
- package/dist/esm/query/season/getSeasonStandings.mjs +264 -0
- package/dist/esm/query/season/planNextPeriod.mjs +84 -0
- package/dist/esm/query/standings/fromV1.mjs +98 -0
- package/dist/esm/query/standings/orderParticipants.mjs +310 -0
- package/dist/esm/query/standings/resultPoints.mjs +40 -0
- package/dist/esm/query/tournaments/getTournamentInconsistencies.mjs +75 -2
- package/dist/esm/query/tournaments/getTournamentInfo.mjs +4 -3
- package/dist/esm/query/venues/getInContextCourt.mjs +12 -2
- package/dist/esm/query/venues/venuesAndCourtsGetter.mjs +1 -0
- package/dist/esm/tests/engines/asyncEngine/index.mjs +1 -2
- package/dist/esm/tools/civilDateTime.mjs +1 -1
- package/dist/esm/tools/clock.mjs +1 -1
- package/dist/esm/validators/isValidMatchUpFormat.mjs +30 -3
- package/dist/esm/validators/rotatingPartnerDraw.mjs +2 -3
- package/dist/esm/validators/validateCollectionDefinition.mjs +63 -25
- package/dist/esm/validators/validateEntryProfile.mjs +86 -0
- package/dist/esm/validators/validateSeason.mjs +249 -0
- package/dist/esm/validators/validateTallyPolicy.mjs +171 -0
- package/dist/esm/validators/validateTeamLineUp.mjs +6 -0
- package/dist/esm/validators/validateTieFormat.mjs +14 -1
- package/dist/governors.d.cts +2 -0
- package/dist/governors.d.mts +2 -0
- package/dist/governors.d.ts +2 -0
- package/dist/governors.js +3 -0
- package/dist/schema/tournament.schema.json +1700 -355
- package/dist/tods-competition-factory.d.cts +3984 -2821
- package/dist/tods-competition-factory.d.mts +3984 -2821
- package/dist/tods-competition-factory.d.ts +3984 -2821
- package/dist/tods-competition-factory.development.cjs.js +17166 -10793
- package/dist/tods-competition-factory.development.cjs.js.map +1 -1
- package/dist/tods-competition-factory.production.cjs.min.js +1 -1
- package/dist/tods-competition-factory.production.cjs.min.js.map +1 -1
- package/package.json +29 -16
|
@@ -2,9 +2,9 @@ import { checkRequiredParameters } from '../helpers/parameters/checkRequiredPara
|
|
|
2
2
|
import { firstClassOrExtension } from './firstClassOrExtension.mjs';
|
|
3
3
|
import { structureSort } from '../functions/sorters/structureSort.mjs';
|
|
4
4
|
import { structuresOf } from './structureMembers.mjs';
|
|
5
|
-
import {
|
|
5
|
+
import { MISSING_DRAW_DEFINITION, MISSING_STRUCTURES, STRUCTURE_NOT_FOUND } from '../constants/errorConditionConstants.mjs';
|
|
6
6
|
import { STRUCTURE_ID, DRAW_DEFINITION } from '../constants/attributeConstants.mjs';
|
|
7
|
-
import {
|
|
7
|
+
import { validStages, ITEM } from '../constants/drawDefinitionConstants.mjs';
|
|
8
8
|
import { ROUND_TARGET } from '../constants/extensionConstants.mjs';
|
|
9
9
|
|
|
10
10
|
function findStructure(params) {
|
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
import { competitionEngineAsync as competitionEngineAsync$1 } from '../../../tests/engines/asyncEngine/index.mjs';
|
|
2
|
+
import { asyncEngine as asyncEngine$1 } from './index.mjs';
|
|
3
|
+
|
|
4
|
+
const asyncEngine = asyncEngine$1;
|
|
5
|
+
const competitionEngineAsync = competitionEngineAsync$1;
|
|
6
|
+
const tournamentEngineAsync = competitionEngineAsync;
|
|
7
|
+
|
|
8
|
+
export { asyncEngine, competitionEngineAsync, tournamentEngineAsync };
|
|
@@ -11,7 +11,7 @@ import { processResult } from './processResult.mjs';
|
|
|
11
11
|
import { factoryVersion } from '../../../functions/global/factoryVersion.mjs';
|
|
12
12
|
import { setRandomSource } from '../../../tools/prng.mjs';
|
|
13
13
|
import { getTournament, getState, setTournamentRecord, setState, removeUnlinkedTournamentRecords } from './stateMethods.mjs';
|
|
14
|
-
import { setTournamentRecords, getDevContext, getSchemaWriteMode, getOutcomePipeline, getSaveDrawDeletions, getAuditAuthorityServer, setTournamentId, setDeepCopy, getTournamentId, removeTournamentRecord, setDevContext
|
|
14
|
+
import { setTournamentRecords, getDevContext, setSchemaWriteMode, getSchemaWriteMode, setOutcomePipeline, getOutcomePipeline, setSaveDrawDeletions, getSaveDrawDeletions, setAuditAuthorityServer, getAuditAuthorityServer, setTournamentId, setDeepCopy, getTournamentId, removeTournamentRecord, setDevContext } from '../../../global/state/globalState.mjs';
|
|
15
15
|
import { SUCCESS } from '../../../constants/resultConstants.mjs';
|
|
16
16
|
|
|
17
17
|
function engineStart(engine, engineInvoke) {
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { getRecordLinkedTournamentIds } from '../../../acquire/getRecordLinkedTournamentIds.mjs';
|
|
2
2
|
import { makeDeepCopy } from '../../../tools/makeDeepCopy.mjs';
|
|
3
|
-
import { getTournamentId, getTournamentRecord, setTournamentRecord as setTournamentRecord$1, setTournamentId, setTournamentRecords
|
|
3
|
+
import { getTournamentId, getTournamentRecord, getTournamentRecords, setTournamentRecord as setTournamentRecord$1, setTournamentId, setTournamentRecords } from '../../../global/state/globalState.mjs';
|
|
4
4
|
import { INVALID_OBJECT, INVALID_VALUES, INVALID_RECORDS } from '../../../constants/errorConditionConstants.mjs';
|
|
5
5
|
|
|
6
6
|
function getState({ convertExtensions, removeExtensions }) {
|
|
@@ -22,6 +22,8 @@ function units(set) {
|
|
|
22
22
|
return [set.side1TiebreakScore ?? set.side1Score, set.side2TiebreakScore ?? set.side2Score];
|
|
23
23
|
}
|
|
24
24
|
function decideAggregate(match, sets) {
|
|
25
|
+
if (match.overtime)
|
|
26
|
+
return decideOvertime(match, sets);
|
|
25
27
|
const counted = sets.slice(0, match.n);
|
|
26
28
|
if (counted.length < match.n || !counted.every(isClosed))
|
|
27
29
|
return IN_PLAY;
|
|
@@ -39,6 +41,38 @@ function decideAggregate(match, sets) {
|
|
|
39
41
|
return IN_PLAY;
|
|
40
42
|
return { complete: true, winningSide: decider.winningSide };
|
|
41
43
|
}
|
|
44
|
+
function decideOvertime(match, sets) {
|
|
45
|
+
const regulation = sets.slice(0, match.n);
|
|
46
|
+
if (regulation.length < match.n || !regulation.every(isClosed))
|
|
47
|
+
return IN_PLAY;
|
|
48
|
+
let total = sumUnits(regulation);
|
|
49
|
+
if (total[0] !== total[1])
|
|
50
|
+
return moreOf(total);
|
|
51
|
+
const overtime = match.overtime;
|
|
52
|
+
const periods = sets.slice(match.n, overtime.count === 'unlimited' ? undefined : match.n + overtime.count);
|
|
53
|
+
for (const period of periods) {
|
|
54
|
+
const [a, b] = units(period);
|
|
55
|
+
total = [total[0] + a, total[1] + b];
|
|
56
|
+
if (!isClosed(period))
|
|
57
|
+
return overtime.suddenDeath && total[0] !== total[1] ? moreOf(total) : IN_PLAY;
|
|
58
|
+
if (!overtime.exactly && total[0] !== total[1])
|
|
59
|
+
return moreOf(total);
|
|
60
|
+
}
|
|
61
|
+
if (overtime.count === 'unlimited' || periods.length < overtime.count)
|
|
62
|
+
return IN_PLAY;
|
|
63
|
+
if (total[0] !== total[1])
|
|
64
|
+
return moreOf(total);
|
|
65
|
+
if (!match.final)
|
|
66
|
+
return { complete: true };
|
|
67
|
+
const decider = sets[match.n + overtime.count];
|
|
68
|
+
return decider && isClosed(decider) ? { complete: true, winningSide: decider.winningSide } : IN_PLAY;
|
|
69
|
+
}
|
|
70
|
+
function sumUnits(sets) {
|
|
71
|
+
return sets.reduce((sum, set) => {
|
|
72
|
+
const [a, b] = units(set);
|
|
73
|
+
return [sum[0] + a, sum[1] + b];
|
|
74
|
+
}, [0, 0]);
|
|
75
|
+
}
|
|
42
76
|
function decidePastClose(match, sets) {
|
|
43
77
|
if (sets.length < match.n || !sets.every(isClosed))
|
|
44
78
|
return IN_PLAY;
|
|
@@ -1,17 +1,18 @@
|
|
|
1
|
-
import {
|
|
1
|
+
import { overtimeLayout, scoringPeriod, segmentClosed } from '../../../../helpers/matchUpFormatCode/overtimeContext.mjs';
|
|
2
|
+
import { initialState, createContext, step, positionOf, INVALID_FORMAT, serverOf } from './reduce.mjs';
|
|
2
3
|
import { DEFAULT_MATCHUP_FORMAT, takesInput, finalGoverns } from './format.mjs';
|
|
4
|
+
import { readChallenge, readServer, readPoint, CALCULATED_POINT_FIELDS } from './actions.mjs';
|
|
5
|
+
import { replayLegacy, LEGACY_REFUSED_INPUT, LEGACY_IGNORED_INPUT } from './legacy.mjs';
|
|
6
|
+
import { calculateMatchStatistics } from '../../../../query/scoring/statistics/standalone.mjs';
|
|
3
7
|
import { toStatObjects } from '../../../../query/scoring/statistics/toStatObjects.mjs';
|
|
4
|
-
import { initialState, createContext, step, positionOf, INVALID_FORMAT, serverOf } from './reduce.mjs';
|
|
5
8
|
import { createMatchUp } from '../../../../mutate/scoring/createMatchUp.mjs';
|
|
6
9
|
import { getScoreboard } from '../../../../query/scoring/getScoreboard.mjs';
|
|
7
10
|
import { parse } from '../../../../helpers/matchUpFormatCode/parse.mjs';
|
|
8
11
|
import { getEpisodes } from '../../../../query/scoring/getEpisodes.mjs';
|
|
9
|
-
import { readChallenge, readServer, readPoint, CALCULATED_POINT_FIELDS } from './actions.mjs';
|
|
10
|
-
import { replayLegacy, LEGACY_REFUSED_INPUT, LEGACY_IGNORED_INPUT } from './legacy.mjs';
|
|
11
12
|
import { scoreOf, ruleInPlay } from './score.mjs';
|
|
12
13
|
import { materialize } from './record.mjs';
|
|
13
|
-
import { setsWon } from './decide.mjs';
|
|
14
14
|
import { nowIso } from '../../../../tools/clock.mjs';
|
|
15
|
+
import { setsWon } from './decide.mjs';
|
|
15
16
|
import { initialLineUpsOf, substitutionError, substituted, substitutionViolations, copyLineUps, hasLineUps } from './lineUps.mjs';
|
|
16
17
|
import { COMPLETED } from '../../../../constants/matchUpStatusValues.mjs';
|
|
17
18
|
|
|
@@ -63,14 +64,16 @@ class ScoringEngine {
|
|
|
63
64
|
isDoubles: options.isDoubles || false,
|
|
64
65
|
});
|
|
65
66
|
this.entries = [];
|
|
67
|
+
if (this.context().match?.overtime)
|
|
68
|
+
this.write([]);
|
|
66
69
|
}
|
|
67
70
|
context() {
|
|
68
71
|
const context = createContext({
|
|
69
72
|
matchUpFormat: this.matchUpFormat,
|
|
70
73
|
competitionFormat: this.competitionFormat,
|
|
71
74
|
pointMultipliers: this.pointMultipliers,
|
|
72
|
-
});
|
|
73
|
-
if (!this.pastClose || !context.match)
|
|
75
|
+
}, { allowOvertime: true });
|
|
76
|
+
if (!this.pastClose || !context.match || context.match.overtime)
|
|
74
77
|
return context;
|
|
75
78
|
return { ...context, match: { ...context.match, pastClose: true } };
|
|
76
79
|
}
|
|
@@ -104,7 +107,7 @@ class ScoringEngine {
|
|
|
104
107
|
const before = state;
|
|
105
108
|
const result = step(context, state, unindexed);
|
|
106
109
|
let next = result.state;
|
|
107
|
-
if (!result.outcome.recorded) {
|
|
110
|
+
if (!result.outcome.recorded && !context.match?.overtime) {
|
|
108
111
|
const v1 = replayLegacy(context, state, unindexed, result.outcome);
|
|
109
112
|
legacy.add(v1?.shape ?? ('refused' in result.outcome ? LEGACY_REFUSED_INPUT : LEGACY_IGNORED_INPUT));
|
|
110
113
|
if (v1)
|
|
@@ -379,6 +382,10 @@ class ScoringEngine {
|
|
|
379
382
|
}
|
|
380
383
|
patchPoint(pointIndex, fields) {
|
|
381
384
|
const points = [...(this.record.history?.points ?? [])];
|
|
385
|
+
if (this.context().match?.overtime) {
|
|
386
|
+
const { phase: _phase, periodNumber: _period, ...metadata } = fields;
|
|
387
|
+
fields = metadata;
|
|
388
|
+
}
|
|
382
389
|
points[pointIndex] = { ...points[pointIndex], ...fields };
|
|
383
390
|
this.record = { ...this.record, history: { ...this.record.history, points } };
|
|
384
391
|
}
|
|
@@ -434,17 +441,25 @@ class ScoringEngine {
|
|
|
434
441
|
this.legacyShapes = new Set();
|
|
435
442
|
this.stale = false;
|
|
436
443
|
this.initialServer = undefined;
|
|
444
|
+
if (this.context().match?.overtime)
|
|
445
|
+
this.write([]);
|
|
437
446
|
this.eventHandlers?.onReset?.(this.eventContext());
|
|
438
447
|
}
|
|
439
448
|
setState(matchUp) {
|
|
440
449
|
const loaded = copy(matchUp);
|
|
450
|
+
const overtime = !!parse(loaded.matchUpFormat)?.overtimeFormat;
|
|
451
|
+
const overtimeTimeline = overtime ? readOvertimeTimeline(loaded) : undefined;
|
|
441
452
|
this.record = loaded;
|
|
442
453
|
this.matchUpFormat = loaded.matchUpFormat;
|
|
443
454
|
this.redoStack = [];
|
|
444
|
-
this.entries = loaded.history?.entries ? [...loaded.history.entries] : undefined;
|
|
455
|
+
this.entries = overtimeTimeline ?? (loaded.history?.entries ? [...loaded.history.entries] : undefined);
|
|
445
456
|
this.lineUps = lineUpsOf(loaded);
|
|
446
457
|
this.initialLineUps = initialLineUpsOf(this.lineUps, this.entries, loaded.history?.substitutions);
|
|
447
458
|
this.initialServer = loaded.history?.initialServer;
|
|
459
|
+
if (overtime) {
|
|
460
|
+
this.rebuild();
|
|
461
|
+
return;
|
|
462
|
+
}
|
|
448
463
|
this.prepare();
|
|
449
464
|
this.legacyShapes = new Set();
|
|
450
465
|
this.stale = true;
|
|
@@ -571,6 +586,14 @@ class ScoringEngine {
|
|
|
571
586
|
return undefined;
|
|
572
587
|
const closed = this.state.sets.filter((set) => set.winningSide || set.segmentComplete);
|
|
573
588
|
const setNumber = Math.min(positionOf(match, this.state).set.setNumber, Math.max(closed.length + 1, 1));
|
|
589
|
+
const layout = overtimeLayout(structure);
|
|
590
|
+
if (layout) {
|
|
591
|
+
const current = this.state.matchUpStatus === COMPLETED ? (this.state.sets.at(-1)?.setNumber ?? 1) : setNumber;
|
|
592
|
+
const period = scoringPeriod(layout, current);
|
|
593
|
+
if (period?.phase === 'OVERTIME')
|
|
594
|
+
return structure.overtimeFormat?.setFormat;
|
|
595
|
+
return period?.phase === 'DECIDER' ? structure.finalSetFormat : structure.setFormat;
|
|
596
|
+
}
|
|
574
597
|
const final = finalGoverns(match, setNumber, setsWon(this.state.sets.slice(0, setNumber - 1)));
|
|
575
598
|
return final && structure.finalSetFormat ? structure.finalSetFormat : structure.setFormat;
|
|
576
599
|
}
|
|
@@ -653,6 +676,46 @@ class ScoringEngine {
|
|
|
653
676
|
return this.competitionFormat?.playerRules;
|
|
654
677
|
}
|
|
655
678
|
}
|
|
679
|
+
function readOvertimeTimeline(record) {
|
|
680
|
+
const context = createContext({ matchUpFormat: record.matchUpFormat }, { allowOvertime: true });
|
|
681
|
+
if (!context.match?.overtime)
|
|
682
|
+
throw new Error('Unsupported overtime format');
|
|
683
|
+
if (record.history?.entries?.length)
|
|
684
|
+
return [...record.history.entries];
|
|
685
|
+
if (record.history?.points?.length)
|
|
686
|
+
throw new Error('Overtime point records require a scoring timeline');
|
|
687
|
+
const sets = record.score.sets;
|
|
688
|
+
const last = sets.at(-1);
|
|
689
|
+
if (!last)
|
|
690
|
+
return [];
|
|
691
|
+
const open = record.matchUpStatus !== COMPLETED && !segmentClosed(last);
|
|
692
|
+
const entry = {
|
|
693
|
+
type: 'setInitialScore',
|
|
694
|
+
timestamp: record.endTime ?? record.createdAt ?? nowIso(),
|
|
695
|
+
data: {
|
|
696
|
+
sets: open ? sets.slice(0, -1) : sets,
|
|
697
|
+
...(open ? openOvertimeBaseline(last) : {}),
|
|
698
|
+
matchUpStatus: record.matchUpStatus,
|
|
699
|
+
...(record.winningSide === undefined ? {} : { winningSide: record.winningSide }),
|
|
700
|
+
},
|
|
701
|
+
};
|
|
702
|
+
const result = step(context, initialState(), { ...entry });
|
|
703
|
+
if (!result.outcome.recorded)
|
|
704
|
+
refusedWith(result.outcome);
|
|
705
|
+
return [entry];
|
|
706
|
+
}
|
|
707
|
+
function openOvertimeBaseline(set) {
|
|
708
|
+
if (set.isTiebreakOnly) {
|
|
709
|
+
return {
|
|
710
|
+
currentSetScore: { side1Score: 0, side2Score: 0 },
|
|
711
|
+
currentGameScore: {
|
|
712
|
+
side1Points: set.side1GameScores?.at(-1) ?? set.side1TiebreakScore ?? set.side1Score ?? 0,
|
|
713
|
+
side2Points: set.side2GameScores?.at(-1) ?? set.side2TiebreakScore ?? set.side2Score ?? 0,
|
|
714
|
+
},
|
|
715
|
+
};
|
|
716
|
+
}
|
|
717
|
+
return { currentSetScore: { side1Score: set.side1Score ?? 0, side2Score: set.side2Score ?? 0 } };
|
|
718
|
+
}
|
|
656
719
|
function lineUpsAfter(initial, entries) {
|
|
657
720
|
if (!initial)
|
|
658
721
|
return undefined;
|
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
import { overtimeFinalNumber, overtimeGoverns } from './overtime.mjs';
|
|
1
2
|
import { parse } from '../../../../helpers/matchUpFormatCode/parse.mjs';
|
|
2
3
|
|
|
3
4
|
const DEFAULT_MATCHUP_FORMAT = 'SET3-S:6/TB7';
|
|
@@ -47,17 +48,20 @@ function segmentRule(setFormat, gameFormat, context) {
|
|
|
47
48
|
const at = Number(setFormat.tiebreakAt ?? setTo);
|
|
48
49
|
return { kind: 'standard', setTo, winBy: 2, tiebreak: { at, race: raceRule(setFormat.tiebreakFormat) }, game };
|
|
49
50
|
}
|
|
50
|
-
function resolveFormat(code) {
|
|
51
|
+
function resolveFormat(code, options = {}) {
|
|
51
52
|
if (!code)
|
|
52
53
|
return undefined;
|
|
53
54
|
const parsed = parse(code);
|
|
54
|
-
if (!parsed?.setFormat)
|
|
55
|
+
if (!parsed?.setFormat || (parsed.overtimeFormat && !options.allowOvertime))
|
|
55
56
|
return undefined;
|
|
56
57
|
const exactly = parsed.exactly;
|
|
57
58
|
const n = exactly ?? parsed.bestOf ?? 1;
|
|
58
59
|
const context = { tennisFamily: !parsed.matchRoot && !parsed.aggregate && !parsed.simplified };
|
|
59
60
|
const ordinary = segmentRule(parsed.setFormat, parsed.gameFormat, context);
|
|
60
61
|
const final = parsed.finalSetFormat ? segmentRule(parsed.finalSetFormat, parsed.gameFormat, context) : undefined;
|
|
62
|
+
const overtime = parsed.overtimeFormat;
|
|
63
|
+
if (overtime && !supportsOvertime(parsed, n, ordinary, final))
|
|
64
|
+
return undefined;
|
|
61
65
|
return {
|
|
62
66
|
code,
|
|
63
67
|
mode: exactly ? 'exactly' : 'bestOf',
|
|
@@ -66,12 +70,34 @@ function resolveFormat(code) {
|
|
|
66
70
|
setsToWin: Math.floor(n / 2) + 1,
|
|
67
71
|
ordinary,
|
|
68
72
|
...(final ? { final } : {}),
|
|
73
|
+
...(overtime
|
|
74
|
+
? {
|
|
75
|
+
overtime: {
|
|
76
|
+
count: overtime.count,
|
|
77
|
+
exactly: !!overtime.exactly,
|
|
78
|
+
suddenDeath: !!overtime.suddenDeath,
|
|
79
|
+
rule: segmentRule(overtime.setFormat, parsed.gameFormat, context),
|
|
80
|
+
},
|
|
81
|
+
}
|
|
82
|
+
: {}),
|
|
69
83
|
};
|
|
70
84
|
}
|
|
85
|
+
function supportsOvertime(parsed, n, ordinary, final) {
|
|
86
|
+
const overtime = parsed.overtimeFormat;
|
|
87
|
+
if (parsed.matchUpConstraint || ordinary.kind !== 'timed' || ordinary.tiebreak)
|
|
88
|
+
return false;
|
|
89
|
+
if (!overtime.setFormat.timed || overtime.setFormat.tiebreakFormat)
|
|
90
|
+
return false;
|
|
91
|
+
if (final && final.kind !== 'tiebreakOnly' && (final.kind !== 'timed' || final.tiebreak))
|
|
92
|
+
return false;
|
|
93
|
+
return overtime.count === 'unlimited' || Number.isSafeInteger(n + overtime.count + (final ? 1 : 0));
|
|
94
|
+
}
|
|
71
95
|
function configuredFormat(config) {
|
|
72
96
|
return config.matchUpFormat ?? config.competitionFormat?.matchUpFormat ?? DEFAULT_MATCHUP_FORMAT;
|
|
73
97
|
}
|
|
74
98
|
function finalGoverns(match, setNumber, setsWon) {
|
|
99
|
+
if (match.overtime)
|
|
100
|
+
return setNumber === overtimeFinalNumber(match);
|
|
75
101
|
if (match.mode === 'exactly')
|
|
76
102
|
return setNumber === (match.aggregate ? match.n + 1 : match.n);
|
|
77
103
|
if (setNumber === match.n)
|
|
@@ -82,6 +108,8 @@ function finalGoverns(match, setNumber, setsWon) {
|
|
|
82
108
|
return setsWon[0] === oneFromWinning && setsWon[1] === oneFromWinning;
|
|
83
109
|
}
|
|
84
110
|
function ruleForSet(match, setNumber, setsWon) {
|
|
111
|
+
if (match.overtime && overtimeGoverns(match, setNumber))
|
|
112
|
+
return match.overtime.rule;
|
|
85
113
|
return match.final && finalGoverns(match, setNumber, setsWon) ? match.final : match.ordinary;
|
|
86
114
|
}
|
|
87
115
|
function takesInput(rule, input) {
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
import { scoringPeriod } from '../../../../helpers/matchUpFormatCode/overtimeContext.mjs';
|
|
2
|
+
|
|
3
|
+
function overtimeGoverns(match, setNumber) {
|
|
4
|
+
const overtime = match.overtime;
|
|
5
|
+
return !!overtime && setNumber > match.n && (overtime.count === 'unlimited' || setNumber <= match.n + overtime.count);
|
|
6
|
+
}
|
|
7
|
+
function overtimeFinalNumber(match) {
|
|
8
|
+
const overtime = match.overtime;
|
|
9
|
+
return overtime && overtime.count !== 'unlimited' && match.final ? match.n + overtime.count + 1 : undefined;
|
|
10
|
+
}
|
|
11
|
+
function lastPlayableSet(match) {
|
|
12
|
+
if (match.overtime) {
|
|
13
|
+
if (match.overtime.count === 'unlimited')
|
|
14
|
+
return undefined;
|
|
15
|
+
return match.n + match.overtime.count + (match.final ? 1 : 0);
|
|
16
|
+
}
|
|
17
|
+
return match.n + (match.mode === 'exactly' && match.aggregate && match.final ? 1 : 0);
|
|
18
|
+
}
|
|
19
|
+
function overtimeTotalError(match, setNumber, totals) {
|
|
20
|
+
return match.overtime?.suddenDeath && overtimeGoverns(match, setNumber) && totals[0] > 0 && totals[1] > 0
|
|
21
|
+
? 'a sudden-death overtime total cannot have scoring by both sides'
|
|
22
|
+
: undefined;
|
|
23
|
+
}
|
|
24
|
+
function periodForSet(match, setNumber) {
|
|
25
|
+
return match.overtime
|
|
26
|
+
? scoringPeriod({ regulationCount: match.n, overtimeCount: match.overtime.count, finalDecider: !!match.final }, setNumber)
|
|
27
|
+
: undefined;
|
|
28
|
+
}
|
|
29
|
+
|
|
30
|
+
export { lastPlayableSet, overtimeFinalNumber, overtimeGoverns, overtimeTotalError, periodForSet };
|
|
@@ -1,4 +1,6 @@
|
|
|
1
1
|
import { hasLineUps, substituted, activePlayersOf } from './lineUps.mjs';
|
|
2
|
+
import { overtimeScoreContext } from '../../../../helpers/matchUpFormatCode/overtimeContext.mjs';
|
|
3
|
+
import { parse } from '../../../../helpers/matchUpFormatCode/parse.mjs';
|
|
2
4
|
import { isClosed } from './decide.mjs';
|
|
3
5
|
import { COMPLETED } from '../../../../constants/matchUpStatusValues.mjs';
|
|
4
6
|
import { POINT, SUBSTITUTION } from './actions.mjs';
|
|
@@ -59,6 +61,10 @@ function materialize({ base, state, entries, completedBy, lineUps, timeline, ini
|
|
|
59
61
|
score: { sets: recordedSets(state) },
|
|
60
62
|
sides: (identity.sides ?? []).map((side) => lineUps.current?.[side.sideNumber] ? { ...side, lineUp: lineUps.current[side.sideNumber] } : side),
|
|
61
63
|
};
|
|
64
|
+
const format = parse(base.matchUpFormat);
|
|
65
|
+
const overtime = format && overtimeScoreContext(format, recorded.score.sets, state.matchUpStatus);
|
|
66
|
+
if (overtime)
|
|
67
|
+
recorded.score.overtime = overtime;
|
|
62
68
|
if (previous || entries.length || points.length || initialServer !== undefined)
|
|
63
69
|
recorded.history = history;
|
|
64
70
|
return recorded;
|
|
@@ -1,14 +1,15 @@
|
|
|
1
1
|
import { INITIAL_SERVICE, nextServer, corrected, serveSide, afterPoint, serviceCode } from './service.mjs';
|
|
2
|
+
import { lastPlayableSet, overtimeTotalError, periodForSet, overtimeGoverns } from './overtime.mjs';
|
|
2
3
|
import { resolveFormat, configuredFormat, ruleForSet, takesInput } from './format.mjs';
|
|
3
|
-
import { pointsTo, isBreakpoint } from './view.mjs';
|
|
4
4
|
import { setsWon, isClosed, decideMatch } from './decide.mjs';
|
|
5
|
-
import {
|
|
5
|
+
import { pointsTo, isBreakpoint } from './view.mjs';
|
|
6
6
|
import { NEEDS_A_FORMAT, refusal, ANNOTATION, SUBSTITUTION, CHALLENGE, readChallenge, SET_SERVER, readServer, END_SEGMENT, SET_INITIAL_SCORE, SET, GAME, POINT, readEndSegment, readSetTotal, readGame, readPoint, pointFacts } from './actions.mjs';
|
|
7
|
+
import { openSet, atTimeIn, segmentEnd, segmentTotal, segmentGame, pointsAreUnits, segmentPoint, decidedInPlay } from './segments/segment.mjs';
|
|
7
8
|
import { TO_BE_PLAYED, COMPLETED, IN_PROGRESS } from '../../../../constants/matchUpStatusValues.mjs';
|
|
8
9
|
|
|
9
|
-
function createContext(config) {
|
|
10
|
+
function createContext(config, options = {}) {
|
|
10
11
|
return {
|
|
11
|
-
match: resolveFormat(configuredFormat(config)),
|
|
12
|
+
match: resolveFormat(configuredFormat(config), options),
|
|
12
13
|
multipliers: config.pointMultipliers ?? config.competitionFormat?.pointMultipliers ?? [],
|
|
13
14
|
rules: { winnerServes: config.competitionFormat?.serverRule === 'WINNER_SERVES' },
|
|
14
15
|
};
|
|
@@ -48,20 +49,27 @@ function target(match, state) {
|
|
|
48
49
|
return { set: last, rule, game: state.game, index: state.sets.length - 1, atTime: atTimeIn(rule, last) };
|
|
49
50
|
}
|
|
50
51
|
const setNumber = state.sets.length + 1;
|
|
51
|
-
const
|
|
52
|
-
if (setNumber >
|
|
52
|
+
const limit = lastPlayableSet(match);
|
|
53
|
+
if (limit !== undefined && setNumber > limit && !match.pastClose)
|
|
53
54
|
return undefined;
|
|
54
55
|
const rule = ruleForSet(match, setNumber, setsWon(state.sets));
|
|
55
56
|
return { set: openSet(rule, setNumber), rule, index: state.sets.length, atTime: false };
|
|
56
57
|
}
|
|
57
58
|
function scored(match, state, at, result, scoring = true) {
|
|
58
|
-
const
|
|
59
|
+
const labeled = { ...result.set, ...periodForSet(match, at.set.setNumber) };
|
|
60
|
+
const sets = [...state.sets.slice(0, at.index), labeled];
|
|
59
61
|
const decision = decideMatch(match, sets);
|
|
62
|
+
const suddenDeathWin = match.overtime?.suddenDeath &&
|
|
63
|
+
overtimeGoverns(match, at.set.setNumber) &&
|
|
64
|
+
decision.complete &&
|
|
65
|
+
decision.winningSide;
|
|
66
|
+
if (suddenDeathWin)
|
|
67
|
+
sets[at.index] = { ...labeled, segmentComplete: true, winningSide: decision.winningSide };
|
|
60
68
|
const { winningSide: _previous, game: _game, ...rest } = state;
|
|
61
69
|
return {
|
|
62
70
|
...rest,
|
|
63
71
|
sets,
|
|
64
|
-
...(result.game ? { game: result.game } : {}),
|
|
72
|
+
...(result.game && !suddenDeathWin ? { game: result.game } : {}),
|
|
65
73
|
matchUpStatus: decision.complete ? COMPLETED : IN_PROGRESS,
|
|
66
74
|
...(decision.winningSide ? { winningSide: decision.winningSide } : {}),
|
|
67
75
|
scoringEntries: state.scoringEntries + (scoring ? 1 : 0),
|
|
@@ -115,6 +123,7 @@ function point(context, match, state, entry) {
|
|
|
115
123
|
const index = state.points.length;
|
|
116
124
|
const materialized = {
|
|
117
125
|
...pointFacts(entry.data),
|
|
126
|
+
...periodForSet(match, at.set.setNumber),
|
|
118
127
|
winner,
|
|
119
128
|
winningSide: (winner + 1),
|
|
120
129
|
...(server === undefined ? {} : { server, serverSideNumber: (server + 1) }),
|
|
@@ -156,6 +165,9 @@ function set(match, state, entry) {
|
|
|
156
165
|
const at = aimed(match, state);
|
|
157
166
|
if (typeof at === 'string')
|
|
158
167
|
return ignored(state, at);
|
|
168
|
+
const overtimeError = overtimeTotalError(match, at.set.setNumber, facts.total.totals);
|
|
169
|
+
if (overtimeError)
|
|
170
|
+
return refused(state, refusal(overtimeError));
|
|
159
171
|
const result = segmentTotal(at.rule, at.set.setNumber, facts.total);
|
|
160
172
|
if ('refused' in result)
|
|
161
173
|
return refused(state, refusal(result.refused));
|
|
@@ -202,9 +214,14 @@ function baselineSets(match, given) {
|
|
|
202
214
|
const sets = [];
|
|
203
215
|
let atTime = false;
|
|
204
216
|
for (const [i, data] of given.entries()) {
|
|
217
|
+
if (match.overtime && decideMatch(match, sets).complete)
|
|
218
|
+
return { refused: 'an overtime baseline includes a segment after the match was decided' };
|
|
205
219
|
const facts = readSetTotal(data);
|
|
206
220
|
if (facts.refused)
|
|
207
221
|
return { refused: facts.refused.message };
|
|
222
|
+
const overtimeError = overtimeTotalError(match, i + 1, facts.total.totals);
|
|
223
|
+
if (overtimeError)
|
|
224
|
+
return { refused: overtimeError };
|
|
208
225
|
const rule = ruleForSet(match, i + 1, setsWon(sets));
|
|
209
226
|
const judged = segmentTotal(rule, i + 1, facts.total);
|
|
210
227
|
if ('refused' in judged)
|
|
@@ -214,7 +231,7 @@ function baselineSets(match, given) {
|
|
|
214
231
|
return { refused: `Set ${i + 1} is not finished and is not the last set` };
|
|
215
232
|
if (atTimeSet)
|
|
216
233
|
atTime = true;
|
|
217
|
-
sets.push(judged.set);
|
|
234
|
+
sets.push({ ...judged.set, ...periodForSet(match, i + 1) });
|
|
218
235
|
}
|
|
219
236
|
return { sets, atTime };
|
|
220
237
|
}
|
|
@@ -245,15 +262,45 @@ function baselineInPlay(match, sets, data) {
|
|
|
245
262
|
if (given && raceInPlay)
|
|
246
263
|
return { refused: raceNamedTwice(setNumber) };
|
|
247
264
|
const base = open && !raceInPlay ? last : openSet(rule, setNumber);
|
|
248
|
-
const
|
|
265
|
+
const checked = overtimeBaselineSet(match, rule, {
|
|
266
|
+
...base,
|
|
267
|
+
side1Score: base.side1Score + games[0],
|
|
268
|
+
side2Score: base.side2Score + games[1],
|
|
269
|
+
...periodForSet(match, setNumber),
|
|
270
|
+
}, given, !!currentSetScore);
|
|
271
|
+
if ('refused' in checked)
|
|
272
|
+
return checked;
|
|
273
|
+
const inPlay = checked;
|
|
249
274
|
if (decidedInPlay(rule, [inPlay.side1Score, inPlay.side2Score]))
|
|
250
275
|
return { refused: 'the set in play is already won' };
|
|
251
276
|
if (rule.kind === 'combined')
|
|
252
277
|
return { sets: [...closed, inPlay] };
|
|
253
|
-
const points =
|
|
278
|
+
const points = baselinePoints(match, rule, inPlay, raceInPlay ? last : undefined, given);
|
|
254
279
|
const withGame = { ...inPlay, side1GameScores: [points[0]], side2GameScores: [points[1]] };
|
|
255
280
|
return { sets: [...closed, withGame], game: { score: points, pointsPlayed: points[0] + points[1] } };
|
|
256
281
|
}
|
|
282
|
+
function baselinePoints(match, rule, inPlay, race, given) {
|
|
283
|
+
if (given)
|
|
284
|
+
return given;
|
|
285
|
+
if (match.overtime && rule.kind === 'timed')
|
|
286
|
+
return [inPlay.side1Score, inPlay.side2Score];
|
|
287
|
+
return race ? [race.side1Score, race.side2Score] : [0, 0];
|
|
288
|
+
}
|
|
289
|
+
function overtimeBaselineSet(match, rule, set, given, setGiven) {
|
|
290
|
+
if (!match.overtime)
|
|
291
|
+
return set;
|
|
292
|
+
let inPlay = set;
|
|
293
|
+
if (rule.kind === 'timed' && given) {
|
|
294
|
+
if (setGiven && (given[0] !== set.side1Score || given[1] !== set.side2Score))
|
|
295
|
+
return { refused: 'timed overtime baseline games and points name the same totals and must agree' };
|
|
296
|
+
inPlay = { ...set, side1Score: given[0], side2Score: given[1] };
|
|
297
|
+
}
|
|
298
|
+
if (match.overtime.suddenDeath &&
|
|
299
|
+
overtimeGoverns(match, set.setNumber) &&
|
|
300
|
+
[inPlay.side1Score, inPlay.side2Score, ...(given ?? [])].some((score) => score > 0))
|
|
301
|
+
return { refused: 'a sudden-death overtime with a nonzero score is already decided, not in play' };
|
|
302
|
+
return inPlay;
|
|
303
|
+
}
|
|
257
304
|
const raceNamedTwice = (setNumber) => `Set ${setNumber} is a tiebreak-only set in play, and a currentGameScore names its points again`;
|
|
258
305
|
function combinedInPlay(match, sets, open) {
|
|
259
306
|
const closed = open ? sets.slice(0, -1) : sets;
|
|
@@ -341,5 +388,19 @@ function apply(context, state, entry, live) {
|
|
|
341
388
|
return scoreless(state);
|
|
342
389
|
}
|
|
343
390
|
}
|
|
391
|
+
function reduce(config, timeline, options = {}) {
|
|
392
|
+
const context = createContext(config, options);
|
|
393
|
+
const outcomes = [];
|
|
394
|
+
const legacy = [];
|
|
395
|
+
let state = initialState();
|
|
396
|
+
for (const [index, entry] of timeline.entries()) {
|
|
397
|
+
const result = step(context, state, entry);
|
|
398
|
+
outcomes.push(result.outcome);
|
|
399
|
+
if (!result.outcome.recorded)
|
|
400
|
+
legacy.push(index);
|
|
401
|
+
state = result.state;
|
|
402
|
+
}
|
|
403
|
+
return { state, outcomes, legacy };
|
|
404
|
+
}
|
|
344
405
|
|
|
345
|
-
export { INVALID_FORMAT, createContext, initialState, positionOf, raceNamedTwice, serverOf, step };
|
|
406
|
+
export { INVALID_FORMAT, createContext, initialState, positionOf, raceNamedTwice, reduce, serverOf, step };
|
|
@@ -1,6 +1,8 @@
|
|
|
1
|
-
import {
|
|
1
|
+
import { overtimeScoreContext, overtimeScoreString } from '../../../../helpers/matchUpFormatCode/overtimeContext.mjs';
|
|
2
|
+
import { parse } from '../../../../helpers/matchUpFormatCode/parse.mjs';
|
|
2
3
|
import { combinedClosed } from './segments/combined.mjs';
|
|
3
4
|
import { inTiebreak } from './segments/standard.mjs';
|
|
5
|
+
import { positionOf, serverOf } from './reduce.mjs';
|
|
4
6
|
import { atTimeIn } from './segments/segment.mjs';
|
|
5
7
|
import { isClosed } from './decide.mjs';
|
|
6
8
|
import { pointsTo } from './view.mjs';
|
|
@@ -110,9 +112,12 @@ function inPlay(context, state) {
|
|
|
110
112
|
}
|
|
111
113
|
function scoreOf(context, state, sets) {
|
|
112
114
|
const { games, points, pointDisplay } = inPlay(context, state);
|
|
115
|
+
const format = context.match?.overtime && parse(context.match.code);
|
|
116
|
+
const overtime = format && overtimeScoreContext(format, sets, state.matchUpStatus);
|
|
113
117
|
return {
|
|
114
118
|
sets,
|
|
115
|
-
scoreString: scoreString(sets),
|
|
119
|
+
scoreString: overtime ? overtimeScoreString(overtime) : scoreString(sets),
|
|
120
|
+
...(overtime ? { overtime } : {}),
|
|
116
121
|
games,
|
|
117
122
|
points,
|
|
118
123
|
pointDisplay,
|
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
import { playRacePoint, playGamePoint, NEW_GAME } from './segments/game.mjs';
|
|
2
2
|
import { inTiebreak, standardSetWinner } from './segments/standard.mjs';
|
|
3
|
+
import { overtimeGoverns } from './overtime.mjs';
|
|
3
4
|
import { ruleForSet } from './format.mjs';
|
|
4
5
|
import { setsWon } from './decide.mjs';
|
|
5
6
|
|
|
@@ -108,6 +109,8 @@ function counted(rule) {
|
|
|
108
109
|
return rule.kind === 'standard' || rule.kind === 'tiebreakOnly';
|
|
109
110
|
}
|
|
110
111
|
function pointsTo(state, position) {
|
|
112
|
+
if (position.match.overtime?.suddenDeath && overtimeGoverns(position.match, position.set.setNumber))
|
|
113
|
+
return { pointsToGame: [1, 1], pointsToSet: [1, 1], pointsToMatch: [1, 1], gamesToSet: [1, 1] };
|
|
111
114
|
const { rule, set, game } = position;
|
|
112
115
|
if (!counted(rule))
|
|
113
116
|
return undefined;
|
|
@@ -35,7 +35,7 @@ function generateDrawMaticRound(params) {
|
|
|
35
35
|
let sourceRatingType;
|
|
36
36
|
const { competitionPolicy } = getCompetitionPolicy({ tournamentRecord, drawDefinition, event });
|
|
37
37
|
const { competitionState } = competitionPolicy
|
|
38
|
-
? getCompetitionState({ drawDefinition })
|
|
38
|
+
? getCompetitionState({ drawDefinition, competitionPolicy })
|
|
39
39
|
: { competitionState: undefined };
|
|
40
40
|
const useCompetitionRatings = competitionPolicy && competitionState && competitionPolicy.pairingPolicy.ratingSource === 'DYNAMIC_FORM';
|
|
41
41
|
if (useCompetitionRatings) {
|
package/dist/esm/assemblies/generators/drawDefinitions/drawTypes/adHoc/swiss/generateSwissRound.mjs
CHANGED
|
@@ -47,7 +47,7 @@ function generateSwissRound(params) {
|
|
|
47
47
|
}
|
|
48
48
|
const { competitionPolicy } = getCompetitionPolicy({ tournamentRecord, drawDefinition, event });
|
|
49
49
|
const { competitionState } = competitionPolicy
|
|
50
|
-
? getCompetitionState({ drawDefinition })
|
|
50
|
+
? getCompetitionState({ drawDefinition, competitionPolicy })
|
|
51
51
|
: { competitionState: undefined };
|
|
52
52
|
let adHocRatings;
|
|
53
53
|
if (competitionPolicy && competitionState && competitionPolicy.pairingPolicy.ratingSource === 'DYNAMIC_FORM') {
|
package/dist/esm/assemblies/generators/drawDefinitions/drawTypes/generateVoluntaryConsolation.mjs
CHANGED
|
@@ -35,7 +35,7 @@ function generateVoluntaryConsolation(params) {
|
|
|
35
35
|
return { error: INVALID_DRAW_SIZE };
|
|
36
36
|
let { tieFormat, matchUpType } = params;
|
|
37
37
|
if (tieFormat) {
|
|
38
|
-
const result = validateTieFormat({ tieFormat });
|
|
38
|
+
const result = validateTieFormat({ tieFormat, enforceValues: true });
|
|
39
39
|
if (result.error)
|
|
40
40
|
return result;
|
|
41
41
|
}
|
package/dist/esm/assemblies/generators/drawDefinitions/generateAndPopulatePlayoffStructures.mjs
CHANGED
|
@@ -22,7 +22,7 @@ import { addGoesTo } from '../../../query/matchUps/addGoesTo.mjs';
|
|
|
22
22
|
import { generateTieMatchUps } from './tieMatchUps.mjs';
|
|
23
23
|
import { makeDeepCopy } from '../../../tools/makeDeepCopy.mjs';
|
|
24
24
|
import { ensureInt } from '../../../tools/ensureInt.mjs';
|
|
25
|
-
import {
|
|
25
|
+
import { MISSING_DRAW_DEFINITION, INVALID_VALUES, STRUCTURE_NOT_FOUND } from '../../../constants/errorConditionConstants.mjs';
|
|
26
26
|
import { TOP_DOWN, LOSER, CONTAINER, PLAY_OFF } from '../../../constants/drawDefinitionConstants.mjs';
|
|
27
27
|
import { BYE } from '../../../constants/matchUpStatusValues.mjs';
|
|
28
28
|
import { SUCCESS } from '../../../constants/resultConstants.mjs';
|