Skip to content

HTTP Methods Reference — JavaScript source

A searchable reference for every HTTP request method - GET, POST, PUT, PATCH, DELETE, and more. See at a glance which are safe, idempotent, and cacheable, then compare any two methods side by side.

This is the JavaScript implementation — the same logic the interactive tool runs, in a shareable, citable form.

// @file javascript.js
// @language JavaScript
//
// HTTP request-method reference - pure, deterministic data + lookups. No DOM,
// no React, no external dependencies.
//
// CosmoDev polyglot showcase port of the `http-methods` tool, ported from
// src/lib/http-methods.ts. Functionally equivalent: identical inputs yield
// identical outputs (case-insensitive lookup, flag + free-text filtering, and
// a human-readable semantic comparison report).
//
// Property flags (safe / idempotent / cacheable / hasBody) follow RFC 9110
// and the MDN reference table.
//
// Display source - part of CosmoDev's polyglot tool pages.

'use strict';

/**
 * @typedef {Object} MethodEntry
 * @property {string}  method       Uppercase method name, e.g. "GET".
 * @property {boolean} safe         Read-only semantics - no server state change.
 * @property {boolean} idempotent   Repeating the call has the same effect as one.
 * @property {boolean} cacheable    Responses may be stored by a cache (RFC 9110 / MDN).
 * @property {boolean} hasBody      The method conventionally carries a request body.
 * @property {string}  description  Short semantic summary.
 * @property {string}  typicalUse   One-line "when you reach for it" example.
 */

/**
 * The nine HTTP request methods (RFC 9110 / 9111).
 *
 * Frozen deeply so callers cannot mutate the canonical table; the lookup
 * helpers return references into this single source of truth.
 *
 * @type {readonly Readonly<MethodEntry>[]}
 */
export const METHODS = Object.freeze([
  Object.freeze({
    method: 'GET',
    safe: true,
    idempotent: true,
    cacheable: true,
    hasBody: false,
    description: 'Retrieves a representation of the target resource; a read-only request.',
    typicalUse: 'Fetching a web page, reading an API resource, loading an image.',
  }),
  Object.freeze({
    method: 'POST',
    safe: false,
    idempotent: false,
    cacheable: true,
    hasBody: true,
    description: 'Submits data to be processed, typically creating a new resource or triggering an action.',
    typicalUse: 'Submitting a form, creating a record, publishing a message.',
  }),
  Object.freeze({
    method: 'PUT',
    safe: false,
    idempotent: true,
    cacheable: false,
    hasBody: true,
    description: 'Replaces the target resource entirely with the request body.',
    typicalUse: 'Updating a full record at a known URL, uploading a file by its path.',
  }),
  Object.freeze({
    method: 'PATCH',
    safe: false,
    idempotent: false,
    cacheable: false,
    hasBody: true,
    description: 'Applies a partial modification to the target resource.',
    typicalUse: 'Updating one field of a record, toggling a flag.',
  }),
  Object.freeze({
    method: 'DELETE',
    safe: false,
    idempotent: true,
    cacheable: false,
    hasBody: false,
    description: 'Removes the target resource.',
    typicalUse: 'Deleting a record or file by its URL.',
  }),
  Object.freeze({
    method: 'HEAD',
    safe: true,
    idempotent: true,
    cacheable: true,
    hasBody: false,
    description: 'Identical to GET but returns only the response headers, no body.',
    typicalUse: 'Checking existence, size, or freshness before downloading.',
  }),
  Object.freeze({
    method: 'OPTIONS',
    safe: true,
    idempotent: true,
    cacheable: false,
    hasBody: false,
    description: 'Describes the communication options for the target resource.',
    typicalUse: 'CORS preflight requests, discovering allowed methods.',
  }),
  Object.freeze({
    method: 'CONNECT',
    safe: false,
    idempotent: false,
    cacheable: false,
    hasBody: false,
    description: 'Establishes a tunnel to the server (used with TLS/HTTPS proxies).',
    typicalUse: 'Proxying encrypted connections through an intermediary.',
  }),
  Object.freeze({
    method: 'TRACE',
    safe: true,
    idempotent: true,
    cacheable: false,
    hasBody: false,
    description: 'Performs a message loop-back test along the path to the target (debugging only).',
    typicalUse: 'Diagnosing request transformations by intermediaries.',
  }),
]);

