How to Test a REST API in the Browser Without Postman

How to test an API without Postman: curl, Bruno, Hoppscotch, VS Code clients and browser testers compared, plus CORS, proxies, auth headers and OpenAPI specs.

On this page

You can test an API without Postman using tools you already have. For a single call, curl in a terminal or fetch() in the browser console is enough. If the API has an OpenAPI or Swagger spec, a browser-based tester that reads the spec is faster still, because it builds each request from the documented paths, parameters and auth for you. Browser testers have one catch: CORS can block the call, so the good ones route the request through a server-side proxy when that happens. This guide compares the options, explains the CORS problem and how proxies work around it, and walks through testing one endpoint from a spec.

When Postman is more than you need

Postman is built for teams that keep shared collections, environments, mock servers and monitors in one workspace. If that describes your week, keep using it. Many API checks are smaller than that:

  • You want to see what one endpoint returns before you write the frontend code that calls it.
  • A teammate sent a Swagger UI link and you need to confirm the staging API answers with the fields the docs promise.
  • You are on a locked-down work laptop where installing a desktop app means a ticket to IT.
  • You are reproducing a bug report and need the exact status code and headers, once.
  • You would rather not sign in to a cloud account to send a GET request.

For these jobs the cost of Postman is setup: installing the app, signing in, creating a workspace, and then typing in a URL, headers and body by hand. Recent Postman versions push you toward an account, and the features available while signed out have changed more than once, so check the current terms if that matters to you.

The options, compared

Each tool below can send an HTTP request and show you the response. They differ in where they run, whether they ask for an account, and whether they can read an OpenAPI spec. Pricing and login rules change often, so treat the account column as a starting point and confirm on each project's site.

ToolRuns inAccount to startImports OpenAPIGood fit
Browser DevTools fetch()Any browser consoleNoneNoA quick call to an API on the same origin as the open page
curlTerminal (ships with macOS, most Linux distros and Windows 10+)NoneNoOne-off calls, scripts, sharing an exact repro
HTTPieTerminal (open-source CLI); also desktop and web appsNone for the CLIVaries by appReadable command-line requests with JSON shortcuts
BrunoDesktop app (open source)None for the core appYesCollections stored as plain files in your Git repo
HoppscotchBrowser (hosted or self-hosted), also desktopNone for basic useYesA Postman-style interface in a browser tab
InsomniaDesktop appHas varied by version; local-only storage is availableYesTeams already on Kong tooling
VS Code REST ClientVS Code extensionNoneNoRequests saved as .http files next to your code
Thunder ClientVS Code extensionSome features are on paid plansYesA GUI client without leaving the editor
APIForgeBrowserNoneYes, it starts from the specTesting endpoints straight from an OpenAPI or Swagger URL, with response validation
Account requirements and plans change. Check each tool's current docs before you standardize on one.

If you live in a terminal, curl and HTTPie are hard to beat for single calls. If you want saved collections under version control, Bruno and the VS Code REST Client keep requests as files you can commit. Hoppscotch is the closest thing to Postman in a browser tab. APIForge covers a narrower job: you have a spec, and you want to call its endpoints and check the responses against it without building each request yourself.

The same request in three tools

Shellcurl and HTTPie
# curl
curl -i https://api.example.com/v1/users/42 \
  -H "Authorization: Bearer $TOKEN" \
  -H "Accept: application/json"

# HTTPie
http GET https://api.example.com/v1/users/42 \
  "Authorization:Bearer $TOKEN" Accept:application/json
HTTPusers.http (VS Code REST Client)
@token = paste-a-test-token-here

GET https://api.example.com/v1/users/42
Authorization: Bearer {{token}}
Accept: application/json

All three are fine for one endpoint you already know. The work grows with the API: for a spec with 60 operations you still have to read the docs for each path, its parameters and its body shape, then type them in.

Why browser-based testers hit CORS

A request sent from JavaScript on a web page follows the browser's same-origin policy. When a page on one origin calls an API on another, the browser sends the request (or first an OPTIONS preflight) and only hands the response to the page if the API replies with matching Access-Control-Allow-Origin and related headers. curl, HTTPie, Bruno and the VS Code extensions never run into this, because they are not web pages.

