BeforeMerge

AI-native code review knowledge base. Structured rules that catch what linters miss.

Product

  • Features
  • Explore
  • Pricing
  • Docs
  • GitHub

Company

  • About
  • Blog
  • Contributors
  • Contributing

Legal

  • Privacy Policy
  • Terms of Service
  • MIT License

© 2026 BeforeMerge. Built by Peter Krzyzek

BeforeMerge
Features
Explore
PricingBlogContributorsInstall Guide
3Sign In
FeaturesExplore
RulesSkillsKnowledgePrompts
PricingBlogContributorsInstall Guide
Sign In

Explore

Browse 354 rules, 42 knowledge articles, and 28 prompt templates across security, performance, architecture, and quality.

Sort:
Previous1...91011...15Next

Automate these checks on every PR

BeforeMerge scans your pull requests against these rules automatically. Get actionable feedback before code ships to production.

Join WaitlistLearn More

354 rules

Use the Correct WordPress Hook for Each Operation

MEDIUM

Registering CPTs on plugins_loaded, enqueueing scripts on init, or running admin-only code on every request wastes resources and causes subtle bugs.

Architecturefilterswordpressbeforemerge-wordpress-review

Use WordPress Path and URL Functions — Never Hardcode

MEDIUM

Hardcoded URLs and filesystem paths break across environments (local/staging/prod), subdirectory installs, multisite, and custom wp-content directories.

Architecturepaths

Prevent SQL Injection in Custom RPC Functions

CRITICAL

String interpolation in .rpc() calls or custom PostgreSQL functions allows attackers to inject arbitrary SQL. Always use parameterized queries. [CWE-89 · A03:2021]

Securityrpcsupabase

Never Use Service Role Client in Auth-Context Routes

CRITICAL

createServiceRoleClient() bypasses ALL RLS policies. Using it in request handlers lets any authenticated user access or modify all data. [CWE-269 · A04:2021]

Securityservice-rolesupabase

Never Log Sensitive Data

HIGH

Logging OAuth tokens, API keys, passwords, or PII exposes secrets in log aggregation services and crash reporters. Use scoped loggers with sanitization. [CWE-532 · A09:2021]

SecuritysupabaseSecrets

Close RLS Policy Gaps for All Operations

HIGH

Tables with RLS enabled but missing policies for certain operations silently deny access. Ensure every table has policies for SELECT, INSERT, UPDATE, and DELETE. [CWE-862 · A01:2021]

Securitysupabaserls

Enable RLS on Every Table with Complete Policies

CRITICAL

Every table must have Row Level Security enabled with at least one policy per operation. Tables without RLS are accessible to any authenticated user. [CWE-862 · A01:2021]

Securitysupabaserls

Use Migration Files Instead of MCP or Dashboard SQL

HIGH

Schema changes via Supabase MCP, SQL editor, or dashboard don't create migration files. This causes schema drift between environments.

SecuritysupabaseDatabase

Use getUser() Instead of getSession() for Auth Checks

CRITICAL

getSession() reads from cookies and can be spoofed. getUser() verifies the token with the Supabase Auth server, making it tamper-proof. [CWE-287 · A07:2021]

Securitysessionsupabase

Never Expose Service Role Key in Client-Side Code

CRITICAL

Using NEXT_PUBLIC_ prefix on SUPABASE_SERVICE_ROLE_KEY or DATABASE_URL embeds secrets into client-side JavaScript bundles, bypassing all RLS. [CWE-798 · A07:2021]

Securitynextjssupabase

Validate Input at Runtime with Zod Instead of Type Assertions

HIGH

Using 'as' type assertions on external input (params, form data, request bodies) provides zero runtime safety. Use Zod for runtime validation. [CWE-20 · A03:2021]

QualitysupabaseValidation

Always Check Error Before Using Data from Supabase Queries

HIGH

Destructuring { data } without checking { error } from Supabase queries ignores failures silently. When error is non-null, data is always null. [CWE-252]

Qualitysupabasequality

Distinguish Not-Found from Other Supabase Errors

MEDIUM

Treating all Supabase errors the same (if error, throw) hides whether a record is missing or the query itself failed. Check error codes for proper handling.

Qualitypostgrestsupabase

Avoid select('*') — Request Only the Columns You Need

HIGH

Using .select('*') fetches all columns including large text/json fields, wastes bandwidth, leaks data shape, and prevents index-only scans.

PerformanceQueriessupabase

Avoid N+1 Queries with Supabase Relational Selects

HIGH

Fetching parent records then looping to fetch children creates N+1 HTTP requests. Use Supabase nested .select('*, children(*)') to resolve in a single query. [CWE-400]

PerformanceQueriessupabase

Add Indexes for Filtered and Ordered Columns

HIGH

Filtering or ordering on unindexed columns causes full table scans. RLS policy columns like user_id and org_id especially need indexes. [CWE-405]

PerformanceQueriessupabase

Use Cursor-Based Pagination Instead of Offset Pagination

HIGH

Using .range() offset pagination for large datasets forces PostgreSQL to scan all skipped rows. Use cursor-based pagination with .gt()/.lt() for constant-time page fetches.

PerformancecursorQueries

Use Connection Pooling (Supavisor) for Serverless Deployments

HIGH

Each serverless invocation opening a direct database connection exhausts PostgreSQL's connection limit. Use Supavisor pooler URLs for all serverless environments.

Performancesupabasesupavisor

Use Batch Operations Instead of Single-Row Loops

HIGH

Inserting or updating rows one at a time in a loop creates N HTTP requests. Use .insert([...]) or .upsert([...]) to batch into a single request.

Performancesupabasebulk

Generate Database Types from Schema

MEDIUM

Hand-writing TypeScript interfaces for database tables leads to drift between code and schema. Use supabase gen types to generate types automatically.

Architecturesupabase

Follow Canonical Migration File Structure

MEDIUM

Migration files without proper structure (table, indexes, RLS, policies, comments) are harder to review and prone to missing critical steps like RLS.

Architecturesupabase

Use the Correct Supabase Client for Each Context

HIGH

Using the wrong Supabase client for the context breaks RLS, leaks auth state, or causes hydration errors. Match client type to Next.js rendering context.

Architecturemiddleware

Prevent Prototype Pollution from Untrusted Input

CRITICAL

Spreading or Object.assign-ing untrusted user input into objects can pollute Object.prototype and lead to security bypasses. [CWE-1321]

SecurityReactPrototype Pollution

Use Cryptographic Randomness for Tokens and IDs

CRITICAL

Math.random() is not cryptographically secure. Use crypto.randomUUID() or crypto.getRandomValues() for tokens, IDs, and security-sensitive values. [CWE-338]

SecurityReactrandomness
wordpress
beforemerge-wordpress-review
Supabase
Supabase
Supabase
Supabase
Supabase
Supabase
Supabase
Supabase
Supabase
Supabase
Supabase
Supabase
Supabase
Supabase
Supabase
Supabase
Supabase
types
Supabase
Database
Supabase
nextjs
Supabase
React
React