@escapenavigator/hooks 1.10.124 → 1.10.125

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.
@@ -63,7 +63,7 @@ const use_players_and_variation_picker_1 = require("../use-players-and-variation
63
63
  * places with subtle drift. This component is the single source of truth.
64
64
  */
65
65
  const PlayersAndVariationPicker = ({ slot, currentTariffId, currentDuration, loadSlotDetails, onVariationChange, onVariationResolved, onDetailsLoaded, players = 0, child = 0, tariff: tariffOverride, currency, minPlayers, maxPlayersLimit, slotDiscount, error, t, onChange, onSave, orderId, }) => {
66
- var _a, _b, _c;
66
+ var _a, _b;
67
67
  const { options: pickerOptions, selectedOptionId, selectedVariation, buildVariationChange, selectVariation, details, } = (0, use_players_and_variation_picker_1.usePlayersAndVariationPicker)({
68
68
  slot,
69
69
  currentTariffId,
@@ -72,20 +72,24 @@ const PlayersAndVariationPicker = ({ slot, currentTariffId, currentDuration, loa
72
72
  t: t,
73
73
  orderId,
74
74
  });
75
+ const onDetailsLoadedRef = (0, react_1.useRef)(onDetailsLoaded);
76
+ const onVariationResolvedRef = (0, react_1.useRef)(onVariationResolved);
77
+ onDetailsLoadedRef.current = onDetailsLoaded;
78
+ onVariationResolvedRef.current = onVariationResolved;
75
79
  (0, react_1.useEffect)(() => {
76
- onDetailsLoaded === null || onDetailsLoaded === void 0 ? void 0 : onDetailsLoaded(details);
77
- // eslint-disable-next-line react-hooks/exhaustive-deps
78
- }, [details === null || details === void 0 ? void 0 : details.slotId, details === null || details === void 0 ? void 0 : details.isFlex, (_a = details === null || details === void 0 ? void 0 : details.variations) === null || _a === void 0 ? void 0 : _a.length, details, onDetailsLoaded]);
80
+ var _a;
81
+ if (!details)
82
+ return;
83
+ (_a = onDetailsLoadedRef.current) === null || _a === void 0 ? void 0 : _a.call(onDetailsLoadedRef, details);
84
+ }, [details === null || details === void 0 ? void 0 : details.slotId, details === null || details === void 0 ? void 0 : details.isFlex, details === null || details === void 0 ? void 0 : details.questroomId, details === null || details === void 0 ? void 0 : details.date, details === null || details === void 0 ? void 0 : details.start]);
79
85
  const tariff = (0, react_1.useMemo)(() => (tariffOverride || (selectedVariation === null || selectedVariation === void 0 ? void 0 : selectedVariation.tariff) || {}), [tariffOverride, selectedVariation === null || selectedVariation === void 0 ? void 0 : selectedVariation.tariff]);
80
86
  (0, react_1.useEffect)(() => {
81
- onVariationResolved === null || onVariationResolved === void 0 ? void 0 : onVariationResolved(selectedVariation);
82
- // eslint-disable-next-line react-hooks/exhaustive-deps
87
+ var _a;
88
+ (_a = onVariationResolvedRef.current) === null || _a === void 0 ? void 0 : _a.call(onVariationResolvedRef, selectedVariation);
83
89
  }, [
84
90
  selectedVariation === null || selectedVariation === void 0 ? void 0 : selectedVariation.id,
85
91
  selectedVariation === null || selectedVariation === void 0 ? void 0 : selectedVariation.tariffId,
86
92
  selectedVariation === null || selectedVariation === void 0 ? void 0 : selectedVariation.duration,
87
- selectedVariation,
88
- onVariationResolved,
89
93
  ]);
90
94
  const [_players, setPlayers] = (0, react_1.useState)(players);
91
95
  const [_children, setChildren] = (0, react_1.useState)(child);
@@ -111,9 +115,18 @@ const PlayersAndVariationPicker = ({ slot, currentTariffId, currentDuration, loa
111
115
  })), [tariff]);
