- Match calibre's URL prefix with the exact path forwarded by your proxy.
- Use browser and server logs to identify failed assets, redirects, and authentication.
- Test calibre directly before changing firewalls, libraries, or installation files.
- Confirm the Symptom With a Small Safe Test
- Match the Reverse Proxy Layout to calibre
- Check Proxy Headers, HTTPS, and Authentication
- Diagnose Static Assets, Paths, and Connection Upgrades
- Check the Operating System and Network Boundary
- Use Logs to Identify the Failing Layer
- Run a Clean Temporary Test Before Reinstalling
- Quick Fix Checklist
- Frequently Asked Questions
When the calibre Content server works directly at http://127.0.0.1:8080 but fails through Nginx, Apache, Caddy, or another reverse proxy, the calibre library itself is usually not the problem. The failure is more often caused by a mismatched URL prefix, an incorrect proxy path, missing request headers, incompatible authentication settings, HTTPS termination, or blocked asset requests. Symptoms can include a login loop, a blank page, missing covers, unstyled pages, failed downloads, broken book browsing, incorrect redirects, or links that unexpectedly point to an internal address.
The safest approach is to test one layer at a time. First prove that the Content server works directly. Then decide whether calibre will use a dedicated hostname or a path such as /calibre/. Finally, verify that the proxy preserves the path and external request information calibre expects. Stop changing settings as soon as the public URL loads, login works, covers appear, and a book can be opened or downloaded.

