@synerise/ds-factors 1.12.9 → 1.12.11

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.
Files changed (3) hide show
  1. package/CHANGELOG.md +8 -0
  2. package/CLAUDE.md +192 -0
  3. package/package.json +31 -30
package/CHANGELOG.md CHANGED
@@ -3,6 +3,14 @@
3
3
  All notable changes to this project will be documented in this file.
4
4
  See [Conventional Commits](https://conventionalcommits.org) for commit guidelines.
5
5
 
6
+ ## [1.12.11](https://github.com/Synerise/synerise-design/compare/@synerise/ds-factors@1.12.10...@synerise/ds-factors@1.12.11) (2026-07-23)
7
+
8
+ **Note:** Version bump only for package @synerise/ds-factors
9
+
10
+ ## [1.12.10](https://github.com/Synerise/synerise-design/compare/@synerise/ds-factors@1.12.9...@synerise/ds-factors@1.12.10) (2026-07-16)
11
+
12
+ **Note:** Version bump only for package @synerise/ds-factors
13
+
6
14
  ## [1.12.9](https://github.com/Synerise/synerise-design/compare/@synerise/ds-factors@1.12.8...@synerise/ds-factors@1.12.9) (2026-07-09)
7
15
 
8
16
  **Note:** Version bump only for package @synerise/ds-factors
package/CLAUDE.md ADDED
@@ -0,0 +1,192 @@
1
+ # Factors (`@synerise/ds-factors`)
2
+
3
+ > A polymorphic input component that renders different input UIs based on a selected factor type (text, number, date, parameter, etc.) with an optional type-switcher dropdown.
4
+
5
+ ## Package structure
6
+
7
+ ```
8
+ src/
9
+ Factors.tsx — main component; defines FACTOR_TYPE_MAPPING
10
+ Factors.types.ts — all types (FactorsProps, FactorsTexts, value types, etc.)
11
+ index.ts — public exports
12
+ style/
13
+ Factors.style.ts — Group wrapper styled component
14
+ hooks/
15
+ useTexts.tsx — merges user texts with react-intl defaults
16
+ FactorTypeSelector/
17
+ FactorTypeSelector.tsx — dropdown to switch between factor types
18
+ FactorTypeSelector.styles.ts — type selector button styles
19
+ FactorValue/
20
+ FactorValue.tsx — dispatcher that renders the correct input component
21
+ FactorValue.style.ts — input wrapper styles
22
+ Text/ — text input (default, expansible-modal, autocomplete modes)
23
+ Number/ — number input via @synerise/ds-input-number
24
+ Parameter/ — parameter selector with grouped/search/virtualized list
25
+ DynamicKey/ — two-field key-value input
26
+ Formula/ — formula editor trigger + modal
27
+ Date/ — date picker via @synerise/ds-date-picker
28
+ DateRange/ — date range picker via @synerise/ds-date-range-picker
29
+ RelativeDate/ — relative date selector (offset + unit + before/after)
30
+ Array/ — array editor with creator, raw paste, and collector modes
31
+ __specs__/
32
+ Factors.spec.tsx — Vitest tests
33
+ Factors.array.spec.tsx — Vitest tests for array type
34
+ ```
35
+
36
+ ## Public exports
37
+
38
+ ### `Factors` (default export)
39
+
40
+ | Prop | Type | Default | Description |
41
+ |------|------|---------|-------------|
42
+ | `selectedFactorType` | `FactorType` | — | **Required.** Currently active factor type |
43
+ | `onChangeValue` | `(value: FactorValueType) => void` | — | **Required.** Called when the value changes |
44
+ | `value` | `FactorValueType` | — | **Required.** Current value |
45
+ | `defaultFactorType` | `FactorType` | `'text'` | Fallback type used when `selectedFactorType` is undefined or unrecognised |
46
+ | `setSelectedFactorType` | `(factor: FactorType) => void` | `NOOP` | Called when user picks a new type from the selector |
47
+ | `textType` | `'default' \| 'expansible' \| 'autocomplete'` | `'default'` | Variant of the text input |
48
+ | `allowClear` | `boolean` | `true` | Shows clear button on inputs that support it |
49
+ | `withoutTypeSelector` | `boolean` | `false` | Hides the type-switcher dropdown |
50
+ | `uncontrolledComponent` | `boolean` | `false` | Sub-components manage their own open/close state internally |
51
+ | `error` | `boolean` | — | Shows error styling on the input |
52
+ | `errorText` | `ReactNode` | — | Error message (usage depends on the input type) |
53
+ | `unavailableFactorTypes` | `FactorType[]` | — | Types to exclude from the switcher |
54
+ | `availableFactorTypes` | `FactorType[]` | — | Explicit allowlist of types to show in the switcher |
55
+ | `customFactorValueComponents` | `Partial<FactorTypeMapping>` | — | Override `component`, `name`, or `icon` for any built-in factor type |
56
+ | `factorValueExtraProps` | `Partial<ExtraPropsMapping>` | — | Pass extra icon/tooltip props to `text` or `dynamicKey` inputs |
57
+ | `getPopupContainerOverride` | `(trigger: HTMLElement \| null) => HTMLElement` | — | Overrides popup container for child dropdowns/tooltips |
58
+ | `onActivate` | `() => void` | — | Called when the input opens/focuses |
59
+ | `onDeactivate` | `() => void` | — | Called when the input closes/blurs |
60
+ | `opened` | `boolean` | — | Externally controls whether the dropdown/modal is open |
61
+ | `loading` | `boolean` | — | Shows loading state in the input |
62
+ | `preventAutoloadData` | `boolean` | — | Prevents auto-fetching data in parameter input |
63
+ | `arrayProps` | `{ itemType?: 'string' \| 'number'; limit?: number; collectorSuggestions?: CollectorValue[] }` | — | Configuration for the array factor type |
64
+ | `autoResize` | `AutoResizeProp` | — | Auto-resize behaviour for text inputs |
65
+ | `relativeDateProps` | `{ triggerValueFormatter?: (value) => string; availableUnits?: RelativeDateUnit[] }` | — | Customise relative date display and available units |
66
+ | `autocompleteText` | `{ options: string[] }` | — | Autocomplete suggestions (used when `textType='autocomplete'`) |
67
+ | `parameters` | See below | — | Configuration for `parameter` / `contextParameter` types |
68
+ | `onParamsClick` | `() => void` | — | Called when the parameter button is clicked (alternative to full parameter dropdown) |
69
+ | `formulaEditor` | `ReactNode` | — | Content rendered inside the formula editor modal |
70
+ | `texts` | `DeepPartial<FactorsTexts>` | — | Override any subset of i18n strings |
71
+ | `factorKey` | `ReactText` | — | Unique key for the factor instance; used to reset state on remount |
72
+ | `inputProps` | `Partial<Omit<InputProps, 'value' \| 'onChange' \| ..>>` | — | Extra props forwarded to text inputs |
73
+ | `readOnly` | `boolean` | — | Disables all interaction |
74
+
75
+ #### `parameters` shape
76
+
77
+ | Field | Type | Description |
78
+ |-------|------|-------------|
79
+ | `buttonLabel` | `ReactNode` | Label shown on the parameter trigger button |
80
+ | `buttonIcon` | `ReactNode` | Icon shown on the trigger button |
81
+ | `items` | `ParameterItem[]` | Full list of selectable parameters |
82
+ | `groups` | `ParameterGroup[]` | Group definitions for grouping items |
83
+ | `recentItems` | `ParameterItem[]` | Items shown at the top as recently used |
84
+ | `selectedButtonColored` | `boolean` | Apply accent colour to the button when a value is selected |
85
+ | `renderEmptyGroups` | `boolean` | Show group headers even if the group has no items |
86
+ | `showAllGroup` | `boolean` | **@deprecated** |
87
+ | `dropdownDimensionsConfig` | `{ defaultHeight?, lowerHeight?, threshold? }` | Override dropdown height at different viewport sizes |
88
+
89
+ ### `factorTypes`
90
+
91
+ The built-in `FACTOR_TYPE_MAPPING` exported as a named value. Maps each `DefinedFactorTypes` key to `{ name, icon, component }`. Use alongside `customFactorValueComponents` to extend or inspect defaults.
92
+
93
+ ### Types exported
94
+
95
+ | Export | Description |
96
+ |--------|-------------|
97
+ | `ALL_FACTOR_TYPES` | Readonly tuple of all 10 type strings |
98
+ | `FactorType` | `LiteralStringUnion` of the 10 types (accepts custom strings) |
99
+ | `DefinedFactorTypes` | Strict union of the 10 built-in type strings |
100
+ | `FactorValueType` | Union of all possible value types |
101
+ | `FactorsProps` | Full props interface |
102
+ | `FactorsTexts` | Full texts interface |
103
+ | `ParameterValueType` | Shape of a selected parameter value |
104
+ | `ParameterItem` | Shape of an item in the parameter list |
105
+ | `ParameterGroup` | Shape of a parameter group |
106
+ | `FactorValueComponentProps` | Props received by each factor-value component |
107
+ | `InputProps` | **@deprecated** alias for `FactorValueComponentProps` |
108
+ | `FactorValueType` | All possible value shapes |
109
+ | `DynamicKeyValueType` | `{ key: ReactText; value: ReactText }` |
110
+ | `FormulaValueType` | `{ name: string; value: string }` |
111
+ | `SelectedFactorType` | `{ name, icon, component }` — one entry from the type mapping |
112
+ | `FactorTypeSelectorProps`, `FormulaModalProps`, `TextModalProps`, `ParameterDropdownProps` | Internal component props (for extensibility) |
113
+
114
+ ## Usage patterns
115
+
116
+ ```tsx
117
+ import Factors from '@synerise/ds-factors';
118
+ import type { FactorType, FactorValueType } from '@synerise/ds-factors';
119
+
120
+ const [factorType, setFactorType] = useState<FactorType>('text');
121
+ const [value, setValue] = useState<FactorValueType>('');
122
+
123
+ <Factors
124
+ selectedFactorType={factorType}
125
+ setSelectedFactorType={setFactorType}
126
+ defaultFactorType="text"
127
+ value={value}
128
+ onChangeValue={setValue}
129
+ />
130
+
131
+ // Without type selector
132
+ <Factors
133
+ selectedFactorType="number"
134
+ defaultFactorType="number"
135
+ withoutTypeSelector
136
+ value={42}
137
+ onChangeValue={setValue}
138
+ />
139
+
140
+ // Array type with limit
141
+ <Factors
142
+ selectedFactorType="array"
143
+ defaultFactorType="array"
144
+ value={['a', 'b']}
145
+ onChangeValue={setValue}
146
+ arrayProps={{ itemType: 'string', limit: 10 }}
147
+ />
148
+
149
+ // Custom factor component override
150
+ import { factorTypes } from '@synerise/ds-factors';
151
+ <Factors
152
+ selectedFactorType="text"
153
+ defaultFactorType="text"
154
+ value=""
155
+ onChangeValue={setValue}
156
+ customFactorValueComponents={{
157
+ text: { ..factorTypes.text, component: MyCustomTextInput },
158
+ }}
159
+ />
160
+ ```
161
+
162
+ ## Custom hooks
163
+
164
+ ### `useTexts`
165
+
166
+ Merges the user-provided `texts` (any `DeepPartial<FactorsTexts>`) with react-intl defaults using `lodash.merge`. Returns a complete `FactorsTexts` object. All default strings come from `DS.FACTORS.*` intl message IDs. Requires an `IntlProvider` ancestor.
167
+
168
+ ## Styling
169
+
170
+ Styles are minimal — the outer `Group` wrapper uses `@synerise/ds-input` group primitives. Individual factor value components each have their own styles files. All use `@synerise/ds-core` theme tokens; no hardcoded colours.
171
+
172
+ ## Key dependencies
173
+
174
+ - `@synerise/ds-input` — text and number inputs
175
+ - `@synerise/ds-date-picker` / `@synerise/ds-date-range-picker` — date/dateRange types
176
+ - `@synerise/ds-collector` — multi-value entry in the array editor
177
+ - `@synerise/ds-autocomplete` — text type with `textType='autocomplete'`
178
+ - `@synerise/ds-information-card` — optional info card on parameter items
179
+ - `react-window` — virtualized list in the parameter dropdown
180
+ - `react-intl` — i18n for all default text strings
181
+
182
+ ## Implementation notes
183
+
184
+ - **`FactorType` vs `DefinedFactorTypes`**: `FactorType` is a `LiteralStringUnion` that accepts any string (for custom types). `DefinedFactorTypes` is the strict union of the 10 built-in types. If `selectedFactorType` is not in `FACTOR_TYPE_MAPPING`, the component silently falls back to `defaultFactorType` (default `'text'`).
185
+ - **`customFactorValueComponents` merging**: Custom entries are shallowly merged with `FACTOR_TYPE_MAPPING` entries — you can override only `component`, `name`, or `icon` independently.
186
+ - **`parameter` vs `contextParameter`**: Both use the same `ParameterInput` component. The distinction is semantic and controlled by the consumer.
187
+ - **`uncontrolledComponent`**: When `true`, each sub-component manages its own open state. When `false` (default), the parent controls open state via the `opened` prop.
188
+ - **Array raw mode**: Backtick-wrapped items (`` `value` ``) are treated as single units containing commas. Numeric arrays validate each item on paste.
189
+ - **`parameters.showAllGroup`** is `@deprecated` — do not use.
190
+ - **`InputProps` export** is `@deprecated** — use `FactorValueComponentProps` instead.
191
+ - **`react-intl` is a peer dependency** — component throws at runtime without an `IntlProvider` ancestor.
192
+ - **Vitest**: This package uses Vitest (not Jest) — `vitest.config.ts` is present.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@synerise/ds-factors",
3
- "version": "1.12.9",
3
+ "version": "1.12.11",
4
4
  "description": "Factors UI Component for the Synerise Design System",
5
5
  "license": "ISC",
6
6
  "repository": "Synerise/synerise-design",
@@ -17,6 +17,7 @@
17
17
  "files": [
18
18
  "/dist",
19
19
  "CHANGELOG.md",
20
+ "CLAUDE.md",
20
21
  "README.md",
21
22
  "package.json",
22
23
  "LICENSE.md"
@@ -41,34 +42,34 @@
41
42
  ],
42
43
  "types": "dist/index.d.ts",
43
44
  "dependencies": {
44
- "@synerise/ds-alert": "^1.1.60",
45
- "@synerise/ds-autocomplete": "^1.2.49",
46
- "@synerise/ds-badge": "^1.0.57",
47
- "@synerise/ds-button": "^1.5.33",
48
- "@synerise/ds-button-group": "^1.1.58",
49
- "@synerise/ds-collector": "^1.4.49",
50
- "@synerise/ds-date-picker": "^1.4.20",
51
- "@synerise/ds-date-range-picker": "^1.7.10",
52
- "@synerise/ds-divider": "^1.3.15",
53
- "@synerise/ds-dropdown": "^1.3.18",
54
- "@synerise/ds-empty-states": "^1.0.48",
55
- "@synerise/ds-icon": "^1.18.4",
56
- "@synerise/ds-information-card": "^1.7.6",
57
- "@synerise/ds-inline-edit": "^1.1.46",
58
- "@synerise/ds-input": "^1.7.12",
59
- "@synerise/ds-input-number": "^1.2.49",
60
- "@synerise/ds-list-item": "^1.6.0",
61
- "@synerise/ds-modal": "^1.6.4",
62
- "@synerise/ds-result": "^1.0.64",
63
- "@synerise/ds-scrollbar": "^1.5.1",
64
- "@synerise/ds-search": "^1.5.32",
65
- "@synerise/ds-select": "^1.3.33",
66
- "@synerise/ds-short-cuts": "^1.0.55",
67
- "@synerise/ds-skeleton": "^1.0.59",
68
- "@synerise/ds-tabs": "^1.2.4",
69
- "@synerise/ds-tag": "^1.4.31",
70
- "@synerise/ds-tooltip": "^1.5.3",
71
- "@synerise/ds-utils": "^1.10.1",
45
+ "@synerise/ds-alert": "^1.1.62",
46
+ "@synerise/ds-autocomplete": "^1.2.51",
47
+ "@synerise/ds-badge": "^1.0.58",
48
+ "@synerise/ds-button": "^1.5.35",
49
+ "@synerise/ds-button-group": "^1.1.60",
50
+ "@synerise/ds-collector": "^1.4.51",
51
+ "@synerise/ds-date-picker": "^1.4.22",
52
+ "@synerise/ds-date-range-picker": "^1.7.12",
53
+ "@synerise/ds-divider": "^1.3.16",
54
+ "@synerise/ds-dropdown": "^1.3.20",
55
+ "@synerise/ds-empty-states": "^1.0.49",
56
+ "@synerise/ds-icon": "^1.18.5",
57
+ "@synerise/ds-information-card": "^1.7.8",
58
+ "@synerise/ds-inline-edit": "^1.1.48",
59
+ "@synerise/ds-input": "^1.7.13",
60
+ "@synerise/ds-input-number": "^1.2.50",
61
+ "@synerise/ds-list-item": "^1.6.2",
62
+ "@synerise/ds-modal": "^1.6.6",
63
+ "@synerise/ds-result": "^1.0.66",
64
+ "@synerise/ds-scrollbar": "^1.5.2",
65
+ "@synerise/ds-search": "^1.5.34",
66
+ "@synerise/ds-select": "^1.3.34",
67
+ "@synerise/ds-short-cuts": "^1.0.56",
68
+ "@synerise/ds-skeleton": "^1.0.60",
69
+ "@synerise/ds-tabs": "^1.2.6",
70
+ "@synerise/ds-tag": "^1.4.32",
71
+ "@synerise/ds-tooltip": "^1.5.4",
72
+ "@synerise/ds-utils": "^1.10.2",
72
73
  "lodash.merge": "^4.6.2",
73
74
  "react-window": "^1.8.11",
74
75
  "uuid": "^8.3.2"
@@ -85,5 +86,5 @@
85
86
  "styled-components": "^5.3.3",
86
87
  "vitest": "4"
87
88
  },
88
- "gitHead": "5c90008871be36fb52553a2ed3a633acf5db5b3b"
89
+ "gitHead": "d0a43cc43d8528a36f105aceea52ab470edb71d9"
89
90
  }