112
116
  const playersArray = (0, get_prices_1.getPricesPlayersArray)(tariff);
113
117
  const maxFromTariff = playersArray.length ? +playersArray[playersArray.length - 1] : 0;
118
+ const minFromTariff = playersArray.length ? +playersArray[0] : 0;
119
+ // Верхняя граница = пересечение тарифа и questroom-капа (с учётом
120
+ // numSeatsAvailable). За пределы тарифа всё равно нельзя — нет цены.
114
121
  const effectiveMax = typeof maxPlayersLimit === 'number' && Number.isFinite(maxPlayersLimit)
115
122
  ? Math.min(maxFromTariff, maxPlayersLimit)
116
123
  : maxFromTariff;
124
+ // Нижняя граница — приоритет questroom.playersMin (canonical), но не
125
+ // ниже минимального ключа тарифа (иначе не на что кликать). Если
126
+ // questroom.playersMin шире тарифа — берём тарифный минимум.
127
+ const effectiveMin = typeof minPlayers === 'number' && Number.isFinite(minPlayers)
128
+ ? Math.max(minFromTariff, minPlayers)
129
+ : minFromTariff;
117
130
  const childrenOptions = (0, react_1.useMemo)(() => {
118
131
  if (!tariff.child || !maxFromTariff)
119
132
  return [];
@@ -131,7 +144,7 @@ const PlayersAndVariationPicker = ({ slot, currentTariffId, currentDuration, loa
131
144
  const totalHeads = _players + (_children || 0);
132
145
  const personPrice = totalHeads > 0 ? Math.floor(teamPrice / totalHeads) : 0;
133
146
  const showVariations = pickerOptions.length > 1;
134
- const variationDescription = (_b = selectedVariation === null || selectedVariation === void 0 ? void 0 : selectedVariation.description) !== null && _b !== void 0 ? _b : null;
147
+ const variationDescription = (_a = selectedVariation === null || selectedVariation === void 0 ? void 0 : selectedVariation.description) !== null && _a !== void 0 ? _a : null;
135
148
  const handleVariationClick = (optionId, isFree) => {
136
149
  if (!isFree)
137
150
  return;
@@ -170,7 +183,10 @@ const PlayersAndVariationPicker = ({ slot, currentTariffId, currentDuration, loa
170
183
  tariff[_players] != null &&
171
184
  `(${(0, format_amount_1.formatAmount)(tariff[_players], currency)})`),
172
185
  react_1.default.createElement(flex_1.Flex, { gap: 'xs', wrap: true, justify: 'start' }, playersOptions
173
- .filter((p) => p.key + (_children || 0) <= effectiveMax)
186
+ .filter((p) => {
187
+ const total = p.key + (_children || 0);
188
+ return total >= effectiveMin && total <= effectiveMax;
189
+ })
174
190
  .map((p) => (react_1.default.createElement(button_1.Button, { key: `adult-${p.key}`, size: 'xs', style: { width: 40, minWidth: 40 }, onClick: () => handleChangePlayers(p.key), view: _players === p.key ? 'primary' : 'outlined' }, p.key))))),
175
191
  !!childrenOptions.length && (react_1.default.createElement(flex_columns_1.FlexColumns, { columns: 1, gr: 8 },
176
192
  react_1.default.createElement(typography_1.Typography.Text, { view: 'title', color: 'secondary' },
@@ -179,7 +195,7 @@ const PlayersAndVariationPicker = ({ slot, currentTariffId, currentDuration, loa
179
195
  !!_children &&
180
196
  tariff.child != null &&
181
197
  `(${(0, format_amount_1.formatAmount)(_children * tariff.child, currency)})`),
182
- !!((_c = selectedVariation === null || selectedVariation === void 0 ? void 0 : selectedVariation.childPriceDescription) === null || _c === void 0 ? void 0 : _c.trim()) && (react_1.default.createElement("div", { style: { whiteSpace: 'pre-line' } },
198
+ !!((_b = selectedVariation === null || selectedVariation === void 0 ? void 0 : selectedVariation.childPriceDescription) === null || _b === void 0 ? void 0 : _b.trim()) && (react_1.default.createElement("div", { style: { whiteSpace: 'pre-line' } },
183
199
  react_1.default.createElement(typography_1.Typography.Text, { view: 'caps', color: 'secondary' }, selectedVariation.childPriceDescription))),
184
200
  react_1.default.createElement(flex_1.Flex, { gap: 'xs', wrap: true, justify: 'start' }, childrenOptions
185
201
  .filter((count) => _players + count <= effectiveMax)
@@ -38,7 +38,7 @@ const usePlayersAndVariationPicker = ({ slot, currentTariffId, currentDuration,
38
38
  const loading = !!api[`${loadSlotDetails.displayName}Loading`];
39
39
  const fetch = api[`${loadSlotDetails.displayName}Fetch`];
40
40
  (0, react_1.useEffect)(() => {
41
- if (!slot)
41
+ if (!(slot === null || slot === void 0 ? void 0 : slot.id) || !slot.questroomId || !slot.date || !slot.start)
42
42
  return;
43
43
  fetch({
44
44
  slotId: slot.id,
@@ -47,8 +47,10 @@ const usePlayersAndVariationPicker = ({ slot, currentTariffId, currentDuration,
47
47
  start: slot.start,
48
48
  orderId,
49
49
  });
50
- // eslint-disable-next-line react-hooks/exhaustive-deps
51
- }, [slot === null || slot === void 0 ? void 0 : slot.id, slot === null || slot === void 0 ? void 0 : slot.questroomId, slot === null || slot === void 0 ? void 0 : slot.date, slot === null || slot === void 0 ? void 0 : slot.start, orderId, slot, fetch]);
50
+ // Only primitive slot fields — callers often pass inline `{ id, date, ... }`
51
+ // objects that get a new reference every render; including `slot` here
52
+ // re-triggers `/slots/details` on every parent render (ERR_INSUFFICIENT_RESOURCES).
53
+ }, [slot === null || slot === void 0 ? void 0 : slot.id, slot === null || slot === void 0 ? void 0 : slot.questroomId, slot === null || slot === void 0 ? void 0 : slot.date, slot === null || slot === void 0 ? void 0 : slot.start, orderId, fetch]);
52
54
  const variations = (0, react_1.useMemo)(() => (data === null || data === void 0 ? void 0 : data.variations) || [], [data === null || data === void 0 ? void 0 : data.variations]);
53
55
  const isFlex = !!(data === null || data === void 0 ? void 0 : data.isFlex);
54
56
  const findCurrentVariation = (rows) => {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@escapenavigator/hooks",
3
- "version": "1.10.124",
3
+ "version": "1.10.125",
4
4
  "publishConfig": {
5
5
  "access": "public"
6
6
  },
@@ -14,9 +14,9 @@
14
14
  "test": "jest"
15
15
  },
16
16
  "dependencies": {
17
- "@escapenavigator/services": "^1.10.132",
18
- "@escapenavigator/types": "^1.10.123",
19
- "@escapenavigator/utils": "^1.10.127",
17
+ "@escapenavigator/services": "^1.10.133",
18
+ "@escapenavigator/types": "^1.10.124",
19
+ "@escapenavigator/utils": "^1.10.128",
20
20
  "react": "19.2.6"
21
21
  },
22
22
  "peerDependencies": {
@@ -30,5 +30,5 @@
30
30
  "ts-jest": "^29.1.1",
31
31
  "typescript": "^5.6"
32
32
  },
33
- "gitHead": "3a138ac9ae22dc8e7c80be4b2bf427a90d703b6c"
33
+ "gitHead": "95bbddd22cbec3e4671d134dc1ff3b6db962329b"
34
34
  }