Sitemap

How I Passed OSWE: The System That Actually Worked for Me

6 min readApr 26, 2026

--

Press enter or click to view image in full size

The OSWE exam is not a bug bounty. You don’t find one vulnerability, write it up, and move on. The exam wants a full compromise, and if you found SQL injection but can’t turn it into remote code execution, you’re not done. That expectation changed how I prepared for everything.

The mindset shift that made the difference

When I started, I was asking the wrong question. “Does this app have SQL injection?” is a terrible question because it leads to random testing. The right question is “where does user input touch a SQL query, and what stands between those two points?” That small reframe changes everything about how you read code and how you test.

Three ideas became the backbone of how I worked. First, every vulnerability is a path from something the attacker controls to somewhere dangerous, and your job is to check whether the stuff in the middle actually blocks that path or just looks like it does. Second, a finding that doesn’t chain to anything bigger is almost worthless under time pressure. A blind SQLi that leaks one character per request becomes interesting when it gets you a password reset token, which gets you into an admin panel, which has an XML import feature, which reads an SSH key. Third, features tell you where bugs live. File upload means think path traversal. Sortable search results mean think ORDER BY injection. You don’t guess, you look at the feature and the feature points you somewhere.

What I studied before the course even started

I spent two months studying each vulnerability class before I bought the course. SQL injection across four database engines, SSTI across sixteen template engines, XXE, deserialization in five languages, prototype pollution, SSRF, authentication bypass patterns. By the time the labs started, I wasn’t learning what these bugs were. I was learning how to chain them and how to find them fast in a large codebase.

Hack The Box trained my enumeration habits. Nobody gives you the vulnerability on the homepage there, and pushing through that frustration built instincts I used on exam day. PortSwigger Web Security Academy gave me structured depth on each vulnerability class, and their white-box labs where source code is provided are the closest thing publicly available to what OSWE actually tests. PentesterLab is where I learned to find bugs through code review specifically, which is the core of what this cert is about.

The habit that paid off more than any platform was reading disclosed HackerOne bug bounty reports. Not to copy payloads, but to understand the reasoning behind each bypass. Why XOR instead of OR? What makes a polyglot payload work? That kind of thinking means you’re never starting from zero when you hit a filter.

The methodology I applied to every target

I used the same four phases whether I was in a practice lab or on the actual exam.

The first phase was always mapping the application for 20 to 30 minutes before writing a single payload or opening any source code. Tech stack identification from headers, cookies, and error messages. Role enumeration. Mapping every feature and every input vector with Burp Proxy capturing everything. File uploads, sort parameters, import and export features, password reset flows, API endpoints, all of it. I skipped this phase once in practice and spent two hours on a complex SQL injection chain before noticing there was an unauthenticated file upload sitting right there the whole time. I never skipped it again.

The second phase was forming specific hypotheses from that feature map. A search feature with column sorting gets tested for ORDER BY injection. An XML-accepting API gets tested for XXE. A password reset flow gets tested for weak token generation. Every test was confirmation or elimination of a specific hypothesis, not random spraying.

The third phase was black-box testing based on those hypotheses. Targeted fuzzing, careful reading of response differences including timing, and writing down every result including “no difference” because a documented negative saves you from re-testing the same thing later.

The fourth phase was white-box code review. Set up the environment properly first, which means error display on, query logging on, debugger attached. Map routes to handler functions before reading any business logic. Then grep for dangerous sink patterns and narrow with negative filters. A search for query.*select returns 200 results. Adding a filter to exclude lines with prepare or setParameter reduces that to five results actually worth reading. Trace user input from source through every transformation to the sink, check sanitization for bypass potential, and validate with a test.

Remote debugging is not advanced, it’s fundamental

I treated debugging as an advanced technique and waited too long to set it up. Setting a breakpoint at a suspicious function and watching the application execute tells you in 60 seconds whether user input actually reaches the sink, what transformations happened along the way, and whether a filter is stripping characters or silently passing them through. That’s more information than an hour of guessing.

Get ABDELKARIM MOUCHQUELITA’s stories in your inbox

Join Medium for free to get updates from this writer.

The thing that bites everyone is the firewall port. Application started with debug flags, debugger listening on all interfaces, port open in the guest firewall, port forwarding working, source code in your IDE matching what’s running. Verify with telnet localhost <PORT> before assuming it works.

Writing exploits without AI assistance

I didn’t use any AI coding tools during preparation. The exam doesn’t allow them, AI-generated exploit code gets subtle encoding and HTTP parsing details wrong in ways that are hard to debug if you don’t understand the mechanism, and honestly the struggle is where the learning happens. Every time I got stuck and had to dig through framework documentation or re-read the source code, I was building instincts that transferred to the next target.

My exploit workflow was always the same. Confirm the vulnerability manually with one request in Burp Repeater before writing any code. Read the source to understand what the vulnerable function expects. Copy the request as Python using Burp’s extension to get a working HTTP skeleton with zero typos. Write a minimal proof of concept. Generalize it. Then chain it to something bigger.

Time management on exam day

The 30-minute rule saved me more than once. If I had spent 30 minutes on a single vulnerability with no progress at all, I stopped and asked whether I was missing a simpler path. Trying increasingly exotic bypass variations is usually a sign the vulnerability isn’t exploitable the way you’re thinking about it. An application with dozens of endpoints has more than one vulnerability.

For priority, SSTI and deserialization get chased first because they often lead directly to RCE. SQL injection with stacked queries is next. XXE is high value because file read can chain to credential extraction which can chain to everything else. Blind SQLi is slow but useful. XSS requires user interaction and goes last.

Things I’d do differently

Set up remote debugging on day one. I waited until month three and lost a lot of time to guessing that a debugger would have resolved immediately.

Practice exploit chains earlier. I spent too long getting good at individual vulnerability classes in isolation. The exam tests the chain: SQLi to auth bypass to admin access to XXE to file read to credential extraction to RCE. That specific skill of linking bugs together needs its own practice time.

Build the grep cheat sheet at the start. I accumulated mine organically over months. If I had compiled it systematically from the beginning, my early code reviews would have been much faster.

Put more time into deserialization and prototype pollution. I over-invested in SQL injection and SSTI. Diversify earlier.

Do more timed practice. Most of my prep was untimed. The triage instincts you need under exam pressure only develop when you practice under exam pressure.

What actually matters

The techniques for OSWE are all publicly documented. SQL injection, SSTI, deserialization, XXE, you can learn all of it for free. What the exam tests is whether you can apply those techniques systematically to an application you’ve never seen before, under time pressure, with no hints. That’s a different skill from knowing the techniques, and it only comes from deliberate practice.

Build the methodology. The knowledge follows.

No lab solutions, exam targets, exploitation paths, flags, or credentials are included in this article. Everything here is methodology and habit, which anyone can build through their own work.

--

--