GAP·MAP

OWASP Top 10

[ junior depth ]

The list changed in 2025

The current released edition is OWASP Top 10:2025. OWASP describes it as a standard awareness document for developers and web application security. It groups related weaknesses into broad risk categories. It is not a claim that every vulnerability fits into ten isolated boxes.

The category order matters less in an interview than recognizing the failure, the attacker's path, and the control that breaks that path. Still, use the current names:

  1. A01 Broken Access Control
  2. A02 Security Misconfiguration
  3. A03 Software Supply Chain Failures
  4. A04 Cryptographic Failures
  5. A05 Injection
  6. A06 Insecure Design
  7. A07 Authentication Failures
  8. A08 Software or Data Integrity Failures
  9. A09 Security Logging and Alerting Failures
  10. A10 Mishandling of Exceptional Conditions

SSRF is a version trap. It was A10 in 2021. In 2025, OWASP rolled Server-Side Request Forgery into A01 Broken Access Control, and A10 became Mishandling of Exceptional Conditions.

Wrong "I memorized the 2021 names, so SSRF is still A10."

Right "In the 2025 edition, SSRF is mapped into A01. A10 now covers failures such as improper error handling and failing open."

What an attacker exploits in each category

RiskExploit pathMain prevention direction
Broken Access ControlChange an object ID, call an admin endpoint, tamper with a token, or make the server request a protected network targetDeny by default and enforce permissions in trusted server-side code for every object and action
Security MisconfigurationAbuse default accounts, unnecessary services, open cloud permissions, missing security headers, or verbose errorsAutomate a minimal, repeatable hardened configuration and verify every environment
Software Supply Chain FailuresReach production through vulnerable or malicious dependencies, build tools, repositories, or updatesTrack direct and transitive components, maintain an SBOM, patch by risk, and protect the build path
Cryptographic FailuresRead cleartext traffic or stored data, crack weak password hashes, steal keys, or exploit weak randomnessClassify sensitive data, use trusted cryptographic implementations, manage keys, and use adaptive salted password hashing
InjectionPut untrusted text into SQL, a shell command, an LDAP query, or another interpreter so data becomes executable structureKeep data separate from commands with parameterized interfaces or safe APIs
Insecure DesignAbuse a business flow because a needed control was never designed, such as unlimited expensive operations or an unsafe state transitionDefine security requirements, model threats and failure states, and use secure design patterns before implementation
Authentication FailuresReuse breached credentials, brute-force passwords, fix a session, or exploit weak account recoveryUse established authentication controls, protect sessions, block automation, and use multi-factor authentication where possible
Software or Data Integrity FailuresMake the application trust an unsigned update, an unverified artifact, or attacker-modified serialized dataVerify source and integrity with signatures or similar mechanisms and protect CI/CD changes
Security Logging and Alerting FailuresContinue an attack because failures are not recorded, monitored, alerted on, or protected from tamperingLog security-control successes and failures with useful context, monitor them, and connect alerts to response
Mishandling of Exceptional ConditionsTrigger missing parameters, resource failures, or other abnormal states that crash, leak details, corrupt state, or bypass a controlHandle errors near their source, fail securely, add a global fallback, and monitor repeated error patterns

The web-security and security-backend topics cover the underlying browser and backend mechanisms. Here, the goal is classification and control selection.

Authentication is not authorization

Authentication answers who the caller is. Access control decides what that caller may do. An endpoint can authenticate every request and still expose another user's record:

app.get("/accounts/:id", requireLogin, async (req, res) => {
  const account = await accounts.find(req.params.id);
  res.json(account);
});

The server must enforce the permission for the requested record. Hiding the endpoint in the UI or making identifiers hard to guess does not add that permission check.

app.get("/accounts/:id", requireLogin, async (req, res) => {
  const account = await accounts.findAuthorizedFor(
    req.user.id,
    req.params.id,
  );
  if (!account) return res.sendStatus(404);
  res.json(account);
});

Wrong "The user is logged in, so any account ID they send is authorized."

Right "The server checks the caller's permission for this object and operation on every request."

Injection changes the interpreter's program

