Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat(number): add binary and octal random number generation #1708

Merged
56 changes: 56 additions & 0 deletions src/modules/number/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -205,4 +205,60 @@ export class NumberModule {

return min + offset;
}

/**
* Returns a [binary](https://en.wikipedia.org/wiki/Binary_number) number.
*
* @param options Maximum value or options object. Defaults to `{}`.
* @param options.min Lower bound for generated number. Defaults to `0`.
* @param options.max Upper bound for generated number. Defaults to `1`.
*
* @throws When options define `max < min`.
*
* @example
* faker.number.binary() // '1'
* faker.number.binary(255) // '110101'
* faker.number.binary({ min: 0, max: 65535 }) // '10110101'
*
* @since 8.0.0
*/
binary(options: number | { min?: number; max?: number } = {}): string {
if (typeof options === 'number') {
options = { max: options };
}
const { min = 0, max = 1 } = options;

return this.int({
max,
min,
}).toString(2);
}

/**
* Returns an [octal](https://en.wikipedia.org/wiki/Octal) number.
*
* @param options Maximum value or options object. Defaults to `{}`.
* @param options.min Lower bound for generated number. Defaults to `0`.
* @param options.max Upper bound for generated number. Defaults to `7`.
*
* @throws When options define `max < min`.
*
* @example
* faker.number.octal() // '5'
* faker.number.octal(255) // '377'
* faker.number.octal({ min: 0, max: 65535 }) // '4766'
*
* @since 8.0.0
*/
octal(options: number | { min?: number; max?: number } = {}): string {
if (typeof options === 'number') {
options = { max: options };
}
const { min = 0, max = 7 } = options;

return this.int({
max,
min,
}).toString(8);
}
}
36 changes: 36 additions & 0 deletions test/__snapshots__/number.spec.ts.snap
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,12 @@ exports[`number > 42 > bigInt > with options 1`] = `1n`;

exports[`number > 42 > bigInt > with string value 1`] = `37n`;

exports[`number > 42 > binary > noArgs 1`] = `"0"`;

exports[`number > 42 > binary > with options 1`] = `"100"`;

exports[`number > 42 > binary > with value 1`] = `"0"`;

exports[`number > 42 > float > with max 1`] = `25.84`;

exports[`number > 42 > float > with min 1`] = `-25.9`;
Expand All @@ -36,6 +42,12 @@ exports[`number > 42 > int > with options 1`] = `4`;

exports[`number > 42 > int > with value 1`] = `0`;

exports[`number > 42 > octal > noArgs 1`] = `"2"`;

exports[`number > 42 > octal > with options 1`] = `"4"`;

exports[`number > 42 > octal > with value 1`] = `"0"`;

exports[`number > 1211 > bigInt > noArgs 1`] = `948721906162743n`;

exports[`number > 1211 > bigInt > with big options 1`] = `22017767508700414061739128n`;
Expand All @@ -50,6 +62,12 @@ exports[`number > 1211 > bigInt > with options 1`] = `10n`;

exports[`number > 1211 > bigInt > with string value 1`] = `24n`;

exports[`number > 1211 > binary > noArgs 1`] = `"1"`;

exports[`number > 1211 > binary > with options 1`] = `"1010"`;

exports[`number > 1211 > binary > with value 1`] = `"1"`;

exports[`number > 1211 > float > with max 1`] = `64.07`;

exports[`number > 1211 > float > with min 1`] = `-2.07`;
Expand All @@ -72,6 +90,12 @@ exports[`number > 1211 > int > with options 1`] = `10`;

exports[`number > 1211 > int > with value 1`] = `1`;

exports[`number > 1211 > octal > noArgs 1`] = `"7"`;

exports[`number > 1211 > octal > with options 1`] = `"12"`;

exports[`number > 1211 > octal > with value 1`] = `"1"`;

exports[`number > 1337 > bigInt > noArgs 1`] = `251225403255239n`;

exports[`number > 1337 > bigInt > with big options 1`] = `31258255497061442772623668n`;
Expand All @@ -86,6 +110,12 @@ exports[`number > 1337 > bigInt > with options 1`] = `-15n`;

exports[`number > 1337 > bigInt > with string value 1`] = `25n`;

exports[`number > 1337 > binary > noArgs 1`] = `"0"`;

exports[`number > 1337 > binary > with options 1`] = `"10"`;

exports[`number > 1337 > binary > with value 1`] = `"0"`;

exports[`number > 1337 > float > with max 1`] = `18.08`;

exports[`number > 1337 > float > with min 1`] = `-30.74`;
Expand All @@ -107,3 +137,9 @@ exports[`number > 1337 > int > noArgs 1`] = `2360108468142080`;
exports[`number > 1337 > int > with options 1`] = `2`;

exports[`number > 1337 > int > with value 1`] = `0`;

exports[`number > 1337 > octal > noArgs 1`] = `"2"`;

exports[`number > 1337 > octal > with options 1`] = `"2"`;

exports[`number > 1337 > octal > with value 1`] = `"0"`;
70 changes: 69 additions & 1 deletion test/number.spec.ts
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,9 @@ describe('number', () => {
seededTests(faker, 'number', (t) => {
t.describeEach(
'int',
'hex'
'hex',
'binary',
'octal'
ST-DDT marked this conversation as resolved.
Show resolved Hide resolved
)((t) => {
t.it('noArgs')
.it('with value', 1)
Expand Down Expand Up @@ -348,5 +350,71 @@ describe('number', () => {
);
});
});

describe('binary', () => {
it('generates single binary character when no additional argument was provided', () => {
const binary = faker.number.binary();
expect(binary).toBeTypeOf('string');
expect(binary).toHaveLength(1);
expect(/^[01]+$/.test(binary)).toBe(true);
ST-DDT marked this conversation as resolved.
Show resolved Hide resolved
});

it('generates a random binary string', () => {
ST-DDT marked this conversation as resolved.
Show resolved Hide resolved
const binary = faker.number.binary(5);
const binaryNum = parseInt(binary, 2);
expect(binaryNum).toBeLessThanOrEqual(5);
expect(/^[01]+$/.test(binary)).toBe(true);
});

it('generates a random binary in a specific range', () => {
const binary = faker.number.binary({ min: 15, max: 255 });

const binaryNum = parseInt(binary, 2);
expect(binaryNum).toBeLessThanOrEqual(255);
expect(binaryNum).greaterThanOrEqual(15);
});

it('should throw when min > max', () => {
const min = 10;
const max = 9;

expect(() => {
faker.number.binary({ min, max });
}).toThrowError(`Max ${max} should be greater than min ${min}.`);
});
});

describe('octal', () => {
it('generates single octal character when no additional argument was provided', () => {
const octal = faker.number.octal();
expect(octal).toBeTypeOf('string');
expect(octal).toHaveLength(1);
expect(/^[0-7]+$/.test(octal)).toBe(true);
});

it('generates a random octal string', () => {
ST-DDT marked this conversation as resolved.
Show resolved Hide resolved
const octal = faker.number.octal(5);
const octalNum = parseInt(octal, 8);
expect(octalNum).toBeLessThanOrEqual(5);
expect(/^[0-7]+$/.test(octal)).toBe(true);
});

it('generates a random octal in a specific range', () => {
const octal = faker.number.octal({ min: 15, max: 255 });

const octalNum = parseInt(octal, 8);
expect(octalNum).toBeLessThanOrEqual(255);
expect(octalNum).greaterThanOrEqual(15);
});

it('should throw when min > max', () => {
const min = 10;
const max = 9;

expect(() => {
faker.number.octal({ min, max });
}).toThrowError(`Max ${max} should be greater than min ${min}.`);
});
});
});
});