Create a private page with specific content (Drupal 7)
In my two latest Drupal projects, I had to create a simple private page, where logged in users could read chronological articles with one or more attachments.
This seems very easy to accomplish with a powerful CMS like Drupal 7 but it boggled me that this was rather hard to do.
When it comes to the permission and roles system, there is the option to give access to all content (view published content) and to view own unpublished content, but there is no granular control to give access to a specific content type or to a specific page.
What is the goal?
- Publish content of a specific content type ('document') but hide it from view
- Display all the content of this specific content type ('document') on a private page
- Create a private menu to access this page
- All the content is private, including the attachments
Create an extra role
Mostly, when creating a private page, the Editors (the people filling the website with content) want to give users related to the organisation access to some files and documents. Not everyone can be Editor. So, we need an extra role. The best way to go forward with this is to add a role on top of the Authenticated User role.
The Authenticated user role is for every user that is logging in. If you want more access rights, it should go on top of this role. Don't turn them around!
Limit access to specific node pages
There is a trick I often encounter, namely setting content as unpublished and give a role access to unpublished content. I don't like this method, from a UX perspective, because the content is actually published, but only for specific roles. Also, next to unpublish, there's only one option: deleting. And sometimes a client wants to keep the information in the back-end.
When using Rabbit Hole as a module, you can unpublish content without a problem.
Rabbit Hole is a module that adds the ability to control what should happen when an entity is being viewed at its own page. I often use this module. For example, to hide slideshow nodes. Or when you create a View of employees, but without the option to click through to the nodes.
Install Rabbit Hole and enable the base module and the node submodule.
Next, go to the content type and check 'No access'. The content on its own page will only be accessible to the Administrator.
So, now we have hidden all the content, except for the admin, how do we show the content?
Views to the rescue
Views, the most popular module for Drupal 7 (and in core in Drupal 8) allows us to limit access by role.
Create a page with the nodes of the content type we just hide with Rabbit Hole and publish it on a specific path. Then, click Access and Role. Restrict the Role to Authenticated Users, Editors and (of course) the Administrator.
The only disadvantage of this method is that there is no clickthrough to the node itself.
Create a menu
In the current setup, there is no guidance for Authenticated Users that they have access to hidden content.
So, take this step: add a link to the Management Menu, linking to the page we just created, and drag it to the top.
Next, go to the permissions and give the Authenticated Users access to the administration menu.
Now these users will have access to the administration menu with a direct link to the page with all the documents.
Ok, the content should be private at the moment.
Don't forget to check the access to the files. On the file field, there is an option to make the files private. Check that option.
Test the access of the private files on a (staging) server (on localhost it's a different story: it's perfectly possible you can access the files with a private browser window on localhost but not on the live site). If it's not working as expected, check the Private files download permission module.