Broken Link Checker: Documentation
Detecting dead links, broken images and image files missing from disk on PrestaShop 8 and 9. Installation, scan settings, reading results, fixing and troubleshooting.
Installation
Requirements
- PrestaShop 8.0 to 9.x
- PHP 7.4 minimum, 8.1 or above recommended
- The PHP cURL extension for HTTP checking
- The PHP DOM extension recommended for link extraction (a regular expression fallback takes over if it is missing)
Installing the module
- Download
dfbrokenlinks.zipfrom your customer account. - Go to Modules, Module Manager, Upload a module and drop the ZIP in. You can also upload the
dfbrokenlinks/folder into/modules/over FTP. - Click Install.
Installation creates four SQL tables (ps_dfbl_scan, ps_dfbl_url, ps_dfbl_occurrence, ps_dfbl_ignore) and one back-office tab.
Where to find it
The scanner sits under Catalog, Broken links & images. The module configuration page, in the Module Manager, shows a summary of the last scan and a button that takes you to the scanner.
Running a first scan
Open Catalog, Broken links & images and click Start a new scan. The default settings suit most shops, you can refine them afterwards.
The two phases
A scan runs in two stages:
- Collection. The module walks the content types you ticked, extracts every link and image, deduplicates the URLs, and checks on disk the image files referenced in the database.
- Verification. The remaining URLs are queried over HTTP, several at a time, to read their status code.
The browser drives progress through successive calls. Each call works for the duration set in the settings (12 seconds by default), saves its position in the database, then hands back control. This is what lets a large catalogue run through without ever exceeding max_execution_time.
Following progress
The progress bar shows the current phase. During verification, a counter gives the number of URLs already tested against the total collected. The six counters under the bar update as the scan goes.
Stopping and resuming
The Stop button ends the scan cleanly. Closing the browser tab has the same effect with no loss: the position is saved after every batch. A stopped scan keeps the results already obtained, which stay visible in the table.
Settings
The Scan settings panel is collapsed by default and opens with the icon at the top right of the block.
Content to scan
Each checkbox is one source. Sources carrying a files badge generate no HTTP request at all: they verify that files exist on disk.
- Products: description, short description, in-stock and out-of-stock availability messages
- Categories: description, plus
additional_descriptionif your PrestaShop version has that column - CMS pages: content
- CMS categories: description
- Brands: description and short description
- Suppliers: description
- Stores: note, address line 1 and line 2
- Footer link blocks: custom content from the
ps_linklistmodule - Product image files: presence in
img/p/ - Category, brand, supplier and store image files: presence in
img/c/,img/m/,img/su/,img/st/ - Product attachments: presence in the
download/folder
A source whose table does not exist on your installation, for instance the link blocks when ps_linklist is absent, simply does not appear in the list.
Languages
By default every active language is scanned. Unticking languages shortens collection but leaves links unchecked in the translations you skipped. Useful for a quick first pass, worth switching back to full coverage afterwards.
HTTP options
- Request timeout: maximum time allowed for a complete response. 10 seconds by default. Beyond that the URL counts as dead with a timeout message.
- Connect timeout: maximum time to establish the connection. 5 seconds by default. A domain whose DNS no longer resolves fails here.
- Parallel requests: from 1 to 20, 6 by default. Raising it speeds the scan up but increases outbound load and the risk of rate limiting on remote servers.
- Check internal URLs: on by default. Local URLs pointing at a static file present on disk are validated without a network request anyway, so this option only concerns URLs that go through the PrestaShop router.
- Check external URLs: on by default. Turning it off gives a very fast scan limited to your own content.
- Follow redirects: on by default, five hops maximum. The final code is then the destination’s.
- Report redirected URLs as warnings: on by default. A URL answering 200 after a redirect shows up as a warning, which lets you spot links worth updating even though they still work.
- Verify SSL certificates: off by default. Turn it on if you want expired certificates flagged, keeping in mind that some badly configured servers will then report as errors.
- Only scan active items: off by default. Once ticked, disabled products and categories drop out of scope.
- User agent: the string sent in the header. Some sites answer 403 to identified bots. Replacing the value with a recent browser string clears a good share of those cases.
Batch pacing
Seconds of work per batch sets how long each call works. 12 seconds by default. This value must stay well under your host’s max_execution_time, safety margin included.
Excluded URLs
One pattern per line. Three notations are accepted:
- Plain text: substring match.
staging.mydomain.comexcludes every URL containing that string. - Wildcards:
*stands for any run of characters,?for a single one.https://*.partner.tld/*excludes every subdomain of that partner. - Regular expression: prefix with
re:. The pattern is applied as written, with no delimiters.
A typical list looks like this:
localhost
127.0.0.1
staging.mydomain.com
https://*.partner-network.tld/*
re:^https://[a-z0-9-]+[.]internal-cdn[.]net/
Writing a literal dot as [.] inside a regular expression avoids escaping issues, and is equivalent to the escaped form.
Excluded URLs appear in the table with the ignored status and consume no request.
Reading the results
The six counters
- URLs found: unique URLs collected across every source
- Dead: failing URLs and files, all categories combined
- Warnings: cases worth a look, without urgency
- Dead images: among the dead, those found in an image tag inside content
- Missing files: among the dead, files absent from disk
- Healthy: everything answering correctly
The statuses
- Healthy: 2xx code, or local file present on disk
- Warning: redirect, 401, 403, 429, or a URL reached after a redirect when the matching option is on
- Dead: 404, 410, other 4xx, 5xx, timeout, DNS error, refused connection, or a file absent from disk
- Ignored: URL covered by your exclusions, or added to the ignore list from the table
- Skipped: URL belonging to a category you disabled in the settings, internal or external
The table is sorted by severity, then by usage count. The problems most widespread across the catalogue rise to the top.
Filters and search
The status filter opens on Problems only, which combines dead and warnings. The other filters cover resource type (link, image, local file) and source. The search box queries both the URL and the error message, so you can isolate every Connection timed out in one go.
Location detail
The eye icon opens the list of content using that URL. Each row gives:
- the source type (Products, CMS pages, Brands and so on)
- the item name and its identifier
- the field concerned (
description,description_short,content) - the language
- the anchor text of the link, or the alt attribute for an image
- an Edit button that opens the record in a new tab
A URL present in 34 product records shows as a single row in the table, with 34 locations in the detail. You see the scale of the problem before you start fixing anything.
Fixing
Dead links inside content
Open the detail, click Edit for the location you want, correct or remove the link in the editor, save. If the same URL appears in several languages of the same product, each language is listed separately: PrestaShop stores one body of content per language, so each version needs fixing.
Missing image files
These rows show a path rather than a URL, for example img/p/4/2/9/429.jpg. The file is gone while the database still references it. Three ways out:
- The file exists in a backup: restore it at the path shown.
- The image is gone for good: delete it from the product’s Images tab so the database stops referencing it, then upload a replacement.
- Thumbnails are missing too: after restoring or re-uploading, regenerate them from Design, Image settings.
PS_IMAGE_FORMAT setting. The module treats the file as present as soon as one of jpg, jpeg, png, webp, avif or gif is found. A file is only reported missing when none of those variants exists.
Rechecking a URL
The refresh icon re-runs the check on a single row. Status and code update in place, without re-running the whole scan. Handy after a partner has fixed a page or you have put a file back online.
Ignoring a URL
The ban icon adds the URL to the ignore list. It leaves the table and will not be reported in later scans. The ignore list is kept independently of scans, so it survives the automatic purge.
CSV export
The Export CSV button exports the result set exactly as filtered on screen. The file uses a semicolon separator and starts with a UTF-8 BOM, so Excel opens accented characters directly without going through the import wizard.
Exported columns: URL, type, scope, status, HTTP code, error, redirect, response time in milliseconds, usage count, sources, items concerned.
Large catalogues and performance
Where the time goes
Collection is fast: it reads the database and parses HTML. Scan time comes almost entirely from HTTP verification, and more precisely from how fast remote servers answer. Two mechanisms keep the bill down:
- Deduplication. A URL present 400 times is tested once. On a catalogue where the same size-guide link is copied into every product, the difference is considerable.
- Local validation. A URL on your own domain pointing at an existing static file is validated by reading the filesystem, with no network request. That covers most images inside descriptions.
Suggested settings by size
- Under 500 products: defaults are fine, change nothing.
- 500 to 5,000 products: 6 to 8 parallel requests, 12 to 15 seconds per batch.
- Over 5,000 products: start with a scan with external URLs switched off to deal with your own links and images first, then run a full scan outside business hours.
Shared hosting
On shared hosting, drop parallel requests to 2 or 3 and keep 10 seconds per batch. If you notice the storefront slowing during a scan, turn off internal URL checking: local static files are still verified on disk, you only lose the test on URLs going through the router.
Multistore
The scan scope follows the shop context selected in the back-office top bar. Tables carrying a shop identifier column, such as ps_product_lang or ps_category_lang, are filtered accordingly. To cover a network of three shops, run three scans, switching context between each.
Troubleshooting
The scan seems stuck on the collection phase
Collection shows no detailed counter, so it can look frozen on a very large catalogue while it is actually progressing. Check your browser’s network tab: calls should follow one another roughly every twelve seconds. If a call returns a 500 error, lower the seconds of work per batch and start again.
Lots of 403s on links that work in the browser
Cloudflare and bot protections block requests not identified as a browser. Replace the user agent with a recent Chrome or Firefox string. If the domain stays blocked, add it to the exclusions: it is not a dead link, it is a link that cannot be verified from a script.
SSL certificate problem error
The remote site’s certificate is not validated by your server’s certificate store. If you do not need certificate checking, untick Verify SSL certificates. If the message concerns your own domain, that is a real problem to handle server side.
Every internal URL comes back as an error
Your server cannot call itself, which is common behind a reverse proxy or with unusual internal DNS resolution. Untick Check internal URLs. Missing image files and external links are still detected normally.
Images reported missing while they display fine
Check the path shown in the table. If the file does exist at that location, the cause is almost always a PHP read restriction: check the permissions on the img/ folder and the open_basedir directive.
The banner says cURL is not available
The PHP cURL extension is not installed on your hosting. Ask your host to enable it. In the meantime the module stays usable for missing image files on disk, which do not go through the network.
Technical reference
SQL tables
ps_dfbl_scan: one row per scan, with its phase, resume position and countersps_dfbl_url: the unique URLs of a scan, with their fingerprint, status and HTTP resultps_dfbl_occurrence: the locations, tied to a URL and to a piece of catalogue contentps_dfbl_ignore: the ignore list, independent of scans
Only the last three scans are kept. When a new scan starts, older ones are deleted along with their URLs and locations.
Extracted attributes
The module reads the following attributes in your content HTML:
- a tag:
href - area tag:
href - img tag:
src,data-src,data-original,data-lazy,srcset - source and video tags:
src,srcset,poster - audio, iframe, embed tags:
src - object tag:
data - link and script tags:
href,src styleattribute: anybackground-image: url(...)
Discarded before any check: mailto:, tel:, sms:, callto:, javascript:, data URIs, bare anchors, schemes other than HTTP and HTTPS, and any value containing braces or brackets, which signal a Smarty or shortcode leftover.
Relative URLs are resolved against the shop base URL, honouring . and .. segments. Protocol-relative URLs starting with two slashes inherit the shop scheme. The fragment after the hash is stripped before the request.
Controller and architecture
A single admin controller, AdminDfBrokenLinks, serves the page and the AJAX endpoints. The module declares no hook. Classes are loaded by direct inclusion, with no Composer and no external dependency.
Uninstalling
From the Module Manager, uninstall Broken Links & Images Checker. The four tables, the back-office tab and every configuration key are removed.
ps_dfbl_ignore table is dropped on uninstall. If you have built up a long list of manual exclusions, export it or copy the excluded URLs field before uninstalling.
FAQ
Does the module modify my content?
No. It reads your content and writes only to its own tables. Every fix goes through the standard PrestaShop back office.
Can I schedule an automatic scan?
Version 1.0.0 triggers scans from the back office, with the browser acting as conductor. There is no cron task. In practice a monthly scan started by hand covers most catalogues.
Why does a URL show as a warning when it answers 200?
Because it was reached after a redirect and the Report redirected URLs as warnings option is on. The link works, but it makes your visitors and Google take a pointless hop. Putting the destination URL directly in the content is better.
Does it detect links inside third-party modules?
It scans content stored in standard PrestaShop tables plus the ps_linklist link blocks. A third-party module storing its own text in its own tables is not covered.
Do scans use much bandwidth?
Every check starts with a HEAD request, which fetches headers only. The GET fallback, used when the remote server rejects HEAD, caps the download at the first two kilobytes. The volume stays marginal.
How many scans are kept?
The last three. Enough to compare a before and after state without letting the database grow indefinitely.
Is the module GDPR compliant?
It stores no personal data: only URLs, HTTP codes and references to your content. Nothing is transmitted to DataFirefly.