/**
 * Filter options. Omitted boolean flags are ignored (tri-state: present =>
 * constrain to that value, absent => no constraint). An empty/whitespace
 * `query` returns the flag-filtered pool unchanged.
 *
 * @typedef {Object} MethodFilter
 * @property {boolean} [safe]
 * @property {boolean} [idempotent]
 * @property {boolean} [cacheable]
 * @property {string}  [query]  Free text matched case-insensitively against
 *                              method, description, and typicalUse.
 */

/**
 * Case-insensitive single-method lookup.
 *
 * @param {string} name  Method name (whitespace is trimmed; case-insensitive).
 * @returns {Readonly<MethodEntry> | null}  The entry, or null when unknown.
 */
export function getMethod(name) {
  const n = String(name).trim().toUpperCase();
  return METHODS.find((m) => m.method === n) ?? null;
}

/**
 * Filter the method set by boolean flags and an optional text query.
 *
 * A method must satisfy *every* present flag AND, when a query is given, match
 * it in at least one of {method, description, typicalUse}.
 *
 * @param {MethodFilter} [opts={}]
 * @returns {readonly Readonly<MethodEntry>[]}
 */
export function filterMethods(opts = {}) {
  const q = (opts.query ?? '').trim().toLowerCase();
  return METHODS.filter((m) => {
    if (opts.safe !== undefined && m.safe !== opts.safe) return false;
    if (opts.idempotent !== undefined && m.idempotent !== opts.idempotent) return false;
    if (opts.cacheable !== undefined && m.cacheable !== opts.cacheable) return false;
    if (q) {
      return (
        m.method.toLowerCase().includes(q) ||
        m.description.toLowerCase().includes(q) ||
        m.typicalUse.toLowerCase().includes(q)
      );
    }
    return true;
  });
}

/**
 * @typedef {Object} MethodComparison
 * @property {boolean}   sameSafety       Both methods share the `safe` flag.
 * @property {boolean}   sameIdempotence  Both methods share the `idempotent` flag.
 * @property {string[]}  differences      One sentence per mismatched property
 *                                        (safe, idempotent, cacheable, hasBody).
 */

/**
 * Compare two methods, surfacing where their semantics agree and differ.
 *
 * `differences` lists every mismatched property as a human-readable sentence,
 * reproducing the canonical phrasing verbatim.
 *
 * @param {MethodEntry} a
 * @param {MethodEntry} b
 * @returns {MethodComparison}
 */
export function compareMethods(a, b) {
  /** @type {string[]} */
  const differences = [];

  if (a.safe !== b.safe) {
    differences.push(
      `${a.method} is ${a.safe ? 'safe' : 'not safe'}, ${b.method} is ${b.safe ? 'safe' : 'not safe'}.`,
    );
  }
  if (a.idempotent !== b.idempotent) {
    differences.push(
      `${a.method} is ${a.idempotent ? 'idempotent' : 'not idempotent'}, ${b.method} is ${b.idempotent ? 'idempotent' : 'not idempotent'}.`,
    );
  }
  if (a.cacheable !== b.cacheable) {
    differences.push(
      `${a.method} is ${a.cacheable ? 'cacheable' : 'not cacheable'}, ${b.method} is ${b.cacheable ? 'cacheable' : 'not cacheable'}.`,
    );
  }
  if (a.hasBody !== b.hasBody) {
    differences.push(
      `${a.method} ${a.hasBody ? 'takes' : 'does not take'} a body, ${b.method} ${b.hasBody ? 'takes' : 'does not take'} a body.`,
    );
  }

  return {
    sameSafety: a.safe === b.safe,
    sameIdempotence: a.idempotent === b.idempotent,
    differences,
  };
}

Also available in 13 other languages

Every CosmoDev tool ships its pure logic in TypeScript (web) and Go (CLI), with authored implementations in a dozen-plus languages — the same contract, ported. Compare all languages side by side →