Injection is not the presence of suspicious punctuation. It occurs when untrusted input reaches an interpreter and changes commands or query structure. OWASP's primary SQL defense is a prepared statement with parameter binding:

String query =
    "SELECT account_balance FROM user_data WHERE user_name = ?";
PreparedStatement statement = connection.prepareStatement(query);
statement.setString(1, customerName);
ResultSet results = statement.executeQuery();

The SQL is defined before the value is bound, so the database distinguishes code from data. Input validation remains useful, but it does not replace parameterization. The same principle applies to other interpreters: avoid assembling commands from attacker-controlled strings.

[ middle depth ]

Start from the exploit path

For the OWASP Top 10:2025, a useful answer has four parts: trust boundary, attacker-controlled input or action, security impact, and the control that prevents or contains it. Merely naming A01 or A05 is taxonomy recall.

Consider an authenticated export endpoint that interpolates an account ID into SQL. It has two independent failures. Missing object authorization is A01 Broken Access Control. String-built SQL is A05 Injection. Parameterizing the query does not decide whether the caller owns the account, and an ownership check does not make string-built SQL safe.

String query =
    "SELECT * FROM accounts WHERE owner_id = ? AND account_id = ?";
PreparedStatement statement = connection.prepareStatement(query);
statement.setString(1, currentUserId);
statement.setString(2, requestedAccountId);
ResultSet results = statement.executeQuery();

This example binds both values and scopes the lookup to the caller. The application's actual authorization policy may be richer than ownership, but it must run in trusted server-side code. OWASP also recommends logging access-control failures and applying least privilege so a successful exploit has less reach.

Wrong "Validation solves both issues because only numeric IDs reach the query."

Right "Validation checks expected shape. Authorization decides permission, and parameterization separates SQL code from values."

SSRF is an access path through the server

SSRF abuses an application into interacting with an internal or external network, or with the machine itself. Common entry points include avatar importers, webhooks, callbacks, and services that retrieve a user-provided resource. The attacker uses the application's network position and privileges, so the target may be unreachable from the public internet.

SSRF is not limited to HTTP. OWASP notes that server-side clients may reach other protocols and schemes. A check that rejects the literal text localhost is therefore too narrow. Redirects, alternate IP representations, IPv6, and DNS results can defeat naive string filters.

When the application only needs known destinations, OWASP recommends an allowlist and network-layer restrictions. Do not accept a complete user-controlled URL when a fixed destination plus bounded business data is enough. For example, a Node service using Axios can select a code-owned destination and disable redirect following:

const payrollTargets = {
  cyprus: "https://payroll.internal.example/v1/import",
  ireland: "https://payroll-ie.internal.example/v1/import",
};

const target = payrollTargets[req.body.region];
if (!target) return res.sendStatus(400);

await axios.post(target, validatedEmployeePayload, {
  maxRedirects: 0,
});

The allowlist comparison and disabled redirect following address application-layer bypasses. Egress firewall rules should still limit the service to legitimate flows. If arbitrary public destinations are a business requirement, OWASP's guidance becomes more involved: validate address formats with established libraries, resolve and check all IPv4 and IPv6 results, restrict schemes, disable redirects, and block access to internal, local, and link-local targets. URL filtering alone is not an impenetrable defense.

In the 2025 list, CWE-918 SSRF is mapped into A01 Broken Access Control. A useful threat model for that placement is that the attacker induces the server to cross a boundary the caller could not cross directly.

Cryptographic failures begin with data classification

A04 includes missing cryptography, weak algorithms, key leakage, weak randomness, nonce or IV misuse, and certificate-validation errors. "Encrypt the database" is incomplete because the team must first identify sensitive data in transit and at rest, then select controls and retention rules for it.

OWASP recommends trusted cryptographic implementations, proper key management, authenticated encryption, cryptographic randomness where required, and strong adaptive salted hashing for passwords. Password hashing is intentionally different from reversible encryption:

password -> adaptive salted password hash -> stored verifier
sensitive record -> authenticated encryption with managed key -> ciphertext

Wrong "SHA-256 is strong, so a fast unsalted SHA-256 password hash is adequate."

Right "OWASP calls for a strong adaptive and salted password-hashing function with a work factor, such as Argon2, yescrypt, scrypt, or PBKDF2-HMAC-SHA-512."

