Magecart skimmer detection is the work of proving, on a schedule, that the code running on your payment page is the code you authorised, and that nothing on that page is sending data somewhere it should not go. It is not a single scan. There is no signature file to buy, because Magecart is a label for a method rather than a group, and dozens of separate crews write their own code to do the same job in different ways.
That is why so many merchants pick one tool, tick a box, and stay blind. Each of the five methods below catches a different class of compromise. Each one misses something another method catches. The honest answer is a layered combination, and the layers are cheaper in licence fees than most vendors would like you to believe. They are not cheap in attention.
What Magecart skimmer detection is actually looking for
Three delivery routes account for almost everything. A third-party supplier script is compromised upstream, and the malicious code arrives on your page from a domain you do not control. First-party JavaScript on your own servers is modified, usually a few lines added to a legitimate bundle. Or the platform itself is breached, through an unpatched version, a stolen admin credential or a vulnerable extension, and the attacker injects code through the database or template layer.
Those three routes need three different detection layers. File integrity monitoring on your own web root will never see a supplier compromise. A CSP report will never see code that posts to a host you already allow. The pattern across the well-documented incidents is consistent on this point: the route in determines which check would have caught it.
Then there is evasion, which is the part most guides skip. Skimmers are written to avoid exactly the conditions under which merchants test. Common behaviour includes firing only on the payment URL, staying dormant until a card field actually contains digits, suppressing entirely for sessions with an admin cookie, and checking the visitor IP against known datacentre ranges so that scanners and bots see clean code. Some target mobile user agents only. Some target one country.
Read plainly, that is: a manual look at your own checkout, from the office, while logged in as an administrator, proves almost nothing.
Finally, separate two outcomes in your head, because tools conflate them. One is catching code that should not be there. The other is catching data leaving for somewhere it should not go. A method that is good at the first is often weak at the second.
Method 1: client-side monitoring with CSP in report-only mode
A Content Security Policy in report-only mode declares what the page is allowed to load and connect to, then reports violations to an endpoint instead of blocking them. Nothing breaks. You get a stream of records naming every script source and outbound connection the browser saw that your policy did not expect.
It is the fastest way to learn what your payment page genuinely loads, which is usually more than the team believes. Run it for a fortnight before enforcing anything. A working checkout CSP setup is mostly an exercise in cataloguing surprises.
What it catches well: new script origins, injected tag-manager containers, and exfiltration beacons to a domain nobody has seen before. Because the report comes from the real shopper’s browser, it sees code that hides from your scanners.
What it misses is the important part. Report-only CSP detects destinations. A skimmer that POSTs stolen card data back to a path on your own domain, or piggybacks on an analytics host already in your policy, produces no violation at all. Nor does it see a DOM change: an attacker who adds a hidden input or rewrites a form action inline is invisible to CSP. Some browsers and extensions drop reports entirely. The report-only header documentation on MDN is worth reading on directive behaviour before you trust the absence of reports.
Practical trap: volume. Browser extensions and ad blockers inject scripts, and they will bury your reporting tier in noise within hours. Filter by directive and by page, keep payment-page reports separate, and decide now who reads them at nine on a Saturday night. Unread alerts are not detection.
Method 2: script inventory, SRI pinning and payment-page change detection
PCI DSS 4.0 requirement 6.4.3 wants a list of every script on the payment page, a written justification for each one, a record of who authorised it, and assurance that each script is what it claims to be. Most merchants have some monitoring in place and no inventory. That fails the easier half of the requirement, and it is the half an assessor asks for first.
Subresource Integrity is the integrity half for files you do not host. Pin a hash to the script tag, and the browser refuses to execute the file if a single byte changes. Hash-pinning third-party scripts genuinely detects tampering at the file you pinned.
It says nothing about a brand new script tag injected next to it. It says nothing about a supplier who serves different code to different visitors. And it carries a failure mode nobody warns you about: a legitimate supplier update breaks the hash, a payment feature stops loading on a Friday afternoon, someone removes the integrity attribute to restore service, and it is never reinstated. If you pin, you need a change process with the supplier and a ticket that reinstates the hash.
The broader answer, and the practical route to requirement 11.6.1, is automated diffing. Fetch the payment page, record the HTML, the HTTP response headers, the full list of script sources and the body of each first-party script, hash the lot, and compare against the last known-good snapshot. Alert on difference. Review the difference. Approve or investigate.
What this misses: conditional serving. If a supplier sends clean code to your diffing job and skimmer code to a shopper in Manchester on an iPhone, your snapshot stays identical for weeks.
Method 3: server-side code review and file integrity on the platform
This is the layer that catches modified first-party JavaScript. Read the checkout bundle and the theme files. You are looking for one-liners appended after the final newline, base64 or hex blobs, unexpected event listeners attached to card and CVV fields, and anything that builds a URL from concatenated strings.
Check entry points as well as output. Admin accounts and their last login times. Extension and plugin versions against current releases. Database-stored content, which on Magento means layout XML, CMS blocks and widget instances, because injection there survives a clean file deploy. Cron jobs. Template variables that allow PHP or JavaScript evaluation.
Pattern-based scanning with the open rule sets now circulating is a reasonable first sweep. Treat it as a sweep, not a verdict. Skimmers are obfuscated specifically to defeat string matching, and a clean scan result means your scanner did not match, not that your site is clean. The manual checks for malicious JavaScript still find things automated rules walk past.
What this misses entirely is the supplier you do not host. Ticketmaster UK, June 2018: the skimming code reached the payment page through the Inbenta customer support chat script, a file Ticketmaster neither wrote nor served. No amount of file integrity monitoring on their own servers would have flagged it. The ICO fined Ticketmaster UK £1.25 million in November 2020 over that breach.
Method 4: synthetic checkout runs that behave like a real shopper
Drive a headless browser all the way through: add to basket, enter an address, reach the payment step, type digits into the card field. Record every network request and response, every script that loads, and every mutation to the DOM. Compare today’s run with yesterday’s.
The run has to look human, or the skimmer will not perform for it. That means egress that does not resolve to an obvious cloud range, realistic typing with delays rather than instant value-setting, no leftover automation flags in the browser, a session that is not logged in as staff, and a card field that is actually populated. Most skimmers wait for digits before they activate. An empty form sees nothing.
Vary the shape of the run. Mobile user agent one night, desktop the next. Different UK regions if you can manage it. Country-specific and device-specific targeting is common enough that a single fixed profile is a known blind spot.
What it misses: a skimmer keyed to genuine payment submission with a real card, which no synthetic run will ever trigger safely, and the hours between runs. A nightly job leaves roughly twenty-three hours uncovered. That is usually acceptable. It should be a decision, not an accident.
Method 5: outside signals you did not generate yourself
Your acquirer or a card scheme contacts you about a common point of purchase: a set of compromised cards whose only shared history is your shop. Customers email about a second card prompt, an odd redirect, or fraud on a card used only once. A supplier discloses a breach. A researcher emails about your domain.
By the time a common point of purchase alert arrives, the skimmer has usually been live for weeks and the data is already being sold. Treat outside signals as confirmation, never as your detection layer. But build the route in anyway: a monitored inbox, a support macro that escalates anything mentioning a duplicate payment form, and a named person who reads supplier security bulletins. For many merchants this is still the signal that lands first, which is an uncomfortable thing to be true.
Which combination fits your checkout
For a small UK merchant, a workable stack is report-only CSP on the payment page with a free reporting tier, a nightly headless checkout run with full request logging, a weekly hash diff of payment-page HTML, headers and scripts, a written script inventory kept in the same repository as the code, and one named person who reads the alerts. The licence cost can be nothing. The real cost is perhaps an hour a week of someone competent, plus the initial fortnight of CSP noise reduction.
A multi-brand estate adds a fourth problem: consistency. Each brand has its own tag manager, its own marketing team adding scripts, and its own idea of what the payment page contains. Centralise the inventory and the alert routing or the estate drifts within a quarter.
On compliance, requirements 6.4.3 and 11.6.1 of PCI DSS 4.0 stopped being future-dated on 31 March 2025 and are now in force; the standard itself is published by the PCI Security Standards Council. Requirement 11.6.1 expects tamper detection on payment-page scripts and HTTP headers with alerting, evaluated at least weekly unless a targeted risk analysis supports a different frequency. Methods 1, 2 and 4 cover the detection side; method 2 produces the inventory. The detail of what each requirement asks for matters when an assessor wants evidence rather than assurances; note that the PCI SSC’s revised SAQ A, published in January 2025, removed 6.4.3 and 11.6.1 for merchants who meet its eligibility criteria, so check the current SAQ A version before assuming either applies to you.
Moving card entry into a payment provider’s iframe is still the single most effective reduction in scope. Hosted payment fields put the input boxes inside the provider’s origin, where script in your page cannot read the keystrokes. What they do not stop is an attacker hiding that iframe and laying a convincing fake card form over the top, collecting the details, then passing them through so the payment succeeds. Page-level change detection still earns its place on a reduced-scope checkout.
Whatever you build, give it an owner, a weekly slot in a calendar, and an alert destination a human actually looks at. Detection schemes do not usually fail technically. They lapse in month two.
The short version
- Report-only CSP sees unexpected destinations, not content, and never sees data posted to your own domain.
- SRI proves a pinned file is unchanged, and proves nothing about a new script tag beside it.
- Server-side review catches modified first-party code; British Airways in 2018 is the case in point, and the ICO issued a £20 million penalty in October 2020.
- Platform and admin hygiene is detection too: Sansec recorded roughly 2,000 Magento 1 stores compromised over a single weekend in September 2020 through an unpatched platform.
- Synthetic checkout runs must look like a shopper, with a filled card field, or the skimmer stays asleep.
- Outside signals arrive last. Plan for them, do not rely on them.
Frequently Asked Questions
What is the fastest way to tell if a Magecart skimmer is on my checkout?
Open the payment page in a private window on a normal connection, not as an admin, fill the card field with test digits, and watch the network tab for requests to any host you do not recognise. It takes a few minutes and requires no tooling. A clean result is reassuring rather than conclusive, because cloaking is designed to produce exactly that result.
Can a Content Security Policy detect a skimmer on its own?
No. CSP reports violations of allowed sources and destinations, so it catches code loaded from a new domain or data sent to one. A skimmer that exfiltrates to a path on your own site, or to an analytics host already in your policy, generates no report. Pair it with content-level change detection.
Does Subresource Integrity catch injected skimmer code?
Only in the file you pinned. If an attacker modifies that exact file, the browser refuses to run it and the tampering is obvious. If the attacker adds a new script tag, injects inline code, or the supplier serves different code conditionally, SRI is silent.
How often does PCI DSS 4.0 expect payment-page change detection to run?
Requirement 11.6.1 expects the mechanism to evaluate payment-page scripts and HTTP headers at least once every seven days, or at a different frequency supported by a documented targeted risk analysis. The requirement has been mandatory since 31 March 2025. Keep the evidence of each evaluation, not just the tooling.
If I use hosted payment fields, do I still need skimmer detection?
Yes, at a reduced level. The provider’s iframe keeps card keystrokes out of reach of script in your page, which removes the most common attack. It does not prevent an attacker from hiding the iframe and overlaying a fake form, so monitoring the page for unauthorised changes remains worthwhile.
