mirror of
https://github.com/shishantbiswas/bknd.git
synced 2026-03-17 04:46:05 +00:00
using path instead of pointer, replaced lodash usage
This commit is contained in:
@@ -1,82 +1,10 @@
|
||||
import { autoFormatString } from "core/utils";
|
||||
import { Draft2019, type JsonSchema } from "json-schema-library";
|
||||
import { autoFormatString, omitKeys } from "core/utils";
|
||||
import { type Draft, Draft2019, type JsonSchema } from "json-schema-library";
|
||||
import type { JSONSchema } from "json-schema-to-ts";
|
||||
import type { JSONSchemaType } from "json-schema-to-ts/lib/types/definitions/jsonSchema";
|
||||
import { omit, set } from "lodash-es";
|
||||
import type { FormEvent } from "react";
|
||||
|
||||
export function getFormTarget(e: FormEvent<HTMLFormElement>) {
|
||||
const form = e.currentTarget;
|
||||
const target = e.target as HTMLInputElement | HTMLSelectElement | HTMLTextAreaElement | null;
|
||||
|
||||
// check if target has attribute "data-ignore" set
|
||||
// also check if target is within a "data-ignore" element
|
||||
|
||||
if (
|
||||
!target ||
|
||||
!form.contains(target) ||
|
||||
!target.name ||
|
||||
target.hasAttribute("data-ignore") ||
|
||||
target.closest("[data-ignore]")
|
||||
) {
|
||||
return; // Ignore events from outside the form
|
||||
}
|
||||
return target;
|
||||
}
|
||||
|
||||
export function flatten(obj: any, parentKey = "", result: any = {}): any {
|
||||
for (const key in obj) {
|
||||
if (key in obj) {
|
||||
const newKey = parentKey ? `${parentKey}/${key}` : "#/" + key;
|
||||
if (typeof obj[key] === "object" && obj[key] !== null && !Array.isArray(obj[key])) {
|
||||
flatten(obj[key], newKey, result);
|
||||
} else if (Array.isArray(obj[key])) {
|
||||
obj[key].forEach((item, index) => {
|
||||
const arrayKey = `${newKey}.${index}`;
|
||||
if (typeof item === "object" && item !== null) {
|
||||
flatten(item, arrayKey, result);
|
||||
} else {
|
||||
result[arrayKey] = item;
|
||||
}
|
||||
});
|
||||
} else {
|
||||
result[newKey] = obj[key];
|
||||
}
|
||||
}
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
// @todo: make sure it's in the right order
|
||||
export function unflatten(
|
||||
obj: Record<string, string>,
|
||||
schema: JsonSchema,
|
||||
selections?: Record<string, number | undefined>
|
||||
) {
|
||||
const result = {};
|
||||
const lib = new Draft2019(schema as any);
|
||||
for (const pointer in obj) {
|
||||
const required = isRequired(pointer, schema);
|
||||
let subschema = lib.getSchema({ pointer });
|
||||
//console.log("subschema", pointer, subschema, selections);
|
||||
if (!subschema) {
|
||||
throw new Error(`"${pointer}" not found in schema`);
|
||||
}
|
||||
|
||||
// if subschema starts with "anyOf" or "oneOf"
|
||||
if (subschema.anyOf || subschema.oneOf) {
|
||||
const selected = selections?.[pointer];
|
||||
if (selected !== undefined) {
|
||||
subschema = subschema.anyOf ? subschema.anyOf[selected] : subschema.oneOf![selected];
|
||||
}
|
||||
}
|
||||
|
||||
const value = coerce(obj[pointer], subschema as any, { required });
|
||||
|
||||
set(result, pointer.substring(2).replace(/\//g, "."), value);
|
||||
}
|
||||
return result;
|
||||
}
|
||||
export { isEqual, getPath } from "core/utils/objects";
|
||||
//export { isEqual } from "lodash-es";
|
||||
|
||||
export function coerce(value: any, schema: JsonSchema, opts?: { required?: boolean }) {
|
||||
if (!value && typeof opts?.required === "boolean" && !opts.required) {
|
||||
@@ -98,25 +26,6 @@ export function coerce(value: any, schema: JsonSchema, opts?: { required?: boole
|
||||
return value;
|
||||
}
|
||||
|
||||
/**
|
||||
* normalizes any path to a full json pointer
|
||||
*
|
||||
* examples: in -> out
|
||||
* description -> #/description
|
||||
* #/description -> #/description
|
||||
* /description -> #/description
|
||||
* nested/property -> #/nested/property
|
||||
* nested.property -> #/nested/property
|
||||
* nested.property[0] -> #/nested/property/0
|
||||
* nested.property[0].name -> #/nested/property/0/name
|
||||
* @param path
|
||||
*/
|
||||
export function normalizePath(path: string) {
|
||||
return path.startsWith("#/")
|
||||
? path
|
||||
: `#/${path.replace(/#?\/?/, "").replace(/\./g, "/").replace(/\[/g, "/").replace(/\]/g, "")}`;
|
||||
}
|
||||
|
||||
export function pathToPointer(path: string) {
|
||||
return "#/" + (path.includes(".") ? path.split(".").join("/") : path);
|
||||
}
|
||||
@@ -125,22 +34,28 @@ export function prefixPointer(pointer: string, prefix: string) {
|
||||
return pointer.replace("#/", `#/${prefix.length > 0 ? prefix + "/" : ""}`).replace(/\/\//g, "/");
|
||||
}
|
||||
|
||||
export function prefixPath(path: string = "", prefix: string = "") {
|
||||
const PathFilter = (value: any) => typeof value !== "undefined" && value !== null && value !== "";
|
||||
|
||||
export function prefixPath(path: string = "", prefix: string | number = "") {
|
||||
const p = path.includes(".") ? path.split(".") : [path];
|
||||
return [prefix, ...p].filter(Boolean).join(".");
|
||||
return [prefix, ...p].filter(PathFilter).join(".");
|
||||
}
|
||||
|
||||
export function suffixPath(path: string = "", suffix: string | number = "") {
|
||||
const p = path.includes(".") ? path.split(".") : [path];
|
||||
return [...p, suffix].filter(PathFilter).join(".");
|
||||
}
|
||||
|
||||
export function getParentPointer(pointer: string) {
|
||||
return pointer.substring(0, pointer.lastIndexOf("/"));
|
||||
}
|
||||
|
||||
export function isRequired(pointer: string, schema: JsonSchema, data?: any) {
|
||||
export function isRequired(lib: Draft, pointer: string, schema: JsonSchema, data?: any) {
|
||||
if (pointer === "#/" || !schema) {
|
||||
return false;
|
||||
}
|
||||
const lib = new Draft2019(schema as any);
|
||||
|
||||
const childSchema = lib.getSchema({ pointer, data });
|
||||
const childSchema = lib.getSchema({ pointer, data, schema });
|
||||
if (typeof childSchema === "object" && "const" in childSchema) {
|
||||
return true;
|
||||
}
|
||||
@@ -152,12 +67,17 @@ export function isRequired(pointer: string, schema: JsonSchema, data?: any) {
|
||||
return !!required;
|
||||
}
|
||||
|
||||
type TType = JSONSchemaType | JSONSchemaType[] | readonly JSONSchemaType[] | string | undefined;
|
||||
export function isType(_type: TType, _compare: TType) {
|
||||
if (!_type || !_compare) return false;
|
||||
const type = Array.isArray(_type) ? _type : [_type];
|
||||
const compare = Array.isArray(_compare) ? _compare : [_compare];
|
||||
return compare.some((t) => type.includes(t));
|
||||
export type IsTypeType =
|
||||
| JSONSchemaType
|
||||
| JSONSchemaType[]
|
||||
| readonly JSONSchemaType[]
|
||||
| string
|
||||
| undefined;
|
||||
export function isType(type: IsTypeType, compare: IsTypeType) {
|
||||
if (!type || !compare) return false;
|
||||
const _type = Array.isArray(type) ? type : [type];
|
||||
const _compare = Array.isArray(compare) ? compare : [compare];
|
||||
return _compare.some((t) => _type.includes(t));
|
||||
}
|
||||
|
||||
export function getLabel(name: string, schema: JsonSchema) {
|
||||
@@ -188,19 +108,6 @@ export function getMultiSchemaMatched(
|
||||
return [index, multiSchema, multiSchema[index]];
|
||||
}
|
||||
|
||||
export function removeKeyRecursively<Given extends object>(obj: Given, keyToRemove: string): Given {
|
||||
if (Array.isArray(obj)) {
|
||||
return obj.map((item) => removeKeyRecursively(item, keyToRemove)) as any;
|
||||
} else if (typeof obj === "object" && obj !== null) {
|
||||
return Object.fromEntries(
|
||||
Object.entries(obj)
|
||||
.filter(([key]) => key !== keyToRemove)
|
||||
.map(([key, value]) => [key, removeKeyRecursively(value, keyToRemove)])
|
||||
) as any;
|
||||
}
|
||||
return obj;
|
||||
}
|
||||
|
||||
export function omitSchema<Given extends JSONSchema>(_schema: Given, keys: string[], _data?: any) {
|
||||
if (typeof _schema !== "object" || !("properties" in _schema) || keys.length === 0)
|
||||
return [_schema, _data];
|
||||
@@ -209,13 +116,13 @@ export function omitSchema<Given extends JSONSchema>(_schema: Given, keys: strin
|
||||
|
||||
const updated = {
|
||||
...schema,
|
||||
properties: omit(schema.properties, keys)
|
||||
properties: omitKeys(schema.properties, keys)
|
||||
};
|
||||
if (updated.required) {
|
||||
updated.required = updated.required.filter((key) => !keys.includes(key as any));
|
||||
}
|
||||
|
||||
const reducedConfig = omit(data, keys) as any;
|
||||
const reducedConfig = omitKeys(data, keys) as any;
|
||||
|
||||
return [updated, reducedConfig];
|
||||
}
|
||||
@@ -223,10 +130,3 @@ export function omitSchema<Given extends JSONSchema>(_schema: Given, keys: strin
|
||||
export function isTypeSchema(schema?: JsonSchema): schema is JsonSchema {
|
||||
return typeof schema === "object" && "type" in schema && !isType(schema.type, "error");
|
||||
}
|
||||
|
||||
export function enumToOptions(_enum: any) {
|
||||
if (!Array.isArray(_enum)) return [];
|
||||
return _enum.map((v, i) =>
|
||||
typeof v === "string" ? { value: v, label: v } : { value: i, label: v }
|
||||
);
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user