Many APIs send no CORS headers at all, since their real clients are servers or mobile apps. Others allow only their own frontend's origin. Either way, an online API tester running in your browser gets the same opaque "Failed to fetch" error that Swagger UI shows. A request with an Authorization header or a JSON body makes it more likely, because it triggers a preflight that the server must also answer.

Using the console without a CORS error

JavaScript
// Open DevTools on a page served from api.example.com itself,
// for example its /docs or /health page, then run:
const res = await fetch("/v1/users/42", {
  headers: { Authorization: "Bearer TEST_TOKEN" },
});
console.log(res.status, await res.json());

A request from a page to its own origin is same-origin, so CORS does not apply. Running fetch() from a tab on a different site, such as a blank tab or another app, will be blocked unless the API allows that origin.

There are three common ways around it. You can fix the API's CORS configuration, which is the right answer for your own frontend but needs server access. You can install a browser extension that sends requests outside the page's sandbox; Hoppscotch offers this as one of its options. Or the tester can send the request from its own server, where the browser's rules do not apply.

How a proxy gets around CORS, and what it costs

TextDirect browser request vs proxy fallback
Direct:   browser page  --->  api.example.com
                          <---  response without CORS headers
          browser blocks the response ("Failed to fetch")

Proxy:    browser page  --->  tester's server  --->  api.example.com
                                               <---  response
          browser page  <---  tester's server (same origin, allowed)

Browsers enforce CORS, and a server calling an API skips the check entirely. The page sends the request description (method, URL, headers, body) to the tester's own backend, which is the same origin as the page. That backend calls the API, reads the response and passes it back.

In APIForge, the request panel has three modes. Browser sends the request with fetch() straight from your tab. Proxy always sends it from APIForge's server through the /api/test-request endpoint. Auto, the default, tries the browser first and retries through the proxy only when the browser reports a CORS or network error. A timeout does not trigger the fallback.

The trade-offs are real, and they apply to any proxy-based tester:

  • Your headers, including any token, pass through the tester's server. Use a test or staging token, and avoid production credentials.
  • A hosted proxy cannot reach an API that only exists on your machine, such as http://localhost:3000. For that, use Browser mode with CORS enabled locally, or a terminal tool.
  • Proxies have limits. APIForge's caps each request at a 30-second timeout, a 2 MB request body, a 5 MB response and 3 redirects, with 60 requests per minute per client. It also checks each destination and redirect target before connecting and drops credential headers when a redirect leaves the original origin.
  • A proxy only tells you the API works. Your own frontend will still be blocked until the API sends the right CORS headers.

If Swagger UI shows Failed to fetch and you want to know which header is missing, the Swagger UI Failed to fetch guide covers each cause and its server fix.

Testing from an OpenAPI spec vs building requests by hand

A spec already describes every operation: the path, the method, which parameters are required, the request body schema, the auth scheme and the response schemas for each status code. A tool that reads it can fill in the request form and then check the response you get back.

Hand-built requests vs spec-driven requests

TaskHand-built (curl, generic client)From the spec
Finding the endpointRead the docs, copy the pathPick it from a list grouped by tag
Path and query parametersTyped from memory or docsForm fields generated from the spec, required ones marked
Request bodyWritten by handStarts from the schema or the documented example
AuthYou look up the scheme and header nameThe security scheme tells you bearer, basic or API key
Checking the responseYou eyeball the JSONCompared against the documented schema for that status code
When the API changesYour saved request goes staleReload the spec and the form follows it

Hand-built requests still win when there is no spec, when you need to send something the spec does not allow (a malformed body, a missing header) to test error handling, or when you want a command to paste into a bug report. For everyday checks against a documented API, starting from the spec removes most of the typing and gives you schema validation in the same step. The guide to validating API responses against an OpenAPI schema explains what that check catches.

Sending auth headers

Most failed first requests are auth problems. OpenAPI specs declare the scheme under components.securitySchemes, and the three you will meet most are below.

