fix(number-fields): избегаем потери точности длинных чисел
- number-поля теперь рендерятся как text + inputMode=numeric, чтобы браузер не округлял значения через input type=number - пробелы при вставке в number-поля удаляются - бэкенд нормализует значения number-полей в строку перед сохранением - добавлен хелпер normalizeFieldValueForStorage Closes: искажение расчётного счёта и других длинных числовых полей
This commit is contained in:
165
FIELD_TYPES.md
Normal file
165
FIELD_TYPES.md
Normal file
@@ -0,0 +1,165 @@
|
||||
# Реестр типов полей iistwin
|
||||
|
||||
> Единый источник правды: `shared/field-types.ts`
|
||||
> Дата актуализации: 2026-05-18
|
||||
|
||||
---
|
||||
|
||||
## Сводная таблица всех типов
|
||||
|
||||
| # | ID | Название | Иконка (Lucide) | Опции | Формы | Глобальные | Таблицы |
|
||||
|---|-----|----------|-----------------|-------|:-----:|:----------:|:-------:|
|
||||
| 1 | `text` | Текстовое поле | `Type` | ❌ | ✅ | ✅ | ✅ |
|
||||
| 2 | `number` | Числовое поле | `Hash` | ❌ | ✅ | ✅ | ✅ |
|
||||
| 3 | `date` | Дата | `Calendar` | ❌ | ✅ | ✅ | ✅ |
|
||||
| 4 | `datetime` | Дата и время | `Clock` | ❌ | ✅ | ✅ | ✅ |
|
||||
| 5 | `select` | Выпадающий список | `ChevronDown` | ✅ | ✅ | ✅ | ✅ |
|
||||
| 6 | `checkbox` | Чекбокс | `CheckSquare` | ❌ | ✅ | ✅ | ✅ |
|
||||
| 7 | `toggle` | Переключатель | `ToggleLeft` | ❌ | ✅ | ✅ | ✅ |
|
||||
| 8 | `button` | Кнопка | `MousePointer` | ❌ | ✅ | ❌ | ❌ |
|
||||
| 9 | `user` | Выбор пользователя | `Users` | ❌ | ✅ | ✅ | ✅ |
|
||||
| 10 | `file` | Загрузка файлов | `Paperclip` | ❌ | ✅ | ✅ | ✅ |
|
||||
| 11 | `textarea` | Многострочный текст | `AlignLeft` | ❌ | ✅ | ✅ | ✅ |
|
||||
| 12 | `rich-text` | Богатый текстовый редактор | `FileText` | ❌ | ✅ | ✅ | ✅ |
|
||||
| 13 | `history-number` | Числовое поле с историей | `History` | ❌ | ❌ | ❌ | ✅ |
|
||||
| 14 | `table` | Выбор из таблицы | `Table` | ❌ | ❌ | ❌ | ✅ |
|
||||
| 15 | `task` | Связь с задачей | `Link2` | ❌ | ✅ | ❌ | ✅ |
|
||||
| 16 | `company` | Организация (DaData) | `Building2` | ❌ | ✅ | ✅ | ✅ |
|
||||
| 17 | `geo` | Адрес с координатами | `MapPin` | ❌ | ✅ | ✅ | ✅ |
|
||||
| 18 | `formula` | Формула | `Calculator` | ❌ | ❌ | ❌ | ✅ |
|
||||
|
||||
**Легенда:**
|
||||
- **Опции** — поддерживает ли тип предустановленный список значений (только `select`)
|
||||
- **Формы** — можно создать поле этого типа в редакторе форм
|
||||
- **Глобальные** — можно создать reusable шаблон глобального поля
|
||||
- **Таблицы** — можно использовать как тип колонки в справочнике/таблице
|
||||
|
||||
---
|
||||
|
||||
## Использование по контекстам
|
||||
|
||||
### 1. Формы (`FORM_FIELD_TYPES`) — 17 типов
|
||||
|
||||
Файлы:
|
||||
- `client/src/pages/FormEditor.tsx` — редактор форм
|
||||
- `client/src/pages/TaskDetail.tsx` — карточка задачи
|
||||
- `server/mcp.ts` → tool `add_form_field`
|
||||
|
||||
| Тип | Особенности |
|
||||
|-----|-------------|
|
||||
| `button` | Только в формах. Действия: `open_url`, `create_task` |
|
||||
| `task` | Связь задача→задача (parent/child). `taskRelationType` |
|
||||
| `company` | Интеграция DaData (автозаполнение ИНН, названия) |
|
||||
| `geo` | Адрес с координатами, интеграция карт |
|
||||
| `file` | Загрузка в MinIO S3. `maxFileCount`, `maxFileSizeMB` |
|
||||
| `select` | Единственный тип с `supportsOptions: true` |
|
||||
|
||||
---
|
||||
|
||||
### 2. Глобальные поля (`GLOBAL_FIELD_TYPES`) — 16 типов
|
||||
|
||||
Файлы:
|
||||
- `client/src/pages/GlobalFields.tsx` — UI управления
|
||||
- `server/mcp.ts` → tool `create_global_field`
|
||||
|
||||
**Исключены:** `button`, `history-number`, `formula`
|
||||
|
||||
Глобальные поля — это reusable шаблоны. Создаются один раз, затем вставляются в любую форму через `add_global_field_to_form` или `add_globals_to_table_tab`.
|
||||
|
||||
---
|
||||
|
||||
### 3. Таблицы / Справочники (`TABLE_FIELD_TYPES`) — 16 типов
|
||||
|
||||
Файлы:
|
||||
- `client/src/pages/Tables.tsx` — страница справочников
|
||||
- `client/src/components/tabs/types.ts` — типизация колонок
|
||||
- `server/mcp.ts` → tool `add_globals_to_table_tab`
|
||||
|
||||
**Исключён:** `button`
|
||||
|
||||
| Тип | Особенности |
|
||||
|-----|-------------|
|
||||
| `history-number` | Хранит историю изменений значения (audit trail) |
|
||||
| `formula` | Вычисляемое поле. Движок: `client/src/lib/formulaEngine.ts` |
|
||||
| `table` | Ссылка на другой справочник (foreign key) |
|
||||
|
||||
---
|
||||
|
||||
### 4. Пользовательские поля (User Custom Fields) — 6 типов ⚠️
|
||||
|
||||
Файлы:
|
||||
- `shared/schema.ts:698`
|
||||
- `client/src/pages/Users.tsx`
|
||||
|
||||
```ts
|
||||
z.enum(["text", "number", "date", "select", "user", "checkbox"])
|
||||
```
|
||||
|
||||
**Проблема:** не синхронизирован с `shared/field-types.ts`. Нет: `datetime`, `toggle`, `file`, `textarea`, `rich-text`, `company`, `geo`.
|
||||
|
||||
---
|
||||
|
||||
### 5. API эндпоинт
|
||||
|
||||
```
|
||||
GET /api/field-types
|
||||
```
|
||||
|
||||
Возвращает полный реестр с метаданными:
|
||||
```json
|
||||
{
|
||||
"success": true,
|
||||
"fieldTypes": [
|
||||
{ "id": "text", "label": "Текстовое поле", "iconName": "Type", "supportsOptions": false, "allowedIn": ["form","global","table"] },
|
||||
...
|
||||
]
|
||||
}
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
### 6. MCP Tools
|
||||
|
||||
| Tool | Допустимые типы |
|
||||
|------|-----------------|
|
||||
| `add_form_field` | `FORM_FIELD_TYPES` (17 типов) |
|
||||
| `create_global_field` | `GLOBAL_FIELD_TYPES` (16 типов) |
|
||||
| `add_globals_to_table_tab` | фильтрует по `TABLE_FIELD_TYPES` |
|
||||
|
||||
---
|
||||
|
||||
## Техдолг и планы
|
||||
|
||||
| Место | Проблема | Приоритет |
|
||||
|-------|----------|-----------|
|
||||
| `User Custom Fields` | 6 hardcoded типов, не использует `shared/field-types.ts` | 🔴 Высокий |
|
||||
| `client/src/lib/fieldTypes.ts` | Дублирует реестр (React-иконки Lucide). Можно сделать динамический импорт | 🟡 Средний |
|
||||
| `shared/schema.ts:1474` | Hardcoded union `'text' \| 'number' \| ...` | 🟡 Средний |
|
||||
|
||||
---
|
||||
|
||||
## Как добавить новый тип поля
|
||||
|
||||
### Шаг 1. Реестр
|
||||
Добавить в `shared/field-types.ts`:
|
||||
```ts
|
||||
{ id: "rating", label: "Рейтинг", iconName: "Star", supportsOptions: false, allowedIn: ["form", "global", "table"] }
|
||||
```
|
||||
|
||||
### Шаг 2. Иконка (если нужна на фронте)
|
||||
Добавить в `client/src/lib/fieldTypes.ts`:
|
||||
```ts
|
||||
import { Star } from 'lucide-react';
|
||||
// ...
|
||||
{ value: 'rating', label: 'Рейтинг', icon: Star },
|
||||
```
|
||||
|
||||
### Шаг 3. Рендерер (если нужна кастомная логика)
|
||||
- `FormEditor.tsx` — UI в редакторе форм
|
||||
- `TaskDetail.tsx` — отображение в карточке задачи
|
||||
|
||||
### Шаг 4. Бэкенд (если нужна кастомная валидация)
|
||||
- `server/services/form.service.ts` — валидация значений
|
||||
- `server/services/task.service.ts` — обработка при создании/обновлении
|
||||
|
||||
> Всё остальное (MCP, `/api/field-types`, `GlobalFields.tsx`, `Tables.tsx`, `Users.tsx`) синхронизируется **автоматически**.
|
||||
Reference in New Issue
Block a user