Why My WordPress Subdomain Didn’t Load Media Files From CDN While the Main Domain Did and the CORS Header Addition That Fixed It

If you’ve recently set up a WordPress subdomain on your site and configured it to use a Content Delivery Network (CDN) for serving media files, you might have run into a puzzling issue: your main domain loads all assets from the CDN perfectly, but the subdomain does not. This can be especially frustrating when everything seems configured correctly—CDN URLs are set, caching is working, and yet, images or JavaScript files served via CDN just won’t load on the subdomain. 

TL;DR

The issue likely stems from missing Cross-Origin Resource Sharing (CORS) headers on your CDN or server configuration. While your main domain handles media files correctly, a subdomain counts as a different origin and thus requires explicit permission to load media from the CDN. Adding appropriate CORS headers in your CDN settings or via your origin server fixes this by enabling your subdomains to securely access media resources.

Understanding the Problem

At a glance, the directory structure and media URLs from the WordPress Media Library may seem consistent across your main site and subdomain. However, browsers enforce strict same-origin policies when loading external resources, and this is where things can break unexpectedly.

Imagine your main domain is www.example.com and you’ve just launched a new subdomain at blog.example.com. You’ve configured both to serve media files from cdn.examplecdn.com. On your main domain, images, scripts, and stylesheets load from CDN smoothly. But on the subdomain, none of the images load, and you see mysterious CORS errors in the browser console.

Image not found in postmeta

What is CORS and Why Does It Matter?

CORS (Cross-Origin Resource Sharing) is a security feature implemented by browsers to prevent websites from making requests to a different domain (or subdomain) unless the server explicitly allows it. In our case, although both www.example.com and blog.example.com appear to be related, browsers treat them as separate origins.

If the CDN or origin server doesn’t include the right CORS headers—like Access-Control-Allow-Origin—the browser will block the request. This is why your images or scripts fail silently or show errors like:

Access to image at 'https://cdn.examplecdn.com/image.jpg' from origin 'https://blog.example.com' has been blocked by CORS policy. No 'Access-Control-Allow-Origin' header is present on the requested resource.

To summarize—with CORS, the CDN or your origin server needs to acknowledge and permit cross-origin requests. Without this, your subdomain is essentially denied access.

Confirming It’s a CORS Issue

Before jumping into solutions, it’s good to confirm that the issue is indeed CORS-related. Here’s how:

  • Open your browser’s Developer Tools (F12 or right-click > Inspect).
  • Go to the Console or Network tab.
  • Reload the page on the subdomain and check for errors marked in red.

If the CORS header is missing or misconfigured, you’ll see error messages mentioning ‘blocked by CORS policy’ or ‘No Access-Control-Allow-Origin header’.

Why the Main Domain Worked But Subdomain Didn’t

This confusion often arises because most browsers allow same-origin requests implicitly—this means that as long as your main domain and CDN configuration are both aligned (e.g., through rewriting URLs), the CDN doesn’t have to do anything special.

However, your subdomain is considered a different origin from the main domain. Even though it’s part of the same family of domains, to the browser, blog.example.comwww.example.com. So, without the proper CORS headers saying, “Yes, this subdomain can use files from the CDN,” the browser blocks it.

Lesson Learned: Your CDN needs to serve files with the correct CORS headers if you plan to use the same CDN across multiple subdomains.

How I Fixed It: The Magic of CORS Headers

Once I identified the problem as missing CORS headers, the solution became a matter of configuring my server and CDN to send the correct response. Here’s how I added them:

1. Adding Headers via CDN Dashboard

If you’re using a CDN provider like Cloudflare, Bunny.net, KeyCDN, or AWS CloudFront, you can usually configure CORS headers in their management console.

Here’s what I did:

  • Logged into my CDN provider’s dashboard.
  • Found the section for HTTP Headers or Custom Rules.
  • Added the following header rule to allow all subdomains:
Access-Control-Allow-Origin: *

Alternatively, to be more secure and specific, you could replace * with https://blog.example.com.

2. Configuring the Origin Server (.htaccess Example)

If your CDN pulls from an origin server and doesn’t modify headers, you might also need to update the origin. For Apache, here’s how you can do it in your .htaccess file:


  Header set Access-Control-Allow-Origin "*"

If you only want to allow a specific subdomain:


  Header set Access-Control-Allow-Origin "https://blog.example.com"

For Nginx:

add_header 'Access-Control-Allow-Origin' '*';

After saving and restarting your server/CDN, the issues disappeared almost instantly. All my subdomain media files loaded as expected.

Don’t Forget About Preflight Requests

When it comes to API calls or JavaScript-heavy assets, browsers might send a CORS preflight request—an extra OPTIONS call to check permissions. In such cases, you also need to support these headers:

Access-Control-Allow-Methods: GET, POST, OPTIONS
Access-Control-Allow-Headers: Content-Type
Access-Control-Max-Age: 86400

Most CDNs let you configure this in full, but if you’re self-hosting or using a more basic CDN, you may need to explicitly define these on the origin server.

Final Thoughts and Tips

If you’re building or scaling a WordPress-powered site that uses a CDN across multiple subdomains, make CORS header configuration a top priority during initial setup. The symptoms of a misconfigured setup may be subtle—silent script fails, missing images, or JS runtime errors—but the impact on UX and performance is huge.

Here are some quick tips to keep in mind:

  • Always test CDN access separately for each subdomain you use.
  • Prefer specific allowed origins over a wildcard, especially for sensitive data.
  • Review CDN settings after any update or migration—they may reset headers.
  • Use browser dev tools to get clarity on what is and isn’t loading correctly.

Conclusion

The mismatch between your WordPress main domain and subdomain when loading CDN media files often boils down to the overlooked CORS policy. While the main domain may seem to work ‘by magic’, subdomains demand explicit permission to access assets.

By understanding how CORS works and configuring your headers properly—either via your CDN or origin server—you make sure that all parts of your WordPress ecosystem can reliably access media assets, no matter the domain.

It’s one of those small tweaks that provide big peace of mind—and better performance for your users.

Happy coding!

Share
 
Ava Taylor
I'm Ava Taylor, a freelance web designer and blogger. Discussing web design trends, CSS tricks, and front-end development is my passion.