@sberbusiness/triplex-next-mcp-server 1.46.0-beta → 1.48.0-beta
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/README.md +7 -7
- package/bundle/components/AmountField.md +222 -323
- package/bundle/components/Avatar.md +138 -146
- package/bundle/components/CardStatic.md +402 -0
- package/bundle/components/CheckboxTree.md +157 -215
- package/bundle/components/CheckboxTreeExtended.md +7 -7
- package/bundle/components/ChipGroup.md +1 -1
- package/bundle/components/ChipMonthYearPicker.md +4 -4
- package/bundle/components/ChipSuggest.md +7 -6
- package/bundle/components/CollapsibleTree.md +8 -4
- package/bundle/components/CollapsibleTreeExtended.md +8 -6
- package/bundle/components/Confirm.md +346 -281
- package/bundle/components/DateRange.md +351 -210
- package/bundle/components/FooterPage.md +1 -0
- package/bundle/components/FormField.md +11 -4
- package/bundle/components/FormGroup.md +3 -2
- package/bundle/components/LightBox.md +8 -0
- package/bundle/components/ListMaster.md +2 -2
- package/bundle/components/ListTableItem.md +6 -6
- package/bundle/components/MonthYearField.md +15 -4
- package/bundle/components/Slider.md +389 -97
- package/bundle/components/SliderRange.md +486 -105
- package/bundle/components/StatusTracker.md +386 -94
- package/bundle/components/Stepper.md +355 -102
- package/bundle/components/StepperExtended.md +633 -0
- package/bundle/components/SuggestField.md +1049 -96
- package/bundle/components/SwipeableArea.md +7 -7
- package/bundle/components/Tabs.md +265 -92
- package/bundle/components/TabsExtended.md +18 -18
- package/bundle/components/TabsLine.md +301 -127
- package/bundle/components/TagColor.md +187 -66
- package/bundle/components/TagGroup.md +184 -48
- package/bundle/components/TextareaField.md +278 -70
- package/bundle/components/TopOverlay.md +17 -1
- package/bundle/components/TreeView.md +16 -7
- package/bundle/components/TriggerClickOnKeyDownEvent.md +277 -0
- package/bundle/components/UploadZone.md +318 -0
- package/bundle/guides/codestyle.md +16 -1
- package/bundle/guides/commits.md +47 -1
- package/bundle/guides/tests.md +23 -2
- package/bundle/manifest.json +48 -21
- package/bundle/release-notes/1.47.0.mdx +115 -0
- package/bundle/release-notes/1.48.0.mdx +68 -0
- package/bundle/release-notes/1.49.0.mdx +7 -0
- package/bundle/tokens.json +3 -3
- package/dist/index.js +220 -6
- package/dist/index.js.map +1 -1
- package/package.json +1 -1
|
@@ -62,7 +62,7 @@ version: "1.0"
|
|
|
62
62
|
- Горизонтальные внутренние отступы корневого `div` задаются инлайн-стилем из ширин префикса и постфикса (`paddingLeft: prefixWidth`, `paddingRight: postfixWidth`). Значение по умолчанию — `TARGET_PADDING_X_DEFAULT` (12px); `FormFieldPrefix` / `FormFieldPostfix` измеряют себя через `ResizeObserver` и обновляют его. Пользовательский `style` мерджится последним и может переопределить отступы.
|
|
63
63
|
- Класс `filled` выставляется, когда вложенный элемент ввода сообщил о наличии значения. Для `FormFieldInput` / `FormFieldTextarea` это включает браузерное автозаполнение (ловится через CSS-анимационные хуки `autofill-applied-hook` / `autofill-cancelled-hook`), для `FormFieldTarget` — наличие `children`.
|
|
64
64
|
- Кнопка `FormFieldClear` показывается стилями только при `filled` и hover/активном состоянии непустого и не заблокированного поля, а также при собственном фокусе (`:focus`) — чтобы кнопка оставалась видимой при клавиатурной навигации.
|
|
65
|
-
- Идентификаторы генерируются субкомпонентами (`uniqueId` из `lodash-es`, не `React.useId` — код должен оставаться совместимым с React 17) и попадают в контекст как `targetId` / `labelId`; на них опирается связка `
|
|
65
|
+
- Идентификаторы генерируются субкомпонентами (`uniqueId` из `lodash-es`, не `React.useId` — код должен оставаться совместимым с React 17) и попадают в контекст как `targetId` / `labelId`; на них опирается связка лейбла и поля. `targetId` публикуют только labelable-элементы (`FormFieldInput`, `FormFieldTextarea`, а также `FormFieldMaskedInput` — он рендерит `FormFieldInput` внутри себя через `render`); `FormFieldTarget` его не публикует — см. Accessibility.
|
|
66
66
|
- Вне `FormField` субкомпоненты используют `initialFormFieldContext`, где `filled: true` — это осознанный временный фикс для `DropdownMobileHeader`, а сеттеры являются no-op.
|
|
67
67
|
|
|
68
68
|
---
|
|
@@ -104,9 +104,10 @@ FormField.Target_PlaceholderColor_Default
|
|
|
104
104
|
- Barrel `src/components/FormField/index.ts` реэкспортирует `enums`, `types`, `components` и сам `FormField` — состав экспортов не сокращать. Маппинг статуса на класс (`STATUS_TO_CLASS_NAME_MAP`) — внутренняя константа модуля и в barrel не входит.
|
|
105
105
|
- `FormFieldContext` и `FormFieldDescriptionContext` в barrel не входят: это внутренний механизм семейства, но на нём завязаны все субкомпоненты — менять форму значения контекста без правки субкомпонентов нельзя.
|
|
106
106
|
- Классы `formField`, `filled`, `active`, `error`, `warning`, `disabled`, а также `sm` / `md` / `lg` проверяются unit-тестами и используются в вложенных селекторах стилей семейства.
|
|
107
|
+
- `disabled` исключён из props элементов ввода (`IFormFieldInputProps`, `IFormFieldTextareaProps`, `IFormFieldMaskedInputProps` — через `Omit`): блокировка задаётся только `status={EFormFieldStatus.DISABLED}`, иначе переданное значение молча перетиралось бы внутренним.
|
|
107
108
|
- Генерация id — через `uniqueId` (`lodash-es`), без `React.useId`: ветка `release-0` собирается на React 17.
|
|
108
109
|
- `FormFieldDescription` и `FormFieldCounter` объявлены как `React.FC` без `forwardRef` — осознанное историческое отличие от остальных субкомпонентов. Добавление ref расширяет публичный API; решение владельца — оставить как есть.
|
|
109
|
-
- Внутренние утилиты семейства (`components/utils.ts` — `isFilled
|
|
110
|
+
- Внутренние утилиты семейства (`components/utils.ts` — `isFilled`; `components/useFormFieldAffixWidth.ts`) намеренно не попадают в barrel `components/index.ts`. Общий `setForwardedRef` вынесен в `src/helpers/setForwardedRef.ts` и импортируется относительным путём.
|
|
110
111
|
- Компонент не рендерит собственных подписей и текстов — библиотека мультиязычная.
|
|
111
112
|
|
|
112
113
|
---
|
|
@@ -114,9 +115,11 @@ FormField.Target_PlaceholderColor_Default
|
|
|
114
115
|
## Accessibility
|
|
115
116
|
|
|
116
117
|
- Корневой элемент — обычный `div` без роли: семантику даёт вложенный нативный `input` / `textarea`.
|
|
117
|
-
- Связка лейбла и поля: `FormFieldLabel`
|
|
118
|
+
- Связка лейбла и поля: когда в поле есть labelable-элемент, `FormFieldLabel` рендерит `<label htmlFor={targetId}>`, а элемент ввода — сгенерированный `id`. Поэтому `screen.getByLabelText(...)` находит поле.
|
|
118
119
|
- `FormFieldTarget` (нередактируемое значение, например для select-подобных полей) получает `tabIndex={0}`, `aria-labelledby={labelId}` и `aria-disabled`; при `status = DISABLED` — `tabIndex={-1}`.
|
|
119
|
-
-
|
|
120
|
+
- `FormFieldTarget` намеренно **не** публикует свой `id` как `targetId`: это `<div>`, а не labelable-элемент, и `label[htmlFor]` на него ссылаться не может. В таких полях `FormFieldLabel` рендерит `<span>`, а не `<label>` — несвязанный `<label>` браузер тоже считает ошибкой разметки. Имя полю даёт `aria-labelledby` на `FormFieldTarget`, поэтому `screen.getByLabelText(...)` продолжает находить поле.
|
|
121
|
+
- Следствие выбора тега по контексту: `targetId` публикуется в `useLayoutEffect`, поэтому в полях с labelable-элементом лейбл на первом рендере — `<span>`, а после layout-эффекта DOM-узел заменяется на `<label>`. Замена происходит до отрисовки и визуально незаметна, но ref на `FormFieldLabel` вызывается для обоих узлов.
|
|
122
|
+
- При `status = DISABLED` вложенные `input` / `textarea` получают нативный `disabled`, то есть выпадают из таб-порядка. Передать `disabled` мимо статуса нельзя — атрибут исключён из props элементов ввода.
|
|
120
123
|
- Плейсхолдер маски в `FormFieldMaskedInput` рендерится с `aria-hidden="true"` — скринридер читает только реальное значение input.
|
|
121
124
|
- Текст описания (`FormFieldDescription`) визуально связан с полем, но не связывается автоматически через `aria-describedby` — при необходимости потребитель передаёт `aria-describedby` элементу ввода сам.
|
|
122
125
|
|
|
@@ -168,6 +171,10 @@ FormField.Target_PlaceholderColor_Default
|
|
|
168
171
|
| 2026-08-03 | Ломающее изменение: `statusToClassNameMap` убран из публичного barrel и переименован во внутреннюю константу `STATUS_TO_CLASS_NAME_MAP`. Зафиксировано в release notes 1.41.0. |
|
|
169
172
|
| 2026-09-04 | Исправлено: у `FormFieldTextarea` фиксированная `height` для размеров `sm` / `md` / `lg` заменена на `min-height`. |
|
|
170
173
|
| 2026-09-09 | Исправлено: значение с кодом страны раскладывалось по маске телефона со сдвигом и теряло последнюю цифру. Нормализация номера вынесена в `normalizePhoneText` и применяется и к внешнему `value`, и к слою с маской |
|
|
174
|
+
| 2026-09-16 | Исправлено: `FormFieldTarget` больше не публикует свой `id` как `targetId`, а `FormFieldLabel` рендерит `<span>` вместо `<label>`, когда в поле нет labelable-элемента. Ref `FormFieldLabel` типизирован как `HTMLElement`, props — как `React.HTMLAttributes<HTMLElement>`. Доступное имя по-прежнему даёт `aria-labelledby`. |
|
|
175
|
+
| 2026-09-16 | Исправлено: `FormFieldInput` и `FormFieldTextarea` очищают `targetId` при размонтировании — иначе после замены элемента ввода на `FormFieldTarget` лейбл сохранял `htmlFor` с `id` удалённого элемента. |
|
|
176
|
+
| 2026-09-17 | Ломающее изменение: `disabled` убран из `IFormFieldTextareaProps` через `Omit` — так же, как он уже был убран у `FormFieldInput` и `FormFieldMaskedInput`. Поведение не менялось (статус перетирал переданное значение и раньше), но передача `disabled` в props теперь ошибка компиляции. Правка по ревью PR #629, зафиксирована в release notes 1.47.0 |
|
|
177
|
+
| 2026-09-23 | Исправлено: при смене `status` на `EFormFieldStatus.DISABLED`, пока вложенный элемент ввода в фокусе, `FormField` теперь явно сбрасывает состояние `focused` в `useLayoutEffect`. |
|
|
171
178
|
|
|
172
179
|
---
|
|
173
180
|
|
|
@@ -76,8 +76,9 @@ version: "1.0"
|
|
|
76
76
|
Семантику задаёт потребитель через проброшенные атрибуты — например `role="group"` вместе с
|
|
77
77
|
`aria-labelledby`, если группа должна объявляться скринридером как единое целое.
|
|
78
78
|
|
|
79
|
-
Лейбл связывается с полем внутри `FormField`:
|
|
80
|
-
в `FormFieldContext
|
|
79
|
+
Лейбл связывается с полем внутри `FormField`: в полях с элементом ввода `FormFieldLabel` берёт
|
|
80
|
+
`htmlFor` из `targetId` в `FormFieldContext`, в select-подобных — связь даёт `aria-labelledby`
|
|
81
|
+
на `FormFieldTarget` (см. `FormField-ai.md`). Описание автоматически не связывается — `aria-describedby` на элементе
|
|
81
82
|
ввода (как и `aria-invalid` для ошибки) задаёт потребитель, см. `FormField-ai.md`. `FormGroup`
|
|
82
83
|
не участвует ни в том, ни в другом.
|
|
83
84
|
|
|
@@ -101,6 +101,13 @@ LightBox.SideOverlay_Background
|
|
|
101
101
|
css-переменную `--lightBox-scroll-width`, которую вычитают из ширины оверлеев. Ширины размеров
|
|
102
102
|
(`664/864/1064/1264`) заданы LESS-константами `@lightBox-content-max-width-*`.
|
|
103
103
|
|
|
104
|
+
Боковые отступы контента лайтбокса (`@lightBoxContentPaddingX`, 80px — место под кнопки
|
|
105
|
+
вперёд/назад, на экранах до 1024px включительно 0) публикуются css-переменной
|
|
106
|
+
`--lightBox-content-padding-x` на `.lightBoxContent`. По ней потомки выравниваются с колонкой
|
|
107
|
+
страницы — так это делает обёртка `TopOverlay`. Переменная объявлена именно на `.lightBoxContent`,
|
|
108
|
+
поэтому вне его поддерева (например в `LightBox.SideOverlay` — он сиблинг `LightBox.Content`,
|
|
109
|
+
а не его потомок) она не видна, и читающие её стили получают фолбэк 0.
|
|
110
|
+
|
|
104
111
|
---
|
|
105
112
|
|
|
106
113
|
## Инварианты
|
|
@@ -202,6 +209,7 @@ css-переменную `--lightBox-scroll-width`, которую вычита
|
|
|
202
209
|
|
|
203
210
|
| Дата | Изменение |
|
|
204
211
|
|---|---|
|
|
212
|
+
| 2026-09-21 | Боковые отступы `.lightBoxContent` вынесены в css-переменную `--lightBox-content-padding-x` (константа `@lightBoxContentPaddingX`). Нужна, чтобы `TopOverlay` выравнивался по колонке контента |
|
|
205
213
|
| 2026-07-22 | Создан документ (Phase 1 AI-Ready). В том же изменении — AI-рефакторинг: JSDoc на props, общий `LightBoxArrow` для Prev/Next, хук `useLightBoxSidebarVisibility` для сайдбаров, устранение eslint-подавлений; публичный API не менялся |
|
|
206
214
|
| 2026-07-22 | Добавлен `export` к props-интерфейсам `ILightBoxControlsProps`, `ILightBoxCloseProps`, `ILightBoxPrevProps`, `ILightBoxNextProps`, `ILightBoxSideOverlayLoaderProps` (аддитивно, для консистентности с остальными интерфейсами компонента) |
|
|
207
215
|
| 2026-07-22 | Багфиксы по ревью PR #474: клавиатурные триггеры контролов целятся в видимую кнопку (стрелки не работали на desktop, Esc — на mobile); таймер-хак блокировки скролла заменён счётчиком смонтированных лайтбоксов; `LightBoxViewManager` снимает классы mount-ноды при размонтировании последнего менеджера |
|
|
@@ -628,13 +628,13 @@ export const Default = () => {
|
|
|
628
628
|
controlButtons={
|
|
629
629
|
<>
|
|
630
630
|
<ListItemControlsButton
|
|
631
|
-
icon={<AttachmentStrokeSrvIcon20 paletteIndex={
|
|
631
|
+
icon={<AttachmentStrokeSrvIcon20 paletteIndex={0} />}
|
|
632
632
|
>
|
|
633
633
|
Скачать
|
|
634
634
|
</ListItemControlsButton>
|
|
635
635
|
|
|
636
636
|
<ListItemControlsButtonDropdown
|
|
637
|
-
icon={<DotshorizontalStrokeSrvIcon20 paletteIndex={
|
|
637
|
+
icon={<DotshorizontalStrokeSrvIcon20 paletteIndex={0} />}
|
|
638
638
|
options={itemActions}
|
|
639
639
|
>
|
|
640
640
|
Действия
|
|
@@ -156,11 +156,11 @@ export const Default = () => {
|
|
|
156
156
|
onClickItem={() => {}}
|
|
157
157
|
controlButtons={
|
|
158
158
|
<>
|
|
159
|
-
<ListItemControlsButton icon={<AttachmentStrokeSrvIcon20 paletteIndex={
|
|
159
|
+
<ListItemControlsButton icon={<AttachmentStrokeSrvIcon20 paletteIndex={0} />}>
|
|
160
160
|
Скачать
|
|
161
161
|
</ListItemControlsButton>
|
|
162
162
|
<ListItemControlsButtonDropdown
|
|
163
|
-
icon={<DotshorizontalStrokeSrvIcon20 paletteIndex={
|
|
163
|
+
icon={<DotshorizontalStrokeSrvIcon20 paletteIndex={0} />}
|
|
164
164
|
options={options}
|
|
165
165
|
>
|
|
166
166
|
Действия
|
|
@@ -245,11 +245,11 @@ export const Selectable = () => {
|
|
|
245
245
|
onClickItem={() => console.log("Клик по карточке.")}
|
|
246
246
|
controlButtons={
|
|
247
247
|
<>
|
|
248
|
-
<ListItemControlsButton icon={<AttachmentStrokeSrvIcon20 paletteIndex={
|
|
248
|
+
<ListItemControlsButton icon={<AttachmentStrokeSrvIcon20 paletteIndex={0} />}>
|
|
249
249
|
Скачать
|
|
250
250
|
</ListItemControlsButton>
|
|
251
251
|
<ListItemControlsButtonDropdown
|
|
252
|
-
icon={<DotshorizontalStrokeSrvIcon20 paletteIndex={
|
|
252
|
+
icon={<DotshorizontalStrokeSrvIcon20 paletteIndex={0} />}
|
|
253
253
|
options={options}
|
|
254
254
|
>
|
|
255
255
|
Действия
|
|
@@ -354,11 +354,11 @@ export const WithSwipeEmulation = () => {
|
|
|
354
354
|
onClickItem={() => console.log("Клик по карточке.")}
|
|
355
355
|
controlButtons={
|
|
356
356
|
<>
|
|
357
|
-
<ListItemControlsButton icon={<AttachmentStrokeSrvIcon20 paletteIndex={
|
|
357
|
+
<ListItemControlsButton icon={<AttachmentStrokeSrvIcon20 paletteIndex={0} />}>
|
|
358
358
|
Скачать
|
|
359
359
|
</ListItemControlsButton>
|
|
360
360
|
<ListItemControlsButtonDropdown
|
|
361
|
-
icon={<DotshorizontalStrokeSrvIcon20 paletteIndex={
|
|
361
|
+
icon={<DotshorizontalStrokeSrvIcon20 paletteIndex={0} />}
|
|
362
362
|
options={options}
|
|
363
363
|
>
|
|
364
364
|
Действия
|
|
@@ -61,7 +61,6 @@ version: "1.0"
|
|
|
61
61
|
- `forwardRef` на компоненте — не убирать. Ref пробрасывается в `DatePickerExtended` (корневой DOM-элемент — элемент `DatePickerExtended`).
|
|
62
62
|
- Публичный API (`IMonthYearFieldProps`: `value`, `onChange`, `onClear`, `targetProps`, `placeholder` + унаследованные `size`/`status`/`label` и props `DatePickerExtended`) — изменение имён/типов/значений — breaking change.
|
|
63
63
|
- Поле read-only по контракту — не делать его редактируемым без обсуждения (компонент не имеет логики валидации клавиатурного ввода).
|
|
64
|
-
- Отображаемый формат `"MMM YYYY"` зафиксирован в `inputMonthYearFormat`; менять его — визуальный breaking change для потребителей.
|
|
65
64
|
- Sync-эффект в `MonthYearField.tsx` (`useEffect` по `[value, format, limitRange]` с `eslint-disable react-hooks/exhaustive-deps`) — намеренная синхронизация derived-стейта `pickerValues` с внешним `value`. Не переписывать без анализа поведения: сравнение идёт по `inputString`, чтобы не сбрасывать стейт при эквивалентных значениях.
|
|
66
65
|
- Внутренние символы `MonthYearPickerUtils` (`utils.ts`), `MonthYearFieldContext`, `MonthYearFieldTarget` не экспортируются через barrel — это приватные детали реализации.
|
|
67
66
|
|
|
@@ -130,7 +129,7 @@ export const DefaultExample = () => {
|
|
|
130
129
|
|
|
131
130
|
return (
|
|
132
131
|
<div style={{ maxWidth: 300 }}>
|
|
133
|
-
<MonthYearField value={value} placeholder="
|
|
132
|
+
<MonthYearField value={value} placeholder="Select to proceed" label="Label" onChange={setValue} />
|
|
134
133
|
</div>
|
|
135
134
|
);
|
|
136
135
|
};
|
|
@@ -154,7 +153,13 @@ const SizeItem = ({ size }: ISizeItemProps) => {
|
|
|
154
153
|
return (
|
|
155
154
|
<div style={{ maxWidth: 300 }}>
|
|
156
155
|
<div style={{ marginBottom: 8, fontSize: 16, fontWeight: 700 }}>{size.toUpperCase()}</div>
|
|
157
|
-
<MonthYearField
|
|
156
|
+
<MonthYearField
|
|
157
|
+
size={size}
|
|
158
|
+
value={value}
|
|
159
|
+
label="Label"
|
|
160
|
+
placeholder="Select to proceed"
|
|
161
|
+
onChange={setValue}
|
|
162
|
+
/>
|
|
158
163
|
</div>
|
|
159
164
|
);
|
|
160
165
|
};
|
|
@@ -188,7 +193,13 @@ const StatusItem = ({ status }: IStatusItemProps) => {
|
|
|
188
193
|
return (
|
|
189
194
|
<div style={{ maxWidth: 300 }}>
|
|
190
195
|
<div style={{ marginBottom: 8, fontSize: 16, fontWeight: 700 }}>{status.toUpperCase()}</div>
|
|
191
|
-
<MonthYearField
|
|
196
|
+
<MonthYearField
|
|
197
|
+
status={status}
|
|
198
|
+
value={value}
|
|
199
|
+
label="Label"
|
|
200
|
+
placeholder="Select to proceed"
|
|
201
|
+
onChange={setValue}
|
|
202
|
+
/>
|
|
192
203
|
</div>
|
|
193
204
|
);
|
|
194
205
|
};
|