Start with free Canva bundles
Browse the freebies page to claim ready-to-use Canva bundles, then get 25% off your first premium bundle after you sign up.
Free to claim. Canva-ready. Instant access.
1. Confirm the Symptom With a Small Safe Test
Before editing a proxy configuration, confirm whether the failure is inside calibre or between the browser and the proxy. This prevents a reverse proxy problem from being confused with a damaged library, an unavailable service, or a blocked local port.
1.1 Test the Content Server Directly
On the computer running calibre, open a current browser and visit:
http://127.0.0.1:8080
Replace 8080 if the Content server uses another port. If you configured a URL prefix, include it in the direct test. For example:
http://127.0.0.1:8080/calibre/
Try these actions during the direct test:
- Open the library list.
- Browse into one library.
- Open a book details page.
- Load a cover image.
- Download or read a book you are authorized to access.
- Sign in if calibre authentication is enabled.
Success looks like this: the page is styled correctly, navigation remains on the expected local address, and book pages load without repeated login prompts. If the direct connection fails, stop adjusting the reverse proxy. Restart the Content server, confirm its port and library path, and resolve the direct server error first.
1.2 Compare Direct and Proxied Results
After the direct test succeeds, open the public address in a private browser window. Use the exact address readers are expected to use, such as https://books.example.com/ or https://example.com/calibre/.
Note the first visible difference:
- A
502or503usually means the proxy cannot reach calibre. - A
404on the main page often indicates a path or prefix mismatch. - A page without styling usually means JavaScript, CSS, or image URLs are being requested from the wrong path.
- A login loop points toward authentication, cookies, HTTPS, or forwarded-header handling.
- A redirect to
127.0.0.1, an internal hostname, or plain HTTP indicates an external URL mismatch. - A working home page with broken book browsing can indicate that only part of the URL space is being proxied.
Change only the setting related to the observed failure. A broad rewrite of several proxy and calibre settings at once makes it difficult to identify the real fix.
2. Match the Reverse Proxy Layout to calibre
The most important configuration decision is whether calibre occupies an entire hostname or appears below a URL prefix. These are different layouts and should not be mixed.
2.1 Use a Full Virtual Host for the Simplest Setup
A dedicated hostname such as books.example.com is usually the least complicated arrangement. The browser requests paths from the root, and the proxy forwards those paths to calibre on its local port. In this layout, do not set a calibre URL prefix unless there is another specific reason to do so.
A minimal Nginx location can resemble:
location / {
proxy_pass http://127.0.0.1:8080;
proxy_set_header Host $host;
proxy_set_header X-Forwarded-Host $host;
proxy_set_header X-Forwarded-Proto $scheme;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
}A basic Caddy site can resemble:
books.example.com {
reverse_proxy 127.0.0.1:8080
}For Apache, the proxy mapping should cover the root path consistently:
<VirtualHost *:443>
ServerName books.example.com
ProxyPreserveHost On
ProxyPass / http://127.0.0.1:8080/
ProxyPassReverse / http://127.0.0.1:8080/
</VirtualHost>These are examples rather than universal drop-in files. Certificate directives, logging, modules, service accounts, and platform-specific paths still depend on the local installation.
Success looks like this: every public link remains under https://books.example.com/, and no link unexpectedly gains a /calibre prefix. Once that happens, do not add prefix rewrites as an extra precaution.
2.2 Configure a URL Prefix on Both Sides
If the public address is https://example.com/calibre/, calibre must know that its application lives below /calibre. Start the standalone server with an equivalent of:
calibre-server --listen-on 127.0.0.1 --port 8080 --url-prefix /calibre "/path/to/Calibre Library"The prefix should begin with one slash and normally should not have a trailing slash in the calibre option. The browser-facing address should normally include the trailing slash: /calibre/.
The official calibre Nginx pattern preserves the complete requested URI instead of stripping the prefix before the request reaches calibre:
location /calibre/ {
proxy_buffering off;
proxy_pass http://127.0.0.1:8080$request_uri;
}
location = /calibre {
return 301 /calibre/;
}With Caddy, be careful with handle_path. That directive strips the matched prefix before proxying. If calibre was started with --url-prefix /calibre, it expects to receive that prefix. A path-preserving handler is therefore the safer pattern:
example.com {
redir /calibre /calibre/ 308
handle /calibre/* {
reverse_proxy 127.0.0.1:8080
}
}For Apache, the official calibre documentation uses rewriting that passes the prefix through to the backend:
AllowEncodedSlashes On
RewriteEngine On
RewriteRule ^/calibre/(.*) http://127.0.0.1:8080/calibre/$1 [P]
RedirectMatch permanent ^/calibre$ /calibre/The critical rule is simple: either preserve /calibre
Success looks like this: the direct URL http://127.0.0.1:8080/calibre/ and the public URL https://example.com/calibre/ both work, while CSS, scripts, covers, searches, and book links remain below /calibre/.
3. Check Proxy Headers, HTTPS, and Authentication
A proxy can deliver the page while still hiding important details about the original request. calibre may receive an HTTP request from localhost even though the reader connected to an HTTPS public hostname. Correct forwarding and compatible authentication settings prevent redirects, login flows, and generated URLs from using the wrong scheme or host.
3.1 Forward the External Host and Scheme
For Nginx, explicitly forwarding the following information is a practical baseline:
proxy_set_header Host $host;
proxy_set_header X-Forwarded-Host $host;
proxy_set_header X-Forwarded-Proto $scheme;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;Do not set X-Forwarded-Proto permanently to http when the public site uses HTTPS. Likewise, avoid replacing the public Host value with 127.0.0.1:8080 unless a documented application requirement calls for it.
Apache users should normally enable ProxyPreserveHost On for a dedicated virtual host. ProxyPassReverse is also useful because it adjusts certain redirect headers returned by the backend. Caddy's standard reverse proxy handles common forwarding behavior automatically, so custom header manipulation should be added only when there is a specific upstream or multi-proxy requirement.
Success looks like this: after signing in or opening a book, the browser stays on the public HTTPS hostname. If redirects and links are correct, stop changing forwarded headers.
3.2 Align calibre Authentication With HTTPS Termination
There may be two separate authentication layers:
- Authentication configured in calibre.
- Authentication configured in Nginx, Apache, Caddy, an identity gateway, or another front-end service.
During troubleshooting, identify which layer is producing the prompt. Two overlapping login systems can produce repeated prompts, unexpected 401 responses, or a successful proxy login followed by a separate calibre login.
If the reverse proxy terminates HTTPS and calibre authentication remains enabled, calibre's documentation recommends using basic authentication mode for the Content server. For a standalone server, the relevant option is:
--auth-mode=basicBasic authentication should be exposed only through HTTPS. The public connection must be encrypted before credentials are sent. Keep the calibre backend limited to localhost or a trusted private network so it cannot be reached directly from the internet.
If a front-end authentication gateway is used, do not assume that it automatically signs the reader into calibre. Unless the integration explicitly supports calibre's authentication model, the two systems remain separate.
Success looks like this: the reader encounters only the intended login flow, valid credentials are accepted once, and subsequent library requests do not return to the login page.
3.3 Avoid Conflicting HTTPS Configurations
The common design is HTTPS between the browser and reverse proxy, then HTTP over localhost between the proxy and calibre. In that arrangement, the proxy owns the certificate and calibre listens on a local HTTP port.
If calibre is also configured for HTTPS, the proxy upstream must use HTTPS and handle certificate validation appropriately. Accidentally sending plain HTTP to a TLS-enabled calibre port, or HTTPS to a plain HTTP port, commonly produces a bad gateway error or a connection reset.
Check for mixed-content errors in the browser console. A page opened over HTTPS should not attempt to load scripts, styles, covers, or API requests over plain HTTP. Fix the external scheme information rather than disabling browser security.
4. Diagnose Static Assets, Paths, and Connection Upgrades
A partially rendered page provides useful evidence. If the text appears but the layout, covers, or controls are missing, the main HTML request reached calibre. The next step is to inspect the individual asset and API requests rather than changing the library.
4.1 Use the Browser Network and Console Panels
Open the browser's developer tools, reload the failing public page, and review the Console and Network panels. Look for:
404responses for JavaScript, CSS, cover images, or API paths.401or403responses after an apparently successful login.502or504responses from the reverse proxy.- Requests missing the expected
/calibre/prefix. - Requests containing the prefix twice, such as
/calibre/calibre/. - Requests sent to
http://from anhttps://page. - Redirects to localhost, an internal port, or an internal hostname.
Click one failed request and compare its Request URL with the intended public URL. A consistent missing or duplicated prefix usually identifies the configuration error immediately.
Success looks like this: a fresh reload has no repeating asset failures, the page has its normal styling, and cover images and controls appear. One unrelated browser-extension warning is not a reason to keep modifying the server.
4.2 Check WebSocket Handling Only When Evidence Points There
Do not add WebSocket directives blindly. First look for failed requests that explicitly use a connection upgrade or for proxy logs showing an upgrade failure. Where WebSocket proxying is relevant, Nginx requires the upgrade information to be passed explicitly because hop-by-hop headers are not forwarded automatically.
A common Nginx pattern is:
proxy_http_version 1.1;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection $connection_upgrade;This is normally paired with an Nginx map that sets $connection_upgrade to upgrade only when appropriate. Caddy's reverse proxy supports upgraded connections without requiring the same manual header pattern in a basic setup.
If the Network panel contains no failed upgrade request, focus on ordinary path, asset, authentication, or forwarded-scheme errors instead.
4.3 Preserve Encoded Paths
Some library and book routes can include encoded characters. Apache rejects encoded path separators by default, which is why the calibre reverse proxy example includes AllowEncodedSlashes On. If the home page works but specific books, searches, or nested routes return 404, compare the failed path in the browser and Apache access log.
Do not solve this by adding broad rewrite rules that decode or rebuild every URL. Start with calibre's documented Apache pattern, then make the smallest adjustment required by the installed Apache configuration.
5. Check the Operating System and Network Boundary
Reverse proxy failures can occur even when both services appear to be running. The proxy process must be able to connect to the exact address and port where calibre is listening.
5.1 Verify the Listening Address
When the proxy and calibre run on the same computer, calibre should normally listen on 127.0.0.1. This reduces exposure and ensures that readers reach it through the protected public proxy.
If the reverse proxy runs in a container, virtual machine, or different computer, its 127.0.0.1 is not the calibre host. Use an appropriate private address, container service name, or host gateway instead. Keep firewall access limited to the proxy system.
A 502 Bad Gateway typically warrants checking:
- Whether the calibre Content server process is running.
- Whether the upstream port matches calibre's configured port.
- Whether another program is using that port.
- Whether the proxy is attempting IPv6 while calibre listens only on IPv4, or the reverse.
- Whether a host firewall blocks the proxy process.
- Whether container networking makes the configured loopback address incorrect.
Success looks like this: the proxy can retrieve the calibre home page from its own execution environment. Once upstream requests return a normal HTTP response, stop changing firewall rules.
5.2 Confirm Service Permissions and Library Access
If calibre runs as a Windows service, launch agent, systemd service, container, or separate user account, that account must be able to read the library directory and its files. A service started under a different account may not see a mapped network drive, mounted volume, cloud folder, or user-specific path that works in the desktop application.
On Linux, run the service as the user that owns or has appropriate access to the library. On Windows, verify the service account and use a stable local or UNC path rather than relying on an interactive user's mapped drive letter. On macOS, confirm that the background process has access to the library location, especially when privacy controls or external volumes are involved.
Cloud synchronization can also temporarily lock or replace database and book files. It is not the first suspect when only the proxied URL fails, but it becomes relevant if direct browsing also reports unavailable books or database errors.

6. Use Logs to Identify the Failing Layer
Logs are most useful when one controlled request is made at a known time. Clear or note the current endpoint, reproduce the failure once, and then compare the browser, proxy, and calibre records.
6.1 Enable calibre Server and Access Logs
The standalone Content server supports separate server and access logs. A diagnostic command can include paths appropriate for the operating system:
calibre-server "/path/to/Calibre Library" \
--listen-on 127.0.0.1 \
--port 8080 \
--log "/path/to/calibre-server.log" \
--access-log "/path/to/calibre-access.log"Add --url-prefix /calibre only if the public deployment actually uses that prefix.
Interpret the result in layers:
- No calibre access-log entry means the request did not reach calibre.
- A calibre
404means the request arrived, but the path was not one calibre recognized. - A calibre
401points toward its authentication layer. - A successful calibre response paired with a browser failure suggests proxy rewriting, response handling, caching, or browser security.
Do not publish logs without reviewing them. They can contain usernames, IP addresses, library names, paths, query strings, and other private details.
6.2 Compare Proxy Access and Error Logs
Nginx, Apache, and Caddy logs can distinguish a routing failure from an upstream failure. Useful details include the public request path, response status, upstream status, selected virtual host, and connection error.
Common clues include:
- Connection refused: wrong port, stopped server, or wrong network address.
- Upstream timed out: unreachable backend, blocked connection, or an operation exceeding a proxy timeout.
- 404 without an upstream entry: the proxy location or route did not match.
- 301 or 302 loop: conflicting slash, scheme, hostname, or authentication redirects.
- Request too large: proxy upload limits are lower than the intended book upload size.
Use calibre-debug only when the ordinary Content server logs indicate an internal calibre failure or when support documentation specifically asks for it. It is not normally the first tool for a proxy path mismatch.
7. Run a Clean Temporary Test Before Reinstalling
Reinstalling calibre rarely fixes a reverse proxy configuration mismatch. Deleting the library is even less appropriate because the proxy does not control calibre's metadata database. A clean temporary test can isolate the configuration without risking the real library.
7.1 Build a Minimal Dedicated-Hostname Test
- Keep a backup of the current proxy configuration.
- Start calibre on an unused local port with one readable test library.
- Do not configure a URL prefix.
- Create a temporary dedicated hostname or local host entry.
- Proxy the entire hostname root to the test port.
- Enable HTTPS and use calibre basic authentication mode if calibre authentication is enabled behind the SSL proxy.
- Test login, browsing, covers, reading, and downloading.
If this clean virtual-host setup works, calibre and the library are healthy. The original failure is probably in the path-prefix rules, middleware, or authentication chain.
7.2 Add Complexity One Change at a Time
After the clean test works, add only one production feature at a time:
- Add the intended authentication layer.
- Add the URL prefix if one is required.
- Add security headers or proxy middleware.
- Add CDN, tunnel, or additional proxy layers.
- Add custom caching or compression rules last.
Retest after every addition. The first change that breaks library browsing identifies the area to correct. Restore the last working configuration instead of continuing to stack speculative fixes.
8. Quick Fix Checklist
- Confirm that calibre works directly on its local address and port.
- Decide between a dedicated hostname and a
/calibre/URL prefix. - Do not configure
--url-prefixfor a root-level dedicated hostname. - For a prefix deployment, use the same prefix publicly and in calibre.
- Preserve the prefix if calibre is configured to receive it.
- Redirect
/calibreto/calibre/. - Forward the original host, client information, and HTTPS scheme appropriately.
- Use
--auth-mode=basicwhen calibre authentication sits behind an HTTPS proxy. - Ensure the public login is protected by HTTPS.
- Check the browser console and Network panel for failed assets and redirects.
- Check proxy logs for routing, upstream, timeout, and connection errors.
- Check calibre access logs to see the exact path received.
- Pass upgrade headers only when a failed upgraded connection is actually involved.
- Allow encoded paths in Apache as required by calibre's documented setup.
- Bind calibre to localhost when the proxy runs on the same computer.
- Use a reachable private address when the proxy runs in another container or host.
- Stop changing settings once login, browsing, covers, reading, and downloads work.
9. Frequently Asked Questions
9.1 Why Does calibre Work on Port 8080 but Not Through My Domain?
This proves that the Content server is running and strongly suggests the failure is in the proxy layer. Check whether the proxy can reach 127.0.0.1:8080 from its own environment, whether the correct virtual host matches the domain, and whether the proxy path agrees with calibre's URL-prefix setting.
9.2 Should I Use a Subdomain or a URL Prefix?
A dedicated hostname such as books.example.com is generally simpler because it avoids prefix stripping and rewriting. A path such as example.com/calibre/ is fully workable, but calibre and the proxy must agree that /calibre is part of every application URL.
9.3 Why Does the Login Page Keep Reappearing?
First identify whether the prompt comes from calibre or the reverse proxy. Then check HTTPS, authentication mode, cookies, redirects, and forwarded host and scheme information. If both the proxy and calibre require separate credentials, two login stages may be expected unless the systems have been intentionally integrated.
9.4 Why Is the Page Blank or Missing Covers and Buttons?
The main HTML may be loading while JavaScript, CSS, images, or API routes return errors. Open the browser Network panel and inspect the failed URLs. Missing, duplicated, or stripped /calibre/ prefixes are common causes. Mixed HTTP and HTTPS requests can produce a similar symptom.
9.5 Do I Need WebSocket Settings for calibre?
Only add special upgrade handling when browser or proxy logs show a failed upgraded connection. Ordinary pages, covers, API requests, and downloads still depend primarily on correct HTTP routing. Caddy handles common connection upgrades automatically, while Nginx may require explicit upgrade headers when such a connection is used.
9.6 Should I Reinstall calibre or Rebuild the Library?
Not if the server works directly. A working direct connection means the installed Content server and library are fundamentally accessible. Test a minimal reverse proxy configuration instead. Reinstallation does not repair a stripped prefix, wrong upstream port, missing forwarded scheme, or authentication conflict.