Last updated: May 2026
REST API endpoint naming is the practice of choosing consistent, resource-oriented URLs for every operation in your API. Good naming makes an API predictable, easier to integrate, and — increasingly — easier for AI agents to use safely. Bad naming makes every endpoint a question mark, slows integration, and produces bugs. This guide covers the conventions used by the best public APIs (Stripe, GitHub, Twilio), the common mistakes that hurt API quality, and how AI consumption via the Model Context Protocol changes what good naming looks like in 2026.
POST /orders, not /createOrder./customers for the collection, /customers/123 for a single item./order-items, not /OrderItems or /order_items./customers/123/orders, not /customers/123/orders/456/items./v1/customers in the path, or via the Accept header.An API is a contract. The URL of every endpoint is part of that contract — and unlike most other parts of an API design, it's the most public, the most often-cited, and the hardest to change later. Backwards-incompatible URL changes break every consumer. Consistent, predictable naming therefore pays compounding interest.
Good naming has three direct effects:
GET /customers/123/orders needs no documentation if the rest of the API uses the same shape.A REST API endpoint is the combination of a URL and an HTTP method that, together, identify a single operation in your API. GET /customers/123 is one endpoint; DELETE /customers/123 is a different endpoint, even though the URL is identical. The URL identifies the resource; the HTTP method identifies the action.
Three terms get confused in this area:
https://api.example.com/v1/customers/123./v1/customers/123. This is what most "endpoint" discussions focus on.GET /v1/customers/123. This is the actual operation.For more on the underlying architecture, see REST APIs: an overview of basic principles.
The following conventions show up across virtually every well-regarded public API. They aren't laws — but if you deviate from them, deviate deliberately, and document why.
POST /orders, not /createOrder; GET /customers/123, not /getCustomerById?id=123./customers, not /customer. The same path with an ID points to a single item: /customers/123. Plural-only is the dominant convention in modern APIs and keeps URL grammar consistent./order-items, not /OrderItems or /order_items. URLs are case-sensitive in the HTTP spec but case-insensitive in many real-world stacks — sticking to lowercase prevents inconsistency. Hyphens are easier to read than underscores in browser URL bars./customers/123/orders for the orders belonging to customer 123. This makes URLs self-documenting./customers/123/orders/456/items/789/notes couples your URL structure to your data model and breaks every time relationships change. Link deeper resources from their own top-level paths..json or .xml. Use the Accept header or a query parameter to negotiate format. The URL identifies the resource; the format is a presentation concern.?, &, =, % have specific meanings in URLs. Spaces and Unicode characters cause encoding problems./v1/customers in the path, or Accept: application/vnd.example.v1+json in headers. Pick one and stick with it. Never have an unversioned API and a versioned API serving different responses./orders?status=paid&page=2. Don't put filters in the path./customers, also pluralise /orders, /products, /payments. Mixing conventions within the same API is worse than picking the "wrong" one consistently.Concrete examples of the same operations done well and done badly. The "Bad" column is drawn from real APIs in the wild.
| Operation | Good | Bad | Why |
|---|---|---|---|
| List customers | GET /customers |
GET /getAllCustomers |
HTTP method is the verb; URL is the resource |
| Get one customer | GET /customers/123 |
GET /customer?id=123 |
Use path segments for IDs, query for filters |
| Create customer | POST /customers |
POST /createCustomer |
HTTP verb already says "create" |
| Update customer | PATCH /customers/123 |
POST /updateCustomer?id=123 |
PATCH is the partial-update verb |
| Delete customer | DELETE /customers/123 |
POST /deleteCustomer?id=123 |
DELETE has clear intent + supports caching invalidation |
| List a customer's orders | GET /customers/123/orders |
GET /orders/byCustomer?customerId=123 |
Hierarchical path expresses ownership |
| Filter and paginate | GET /orders?status=paid&page=2 |
GET /paidOrdersPage2 |
Query string is the right tool for filters/pagination |
| Versioned endpoint | GET /v1/customers |
GET /customers_new |
Explicit versioning beats version-by-suffix |
| Action on a resource | POST /orders/123/refund |
POST /refundOrder?id=123 |
Sub-action is acceptable when the verb doesn't fit CRUD; still use a noun |
Beyond the positive practices, these are the recurring naming mistakes that hurt API quality:
/data, /info, /process. Names that don't describe the resource force every consumer to read documentation to understand what an endpoint returns./orderItems in one place, /order-items in another, and /order_items in a third. Pick one and stick with it across the whole API./getOrder, /saveCustomer, /updateProfile. The HTTP method already conveys the verb./customers/v2_active_premium tries to encode multiple dimensions in a single path segment. Use query parameters or separate endpoints.The biggest shift to API design in the last two years isn't a new framework — it's who's calling the API. AI agents built on large language models now make a growing share of API calls, fetching data, invoking tools, and chaining requests across services on behalf of users.
This creates a new layer in the stack. The Model Context Protocol (MCP), introduced by Anthropic and rapidly adopted by other LLM providers, is the emerging standard for how AI models discover and call APIs at runtime. An MCP server exposes API endpoints as tools the model can read and invoke; an MCP client (like Claude or ChatGPT) consumes those tools.
That changes a few things for endpoint naming specifically:
description field is no longer optional metadata — it's the primary signal an LLM uses to understand what an endpoint does. Write it for an intelligent reader who's never seen the API.The piece of infrastructure handling that data-access layer is the AI Data Gateway — a secure intermediary between enterprise data sources and AI systems. Where a traditional API gateway handles authentication, rate limiting, and routing for human-driven traffic, an AI Data Gateway adds AI-aware controls: identity passthrough, deterministic query enforcement, prompt logging, content filtering, and field-level data governance for agent traffic.
For teams already running an API gateway, an AI Data Gateway sits as a complementary layer — purpose-built for the specific risks and traffic patterns of AI consumption. See What is an AI Data Gateway for the full architecture, and Zero Trust for LLMs for how the security model works in practice.
The compound effect of getting endpoint naming right shows up in five places:
DreamFactory's foundational capability is instant REST API generation: connect a database (Oracle, SQL Server, PostgreSQL, MySQL, Snowflake, Databricks, MongoDB — 40+ supported), and the platform auto-generates a fully documented, role-protected REST API in minutes, with no code written. The platform has been doing exactly this for over a decade. Authentication (Microsoft Entra ID, OAuth 2.0, OpenID Connect, SAML 2.0, LDAP, Active Directory, API keys), role-based access control (per table, endpoint, and HTTP verb), rate limiting (per user, role, or service), audit logging (every call captured with calling user, timestamp, and payload), and OpenAPI documentation are built in. Server-side scripting in PHP, Python, or Node.js handles custom business logic.
The AI Data Gateway is the newer chapter — a built-in MCP server that exposes the same auto-generated REST API to AI agents (Claude Desktop, Claude Code, ChatGPT, Cursor, Windsurf). The company's framing: "turn your database into an auditable, governed API layer for AI." The core principle is data stays put — keep your systems of record intact, generate a governed API on top, and let AI agents query through that layer rather than receiving raw data extracts. In DreamFactory's MCP tutorial, CTO Kevin McGahey demonstrates the full flow: database credentials, one MCP call, auto-generated API, read-only role, API key — and Claude Code building a working dashboard in minutes.
DreamFactory deploys via Linux installer (Ubuntu, Debian, CentOS, RHEL, Fedora), Windows (IIS or Apache), Docker, Kubernetes via official Helm chart, or NPX quick install. Air-gapped deployment is fully supported — as used by the Vermont Agency of Transportation to expose an Oracle database and a 1970s-era IBM S370 mainframe through a unified API layer.
DreamFactory's customers include ExxonMobil, Toyota, Saint-Gobain, PPG, Deloitte, Google Cloud, AkerBP, Netgear, Miller Industries, the National Institutes of Health, the Vermont Agency of Transportation, D.A. Davidson, and Pillsbury Law — spanning energy, automotive, industrial, finance, government, healthcare, and legal. G2 rates the product 4.7 with badges for "Easiest to Use," "Fastest Implementation," and "Best ROI." See the DreamFactory AI page or request a demo.
Consistent naming makes an API predictable, easier to learn, and easier to maintain. Developers (and increasingly, AI agents) rely on patterns to guess what an endpoint does without reading documentation. Inconsistent naming forces every consumer to look up every endpoint, which slows integration, increases support burden, and produces bugs.
REST is built around the idea that endpoints describe resources (nouns), and HTTP methods describe actions (verbs). Use POST /orders instead of /createOrder; DELETE /orders/123 instead of /deleteOrder?id=123. The HTTP method already conveys the action, so duplicating it in the URL is noise.
Use plural nouns for collections. /customers, not /customer. The same path with an ID points to a single item: /customers/123. Plural-only is the dominant convention in modern API design — Stripe, GitHub, Twilio all follow it — and it keeps the URL grammar consistent across collection and single-item operations.
HTTP methods carry the verb. GET reads, POST creates, PUT replaces, PATCH partially updates, DELETE removes. Combined with resource-oriented URLs, they let you express the entire CRUD vocabulary without ever putting a verb in the URL. See our guide to idempotency for which methods are safe to retry.
Deep nesting (/customers/123/orders/456/items/789/notes) couples your URL structure to your data model and makes endpoints fragile when relationships change. As a rule, nest one level deep at most (/customers/123/orders) and link to deeper resources via their own top-level paths.
The two common patterns are URL path versioning (/v1/customers) and header-based versioning (Accept: application/vnd.example.v1+json). URL versioning is simpler and easier to debug; header versioning keeps URLs cleaner. Pick one and stick with it. Always treat the version as a contract and avoid breaking changes within a version.
When AI agents discover and call your API via the Model Context Protocol (MCP), the endpoint name and description become the input to the model's tool-selection decision. Use clear, descriptive resource names; pair each endpoint with a one-sentence semantic description in your OpenAPI spec; avoid abbreviations the model won't recognise; and keep the auth and scope boundaries fine-grained so an agent can be given exactly the access it needs.
Use hyphens. /order-items reads more naturally and is the convention across most major public APIs. Underscores are harder to read in URLs (the underscore can be hidden by the link underline) and aren't compatible with some legacy tooling. Never use camelCase in paths — URLs are case-sensitive in spec but case-insensitive in many real-world deployments, which causes inconsistency.
Predictable names mean new team members can guess endpoints correctly, AI agents can self-discover available operations, monitoring and logging tools can pattern-match URL structures, and refactoring is safer because the impact of a name change is local. Cumulatively, consistent naming reduces both the cognitive load on humans and the error rate of LLM-driven integrations.