title: a function to return the quiz nid

text:
# Question
Title: a function to return the quiz nid
There is a template file in the quiz/template/quiz-report-form.tpl.php of Quiz module. this is the code:

```
<?php

/**
 * @file
 * Themes the question report
 *
 * Available variables:
 * $form - FAPI array
 *
 * All questions are in form[x] where x is an integer.
 * Useful values:
 * $form[x]['question'] - the question as a FAPI array(usually a form field of type "markup")
 * $form[x]['score'] - the users score on the current question.(FAPI array usually of type "markup" or "textfield")
 * $form[x]['max_score'] - the max score for the current question.(FAPI array of type "value")
 * $form[x]['response'] - the users response, usually a FAPI array of type markup.
 * $form[x]['#is_correct'] - If the users response is correct(boolean)
 * $form[x]['#is_evaluated'] - If the users response has been evaluated(boolean)
 */
// $td_classes = array('quiz-report-odd-td', 'quiz-report-even-td');
// $td_class_i = 0;
$p = drupal_get_path('module', 'quiz') .'/theme/';
$q_image = $p. 'question_bg.png';
?>
<h2><?php print t('Question Results');?></h2>
<div class="quiz-report">
<?php
foreach ($form as $key => $sub_form):
  if (!is_numeric($key) || isset($sub_form['#no_report'])) continue;
  unset($form[$key]);
  $c_class = ($sub_form['#is_evaluated']) ? ($sub_form['#is_correct']) ? 'q-correct' : 'q-wrong' : 'q-waiting';
  $skipped = $sub_form['#is_skipped'] ? '<span class="quiz-report-skipped">'. t('(skipped)') .'</span>' : ''?>

    <div class="dt">
      <div class="quiz-report-score-container <?php print $c_class?>">
        <span>
          <?php print t('Score')?>
        <?php print drupal_render($sub_form['score'])?>
        <?php print t('of') .' '. $sub_form['max_score']['#value']?>
        <?php print '<br><em>'. $skipped .'</em>'?>
      </span>
    </div>
      <p class="quiz-report-question"><strong><?php print t('Question')?>: </strong></p>
      <?php print drupal_render($sub_form['question']);?>
    </div>
  <div class="dd">
    <p><strong><?php print t('Response')?>: </strong></p>
    <?php print drupal_render($sub_form['response']); ?>
  </div>
  <div class="dd">
    <?php print drupal_render($sub_form['answer_feedback']); ?>
  </div>
<?php endforeach; ?>
</div>
<div class="quiz-score-submit"><?php print drupal_render_children($form);?></div>

```

Now I want to change this codes and I need a function to return the nid(number of id) of quiz that the user is seeing. please help me.

# Answer
> 0 votes
Here is a very simple way to get the nid of the *node currently being viewed*:

```
$path = current_path();
list($entity_type, $entity_id) = explode('/', $path);

```

After this, you will have the entity id (the nid in the case of nodes) in the variable $entity\_id.

---
Tags: 7, quiz
---


# Question
Title: How do I give a role permission to set a site variable?
I have a custom variable in one of my modules and I want to be able to give permission to that variable to a specific role on my site.

I have the hook\_permission function setup and I can see it in the **admin/people/permissions** interface, but I'm not sure how to implement a hook or whatever to give the user access to **admin/config/system/variable/edit/my\_custom\_variable**

# Answer
> 2 votes
One method would be to use something like https://drupal.org/project/config\_perms to add a custom permission to the **admin/config/system/variable/edit/my\_custom\_variable** path. You can then use this custom permission to grant access to it.

# Answer
> 0 votes
In hook\_menu we have:

```
$items['admin/config/system/variable/edit/%'] = array(
  'title' => 'Edit variable',
  'page callback' => 'drupal_get_form',
  'page arguments' => array('variable_edit_form', 5),
  'access callback' => 'variable_access',
  'access arguments' => array(5),
);

```

Now, what's `'access callback'`? By the API:

> **"access callback"**: A function returning TRUE if the user has access rights to this menu item, and FALSE if not. It can also be a boolean constant instead of a function, and you can also use numeric values (will be cast to boolean). Defaults to user\_access() unless a value is inherited from the parent menu item; only MENU\_DEFAULT\_LOCAL\_TASK items can inherit access callbacks. To use the user\_access() default callback, you must specify the permission to check as 'access arguments' (see below).

So the module is using `function variable_access($variable, $account = NULL)` defined in the main `variable.module`. Now, this function uses data provided by `function variable_get_info($name = NULL, $options = array())`, that collects it's data from modules that implements `hook_variable_info()`.

**TL;DR**

In `hook_variable_info()` when defining your variable, set 'access' to an existing permission, or permission your module provides. Then simply give that permission to user roles that should be able to edit variable.

---
Tags: 7, users
---


title: Need help clearing the schema cache

text:
# Question
Title: Need help clearing the schema cache
I am checking of a particular field type in the schema using:

```
drupal_get_schema('MY_FIELD');

```

I see in the database the field type is int, but when I check after:

```
$schema[$table]['fields']['MY_FIELD']['type']

```

is giving me always 'datetime'.

I assume is a cache issue: I am using:

```
cache_clear_all('schema', 'cache');

```

but still no luck.

# Answer
> 2 votes
There are a few different cache entries for the schema, `schema:`, `schema:runtime`, `schema:runtime:1`, and so on.

To clear the lot, try using a wildcard:

```
cache_clear_all('schema', 'cache', TRUE);

```

---
Tags: database
---


# Question
Title: cookie is being stored as different value
I have the following code:

```
if(isset($ret["token"])) {
    drupal_set_message("TOKEN: " . $ret["token"]);
    user_cookie_save(array("my_token"=>$ret["token"]));
    drupal_set_message("KEY: " . $_COOKIE['Drupal_visitor_my_token']);
  }

```

Here is the printout of values:

```
TOKEN: 339497878
KEY: 354541465

```

Why am I getting different values?

# Answer
`$_COOKIE` superglobal contains values that was in cookies at the moment of HTTP request. Setting new cookies does not affect / update this array - new value will be available at *next* page load.
> 2 votes

---
Tags: users, cookies
---


title: Different in theme as table and page

text:
# Question
Title: Different in theme as table and page
I am studying the pager\_example in example module.
When creating an render array, it first assign #theme as 'table'. But it assign the #theme as 'pager' just before returning.
What is the purpose of attach the pager theme ?
pager\_example.module:

```
// Create a render array ($build) which will be themed as a table with a
// pager.
$build['pager_table'] = array(
  '#theme' => 'table',
  '#header' => $header,
  '#rows' => $rows,
  '#empty' => t('There are no date formats found in the db'),
);

// attach the pager theme
$build['pager_pager'] = array('#theme' => 'pager');  <---- why need this ?
return $build[];

```

Then I remove the coding "$build\['pager\_pager'\] = array('#theme' =\> 'pager');". The result is the same.
When compare to tablesort\_example.module, it don't have attach the pager theme before the return.
tablesort\_example.module:

```
// build the table for the nice output.
$build['tablesort_table'] = array(
  '#theme' => 'table',
  '#header' => $header,
  '#rows' => $rows,
);

return $build;

```

# Answer
The code `$build['pager_pager'] = array('#theme' => 'pager');` returns the pager for the table.

The example module output with that line of code:

The example module output without that line of code:

If you are not seeing the same difference I am, it might be a cache issue, try clearing your cache between changes.
> 2 votes

---
Tags: theming
---


# Question
Title: How do you use BLOCK_VISIBILITY_PHP, in hook_block_info, to hide a block?
I am user #1; I do have the PHP filter module enabled, but still my block is displaying, when I'd like it to be hidden. Here's my implementation of hook\_block\_info:

```
/**
 * Implements hook_block_info().
 */
function alerts_block_info() {
    $blocks['get_e_mail_alerts'] = array(
        'info' => t('Get e-mail alerts'),
        'status' => TRUE,
        'region' => 'sidebar_first',
        'weight' => 0,
        'visibility' => BLOCK_VISIBILITY_PHP,
        'pages' => '<?php global $user; if ($user->uid == 1) { return FALSE; } else { return TRUE; } ?>',
    );
    return $blocks;
}

```

Thanks.

# Answer
> 1 votes
I put this in my php code and it works just right:

```
<?php drupal_set_message("here"); global $user; if ($user->uid == 1) { return 0; } else { return 1; } ?>

```

The drupal\_set\_message is called and everything.

---
Tags: blocks
---


# Question
Title: Reset boost cache in a busy site without crash
We are having a high traffic Drupal 6.x site (25,000) uniques per day, mostly landing pages.

Everythings works OK, with great performance, until we try to reset the boost cache.

Once we reset it, Drupal tries to regenerate HTML from PHP and MYSQL, and we reach a performance crisis where the site crawls and becomes unusable due to slow performance.

Is there a better solution? I imagine there could be a script which clears cache slowly, resets files one by one, wait(10 seconds), wget the url, and then go to the next url.

More info added (edits):

* The site has about 20,000 nodes.
* We have two Linode 4096 machines: 4 GB RAM, 8 CPU (4x priority), 192 GB Storage, 8 TB Transfer each. Only one of them stores MySQL.
* The reason we do manual purge is because when Boost purges pages by itself, we can get to a point where a lot of pages are not in the cache. This can cause a big performance hit. When the server is too busy, PHP returns WSOD and then Boost caches it! So we get a page, in cache that is actually WSOD!!! Since this is a critical problem, we decided to affectively disable Boost from purging cache on it own and do it On Demand.
* Why clear the boost cache? The CSS and JS files are global. If we change the CSS, or add some JS, then we "drush cc css-js" to load the new changes. Doing that, the CSS/JS files are deleted and we are left with cached HTML pointing to non-existing CSS/JS files. So we get "broken" pages. The solution is to refresh the Boost cache.

Will the advagg module help?

Any other solutions?

Pleae advise.

# Answer
> 1 votes
Here is the script that does the job:

