Out of the box, Paid Memberships Pro will give you many options to lock down your WordPress posts and pages. You may need to restrict access to protected files as well. This recipe will show you how to lock down files in your WordPress media library using Paid Memberships Pro.

Understanding File Protection

Protecting files in your WordPress site requires a few additional restriction steps at the server level. We don’t enable file protection by default in core PMPro because of these server considerations. In order to protect files, you will need:

  1. The ability to add rewrite rules by editing the .htaccess file.
  2. The ability to edit the WordPress wp-config.php file.
  3. Enough memory on your server to serve files through a PHP script.
  4. To make sure your uploads folder is not served by a CDN (e.g. with WP Engine and some other hosts)

With respect to item 3 above, the amount of memory available to your site will limit how large of a file you can serve protected. For example, after enabling file protection, you may be able to serve a 1MB image, but not a 50MB PowerPoint document. We recommend testing a few files that are the size you intend to share to make sure your server has enough memory to support file protection.

Note that this method is only applicable to files uploaded through the “Media” library in your WordPress site. If you wish to lock down files and directories outside of WordPress, you can view the tutorial here.

How to Lock Files for Members Only

Follow the steps below to add file protection for members only to your WordPress membership site.

  1. Add this line to your wp-config.php file

  2. For sites hosted with Apache, add this code to your .htaccess file, above the # BEGIN WordPress line.

    Make sure there are no line breaks/text wrap after adding this rule to your .htaccess file. This rule may need to be adjusted for sites that have WordPress installed in a subdirectory or if the paths on your setup are different.

    For sites hosted with NGINX, add this code to your NGINX config file, below the other WP rules. Again, this rule may need to be adjusted for sites that have WordPress installed in a subdirectory or if the paths on your setup are different.

  3. Alternately, you can adjust the .htaccess rule to lock specific file types only.

    The following rule will lock down only pdf, doc, docx, ppt, and zip files.This adjustment avoids running images and other static files that might be in your uploads folder through the getfile.php script, which can slow sites down. You can change the protected file extensions to the specific file types you need to protect.

  4. Here is the version of that rule you would use for NGINX servers:

  5. Make sure your files are “attached” to protected posts. Files uploaded from the edit post screen are attached to that post. Files uploaded to the Media Library directly are unattached. To check a file’s attachment, find it in the Media Library and check the “Uploaded To” tab. From there, you can detach it or attach it to the correct protected post.

Once you’ve completed these steps, test the protection by uploading a file to a page or post that requires membership to access. The attached file will require the same membership level(s) to view.

Be careful when trying to protect images. Besides potentially putting strain on your server if you have a lot of images that don’t need protection, WordPress will create resized versions of image files, and PMPro is not clever enough yet to associate the resized versions with the attached post.

How this Method of File Protection Works

What’s happening here is that any link to a file in /wp-content/uploads/.../ will be routed through the getfile.php script before it loads in the browser. That script figures out the post the file is attached to, then checks if the logged-in user has access to that post. If so, the file is served through the script. If not, a 503 error is shown.

Let me know how this works for you. If you have any issues, post something to the forums here. We will try to help you through any issues you are having.

Note that this kind of functionality is highly reliant on your server setup and you may need to hire a developer or pay extra to have someone set this up fully.

Tagged . Bookmark the . Last updated: . Titled

Don’t know if this can be of any help to others but I tried to maintain speed by applying the rewriting rule only to files with “onlymembers” or “onlyreaders” in their name.

RewriteBase /
RewriteCond “%{REQUEST_URI}” “onlymembers” [NC,OR]
RewriteCond “%{REQUEST_URI}” “onlyreaders” [NC]
RewriteRule ^wp-content/uploads/(.*)$ /wp-content/plugins/paid-memberships-pro/services/getfile.php [R,L]

Works fine for me.


Hi, It’s possible only protect files in a subdirectory like this
wp-content / uploads / myfolder

Update: I fixed it! Info in case the moderator chooses to publish my traumas to help others…

The rewrite rule had a couple of issues 1) my site is in a subdirectory so the leading / 404s all requests. 2) the wild card filename selector needs to be outside of the brackets.

I also added a selector for just this month to maintain speed on all existing unprotected resources. Thus:
RewriteRule ^wp-content/uploads/2019/06/.*(\.pdf|\.doc|\.docx|\.pptx|\.zip)$ wp-content/plugins/paid-memberships-pro/services/getfile.php [L]

PS File protection is based upon the post a resources is FIRST uploaded to.
Thanks all

Hi Jason or Travis,

For ease or experimentation, I tried this foolishly on a PDF used in another post. Everything worked great. However, after removing the reference to this PDF from a members only page to which I’ve added the media, the PDF remains protected from non-members.

