Skip to content

Instantly share code, notes, and snippets.

@lxchurbakov
Created November 8, 2022 08:46
Show Gist options
  • Save lxchurbakov/ae7b73b8741c74de99f52a61a2370b2a to your computer and use it in GitHub Desktop.
Save lxchurbakov/ae7b73b8741c74de99f52a61a2370b2a to your computer and use it in GitHub Desktop.
moment-like-string-format-parser
const extractParams = (after: string) => {
if (!after.startsWith('(')) {
return [after, {}];
}
const paramsEnd = after.indexOf(')');
return [
after.slice(paramsEnd + 1),
Object.fromEntries(
after
.slice(1, paramsEnd)
.split(',')
.map((v) => (v.includes('=') ? v.split('=') : [v, true])),
),
];
};
// Simple parser for generic format strings like
// token(foo=bar)~token(baz=qux)~anothertokens
//
// Omits ~ signs and returns an array of { token: string, params: string[] }
export const parseGenericFormatString = <T extends string>(
format: string,
tokens: T[],
// eslint-disable-next-line @typescript-eslint/no-explicit-any
): { token: T; params: any }[] => {
// eslint-disable-next-line no-restricted-syntax
for (const token of tokens) {
const tokenPosition = format.indexOf(token);
if (tokenPosition > -1) {
const before = format.slice(0, tokenPosition);
const [after, params] = extractParams(format.slice(tokenPosition + token.length));
return [
...parseGenericFormatString(before, tokens),
{ token, params },
...parseGenericFormatString(after, tokens),
];
}
}
return [{ token: 'text' as T, params: { text: format.replace(/~/g, '') } }];
};
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment