I have the following rule for Book pages: book/[bookpath-raw]/[title-raw]. I guess it's a reasonable choice for books, but I have a book with a lot of subpages, so the paths are long. This means, they get truncated. One would expect that -0, -1, etc should appear at the end of the paths, and for mostly it works. However, let's see the paths I got after auto-generation:

book/operator-kezikonyv/szemelyi-ugyek-regisztraciok/operatorra-valas-lepesei/4-a-dc-n-kivuli-vila-0	node/578
book/operator-kezikonyv/szemelyi-ugyek-regisztraciok/operatorra-valas-lepesei/4-a-dc-n-kivuli-vila-1	node/579
book/operator-kezikonyv/szemelyi-ugyek-regisztraciok/operatorra-valas-lepesei/4-a-dc-n-kivuli-vila-2	node/580
book/operator-kezikonyv/szemelyi-ugyek-regisztraciok/operatorra-valas-lepesei/4-a-dc-n-kivuli-vilag	node/377
book/operator-kezikonyv/szemelyi-ugyek-regisztraciok/operatorra-valas-lepesei/4-a-dc-n-kivuli-vilag/	node/577

The auto-generated path for node 377 is a complete path, not truncated, because that's the "parent" of the other book pages listed here. However, the path for node 577 is truncated because it's too long to fit. Unfortunately, the length of the generated path for node 377 is "allowed length minus 1", so when the path is generated for node 577, it becomes longer by a single character which would be the /-sign. For pathauto, these are different paths, so no -0, -1, etc is added. But when you try to visit it from the browser, you are always redirected to node377 because for browsers http://www.google.com is totally the same as http://www.google.com/ .

I think the solution would be to verify is the generated path ends with /. If it does, then it should be truncated, and if the truncated path already exists, -0, -1, should be added. I assume that during normal usage this only can happen when you use / as a spearator in the middle of a path, not sure if any other "normal" use case could trigger it.

#1 1037142-1-strip-trailing-slashes.patch531 bytesjagopian
PASSED: [[SimpleTest]]: [MySQL] 0 pass(es). View


jagopian’s picture

531 bytes
PASSED: [[SimpleTest]]: [MySQL] 0 pass(es). View

This patch should fix your problem ;)

jagopian’s picture

Version:6.x-1.5» 6.x-1.x-dev
Status:Active» Needs review

i forgot to change the status

Dave Reid’s picture

Title:/-sign should be truncated automatically from the very end of generated paths» When creating unique variants, aliases can end up with a trailing slash or delimiter
Version:6.x-1.x-dev» 7.x-1.x-dev
Assigned:Unassigned» Dave Reid
Status:Needs review» Active

Ah, I know where this is coming from and can duplicate it. And it's not where #1 is patching.

The problem is here:

  // If the alias already exists, generate a new, hopefully unique, variant
  if (_pathauto_alias_exists($alias, $source, $language)) {
    $maxlength = min(variable_get('pathauto_max_length', 100), _pathauto_get_schema_alias_maxlength());
    $separator = variable_get('pathauto_separator', '-');
    $original_alias = $alias;

    $i = 0;
    do {
      // Append an incrementing numeric suffix until we find a unique alias.
      $unique_suffix = $separator . $i;
      $alias = pathauto_truncate_utf8($original_alias, $maxlength - drupal_strlen($unique_suffix, TRUE)) . $unique_suffix;
    } while (_pathauto_alias_exists($alias, $source, $language));

    // Alert the user why this happened.
    _pathauto_verbose(t('The automatically generated alias %original_alias conflicted with an existing alias. Alias changed to %alias.', array(
      '%original_alias' => $original_alias,
      '%alias' => $alias,
    )), $op);

The call to pathauto_truncate_utf8 is not passing in TRUE for the $wordsafe parameter, which would prevent this.

DeFr’s picture

@#3: That seems wrong, because this code isn't hit.

Consider carefully the op situation, and the alias that would be generated untruncated for the first subpage, namely when you're in the situation where:

  • book/operator-kezikonyv/szemelyi-ugyek-regisztraciok/operatorra-valas-lepesei/4-a-dc-n-kivuli-vilag <= That's the parent page alias, it already exists
  • book/operator-kezikonyv/szemelyi-ugyek-regisztraciok/operatorra-valas-lepesei/4-a-dc-n-kivuli-vilag/whatever <= That's the first subpage we're creating

After pathauto_clean_alias, the second one will be truncated to book/operator-kezikonyv/szemelyi-ugyek-regisztraciok/operatorra-valas-lepesei/4-a-dc-n-kivuli-vilag/ ; pathauto_alias_exists only checks for exact matches, and the version with a trailing / isn't the same as the one with one, so it'll return FALSE and the whole while loop is skipped.

As far as I can tell, pathauto_clean_alias is the place to fix this.

Dave Reid’s picture

Correct - the 6.x-2.x branch and above use a different method to trim, but they will have the same problem in the end, so I have to fix this minor bug in 7.x-1.x, 6.x-2.x, then fix it separately in 6.x-1.x.

j_nunes’s picture

I have a small script that runs a .CSV file of names to programmatically create taxonomy terms.
I am trying to have a single path alias for single taxonomy term names but "The automatically generated alias (term_name) conflicted with an existing alias". Alias changed to "term_name-0" (And so on..)
It keeps iterating to term_name-0, term_name-1, term_name-2, etc.. for some of the taxonomy terms (not always).

I set this up to [term:name] to create path alias and also a combination of settings in update actions but no luck.
I trying looking at the redirect module and global redirect also, but none of them is helping me preventing the term_name-0 to be used.