Skip to content

Instantly share code, notes, and snippets.

@aparx
Last active January 29, 2024 01:54
Show Gist options
  • Save aparx/3bd207a685fe78b4332702e7121faa7d to your computer and use it in GitHub Desktop.
Save aparx/3bd207a685fe78b4332702e7121faa7d to your computer and use it in GitHub Desktop.
Typesafe string joining
type _JoinableElement = string | number | null | undefined | boolean;
type _JoinableArray = _JoinableElement[];
export type JoinArray<
TArray extends _JoinableArray,
TDelimiter extends string = " "
> = _JoinArray<TArray, TDelimiter>;
type _JoinArray<
TArray extends _JoinableArray,
TDelimiter extends string,
_TValue = _CircularJoin<TArray, TDelimiter>
> = _TValue extends null ? string : _TValue;
type _CircularJoin<
TArray extends _JoinableArray,
TDelimiter extends string,
R extends string | null = null
> = TArray extends [
infer TNext extends _JoinableElement,
...infer TAfter extends _JoinableArray
]
? R extends null
? _CircularJoin<TAfter, TDelimiter, `${TNext}`>
: _CircularJoin<TAfter, TDelimiter, `${R}${TDelimiter}${TNext}`>
: TArray extends [infer TNext extends _JoinableElement]
? R extends null
? TNext
: `${R}${TDelimiter}${TNext}`
: R;
export function join<
TArray extends _JoinableArray,
TDelimiter extends string = " "
>(
array: TArray,
separator: TDelimiter = " " as TDelimiter
): JoinArray<TArray, TDelimiter> {
return array.join(separator) as JoinArray<TArray, TDelimiter>;
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment