diff --git a/src/modules/color/index.ts b/src/modules/color/index.ts index 8b5fdba277c..d64b7750545 100644 --- a/src/modules/color/index.ts +++ b/src/modules/color/index.ts @@ -297,7 +297,7 @@ export class Color { let color: string | number[]; let cssFunction: CSSFunction = 'rgb'; if (format === 'hex') { - color = this.faker.datatype.hexadecimal(includeAlpha ? 8 : 6).slice(2); + color = this.faker.datatype.hexadecimal({ length: includeAlpha ? 8 : 6 }); color = formatHexColor(color, options); return color; } diff --git a/src/modules/database/index.ts b/src/modules/database/index.ts index 073d3f8a1dd..5887ab097e5 100644 --- a/src/modules/database/index.ts +++ b/src/modules/database/index.ts @@ -69,7 +69,6 @@ export class Database { * faker.database.mongodbObjectId() // 'e175cac316a79afdd0ad3afb' */ mongodbObjectId(): string { - // strip the "0x" from the hexadecimal output - return this.faker.datatype.hexadecimal(24).replace('0x', '').toLowerCase(); + return this.faker.datatype.hexadecimal({ length: 24, case: 'lower' }); } } diff --git a/src/modules/datatype/index.ts b/src/modules/datatype/index.ts index 347013681b5..671e8c6c53d 100644 --- a/src/modules/datatype/index.ts +++ b/src/modules/datatype/index.ts @@ -1,5 +1,6 @@ import type { Faker } from '../..'; import { FakerError } from '../../errors/faker-error'; +import { deprecated } from '../../internal/deprecated'; /** * Module to generate various primitive values and data types. @@ -187,13 +188,40 @@ export class Datatype { /** * Returns a [hexadecimal](https://en.wikipedia.org/wiki/Hexadecimal) number. * - * @param length Length of the generated number. Defaults to `1`. + * @param options The optional options object. + * @param options.length Length of the generated number. Defaults to `1`. + * @param options.prefix Prefix for the generated number. Defaults to `''`. + * @param options.case Case of the generated number. Defaults to `'mixed'`. * * @example - * faker.datatype.hexadecimal() // '0xb' - * faker.datatype.hexadecimal(10) // '0xaE13F044fb' + * faker.datatype.hexadecimal() // 'B' + * faker.datatype.hexadecimal({ length: 10 }) // 'aE13d044cB' + * faker.datatype.hexadecimal({ prefix: '0x' }) // '0xE' + * faker.datatype.hexadecimal({ case: 'lower' }) // 'f' + * faker.datatype.hexadecimal({ length: 10, prefix: '0x' }) // '0xf12a974eB1' + * faker.datatype.hexadecimal({ length: 10, case: 'upper' }) // 'E3F38014FB' + * faker.datatype.hexadecimal({ prefix: '0x', case: 'lower' }) // '0xd' + * faker.datatype.hexadecimal({ length: 10, prefix: '0x', case: 'mixed' }) // '0xAdE330a4D1' */ - hexadecimal(length = 1): string { + hexadecimal( + options: + | { length?: number; prefix?: string; case?: 'lower' | 'upper' | 'mixed' } + | number = {} + ): string { + if (typeof options === 'number') { + deprecated({ + deprecated: 'faker.datatype.hexadecimal(length)', + proposed: 'faker.datatype.hexadecimal({ length })', + since: '7.5', + until: '8.0', + }); + options = { + length: options, + }; + } + + const { length = 1, prefix = '', case: letterCase = 'mixed' } = options; + let wholeString = ''; for (let i = 0; i < length; i++) { @@ -223,7 +251,13 @@ export class Datatype { ]); } - return `0x${wholeString}`; + if (letterCase === 'upper') { + wholeString = wholeString.toUpperCase(); + } else if (letterCase === 'lower') { + wholeString = wholeString.toLowerCase(); + } + + return `${prefix}${wholeString}`; } /** diff --git a/src/modules/finance/index.ts b/src/modules/finance/index.ts index 7085ea3654c..f1b089e320c 100644 --- a/src/modules/finance/index.ts +++ b/src/modules/finance/index.ts @@ -321,7 +321,11 @@ export class Finance { * faker.finance.ethereumAddress() // '0xf03dfeecbafc5147241cc4c4ca20b3c9dfd04c4a' */ ethereumAddress(): string { - const address = this.faker.datatype.hexadecimal(40).toLowerCase(); + const address = this.faker.datatype.hexadecimal({ + length: 40, + prefix: '0x', + case: 'lower', + }); return address; } diff --git a/test/__snapshots__/datatype.spec.ts.snap b/test/__snapshots__/datatype.spec.ts.snap index e7b8e414320..97f2d4c64e1 100644 --- a/test/__snapshots__/datatype.spec.ts.snap +++ b/test/__snapshots__/datatype.spec.ts.snap @@ -70,9 +70,15 @@ exports[`datatype > 42 > float > with min and max 1`] = `-0.43`; exports[`datatype > 42 > float > with min, max and precision 1`] = `-0.4261`; -exports[`datatype > 42 > hexadecimal > noArgs 1`] = `"0x8"`; +exports[`datatype > 42 > hexadecimal > noArgs 1`] = `"8"`; -exports[`datatype > 42 > hexadecimal > with length 1`] = `"0x8BE4ABdd39321aD7d3fe01FfCE404F4d6db0906bd8"`; +exports[`datatype > 42 > hexadecimal > with casing 1`] = `"8"`; + +exports[`datatype > 42 > hexadecimal > with length 1`] = `"8BE4ABdd39321aD7d3fe01FfCE404F4d6db0906bd8"`; + +exports[`datatype > 42 > hexadecimal > with length, prefix, and casing 1`] = `"0x8be4abdd39321ad7d3fe"`; + +exports[`datatype > 42 > hexadecimal > with prefix 1`] = `"0x8"`; exports[`datatype > 42 > json 1`] = `"{\\"foo\\":79654,\\"bar\\":\\"2eiXX/J/*&\\",\\"bike\\":86617,\\"a\\":60111,\\"b\\":70807,\\"name\\":\\"\\\\\\"&{dnx4!1}\\",\\"prop\\":61748}"`; @@ -180,9 +186,15 @@ exports[`datatype > 1211 > float > with min and max 1`] = `61.07`; exports[`datatype > 1211 > float > with min, max and precision 1`] = `61.0658`; -exports[`datatype > 1211 > hexadecimal > noArgs 1`] = `"0xE"`; +exports[`datatype > 1211 > hexadecimal > noArgs 1`] = `"E"`; + +exports[`datatype > 1211 > hexadecimal > with casing 1`] = `"e"`; + +exports[`datatype > 1211 > hexadecimal > with length 1`] = `"EaDB42F0e3f4A973fAB0AeefCE96DFCF49cD438dF9"`; -exports[`datatype > 1211 > hexadecimal > with length 1`] = `"0xEaDB42F0e3f4A973fAB0AeefCE96DFCF49cD438dF9"`; +exports[`datatype > 1211 > hexadecimal > with length, prefix, and casing 1`] = `"0xeadb42f0e3f4a973fab0"`; + +exports[`datatype > 1211 > hexadecimal > with prefix 1`] = `"0xE"`; exports[`datatype > 1211 > json 1`] = `"{\\"foo\\":\\"Kti5-}$_/\`\\",\\"bar\\":76408,\\"bike\\":35403,\\"a\\":69406,\\"b\\":\\"l\\\\\\"h^]dnwI<\\",\\"name\\":\\"|p|5KWu3/C\\",\\"prop\\":\\"|Jh!E=x\\\\\\"RH\\"}"`; @@ -290,9 +302,15 @@ exports[`datatype > 1337 > float > with min and max 1`] = `-12.92`; exports[`datatype > 1337 > float > with min, max and precision 1`] = `-12.9153`; -exports[`datatype > 1337 > hexadecimal > noArgs 1`] = `"0x5"`; +exports[`datatype > 1337 > hexadecimal > noArgs 1`] = `"5"`; + +exports[`datatype > 1337 > hexadecimal > with casing 1`] = `"5"`; + +exports[`datatype > 1337 > hexadecimal > with length 1`] = `"5c346ba075bd57F5A62B82d72AF39CBBB07a98cbA8"`; + +exports[`datatype > 1337 > hexadecimal > with length, prefix, and casing 1`] = `"0x5c346ba075bd57f5a62b"`; -exports[`datatype > 1337 > hexadecimal > with length 1`] = `"0x5c346ba075bd57F5A62B82d72AF39CBBB07a98cbA8"`; +exports[`datatype > 1337 > hexadecimal > with prefix 1`] = `"0x5"`; exports[`datatype > 1337 > json 1`] = `"{\\"foo\\":56052,\\"bar\\":21258,\\"bike\\":54308,\\"a\\":3397,\\"b\\":23538,\\"name\\":\\"X9@{:e=+kD\\",\\"prop\\":62850}"`; diff --git a/test/datatype.spec.ts b/test/datatype.spec.ts index 56d4ea17f27..a57139fdd0c 100644 --- a/test/datatype.spec.ts +++ b/test/datatype.spec.ts @@ -59,7 +59,15 @@ describe('datatype', () => { t.itRepeated('boolean', 5); t.describe('hexadecimal', (t) => { - t.it('noArgs').it('with length', 42); + t.it('noArgs') + .it('with length', { length: 42 }) + .it('with prefix', { prefix: '0x' }) + .it('with casing', { case: 'lower' }) + .it('with length, prefix, and casing', { + length: 20, + prefix: '0x', + case: 'lower', + }); }); t.it('json'); @@ -323,14 +331,36 @@ describe('datatype', () => { describe('hexadecimal', () => { it('generates single hex character when no additional argument was provided', () => { const hex = faker.datatype.hexadecimal(); - expect(hex).toMatch(/^(0x)[0-9a-f]{1}$/i); - expect(hex.substring(2)).toHaveLength(1); + expect(hex).toMatch(/^[0-9a-f]{1}$/i); + expect(hex).toHaveLength(1); + }); + + it('generates a random hex string with a provided length', () => { + const hex = faker.datatype.hexadecimal({ length: 5 }); + expect(hex).toMatch(/^[0-9a-f]+$/i); + expect(hex).toHaveLength(5); }); - it('generates a random hex string', () => { - const hex = faker.datatype.hexadecimal(5); - expect(hex).toMatch(/^(0x)[0-9a-f]+$/i); - expect(hex.substring(2)).toHaveLength(5); + it('generates a hex string with a provided prefix', () => { + const hex = faker.datatype.hexadecimal({ prefix: '0x' }); + expect(hex).toMatch(/^(0x)[0-9A-F]+$/i); + expect(hex).toHaveLength(3); + }); + + it('generates a hex string with a provided casing', () => { + const hex = faker.datatype.hexadecimal({ case: 'lower' }); + expect(hex).toMatch(/^[0-9a-f]+$/i); + expect(hex).toHaveLength(1); + }); + + it('generates a hex string with a provided prefix, length, and casing', () => { + const hex = faker.datatype.hexadecimal({ + prefix: '0x', + length: 7, + case: 'upper', + }); + expect(hex).toMatch(/^(0x)[0-9A-F]+$/i); + expect(hex.substring(2)).toHaveLength(7); }); });