UNPKG

@enonic/js-utils

Version:
256 lines (240 loc) 7.75 kB
import { VALUE_TYPE_ANY, VALUE_TYPE_BOOLEAN, VALUE_TYPE_DOUBLE, VALUE_TYPE_GEO_POINT, VALUE_TYPE_INSTANT, VALUE_TYPE_LOCAL_DATE, VALUE_TYPE_LOCAL_DATE_TIME, VALUE_TYPE_LOCAL_TIME, //VALUE_TYPE_LONG, VALUE_TYPE_REFERENCE, VALUE_TYPE_SET, VALUE_TYPE_STRING, VALUE_TYPES } from './constants'; import { isBoolean, isDate, //isFloat, // Not possible for any number where the decimals are 0 isGeoPointArray, isGeoPointString, isInstantString, //isInteger, isLocalDateString, isLocalDateTimeString, isNumber, isObject, isString, isTimeString, isUuidV4String } from '../../../value' type ValueType = typeof VALUE_TYPES[number]; /* Any <- Set <- String <- GeoPointString <- InstantString <- Date <- LocalDateString <- LocalDateTimeString <- TimeString <- UuidV4String <- Boolean <- Double <- GeoPointArray */ export function detectCommonValueType(array :Array<unknown>) :ValueType { //console.debug('array', array); let anyStringCount = 0; //let booleanCount = 0; //let dateCount = 0; let geoPointArrayCount = 0; //let geoPointStringCount = 0; //let instantStringCount = 0; //let localDateStringCount = 0; //let localDateTimeStringCount = 0; //let numberCount = 0; let objectCount = 0; //let stringCount = 0; //let timeStringCount = 0; //let uuidV4StringCount = 0; let commonValueType :ValueType|undefined; for (let i = 0; i < array.length; i++) { const value = array[i]; //console.debug('value', value); if (isGeoPointArray(value)) { //console.debug('isGeoPointArray === true value', value); if (!commonValueType) { commonValueType = VALUE_TYPE_GEO_POINT; //} else if (commonValueType === VALUE_TYPE_SET) { } else if (objectCount) { return VALUE_TYPE_ANY; } else if (commonValueType === VALUE_TYPE_DOUBLE || commonValueType === VALUE_TYPE_GEO_POINT) { // Leave it as is } else if (anyStringCount) { commonValueType = VALUE_TYPE_STRING; } geoPointArrayCount++; } else if (Array.isArray(value)) { //console.debug('isArray === true value', value); throw new Error("TODO: Enonic XP doesn't support Matrixes!"); /*if (!value.length) { return VALUE_TYPE_ANY; }*/ //commonValueType = detectCommonValueType(value); // Recurse } else if (isBoolean(value)) { //console.debug('isBoolean === true value', value); if (!commonValueType || commonValueType === VALUE_TYPE_BOOLEAN) { commonValueType = VALUE_TYPE_BOOLEAN } else if (objectCount) { return VALUE_TYPE_ANY; } else if (anyStringCount) { commonValueType = VALUE_TYPE_STRING; } //booleanCount++; } else if (isDate(value)) { //console.debug('isDate === true value', value); if (!commonValueType || commonValueType === VALUE_TYPE_INSTANT) { commonValueType = VALUE_TYPE_INSTANT } else if (objectCount) { return VALUE_TYPE_ANY; } else if (anyStringCount) { commonValueType = VALUE_TYPE_STRING; } //dateCount++; } else if(isNumber(value)) { //console.debug('isNumber === true value', value); if (!commonValueType) { commonValueType = VALUE_TYPE_DOUBLE } else if (objectCount) { return VALUE_TYPE_ANY; } else if (commonValueType === VALUE_TYPE_DOUBLE) { // Leave as is } else if (anyStringCount) { commonValueType = VALUE_TYPE_STRING; } else if (geoPointArrayCount) { commonValueType = VALUE_TYPE_DOUBLE } //numberCount++; } else if(isObject(value)) { //console.debug('isObject === true value', value); if (!commonValueType || commonValueType === VALUE_TYPE_SET) { commonValueType = VALUE_TYPE_SET } else /*if (commonValueType !== VALUE_TYPE_SET)*/ { // No-overlap return VALUE_TYPE_ANY; } objectCount++; } else if(isString(value)) { //console.debug('isString === true value', value); if (isGeoPointString(value)) { //console.debug('isGeoPointString === true value', value); if (!commonValueType || commonValueType === VALUE_TYPE_GEO_POINT) { commonValueType = VALUE_TYPE_GEO_POINT; } else if (anyStringCount) { commonValueType = VALUE_TYPE_STRING; } //geoPointStringCount++; } else if (isInstantString(value)) { //console.debug('isInstantString === true value', value); if (!commonValueType || commonValueType === VALUE_TYPE_INSTANT) { commonValueType = VALUE_TYPE_INSTANT; } else if (anyStringCount) { commonValueType = VALUE_TYPE_STRING; } //instantStringCount++; } else if (isLocalDateString(value)) { //console.debug('isLocalDateString === true value', value); if (!commonValueType || commonValueType === VALUE_TYPE_LOCAL_DATE) { commonValueType = VALUE_TYPE_LOCAL_DATE; } else if (anyStringCount) { commonValueType = VALUE_TYPE_STRING; } //localDateStringCount++; } else if (isLocalDateTimeString(value)) { //console.debug('isLocalDateTimeString === true value', value); if (!commonValueType || commonValueType === VALUE_TYPE_LOCAL_DATE_TIME) { commonValueType = VALUE_TYPE_LOCAL_DATE_TIME; } else if (anyStringCount) { commonValueType = VALUE_TYPE_STRING; } //localDateTimeStringCount++; } else if (isTimeString(value)) { //console.debug('isTimeString === true value', value); if (!commonValueType || commonValueType === VALUE_TYPE_LOCAL_TIME) { commonValueType = VALUE_TYPE_LOCAL_TIME; } else if (anyStringCount) { commonValueType = VALUE_TYPE_STRING; } //timeStringCount++; } else if (isUuidV4String(value)) { //console.debug('isUuidV4String === true value', value); if (!commonValueType || commonValueType === VALUE_TYPE_REFERENCE) { commonValueType = VALUE_TYPE_REFERENCE; } else if (anyStringCount) { commonValueType = VALUE_TYPE_STRING; } //uuidV4StringCount++; } else { //console.debug('isString === true value', value); commonValueType = VALUE_TYPE_STRING; //stringCount++; } anyStringCount++; } else { return VALUE_TYPE_ANY; } //console.debug('commonValueType', commonValueType, 'value', value); } // for /*console.debug({ anyStringCount, booleanCount, commonValueType, dateCount, geoPointArrayCount, geoPointStringCount, instantStringCount, localDateStringCount, localDateTimeStringCount, numberCount, objectCount, stringCount, timeStringCount, uuidV4StringCount });*/ return commonValueType as ValueType; } export function detectValueType( value :unknown //) :Omit<ValueType, 'any'> { ) :ValueType { if (isGeoPointArray(value)) { return VALUE_TYPE_GEO_POINT; } if (Array.isArray(value)) { if (!value.length) { return VALUE_TYPE_ANY; } return detectCommonValueType(value); } if (isBoolean(value)) { return VALUE_TYPE_BOOLEAN; } // By default Enonic XP stores a Date object as an instant. // Can also be casted to: // VALUE_TYPE_LOCAL_DATE_TIME, VALUE_TYPE_LOCAL_DATE or VALUE_TYPE_LOCAL_TIME if (isDate(value)) { return VALUE_TYPE_INSTANT; } /*if(isInteger(value)) { //return VALUE_TYPE_LONG; // Any double where the decimals are 0 becomes an integer return VALUE_TYPE_DOUBLE; // So this is safer }*/ if(isNumber(value)) { return VALUE_TYPE_DOUBLE; } // This covers integers too. if(isObject(value)) { return VALUE_TYPE_SET; } if(isString(value)) { if (isGeoPointString(value)) { return VALUE_TYPE_GEO_POINT; } if (isInstantString(value)) { return VALUE_TYPE_INSTANT; } if (isLocalDateString(value)) { return VALUE_TYPE_LOCAL_DATE; } if (isLocalDateTimeString(value)) { return VALUE_TYPE_LOCAL_DATE_TIME; } if (isTimeString(value)) { return VALUE_TYPE_LOCAL_TIME; } if (isUuidV4String(value)) { return VALUE_TYPE_REFERENCE; } return VALUE_TYPE_STRING; } // !string return VALUE_TYPE_ANY; }