ui-nyla/src/utils/attributeTypeMapper.ts
2025-12-22 07:31:56 +01:00

181 lines
4.1 KiB
TypeScript

/**
* Utility functions for mapping attribute types to HTML input types and component types
*/
export type AttributeType =
| 'text'
| 'textarea'
| 'select'
| 'multiselect'
| 'integer'
| 'float'
| 'number'
| 'timestamp'
| 'date'
| 'time'
| 'checkbox'
| 'boolean'
| 'email'
| 'url'
| 'password'
| 'file'
| 'string'
| 'enum'
| 'readonly';
export type InputComponentType =
| 'text'
| 'textarea'
| 'select'
| 'multiselect'
| 'checkbox'
| 'file'
| 'email'
| 'url'
| 'password'
| 'date'
| 'time'
| 'datetime-local'
| 'number';
/**
* Maps attribute type to HTML input type
*
* @param attributeType - The attribute type from the backend
* @returns The corresponding HTML input type
*
* Mapping rules:
* - text → text (single line)
* - textarea → textarea (multi-line)
* - select → select (dropdown with options)
* - multiselect → multiselect (multiple selection)
* - integer → number (integer only)
* - float or number → number (decimal allowed)
* - timestamp → datetime-local (date/time picker)
* - date → date (date picker, date only)
* - time → time (time picker, time only)
* - checkbox or boolean → checkbox (boolean)
* - email → email (with email validation)
* - url → url (with URL validation)
* - password → password (masked)
* - file → file (file upload)
*/
export function attributeTypeToInputType(attributeType: AttributeType): InputComponentType {
switch (attributeType) {
case 'text':
case 'string':
return 'text';
case 'textarea':
return 'textarea';
case 'select':
case 'enum':
return 'select';
case 'multiselect':
return 'multiselect';
case 'integer':
case 'number':
case 'float':
return 'number';
case 'timestamp':
return 'datetime-local';
case 'date':
return 'date';
case 'time':
return 'time';
case 'checkbox':
case 'boolean':
return 'checkbox';
case 'email':
return 'email';
case 'url':
return 'url';
case 'password':
return 'password';
case 'file':
return 'file';
case 'readonly':
return 'text'; // Default to text for readonly, but should be rendered as readonly
default:
// Default fallback to text input
return 'text';
}
}
/**
* Determines if an attribute type should render as a textarea
*/
export function isTextareaType(attributeType: AttributeType): boolean {
return attributeType === 'textarea';
}
/**
* Determines if an attribute type should render as a select dropdown
*/
export function isSelectType(attributeType: AttributeType): boolean {
return attributeType === 'select' || attributeType === 'enum';
}
/**
* Determines if an attribute type should render as a multiselect
*/
export function isMultiselectType(attributeType: AttributeType): boolean {
return attributeType === 'multiselect';
}
/**
* Determines if an attribute type should render as a checkbox
*/
export function isCheckboxType(attributeType: AttributeType): boolean {
return attributeType === 'checkbox' || attributeType === 'boolean';
}
/**
* Determines if an attribute type should render as a file input
*/
export function isFileType(attributeType: AttributeType): boolean {
return attributeType === 'file';
}
/**
* Determines if an attribute type should render as a number input
*/
export function isNumberType(attributeType: AttributeType): boolean {
return attributeType === 'integer' || attributeType === 'number' || attributeType === 'float';
}
/**
* Determines if an attribute type should render as a date/time input
*/
export function isDateTimeType(attributeType: AttributeType): boolean {
return attributeType === 'timestamp' || attributeType === 'date' || attributeType === 'time';
}
/**
* Gets the default value for an attribute type
*/
export function getDefaultValueForType(attributeType: AttributeType): any {
if (isCheckboxType(attributeType)) {
return false;
}
if (isMultiselectType(attributeType)) {
return [];
}
if (isNumberType(attributeType)) {
return 0;
}
return '';
}