```
<?php

/* function to list all relevant HTML files in a given directory */
function ListIn($dir, $prefix = '') {
  $dir = rtrim($dir, '\\/');
  $result = array();

    foreach (scandir($dir) as $f) {
      if ($f !== '.' and $f !== '..') {
        if (is_dir("$dir/$f")) {
          $result = array_merge($result, ListIn("$dir/$f", "$prefix$f/"));
        } else {
          if (stripos($f,".gz") === FALSE) {
            $result[] = $prefix.$f;
          }
        }
      }
    }

  return $result;
}

/* main function */
function go() {
  $isToNotify = false;
  // get all relevant HTML files, recursively
  $files = ListIn('/var/www/drupal_site/cache/normal/my.domain.com','');
  foreach($files as $file) {
    // save filename for later
    $filename = str_replace("_.html","",$file);
    // normalize path to file
    $file = "/var/www/drupal_site/cache/normal/my.domain.com/" . $file;
    echo "\n************************************\n\nChecking $file" . "...\n\n";
    // get HTML from file into string variable
    $html = file_get_contents($file);
    // create DOM object for easy parsing
    $dom = new DOMDocument;
    $dom->loadHTML($html);
    // get all <link> tags
    $links = $dom->getElementsByTagName("link");
    foreach($links as $link) {
      $css = $link->getAttribute('href');
      $css = str_replace("http://my.domain.com","",$css);
      // find only the relevant tags with the CSS file
      if (stripos($css,"css_") !== FALSE) {
        // normalize path to CSS file
        $path = "/var/www/drupal_site" .$css;
        // check if CSS exists
        if (file_exists($path)) {
          echo "The file $path exists\n";
          // no need to do anything else
        }
        else {
          echo "The file $path does not exist\n";
          // set notification ON
          $isToNotify = true;
          // delete HTML with links to not existing CSS file
          unlink("/var/www/drupal_site/cache/normal/my.domain.com/$filename"."_.html");
          unlink("/var/www/drupal_site/cache/normal/my.domain.com/$filename"."_.html.gz");
          // GET the HTML from scratch so Boost will re-cache it
          echo file_get_contents("http://my.domain.com/$filename");
          echo "Adding log entry...\n";
          // log activity
          $content = "\n\n".(date("Y-m-d H:i:s"))."\n    Refreshed HTML: my.domain.com/".$filename."\n    CSS file which was not found: ".$css;
          file_put_contents("/root/scripts/logs/monitorCSS.log",$content,FILE_APPEND);
          echo "Going to sleep for a while ZzZzZz...\n";
          // sleep for a while to avoid bombardment of the server by this script
          sleep(20); // in seconds
          // go to next file - no need to refresh same file more than once (if more than one CSS file was not-found in HTML)
          break;
        }
      }
    }
  }
  if ($isToNotify) {
    // send email notification if needed (we found some missing CSS files)
    mail('my@email.address', 'Monitor CSS Notification', wordwrap("Some missing CSS files discovered - see log file for more info...", 70));
  }
}

// call main function
go();
?>

```

# Answer
> -1 votes
You mention the amount of visitors but not the number of nodes. That is likely more important here, since Boost will want to rebuild it's cache.

That said, why are you trying to flush the cache often? With boost, you typically don't need to do an entire wipe of the page cache unless you're actually changing things often. Rather, you can set a minimum cache lifetime and then just let it do it's ting.

Unless of course, you have a use case I'm not picturing.

Lastly, what size Linode do you have? It's possible that you're hitting a hardware limit for the amount of content and traffic you have.

---
Tags: 6, performance, caching
---


# Question
Title: Created a development/test server from an existing site, struggling with permissions errors on Cent OS 6 server
I am hoping a I can get a little help on a problem that I continually struggle with and that seems to impact a number of places on a site that I have copied over from a production version.

So I have a site for which I created a development environment for on an Amazon EC2 instance (original site is not on Amazon EC2). So far everything is loading up and showing for the most part. But it is becoming clear that in handling administrative tasks I am running into file permission problems.

For instance, If I go to \*Administrator \> Site Building \> Themes \> *My Custom Theme** to configure the favicon, I get the error:

> The directory sites/default/files is not writable

I have tried `chmod 775` and that does not work. If I do `chmod 777` the css files don't load and the site is without styles. I have tried `chown 6226` (which seems to be the default user from when I did a fresh install of drupal 6.20 on the new server). And have tried `chown ec2-user` (the default ec2 instance user) as well as *`chown` the user from the production server* (for which there is a user with the same name on the new server).

So far nothing works and the directory is still not writeable. Where can I go just to see what the new server expects for write permissions to the files it needs permissions to access? These are not problems on the production server.

# Answer
> 3 votes
The best to fix the permission issue is run the `fix-permission` script available at https://drupal.org/node/244924

First download the script from here and than run the script as:

```
sudo bash fix-permissions.sh your/drupal/path your_user_name

```

Note: The server group name is assumed "www-data", if it differs modify it in the script code

Drupal official doc for file permission is available at https://drupal.org/node/244924

---

Generally Recommended Permissions for Drupal Files and Folders is following:

```
drupal/sites/default                                        750
drupal/sites/default/files (including sub folders & files)  755 or 770 *
drupal/sites/default/settings.php                           400 or 440 *
drupal/sites/default/default.settings.php                   400 or 440 *
drupal/sites/all/themes (including sub folders & files)     755
drupal/sites/all/modules (including sub folders & files)    755

```

* depends on system setup. Some extra modules and/or server rules may require different permissions.

---
Tags: 6, files
---


title: embedding queries

text:
# Question
Title: embedding queries
In reading Drupals Building Blocks, in the discussion about optimizing an sql query, it mentions embedding queries.

I've read all the pros/cons and for one specific page I have, I would like to embed four different displays of one view so I'm trying to figure out the best place to do this.

My goal is that the **"Maximum execution time of 30 seconds exceeded"** will fall away. There is no problem anywhere on the site except for this one page *(which was a marketing brain-child to put everything on one page; in affect to disregard the rest of the site*).

Do I create a `page.tpl.php` specific template and stick the code there or somewhere else?

I was trying to use:

```
$view = views_get_view('my_view_name');
print $view->execute_display('Display One Here');

```

But in addition to putting it in the right place, do I list the display with quotes and commas as in 'display two here', 'display three here' or do I need to repeat the `print $view->` for each display?

Of course, maybe there is a better way to do all of this?

The page in question generates a long list of products.

# Answer
> 0 votes
I guess the Entity view attachment module is what you would require to use.

The Entity Views Attachment (EVA) module extends the Views module to allow you to attach a view to any entities on your site. The placement of the view in the entity's content can be reordered on the "Field Display" administration page for that entity, like other added fields.

Views on its own will let you create a page for your view, with its own URL, and it also lets you attach multiple views to the same Views page, but it doesn't let you do something like attach a view to a node, or a user

One good example of this module is available at: https://drupal.stackexchange.com/questions/5732/is-there-a-good-tutorial-for-entity-views-attach-module

---
Tags: views, database
---


# Question
Title: What are the Steps to Translate the Current Search Block and Facet Search block(s)
I have been unable to configure things such that the Current Search Block or Search Facet block(s) have their strings show up in the Translation tool at :

> admin/config/regional/translate/translate

They are however available in options in the translation tools filter

I do have Facet API Translation installed

I have tried refreshing String translations at:

> admin/config/regional/translate/i18n\_string

And I have tried specifying the blocks as translatable on their respective blocks configuration forms (the form states that because the module is responsible for the content of the block that only Title translations are possible ... this is obviously not what I need to do to translate the blocks contents)

What are the Steps required to Translate Facet Search Block(s) and Current Search Block ?

# Answer
I was able to solve this issue; however not in an ideal way:

see: https://drupal.org/node/1478908

see: https://drupal.org/node/1387504

see: https://drupal.org/node/1376786

see: https://drupal.org/project/facetapi\_i18n

By implementing hook\_block\_view\_alter and passing pieces of the markup to the translation function.

```
function MY_MODULE_block_view_alter(&$data, $block) {
    if($block->module == 'current_search'){
            $original_markup = $data['content']['results']['#markup'];
            $original_filtered = strip_tags($original_markup);
            $results_count_int = filter_var($original_filtered, FILTER_SANITIZE_NUMBER_INT);
            if($results_count_int){
                    $new_text = t('Search found @count item(s)', array('@count' => $results_count_int));
                    $new_markup = "<h3 class=\"\">$new_text</h3>";
                    $data['content']['results']['#markup'] = $new_markup;
            }
    }

```

}
> 0 votes

---
Tags: i18n-l10n, search
---


# Question
Title: Deploying content updates from staging server to live server
We are trying to deploy content updates from our staging server to our live server but are having difficulty finding a good way to do this. We need to be able to deploy new pages, page updates and occasinally page deletes. Our site also makes extensive use of the book module so the Deploy module doesn't work for us at this time. We are using features for large structure updates. So, our concern is just the daily content updates.

Are there any modules that can do this and handle book pages?

# Answer
> 3 votes
UUID and UUID Features allows you to export a Node to a Feature, which could be just what you're after, means no need to mess with the database.

# Answer
> 1 votes
Have you tried node\_export and Backup Migrate. Both modules are used for migrating content between Drupal installations. Here's a comparison between data import/export modules that you might find useful.

# Answer
> 1 votes
I'm assuming Drupal 6 here, and don't personally know if it will work with book module, but have you looked into Deployment?

# Answer
> 0 votes
You could also give a try to Phing, with which you could automatically:

* Dump the staging database using mysqldump.
* Copy the mysqldump file from one server to another using SCP and Public-Private Key encryption.
* Import the mysqldump from the filesystem into the database.
* Run the **Feature Revert All** command (`drush fra -y`) so your production server picks up production settings (such as blocks, views, contexts, etc) found in your Features code.

Problems I see with this approach:

You will need to do a very fine grained database export, this means taking only node, node\_revisions, cck and menu tables.

On that last point (menu links) unless you access both your stage and prod server using the same URL aliases, you will have different menu item entries, and this will be a serious problem.

# Answer
> 0 votes
I actually like the full DB dump method, which could be scripted and often can complete in just a few seconds. (Keeping your revisions under control and excluding cache tables etc. can reduce the size a lot.) You could even create a simple module to provide an interface for content publishers to trigger this process.

You do need to account for any content you might accept from users of your live site, such as comments or contact form submissions. If there is any - surprisingly often there is none - you could either use an external service, such as Disqus for comments or Marketo for lead generation forms, carefully segregate such submissions into a separate Drupal database which is not overwritten, or carefully not overwrite those affected tables during the export/import process.

