The first time random numbers bit me was on a Laravel side project years before I started building toolz.dev. I needed short referral codes, reached for rand() because it was right there, and shipped it. A week later two users had the same code. Not because the odds were astronomical, but because I had misunderstood what rand() actually promised. That small embarrassment taught me a lesson I have carried into every tool on toolz.dev: "random" is not one thing. There is the casual random that is fine for a dice roll, and there is the serious random you need the moment a value guards anything.
This guide is the long version of what I wish someone had told me back then. I will walk through how to generate random numbers with the Random Number Generator on toolz.dev, when unique-only sets matter, why the source of randomness changes what you can safely use the output for, and the practical cases where I reach for it while building.
TL;DR: A random number generator draws values from a range you define. Set a minimum and maximum, pick how many numbers you want, and choose integers or decimals. Turn on unique-only when no value may repeat, which is what you want for lotteries, raffles, and sampling without replacement. The toolz.dev generator runs entirely in your browser and prefers the Web Crypto API for its randomness, so nothing you generate ever leaves your device.
What does a random number generator actually do?
A random number generator maps an unpredictable source of bits onto a range. That is the whole job. In a browser the source that matters is crypto.getRandomValues(), which the Web Cryptography API requires to be cryptographically strong - unlike Math.random(), which makes no such promise. You tell it the interval, say 1 to 100, and it returns a value from inside that interval where, ideally, every value has an equal chance of appearing. Ask for more than one and it repeats the draw.
The interesting part is the word "unpredictable," because computers are deterministic machines that do not naturally produce surprise. What they produce is pseudo-randomness: a sequence that looks random and passes statistical tests but is generated by an algorithm from a starting seed. Give the same algorithm the same seed and you get the same sequence every time. That reproducibility is a feature when you are writing a test that needs to be repeatable, and a liability when you are minting something that must be unguessable.
On toolz.dev the generator sits in the browser and reads its bits from crypto.getRandomValues when the browser exposes it, which every modern browser does. That function is defined by the W3C Web Cryptography API and is backed by the operating system's cryptographically secure source. When that source is present, the numbers are unpredictable enough for security-adjacent work like picking tokens or shuffling a deck. When it is somehow unavailable, the tool falls back to the standard JavaScript generator, which is fine for games and sampling but should never seed anything secret. Knowing which of those two worlds you are in is the single most important thing about using any RNG well.
How do I generate random numbers on toolz.dev?
The flow is deliberately short because most of the time you just want a number and you want it now.
First, set the range. Enter the minimum and the maximum. For integers the range is inclusive on both ends, so 1 to 6 can return any of 1, 2, 3, 4, 5, or 6, exactly like a die. Negative values and ranges that span zero, such as -50 to 50, work the same way.
Second, choose how many numbers you want. One number for a quick pick, or a batch of up to ten thousand when you are seeding test data or building a sample.
Third, pick the options. Leave "integers only" on for whole numbers, or turn it off and set the number of decimal places when you need fractional values. Turn on "unique values only" when no number may repeat.
Finally, click Generate. The result shows the list along with the sum and the average, and the whole batch copies as a newline-separated list so it drops straight into a spreadsheet column, a script, or a test fixture. If you have used the UUID Generator or the Password Generator on toolz.dev, the shape of this will feel familiar, because I try to keep the generators consistent.
When should I use unique-only numbers?
This is the option people miss, and it is the one that changes the math the most.
By default the generator draws with replacement. Every draw is independent, so a number can appear more than once in the same batch. That is correct for rolling dice, because a real pair of dice can absolutely come up with two fours. But it is wrong for a lottery draw, a raffle, or any time you are choosing a sample without putting the token back in the bag.
Turn on unique-only and the generator draws without replacement. It keeps a record of what it has already produced and skips repeats until it has filled your batch. The classic use is lottery numbers: if you want six numbers from 1 to 49 with no duplicates, unique-only is the difference between a valid ticket and a broken one.
There is a natural limit here, and the tool respects it. You cannot draw more unique integers than the range can hold. Ask for ten unique numbers between 1 and 5 and there is no valid answer, because only five distinct integers exist in that interval. Rather than spinning forever trying to find a sixth impossible value, the generator stops and tells you the range is too small. I built that guard in on purpose after watching too many naive shuffle loops hang in production code.
Integers or decimals: which do I need?
Integers cover most requests. Dice, lottery balls, array indices, and record counts are all whole numbers, and integer mode gives you an inclusive range that matches how people think about those things.
Decimals are for continuous quantities: a random price, a simulated sensor reading, a weight, a probability. Turn off integer mode and the tool draws from the half-open interval that includes the minimum but not the maximum. That half-open convention, minimum included and maximum excluded, is the same one that underlies almost every floating-point RNG in every language, including JavaScript's own Math.random, which returns a value in the range from 0 up to but not including 1. Matching that convention means the numbers you get here behave like the numbers you would get in code.
You also control the number of decimal places, from one to ten. Two places is right for currency-like values, more when you are simulating measurements that need finer resolution. Keep in mind that unique-only plus decimals is almost always satisfiable because the space of distinct decimals is enormous, whereas unique-only plus a tiny integer range is where you hit the wall described above.
How random is "random enough"?
Here is the table I wish I had seen before that referral-code incident. It maps the common use cases to the kind of randomness they actually require.
| Use case | Randomness needed | Repeats allowed? | Notes |
|---|---|---|---|
| Dice, board games | Pseudo-random is fine | Yes | Independence per roll is the point |
| Picking a random winner | Cryptographic preferred | No (unique-only) | Fairness matters, use unique-only |
| Lottery or raffle numbers | Cryptographic preferred | No (unique-only) | Draw without replacement |
| Sampling rows for analysis | Pseudo-random is fine | Usually no | Unique-only for sampling without replacement |
| Seeding test fixtures | Pseudo-random is fine | Yes | Reproducibility can even be desirable |
| Security tokens, secrets | Cryptographic required | No | Never use a plain PRNG here |
The row that trips people up is "security tokens." A general-purpose RNG, even a good one, is not a substitute for a purpose-built secret generator. If you are creating an API key, a session token, or a password, use a tool designed for that job, like the Password Generator, or a hashing tool like the Hash Generator when you need a fixed-length digest. The random number generator is for numbers in a range, not for cryptographic key material, and the honest framing of that boundary is more useful than pretending one tool does everything.
What can I actually build with it?
A few of the ways this earns its place in my workflow.
When I am testing a UI that renders lists, I generate a batch of a few hundred numbers to stand in for quantities, prices, or scores, paste them into a fixture, and suddenly the layout is exercised with realistic variety instead of the same three hand-typed rows. For WordPress work on WP Adminify I have used random values to populate demo content so a settings screen looks alive in a screenshot.
When a client runs a giveaway, unique-only mode picks winners fairly from a numbered list of entrants. Assign each entrant a number, draw as many unique winners as there are prizes, done. No spreadsheet formula, no argument about whether the draw was rigged, because the numbers came from a source neither of us controls.
For quick statistical intuition, generating a large batch and glancing at the sum and average is a fast sanity check that the range and distribution are behaving. If I ask for numbers from 1 to 100 and the average comes back near 50, the world is as expected.
And for the everyday stuff, it is a dice roller, a coin flip when you treat 1 and 2 as heads and tails, and a "pick a number" settler of small arguments. Not every use has to be serious to be useful.
How does this compare to writing your own?
You could write Math.floor(Math.random() * (max - min + 1)) + min and be done. I have written that line a thousand times. So why reach for a tool?
Two reasons, both learned the hard way. The first is the off-by-one and modulo-bias mistakes that creep into hand-rolled range math, especially once you add the inclusive-versus-exclusive boundary and the unique-only requirement. The tool handles the edge cases, including the "you asked for more unique values than exist" case, so you do not rediscover them at 2am. The second is that Math.random is explicitly not cryptographically secure, a fact the MDN documentation states plainly, and it is easy to forget that when you paste a snippet into code that later guards something real. The toolz.dev generator defaults to the crypto source, so the safer behavior is the one you get without thinking about it.
For a one-off number in an environment you control, a snippet is fine. For repeatable draws, unique sets, batches you want to copy, or anything where you want the crypto source by default, the tool saves the fiddly parts.
If your work leans more toward encoding and formatting than number generation, the same client-side philosophy runs through the rest of the toolbox, from the Lorem Ipsum generator for placeholder text to the wider set covered in the developer productivity tools guide. And because every one of these runs locally, the data privacy story is the same across all of them: your inputs stay in your browser.
What are the common mistakes people make with random numbers?
After years of reviewing code, mine and other people's, the same handful of mistakes show up again and again, and they are worth naming so you can avoid them.
The first is confusing "unlikely" with "impossible." My referral-code story is exactly this. When you draw with replacement from a range, collisions are not a bug, they are a statistical certainty given enough draws. The birthday paradox is the classic illustration: in a group of just 23 people the chance of two sharing a birthday is over 50 percent, far higher than intuition suggests, because you are comparing every pair, not comparing everyone to one fixed date. If your values must be unique, do not hope the range is big enough. Turn on unique-only and remove the doubt.
The second is reaching for the wrong source. Plenty of tutorials show a range formula built on Math.random and never mention that it is unsuitable for anything security-sensitive. The value looks random, the demo works, and the habit sticks. Then someone copies that snippet into code that generates a password reset token, and now the "random" token is predictable to anyone who understands the underlying algorithm. The rule is blunt: if a human should never be able to guess the value, it needs a cryptographic source. The toolz.dev generator defaults to that source, which is the safer default to build a habit around.
The third is off-by-one errors at the range boundaries. Inclusive versus exclusive endpoints trip up even experienced developers, because different languages and different functions make different choices. Is 100 a possible output when I ask for 1 to 100? For integers here, yes, both ends are included. For decimals the maximum is excluded, matching the floating-point convention. Being explicit about which convention applies prevents the quiet bug where your dice never roll a six because you wrote < max instead of <= max.
The fourth is assuming a small sample looks random. True randomness produces clumps and streaks. Flip a fair coin ten times and a run of four heads is completely normal, yet people see it and assume the coin, or the generator, is broken. Randomness is not the same as even spacing. If you want evenly spaced values, you do not want a random number generator at all, you want a sequence. Knowing which one you actually need is half the battle.
Frequently asked questions
How does a random number generator work?
A random number generator maps an unpredictable source of bits onto the range you choose. This tool reads bytes from the Web Crypto API when it is available and scales them into your minimum-to-maximum interval, so each value in the range has an equal chance of being drawn.
Are the numbers truly random?
They are cryptographically strong pseudo-random numbers, which are unpredictable for all practical purposes. When the browser exposes crypto.getRandomValues the output is suitable for tokens and shuffling; if only the standard generator is available the values are still well-distributed but should not be used for secrets.
How do I generate unique random numbers with no repeats?
Enable the unique-only option before generating. The tool then draws without replacement, so every number in the batch is different. If you ask for more unique integers than the range can hold, it tells you instead of looping forever.
Can it generate decimal numbers?
Yes. Turn off the integer option and set how many decimal places you want. Decimals are drawn from the half-open interval that includes the minimum but not the maximum, which is the standard convention for continuous ranges.
Can I use negative numbers?
Yes. Enter a negative minimum, a negative maximum, or a range that spans zero, such as -50 to 50. The generator handles negative and mixed ranges the same way it handles positive ones.
How many numbers can I generate at once?
Up to 10,000 numbers per batch. The result includes the sum and average so you can sanity-check large batches at a glance, and the whole list copies as newline-separated values.
Is this random number generator free and private?
Yes. It is free with no signup and no usage cap, and every number is generated in your browser. No range, count, or result is ever transmitted to a server.
What can I use a random number generator for?
Common uses include picking lottery or raffle numbers, rolling dice for games, choosing a random winner, seeding test data, sampling rows for analysis, and randomizing the order of a list. Unique-only mode covers any case that needs sampling without repeats.