How can I make my download available again for an established, Google indexed PDF? It’s not my browser cache. I’ve purged my LightSpeed server cache.


While the image files are not able to be accessed by using the permalink, they are still accessed by using the File URL (by copying the image address). Is there a specific way to set up my media files for this method to work?

Hi there,

The tutorial shows how to do this.

Note – that the media files must be stored in the wp-content/uploads/ folder and must have been uploaded (attached) to a member restricted post in order for the files to be restricted.

It’s also possible that the rewrite rules are off (maybe due to WP being installed in a different directory). You can test the rewrite rules by using [R,L] instead of [L] to see if visiting the image URLs is really redirected to the getfile.php script.

If you open up a support topic on our support forums we can take a closer look into this for you.

Hi Travis Lima,
Is it possible to protect acccess to pdf files and not the page/post where it is attached ?

Thanks for your awnser

This is an excellent hack. Is there a way to show a default or specified page rather than the 503 error? I’m concerned about a lot of 503 errors in log files.

Hej Jason, can you tell me how to lock my .mp3 files. It works fine with my .pdf’s but it is not protecting my mp3 files
Aby ideas?


This solutions seems to work fine for none-logged in users, and serach engines.

I might have found a case that I would love to eliminate.

> In this case someone waiting for approval for a level and are a subscriber can still download the file if they know the url.

> When going to the page they get the right message that the page is restricted, but for the file they arev prompted to download

Any ideas?


Seems this script doesn’t work with url encoded filenames.
So I added $uri = urldecode($uri); on line 37 of getfile.php


Does anyone know a nginx NGINX version of the HTACCESS rule? I am getting an error because of the [L] possibly.

Hi Jason,
Is it necessary to have the folder I want to protect in the wp-content folder only or can I have it in the public_html folder too?

Once I sign up for the pro subscription and incase I’m not able to figure out how to block it would you help me achieve that?

Looking forward for your response.


I assume the directory needs to be within wp-content correct? is there a way to protect files that are in the main public_html folder as well?

I’m considering using PMP for a site that will have different protected content for different membership levels. I have looked all over for the answer to this question: Does PMP provide a search mechanism for the protected content? I want my members to be able to search all those protected pages/documents – but don’t want them accessible without logging in to the site.

There is an option on the advanced settings tab of the PMPro settings on whether or not to filter searches for non-members. If you choose “no” it will show the excerpt (make sure your theme is set to show excerpts in search results) to non-members, but they won’t have access to the full post when clicking through.

If you run into any trouble getting this setup (some themes make this tricky), we can help in the member forums, but you should be okay just switching that one setting.

This is preventing Jetpack from generating thumbnails. Is there a way to allow jetpack access? Perhaps allowing the wp.com domain access? Let me know if there are any ideas.

If you use Jetpack image galleries (e.g. tiled mosaic), this will disable preview images. Jetpack needs to access the images to create previews that look something like this: src=”http://i1.wp.com/www.example.com/wp-content/uploads/2015/08/AM3_2633.jpg”

I’ve tried some work-arounds but they all eventually break. I’m not sure if there is a way to allow Jetpack access as if it had a membership.

If you post to our forums, we can help you to work this out. It would make sense to find a way to put protected files in the same folder or name them in a certain way so you can target these files specifically in the .htaccess file.

I’ve added both codes and for some reason it stopped showing all the styling in the theme I am using. So I had to remove the .htaccess code. Would you know why it is doing that and how to prevent it?

Thank you.

Maybe you have a caching plugin or something else combining and serving your CSS and/or style images from the wp-content/uploads/ folder. You could update your .htaccess to ignore certain directories or be more specific about which files to lock down.

Could I change the code to restrict only one file by adding the file name like this?

RewriteRule ^wp-content/uploads/get_me_in_the_kitchen_bit@hes.pdf $

There are issues with how WP Engine does things. Namely I think they offload your wp-content/uploads to a CDN so requests for those files don’t go through apache .htaccess. I believe you can ask their support to turn this off (double check first) and they will. They might be able to turn it off for specific directories. This will slow down your site a bit as loading images/etc over the CDN is faster which is why they do it. But if you want to put a member check in front of files, you have to do something like this.

After I made the changes (back to the lockdown with the additional code to htaccess), my site suddenly became very, very slow. My CPU was maxed out and I was hitting my 2G of memory maximum. My subscribers were complaining. I didn’t correlate it to the htaccess changes until I saw the Google Chrome Network monitor and noticed the images were taking an extremely long time to load, I removed the code from htaccess and everything went back to normal.

Does this code typically affect performance in this way? I have a lot of images on my site. Is there another option for locking down the content?