Where it can be made to work, it may end up being the simplest, fastest, most reliable method. And a site which never accepts input from users (other than into external services) opens a lot of doors to being made much faster and more secure.

---
Tags: deployment, staging
---


title: How to style menu local tasks

text:
# Question
Title: How to style menu local tasks
**Problem**

I'm trying to theme the menu local tasks that Drupal places without any unique css classes. How would I do this?

(Specifically I'm looking to hide certain links on certain pages by giving each one a unique css class).

*Links Sample HTML*

*Which is generated by this line in page.tpl.php.*

```
<?php if ($primary_local_tasks): ?><ul class='links'><?php print render($primary_local_tasks) ?></ul><?php endif; ?>

```

**So Far**

To do that I'm trying to use theme\_menu\_local\_tasks however I can't get it to work. I've put this snippet in my template file but it doesn't print anything or show me any variables.

```
function tefltheme_menu_local_tasks (&$variables) {
  dpm($variables);
  print("hello");
  return theme_menu_local_tasks($variables);
}

```

I'm using Tao sub-theme which means it splits menu local tasks into primary and secondary.

```
function tao_preprocess_page(&$vars) {
  // Split primary and secondary local tasks
  $vars['primary_local_tasks'] = menu_primary_local_tasks();
  $vars['secondary_local_tasks'] = menu_secondary_local_tasks();

```

Could this be affecting anything?

# Answer
> 4 votes
`theme_menu_local_tasks()` will never be invoked using those two methods, so it makes sense that your `dpm()` fails.

Both functions do eventually invoke `hook_menu_local_tasks_alter()`, though, and that's where you can make your changes:

```
function MYTHEME_menu_local_tasks_alter(&$data, $router_item, $root_path) {
  if ($some_condition) {
    // Grab the first tab.
    $first_tab = &$data['tabs'][0]['output'][0];

    // Add a class to the link element.
    $first_tab['#link']['localized_options']['attributes']['class'][] = 'some-class';
  }
}

```

If you want to add a class to the `<li>` element you'll need to go a step further, and override `theme_menu_local_task()`.

The class attribute is hard-coded at the moment so that'll will need to be changed, based on a contextual variable you can pass into the theme function from the local tasks hook above.

That would look something like this in the alter hook

```
$first_tab['#extra_class'] = 'some-class';

```

And along these lines for the theme function

```
function MYTHEME_menu_local_task($vars) {
  // Copy the code from theme_menu_local_task() but change the HTML output
  // to include an extra class if $vars['extra_class'] is set
}

```

You might also need to implement `hook_theme_registry_alter()` to let it know about the new variable (can't remember if it matters but it can't hurt)

```
function MYTHEME_theme_registry_alter(&$theme_registry) {
  $theme_registry['menu_local_task']['variables']['extra_class'] = NULL;
}

```

# Answer
> 1 votes
Here's the final code that went into my template file:

```
function MYTHEME_menu_local_tasks_alter(&$data, $router_item, $root_path) {

  //check the path of the page
  if ($root_path == 'user/register') {
        //add classes to the tabs. I left out tab 0 which is the active tab
        //and styled differently. It comes with active as a class.
        $tab1 = &$data['tabs'][0]['output'][1];
        $tab1['#link']['localized_options']['attributes']['class'][] = 'tab1';
        $tab2 = &$data['tabs'][0]['output'][2];
        $tab2['#link']['localized_options']['attributes']['class'][] = 'tab2';
  }
}

```

---
Tags: 7, theming
---


# Question
Title: Simpletest on select field loaded by ajax
I have searched through Google and haven't found an answer. Stack Exchange is my last resort.

In my form, I have two select fields:

```
$form['system']['foo'] = array(
  ...
  '#type' => 'select',
  '#options' => array('A', 'B', 'C'),
  ...
  '#ajax' => array(
    'event' => 'change',
    ...
    'method' => 'replace',
  ),
);

$form['system']['bar'] = array(
  ...
  '#type' => 'select',
  '#options' => array(),
  '#prefix' => ...
  '#suffix' => ...
);

```

If user selects any of the options in `foo` field, the `bar` field dynamically loads the options through ajax. Example: If 'A' is selected on `foo`, `bar` field generates options like 'aaa', 'bbb', 'ccc' and can be selected by the user.

This form works and I need to provide its unit test using 'Simpletest'.

On my test case:

```
$edit = array(
  'system[foo]' => 1, // value for 'A'
  'system[bar]' => 2, // value for 'bbb'
);
$this->drupalPost('mymodule/mypath', $edit, t('Submit'));

```

gives an error saying `system[bar]` cannot be set to 2 (because it has no value of 2 yet?)

I need to emulate ajax call on `system[foo]` before setting `system[bar]`.

I have tried `drupalPostAjax`:

```
$edit = array(
  'system[foo]' => 1, // value for A
);
$this->drupalPostAjax('mymodule/mypath', $edit, 'system[foo]');

```

and gives me a success result on ajax. On the next lines of code, I tried calling `drupalPost()` again using the previous code snippet but gives me the same error saying `system[bar]` cannot be set to 2.

How can I solve my problem? Please provide sample code as it can help me a lot..

---

EDIT:

Ajax works on the actual page (i.e the values are dynamically loaded to `system['bar']`). So I can assume my code in the forms is working.

However, I just noticed that ajax does not work on the generated page from Simpletest (the one found in **sites/default/files/simpletest/verbose**). Console from Google Chrome does not show any errors. Ajax returns status 200 but does not have any response.

I am using the default theme upon installation.

---

EDIT: The form and simpletest code

The form: I copied the form posted by znerol.

The simpletest code:

```
class MyModuleTestCase extends DrupalWebTestCase {
  protected $admin_user;

  public static function getInfo() {
    return array(
      'name' => 'Test Case name',
      'description' => 'Test Case Description',
      'group' => 'My Module',
    );
  }

  public function setUp() {
    // Enable module
    parent::setUp(array('mymodule'));

    // Get permissions
    $permissions = mymodule_get_permissions();
    // Permissions obtained correctly.

    // Create and login admin user
    $this->admin_user = $this->drupalCreateUser($permissions);
    $this->drupalLogin($this->admin_user);
  }

  // Test section
  public function testSystem() {
    $this->drupalGet('mymodule/mypath');
    $edit = array(
      'system[foo]' => 1, // Selects 'A'. Tested!
    );
    $this->drupalPostAjax(NULL, $edit, 'system[foo]');
    // Bar after ajax is loaded
    $edit = array(
      'system[bar]' => 1, // Selects 'aaa'
    );
    $this->drupalPost(NULL, $edit, t('Submit')); // Error here.
    $this->assertText(t('Submitted!'));
  }
}

```

However, when running simpletest, simpletest complains that `system['bar']` cannot be set to `1` (aaa).

I have noticed simpletest shows the following warning before it calls ajax.

> Undefined offset: 0 Notice drupal\_web\_test\_case.php 2147 DrupalWebTestCase \>drupalPostAJAX()
>
> Undefined index: Notice drupal\_web\_test\_case.php 2148 DrupalWebTestCase-\>drupalPostAJAX()
>
> Undefined index: #ajax Notice ajax.inc 379 ajax\_form\_callback()

Since `system['bar']` is loaded dynamically through ajax, it has an empty array initially `array()`. From the warning above, I tried adding a temporary option `array('1', '2')` in `system['bar']`. The same error and warning occurs.

# Answer
You should set the `$path` parameter to `NULL` when submitting to the same form. Otherwise drupalPost / drupalPostAJAX will first retrieve the page again, and thus generating a new form instead of rebuilding the current one.

The following test should do what you want:

```
// First retrieve the page once
$this->drupalGet('mymodule/mypath');

// Set $path to NULL on subsequent requests to the same form
$edit = array('system[foo]' => 1);
$this->drupalPostAJAX(NULL, $edit, 'system[foo]');

$edit = array('system[bar]' => 2);
$this->drupalPost(NULL, $edit, t('Submit'));

```

The test case succeeds when performed on the following form:

```
function mymodule_myform($form, &$form_state) {
  $foo_options = array('A', 'B', 'C');
  $foo_default = isset($form_state['values']['system']['foo']) ? $form_state['values']['system']['foo'] : NULL;

  $form['system']['#tree'] = TRUE;

  $form['system']['foo'] = array(
    '#type' => 'select',
    '#options' => $foo_options,
    '#default_value' => $foo_default,
    '#ajax' => array(
      'callback' => 'mymodule_myform_ajax_callback',
      'wrapper' => 'bar-div',
      'method' => 'replace',
    ),
  );

  $bar_choices = array(
    0 => array('aaa', 'bbb', 'ccc'),
    1 => array('ddd', 'eee', 'fff'),
    2 => array('ggg', 'hhh', 'iii'),
  );
  $form['system']['bar'] = array(
    '#prefix' => '<div id="bar-div">',
    '#suffix' => '</div>',
    '#type' => 'select',
    '#options' => isset($bar_choices[$foo_default]) ? $bar_choices[$foo_default] : array(),
  );

  $form['submit'] = array(
    '#type' => 'submit',
    '#value' => t('Submit'),
  );
  return $form;
}

function mymodule_myform_ajax_callback($form, $form_state) {
  return $form['system']['bar'];
}

```
> 4 votes

# Answer
One thing I have noticed in your following code:

```
$form['system']['foo'] = array(
  ...
  '#type' => 'select',
  '#options' => array('A', 'B', 'C'),
  ...
  '#ajax' => array(
    'event' => 'change',
    ...
    'method' => 'replace',
  ),
);

$form['system']['bar'] = array(
  ...
  '#type' => 'select',
  '#options' => array(),
  '#prefix' => ...
  '#suffix' => ...
);

```

the `system[bar]` fields has been initialized with an empty array: array().

And than you are trying to set the value of that field that doesn't contains any option. My guess is can you initialize the options for `system[bar]` fields as well. I know you have mentioned that the `bar` field dynamically loads the options through ajax. But I think the value on that field cannot be set unless it is initialized with proper set of result.
> 0 votes

---
Tags: 7, forms, ajax, testing
---


title: Expiration date for static files

text:
# Question
Title: Expiration date for static files
I don't understand the following:

In Drupal 7's default *.htaccess* file the Apache module `mod_expires` is ordered to let files without a *.php* extension expire after two weeks.

How is web development with this setting possible? When I change a *.css* file, I want the changes to be reflected immediately. Do browsers ignore the expiration setting?

I've stumbled upon this issue because I'm currently experiencing troubles with a Varnish caching system. I currently do not know what causes my files not to be refreshed immediately.

# Answer
> 1 votes
The `Cache-Control` header which `mod_expires` sets tells the browser when a set of cached content should expire and be redownloaded. If you are interested in learning more about how that header works, read http://blog.httpwatch.com/2007/12/10/two-simple-rules-for-http-caching/ it explains it really well. Browsers do not ignore this setting. But if you "shift reload" or do something which forces the browser to ignore the cache and redownload anyways you'll ignore it.

A common approach for this is to implement a timestamp based update for CSS/JS. For example you have the following stylesheet link

```
<link rel="stylesheet" type="text/css" media="all" href="style.css">

```

You would append a last changes tag to it, something like

```
<link rel="stylesheet" type="text/css" media="all" href="style.css?c=20131001">

```

and then you can just auto increment this every time you change the css. This will force ALL browsers to redownload, but won't destroy the cache benefits.

---
Tags: caching, .htaccess
---


# Question
Title: Varnish 3.0 and Drupal 7, get registered user to always have non-cached content
I have issue with Varnish on Drupal 7 detailed here: http://drupal.org/node/1886218

Basically, what happens is:

1. User visits the certain page as anonymous, gets content served by Varnish Cache (OK)
2. Logs in
3. Clicks the link of the page that he visitied as anonymous previosly, but he gets cached page, instead of user-specific (that should not happen)
4. If he reloads page (f5), he gets backend served page, but if he clicks that link on the menu, he gets cached page.

It turns out that cached page was delivered by browser, not by Varnish; anyway, that should not happen, because user thinks he is logged out (I have user specific block in header).

How i can deliver such cache-control in header, so Registered users always get updated (not cached) content, even if they browsed site as anonymous before they have logged in ?

Thanks for help!

HTTP response:

```
The url we checked: www.mydomain.com
    HTTP/1.1 200 OK
Server: Apache (removed from security)
X-Powered-By:   PHP(removed from security)
X-Drupal-Cache: MISS
Expires:    Sun, 19 Nov 1978 05:00:00 GMT
Last-Modified:  Tue, 15 Jan 2013 08:38:54 +0000
Cache-Control:  public, max-age=10800
ETag:   "1358239134-1"
Content-Language:   hr
X-Generator:    Drupal 7 (http://drupal.org)
Link:   <http://www.mydomain.com/>; rel="canonical",<http://www.mydomain.com/>; rel="shortlink"
Vary:   Accept-Encoding
Content-Encoding:   gzip
Content-Type:   text/html; charset=utf-8
Content-Length: 33254
Accept-Ranges:  bytes
Date:   Tue, 15 Jan 2013 08:49:22 GMT
X-Varnish:  1420616326 1420614128
Age:    622
Via:    1.1 varnish
Connection: keep-alive
X-Varnish-Cache:    HIT

```

# Answer
> 1 votes
You seem to be missing `Vary: Cookie` in addition to `Vary: Accept-Encoding`. You may add it in `vcl_deliver` using something like this:

```
if (resp.http.Vary !~ "Cookie") {
    set resp.http.Vary = resp.http.Vary + ", Cookie";
    set resp.http.Vary = regsub(resp.http.Vary, "^,\s*", "");
}

```

# Answer
> 0 votes
Try changing the response Cache-Control headers:

```
Cache-Control:no-cache, max-age=0, must-revalidate

```

---
Tags: proxies
---


# Question
Title: How to print a string for flagged nodes?
I have a flag called "Mark as SOLD" which can be flagged only by node author. When he flags it as "Sold", I want the node teaser to print a translatable string t('SOLD'), so that everyone else (even anonymous) can see that this item is now sold.

In my corolla template.php I already have custom function that gives classes to different flags:

```
    function corolla_preprocess_node(&$variables) {
  $flag = flag_get_flag('sold'); // Machine name of your flag.
  if ($flag && $flag->is_flagged($variables['node']->nid)) {
    $variables['classes_array'][] = 'node-flag-sold';
  }
$flag = flag_get_flag('withdraw'); // Machine name of your flag.
  if ($flag && $flag->is_flagged($variables['node']->nid)) {
    $variables['classes_array'][] = 'node-flag-withdraw';
  }
}

```

But I know that I need to modify this function and/or node--type.tpl.php to actually print a string t('SOLD').

How can I achieve this?

# Answer
> 3 votes
You can set a new variable in your preprocess function and print it in your node--type.tpl.php as follows:

In template.php

```
function YOURTHEME_preprocess_node(&$variables) {
  $node = $variables['node'];
  if ($node->type == 'YOUR_CONTENT_TYPE') {
    $flag = flag_get_flag('sold');
    if ($flag && $flag->is_flagged($node->nid)) {
      $variables['classes_array'][] = 'node-flag-sold';
      $variables['flagged_text'] = t('Sold');
    }
  }
}

```

And in your node--YOUR-CONTENT-TYPE.tpl.php, put simply this snippet wherever you want to print the string:

```
<?php if ($flagged_text): ?>
  <?php print $flagged_text; ?>
<?php endif; ?>

```

or the same code shorter:

```
<?php if ($flagged_text) print $flagged_text; ?>

```

But the first one is better for readability and follows the Drupal's coding standards for template files.

---
Tags: theming, flags
---


# Question
Title: Get NID of newly created node from entity_metadata_wrapper
I need to pull the nid immediately after it is created using entity\_metadata\_wrapper as a creation method.

Here is a brief example:

```
$values = array(
  'type' => 'content_type',
  'uid' => $user->uid,
  'status' => 1,
  'comment' => 1,
  'promote' => 0,
);

$entity = entity_create('node', $values);
$wrapper = entity_metadata_wrapper('node', $entity);
$wrapper->title->set('title');
$wrapper->save(true);
entity_save('node', $entity);

// From this, where can I get a NID value for the node that was just created?

```

# Answer
> 28 votes
You can simply use the entity\_metadata\_wrapper's integrated method to get the ID:

```
$wrapper->getIdentifier()

```

# Answer
> 6 votes
Easy.

```
 $wrapper->save();
 $node = $wrapper->value();
 dsm($node); // which has $node->nid;

```

Figured I'd answer for somebody else to use.

**Update:**

The answer above is a better answer `$wrapper->getIdentifier()`.

There are situations when the entity may have some sort of unique identifier.

---
Tags: 7, nodes, entities
---


title: Theme get blocks

text:
# Question
Title: Theme get blocks
I'm trying to get a list of all blocks for a certain path but can't figure how to do that.

For example, on the page at url "node/5", I have a few blocks on different regions (sidebars, content bottom, footer). I need to get a list of all these blocks that should be rendered on this page (node/5)

**UPDATE:**

this seems to work but only for the "content" region.

```
global $theme;
$all_regions = system_region_list($theme);
$blocks = array();
foreach (array_keys($all_regions) as $region) {
  $blocks += block_list($region);
}

```

Before this piece of code I run `menu_execute_active_handler('node/2', false)` because i want to get the blocks for a specific path (Eg: node/2). Unfortunately, it only grab the "content" blocks, no header/footer blocks

Any ideeas? Thanks

# Answer
> 0 votes
enter link description hereAlready answered before at stackoverflow

```
  global $theme;
  $all_regions = system_region_list($theme);
  $blocks = array();
  foreach (array_keys($all_regions) as $region) {
    $blocks += block_list($region);
  }

```

this code will tell about all blocks on current page.

**Updated:**

check if dpm(\_block\_load\_blocks()); helps you

---
Tags: 7, blocks, theming
---


# Question
Title: how to use hook_user_login to catch username and password
I am trying to catch the username and password which are entered on the user login form. This is my code:

```
function impak_integration_user_login(&$edit, $account) {
  drupal_set_message("Welcome User!" . print_r($edit). print_r($account));
  global $user;
  drupal_set_message(print_r($user));
  }

```

The hook does work, as It does print out the Welcome message after login. However, I can't figure out how to get any of the user information, specifically the entered username and password.

# Answer
The information send in the login form is in the $edit array. You can get this information as follows:

```
function YOURMODULE_user_login(&$edit, $account) {
  $username = $edit['input']['name'];
  $password = $edit['input']['pass'];
  drupal_set_message("Welcome $username your password is $password");
}

```
> 2 votes

# Answer
Think twice why you need to do something before login! As one of the possible answer
\- In order to catch the user login, you can implement hook\_form\_alter() as below

```
/**
* Implements hook_form_alter().
*/
function MYMODULE_form_alter(&$form, $form_state, $form_id) {
  switch ($form_id) {
    case 'user_login_block':
    case 'user_login' :
      array_unshift($form['#submit'], 'custom_login_submit');
      break;
  }
}

/**
* Custom submit handler
*/
function custom_login_submit($form, &$form_state) {
  //code here
  dpm($form_state);
}

```

clearly you will get both things in $formstate

The reason you might not be getting pass in hook\_user\_login() is because it is called after login.
> 1 votes

---
Tags: hooks, users
---


# Question
Title: How to print render each term in a vocabulary?
I kinda feel ashamed to ask this but I really did not find any answer on this...

How can I print each term in a given display mode, for instance 'teaser', anywhere I have loaded a vocabulary's terms?

```
<?php
    $vid = taxonomy_vocabulary_machine_name_load('finder_items');
    $tax = taxonomy_get_tree($vid->vid, 0);

    $tids = array();

    foreach ($tax as $key => $value) {
        $tids[] = $tax[$key]->tid;
    }

    // ?? causes exception
    $tvm = taxonomy_term_view_multiple($tids, 'full', 0, 'de');

    print $terms;

?>

```

I want to fully render them, with all their fields.

# Answer
> 0 votes
Reason of Error: you were passing the "terms ids" to the taxonomy\_term\_view\_multiple().

> **Solution**: First load the term objects using `taxonomy_term_load_multiple()` and pass its result to the `taxonomy_term_view_multiple()` as below:

```
<?php
    $vid = taxonomy_vocabulary_machine_name_load('finder_items');
    $tax = taxonomy_get_tree($vid->vid, 0);
    // Initilize the array for storing the term ids.
    $tids = array();
    // Check if any term present in voacb, otherwise foreach will throw error.
    if (!empty($tax)) {
      foreach ($tax as $key => $value) {
        $tids[] = $tax[$key]->tid;
      }

      // Get the term obj by passing array of term ids.
      $term_details = taxonomy_term_load_multiple($tids);

      // This will provide you the required result.
      $terms = taxonomy_term_view_multiple($term_details, 'full', 0, 'de');

      // Render each term.
      foreach($terms as $term) {
        print drupal_render($term);
      }
    }
?>

```

# Answer
> 2 votes
You might be seeing Exception as

> EntityMalformedException: Missing bundle property on entity of type taxonomy\_term. in entity\_extract\_ids()

**Reason being:**

> In taxonomy\_term\_view\_multiple($terms,..)
> $terms: An array of taxonomy terms as returned by taxonomy\_term\_load\_multiple().

```
    $vid = taxonomy_vocabulary_machine_name_load('finder_items');
    $tax = taxonomy_get_tree($vid->vid, 0);
    if (!empty($tax)) {
      foreach ($tax as $term) {
        $tids[] = $term->tid;
      }
    }

    // Get the term obj by passing array of term ids.
    $term_details = taxonomy_term_load_multiple($tids);
    $terms = taxonomy_term_view_multiple($term_details, 'full', 0, 'de');

   // Render the return array
   foreach($terms as $term) {
     print drupal_render($term);
    }

```

---
Tags: taxonomy-terms
---


title: Hide a field in a view if it is empty

text:
# Question
Title: Hide a field in a view if it is empty
I customised the output of a field (using Rewrite the output of this field) but if the field is empty, only the customizations and not the content appears. I want to hide both the customizations and the content if the field is empty

# Answer
> 4 votes
Check if the screenshot settings work for you,this the setting for the field you want to hide when empty. It provides option to hide the **rewritten** content as well.

# Answer
> 2 votes
Enable the **Hide if empty** and **Hide rewriting if empty** present in "No results behavior" tab of the field whose customization and content you want to hide as below:

---
Tags: views, entities
---


# Question
Title: How do I remove the rollover effect from Rubik tooltips
I am using Rubik and the tooltips are rollovers. Generally this is fine, but for one site I need them to display with the field instead. Is there a setting to disable the rollover effect and just make it look like help text?

# Answer
> 0 votes
I have not used this theme before, but there is a checkbox on the theme settings page to toggle "Display form field descriptions inline". I believe this is what you are looking for.

---
Tags: tooltips
---


title: module_load_include not working

text:
# Question
Title: module_load_include not working
I've been looking on several sites trying to figure this out, but no dice yet.

I have a module, 'spower'. I need to include several php files inside the polygon folder (spower/polygon/***.php). In the spower.module file, I've included the line:

module\_load\_include('php', 'spower', 'polygon/polygonBase');

However, when I run the module, I get the error `Call to undefined function PolygonBase`, so obviously, something's not loading right.

# Answer
Assuming you want to load

```
sites/all/modules/custom/spower/polygon/polygonBase.php

```

then

```
module_load_include('php', 'spower', 'polygon/polygonBase');

```

should work fine.

* Make sure the file `polygonBase.php` is readable by the webserver user.
* Make sure `module_load_include` is added for processing prior to using functions in that file.
> 2 votes

# Answer
In order to debug whether module\_load\_include() is working or not, you can check the return value using code as

```
$file_path = module_load_include('php', 'spower', 'polygon/polygonBase');

if ($file_path === FALSE) {
  dpm('Failed to include: ' . $filename);
}
else {
  dpm('Successfully included: ' . $file_path);
}

```
> 1 votes

---
Tags: 7
---


# Question
Title: How to output a custom field in my template?
In my content type I have created a custom field field\_image\_style which is a list (text).

How can I print its value in node.tpl.php?

```
print render($content['field_image_style']);

```

This doesn't work?

(What I actually want to achieve later is to use the selection the user made in field\_image\_style to apply a specific image style to the images of the content element.)

EDIT: Somehow the Zen theme was the reason. With my own Stark based theme it works like it's supposed to.

# Answer
> 1 votes
This is a perfect use case for the Field Formatter CSS Class module.

After adding a text list, radio, or taxonomy field to a content type, you then put the field on the view mode you would like for the class to be on. Use the CSS Class formatter and what level you would like to apply the class (generally node is fine), then you can add your CSS rules for whatever you want.

For example, you can change the individual caption background color on slides in a rotator, or specific stylings per post in a blog feed.

---
Tags: theming, entities
---


# Question
Title: How would one encrypt or protect a Drupal 7 Views Configuration Recipe from prying eyes?
I spent quite a number of days developing a Views configuration recipe and I would like to protect it from other's stealing this by just viewing the Views page. Is there a module or a way to encrypt a views configuration recipe? Currently I built a site for a client and I don't want him just hiring someone that can just easily steal my views setup.

# Answer
Short answer... no.

Slightly longer answer...

Anything that views makes needs to be processed and displayed, there is no way (unless you make your own encrypted syntax then manually add a new view every single time then output it) to "encrypt" a view configuration.

Even PHP code that is encrypted can be decrypted. And that kind of encryption is ten times stronger (due to the fact it's at the C compiled level) then anything you could come up with using PHP.

If you really have a lot of time of your hands, you could redo the views module part that processes the configuration, create your own syntax that's encrypted to your own system, and store that (but please don't, and even that can be decrypted with a lot of effort.).
> 4 votes

---
Tags: 7, views
---


# Question
Title: Why is the expire header set to some time in the past ('Sun, 11 Mar 1984 12:00:00 GMT') in Drupal 6/ PressFlow and Drupal 7?
I have been trying to understand why the expires header is set to the past. I read the comment In boostrap.inc drupal 6 but I am still a bit confused about it and the relation between `expires` and `vary` headers. I looked into this because I am trying to set the expire header in the hope of controlling varnish object cache expiration regardless of TTL. The code reads:

```
  // HTTP/1.0 proxies do not support the Vary header, so prevent any caching
  // by sending an Expires date in the past. HTTP/1.1 clients ignores the
  // Expires header if a Cache-Control: max-age= directive is specified (see RFC
  // 2616, section 14.9.3).
  $default_headers['Expires'] = 'Sun, 11 Mar 1984 12:00:00 GMT';

```

Would it affect me if I set the caching headers like expire? I want to do this only for anonymous users.

I posted a varnish question related to this here: https://stackoverflow.com/questions/19121220/how-to-control-how-long-varnish-expire-a-page-from-the-backend

# Answer
See http://www.w3.org/Protocols/rfc2616/rfc2616-sec14.html#sec14.9.3.

> If a response includes both an Expires header and a max-age directive, the max-age directive overrides the Expires header, even if the Expires header is more restrictive. This rule allows an origin server to provide, for a given response, a longer expiration time to an HTTP/1.1 (or later) cache than to an HTTP/1.0 cache.

And if you look at the following code, you can see that the reason they do that is to prevent caching and allow you to do your own caching. This disables the internal page cache but returns headers allowing downstream caches (such as Squid, Varnish, and other reverse proxies) to cache full pages.

```
function drupal_page_cache_header_external() {
  // Get headers set in hook_boot(). Keys are lower-case.
  $hook_boot_headers = drupal_get_header();

  $max_age = variable_get('page_cache_max_age', 0);
  drupal_set_header('Cache-Control', 'public, max-age=' . $max_age);
  drupal_set_header('Last-Modified', gmdate(DATE_RFC1123, $_SERVER['REQUEST_TIME']));

  // HTTP/1.0 proxies do not support the Vary header, so prevent any caching
  // by sending an Expires date in the past. HTTP/1.1 clients ignores the
  // Expires header if a Cache-Control: max-age= directive is specified (see RFC
  // 2616, section 14.9.3).
  drupal_set_header('Expires', 'Sun, 11 Mar 1984 12:00:00 GMT');

  // Allow HTTP proxies to cache pages for anonymous users without a session
  // cookie. The Vary header is used to indicates the set of request-header
  // fields that fully determines whether a cache is permitted to use the
  // response to reply to a subsequent request for a given URL without
  // revalidation. If a Vary header has been set in hook_boot(), it is assumed
  // that the module knows how to cache the page.
  if (!isset($hook_boot_headers['vary']) && !variable_get('omit_vary_cookie', FALSE)) {
    drupal_set_header('Vary', 'Cookie');
  }
}

```
> 4 votes

---
Tags: caching, performance, 6, proxies
---


# Question
Title: View: display first value in a single field in field collection
* Drupal 7, view 3 and field collection.
* I have a custom content type with a field collection called personal detail.
* Personal detail have 2 fields: name and contact.
* Personal detail is zero to unlimited.
* In view, I am able to display the values of 'name' field. The problem is there are multiple values for 'name' field. This caused me to have duplicated records (i.e. same node id appears more than once, because the 'name' field)
* I only want to display the very first one value of 'name' field which is stored the order of a node.

**Solution**: In Go to field collection in view's relationship (right column)

There is a statement: The delta allows you to select which item in a multiple value field to key the relationship off of. Select "1" to use the first item, "2" for the second item, and so on. If you select "All", each item in the field will create a new row, which may appear to cause duplicates.

So select "1" will show the first fields.

# Answer
This can be done by modifying the `Multiple field settings` of your `name` field:

* Click on the "name" field in your view (to edit the settings of field)
* Navigate to "Multiple field settings" (present just above "Style" settings)
* Click on the checkbox: "Display all values in the same row"
* Choose "Display type": Ordered list
* Below display type, there is one field "Display": Replace "ALL" with 1
* Save the settings and the view.
> 5 votes

---
Tags: views, entities
---


title: Form API managed_file doesn't show up

text:
# Question
Title: Form API managed_file doesn't show up
I am working with Drupal 7. When I use the following code, nothing shows up in the form; when I change managed\_file with file, everything is fine.

```
$form['mfile'] = array (
  '#type' => 'managed_file',
  '#title' => t('File to upload'),
  '#size' => 22,'#upload_location' => 'public://vm-files',
);

```

Do you know why this happens?

# Answer
> 4 votes
You have to set the `#default_value` (as you would nearly any FAPI element) if you want the current set value to show up on the form when you visit the page. I have code such as the following in my module:

```
  for($i=1,$z=MAX_FRONTPAGE_IMAGES;$i<=$z;$i++) {
  $form["frontpage_image_fid_$i"] = array(
    '#type'            => 'managed_file',
    '#upload_location' => 'public://site_theme_assets/',
    '#default_value'   => variable_get("frontpage_image_fid_$i", ''),
    '#title'           => t("Random Image #$i for Frontpage"),
    '#description'     => t('This image will appear on the frontpage of the  site and have line1 and line2 on top of it.'),
  );
  }

```

The only gotcha I have when trying to use `managed_file` is that after save, on edit I get an error about the File status. That's because you should notify the file\_usage table that your module owns/uses the file upon upload, eg:

```
/** callback for fapi admin settings page form that uses managed_file elements */
function foundation_frontpage_admin_submit($form, &$form_state) {
  for($i=1,$z=MAX_FRONTPAGE_IMAGES;$i<=$z;$i++) {
    if ($form_state['values']["frontpage_image_fid_$i"]) {
      $f = $form_state['values']["frontpage_image_fid_$i"];
      // Load the file via file.fid
      $file = file_load($f);
      // Change status to permanent.
      $file->status = FILE_STATUS_PERMANENT;
      // Save.
      file_save($file);

      // I was receiving an error on Edit of a filled out form/file upload.
      // Managed file: the file used in the field may not be referenced
      // The solution is file_usage_add() to this module as commented here.
      //
      // http://drupal.stackexchange.com/a/4819/3279
      file_usage_add($file, 'foundation', 'variable:frontpage_image_fid_', $i, 1);

      variable_set("frontpage_image_fid_$i", $f);
    } else {
      variable_set("frontpage_image_fid_$i", NULL);
    }
  }
  drupal_set_message('Changes saved for frontpage.');
}

```

# Answer
> 1 votes
You must enable the File module, which is the one defining the managed\_file form element. (See file\_element\_info().)

The module is a dependency for the Standard profile that comes with Drupal (see standard.info), which means it is enabled for that installation profile, but the Minimal profile doesn't enable it (see minimal.info), and there could be other installation profiles that don't enable it. If that is the case, using managed\_file as form element doesn't make appear a form element.

---
Tags: forms, files
---


title: Uploaded Private files access problems

text:
# Question
Title: Uploaded Private files access problems
On my Drupal 7 install, I have content type in which user can upload files to the server, via file upload field. I was sure everything was fine, I forgot about the system (was sure it was working, tested it). But strange enough, after some time I tested it, I could not download files, not by clicking on file link on that content type, nor by pasting url of the file in adress bar.

When I tried to access files, I got HTTP request status: 403 (Forbidden in http headers, while browser shows login page and path in the adress bar was path of that file...

And strange enough, under /admin/config/media/file-system I defined private files path to be **files/private**, and files were uploaded to that directory. But on the content type page - link to file ignored files/private path and rather had path **system/files** that I have not defined anywhere!

To test things, I migrated user private files to system/files (actually created that folder and subfolder in drupal root) and defined path of the private files to be also system/files (on /admin/config/media/file-system ).

Got some "progress" - Apache "Forbidden" page - when acessing private files. There was .htaccess file in the folder, with config

```
SetHandler Drupal_Security_Do_Not_Remove_See_SA_2006_006
Deny from all
Options None
Options +FollowSymLinks

```

And for test, I renamed that file to bypass "Deny", and voila, I could access my newly uploaded files. But previously uploaded files still throws mysterious HTTP request status: 403 (Forbidden in http headers, while browser showed login page and path in the adress bar was path of that file...

I was using **Public local files served by the webserver.** under /admin/config/media/file-system. I noticed also, when I enter that config, if I am missing .htaccess file in private files dir, a new one is being created.

I have to mention that I implemented Varnish cache and APC in Drupal, but things are not better after clearing the cache.

Could someone please tell me what is happening and how I can set it to work correctly/securely? Thanks!

# Answer
Although and older issue, it's worth noting that **system/files** is *normal* for Drupal private file mode paths.

That is because `system/files` is the logical application path that handles and routes to the file on the actual file system.

It is this logical path that allows the additional authentication checks that private file mode allows.

You can put your private files under `sites/default/files/private` and Drupal will automatically create an `.htaccess` file to deny direct web access to them.

However, for safety, it's recommended to put your private files directory outside the html web root. For example, one level up from your website document root, or some other designated folder.

If curious private files are served via `system_menu` which defines the `system/files` url callback to `file_download`.

Following that `hook_file_download` is used to provide access control to the requested private file.
> 3 votes

# Answer
Make sure that the permissions on you private files directorie are correct.

Also check the status report /admin/reports/status and the recent log entries /admin/reports/dblog for clues about why it is going wrong.
> 0 votes

---
Tags: files
---


# Question
Title: How do I load a field collection from a node?
I have a node that has a few field collections on it.

When I look at `node_load()` output, I see:

```
[field_rich_text_group] => Array
        (
            [und] => Array
                (
                    [0] => Array
                        (
                            [value] => 6
                        )

                    [1] => Array
                        (
                            [value] => 7
                        )

                    [2] => Array
                        (
                            [value] => 8
                        )

                )

        )

```

What API function can I use to actually load the field data contained in the collection that has an entity\_id of 6, 7, 8, etc?

# Answer
Doh! I should have looked in the field collection module:

```
entity_load('field_collection_item', array($item_id))

```
> 90 votes

# Answer
There is also a wrapper function that does the same trick:

`field_collection_item_load($id, $reset = FALSE)`

or as per comment, use:

```
field_collection_item_load_multiple($ids = array(), $conditions = array(), $reset = FALSE)

```

to load multiple collections (for example if you have an *Add more* buttons).
> 41 votes

# Answer
field\_collection\_field\_get\_entity() should be used in order to load the correct revision.

Example usage:

```
$node = node_load(1);
$items = field_get_items('node', $node, 'field_fc');
foreach ($items as $item) {
 $fc = field_collection_field_get_entity($item);
 // Do something.
}

```
> 22 votes

# Answer
You can use `entity_metadata_wrapper` from the Entity API module:

```
$node_wrapper = entity_metadata_wrapper('node', $node);
$field_collection = $node_wrapper->field_rich_text_group[0]->value();
dpm($field_collection);

```

You can loop all the collections as well:

```
$node_wrapper = entity_metadata_wrapper('node', $node);
foreach ($node_wrapper->field_rich_text_group as $field_collection_wrapper) {
  $field_collection = $field_collection_wrapper->value();
  dpm($field_collection);
}

```
> 13 votes

---
Tags: 7, entities
---


title: 301 Redirect Module

text:
# Question
Title: 301 Redirect Module
I need to redirect specific broken/dead links to other pages within my site. I'm looking for a module that I can setup, then have my support team change without needed htaccess, etc.

I came across the Path Redirect module, which then sent me to the Redirect module. Can the Redirect module accomplish that? Again, I am NOT looking to redirect the entire site nor looking to setup redirect rules. I need to redirect specific pages, and would like a non-dev on my team to be able to do so.

# Answer
> 10 votes
Yes, the Redirect module will do this. It will go through the `{watchdog}` table for "Page Not Found" errors, and then give you a UI for adding redirects for each 404 it found. My team (many of which are non-technical) have been able to manage this without me writing any manual redirects.

# Answer
> 1 votes
May be you are looking for Global redirect module: https://drupal.org/project/globalredirect

Global redirect: Global Redirect searches for an alias of the current URL and does a 301 redirects to it if found. This prevents content from being displayed on multiple urls when the path module is enabled. Displaying duplicate content at multiple url's can cause a loss of search engine site ranking. This way it is very useful to maintain the site ranking along with maintaining the redirects.

# Answer
> 0 votes
I doubt on global redirect module as the description provided pretty much says global redirect module role is to kill the redundant route for a page, so if you have a node with path alias www.yoursite.com/xxxx there will be parallel route for the same page as www.yoursite.com/node/nid so this will make row ranking in seo,

if your question is to redirect specific broken/dead links to other pages within my site redirect module is the one you are looking for.

---
Tags: redirection
---


# Question
Title: Why can't I override my menu in Drupal 7 with theme_menu_tree?
I'm working in drupal for the first time and I'm coming along nicely and learning as I go. I need to remove the UL and LI from my menu so I've been doing some research and "MYTHEME\_menu\_tree\_menu\_name" was suggested to override the container. As A test I'm trying this in my template.php file:

```
function storm_menu_tree__menu_social_media($variables) {
  return '<span class="test-menu">' . $variables['tree'] . '</span>';
}

```

Where "storm" is my theme name. My menu name is "Social Media" but D7 shows the machine name as "menu-social-media".

When I test this nothing is affected. What am I missing?

I should note this is a sub-theme based off Zen Theme.

--- edit ---

this is what I'm using to call the menu:

```
<?php
$menu_name = 'menu-social-media';
$menu_id = 'social-media';
print theme('links', array('links' => menu_navigation_links($menu_name), 'attributes' => array('id' => $menu_id, 'role' => 'navigation', 'class'=> array('links', 'inline'))));
?>

```

# Answer
> Drupal 7 theme can implement a THEMENAME\_menu\_tree\__MENU\_NAME() or THEMENAME\_menu\_link\__MENU\_NAME() function to override theme\_menu\_tree() or theme\_menu\_link() for a specific menu.

References for overriding the specific menu:

Can you once try passing $variables as reference to the THEMENAME\_menu\_tree\__MENU\_NAME() as below:

```
function storm_menu_tree__menu_social_media($variables) {
  return '<span class="test-menu">' . $variables['tree'] . '</span>';
}

```

**Note:** Clear the cache after making the changes to the code in order to make sure implemented changes reflects on the site.
> 2 votes

---
Tags: 7, routes, theming
---


# Question
Title: How do I move more link to title of views block?
I am using Drupal 7 and Views, I created a block and a "more link" for showing on the frontpage.

How can I move the "more link" next to the title of views block?

# Answer
You should copy the views-view.tpl.php from views module into your theme folder. If you want to do this only for a specific views, you should also rename the file like `views-view--your-view.tpl.php`. Then you can simply move the 'more link' part wherever you like in this template file.

UPDATE: Thanks to @Mołot's pointing about an issue that the title is rendered by the block, I've found out that there is already a discussion about that in the API page. As a workaround, you can set in the block configuration the title to `<none>` so that it isn't rendered by block. And in the views template replace the following part which is responsible for printing title:

```
<?php if ($title): ?>
  <?php print $title; ?>
<?php endif; ?>

```

with this:

```
<?php if (empty($title)): ?>
  <?php $title = check_plain($view->get_title()); ?>
<?php else: ?>
  <?php print $title; ?>
<?php endif; ?>

```
> 2 votes

# Answer
**If you don't want the process, just result, scroll to TL;DR below!**

In your view setting page, go to display of your block. In it, expand *Advanced* column, and on the bottom click *Theme: Information*. You will get screen like this:

Here you can see selection of names. You don't want to override *views-view.tpl.php* as it's default for all views and all displays. You want it for blocks, so *views-view--block.tpl.php* is a natural choice for all blocks, and *views-view--test--block.tpl.php* if you only want to affect view named *test*.

Create an empty file with selected name, click "Display output" link, copy what you see there into your file, save, and upload to your theme directory. Then, click *Rescan template files* \- now your new template is in use and can be edited.

Problem is that block's title is not rendered in it. The part

```
<?php print render($title_prefix); ?>
<?php if ($title): ?>
  <?php print $title; ?>
<?php endif; ?>
<?php print render($title_suffix); ?>

```

is not executed as title was already rendered by *block.tpl.php* of your template, probably something like this:

```
<?php print render($title_prefix); ?>
<?php if ($title): ?>
  <h2<?php print $title_attributes; ?>><?php print $title; ?></h2>
<?php endif;?>
<?php print render($title_suffix); ?>

```

Similar, yes, but *block.tpl.php* cannot know about your `$more`. Trying to import it with `global $more` causes:

> Notice: Undefined variable: more

So what do we have defined? Time to

```
<?php dpr(get_defined_vars()); ?>

```

Sadly, no luck here. So maybe we should force our theme to use view's tpl directly for blocks? In `theme_preprocess_block(&$variables, $hook)` temporarily add `dpr($variables['block_html_id']);`. Now, I see my block's id is *block-views-test-block-1*, so in the hook I add:

```
if ($variables['block_html_id'] == 'block-views-test-block-1') {
  $variables['theme_hook_suggestions'][] = 'views_view__test__block';
}

```

Note that `-` and `_` are swapped between suggestion and file name. But that will not work - it will execute our tpl in a context where it has no variables. What's now? I add a bare block template, of course:

```
if ($variables['block_html_id'] == 'block-views-test-block-1') {
  $variables['theme_hook_suggestions'][] = 'block__raw';
}

```

With only one line in it:

```
<?php print $content ?>

```

Now the title is not printed using main *block.tpl.php*, so in your *views-view--block.tpl.php* you can move following section around:

But wait, $title is **NOT** available inside view's block template, now you can have more within the title area, but title itself is not there. So time to rollback template suggestion.

**TL;DR**

From your *views-view--block.tpl.php* remove lines that print `$more`. At the beginning, add:

```
global $block_more;
$block_more = $more;

```

In your main *block.tpl.php*, use something like:

```
<?php if ($title): ?>
  <h2<?php print $title_attributes; ?>><?php print $title; ?>
  <?php global $block_more; ?>
  <?php if (@$block_more): ?>
    <?php print $block_more; ?>
  <?php endif; ?>
  </h2>
<?php endif;?>

```

The rest is a matter of CSS.
> 2 votes

# Answer
One solution is to customise both the views block template (the inner part of the HTML) and the block template for the view or views in general (the outer part). So you might have a views block template as per Create template file for views block and also a block template block--views.tpl.php in your theme.

Thus you can amend your views template so it renders the title from $view-\>get\_title() instead of the $title variable (which will be blank), and put the more link after it. At the same time you would amend the block template so it doesn't show the title at all.

But a pure CSS solution may work just as well.
> 0 votes

---
Tags: views, theming, blocks
---


# Question
Title: How to add a condition based on a line-item's product type in a rules tax component?
In Drupal Commerce, when you create a tax rate of a particular type, let's say a "VAT low" of type VAT, a rule "Calculate taxes: VAT" is created, as well as a rule component "Calculate VAT Low".

Now I want to make the "Calculate VAT Low" component conditional on the product type of the product referenced in the line item. The examples for conditions in the tax component that I found, however, use data selectors of the order like address, not a line item. Other examples of using conditions based on the product type referenced by the line item are configured at the level of the rule, not the component (e.g. here). The `commerce-line-item:commerce-product:type` does not seem to be available when adding conditions to a component.

Is it possible to make tax components conditional on the product type of the line item? Or should I create a separate rule for each tax rate component rather than use the default "Calculate taxes: VAT"?

# Answer
I found out how to use product type as a condition - it actually does work the same for rules and rules components.

When I tested this, I was adding the condition "Entity has field": `field_product`, but in order for the `commerce-line-item:commerce-product:type` data selector to appear under the Data comparison condition, you have to use the field `commerce_product`, which is the product reference field used on the line-item entity.
> 1 votes

---
Tags: commerce, rules
---


title: Custom field on user page

text:
# Question
Title: Custom field on user page
I'm trying to add a new fields with hook\_form\_alter on **user\_profile\_form**. From the core module right now there are:

Password confirm

Pass and re-enter pass

E-mail

This is the part of my code:

```
/*
 * Implements hook_form_alter().
 */

 function mymodule_form_alter (&$form, &$form_state, $form_id) {

switch ($form_id) {
        case 'user_profile_form':

        $form['account']['telephone'] = array(
        '#type' => 'textfield',
        '#title' => t('New mobile'),
        );

        $form['account']['pass_title'] = array(
        '#type' => 'markup',
        '#markup' => '<div class="profile-pass-title">Password change</div>',
        '#weight' => -6,
        );

        //krumo($form);
        break;
        }
}

```

As you can see I've added the telephone field into the form, but when I add text into that text field it doesn't save. The url is **user/%/edit**. I'm missing something.

The core fields password and email are properly saving.

The next thing is to do is when I add a new field on **user\_profile\_form** to be displayed into user/%.

Previously I've mention **admin/config/people/accounts/fields**, when I add a field from there let's say "telephone" it's working great. On **user/%/edit** is appearing as a form field and on **user/%** the result is rendering well. But my idea is: when I've added this field I want to have a title over the "telephone" field result. The title will be "Changing telephone" and bellow will be displayed the "telephone" field result (the result is what the user filled in the textfield on **user/%/edit**).

@Alfred Armstrong post helped a lot.

With The **Field group** module this is possible to achieve. It's amazing that on user\_profile\_form I can use fieldset and wrap the field into, it displays into user/%/edit and on display field that render the results on user/% I can use different fieldset and with little CSS I can do exactly what I want. Many thanks to Alfred Amstrong for showing me this module and thank you all who helped me to find an aswer for this task. I wish I could add +1 to you all :)

# Answer
> 1 votes
Take a look at the Field Group module. That will enable you to group fields under a heading as you require. You can add groups on the form or on the display independently.

After you enable the module the display editor at Administration -\> Configuration -\> People -\> Account Settings -\> Manage Display will show a new entry to "Add new group". Add a new group of type fieldset, give it a title as required and set it to be "open" (not collapsible). You can then drag and drop individual fields into the group.

By default the group will display in a box. If you don't want that, the CSS to override it is pretty simple, eg:

```
body.page-user fieldset {border: none;padding:0;margin:0}

```

---
Tags: entities, hooks
---


# Question
Title: Similar Module for Drupal: Easy Folder Listing?
Do you know of a Drupal module that does this: I have been searching for a solution to use in a Drupal site where the Folder Contents are Listed in a Table, exactly as described in the below description of this *Joomla* module.

http://extensions.joomla.org/extensions/directory-a-documentation/downloads/12249

Description: This is a simple-to-use module that is used to list the contents of a folder in either a table or a list. The folder listing can display the filename, with or without the extension, with or without the date modified and file size, as well as a icon representing the file type. It has the feature of allowing the user to specify whether the filename listed should be linked or not.

Main features:

> List files in a specified sub-folder of the Joomla root Show icons for file types List files in either a table or a unordered list Option to link to the files or not

# Answer
> 1 votes
Maybe you have to try two modules who allow to manage files in Drupal:

> The Media module provides an extensible framework for managing files and multimedia assets, regardless of whether they are hosted on your own site or a 3rd party site

* workbench media : it's an integration of the first module in the workbench suite, that's great if you want a listing of all your files uploaded in your site.

If you just want to display files to the users, you can do that quickly with views:

* Add a new view
* In `show` section select files

After you'll be able to show all the files you have in your folder (but you can also restrict to only show files from a specific content type) I took a photo of all the fields available :

# Answer
> 1 votes
I use some simple php in a basic page. This is first draft code (doesn't take into account empty folder, etc.), YMMV, but it works for me.

```
<?php
$path = '/files/my-files/';
$fullPath = '/var/www/drupal/sites/default' . $path;
$myDirectory = opendir($fullPath);
$i = 0;
while($entryName = readdir($myDirectory)) {
  if ($entryName != '.' && $entryName != '..') {
    /* Change order to change sort order */
    $dirArray[$i]['date'] = filemtime($fullPath. $entryName);
    $dirArray[$i]['name'] = $entryName;
    $i++;
  }
}
closedir($myDirectory);

$indexCount = count($dirArray);

sort($dirArray); /* sorts by first field above */

print('<table cellpadding="5" style="width:100%" cellspacing="0">');
print("\n<tr><th>Title</th><th>Updated</th></tr>\n");
/* Reverse or forward order */
for($index = $indexCount -1 ; $index >= 0; $index--) {
  if($index % 2 == 0) $class = ' class="even"'; else $class = ' class="odd"';
    $name = $dirArray[$index]['name'];
    $displayName = str_replace('_', ' ', substr($name, 0, strlen($name)-4));
    $icon = '';
    switch (substr($name, strlen($name)-4, strlen($name))){
      case ".doc": $icon = ' <img alt="doc" src="/images/icon_doc.png">';break;
      case ".pdf": $icon = ' <img alt="pdf" src="/images/icon_pdf.gif">';break;
      case ".xls": $icon = ' <img alt="xls" src="/images/icon_xls.gif">';break;
    }
    print("<tr$class><td><a href=\"$path$name\">".$displayName." $icon</a></td>\n");
    print("<td>");
    print(str_replace(' ', ' ', date('j M Y', $dirArray[$index]['date'])));
    print("</td>");
    print("</tr>\n");
}
print("</table>\n");
?>

```

# Answer
> 1 votes
Somehow late, but you may take a look at the "Directory based organisational layer" module.

Here is a quote about it (from the module's project page):

> ... adds a new organizational layer to drupal, making it easy for managing large numbers of files and nodes. It allows the creation of on the fly directory structures and upload of multiple files at once. Jpeg files are displayed as slideshows, other files can be downloaded from a block.

---
Tags: 7
---


title: Integrate facebook into rating logic

text:
# Question
Title: Integrate facebook into rating logic
I want to build a functionality on my website that allows you to +1 (add a vote) a post. I want to integrate this functionality with facebook, so that 1 single vote is allowed per facebook user (without creating an account for that user on my site -- if it is possible).

Please point me in the right direction for this. I'm looking for any solution that is a Drupal Best Practice, or any idea that you have on the subject and how it can be achieved.

Right now I think I will go with Fivestar module, but I'm not sure how to integrate this.

# Answer
> 4 votes
You are looking for Entity External Rating module. Check the site using this module.

> This module can be used to implement a rating system based on external sources. What that means is that the actual rating, voting or whatever action, happens on an external application (for example on Facebook), and the results are fetched into your system. By itself, this module is intended for developers to use it like an API.

One key question would be why to use this module and not the Voting API with the **Fivestar module** for example. Here are the most important reasons:

* The main advantage of this module is that your system does not handle now the actual rating process. This now happens on external systems.
* You can have many sources from which your rating is fetched. The results will be aggregated from all of them.
* If you have a site with mostly anonymous traffic, it will be very easy for your users to rate content through **Facebook or Twitter**.

---
Tags: social-network, rating
---


title: Cannot log in to Drupal site

text:
# Question
Title: Cannot log in to Drupal site
I have problems with a Drupal 7 site. Sometimes, when I try to log in as non-admin user I am not able to login, despite typing in the correct email and password (I am using the Email Registration module). There is no issue with this module because from the very first day after I installed it, it worked well. However, in the last couple of days or week I am getting errors for when I try to login.

I logged in as admin and changed the password for the non-admin user, after doing that, I was again able to login on my site.

I got this error sometimes, but it is not frequent.

# Answer
The red box you see is a means that the e-mail address you typed in did not match with any e-mail addresses registered on the site, *or* that the password was not recognised. You should also be able to see a red message-box further up on the same page with more information about the problem. For example:

> Sorry, unrecognized username or password. Have you forgotten your password?

The most likely explanation for this error is that you misremembered the password. This also explains why it starts working again after you login as admin and reset the password for the non-admin user.

However, I've noticed that you've definitively ruled out this explanation in your question. Fair enough, I just wanted you to make *sure* this is not what is happening. I've run dozen of Drupal sites for many years (many of them with the Email registration module enabled) - and I've *never* seen this happen *except* when the credentials are mistyped.

If that is *not* what is happening, I have no good alternative explanation.

To progress with debugging, you may extract the `{users}.pass` field (hashed) from your database, and see if the hashed value changes between when you're able to log in, to when you're not. If it is changed, then you have some rogue process (or user) that munges the pass field in your `{users}` database. (If it is *not* changed, then this is very, very mysterious.)
> 1 votes

---
Tags: 7, users
---


# Question
Title: How to programmatically translate/localize taxonomy terms?
I want to use Google Translate for translating taxonomy terms. I have the "Talking to Google" part done, but I can't find much documentation on translating terms & their descriptions programmatically.

Please help!

# Answer
> 3 votes
I was able to do it using the following code:

```
<?php
    $enabled_languages = array_shift(language_list('enabled'));
    foreach ($enabled_languages as $language => $object) {
        if ($language != 'en') {
            //Translate description
            i18n_string_translation_update(
                array('taxonomy', 'term', 12, 'description'), // Path where to store source and translation.
                autotranslate_translate($term->description, 'en', substr($language, 0, 2)),
                $language
            );
            //Translate name
            i18n_string_translation_update(
                array('taxonomy', 'term', 12, 'name'), // Path where to store source and translation.
                autotranslate_translate($term->name, 'en', substr($language, 0, 2)),
                $language
            );
        }
    }

```

?\>

# Answer
> 1 votes
1. Get / translate strings.

For translating these strings, the module must call this function before displaying them:

```
<?php
/**
 * Translate or update user defined string.
 *
 * @param $name
 *   Textgroup and location glued with ':'.
 * @param $string
 *   String in default language. Default language may or may not be English.
 * @param $options
 *  Optional parameters like 'langcode' if language code is different from the page request one.
 *
 * @return $string
 *   Translated string, $string if not found
 */
function i18n_string_translate($name, $string, $options) {
   .....
}
?>

```

For strings that have an input format you must use the function `i18nstrings_text()` that takes care of applying the correct filters if there is a translation.

```
<?php
/**
 * Get filtered translation
 *
 * This function is intended to return translations for strings that have an input format.
 * If no format passed, the default one will be used
 *
 * @param $name
 *   Full string id
 * @param $default
 *   Default string to return if not found, already filtered
 * @param $options
 *   Optional parameters, like 'format'
 */
function i18n_string_text($name, $default, $options) {
  ....
}
?>

```
2. Create translation sets (taxonomy example)

To translate a string, you should use two functions, depending on which i18n mode you use:

* Localize mode: i18n\_string\_translation\_update()
* Translate mode: i18n\_translation\_set\_create()

i18n\_tsid) ? i18n\_translation\_set\_load($source\_term-\>i18n\_tsid) : i18n\_translation\_set\_create('taxonomy\_term', $vocabulary-\>machine\_name);
```
  // 2. Add the full source term in this set.

```
$translation\_set-\>add\_item($source\_term, $source\_term-\>language);
```
  // 3. Add the full translated term in this set.

```
$translation\_set-\>add\_item($translated\_term, $translated\_term-\>language); $translation\_set-\>save(TRUE); ?\>

Strings for other contents and modules

When a module defines its own strings, it must use some additional functions to allow these string to be tracked and updated.

1. Define the textgroup by implementing `hook_i18n_string_info()`. This is how it looks (i18n\_taxonomy module)
```
<?php
/**
 * Implements hook_i18n_string_info()
 */
function i18n_taxonomy_i18n_string_info() {
  $groups['taxonomy'] = array(
    'title' => t('Taxonomy'),
    'description' => t('Vocabulary titles and term names for localizable vocabularies.'),
    'format' => FALSE, // This group doesn't have strings with format
    'list' => FALSE, // This group cannot list all strings
    'refresh callback' => 'i18n_taxonomy_i18n_string_refresh',
  );
  return $groups;
}
?>

```
2. Use i18n\_string\_update() whenever the source string changes.
```
<?php
/**
 * Update / create translation source for user defined strings.
 *
 * @param $name
 *   Textgroup and location glued with ':'.
 * @param $string
 *   Source string in default language. Default language may or may not be English.
 * @param $options
 *   Array with aditional options. The most important one is the 'format' parameter when the string has an input format.
 */
function i18n_string_update($name, $string, $options = array()) {
  ....
}
?>

```

The format parameter is to be used when the string is to be formatted with Input filters before displaying. If so, filter permissions will be properly handled by i18nstrings. Only users that can access the Input format will be able to translate that strings. These strings must be translated using i18nstrings\_text() instead of i18nstrings().

3. Optional refresh callback function as defined in hook\_locale()
```
<?php
/**
 * Update / create translation source for user defined strings.
 *
 * @return $bool
 *   TRUE if update successful, FALSE if not.
 */
  function mymodule_locale_refresh() {
    ...
    // code to call i18n_string_update() for every string used by this module
    ...
    return TRUE; // Update completed with no issues
  }
?>

```

The refresh function should call i18n\_string\_update() for every string that is to be translated in your module. The refresh interface will remove all strings defined by your module and only re-list the strings added by the refresh callback function.

Again, all Drupal core textgroups and strings will be defined and handled by i18n\_string when edited using the default pages for it. So you just need to implement these other functions when your module uses specific user defined strings.

The easiest way to have the strings translated without adding a new module dependency is to create a wrapper for your module which just translates the strings when i18n\_string module is enabled.

```
<?php
function mymodule_translate($name, $string, $langcode = NULL) {
  return function_exists('i18n_string') ? i18n_string($name, $string, array('langcode' => $langcode)) : $string;
}
?>

```

Or, if your module has its own textgroup, we can have a default parameter for that textgroup and same some code. Note we still keep the 'textgroup' parameter just in case we need to translate other module's strings, like for occasionally translating a taxonomy term or a content type name.

```
<?php
function mymodule_translate($name, $string, $langcode = NULL, $textgroup = 'mytextgroup') {
  return function_exists('i18n_string') ? i18n_string($textgroup . ':' . $name, $string, array('langcode' => $langcode)) : $string;
}
?>

```

Read more at: Using the i18n API from other modules

Related:

How to associate programatically the translation of new term to the original existing term?

---
Tags: taxonomy-terms, i18n-l10n
---


# Question
Title: Full Html Text format (and wysiwyg) show only for administrator role
I use Wysiwyg module with CKeditor since months and all worked well. Wysiwyg module is linekd only wit my input-format "Full html" and this is granted to use to my role "Editor". it worked very good.

Unfortunately, since the last Drupal core update i have a big problem:

it seems that only Administrator users can use the FULL HTML text format, my other roles don't see that format and so also the Wysiwyg module doesn't appear.

I've done many checks and tests (permissions, cache etc) but the only thing i discovered is that is a problem of permission on the TEXT FORMAT and not on the wysiwyg module... The proof is that if i apply wysiwyg to the "Plain text" format, also the EDITOR role see the wysiwig editor.

how can i fix this problem? i also tried to remove and re-set the permissions for the role to use the "Full HTML" format

# Answer
> 2 votes
I've got the same issue because of js error 'once is not defined'. To fix an error I've added to my html.tpl.php:

```
<?php print $scripts; ?>
<script src="/misc/jquery.once.js"></script>

```

---
Tags: users, wysiwyg, input-formats
---