Skip to content

Commit

Permalink
Version 5.0.2 (#31)
Browse files Browse the repository at this point in the history
## Bug fixes
* Fix incorrect type declarations

## Minor changes
* Move source code to a single file to simplify maintaining and output
* Remove unnecessary checks in `escapeRegExp`
  • Loading branch information
vasilii-kovalev committed Jul 29, 2021
1 parent fd4f996 commit 62e4e70
Show file tree
Hide file tree
Showing 14 changed files with 134 additions and 164 deletions.
3 changes: 0 additions & 3 deletions .prettierignore
@@ -1,6 +1,3 @@
# Artifacts
dist

# Coverage directory
coverage

Expand Down
2 changes: 1 addition & 1 deletion README.md
Expand Up @@ -23,7 +23,7 @@ A small, dependency-free and strongly typed template engine.
[minzip-size-badge]: https://flat.badgen.net/bundlephobia/minzip/hydrate-text
[size-link]: https://bundlephobia.com/package/hydrate-text
[types-badge]: https://flat.badgen.net/npm/types/hydrate-text
[types-link]: https://github.com/vasilii-kovalev/hydrate-text/blob/main/src/types.ts
[types-link]: https://github.com/vasilii-kovalev/hydrate-text/blob/main/src/index.ts#L1-L75
[coverage-badge]: https://flat.badgen.net/coveralls/c/github/vasilii-kovalev/hydrate-text
[coverage-link]: https://coveralls.io/github/vasilii-kovalev/hydrate-text
[vulnerabilities-badge]: https://flat.badgen.net/snyk/vasilii-kovalev/hydrate-text
Expand Down
10 changes: 4 additions & 6 deletions package.json
@@ -1,11 +1,11 @@
{
"name": "hydrate-text",
"version": "5.0.1",
"version": "5.0.2",
"description": "A small, dependency-free and strongly typed template engine.",
"sideEffects": false,
"type": "module",
"main": "dist/index.js",
"types": "dist/types.d.ts",
"types": "dist/index.d.ts",
"files": [
"dist"
],
Expand Down Expand Up @@ -37,10 +37,8 @@
"prettier:fix": "prettier . --write",
"lint": "npm-run-all tslint types eslint:check prettier:check",
"test": "jest --coverage",
"build:js": "tsc --project tsconfig.build.json",
"build:types": "tsc --project tsconfig.types.json",
"build": "npm-run-all build:js build:types",
"postbuild": "node postbuild.js",
"build": "tsc --project tsconfig.build.json",
"postbuild": "prettier dist --write",
"prepare": "npm-run-all build",
"prepublishOnly": "npm-run-all lint test",
"postversion": "git push && git push --tags"
Expand Down
3 changes: 0 additions & 3 deletions postbuild.js

This file was deleted.

11 changes: 0 additions & 11 deletions src/constants.ts

This file was deleted.

119 changes: 115 additions & 4 deletions src/index.ts
@@ -1,6 +1,117 @@
import { DEFAULT_INTERPOLATION_OPTIONS } from "./constants";
import { ConfigureHydrateText, HydrateText } from "./types";
import { escapeRegExp, isUndefined } from "./utils";
type ValueType = string | boolean | number | bigint;

type GetVariables<
Text extends string,
Prefix extends string,
Suffix extends string,
> = string extends Text
? string
: Prefix extends ""
? Suffix extends ""
? // Prefix === "", Suffix === ""
Text extends `${infer Letter}${infer Rest}`
? Letter | GetVariables<Rest, Prefix, Suffix>
: never
: // Prefix === "", Suffix !== ""
Text extends `${infer Variable}${Suffix}${infer Rest}`
? Variable | GetVariables<Rest, Prefix, Suffix>
: never
: Suffix extends ""
? // Prefix !== "", Suffix === ""
// eslint-disable-next-line @typescript-eslint/no-unused-vars
Text extends `${infer _Start}${Prefix}${infer Variable}`
? Variable extends `${infer _Variable}${Prefix}${infer Rest}`
? _Variable | GetVariables<`${Prefix}${Rest}`, Prefix, Suffix>
: Variable
: never
: // Prefix !== "", Suffix !== ""
// eslint-disable-next-line @typescript-eslint/no-unused-vars
Text extends `${infer _Start}${Prefix}${infer Variable}${Suffix}${infer Rest}`
? Variable extends `${infer _Start}${Prefix}${infer _Variable}`
? GetVariables<
`${_Start}${Prefix}${_Variable}${Suffix}${Rest}`,
Prefix,
Suffix
>
: Variable | GetVariables<Rest, Prefix, Suffix>
: never;

interface InterpolationOptions<Prefix extends string, Suffix extends string> {
prefix: Prefix;
suffix: Suffix;
}

type DefaultPrefix = "{";

type DefaultSuffix = "}";

interface HydrateText {
<
Text extends string,
Prefix extends string = DefaultPrefix,
Suffix extends string = DefaultSuffix,
>(
text: Text,
variables?: Record<GetVariables<Text, Prefix, Suffix>, ValueType>,
interpolationOptions?: InterpolationOptions<Prefix, Suffix>,
): string;
}

interface ConfigureHydrateText {
<
_Prefix extends string = DefaultPrefix,
_Suffix extends string = DefaultSuffix,
>(
interpolationOptions: InterpolationOptions<_Prefix, _Suffix>,
): <
Text extends string,
Prefix extends string = _Prefix,
Suffix extends string = _Suffix,
>(
text: Text,
variables?: Record<GetVariables<Text, Prefix, Suffix>, ValueType>,
interpolationOptions?: InterpolationOptions<Prefix, Suffix>,
) => string;
}

const DEFAULT_INTERPOLATION_OPTIONS: InterpolationOptions<
DefaultPrefix,
DefaultSuffix
> = {
prefix: "{",
suffix: "}",
};

/*
Used to match `RegExp`.
Syntax characters: http://ecma-international.org/ecma-262/7.0/#sec-patterns.
*/
const reRegExpChar = /[\\^$.*+?()[\]{}|]/g;

const reHasRegExpChar = RegExp(reRegExpChar.source);

/*
Source: https://github.com/lodash/lodash/blob/master/escapeRegExp.js
Escapes the `RegExp` special characters "^", "$", "\", ".", "*", "+", "?",
"(", ")", "[", "]", "{", "}", and "|" in `value`.
*/
const escapeRegExp = (value: string): string => {
if (!value || !reHasRegExpChar.test(value)) {
return value;
}

return value.replace(reRegExpChar, "\\$&");
};

/*
Source: https://github.com/lodash/lodash/blob/master/isUndefined.js
Checks if `value` is `undefined`.
*/
const isUndefined = (value: unknown): value is undefined => {
return value === undefined;
};

const hydrateText: HydrateText = (text, variables, interpolationOptions) => {
if (isUndefined(variables)) {
Expand Down Expand Up @@ -48,4 +159,4 @@ export type {
HydrateText,
InterpolationOptions,
ValueType,
} from "./types";
};
3 changes: 1 addition & 2 deletions src/tests/index.errors.ts
@@ -1,5 +1,4 @@
import { configureHydrateText, hydrateText } from "..";
import { InterpolationOptions } from "../types";
import { InterpolationOptions, configureHydrateText, hydrateText } from "..";

// Test Id: 538c85cdc1d3a5cf2ae0077f35e2637b
// THROWS Expected 1-3 arguments, but got 0.
Expand Down
3 changes: 1 addition & 2 deletions src/tests/index.test.ts
@@ -1,8 +1,7 @@
/* eslint-disable @typescript-eslint/ban-ts-comment */
// import crypto from "crypto";

import { configureHydrateText, hydrateText } from "..";
import { InterpolationOptions } from "../types";
import { InterpolationOptions, configureHydrateText, hydrateText } from "..";

// Inspired by: https://stackoverflow.com/a/11869589/11293963
// const getHash = (string: string) =>
Expand Down
3 changes: 1 addition & 2 deletions src/tests/index.types.ts
@@ -1,5 +1,4 @@
import { configureHydrateText, hydrateText } from "..";
import { InterpolationOptions } from "../types";
import { InterpolationOptions, configureHydrateText, hydrateText } from "..";

// Test Id: e3d1bd7920d571fae01eb16c3b8343ba
hydrateText("");
Expand Down
84 changes: 0 additions & 84 deletions src/types.ts

This file was deleted.

34 changes: 0 additions & 34 deletions src/utils.ts

This file was deleted.

11 changes: 10 additions & 1 deletion tsconfig.build.json
@@ -1,8 +1,17 @@
{
"extends": "./tsconfig.json",
"compilerOptions": {
"declaration": true,
"declarationDir": "./dist",
"noEmit": false,
"outDir": "./dist"
},
"exclude": ["**/tests/*.ts", "**/types.ts"]
"exclude": [
"**/tests/*",
/*
Fixes error TS5055 ("Cannot write file '.../dist/index.d.ts' because
it would overwrite input file").
*/
"dist/*"
]
}
2 changes: 1 addition & 1 deletion tsconfig.tslint.json
@@ -1,4 +1,4 @@
{
"extends": "./tsconfig.json",
"exclude": ["src/tests/index.errors.ts"]
"exclude": ["**/*.errors.ts"]
}
10 changes: 0 additions & 10 deletions tsconfig.types.json

This file was deleted.

0 comments on commit 62e4e70

Please sign in to comment.