Pre-request Scripts

Everything so far — the Tests tab, chained variables — runs after a response arrives. Postman also lets you run JavaScript before the request is even sent, in the Pre-request Script tab (or Scripts → Pre-request in newer versions). This is where you compute values a request needs at send-time: a timestamp that has to be "now," a random string, or a token that was fetched earlier. This lesson uses it to fix a real problem with testing POST /recipes repeatedly against the RecipeBox API.

The Problem: Colliding Test Data

Imagine Create Recipe always sends the same hardcoded body:

{
  "title": "Test Recipe",
  "ingredients": ["Paneer", "Butter", "Tomato"],
  "steps": ["Marinate", "Cook", "Serve"],
  "category": "Dinner",
  "prepMinutes": 20,
  "isPublished": false
}

Run this collection five times and RecipeBox now has five identical recipes titled "Test Recipe". If the API enforces unique titles per user, the second run fails outright with a 409 Conflict that has nothing to do with the thing you're actually testing. Even if titles aren't unique, dev environments fill up with junk data that makes other tests (like Search Recipes) unreliable.

Generating a Unique Title

Open Create Recipe's Pre-request Script tab and generate a title that's different every single run:

// Pre-request Script — runs before this request is sent
var uniqueTitle = "Test Recipe " + Date.now();
pm.variables.set("recipeTitle", uniqueTitle);

Date.now() returns the current time in milliseconds, so uniqueTitle comes out looking like "Test Recipe 1734781204213" — different on every run, virtually guaranteed not to collide. pm.variables.set() stores it as a local variable available for the rest of this request's lifecycle. Then reference it in the request body:

{
  "title": "{{recipeTitle}}",
  "ingredients": ["Paneer", "Butter", "Tomato"],
  "steps": ["Marinate", "Cook", "Serve"],
  "category": "Dinner",
  "prepMinutes": 20,
  "isPublished": false
}

Every time you click Send, the pre-request script runs first, computes a fresh recipeTitle, and the body is built with that value substituted in — no more collisions.

Other Common Uses

Use casePre-request script
Dynamic timestamp for a field like createdAt pm.variables.set("now", new Date().toISOString());
Random string for a unique test user or search query pm.variables.set("randomTag", Math.random().toString(36).slice(2, 8));
Setting an auth token programmatically before it exists yet See below

Setting an Auth Token Programmatically

A pre-request script can also reach for a collection variable that a previous request (like Login) already stored, and copy it wherever the current request needs it — for example into a header that Postman's Auth tab doesn't cover automatically:

// Pre-request Script on Create Recipe
var token = pm.collectionVariables.get("token");
pm.request.headers.add({
  key: "Authorization",
  value: "Bearer " + token
});

This is more manual than the built-in Auth tab (covered next lesson) but shows what's happening underneath it — and it's the pattern you'd reach for if a token needed extra processing, like adding a custom prefix or refreshing it only when it's close to expiring.

Note: A collection can also have a collection-level Pre-request Script (set on the collection itself, in its Scripts tab) that runs before every request inside it — useful for something every RecipeBox request needs, like always attaching a X-Client-Version header, instead of pasting the same snippet into every single request.
Next: Manually attaching an Authorization header from a script works, but Postman has dedicated support for this. Authentication covers Basic Auth, Bearer Tokens, and API Keys — including Postman's built-in Auth tab and a full RecipeBox login flow.