Keeping keys beside ciphertext or checking them into source control removes much of the intended separation. OWASP recommends storing the most sensitive keys in a hardware or cloud-based HSM and rotating keys through a proper key-management process.

The other six categories are different control layers

A02 Security Misconfiguration covers insecure settings across the application, framework, database, cloud service, and server. Examples include default accounts, unnecessary features, open permissions, and verbose errors. The mitigation is a minimal, automated hardening process with configuration verification across environments.

A03 Software Supply Chain Failures reaches across dependencies, build tools, repositories, distribution, and updates. Track direct and transitive dependencies, generate an SBOM, remove unused components, scan regularly, protect the pipeline with least privilege, and patch in a risk-based time frame.

A06 Insecure Design means a required control is missing or ineffective in the design. A perfect implementation cannot supply a control that was never specified. Threat modeling, security requirements, expected and failure flows, and abuse-case testing belong before code review.

A07 Authentication Failures covers invalid users being accepted as legitimate through credential stuffing, brute force, weak recovery, missing multi-factor authentication, session fixation, or incorrect token invalidation. Use established authentication mechanisms and test the complete session lifecycle.

A08 Software or Data Integrity Failures concerns trusting code or data without verifying it. Signed updates, verified artifacts, protected CI/CD changes, and integrity checks on untrusted serialized data are representative controls.

A09 Security Logging and Alerting Failures exists when attacks cannot be detected or acted on. Logs need security context, tamper protection, monitoring, alert thresholds, and a response path. A file full of unreviewed events does not provide detection.

A10 Mishandling of Exceptional Conditions is new in 2025. Attackers can provoke abnormal states that leak information, corrupt state, crash the service, or cause a control to fail open. Handle errors where they occur, add a global fallback, return controlled messages, and alert on repeated patterns.

[ senior depth ]

Treat the Top 10 as a review index

OWASP calls the Top 10:2025 a standard awareness document. It is a compact index into families of weaknesses, not evidence that an application is secure. The 2025 edition contains 248 CWEs across ten categories, with overlap that OWASP says is unavoidable.

The list is data-informed rather than blindly data-driven. OWASP ranked twelve candidate categories from contributed data, selected eight categories from that data, and promoted or highlighted two through a community survey. The survey compensates for emerging and hard-to-test risks that large testing datasets can miss.

The prevalence calculation asks whether an application had at least one instance of a CWE. It does not give extra weight when one scanner reports the same weakness 4,000 times in one application. OWASP also combines prevalence with CVE exploitability and technical impact data. A senior answer should therefore avoid reading the rank as a universal priority order for one company. Local assets, exposure, threat actors, and business impact still drive remediation.

Wrong "A03 ranks above A05, so every dependency finding must be fixed before any SQL injection."

Right "The ranking is an awareness framework built from population data and survey input. A reachable SQL injection against critical data can outrank a low-impact dependency finding in a specific system."

Map categories to engineering evidence

A Top 10 review is useful when each category demands evidence from a different part of delivery:

CategoryEvidence to request
A01 Broken Access ControlServer-side authorization policy, object and function-level tests, deny-by-default behavior, SSRF egress boundaries, access-denial alerts
A02 Security MisconfigurationVersioned hardening baseline, minimal installed features, environment verification, cloud permission review, controlled error responses
A03 Software Supply Chain FailuresSBOM, direct and transitive dependency inventory, trusted repositories, protected build path, separation of duties, patch process
A04 Cryptographic FailuresData classification, retention limits, approved cryptographic implementations, key custody and rotation, password-hashing configuration
A05 InjectionParameterized interpreter interfaces, review of unavoidable dynamic structure, server-side validation, least-privilege runtime accounts
A06 Insecure DesignThreat model, abuse cases, security requirements, expected and failure-state design, tests for business limits
A07 Authentication FailuresMulti-factor authentication where possible, automation defenses, breached-password checks, secure recovery, session rotation and invalidation tests
A08 Software or Data Integrity FailuresSignature or equivalent integrity verification for artifacts and updates, protected code changes, rejection of untrusted serialized data
A09 Security Logging and Alerting FailuresSecurity-event schema, tamper protection, retention, tested alert thresholds, escalation playbooks
A10 Mishandling of Exceptional ConditionsFail-secure behavior, local error handling, global fallback, controlled messages, repeated-error monitoring

