@elliemae/ds-typescript-helpers 3.30.0-next.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1,28 @@
1
+ "use strict";
2
+ var __create = Object.create;
3
+ var __defProp = Object.defineProperty;
4
+ var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
5
+ var __getOwnPropNames = Object.getOwnPropertyNames;
6
+ var __getProtoOf = Object.getPrototypeOf;
7
+ var __hasOwnProp = Object.prototype.hasOwnProperty;
8
+ var __copyProps = (to, from, except, desc) => {
9
+ if (from && typeof from === "object" || typeof from === "function") {
10
+ for (let key of __getOwnPropNames(from))
11
+ if (!__hasOwnProp.call(to, key) && key !== except)
12
+ __defProp(to, key, { get: () => from[key], enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable });
13
+ }
14
+ return to;
15
+ };
16
+ var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__getProtoOf(mod)) : {}, __copyProps(
17
+ // If the importer is in node compatibility mode or this is not an ESM
18
+ // file that has been converted to a CommonJS file using a Babel-
19
+ // compatible transform (i.e. "__esModule" has not been set), then set
20
+ // "default" to the CommonJS "module.exports" for node compatibility.
21
+ isNodeMode || !mod || !mod.__esModule ? __defProp(target, "default", { value: mod, enumerable: true }) : target,
22
+ mod
23
+ ));
24
+ var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: true }), mod);
25
+ var src_exports = {};
26
+ module.exports = __toCommonJS(src_exports);
27
+ var React = __toESM(require("react"));
28
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1,7 @@
1
+ {
2
+ "version": 3,
3
+ "sources": ["../../src/index.ts", "../../../../../scripts/build/transpile/react-shim.js"],
4
+ "sourcesContent": ["export namespace TypescriptHelpersT {\n /*****************************************************************************\n * A11y Helpers\n **************************************************************************** */\n /**\n * WCAG recommends to not use tabindex values greater than 0 to ensure that the tab order is predictable.\n * @example\n * const tabIndex: WCAGTabIndex = 0; // valid\n * const tabIndex: WCAGTabIndex = -1; // valid\n *\n * const tabIndex: WCAGTabIndex = 1; // invalid\n * const tabIndex: WCAGTabIndex = \"1\"; // invalid\n * const tabIndex: WCAGTabIndex = \"0\"; // invalid\n * const tabIndex: WCAGTabIndex = \"-1\"; // invalid\n */\n export type WCAGTabIndex = 0 | -1;\n\n /*****************************************************************************\n * Function Helpers\n **************************************************************************** */\n /**\n * Helper for declaring generic functions easly. This is usually painful because of the argument spreading\n * @example\n * const myFunction: GenericFunc<number,void> = (a) => { console.log(a) }; // a is a number\n * const myFunction2: GenericFunc<[number, number], string> = (a,b) => `${a + b}`; // a and b are numbers, the return type is a string\n */\n export type GenericFunc<T = unknown, R = unknown> = (...args: T extends Array<unknown> ? T : T[]) => R;\n /**\n * Helper for declaring a void function easly. This is usually painful because of the argument spreading.\n * @example\n * const myFunction: VoidGenericFunc<number> = (a) => { console.log(a) }; // a is a number\n * const myFunction2: VoidGenericFunc<[number, string]> = (a,b) => { console.log(a,b) }; // a is a number, b is a string\n */\n export type VoidGenericFunc<T = unknown> = GenericFunc<T, void>;\n /**\n * Helper for declaring a function that returns a boolean easly. This is usually painful because of the argument spreading\n * @example\n * const myFunction: BooleanGetter<number> = (a) => a > 0 // a is a number\n * const myFunction2: BooleanGetter<[number, string]> = (a,b) => a > 0 && b.length > 0 // a is a number, b is a string\n */\n export type BooleanGetter<T = unknown> = GenericFunc<T, boolean>;\n\n /*****************************************************************************\n * Debugging Helpers\n **************************************************************************** */\n /**\n * debugging helper to show the expanded typescript contract,\n * it's only useful to debug, it's NOT MEANT to be used for actual declarations\n * using this for actual declarations will cause the types to be slow to compile/resolve and would have no benefit.\n * https://stackoverflow.com/questions/57683303/how-can-i-see-the-full-expanded-contract-of-a-typescript-type\n * @example\n * type Decorated = {\n * a?: string | null\n * b?: T2\n * c?: T1\n * d: string\n * e: number\n * }\n * type Injected = {\n * inj: object\n * }\n * // overriding the types from Decorated\n * type Text = Decorated &\n * Injected & {\n * name: string;\n * type: \"text\";\n * value: string;\n * subobject: Injected;\n * };\n *\n * type Expanded = DebugExpandT<Text>;\n */\n export type DebugExpandT<T> = T extends (...args: infer A) => infer R\n ? (...args: DebugExpandT<A>) => DebugExpandT<R>\n : T extends infer O\n ? { [K in keyof O]: O[K] }\n : never;\n\n /**\n * debugging helper to show the expanded typescript contract,\n * it's only useful to debug, it's NOT MEANT to be used for actual declarations\n * using this for actual declarations will cause the types to be slow to compile/resolve and would have no benefit.\n * https://stackoverflow.com/questions/57683303/how-can-i-see-the-full-expanded-contract-of-a-typescript-type\n * @example\n * type Decorated = {\n * a?: string | null\n * b?: T2\n * c?: T1\n * d: string\n * e: number\n * }\n * type Injected = {\n * inj: object\n * }\n * // overriding the types from Decorated\n * type Text = Decorated &\n * Injected & {\n * name: string;\n * type: \"text\";\n * value: string;\n * subobject: Injected;\n * };\n * interface SomeFunction {\n * (...args: Text[]): Injected & { error: boolean };\n * }\n *\n * type ExpandedRecursively = DebugExpandRecursivelyT<Text>;\n */\n export type DebugExpandRecursivelyT<T> = T extends (...args: infer A) => infer R\n ? (...args: DebugExpandRecursivelyT<A>) => DebugExpandRecursivelyT<R>\n : T extends object\n ? T extends infer O\n ? { [K in keyof O]: DebugExpandRecursivelyT<O[K]> }\n : never\n : T;\n\n /*****************************************************************************\n * React Helpers\n **************************************************************************** */\n /**\n * An helper useful when you need the type of the second return value of React.useState\n * @example\n * const MyComponent = ({ setFoo }:{\n * setFoo: StateSetter<string>; // our children expects a react \"state setter\"\n * }) => {\n * const handleClick = () => {\n * setFoo('New value');\n * };\n * return <button onClick={handleClick}>Set Foo</button>;\n * };\n * const ParentComponent: React.FC = () => {\n * const [foo, setFoo] = React.useState<string>('Initial value');\n * return (\n * <div>\n * <p>Foo: {foo}</p>\n * <MyComponent setFoo={setFoo} />\n * </div>\n * );\n * };\n */\n export type StateSetter<T = unknown> = React.Dispatch<React.SetStateAction<T>>;\n\n /**\n * An helper useful when you need to type an higher order component that has no special requirements on the interface of the component it implements\n * @example\n * // a generic component that displays a label and a value for the sake of the example\n * interface LabelValueDisplayerPropsT {\n * foo: string;\n * bar: number;\n * }\n * const LabelValueDisplayer: React.ComponentType<LabelValueDisplayerPropsT> = ({ foo, bar }) => (\n * <div>\n * <label>{foo}</label>\n * <div>{bar}</div>\n * </div>\n * );\n *\n * // we are creating an example HOC that logs the props of the component it wraps before rendering it\n * const withLogging: TypescriptHelpersT.ReactFunctionalHOC<LabelValueDisplayerPropsT> = (Component) => (props) => {\n * console.log('Rendering component with props:', props);\n * return <Component {...props} />;\n * };\n *\n * // we can now use the HOC to wrap our component\n * const ComponentWithGenericLogging = withLogging(LabelValueDisplayer);\n * const ExampleUsageInComponent = () => {\n * return <ComponentWithGenericLogging foo=\"Test\" bar={123} />; // <-- this is correctly typed!\n * };\n */\n export type ReactFunctionalHOC<T = Record<string, unknown>> = (\n Component: React.ComponentType<JSX.IntrinsicAttributes & T>,\n ) => React.ComponentType<JSX.IntrinsicAttributes & T>;\n\n /**\n * An helper useful when you need to type an higher order component that has special requirements on the interface of the component it implements\n * @example\n * // a generic component that displays a label and a value for the sake of the example\n * interface LabelValueDisplayerPropsT {\n * foo: string;\n * bar: number;\n * }\n * const LabelValueDisplayer: React.ComponentType<LabelValueDisplayerPropsT> = ({ foo, bar }) => (\n * <div>\n * <label>{foo}</label>\n * <div>{bar}</div>\n * </div>\n * );\n *\n * interface LoggerProps { loggableTemplateLabel: string; loggableTemplateValue: string; }\n *\n * // the HOC we are creating has special requirements on the props of the component it wraps\n * // AND it has some requirements on it's own props\n * const withLogging: ReactFunctionalHOCWithDifferentInterface<LoggerProps, StartingProps> =\n * (Component) => ({ loggableTemplateLabel, loggableTemplateValue }) => {\n * const startingLabel = loggableTemplateLabel.replace(/{{label was}}/g, \"\");\n * const startingValue = parseInt(\n * loggableTemplateValue.replace(/{{value was}}/g, \"\"),\n * 10\n * );\n * console.log(\n * `${loggableTemplateLabel.replace(/{{label was}}/g, \"Label was -> \")}`,\n * `${loggableTemplateValue.replace(/{{value was}}/g, \"Value was -> \")}`\n * );\n * return <Component startA={startingLabel} startB={startingValue} />;\n * };\n *\n * const ComponentWithSpecialLogging = withLogging(LabelValueDisplayer); // <-- this is correctly typed!\n * const ExampleUsageInComponent = () => (\n * <ComponentWithSpecialLogging\n * loggableTemplateLabel=\"{{label was}}Starting count:\"\n * loggableTemplateValue=\"{{value was}}0\"\n * />\n * )\n */\n export type ReactFunctionalHOCWithDifferentInterface<K = Record<string, unknown>, T = Record<string, unknown>> = (\n Component: React.ComponentType<JSX.IntrinsicAttributes & T>,\n ) => React.ComponentType<K>;\n\n /**\n * An helper for declaring the return type of React.useRef in a way that reflects the reality of how it can be used\n * @example\n * const ComponentWithRef = () => {\n * // starting value for ref should be null\n * const myRef: T.AnyRef<HTMLDivElement> = React.useRef<HTMLDivElement>(null);\n * return (<div ref={\n * (node => {\n * // when used it should reflect what you can actually do with it, mutating it is valid.\n * myRef.current = node;\n * })\n * }>Hello, world!</div>)\n * };\n */\n export type AnyRef<T> = React.MutableRefObject<T | null> | ((_ref: T | null) => void);\n\n /**\n * An helper for defining the type of the children prop of a React component\n * @example\n * type ReactChildrenComplete = React.PropsWithChildren<object>[\"children\"];\n * type MyComponentProps = {\n * children: ReactChildrenComplete;\n * foo: string;\n * };\n * const MyComponent = ({ children, foo }: MyComponentProps) => ( <div>{children}{foo}</div> );\n */\n export type ReactChildrenComplete = React.PropsWithChildren<object>['children'];\n\n /*****************************************************************************\n * Object Helpers\n **************************************************************************** */\n\n /**\n * Helper to declare an object that has at least one of the keys of the original object as required\n * https://www.typescriptlang.org/play?#code/C4TwDgpgBAShCOBXAlgJwgQWAGQgQwGdgB5AOwgB4AVAGigGkIQCoIAPYCUgExYGsmAewBmUKlAC8UASBFiAfJICwAKCjqoABWQBjPtToBRNjoA2ibpRlzaDJgXnzVGqADIoAb2cuNAbXpQyKR2zAC6ALQA-ABcsAgo6NwU2noGDI5uWniowMh4psm6+rbGZhaUjMx09I5OahoAvv72oaqqQZyowng60ACyXIgAkpwAtp7eucCmELFEqEEA5gDc3jqCo2CC5KTAMVCkiKMARhCoq-VmRfuHJ2cX6rrbc8ALpCuqDW0qoJBQAMKmIrEVD-DZbHbASRxJBoTA4fBEMiUAaHEYQUZ0ADkVz0WKgAB8oDjwdsuMAsXVVOtSEQoAB3ZDAAAWYM2ZN2sUBwNBpMh0K89XUUxmsQARJwiGKaN51Ot2ZDYgBWABMMqFgRp4qepDFn2+NLpjJZ3L0XKBehBbIh5IFsqgItmUAlECl6pcuL4yoALO6NDrtTS9Sovipqds6WdUIJUAB1JnMgByEATZ3NPOtHKhUkFLkd4slwGl9oDzp1wdD4dpUNIgkMqGjcYTACFBCz05beQrbTn7fnnYXixrPT6-XK+eTYirfSWtWWg-qwypDVCozH4yzWyzY8yuMiABKEWPR95UcBO018K0T3Z2jX9l1u+0jqBKmfDm-AcUEZmCRCmbgoFOA4jlOVAoF3dAhxcUsxXLRdvl+aA4FhdAyFMEBkTSSoWHYTgeH4IRRHEKRrGIxQJHtFJiiMExzEsCgyLEap7Ece13A8KB-ECYIcIiGJ7RcFCEggJJqOwtiNRcdxNGyXJ8goOB1lQJJSnoip7GqeQ6EQHgIGEIJRMklwmj4xDzygdDMPIS9r27W8pGEuErKw1FhjGbFPXxIkSXsikqWXCMazrBt1wTFzyFiCKIFsrsbQciZ7yZUUB1dIsxygF8lQAZnfGC5zghcQwNILWFCptNzbZkotIDDkVizN+V7JLpidR90ufC0vVfXKMvleKvx6jLYPg4ql1UAB6CaxGZZAWA6M5ul6BlkFMUwgOgRACFEh1BAdBY9Es2rrJirqsEa20Oj2-JTEERl3igPBgkEY4ACsIB0KFjWZICqvUdpdkWnpoEvNz0XGXMHWSp15iWB5Mq62JbjA+HS1h94LkrQLqwgwgtx+5q82hgs0ugjQsry8nPynSnHgK0asamqBEz2tdwNOHQ8C26B2F6AgWDAaNIByZBXUe9AoG2DCoG4Oabrunb6V3YJZfQT7pcIAhkEWUglke563o+qEgU6fIoCrOkxjADs+DBsZoWZPGqu+JmWbKxsZddMAmWgK3Hs+xAbpAXGADc9eOP6Oa57axAAZUl47pFrekWBZPAoT9ubHoBLq7Yxc3sctg6+CGXZBAwNa7qWfGarqmyursgboSt1QgA\n * @example\n * const myObject: RequireAtLeastOne<{a: string, b: string}> = {a: 'foo'}; // valid\n * const myObject2: RequireAtLeastOne<{a: string, b: string}> = {b: 'foo'}; // valid\n * const myObject3: RequireAtLeastOne<{a: string, b: string}> = {a: 'foo', b: 'bar'}; // valid\n *\n * const myObject4: RequireAtLeastOne<{a: string, b: string}> = {}; // invalid\n */\n export type RequireAtLeastOne<T, Keys extends keyof T = keyof T> = Pick<T, Exclude<keyof T, Keys>> &\n {\n [K in Keys]-?: Required<Pick<T, K>> & Partial<Pick<T, Exclude<Keys, K>>>;\n }[Keys];\n\n // helper to require specifically only one of the keys of an object\n // E.G.: type MyType = RequireOnlyOne<{a: string, b: string}>; // MyType = {a: string} | {b: string}\n /**\n * Helper to declare an object that has only one of the keys of the original object as required\n * @example\n * const myObject: RequireOnlyOne<{a: string, b: string}> = {a: 'foo'}; // valid\n * const myObject2: RequireOnlyOne<{a: string, b: string}> = {b: 'foo'}; // valid\n *\n * const myObject3: RequireOnlyOne<{a: string, b: string}> = {a: 'foo', b: 'bar'}; // invalid\n */\n export type RequireOnlyOne<T, Keys extends keyof T = keyof T> = Pick<T, Exclude<keyof T, Keys>> &\n {\n [K in Keys]-?: Required<Pick<T, K>> & Partial<Record<Exclude<Keys, K>, undefined>>;\n }[Keys];\n\n /**\n * An Helper that given the type of an object, returns the type of the values of the object\n *\n * This is an useful alternative to typescripts enums, making your code as type safe as enums but without the typescript exclusive declaration and syntax\n *\n * Projects are free to decide wheter or not they wish to allow enums in their code base but we suggest being aware of the pitfalls of enums and double check the official documentation before making a decision\n *\n * https://www.typescriptlang.org/docs/handbook/enums.html#objects-vs-enums\n *\n * > The biggest argument in favour of this format over TypeScript's enum is that it keeps your codebase aligned with the state of JavaScript, and when/if enums are added to JavaScript then you can move to the additional syntax.\n *\n * https://github.com/tc39/proposal-type-annotations?tab=readme-ov-file#intentional-omissions\n * @example\n * type MyObject = {a: string, b: number};\n * type MyObjectValues = ObjectValues<MyObject>; // MyObjectValues = string | number\n * @example\n * const myEnumLikeObject = {\n * a: 'foo',\n * b: 'bar'\n * } as const;\n *\n * type myEnumLikeObjectValues = TypescriptHelpersT.ObjectValues<typeof myEnumLikeObject>; // myEnumLikeObjectValues = 'foo' | 'bar'\n * const foo: myEnumLikeObjectValues = 'foo'; // valid\n * const foo2: myEnumLikeObjectValues = 'bar'; // valid\n *\n * const foo3: myEnumLikeObjectValues = 'baz'; // invalid\n */\n export type ObjectValues<T> = T[keyof T];\n\n /**\n * A type that represents an object in which every key starts with \"data-\" and the value is a string, useful for declaring the data-* attributes of an HTML element\n * @example\n * const myObject: DataProps = { 'data-foo': 'bar' }; // valid\n *\n * const myObject2: DataProps = { 'aria-foo': 123 }; // invalid\n * const myObject3: DataProps = { 'foo': 'bar' }; // invalid\n */\n export type DataProps = {\n [key in `data-${string}`]: string;\n };\n /**\n * A type that represents an object in which every key starts with \"aria-\" and the value is a string, useful for declaring the aria-* attributes of an HTML element\n * @example\n * const myObject: AriaProps = { 'aria-foo': 'bar' }; // valid\n *\n * const myObject2: AriaProps = { 'data-foo': 123 }; // invalid\n * const myObject3: AriaProps = { 'foo': 'bar' }; // invalid\n */\n export type AriaProps = {\n [key in `aria-${string}`]: string;\n };\n /**\n * A type that represents an object in which every key starts with \"data-\" or \"aria-\" and the value is a string, useful for declaring the aria-* and data-* attributes of an HTML element\n * @example\n * const myObject: AriaAndDataProps = { 'aria-foo': 'bar' }; // valid\n * const myObject2: AriaAndDataProps = { 'data-foo': 'bar' }; // valid\n * const myObject3: AriaAndDataProps = { 'aria-foo': 'bar', 'data-foo': 'bar' }; // valid\n *\n * const myObject4: AriaAndDataProps = { 'foo': 'bar' }; // invalid\n */\n export type AriaAndDataProps = {\n [key in `data-${string}` | `aria-${string}`]: string;\n };\n\n /*****************************************************************************\n * Template Literals\n * Snake, Camel, Pascal, Kebab Case\n * https://stackoverflow.com/questions/60269936/typescript-convert-generic-object-from-snake-to-camel-case\n * https://www.typescriptlang.org/play?#code/C4TwDgpgBAygdgQwNYQCoHsDCCC2EA22AzhADwxQQAewEcAJkVEcAE4CWcA5gHxQC8AKCixKNOoygADACQBvTgDMIrKKgC+AfXlKVUAKrqpUAPzDp8jfOxh2wBPnYAvMvGRosuAsTL6ePIygALnMYQUFQSChsPHwMNxQfcjFaBiYWDm4+IREKalTJWQU4ZVUrYtKDQLMRItQUiSYbOwdnMlQ+EygAIk1u4J7u9XkAGXQAdxUAYwQSUg7huRiCeMRE2d8A4xDc8MjoZbj0AAVZmcIN5PzG5jZOXgFohFt7RxdyHgjwaFOic4xDkk8uI0rdMg9+AY4DMXq13jBPvsoL9-ugEhAgQ1QRl7tknrFVu4kvpoc8Wm9XP4vlF0RgUQ5MddsXcso9mq82uQ1h5AZcEZ9qdAANIQABGCFFhPWc2BBXSLIhoSxhR0JT0GgAtKrKoZjDULHINNo5CLxZK0dziVtgqE9t8oAA5R4AFgATHaoqgkABGb2PU0SqUYy7dAAWBHw6G6fAA9DGeuH8JHNON0Kx8PRuoK1D7Xf6xYGLUSQ4nIxrU6xM7H42GI+gU2mM1mkV7vQBmfNmoNJWtJ9DltP0DW0FjRqBxhN1hvp+iaEfAZv21vOzuF9E90v9itD+f9AA+UAA5Ip0P3xaxhxAWIfq5O+9PZ7uoAfuif6+e51eF9nWwBWVfmuulw4qyE4gVwP4+gAbAB3aXFIwDhhqCBwEQkwXuwRBanIDpGLe3SIRAmgoWhKiaJhmhuv0AAUSJOpCboAJQetAqC+o8tKeLEG51mOE69pGi6et6eaQpxvJzAJ9YVk2+GbgA6o2mY-u2HHcgCXgXJJm5zkQ06yeONabqgRCKTOQmsd6K5iepXHeCWU4yZmz49G+mjnnxRl1mZTYua+p4AEIIKwFlqN6-42e4GnccBCq3uBKkwZFKDRfZcwIeGxGoeh5F6fIuFSPhhEAILZSoACSRBUVAtH2vRUBMSxaiun6kKHHB2m8XJvE-q6on4isRbSmQUk+VWhl3smTmhagrodm1mkdSNxmmUpnmTfWwB6dNTWoG2rUDUc9JactXU-m2-XtScZwMg5fZjdG53zYddI3SdpBSSZD0Ci2zoHZxx08X2j2-f1ANvUDU1rYiS7Os94N-LdnX3lt+lVrtv4HcdqXvd0AASZ0tr+-XY3ZuME-d0M-r+z2kxJI0U5GX1Uz+UFY29S0fYzUYw56UEkxzQ3BpJ3PfaztOC0BIt1sz5k-fa5VwGAACuwCoPakJyOYRDcpoMwkJoKAgJo3pBFAcDKzgooqAANNruv60RRuaK6ZvgXb6hNQA8qrKtqxrUByFAADaQpQJwUBG+gihQIrfvq1EsywLZ9OkEKPAALpm3HqsJxAocZ1AnsxgAVOYSI+8A8cB1rIh18wlobCKICm+blvW6wADc5j1zrxYkM3rtgvc3ciJ7JcxuEpdl1AJdQMIc8AKIgkQ7DoHAZuYOvABuKjAObX4QPQUBgKw6CQKwwDsFeC-z7Pk9Ijn-uQA6h-H5r9vuHrGyGxAxut7XOufcUDfwNs7X0bsFQ9wbl-R2v9-5DwSmPO2IhgFETgc7RBCoPZNXEppHwr8WBH3mHieoTJJDoFFAAKwgFMfeXRAGh3DnASOf9o5qCgEnPBMU5hhwAGTDyyFnZOUUyYELfvMAunx1ADFQN7X2udviENoO-ERKUxEbGUcQp+ectH0B4EAA\n **************************************************************************** */\n\n /**\n * Converts a string from snake_case to camelCase\n * @example\n * type MyType = SnakeToCamelCase<'foo_bar'>; // MyType = 'fooBar'\n */\n export type SnakeToCamelCase<S extends string> = S extends `${infer T}_${infer U}`\n ? `${T}${Capitalize<SnakeToCamelCase<U>>}`\n : S;\n /**\n * Converts a string from snake_case to PascalCase\n * @example\n * type MyType = SnakeToPascalCase<'foo_bar'>; // MyType = 'FooBar'\n */\n export type CamelToSnakeCase<S extends string> = S extends `${infer T}${infer U}`\n ? `${T extends Capitalize<T> ? '_' : ''}${Lowercase<T>}${CamelToSnakeCase<U>}`\n : S;\n /**\n * Converts a string from kebab-case to snake_case\n * @example\n * type MyType = KebabToSnakeCase<'foo-bar'>; // MyType = 'foo_bar'\n */\n export type KebabToSnakeCase<S extends string> = S extends `${infer T}-${infer U}`\n ? `${T}_${KebabToSnakeCase<U>}`\n : S;\n /**\n * Converts a string from snake_case to kebab-case\n * @example\n * type MyType = SnakeToKebabCase<'foo_bar'>; // MyType = 'foo-bar'\n */\n export type SnakeToKebabCase<S extends string> = S extends `${infer T}_${infer U}`\n ? `${T}-${KebabToSnakeCase<U>}`\n : S;\n /**\n * Converts a string from camelCase to PascalCase\n * @example\n * type MyType = CamelToPascalCase<'fooBar'>; // MyType = 'FooBar'\n */\n export type CamelToPascalCase<S extends string> = Capitalize<S>;\n /**\n * Converts a string from PascalCase to camelCase\n * @example\n * type MyType = PascalToCamelCase<'FooBar'>; // MyType = 'fooBar'\n */\n export type PascalToCamelCase<S extends string> = Uncapitalize<S>;\n /**\n * Converts a string from PascalCase to snake_case\n * @example\n * type MyType = PascalToSnakeCase<'FooBar'>; // MyType = 'foo_bar'\n */\n export type PascalToSnakeCase<S extends string> = CamelToSnakeCase<Uncapitalize<S>>;\n\n /**\n * Converts a string from snake_case to PascalCase\n * @example\n * type MyType = SnakeToPascalCase<'foo_bar'>; // MyType = 'FooBar'\n */\n export type SnakeToPascalCase<S extends string> = Capitalize<SnakeToCamelCase<S>>;\n\n /*****************************************************************************\n * Template Literals\n * Dimsum specific (internal) helpers\n ****************************************************************************\n */\n export type RemoveDSPrefix<S extends string> = S extends `DS${infer T}` ? T : S;\n export type PropsForGlobalOnSlots<Name extends string, Slots extends Record<string, string>> = {\n [key in ObjectValues<Slots> as `ds${RemoveDSPrefix<Name>}${SnakeToPascalCase<KebabToSnakeCase<key>>}`]?:\n | object\n | ((arg: object) => object);\n };\n export type AriaAndDataPropsOrPropsGetter = AriaAndDataProps | (() => AriaAndDataProps);\n\n export type Hydraters<T, Args = unknown> = {\n [key in keyof T as key extends string ? `get${Capitalize<key>}` : key]: (\n ...args: Args extends Array<unknown> ? Args : Args[]\n ) => T[key];\n };\n}\n", "import * as React from 'react';\nexport { React };\n"],
5
+ "mappings": ";;;;;;;;;;;;;;;;;;;;;;;;AAAA;AAAA;ACAA,YAAuB;",
6
+ "names": []
7
+ }
@@ -0,0 +1,4 @@
1
+ {
2
+ "type": "commonjs",
3
+ "sideEffects": []
4
+ }
@@ -0,0 +1,2 @@
1
+ import * as React from "react";
2
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1,7 @@
1
+ {
2
+ "version": 3,
3
+ "sources": ["../../../../../scripts/build/transpile/react-shim.js"],
4
+ "sourcesContent": ["import * as React from 'react';\nexport { React };\n"],
5
+ "mappings": "AAAA,YAAY,WAAW;",
6
+ "names": []
7
+ }
@@ -0,0 +1,4 @@
1
+ {
2
+ "type": "module",
3
+ "sideEffects": []
4
+ }
@@ -0,0 +1,385 @@
1
+ /// <reference types="react" />
2
+ export declare namespace TypescriptHelpersT {
3
+ /*****************************************************************************
4
+ * A11y Helpers
5
+ **************************************************************************** */
6
+ /**
7
+ * WCAG recommends to not use tabindex values greater than 0 to ensure that the tab order is predictable.
8
+ * @example
9
+ * const tabIndex: WCAGTabIndex = 0; // valid
10
+ * const tabIndex: WCAGTabIndex = -1; // valid
11
+ *
12
+ * const tabIndex: WCAGTabIndex = 1; // invalid
13
+ * const tabIndex: WCAGTabIndex = "1"; // invalid
14
+ * const tabIndex: WCAGTabIndex = "0"; // invalid
15
+ * const tabIndex: WCAGTabIndex = "-1"; // invalid
16
+ */
17
+ type WCAGTabIndex = 0 | -1;
18
+ /*****************************************************************************
19
+ * Function Helpers
20
+ **************************************************************************** */
21
+ /**
22
+ * Helper for declaring generic functions easly. This is usually painful because of the argument spreading
23
+ * @example
24
+ * const myFunction: GenericFunc<number,void> = (a) => { console.log(a) }; // a is a number
25
+ * const myFunction2: GenericFunc<[number, number], string> = (a,b) => `${a + b}`; // a and b are numbers, the return type is a string
26
+ */
27
+ type GenericFunc<T = unknown, R = unknown> = (...args: T extends Array<unknown> ? T : T[]) => R;
28
+ /**
29
+ * Helper for declaring a void function easly. This is usually painful because of the argument spreading.
30
+ * @example
31
+ * const myFunction: VoidGenericFunc<number> = (a) => { console.log(a) }; // a is a number
32
+ * const myFunction2: VoidGenericFunc<[number, string]> = (a,b) => { console.log(a,b) }; // a is a number, b is a string
33
+ */
34
+ type VoidGenericFunc<T = unknown> = GenericFunc<T, void>;
35
+ /**
36
+ * Helper for declaring a function that returns a boolean easly. This is usually painful because of the argument spreading
37
+ * @example
38
+ * const myFunction: BooleanGetter<number> = (a) => a > 0 // a is a number
39
+ * const myFunction2: BooleanGetter<[number, string]> = (a,b) => a > 0 && b.length > 0 // a is a number, b is a string
40
+ */
41
+ type BooleanGetter<T = unknown> = GenericFunc<T, boolean>;
42
+ /*****************************************************************************
43
+ * Debugging Helpers
44
+ **************************************************************************** */
45
+ /**
46
+ * debugging helper to show the expanded typescript contract,
47
+ * it's only useful to debug, it's NOT MEANT to be used for actual declarations
48
+ * using this for actual declarations will cause the types to be slow to compile/resolve and would have no benefit.
49
+ * https://stackoverflow.com/questions/57683303/how-can-i-see-the-full-expanded-contract-of-a-typescript-type
50
+ * @example
51
+ * type Decorated = {
52
+ * a?: string | null
53
+ * b?: T2
54
+ * c?: T1
55
+ * d: string
56
+ * e: number
57
+ * }
58
+ * type Injected = {
59
+ * inj: object
60
+ * }
61
+ * // overriding the types from Decorated
62
+ * type Text = Decorated &
63
+ * Injected & {
64
+ * name: string;
65
+ * type: "text";
66
+ * value: string;
67
+ * subobject: Injected;
68
+ * };
69
+ *
70
+ * type Expanded = DebugExpandT<Text>;
71
+ */
72
+ type DebugExpandT<T> = T extends (...args: infer A) => infer R ? (...args: DebugExpandT<A>) => DebugExpandT<R> : T extends infer O ? {
73
+ [K in keyof O]: O[K];
74
+ } : never;
75
+ /**
76
+ * debugging helper to show the expanded typescript contract,
77
+ * it's only useful to debug, it's NOT MEANT to be used for actual declarations
78
+ * using this for actual declarations will cause the types to be slow to compile/resolve and would have no benefit.
79
+ * https://stackoverflow.com/questions/57683303/how-can-i-see-the-full-expanded-contract-of-a-typescript-type
80
+ * @example
81
+ * type Decorated = {
82
+ * a?: string | null
83
+ * b?: T2
84
+ * c?: T1
85
+ * d: string
86
+ * e: number
87
+ * }
88
+ * type Injected = {
89
+ * inj: object
90
+ * }
91
+ * // overriding the types from Decorated
92
+ * type Text = Decorated &
93
+ * Injected & {
94
+ * name: string;
95
+ * type: "text";
96
+ * value: string;
97
+ * subobject: Injected;
98
+ * };
99
+ * interface SomeFunction {
100
+ * (...args: Text[]): Injected & { error: boolean };
101
+ * }
102
+ *
103
+ * type ExpandedRecursively = DebugExpandRecursivelyT<Text>;
104
+ */
105
+ type DebugExpandRecursivelyT<T> = T extends (...args: infer A) => infer R ? (...args: DebugExpandRecursivelyT<A>) => DebugExpandRecursivelyT<R> : T extends object ? T extends infer O ? {
106
+ [K in keyof O]: DebugExpandRecursivelyT<O[K]>;
107
+ } : never : T;
108
+ /*****************************************************************************
109
+ * React Helpers
110
+ **************************************************************************** */
111
+ /**
112
+ * An helper useful when you need the type of the second return value of React.useState
113
+ * @example
114
+ * const MyComponent = ({ setFoo }:{
115
+ * setFoo: StateSetter<string>; // our children expects a react "state setter"
116
+ * }) => {
117
+ * const handleClick = () => {
118
+ * setFoo('New value');
119
+ * };
120
+ * return <button onClick={handleClick}>Set Foo</button>;
121
+ * };
122
+ * const ParentComponent: React.FC = () => {
123
+ * const [foo, setFoo] = React.useState<string>('Initial value');
124
+ * return (
125
+ * <div>
126
+ * <p>Foo: {foo}</p>
127
+ * <MyComponent setFoo={setFoo} />
128
+ * </div>
129
+ * );
130
+ * };
131
+ */
132
+ type StateSetter<T = unknown> = React.Dispatch<React.SetStateAction<T>>;
133
+ /**
134
+ * An helper useful when you need to type an higher order component that has no special requirements on the interface of the component it implements
135
+ * @example
136
+ * // a generic component that displays a label and a value for the sake of the example
137
+ * interface LabelValueDisplayerPropsT {
138
+ * foo: string;
139
+ * bar: number;
140
+ * }
141
+ * const LabelValueDisplayer: React.ComponentType<LabelValueDisplayerPropsT> = ({ foo, bar }) => (
142
+ * <div>
143
+ * <label>{foo}</label>
144
+ * <div>{bar}</div>
145
+ * </div>
146
+ * );
147
+ *
148
+ * // we are creating an example HOC that logs the props of the component it wraps before rendering it
149
+ * const withLogging: TypescriptHelpersT.ReactFunctionalHOC<LabelValueDisplayerPropsT> = (Component) => (props) => {
150
+ * console.log('Rendering component with props:', props);
151
+ * return <Component {...props} />;
152
+ * };
153
+ *
154
+ * // we can now use the HOC to wrap our component
155
+ * const ComponentWithGenericLogging = withLogging(LabelValueDisplayer);
156
+ * const ExampleUsageInComponent = () => {
157
+ * return <ComponentWithGenericLogging foo="Test" bar={123} />; // <-- this is correctly typed!
158
+ * };
159
+ */
160
+ type ReactFunctionalHOC<T = Record<string, unknown>> = (Component: React.ComponentType<JSX.IntrinsicAttributes & T>) => React.ComponentType<JSX.IntrinsicAttributes & T>;
161
+ /**
162
+ * An helper useful when you need to type an higher order component that has special requirements on the interface of the component it implements
163
+ * @example
164
+ * // a generic component that displays a label and a value for the sake of the example
165
+ * interface LabelValueDisplayerPropsT {
166
+ * foo: string;
167
+ * bar: number;
168
+ * }
169
+ * const LabelValueDisplayer: React.ComponentType<LabelValueDisplayerPropsT> = ({ foo, bar }) => (
170
+ * <div>
171
+ * <label>{foo}</label>
172
+ * <div>{bar}</div>
173
+ * </div>
174
+ * );
175
+ *
176
+ * interface LoggerProps { loggableTemplateLabel: string; loggableTemplateValue: string; }
177
+ *
178
+ * // the HOC we are creating has special requirements on the props of the component it wraps
179
+ * // AND it has some requirements on it's own props
180
+ * const withLogging: ReactFunctionalHOCWithDifferentInterface<LoggerProps, StartingProps> =
181
+ * (Component) => ({ loggableTemplateLabel, loggableTemplateValue }) => {
182
+ * const startingLabel = loggableTemplateLabel.replace(/{{label was}}/g, "");
183
+ * const startingValue = parseInt(
184
+ * loggableTemplateValue.replace(/{{value was}}/g, ""),
185
+ * 10
186
+ * );
187
+ * console.log(
188
+ * `${loggableTemplateLabel.replace(/{{label was}}/g, "Label was -> ")}`,
189
+ * `${loggableTemplateValue.replace(/{{value was}}/g, "Value was -> ")}`
190
+ * );
191
+ * return <Component startA={startingLabel} startB={startingValue} />;
192
+ * };
193
+ *
194
+ * const ComponentWithSpecialLogging = withLogging(LabelValueDisplayer); // <-- this is correctly typed!
195
+ * const ExampleUsageInComponent = () => (
196
+ * <ComponentWithSpecialLogging
197
+ * loggableTemplateLabel="{{label was}}Starting count:"
198
+ * loggableTemplateValue="{{value was}}0"
199
+ * />
200
+ * )
201
+ */
202
+ type ReactFunctionalHOCWithDifferentInterface<K = Record<string, unknown>, T = Record<string, unknown>> = (Component: React.ComponentType<JSX.IntrinsicAttributes & T>) => React.ComponentType<K>;
203
+ /**
204
+ * An helper for declaring the return type of React.useRef in a way that reflects the reality of how it can be used
205
+ * @example
206
+ * const ComponentWithRef = () => {
207
+ * // starting value for ref should be null
208
+ * const myRef: T.AnyRef<HTMLDivElement> = React.useRef<HTMLDivElement>(null);
209
+ * return (<div ref={
210
+ * (node => {
211
+ * // when used it should reflect what you can actually do with it, mutating it is valid.
212
+ * myRef.current = node;
213
+ * })
214
+ * }>Hello, world!</div>)
215
+ * };
216
+ */
217
+ type AnyRef<T> = React.MutableRefObject<T | null> | ((_ref: T | null) => void);
218
+ /**
219
+ * An helper for defining the type of the children prop of a React component
220
+ * @example
221
+ * type ReactChildrenComplete = React.PropsWithChildren<object>["children"];
222
+ * type MyComponentProps = {
223
+ * children: ReactChildrenComplete;
224
+ * foo: string;
225
+ * };
226
+ * const MyComponent = ({ children, foo }: MyComponentProps) => ( <div>{children}{foo}</div> );
227
+ */
228
+ type ReactChildrenComplete = React.PropsWithChildren<object>['children'];
229
+ /*****************************************************************************
230
+ * Object Helpers
231
+ **************************************************************************** */
232
+ /**
233
+ * Helper to declare an object that has at least one of the keys of the original object as required
234
+ * https://www.typescriptlang.org/play?#code/C4TwDgpgBAShCOBXAlgJwgQWAGQgQwGdgB5AOwgB4AVAGigGkIQCoIAPYCUgExYGsmAewBmUKlAC8UASBFiAfJICwAKCjqoABWQBjPtToBRNjoA2ibpRlzaDJgXnzVGqADIoAb2cuNAbXpQyKR2zAC6ALQA-ABcsAgo6NwU2noGDI5uWniowMh4psm6+rbGZhaUjMx09I5OahoAvv72oaqqQZyowng60ACyXIgAkpwAtp7eucCmELFEqEEA5gDc3jqCo2CC5KTAMVCkiKMARhCoq-VmRfuHJ2cX6rrbc8ALpCuqDW0qoJBQAMKmIrEVD-DZbHbASRxJBoTA4fBEMiUAaHEYQUZ0ADkVz0WKgAB8oDjwdsuMAsXVVOtSEQoAB3ZDAAAWYM2ZN2sUBwNBpMh0K89XUUxmsQARJwiGKaN51Ot2ZDYgBWABMMqFgRp4qepDFn2+NLpjJZ3L0XKBehBbIh5IFsqgItmUAlECl6pcuL4yoALO6NDrtTS9Sovipqds6WdUIJUAB1JnMgByEATZ3NPOtHKhUkFLkd4slwGl9oDzp1wdD4dpUNIgkMqGjcYTACFBCz05beQrbTn7fnnYXixrPT6-XK+eTYirfSWtWWg-qwypDVCozH4yzWyzY8yuMiABKEWPR95UcBO018K0T3Z2jX9l1u+0jqBKmfDm-AcUEZmCRCmbgoFOA4jlOVAoF3dAhxcUsxXLRdvl+aA4FhdAyFMEBkTSSoWHYTgeH4IRRHEKRrGIxQJHtFJiiMExzEsCgyLEap7Ece13A8KB-ECYIcIiGJ7RcFCEggJJqOwtiNRcdxNGyXJ8goOB1lQJJSnoip7GqeQ6EQHgIGEIJRMklwmj4xDzygdDMPIS9r27W8pGEuErKw1FhjGbFPXxIkSXsikqWXCMazrBt1wTFzyFiCKIFsrsbQciZ7yZUUB1dIsxygF8lQAZnfGC5zghcQwNILWFCptNzbZkotIDDkVizN+V7JLpidR90ufC0vVfXKMvleKvx6jLYPg4ql1UAB6CaxGZZAWA6M5ul6BlkFMUwgOgRACFEh1BAdBY9Es2rrJirqsEa20Oj2-JTEERl3igPBgkEY4ACsIB0KFjWZICqvUdpdkWnpoEvNz0XGXMHWSp15iWB5Mq62JbjA+HS1h94LkrQLqwgwgtx+5q82hgs0ugjQsry8nPynSnHgK0asamqBEz2tdwNOHQ8C26B2F6AgWDAaNIByZBXUe9AoG2DCoG4Oabrunb6V3YJZfQT7pcIAhkEWUglke563o+qEgU6fIoCrOkxjADs+DBsZoWZPGqu+JmWbKxsZddMAmWgK3Hs+xAbpAXGADc9eOP6Oa57axAAZUl47pFrekWBZPAoT9ubHoBLq7Yxc3sctg6+CGXZBAwNa7qWfGarqmyursgboSt1QgA
235
+ * @example
236
+ * const myObject: RequireAtLeastOne<{a: string, b: string}> = {a: 'foo'}; // valid
237
+ * const myObject2: RequireAtLeastOne<{a: string, b: string}> = {b: 'foo'}; // valid
238
+ * const myObject3: RequireAtLeastOne<{a: string, b: string}> = {a: 'foo', b: 'bar'}; // valid
239
+ *
240
+ * const myObject4: RequireAtLeastOne<{a: string, b: string}> = {}; // invalid
241
+ */
242
+ type RequireAtLeastOne<T, Keys extends keyof T = keyof T> = Pick<T, Exclude<keyof T, Keys>> & {
243
+ [K in Keys]-?: Required<Pick<T, K>> & Partial<Pick<T, Exclude<Keys, K>>>;
244
+ }[Keys];
245
+ /**
246
+ * Helper to declare an object that has only one of the keys of the original object as required
247
+ * @example
248
+ * const myObject: RequireOnlyOne<{a: string, b: string}> = {a: 'foo'}; // valid
249
+ * const myObject2: RequireOnlyOne<{a: string, b: string}> = {b: 'foo'}; // valid
250
+ *
251
+ * const myObject3: RequireOnlyOne<{a: string, b: string}> = {a: 'foo', b: 'bar'}; // invalid
252
+ */
253
+ type RequireOnlyOne<T, Keys extends keyof T = keyof T> = Pick<T, Exclude<keyof T, Keys>> & {
254
+ [K in Keys]-?: Required<Pick<T, K>> & Partial<Record<Exclude<Keys, K>, undefined>>;
255
+ }[Keys];
256
+ /**
257
+ * An Helper that given the type of an object, returns the type of the values of the object
258
+ *
259
+ * This is an useful alternative to typescripts enums, making your code as type safe as enums but without the typescript exclusive declaration and syntax
260
+ *
261
+ * Projects are free to decide wheter or not they wish to allow enums in their code base but we suggest being aware of the pitfalls of enums and double check the official documentation before making a decision
262
+ *
263
+ * https://www.typescriptlang.org/docs/handbook/enums.html#objects-vs-enums
264
+ *
265
+ * > The biggest argument in favour of this format over TypeScript's enum is that it keeps your codebase aligned with the state of JavaScript, and when/if enums are added to JavaScript then you can move to the additional syntax.
266
+ *
267
+ * https://github.com/tc39/proposal-type-annotations?tab=readme-ov-file#intentional-omissions
268
+ * @example
269
+ * type MyObject = {a: string, b: number};
270
+ * type MyObjectValues = ObjectValues<MyObject>; // MyObjectValues = string | number
271
+ * @example
272
+ * const myEnumLikeObject = {
273
+ * a: 'foo',
274
+ * b: 'bar'
275
+ * } as const;
276
+ *
277
+ * type myEnumLikeObjectValues = TypescriptHelpersT.ObjectValues<typeof myEnumLikeObject>; // myEnumLikeObjectValues = 'foo' | 'bar'
278
+ * const foo: myEnumLikeObjectValues = 'foo'; // valid
279
+ * const foo2: myEnumLikeObjectValues = 'bar'; // valid
280
+ *
281
+ * const foo3: myEnumLikeObjectValues = 'baz'; // invalid
282
+ */
283
+ type ObjectValues<T> = T[keyof T];
284
+ /**
285
+ * A type that represents an object in which every key starts with "data-" and the value is a string, useful for declaring the data-* attributes of an HTML element
286
+ * @example
287
+ * const myObject: DataProps = { 'data-foo': 'bar' }; // valid
288
+ *
289
+ * const myObject2: DataProps = { 'aria-foo': 123 }; // invalid
290
+ * const myObject3: DataProps = { 'foo': 'bar' }; // invalid
291
+ */
292
+ type DataProps = {
293
+ [key in `data-${string}`]: string;
294
+ };
295
+ /**
296
+ * A type that represents an object in which every key starts with "aria-" and the value is a string, useful for declaring the aria-* attributes of an HTML element
297
+ * @example
298
+ * const myObject: AriaProps = { 'aria-foo': 'bar' }; // valid
299
+ *
300
+ * const myObject2: AriaProps = { 'data-foo': 123 }; // invalid
301
+ * const myObject3: AriaProps = { 'foo': 'bar' }; // invalid
302
+ */
303
+ type AriaProps = {
304
+ [key in `aria-${string}`]: string;
305
+ };
306
+ /**
307
+ * A type that represents an object in which every key starts with "data-" or "aria-" and the value is a string, useful for declaring the aria-* and data-* attributes of an HTML element
308
+ * @example
309
+ * const myObject: AriaAndDataProps = { 'aria-foo': 'bar' }; // valid
310
+ * const myObject2: AriaAndDataProps = { 'data-foo': 'bar' }; // valid
311
+ * const myObject3: AriaAndDataProps = { 'aria-foo': 'bar', 'data-foo': 'bar' }; // valid
312
+ *
313
+ * const myObject4: AriaAndDataProps = { 'foo': 'bar' }; // invalid
314
+ */
315
+ type AriaAndDataProps = {
316
+ [key in `data-${string}` | `aria-${string}`]: string;
317
+ };
318
+ /*****************************************************************************
319
+ * Template Literals
320
+ * Snake, Camel, Pascal, Kebab Case
321
+ * https://stackoverflow.com/questions/60269936/typescript-convert-generic-object-from-snake-to-camel-case
322
+ * https://www.typescriptlang.org/play?#code/C4TwDgpgBAygdgQwNYQCoHsDCCC2EA22AzhADwxQQAewEcAJkVEcAE4CWcA5gHxQC8AKCixKNOoygADACQBvTgDMIrKKgC+AfXlKVUAKrqpUAPzDp8jfOxh2wBPnYAvMvGRosuAsTL6ePIygALnMYQUFQSChsPHwMNxQfcjFaBiYWDm4+IREKalTJWQU4ZVUrYtKDQLMRItQUiSYbOwdnMlQ+EygAIk1u4J7u9XkAGXQAdxUAYwQSUg7huRiCeMRE2d8A4xDc8MjoZbj0AAVZmcIN5PzG5jZOXgFohFt7RxdyHgjwaFOic4xDkk8uI0rdMg9+AY4DMXq13jBPvsoL9-ugEhAgQ1QRl7tknrFVu4kvpoc8Wm9XP4vlF0RgUQ5MddsXcso9mq82uQ1h5AZcEZ9qdAANIQABGCFFhPWc2BBXSLIhoSxhR0JT0GgAtKrKoZjDULHINNo5CLxZK0dziVtgqE9t8oAA5R4AFgATHaoqgkABGb2PU0SqUYy7dAAWBHw6G6fAA9DGeuH8JHNON0Kx8PRuoK1D7Xf6xYGLUSQ4nIxrU6xM7H42GI+gU2mM1mkV7vQBmfNmoNJWtJ9DltP0DW0FjRqBxhN1hvp+iaEfAZv21vOzuF9E90v9itD+f9AA+UAA5Ip0P3xaxhxAWIfq5O+9PZ7uoAfuif6+e51eF9nWwBWVfmuulw4qyE4gVwP4+gAbAB3aXFIwDhhqCBwEQkwXuwRBanIDpGLe3SIRAmgoWhKiaJhmhuv0AAUSJOpCboAJQetAqC+o8tKeLEG51mOE69pGi6et6eaQpxvJzAJ9YVk2+GbgA6o2mY-u2HHcgCXgXJJm5zkQ06yeONabqgRCKTOQmsd6K5iepXHeCWU4yZmz49G+mjnnxRl1mZTYua+p4AEIIKwFlqN6-42e4GnccBCq3uBKkwZFKDRfZcwIeGxGoeh5F6fIuFSPhhEAILZSoACSRBUVAtH2vRUBMSxaiun6kKHHB2m8XJvE-q6on4isRbSmQUk+VWhl3smTmhagrodm1mkdSNxmmUpnmTfWwB6dNTWoG2rUDUc9JactXU-m2-XtScZwMg5fZjdG53zYddI3SdpBSSZD0Ci2zoHZxx08X2j2-f1ANvUDU1rYiS7Os94N-LdnX3lt+lVrtv4HcdqXvd0AASZ0tr+-XY3ZuME-d0M-r+z2kxJI0U5GX1Uz+UFY29S0fYzUYw56UEkxzQ3BpJ3PfaztOC0BIt1sz5k-fa5VwGAACuwCoPakJyOYRDcpoMwkJoKAgJo3pBFAcDKzgooqAANNruv60RRuaK6ZvgXb6hNQA8qrKtqxrUByFAADaQpQJwUBG+gihQIrfvq1EsywLZ9OkEKPAALpm3HqsJxAocZ1AnsxgAVOYSI+8A8cB1rIh18wlobCKICm+blvW6wADc5j1zrxYkM3rtgvc3ciJ7JcxuEpdl1AJdQMIc8AKIgkQ7DoHAZuYOvABuKjAObX4QPQUBgKw6CQKwwDsFeC-z7Pk9Ijn-uQA6h-H5r9vuHrGyGxAxut7XOufcUDfwNs7X0bsFQ9wbl-R2v9-5DwSmPO2IhgFETgc7RBCoPZNXEppHwr8WBH3mHieoTJJDoFFAAKwgFMfeXRAGh3DnASOf9o5qCgEnPBMU5hhwAGTDyyFnZOUUyYELfvMAunx1ADFQN7X2udviENoO-ERKUxEbGUcQp+ectH0B4EAA
323
+ **************************************************************************** */
324
+ /**
325
+ * Converts a string from snake_case to camelCase
326
+ * @example
327
+ * type MyType = SnakeToCamelCase<'foo_bar'>; // MyType = 'fooBar'
328
+ */
329
+ type SnakeToCamelCase<S extends string> = S extends `${infer T}_${infer U}` ? `${T}${Capitalize<SnakeToCamelCase<U>>}` : S;
330
+ /**
331
+ * Converts a string from snake_case to PascalCase
332
+ * @example
333
+ * type MyType = SnakeToPascalCase<'foo_bar'>; // MyType = 'FooBar'
334
+ */
335
+ type CamelToSnakeCase<S extends string> = S extends `${infer T}${infer U}` ? `${T extends Capitalize<T> ? '_' : ''}${Lowercase<T>}${CamelToSnakeCase<U>}` : S;
336
+ /**
337
+ * Converts a string from kebab-case to snake_case
338
+ * @example
339
+ * type MyType = KebabToSnakeCase<'foo-bar'>; // MyType = 'foo_bar'
340
+ */
341
+ type KebabToSnakeCase<S extends string> = S extends `${infer T}-${infer U}` ? `${T}_${KebabToSnakeCase<U>}` : S;
342
+ /**
343
+ * Converts a string from snake_case to kebab-case
344
+ * @example
345
+ * type MyType = SnakeToKebabCase<'foo_bar'>; // MyType = 'foo-bar'
346
+ */
347
+ type SnakeToKebabCase<S extends string> = S extends `${infer T}_${infer U}` ? `${T}-${KebabToSnakeCase<U>}` : S;
348
+ /**
349
+ * Converts a string from camelCase to PascalCase
350
+ * @example
351
+ * type MyType = CamelToPascalCase<'fooBar'>; // MyType = 'FooBar'
352
+ */
353
+ type CamelToPascalCase<S extends string> = Capitalize<S>;
354
+ /**
355
+ * Converts a string from PascalCase to camelCase
356
+ * @example
357
+ * type MyType = PascalToCamelCase<'FooBar'>; // MyType = 'fooBar'
358
+ */
359
+ type PascalToCamelCase<S extends string> = Uncapitalize<S>;
360
+ /**
361
+ * Converts a string from PascalCase to snake_case
362
+ * @example
363
+ * type MyType = PascalToSnakeCase<'FooBar'>; // MyType = 'foo_bar'
364
+ */
365
+ type PascalToSnakeCase<S extends string> = CamelToSnakeCase<Uncapitalize<S>>;
366
+ /**
367
+ * Converts a string from snake_case to PascalCase
368
+ * @example
369
+ * type MyType = SnakeToPascalCase<'foo_bar'>; // MyType = 'FooBar'
370
+ */
371
+ type SnakeToPascalCase<S extends string> = Capitalize<SnakeToCamelCase<S>>;
372
+ /*****************************************************************************
373
+ * Template Literals
374
+ * Dimsum specific (internal) helpers
375
+ ****************************************************************************
376
+ */
377
+ type RemoveDSPrefix<S extends string> = S extends `DS${infer T}` ? T : S;
378
+ type PropsForGlobalOnSlots<Name extends string, Slots extends Record<string, string>> = {
379
+ [key in ObjectValues<Slots> as `ds${RemoveDSPrefix<Name>}${SnakeToPascalCase<KebabToSnakeCase<key>>}`]?: object | ((arg: object) => object);
380
+ };
381
+ type AriaAndDataPropsOrPropsGetter = AriaAndDataProps | (() => AriaAndDataProps);
382
+ type Hydraters<T, Args = unknown> = {
383
+ [key in keyof T as key extends string ? `get${Capitalize<key>}` : key]: (...args: Args extends Array<unknown> ? Args : Args[]) => T[key];
384
+ };
385
+ }
package/package.json ADDED
@@ -0,0 +1,53 @@
1
+ {
2
+ "name": "@elliemae/ds-typescript-helpers",
3
+ "version": "3.30.0-next.0",
4
+ "license": "MIT",
5
+ "description": "ICE MT - Dimsum - Typescript helpers",
6
+ "files": [
7
+ "dist"
8
+ ],
9
+ "module": "./dist/esm/index.js",
10
+ "main": "./dist/cjs/index.js",
11
+ "types": "./dist/types/index.d.ts",
12
+ "exports": {
13
+ ".": {
14
+ "import": "./dist/esm/index.js",
15
+ "require": "./dist/cjs/index.js"
16
+ }
17
+ },
18
+ "sideEffects": [],
19
+ "repository": {
20
+ "type": "git",
21
+ "url": "https://git.elliemae.io/platform-ui/dimsum.git"
22
+ },
23
+ "engines": {
24
+ "pnpm": ">=8",
25
+ "node": ">=18"
26
+ },
27
+ "author": "ICE MT",
28
+ "jestSonar": {
29
+ "sonar56x": true,
30
+ "reportPath": "reports",
31
+ "reportFile": "tests.xml",
32
+ "indent": 4
33
+ },
34
+ "devDependencies": {
35
+ "@elliemae/pui-cli": "~9.0.0-next.31",
36
+ "@elliemae/ds-monorepo-devops": "3.30.0-next.0"
37
+ },
38
+ "publishConfig": {
39
+ "access": "public",
40
+ "typeSafety": true
41
+ },
42
+ "scripts": {
43
+ "dev": "cross-env NODE_ENV=development node ../../../scripts/build/build.mjs --watch",
44
+ "test": "pui-cli test --passWithNoTests",
45
+ "lint": "node ../../../scripts/lint.mjs",
46
+ "eslint:fix": "eslint --ext='.js,.jsx,.test.js,.ts,.tsx' --fix --config='../../../.eslintrc.js' src/",
47
+ "dts": "node ../../../scripts/dts.mjs",
48
+ "build": "cross-env NODE_ENV=production node ../../../scripts/build/build.mjs",
49
+ "dev:build": "pnpm --filter {.}... build",
50
+ "dev:install": "pnpm --filter {.}... i --no-lockfile && pnpm run dev:build",
51
+ "checkDeps": "npm exec ../../util/ds-codemods -- check-missing-packages --projectFolderPath=\"./\" --ignorePackagesGlobPattern=\"\" --ignoreFilesGlobPattern=\"**/test-ables/*,**/tests/*\""
52
+ }
53
+ }