Scheme in the specWhat gets sentcurl example
http, scheme: bearerAuthorization: Bearer <token>-H "Authorization: Bearer $TOKEN"
http, scheme: basicAuthorization: Basic base64(user:password)-u user:password
apiKey, in: headerA named header, for example X-API-Key: <key>-H "X-API-Key: $KEY"
apiKey, in: queryA query parameter, for example ?api_key=<key>"https://api.example.com/v1/items?api_key=$KEY"

APIForge has fields for all four. It builds the Basic header from the username and password you enter, and it puts an API key in the header or query string based on the location you choose. If you add your own Authorization header, the auth fields will not overwrite it.

A request that adds an Authorization header is no longer a CORS "simple" request, so the browser sends a preflight first. This is why a public GET often works in a browser tester while the same endpoint with a token fails. The Swagger UI bearer token guide covers the other common token mistakes.

Step by step: test an endpoint from a spec in the browser

Testing one endpoint with APIForge

  1. Find the spec URL

    Look for /openapi.json, /swagger.json, /v3/api-docs or /swagger/v1/swagger.json on the API's host. If you only have a Swagger UI page, APIForge can usually discover the spec from it, and the guide to getting the OpenAPI JSON from Swagger UI lists the manual routes. A local .json or .yaml file works too.

  2. Load it

    Paste the URL or upload the file on the APIForge home page. The endpoints appear grouped by tag, with the method and path for each operation.

  3. Pick the server

    Specs often list several servers (production, staging, local). Choose staging or a sandbox for testing, so test writes do not touch real data.

  4. Fill in parameters and body

    Required path and query parameters are marked. For POST, PUT and PATCH, start from the generated body and change only the fields you are testing.

  5. Add auth

    Choose bearer, basic or API key to match the security scheme in the spec, and paste a test credential.

  6. Send in Auto mode

    The request goes from your browser first. If CORS or the network blocks it, APIForge retries through its proxy and shows which mode returned the response.

  7. Read the result

    Check the status code, headers, timing and body, then the schema validation result. A missing required field or a wrong type in the response points to drift between the API and its docs.

  8. Take it further

    Generate TypeScript types or an AI IDE prompt for the endpoint, or check the spec's quality score before you build against it.

Which tool should you reach for?

ScenarioRecommendationAlternative
You need one quick call and you have a terminal opencurl or HTTPiefetch() in the console if you are already on the API's own origin
The API has an OpenAPI or Swagger spec and you want to try several endpointsA spec-driven browser tester such as APIForgeImport the spec into Bruno or Hoppscotch if you want a saved collection
You want requests versioned in Git alongside the codeBruno or VS Code REST Client .http files—
The API runs only on localhostA terminal or desktop tool, or a browser tester in direct mode with CORS enabled on your dev server—
Your team shares collections, environments and monitors every dayPostman or Insomnia are built for that, and the setup pays off—

Frequently asked questions

For terminal work, curl and the HTTPie CLI need no account. For a desktop app, Bruno's core app runs without one and stores collections as files. In the browser, Hoppscotch can be used without signing in for basic requests, and APIForge needs no account at all when you are testing from an OpenAPI spec. Login rules change, so confirm on each tool's site.

Yes. Use fetch() in the DevTools console for an API on the same origin as the page, or an online API tester. For APIs on other origins, the tester needs a proxy or browser extension to get past CORS, or the API must send CORS headers that allow the tester's origin.

The token travels through the tester's server, so treat it like sharing it with that service. Use a test or staging token with limited scope, and avoid production credentials. If the API allows your browser's origin, a tester in direct browser mode sends the token from your machine only.

curl is not subject to CORS. A browser tester runs as a web page, so the browser blocks the response unless the API sends matching Access-Control-Allow-Origin headers and answers the preflight for requests with auth headers or JSON bodies. Switch the tester to proxy mode to confirm the API works, then fix the CORS headers for your own frontend.

Sources

  1. Cross-Origin Resource Sharing (CORS)MDN
  2. OpenAPI Specification: Security Scheme ObjectOpenAPI Initiative
  3. curl man pagecurl.se
  4. Bruno documentationusebruno.com
  5. Hoppscotch documentationhoppscotch.io