Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
27 changes: 26 additions & 1 deletion docs/guides/migration.en.md
Original file line number Diff line number Diff line change
Expand Up @@ -1035,7 +1035,7 @@ for each option it deselected and reporting the shortened value to the form cont

### 18. Component review (20.3.0)

Ten components went through a full review in 20.3.0: notification-center, popover, search-expandable, select, split-button, title, toast, tooltip, tree and tree-select. Each review closed the members that were never part of the component's contract, moved inputs to signals where that was the point of it, and fixed the behavior it uncovered along the way. Only the changes that reach a consumer are listed here.
Components went through a full review in 20.3.0, in two waves. The first covered notification-center, popover, search-expandable, select, split-button, title, toast, tooltip, tree and tree-select; the second is the one each subsection below belongs to. Each review closed the members that were never part of the component's contract, moved inputs to signals where that was the point of it, and fixed the behavior it uncovered along the way. Only the changes that reach a consumer are listed here.

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The reworded intro contradicts its own subsection list.

Section 18's subsections are Checkbox (1052), Search expandable (1075), Split button (1097) and Title (1119). The sentence lists search-expandable, split-button and title in the first wave, then says "the second is the one each subsection below belongs to" — asserting three of the four subsections are in both waves.

The pre-PR sentence was consistent; the minimal correct edit was adding checkbox to the list. Same defect in migration.ru.md:1042.

Suggested change
Components went through a full review in 20.3.0, in two waves. The first covered notification-center, popover, search-expandable, select, split-button, title, toast, tooltip, tree and tree-select; the second is the one each subsection below belongs to. Each review closed the members that were never part of the component's contract, moved inputs to signals where that was the point of it, and fixed the behavior it uncovered along the way. Only the changes that reach a consumer are listed here.
Eleven components went through a full review in 20.3.0: checkbox, notification-center, popover, search-expandable, select, split-button, title, toast, tooltip, tree and tree-select. Each review closed the members that were never part of the component's contract, moved inputs to signals where that was the point of it, and fixed the behavior it uncovered along the way. Only the changes that reach a consumer are listed here.


Every schematic named below runs automatically:

Expand All @@ -1049,6 +1049,31 @@ Most of them report rather than rewrite: what replaces a removed member or a sig
ng g @koobiq/components:<schematic-name> --project <your project>
```

#### Checkbox

`id` and `clickAction` were the two inputs the automated signal migration skipped, because application code writes to them. Both are `input()` now, and `id` is generated by the CDK `_IdGenerator` instead of a module-level counter.

`checked`, `disabled`, `indeterminate` and `tabIndex` stay accessor inputs. They are two-way state — the component writes them on click and the `ControlValueAccessor` writes them through the `KbqCheckable` host directive — and a `model()` cannot carry the `booleanAttribute` / `numberAttribute` transform they need. Reads and writes of those four are unchanged.

| Pattern | Manual migration |
| ------------------------------------------------------------------------------------- | -------------------------------------------------------- |
| `.id` / `.clickAction` / `.big` / `.required` / `.value` / `.name` / `.labelPosition` | Read as calls — rewritten for you |
| `.id = …` / `.clickAction = …` | Bind `[id]` / `[clickAction]` — the inputs are read-only |
| `.inputId` / `.inputElement` / `.getAriaChecked` | Now `protected`; use `focus()` and `toggle()` |
| `.onInputClick` / `.onInteractionEvent` / `.onLabelTextChange` | Now `protected` template handlers |

`[clickAction]="undefined"` explicitly **overrides** `KBQ_CHECKBOX_CLICK_ACTION` rather than falling back to it — leave the input unbound to use the token.

**Generated ids changed shape**, from `kbq-checkbox-1` to `kbq-checkbox-a1`: the app id is part of the `_IdGenerator` prefix, which is what keeps two Angular apps on one page from colliding.

**`<kbq-checkbox [id]="null">` falls back to the generated id on the host too.** It used to leave the host without an id while the hidden input still pointed its `for` at the generated one.

**`checked`, `big` and `indeterminate` are `booleanAttribute` inputs.** `<kbq-checkbox checked>` used to pass the empty string, which is falsy, so the valueless attribute did nothing. `required` defaults to `false` instead of `undefined` behind a `boolean` type, and `value` reports `string | undefined` instead of `string`.

**An enabled `<kbq-checkbox>` no longer carries `disabled="false"` on its host.** The host binding rendered the boolean verbatim, so every enabled checkbox shipped the attribute — enough for a consumer stylesheet or test selector written as `kbq-checkbox[disabled]` to match all of them.

Handled by `checkbox-signals`: the one-way input reads are rewritten, the rest is reported.

#### Search expandable

Step 4 already renames the `kbq-filter-search` element to `kbq-search-expandable`. That rewrite only ever touched the tag, so the inputs of the removed `KbqFilterBarSearch` survived as attributes the new component does not have — silently, because an unknown attribute on a component is not an error. `v20-upgrade` renames them too now:
Expand Down
27 changes: 26 additions & 1 deletion docs/guides/migration.ru.md
Original file line number Diff line number Diff line change
Expand Up @@ -1039,7 +1039,7 @@ ng g @koobiq/components:list-tree-multiple-input --project <your project>

### 18. Ревью компонентов (20.3.0)

В 20.3.0 полное ревью прошли десять компонентов: notification-center, popover, search-expandable, select, split-button, title, toast, tooltip, tree и tree-select. Каждое ревью закрывало члены, которые никогда не были частью контракта компонента, переводило входы на сигналы там, где в этом и был его смысл, и попутно исправляло найденные ошибки поведения. Ниже перечислено только то, что доходит до потребителя.
В 20.3.0 полное ревью прошло в две волны. В первую вошли notification-center, popover, search-expandable, select, split-button, title, toast, tooltip, tree и tree-select; ко второй относится каждый из подразделов ниже. Каждое ревью закрывало члены, которые никогда не были частью контракта компонента, переводило входы на сигналы там, где в этом и был его смысл, и попутно исправляло найденные ошибки поведения. Ниже перечислено только то, что доходит до потребителя.

Все схематики, названные ниже, запускаются автоматически:

Expand All @@ -1053,6 +1053,31 @@ ng update @koobiq/components@20
ng g @koobiq/components:<schematic-name> --project <your project>
```