This is possible, especially if you have a lot of images on your site… or if your site is using a lot of caching that this would disable. The .htaccess code can be updated to check for specific file types or folders/etc so it isn’t run on every single image. If you open something in our member forums, we can help you out there.

I made these changes a couple of months ago, but now my changes are gone. Is it because I’ve been installing updates to PMPro? Or, because of WordPress updates? If so, how do I avoid having to repeat the steps?

Hmmm. Is it the .htaccess changes that are being overwritten? Maybe there is a service on your host or an overzealous WP plugin that is overwriting your htaccess file. In theory, lines outside of the # BEING WORDPRESS and # END WORDPRESS lines should be ignore by WordPress when it updates the htaccess.

Did you make other changes to the core pmpro plugin files? If so, and you let us know what you did (in our member forums) we can show you how to add them to a custom plugin so they aren’t overwritten by updates.

I don’t think I made any other changes. I am going to keep a log of all changes I make. So, if it happens again I will know the cause. Thanks for replying.

You would upload the file to a page or post in WordPress. (Click “add media” button on the edit post page…) If the post or page the file is attached to is locked down for membership, the file will be too if you set this up.

Also, what does the ” [L]” mean at the end of the second RewriteRule? It is not even mentioned in the writeup.

Running the IIS URL Rewriter on your sample .htaccess script fails. It says that the “RewriteBase /” command cannot be translated.

Therefore, my question remains about the appropriate web.conf file to use that will trigger your getfile.php.

For the benefit of readers, here is what the Microsoft URL rewriter converter says is the equivalent web.config content for the .htaccess file example given by Jason:

Thanks for that info, Jason. Your article is very helpful.

For those unfortunate few who are running WordPress on a Windows 2012R2 server, what would the equivalent web.config file look like for a protected directory in the article you posted above and at:

I found an article on the subject of url rewrite equivalents in Windows Server web.config files, but the exact syntax is unclear:

You may also wish to update the above article of yours on the subject as well to address the OTHER half of your user audience.

Thanks in advance for any help you can provide.

I’m now discovering that files on protected pages are not protected and can be found if someone knows the direct link or happens across file links in Google. We have a client that uses this plugin to protect mainly files (pdfs, docs, xls, etc.)… the files are linked to from within posts that are protected. I followed the instructions above and it’s working, but not on files that are already uploaded… so now it seems I have to delete and reupload at least 100 files, before our client discovers that files that we thought were protected, aren’t. Is there any other way around having to delete and re-upload all these files?

actually never mind my comment above, it’s working!! for some reason the first couple files i tested were still showing, until i deleted and reuploaded, but upon further testing other files showed the 503 error. perhaps those first couple files were in the cache. Thank goodness!!

Hi there! I think we might have helped you set this up. If you post to the member forums here we can diagnose and help you with any issues you might be having. Note that files need to be “attached” to posts to inherit the membership levels of that post (you can attach files already upload through the media section of the dashboard), and note that the getfile.php script will serve a 503 error to non-members trying to access files. You can change this to redirect to the levels or checkout page using some code we can share with you in the member forums. Cheers.

Is it possible to block specific file types rather than all media files at once? Like blocking PDFs only, or JPEGs only?

Even when the member has the correct access to the page that the download is on I am usually (but not always) getting a 503 error – is this likely due to memory issues (shared hosting)? The files are not big – much less than 1Mb.

I just paid for a membership to get access to this info (I want to be able to restrict access to media files on one of my sites), and it doesn’t work! I’m using WP multi-site, and the URL that is linked to the media file is http://domain.com/files/2013/12/img001.jpg but the directory structure is actually /wp-content/blogs.dir/8/files/… Any ideas? Really, I only want the files from that one blog (number 8) to be protected like this.

I also have a subdirectory installation, but when I do your trick I get an internal server error. My WP site is installed on a WAMPserver. Any ideas how I can solve that? Thanks

No more internal error, but the script does not seem to work: download links are still fully responsive. My .htaccess file contains the following:
RewriteBase /
RewriteRule ^wp-content/uploads/(.*)$ /wp-content/plugins/paid-memberships-pro/services/getfile.php [L]
# BEGIN WordPress

# END WordPress

[…] Version 2.0.3 of Memberlite theme is out with enhancements to the shortcode, additional color settings in Customize screen for primary navigation, a new theme customizer option to load a “dark” stylesheet (for dark/inverted backgrounds), improved formatting for comments and a tabbed display for separating comments, pingbacks and trackbacks (see demo on this post). […]

Leave a Reply

For faster support related to issues on your specific site please open a ticket in our members support area.

Your email address will not be published. Required fields are marked *