This mapping also prevents tool monoculture. A dependency scanner can contribute evidence for A03. It cannot prove that record ownership is enforced, an abuse case was designed out, alerts reach a responder, or an authorization service fails securely.

Root cause boundaries interviewers probe

OWASP's 2025 structure prefers root causes over symptoms where possible. Three boundaries are especially useful in review conversations.

First, A06 Insecure Design and implementation defects need different remedies. If a transfer flow never defined a business limit or a safe failure state, linting the implementation cannot invent the missing requirement. If the design requires object authorization but one handler omits the check, the design may be sound while the implementation is vulnerable.

Second, A03 and A08 both touch software artifacts but at different levels. A03 covers breakdowns or compromises across the dependency, build, distribution, and update ecosystem. A08 focuses on accepting particular software or data as trusted without verifying integrity. An unmaintained transitive dependency belongs in A03. Applying an update without checking its signature is an A08 example, though a real incident can cross both categories.

Third, A02 and A10 can both expose errors. A02 includes a stack trace exposed because central error-response configuration is insecure. A10 covers abnormal conditions that are not prevented, detected, or handled safely, including fail-open behavior. Classification should point to the corrective owner and control, not force a single label when the causes overlap.

SSRF needs an architectural answer

The 2025 edition rolls SSRF into A01 Broken Access Control. One useful threat model is a confused deputy: the attacker uses the application to reach a network or machine resource outside the caller's intended authority.

An allowlist works when legitimate destinations are known. OWASP advises strict comparison against identified trusted destinations, disabling redirect following, and restricting network routes. When arbitrary public destinations are required, the application must account for IPv4, IPv6, DNS resolution, local and link-local addresses, schemes, and redirects. Network egress controls provide another boundary if URL validation is bypassed.

service: webhook-dispatcher
egress:
  allow:
    - public-http-via-controlled-proxy
  deny:
    - loopback
    - link-local
    - private-service-networks
    - cloud-metadata-endpoints
http-client:
  follow-redirects: false
  allowed-schemes: [https]

This is an architectural policy sketch, not portable firewall syntax. Its value is that the code-level URL decision and the network-level route decision are independently reviewable.

Wrong "Parse the hostname once and reject strings that start with 127.."

Right "Use established parsers, validate every resolved IPv4 and IPv6 address against the policy, disable redirects, and enforce egress restrictions outside the application."

Controls should compose

Take SQL injection. Parameter binding keeps values separate from SQL structure. Server-side authorization limits which rows a caller may request. A least-privilege database account contains damage if another flaw remains. Security logging and alerting make repeated failures visible. These controls correspond to A05, A01, A05's defense in depth, and A09 without pretending one control solves all four.

String query =
    "SELECT balance FROM accounts WHERE owner_id = ? AND account_id = ?";
PreparedStatement statement = connection.prepareStatement(query);
statement.setString(1, currentUserId);
statement.setString(2, requestedAccountId);
ResultSet results = statement.executeQuery();

OWASP discourages escaping all user input as the primary SQL injection defense because it is database-specific and fragile. Parameterized queries define the SQL first and bind values later. Where SQL identifiers or sort direction must vary and cannot be bound, map a bounded user choice to a code-owned identifier instead of copying arbitrary input into the statement.

String sortDirection = switch (requestedSort) {
  case "oldest" -> "ASC";
  case "newest" -> "DESC";
  default -> throw new InputValidationException("unknown sort order");
};

The review ends with residual risk and ownership: which exploit paths remain, which layer contains them, which signal detects them, and who responds. A passed checklist without that evidence is awareness activity, not a security conclusion.

dig deeper

Primary sources behind these notes - the specs and official docs worth reading in full.

beta

The interviewer part is in the works.

The diagnostic, personal maps, and AI mock interviews are being finished right now. The notes stay free either way. Leave an email and you'll get the first-cohort invite, plus a month of Pro when it opens.

builds on

more Backend Security

was this useful?