1

Problem

I'm running a job site where content appears and disappears quickly. This means I end up with a lot of 404s from Google indexing pages only for them to disappear.

I want to redirect all unpublished nodes of a certain type to a particular page, depending on a value on the node and display a drupal message depending on what just happened.

I'm trying to come with a solution which is easy to maintain and will scale, should the site grow to have thousands of nodes.

Has anyone solved this sort of problem? What kind of solution did you use?

My current ideas

  1. Use the redirect module.

I've created a module which will redirect all my nodes when they're unpublished via either a cron action or a form action using the redirect API.

The problem is this creates a lot of redirects. While it might take a while to become unmanageable, several other questions mention the module scales quite well into the thousands I would like it to be future proof is possible.

One option to solve this was to delete unused redirects however because I run Varnish in front as a cache, it is unable to tell which redirects have been active.

  1. Do it server side

I'm running Nginx, I presumably could set up a location block which would redirect all 404s.

If I put the node information I needed in the URL I could just grab it from there and then redirect each set of nodes.

This is an ok solution, but the pages are redirecting to country so there would have to be 330 location blocks in my nginx config, which isn't particularly slick.

It also makes it impossible to set a message on page load.

  1. Use the rules module

You can setup content viewed redirects using the rules modules but unfortunately Varnish caching breaks this.

1

I ended up going with the first option and using the following solution to make sure the redirects never got out of hand:

Basically when a job advert goes down it will get given a 301 redirect. Then I remove every redirect for a job advert older than 3 months.

Hopefully this will remove the worst of the 404 problem because: If Google crawls the link in the three months then it will be redirected and change its index.

If a person comes across it in the three months they'll be correctly redirected and if no-one has bothered to try it for three months then I've probably avoided the 404 problem.

The code just involved calling an extra cron job and then altering a version of the redirect_purge_inactive_redirects(); function.

function redirect_purge_job_redirects(array $types = array('redirect'), $interval = NULL) {
  //set interval in code to 3 months in seconds
  $interval = 7776000;
  $query = db_select('redirect');
  $query->addField('redirect', 'rid');
  if (!empty($types)) {
    $query->condition('type', $types);
  }
  //add in condition here to select all redirects 
  //for the job adverts.
  //the path for all the job adverts begins with job
  //so I look for that.
  $query->condition('redirect', 'job'.'%', 'LIKE');
  $query->condition('access', REQUEST_TIME - $interval, '<');
  $query->addTag('redirect_purge');
  $rids = $query->execute()->fetchCol();

  if (count($rids)) {
    redirect_delete_multiple($rids);
    watchdog('redirect', format_plural(count($rids), 'Removed 1 inactive redirect from the database.', 'Removed @count inactive redirects from the database.'));
    return $rids;
  }
}
  • Came across this answer searching for solutions to the exact same problem - thank you for sharing. In your answer you say "when a job advert goes down it will get given a 301 redirect". Could you elaborate on this? Since the subject of your question was "How to redirect all unpublished nodes of a certain type", it's that bit that I'm really interested in. Could you share more about your module (the one you mentioned in the original post at point 1)? – mozz100 Nov 17 '14 at 15:10
  • It's pretty simple. Although some of it is specific to my site structure. First is a radio form option which if selected is picked up in the validation and then uses the redirect API to create a redirect and forces the node to unpublish. The other is when a node (job ad) is created rules schedules an action to unpublish it a month later and create a redirect. Hope that helps! – Dominic Woodman Nov 17 '14 at 18:13
1

Another option may be to write your own simple module to do the redirect when an unpublished node is loaded/viewed by a user who does not have permission.

You could implement one of the node API hooks to call drupal_goto() if the node is an unpublished one ($node->status == NODE_NOT_PUBLISHED) and the user doesn't have permission. (Use user_access() to check permission)

The one problem may be with the order in which permissions are checked versus those hooks, which at this moment in time I can't quite remember the order things fire with regards hooks for node load/view and user permissions. But hopefully it gives you some ideas.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.