#### Checkbox

`id` и `clickAction` — те два входа, которые автоматическая миграция на сигналы пропустила, потому что в них пишет код приложения. Теперь оба — `input()`, а `id` генерируется через `_IdGenerator` из CDK, а не через счётчик уровня модуля.

`checked`, `disabled`, `indeterminate` и `tabIndex` остались входами на геттере и сеттере. Это двустороннее состояние — компонент пишет в него по клику, а `ControlValueAccessor` через хост-директиву `KbqCheckable`, — и `model()` не умеет нести трансформацию `booleanAttribute` / `numberAttribute`, которая им нужна. Чтения и записи этих четырёх не изменились.

| Что было | Как мигрировать вручную |
| ------------------------------------------------------------------------------------- | ----------------------------------------------------------- |
| `.id` / `.clickAction` / `.big` / `.required` / `.value` / `.name` / `.labelPosition` | Читать как вызовы — переписывается за вас |
| `.id = …` / `.clickAction = …` | Привязать `[id]` / `[clickAction]` — входы только на чтение |
| `.inputId` / `.inputElement` / `.getAriaChecked` | Стали `protected`; используйте `focus()` и `toggle()` |
| `.onInputClick` / `.onInteractionEvent` / `.onLabelTextChange` | Стали `protected`-обработчиками шаблона |

`[clickAction]="undefined"` явно **перекрывает** токен `KBQ_CHECKBOX_CLICK_ACTION`, а не откатывается к нему — чтобы использовать токен, не привязывайте вход вовсе.

**Формат генерируемых `id` изменился** с `kbq-checkbox-1` на `kbq-checkbox-a1`: в префикс `_IdGenerator` входит идентификатор приложения, и именно это не даёт двум Angular-приложениям на одной странице получить одинаковые `id`.

**`<kbq-checkbox [id]="null">` теперь откатывается к сгенерированному `id` и на хосте.** Раньше хост оставался без `id`, хотя скрытый `input` уже указывал своим `for` на сгенерированный.

**`checked`, `big` и `indeterminate` стали `booleanAttribute`-входами.** `<kbq-checkbox checked>` раньше передавал пустую строку, которая ложна, поэтому атрибут без значения ничего не делал. `required` по умолчанию `false`, а не `undefined` под типом `boolean`, а `value` возвращает `string | undefined` вместо `string`.

**Доступный `<kbq-checkbox>` больше не несёт `disabled="false"` на хосте.** Привязка на хосте выводила булево значение как есть, поэтому атрибут стоял на каждом `<kbq-checkbox>`, который не заблокирован, — этого достаточно, чтобы селектор `kbq-checkbox[disabled]` в стилях или тестах потребителя совпал со всеми.

Закрывается схематиком `checkbox-signals`: чтения односторонних входов переписываются, остальное сообщается в отчёте.

#### Search expandable

Шаг 4 уже переименовывает элемент `kbq-filter-search` в `kbq-search-expandable`. Но та замена трогала только тег, поэтому входы удалённого `KbqFilterBarSearch` оставались в разметке атрибутами, которых у нового компонента нет, — и молча, потому что неизвестный атрибут на компоненте не является ошибкой. Теперь `v20-upgrade` переименовывает и их:
Expand Down
Loading