Hi,

I'm working on a multiligual site, and we sometimes get page not found errors on defaults view that exist. The problem seems to be located in the way Views caches data about these views in _views_discover_default_views().

If the views index is not found, Views invokes hook_views_default_views() and caches them using the current language. It also caches the key 'views_default_views_index' with an index of all views that have been cached. However, Views does not use the language to store the index, and this is the problem. The next time _views_discover_default_views() is invoked, say using a different language, since 'views_default_views_index' exists, it will not try to rebuild the default views, and since these were cached using the language, which is now different, Views is unable to find them.

The fix is pretty simple, I think: Use the current language to cache the default views index too.

 function _views_discover_default_views() {
   static $cache = NULL;

   if (!isset($cache)) {
-    $index = views_cache_get('views_default_views_index');
+    $index = views_cache_get('views_default_views_index', TRUE);

     // Retrieve each cached default view
     if (isset($index->data) && is_array($index->data)) {
       $cache = array();
       foreach ($index->data as $view_name) {
         $data = views_cache_get('views_default:' . $view_name, TRUE);
         if (isset($data->data) && is_object($data->data)) {
           $cache[$view_name] = $data->data;
         }
       }
     }
     // If missing index, rebuild the cache
     else {
       views_include_default_views();
       $defaults = module_invoke_all('views_default_views');
       $cache = array();

       foreach ($defaults as $name => $view) {
         // Only views with a sufficiently high api version are eligible.
         if (isset($view->api_version) && $view->api_version >= 2) {
           // Do not cache dead handlers.
           $view->destroy();
           $cache[$name] = $view;
         }
       }

       // Allow modules to modify default views before they are cached.
       drupal_alter('views_default_views', $cache);

       // Cache the index
       $index = array_keys($cache);
-      views_cache_set('views_default_views_index', $index);
+      views_cache_set('views_default_views_index', $index, TRUE);

       // Cache each view
       foreach ($cache as $name => $view) {
         views_cache_set('views_default:' . $name, $view, TRUE);
       }
     }
   }

   return $cache;
 }
CommentFileSizeAuthor
#2 views-673184-2.patch1013 bytesmarkus_petrux
#1 views-673184-1.patch1014 bytesmarkus_petrux
Support from Acquia helps fund testing for Drupal Acquia logo

Comments

markus_petrux’s picture

FileSize
1014 bytes

Here's the patch against 6.x-2.x-dev (just checked out from cvs).

markus_petrux’s picture

FileSize
1013 bytes

Patch re-rolled due to line offsets.

markus_petrux’s picture

Here's how to reproduce the issue:

1) Enable more than one language in your site.
2) Enable one default view implemented by any module.
3) Clear the Views cache.
4) Visit that default view in your current site language.
5) Now, switch your site language and visit that default view again.

Page not found!

merlinofchaos’s picture

Status: Needs review » Fixed

Committed to all branches. Thanks!

Status: Fixed » Closed (fixed)

Automatically closed -- issue fixed for 2 weeks with no activity.