Okay... I will probably ramble quite a bit, mostly owing to a grossly incomplete understanding of drupal's node access system ... but please bear with me.

Problem: domain access module starts throwing sql errors whenever complex domain access rules are enabled.

Versions:

  • Drupal: 5.7
  • Domain Access: 5.x.1.4
  • MySQL: 5.0.51a (dev) & 5.0.45 (production)
  • PHP: 5.2.3 (dev) & 5.2.5 (production)
  • Apache: 2.2.4 Win32 (dev) & 2.2.8 (production

After much tracing, hair pulling and sulphurous exclamatory comments (!) ...

node.module, function node_access_view_all_nodes (line 2839) builds an SQL query on the node_access table, using a grants array that is generated with a call to function node_access_grants (node.module, line 2824).

Function node_access_grants calls function

module_invoke_all('node_grants'...)

which, amongst many others, calls function domain_node_grants (domain.module, line 665). When complex access rules are enabled, function domain_node_grants includes an array element 'groups' with a value of 'domain' which on return, is interpreted as a gid of value 'domain' instead of a numeric value - this is mindlessly included in the SQL query where it is interpreted as a field name - which does not exist - hence the SQL error being generated.

I have no clear idea of *WHY* this array element needs to be inserted here so I'm not willing to meddle with it at this point in time... but the problem can be stepped around with a slight patch to node.module.

file node.module, function node_access_view_all_nodes() starts at line 2839.

Line 2844 calls node_access_grants to form the associative grants array and then steps through the array for each value of realm and associated array of gids.

The next line steps through the array of gids, generating a phrase of SQL for each realm/gid combination.

  foreach (node_access_grants('view') as $realm => $gids) {
    foreach ($gids as $gid) {
      $grants[] = "(gid = $gid AND realm = '$realm')";
    }
  }

Because of the associative element 'group' => 'domain' coming from domain_node_grants, an incorrect SQL phrase is generated here.

If the inner foreach loop is changed slightly to return associative keys as well as the element values, the key can be tested and ignored if it is a string. For the gid elements, which were not entered as associative elements, $ix returns a numeric value which is the array ordinal for that element.

  foreach (node_access_grants('view') as $realm => $gids) {
    foreach ($gids as $ix => $gid) {
      if (!is_string($ix) {
        $grants[] = "(gid = $gid AND realm = '$realm')";
      }
    }
  }

... and this *seems* to overcome the problem.

Obviously it would be preferable to handle this problem in domain.module rather than patching the core module node.module (e.g. by not returning the 'group' => 'domain' element in the grants array) but, as I said, I don't know *why* the element is being inserted so I am leaving it alone lest I generate even worse problems by removing it.

Comments

agentrickard’s picture

Status: Active » Closed (fixed)

It sounds like you did not install the multiple_node_access.patch included in the download. Please see INSTALL.txt

----
3.1 multiple_node_access.patch

You should apply this patch only if you use Domain Access along with
another Node Access module, such as Organic Groups (OG).

The multiple_node_access.patch allows Drupal to run more than one
node access control scheme in parallel.  Instead of using OR logic to
determine node access, this patch uses subselects to enable AND logic
for multiple node access rules.

WARNING: This patch uses subselect statements and requires pgSQL or
MySQL 4.1 or higher.

Developers: see http://drupal.org/node/191375 for more information.

This patch is being submitted to Drupal core for version 7.

For more information, see http://drupal.org/patch/apply

alansch’s picture

Category: bug » support
Priority: Normal » Minor

Hmmmm... I *did* apply the patch, using GnuWin32, but I've just been over the patch file line by line manually to check my *supposedly* patched copy of node.module and discovered the following...

@@ -2731,22 +2731,19 @@ function node_access($op, $node = NULL)
was applied correctly
@@ -2793,17 +2790,7 @@ function _node_access_where_sql($op = 'v
was *not* applied
@@ -2833,7 +2820,6 @@ function node_access_grants($op, $uid =
is trivial - removal of one blank line - but was applied
@@ -2844,18 +2830,7 @@ function node_access_view_all_nodes() {
was *not* applied
@@ -2865,6 +2840,87 @@ function node_access_view_all_nodes() {
was applied

I did check this previously, but I just confirmed the first patch segment had been applied and ass-u-me'd the entire patch had applied correctly.

Okay, now I've gone through node.module and manually applied the missing patch segments and an initial quick test on the development server seems to indicate the SQL errors have gone. I will now slink away with a red face and my tail between my legs and test more thoroughly.

Thanks for the assist.

agentrickard’s picture

Status: Closed (fixed) » Postponed (maintainer needs more info)

Just checking: That patch should be current for Drupal 5.7.

Was this user error or an error with the patch file?

agentrickard’s picture

Status: Postponed (maintainer needs more info) » Closed (fixed)

Patch applies cleanly to Drupal 5.7.