Skip to content

Commit

Permalink
Add numberSelector utility (#1126)
Browse files Browse the repository at this point in the history
  • Loading branch information
trivikr authored Dec 28, 2023
1 parent 2df620b commit dd2b9c7
Show file tree
Hide file tree
Showing 7 changed files with 65 additions and 5 deletions.
5 changes: 5 additions & 0 deletions .changeset/forty-stingrays-lay.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
---
"@smithy/util-config-provider": minor
---

Add numberSelector utility
3 changes: 2 additions & 1 deletion packages/util-config-provider/src/booleanSelector.spec.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
import { booleanSelector, SelectorType } from "./booleanSelector";
import { booleanSelector } from "./booleanSelector";
import { SelectorType } from "./types";

describe(booleanSelector.name, () => {
const key = "key";
Expand Down
5 changes: 1 addition & 4 deletions packages/util-config-provider/src/booleanSelector.ts
Original file line number Diff line number Diff line change
@@ -1,7 +1,4 @@
export enum SelectorType {
ENV = "env",
CONFIG = "shared config entry",
}
import { SelectorType } from "./types";

/**
* Returns boolean value true/false for string value "true"/"false",
Expand Down
2 changes: 2 additions & 0 deletions packages/util-config-provider/src/index.ts
Original file line number Diff line number Diff line change
@@ -1 +1,3 @@
export * from "./booleanSelector";
export * from "./numberSelector";
export * from "./types";
32 changes: 32 additions & 0 deletions packages/util-config-provider/src/numberSelector.spec.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
import { numberSelector } from "./numberSelector";
import { SelectorType } from "./types";

describe(numberSelector.name, () => {
const key = "key";
const obj: { [key]: any } = {} as any;

describe.each(Object.entries(SelectorType))(`Selector %s`, (selectorKey, selectorValue) => {
beforeEach(() => {
delete obj[key];
});

it(`should return undefined if ${key} is not defined`, () => {
expect(numberSelector(obj, key, SelectorType[selectorKey])).toBeUndefined();
});

it.each([
[0, "0"],
[1, "1"],
])(`should return number %s if ${key}="%s"`, (output, input) => {
obj[key] = input;
expect(numberSelector(obj, key, SelectorType[selectorKey])).toBe(output);
});

it.each(["yes", "no", undefined, null, void 0, ""])(`should throw if ${key}=%s`, (input) => {
obj[key] = input;
expect(() => numberSelector(obj, key, SelectorType[selectorKey])).toThrow(
new TypeError(`Cannot load ${selectorValue} '${key}'. Expected number, got '${obj[key]}'.`)
);
});
});
});
19 changes: 19 additions & 0 deletions packages/util-config-provider/src/numberSelector.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
import { SelectorType } from "./types";

/**
* Returns number value for string value, if the string is defined in obj[key].
* Returns undefined, if obj[key] is not defined.
* Throws error for all other cases.
*
* @internal
*/
export const numberSelector = (obj: Record<string, string | undefined>, key: string, type: SelectorType) => {
if (!(key in obj)) return undefined;

const numberValue = parseInt(obj[key] as string, 10);
if (Number.isNaN(numberValue)) {
throw new TypeError(`Cannot load ${type} '${key}'. Expected number, got '${obj[key]}'.`);
}

return numberValue;
};
4 changes: 4 additions & 0 deletions packages/util-config-provider/src/types.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
export enum SelectorType {
ENV = "env",
CONFIG = "shared config entry",
}

0 comments on commit dd2b9c7

Please sign in to comment.