On this page
Cursor Rules Examples: Real Working Configurations
Most Cursor users still rely on deprecated monolithic .cursorrules files, leaving 30% of the tool's value unused and paying 2-3x higher token costs. This guide shares real working .mdc rule configurations, explains the four activation types, and provides a step-by-step migration path to unlock Cursor's full agentic capabilities.
Here’s a number that should make most Cursor users uncomfortable: the PatrickJS/awesome-cursorrules repository contains 257 ready-to-copy rule files and has 40,049 GitHub stars (verified June 21, 2026), yet the majority of Cursor projects still run either a bloated monolithic .cursorrules file or no rules at all. That gap — between what’s available and what’s actually in use — is where most of the tool’s value sits untouched.
The reason isn’t laziness. It’s that the format changed, the documentation scattered across community guides, and the migration path from legacy to modern rules was never made urgent enough. If you’re still running a root-level .cursorrules file in 2026, you’re not just using a deprecated format — you’re actively paying more per request and getting worse agent behavior than you should be.
Why the format change matters more than you think
Cursor supports two rule formats: the legacy single-file .cursorrules at the project root (deprecated but still functional as a fallback in non-Agent modes), and the modern .cursor/rules/*.mdc directory format with YAML frontmatter (the current standard) [per learncursor.dev]. The legacy file still loads in non-Agent modes as of Cursor 3.x [per stackbrief.dev], which is precisely why migration urgency feels low — nothing breaks visibly.
But here’s the hidden cost. A monolithic .cursorrules file loads every instruction into every session, whether relevant or not. For a small single-language repo, that’s tolerable. For a platform repo touching YAML manifests, Python controllers, Helm charts, and shell scripts, you end up with rules that contradict each other or are irrelevant to the current task. The MDC format solves this with scoped activation — rules only load when you’re editing matching file types.
What I call the Context Scoping Foundation pattern is the unspoken foundational layer enabling Cursor’s entire agentic product roadmap. Scoped rules reduce per-request token costs enough to make always-on agents, automations, and multi-file tasks economically viable. Without them, the economics of Cursor’s Agent mode and Automations features don’t work. But mass adoption of the new rule format lags far behind the rollout of these advanced features, creating a hidden cost and capability gap for most users.
The bottom line: any Cursor user who hasn’t migrated from a root-level .cursorrules file to a scoped .cursor/rules/*.mdc structure is leaving at least 30% of the tool’s value on the table and incurring 2-3x higher per-request token costs than necessary, regardless of their subscription tier.
The anatomy of a working .mdc file
Each .mdc file requires YAML frontmatter with three fields: description (string), globs (string array), and alwaysApply (boolean) [per techsy.io]. Plain .md files placed in .cursor/rules/ are silently ignored by Cursor — only files with the .mdc extension are loaded [per toolchew.com].
Here’s a complete, production-ready example for a Next.js + TypeScript project:
---
description: TypeScript and React conventions for UI components
globs: ["**/*.tsx", "**/*.jsx"]
alwaysApply: false
---
## Code Style
- Use named exports, not default exports
- Prefer `interface` over `type` for object shapes
- Use `const` everywhere; never `let` for primitives
## Component Structure
React components follow this structure:
1. Type definitions
2. Component function
3. Local hooks/helpers
4. Export
## Constraints
- Components must not import from other feature directories
- Cross-feature dependencies go through the shared/ layer
- Default to Server Components unless `useState` or `useEffect` is strictly required
The description field is doing real work here — it’s used by Cursor’s rule-selection logic to decide whether to auto-attach the rule when alwaysApply is false [per polarpoint.io]. Write it as a brief that tells Cursor when this rule is relevant, not as a title. “Apply when editing React UI components” is more useful than “React conventions.”
The four activation types and when to use each
Cursor rules have four activation modes [per openbooklet.com]:
| Type | alwaysApply | globs | description | When It Loads |
|---|---|---|---|---|
| Always | true | empty | optional | Every conversation |
| Auto-Attached | false | pattern set | optional | When matching files are in context |
| Agent-Requested | false | empty | required | AI reads description, decides if relevant |
| Manual | false | empty | optional | Only when @mentioned |
The tradeoff is straightforward. Always-apply rules guarantee the instruction loads in every session with no context evaluation overhead, but they eat tokens from every interaction whether relevant or not. Scoped glob/description rules only load relevant context for the current task, reducing per-request token costs and minimizing context noise for the agent — but they require upfront configuration and occasional misses when the description isn’t specific enough.
Cursor’s official documentation recommends keeping always-apply rules under roughly 500 lines and splitting large rulesets into focused, composable files to limit token cost on every request [per securityboulevard.com]. That’s a hard constraint, not a suggestion. When an always-apply rule grows past that threshold, critical instructions get diluted in the middle of the file and the agent’s adherence drops.
A real directory structure for a Next.js project
A well-structured .cursor/rules/ directory for a Next.js project typically includes files such as general.mdc (alwaysApply: true), react-components.mdc (globs: **/*.tsx), api-routes.mdc (globs: app/api/**/*.ts), and testing.mdc (globs: **/*.test.ts) [per codercops.com]. Here’s what that looks like in practice:
.cursor/
rules/
general.mdc # alwaysApply: true — project overview, stack, invariants
react-components.mdc # globs: **/*.tsx, **/*.jsx
api-routes.mdc # globs: app/api/**/*.ts
database.mdc # globs: lib/db/**/*.ts, **/*.sql
testing.mdc # globs: **/*.test.ts, **/*.spec.ts
The general.mdc file sets the foundation that every other rule builds on:
---
description: Project architecture overview and invariants
alwaysApply: true
---
## Project Overview
E-commerce platform. Next.js 15 App Router. PostgreSQL via Drizzle ORM.
Stripe for payments. Resend for transactional email.
## Layer Rules
- UI: app/ directory, .tsx files only, React Server Components by default
- API: app/api/ for REST endpoints, server actions for form submissions
- Business logic: lib/ directory, pure TypeScript functions
- Database: lib/db/, Drizzle schema and queries only, never raw SQL in routes
- External services: lib/integrations/, each service gets its own file
The strongest stack-specific rule files name concrete versions (e.g., Next.js App Router, Python 3.12, Vue 3 / Nuxt 3) rather than generic instructions like “write clean code” [per securityboulevard.com]. Specificity is what makes the difference between a rule that the agent follows and one that it ignores.
The hierarchy you need to understand
Cursor’s rule hierarchy gives Team Rules the highest precedence, followed by Project Rules (.cursor/rules/*.mdc), User Rules, Legacy Rules (.cursorrules), and AGENTS.md [per design.dev]. This matters for teams because it means a well-placed team rule will override a conflicting project rule, which will override a legacy .cursorrules file.
For individual developers, the practical implication is that your .cursorrules file is the lowest-priority input. If you’ve migrated to .mdc files but still have a legacy .cursorrules at the root, the legacy content loads only when no higher-priority rule covers the same ground. It’s not harmful, but it’s redundant — and it can create confusion about which source is actually driving behavior.
Copy-paste vs. custom: the real tradeoff
The PatrickJS/awesome-cursorrules repository is the single largest reason most developers never write a Cursor rule file from scratch. You copy a stack-matched file, drop it into your project, and Cursor’s agent stops guessing your conventions. That’s fast and it works for common stacks.
But community templates may include irrelevant or conflicting rules for your specific codebase. Writing custom tailored rules is slower initially but perfectly aligned with your team’s conventions and architecture, avoiding context bloat from unused instructions.
The pragmatic approach: start with a vetted community file for your stack, then aggressively prune anything that doesn’t match your actual codebase. Remove rules for libraries you don’t use. Delete conventions your team doesn’t follow. Add the specific patterns your codebase requires that no generic template would know about.
Some teams report that focused rules drive AI suggestion acceptance rates from roughly 30% to 80% or higher [per aicoderscope.com]. Not because the model improved — because it stopped generating code your codebase doesn’t use.
Common reasons rules fail (and how to fix them)
The most frequent causes of Cursor ignoring rules [per learncursor.dev]:
- Globs don’t match edited files — Your rule has
globs: ["**/*.tsx"]but you’re editing a.tsfile. Check your glob patterns. - Using the deprecated
.cursorrulesformat — It’s not loaded in Agent mode at all [per stackbrief.dev]. - Rules too long or contradictory — Critical instructions get diluted. Keep each file focused.
- Malformed
.mdcfrontmatter — A missing colon or unquoted string silently breaks the rule.
The fix for most of these is structural: move rules to .cursor/rules/*.mdc files (one concern per file), set globs so the rule loads for the files it’s about, shorten rules to concrete do/don’t lines with an example, and verify the frontmatter is valid, then reload Cursor [per learncursor.dev].
The migration path
If you’re running a legacy .cursorrules file today, here’s the sequence:
- Create
.cursor/rules/directory at your project root - Split your monolithic file into focused
.mdcfiles by concern - Add proper YAML frontmatter to each file with
description,globs, andalwaysApply - Keep your always-apply rules under 500 lines each
- Delete the legacy
.cursorrulesfile (or keep it only as a reference during migration) - Reload Cursor and verify rules are loading in the UI
The whole process takes about an hour for a typical project. The token savings and improvement in agent output quality start immediately.
For teams running multiple AI coding tools, the configuration landscape gets more complex — AGENTS.md, CLAUDE.md, and Cursor rules each serve different tools and contexts. If you’re managing rules across tools, the layered configuration model with AGENTS.md as the cross-tool source of truth is worth reading alongside this guide.
The question isn’t whether to use rules. It’s whether you’re going to use the format that was designed for the agentic features Cursor is building, or stick with the deprecated one that was designed for single-file completions. The economics and the behavior both favor migration.