diff --git a/ving/docs/change-log.md b/ving/docs/change-log.md index 7be7919a..ebff1904 100644 --- a/ving/docs/change-log.md +++ b/ving/docs/change-log.md @@ -31,6 +31,9 @@ Also don't forget to update the imports in your schema files. * Set filterQualifier to true for the baseSchemaId. * Added better error handling for int2str parseId(). * Added stringToNumber option to int2str parseId(). +* Added allowRealPubicId to ving schema props. +* Fixed: filter on id #203 +* Fixed: How to do a search for hardware ticket by ticket number? #29 ## December 2024 diff --git a/ving/docs/subsystems/ui.md b/ving/docs/subsystems/ui.md index 491edc27..65f9149d 100644 --- a/ving/docs/subsystems/ui.md +++ b/ving/docs/subsystems/ui.md @@ -467,6 +467,16 @@ await users.search(); onBeforeRouteLeave(() => users.dispose()); ``` +#### Filtering + +You can filter the list of records by passing in values to the query object. For example, to filter by an exact value: + +```js +users.query.id = 'xxx'; +``` +For more on filtering see the [rest api](rest#filters) documentation. + + ### useVingRecord() A client for interacting with [server-side ving records](ving-record#record-api) through the [Rest API](rest). diff --git a/ving/docs/subsystems/ving-schema.md b/ving/docs/subsystems/ving-schema.md index 63e0c4be..df5afaff 100644 --- a/ving/docs/subsystems/ving-schema.md +++ b/ving/docs/subsystems/ving-schema.md @@ -385,6 +385,13 @@ An optional boolean that if true will allow searching via the [rest api](rest) f An optional boolean that if true will allow searching via the [rest api](rest) for range matching against this field. This is an alternative to overriding the `describeListFilter()` method in [VingRecord](ving-record). Only use on `int` and `date` type props. +##### allowRealPubicId + +An optional boolean that if true will do 2 things if added to an `id` prop `type`: + +* Allows searching via the [rest api](rest) for exact match filtering against this id using its integer value in addiont to the encrypted string assuming `filterQualifier` is true. +* Adds the real id to the `meta.realId` object in the [rest api](rest) response. + ##### autoUpdate The `autoUpdate` field is an optional boolean that is only used on a prop with type `date`. If `true` the date will automatically get set every time `update()` is called on the record. This is generally never needed by anything other than the built in `dateUpdated` record that every record already has. diff --git a/ving/record/VingRecord.mjs b/ving/record/VingRecord.mjs index ec801900..34d0ed12 100644 --- a/ving/record/VingRecord.mjs +++ b/ving/record/VingRecord.mjs @@ -203,6 +203,17 @@ export class VingRecord { } for (const field of schema.props) { + + // meta + if (isObject(out.meta) + && include.meta + ) { + if (field.allowRealPubicId) { + if (!isObject(out.meta.realId)) out.meta.realId = {}; + out.meta.realId[field.name] = this.#props[field.name]; + } + } + if (field.name == 'id') // already done continue; @@ -214,8 +225,6 @@ export class VingRecord { || (currentUser?.isaRole(roles)); if (!visible) continue; - const fieldName = field.name.toString(); - // props if (field.type == 'id') out.props[field.name] = stringifyId(this.#props[field.name], field.relation?.kind || schema.kind); diff --git a/ving/schema/validator.mjs b/ving/schema/validator.mjs index 55859a55..21c8de9f 100644 --- a/ving/schema/validator.mjs +++ b/ving/schema/validator.mjs @@ -72,6 +72,7 @@ export const validateProps = (schema) => { validatePropFilterQuery(prop, schema); validatePropFilterQualifier(prop, schema); validatePropAutoUpdate(prop, schema); + validatePropAllowRealPubicId(prop, schema); } } @@ -508,7 +509,7 @@ export const validatePropFilterQualifier = (prop, schema) => { return; if (!isBoolean(prop.filterQualifier)) throw ving.ouch(442, `${formatPropPath(prop, schema)}.filterQualifier must be a boolean.`); - if (prop.type == 'id' && prop.relation?.type != 'parent') + if (prop.type == 'id' && prop.relation && prop.relation?.type != 'parent') throw ving.ouch(442, `${formatPropPath(prop, schema)}.filterQualifier can only exist on type id if the relation.type is parent.`); } @@ -532,6 +533,26 @@ export const validatePropFilterRange = (prop, schema) => { throw ving.ouch(442, `${formatPropPath(prop, schema)}.filterRange must be a boolean.`); } +/** + * Validates the allowRealPubicId field of a prop. + * @param {object} prop The prop schema to check against. + * @param {VingSchema} schema The schema to check against. + * @throws 442 if some attribute is outside of the normal definition + * @example + * validatePropAllowRealPubicId(prop, schema) + */ +export const validatePropAllowRealPubicId = (prop, schema) => { + if (!['id'].includes(prop.type)) { + if ('allowRealPubicId' in prop) + throw ving.ouch(442, `${formatPropPath(prop, schema)}.allowRealPubicId should not exist.`); + return; + } + if (!('allowRealPubicId' in prop)) // not required + return; + if (!isBoolean(prop.allowRealPubicId)) + throw ving.ouch(442, `${formatPropPath(prop, schema)}.allowRealPubicId must be a boolean.`); +} + /** * Validates the required field of a prop. * @param {object} prop The prop schema to check against. diff --git a/ving/utils/rest.mjs b/ving/utils/rest.mjs index 321c9bdb..47c7dc94 100644 --- a/ving/utils/rest.mjs +++ b/ving/utils/rest.mjs @@ -25,7 +25,7 @@ const fixColumnData = (column, data) => { return data == 'true' ? true : false; } if (column.vingSchemaProp.type == 'id') { - return parseId(data); + return parseId(data, { stringToNumber: column.vingSchemaProp.allowRealPubicId ? true : false }); } if (column.vingSchemaProp.type == 'int') { return Number(data);