1

So I set the text format to "PHP code" and add the following code:

<?php
function f($x) { return $x; }
?>

When I hit Preview, the page dies with Fatal error: Cannot redeclare f(). I have tried this on two separate Drupal 7 sites, one more or less brand new, with the same result.

Is there a step I'm missing to use D7's PHP filter?

  • Did you put this in a node, a block, or somewhere else? Using the PHP input format is often the wrong way to solve a problem. Can you tell us what you're trying to accomplish? – marcvangend Nov 30 '11 at 22:52
  • This was in a new node. I'm generating some nodes using a data set that I have in a text file. Would have used Feeds, but it's a one-off task and Feeds was giving me pain. – feedbackloop Nov 30 '11 at 23:23
  • Does it work if you change the name? – Ashlar Dec 1 '11 at 0:35
  • @JoeS You mean like function very_weird_name($x) { return $x; }? Sadly, nope, same error. I originally came upon this when I noticed my node_save calls were making two nodes each run. – feedbackloop Dec 1 '11 at 0:45
3
<?php 
  if (!function_exists('f')) { 
    function f($x) { return $x; }
  } 
?>

"should" make everyone happy :-) If not, maybe include_once(FILE.php);

  • I would only add the note that all code must go inside the if (function_exists('f')) block, or else it will still run twice. Otherwise good, simple solution; I will accept. – feedbackloop Dec 1 '11 at 20:42
  • I thought about that, but, that would be true only if your php was doing something you did't want run twice. If, however, it was doing something display oriented, eg, 'today's secret word is ' . f(), there would be no harm done by f() running twice. Of course, you could put some code in and some code out depending. – Jimajamma Dec 1 '11 at 20:52
  • That will solve the fatal errors, but please consider implementing a solution which lets you move away from PHP input filter. Agreed, it's available in Drupal 7, but hopefully not for long: drupal.org/node/1203886 – Chris Burgess Jan 23 '13 at 7:18
5

I just tracked this down.

What happens is that previewing a node will invoke both the teaser display and full node display, and both of those invoke the PHP code.

My solution was to set the teaser to hidden for the content type (at Structure > Content Types > [your node type] > Manage Fields > Teaser). However, I didn't want to do this for default types like Basic Page, so I created a new type "PHP Tests" and only made the change there.

So I think this shows how PHP in nodes can get ugly, but for people like me who basically want to eval code in the Drupal environment without making a module sometimes, the above is an okay solution.

4

Nodes are meant for content, not for custom code. To me, your question looks like "I want to drive my car in reverse, but the steering wheel is on the wrong side. Please help my fix my car." I'd rather teach you how to drive forward :-)

The "Drupal way" to run your own code in your site is to create a custom module. That may sound difficult, but it's not.

First, you create a folder in sites/all/modules. Use the name of your module as folder name, I will use 'mymodule' as example.

Second, you create two files in that folder, called 'mymodule.info' and 'mymodule.module'. In mymodule.info, you enter:

name = My module
description = This is an awesome module.
core = 7.x

Adjust the name and description as you like. See the documentation to learn more about .info files.

Third, enter the following in mymodule.module:

<?php
/**
 * Implement hook_module.
 */
function mymodule_menu() {
  $items['my-module'] = array(
    'title' => 'RSS feed', 
    'page callback' => '_mymodule_run_import', 
    'access callback' => TRUE, 
    'type' => MENU_CALLBACK,
  );
  return $items;
}

function _mymodule_run_import() {
  // Place your custom code here.
}

This code registers the 'my-module' path using hook_menu, which means that Drupal now "knows" that when you navigate to http://example.com/my-module, it needs to run the mymodule_run_import() function.

If you decide to use another name instead of 'mymodule', make sure you replace all occurrences of 'mymodule' (both in file/filder names and in the code) with the new name.

As a final step, you need to enable your module.

I hope that helps.

  • I'm sorry but I can't understand why people are upvoting this. I've written dozens of modules, but this is not the question I asked, which was a very specific phenomenon I was trying to understand. – feedbackloop Dec 1 '11 at 15:37
  • First of all, my apologies for mistaking you for an unexperienced Drupal user. I have been active in community support for years, and I've seen many new users who tried to solve problems with php code in nodes. Because that is not recomended, I usually answer those questions like I did here. I do not know the answer to your specific question. People upvote answers if they find them useful, but you do not have to mark it as accepted if my answer did not satisfy your curiosity. – marcvangend Dec 1 '11 at 16:07
  • I do agree, code in nodes is usually bad. My bad, though, for making a stink about an answer others found useful. Thanks for all your work here. – feedbackloop Dec 1 '11 at 16:43

Your Answer

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

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