WeCodeAcademy

Step 2: Short, unique ids

The short code is the heart of the service. Random ids from crypto.randomBytes are hard to guess, so people cannot discover other people's links by counting. With 62 possible characters (a-z, A-Z, 0-9) and 6 positions there are over 56 billion ids. Collisions are unlikely but possible, so keep drawing until you find an unused one. A base-62 counter also works and is shorter, but it is guessable and reveals how many links exist.

ExampleNode.js
const crypto = require("crypto");

const ALPHABET = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789";

function randomId(length = 6) {
  const bytes = crypto.randomBytes(length);
  let id = "";
  for (const b of bytes) id += ALPHABET[b % ALPHABET.length];
  return id;
}

const id = randomId();
console.log(id.length, /^[A-Za-z0-9]{6}$/.test(id));

// How many different 6-character ids exist?
console.log(62 ** 6);
// A different idea: encode a counter in base 62 (short, unique, but guessable)
function toBase62(n) {
  if (n === 0) return "0";
  let out = "";
  while (n > 0) {
    out = ALPHABET[n % 62] + out;
    n = Math.floor(n / 62);
  }
  return out;
}
console.log(toBase62(1), toBase62(61), toBase62(62), toBase62(125000));

// Avoid collisions: keep trying until the id is unused
const used = new Set(["abc123"]);
function uniqueId() {
  let candidate;
  do { candidate = randomId(); } while (used.has(candidate));
  used.add(candidate);
  return candidate;
}
console.log(used.has(uniqueId()), used.size);
Output
6 true
56800235584
b 9 ba GGi
true 2

Use crypto.randomBytes rather than Math.random() for anything security-related: Math.random() is predictable.

Quick check

Why prefer random ids over a simple counter?

Finish the quick check (and any code exercise) to complete this lesson, or mark it done yourself.

Tip: use the left and right arrow keys to move between lessons.