Knowledge BaseConventions

Code conventions, explained

When BeforeMerge scans a repository it detects the conventions your team already follows — how you name things, structure files, import modules, handle errors, and write components. This page explains what each convention means, why a consistent choice matters, and what good and bad versions look like.

Conventions by type

BeforeMerge groups detected conventions into five types. Accepting a convention turns it into a private project rule, so future scans flag code that breaks the pattern.

Naming

Naming conventions cover how identifiers and files are named. A single consistent scheme makes code easier to scan, keeps imports predictable, and stops trivial casing differences from cluttering code review.

Variable casing

The dominant casing for variables and functions across the codebase.

camelCasesnake_casePascalCaseSCREAMING_SNAKE

File naming

How source files themselves are named.

kebab-casecamelCasePascalCasesnake_case
Avoid
// Mixed casing in the same module — hard to scan
const user_id = 1;
const UserName = "ada";
function get_profile() {}
function FetchData() {}
Prefer
// One consistent casing scheme (camelCase here)
const userId = 1;
const userName = "ada";
function getProfile() {}
function fetchData() {}

File structure

File structure is how files and folders are organized across the project. A consistent strategy makes it obvious where new code belongs and where to find existing code.

Folder organization

Whether the project groups code by technical type, by feature, or keeps everything flat.

Type-based folders (components/, hooks/, lib/)Feature-based folders (auth/, billing/)Flat structure
Avoid
// Inconsistent — some by type, some by feature, some loose
src/
  components/Button.tsx
  auth/LoginForm.tsx
  utils.ts
  billingHelpers.ts
  hooks/useAuth.ts
Prefer
// Consistent feature-based organization
src/
  features/
    auth/   { LoginForm.tsx, useAuth.ts }
    billing/{ Invoice.tsx, helpers.ts }
  shared/
    components/Button.tsx
    lib/utils.ts

Import style

Import style is how modules reference one another. A consistent choice keeps import paths readable and makes files painless to move without rewriting a tangle of relative paths.

Local imports

Whether internal modules use absolute path aliases or relative paths.

Absolute imports (@/lib/utils)Relative imports (../lib/utils)Mixed

Barrel exports

Whether folders re-export their contents through an index file (a "barrel").

Used (index.ts re-exports)Not used
Avoid
// Mixed absolute and deep-relative imports
import { cn } from "@/lib/utils";
import { Button } from "../../../components/Button";
import { api } from "../../lib/api";
Prefer
// Consistent absolute imports via a path alias
import { cn } from "@/lib/utils";
import { Button } from "@/components/Button";
import { api } from "@/lib/api";

Error handling

Error handling is how the code deals with failures. A consistent approach — whether defensive try/catch close to the source or letting errors bubble to a central handler — makes failures predictable and easier to trace.

Error handling style

How aggressively async operations are wrapped in try/catch.

Defensive try/catch on async callsSparse try/catch (errors bubble up)Rare try/catch

Error boundaries

Whether the app uses React error boundaries to contain rendering errors.

Uses React error boundariesNo React error boundaries
Avoid
// Swallowing errors silently hides real failures
async function load() {
  try {
    return await fetchUser();
  } catch {
    return null; // caller can't tell what went wrong
  }
}
Prefer
// Handle what you can, surface the rest
async function load() {
  try {
    return await fetchUser();
  } catch (err) {
    logger.error({ err }, "fetchUser failed");
    throw err; // let a boundary / caller decide
  }
}

Component patterns

Component patterns describe how UI components are authored and rendered. A consistent pattern keeps the component layer easy to read and avoids accidental client-side bloat in frameworks like Next.js.

Component style

Whether components are written as functions (with hooks) or ES classes.

Functional componentsClass componentsMixed component styles

Server vs client components

In Next.js, whether components default to Server Components or Client Components.

Server Components by defaultClient Components by default
Avoid
// Class component + needless "use client" on a static view
"use client";
class Greeting extends React.Component {
  render() {
    return <h1>Hello {this.props.name}</h1>;
  }
}
Prefer
// Function component, server by default (no "use client")
function Greeting({ name }: { name: string }) {
  return <h1>Hello {name}</h1>;
}

Turn your conventions into rules

Run a scan and BeforeMerge surfaces the high-confidence conventions it finds. Accept the ones that matter and they become enforced project rules — no config to write.