Web Hosting Talk







View Full Version : executing php code stored in a variable?


matt2kjones
06-23-2003, 11:58 AM
how would u do this?

i have the following code in a variable:

?>

loads of html
<?php echo($var); ?>
some more html

<?php

this is stored in a variable

basically i want a wat of php to read that var, and instead of echoing ?> read it as the end of php, echo the html inside

then when it finds another <?php tag start parsing as php again

possible?

Rich2k
06-23-2003, 12:06 PM
I believe eval() is what you are looking for?

http://uk.php.net/eval

Lagniappe-labgeek
06-23-2003, 12:19 PM
Just remember to make sure none of the eval'ed code comes from the browser side. They could in effect wedge code in, change variable values, potentially get your database password, etc. But I suspect you want to load in from a database or some other source not the visitor...


Just for fun, eval this --> var_dump(get_defined_vars());

And see what kind of info a user could get at...

matt2kjones
06-23-2003, 01:59 PM
well basically im making a template based site, where the user can change templates to change the look of the site.

the templates are .tpl files, and what i want to do is have all the site code store all the data which is sent to the browser, in variables

then on the .tpl files, where it has text like this:

{var_name} the script will use str_replace to change it to:

<?php echo($var_name); ?>

the once it is all done, the file is stored in a variable, and the script has to execute the variable

so would this function be ok to execute these template files???

no passwords or anything would be stored in the template file varaibles, only data which is being sent to the browser will be

Lagniappe-labgeek
06-23-2003, 02:42 PM
The template files are pre-made right? The visitor can't change the template itself, but can just pick from a list of them? That shouldn't be a problem I wouldn't think. But if the user has the ability to enter/modify and part of the data that is going to be eval'ed, then that would be a potential problem.

With the 1 line above, you can get directory structures, and any variables (database name/username/password in variables?). From there you could get directory listings, and get at any text files with just a little work. Then a little more creativity and they can get at your database.



BTW, there's a note on the php.net site about get_defined_vars not being able to get at vaiables inside of includes. That's garbage... Variable inside of functions won't be seen outside of them but that's a scoping thing.

matt2kjones
06-23-2003, 05:55 PM
uses choose from a list of templates so know they wont be able to have physical access to type in var names to get data out of them

Lagniappe-labgeek
06-23-2003, 06:07 PM
I wouldn't think that would be a problem then.

Saeven
06-23-2003, 07:25 PM
Hello.

A smarter alternative running-time wise is to perform the 'opposite'. Instead of evaluating interspersed php code you would probably be better off parsing out the dynamic parts and running from a template 'engine' of sorts.

Instead of the approach you suggest, consider saving the dynamic data as variables which have text equivalences. Start by using a search/replace array tactic..ex


<?php

$data = array();

// merge the date into the data array
$data = array_merge( $data, array( '+DATE+' => date( "Ymd" ) ) );

// Let's do something else...
$d = "";
for( $i = 0 ; $ < 10 ; $i++ )
$d .= "$i<br>";

// add this last pointless thing to our array
$data = array_merge( $data, array( '+USELESS+' => $d ) );

// now let's get our template
echo getTemplate( 'demo', $data );
?>


Now the next part is to build a file that you can include that contains the getTemplate method. You can handle this the way you want, the idea is to replace the data in the array keys with the data in the array values. Here's an example implementation, I'm typing this on the fly so forgive any lack of planning :)



<?php

function getTemplate( $page, $data ){

// just open the file, ex below is to open a .htm file
// on yourdomain.com
$file = file( 'http://yourdomain.com/'.$page.'.htm' );

// string the page array into one long string
$file = implode( '', $file );

// parse out the data once it's ready
$search = array();
$replace = array();

foreach( $data as $key => $value ){
array_push( $search, $key );
array_push( $replace, $value );
}

$file = str_replace( $search, $replace, $file );

return $file
}

?>


Now all you have to do is build a .htm file called demo.htm and inside of it using your wysiwyg editor add +DATE+ and +USELESS+ which will be parsed out and replaced by dynamic data. Call this from anywhere and your templated data will be formatted as in the htm files.

Hope this helps or at least elucidates a possible solution!
Cheers.
Alex

Rich2k
06-24-2003, 04:46 AM
What I tend to do is enclose variables in templates like so [somevariable] and then only do a str_replace on the ones I want to detect.

matt2kjones
06-27-2003, 08:16 AM
This is how i done it...........

i open the template using file();

i save it into a var called $temp_file

i then run this:

$temp_file = addslashes($temp_file);

to add \ to any data with ' characters

i then add echo(' to the beggining of the file stored in $temp_file

i then add '); to the end of the file stored in $temp_file

i then replace things like {a_var} with '.$a_var.'

the template is then parsed.

so basically if a template held this:

hello<BR />
my name is {my_name}
hope this works

my script would alter it to this, then parse it:

echo('
hello<BR />
my name is '.$my_name.'
hope this works
');

is that a good way to do it???

thanx :)

JustinH
06-27-2003, 02:39 PM
preg_replace_callback('/\{(\w+)\.?(\w*);?(\w*)}/e','$1($2)',$string);

This is far easier then the earlier mentioned methods. What this does is takes anything within {}'s and parses them as a function. So for example:

{someFunc} would be replaced with the output of the function someFunc();. Even cooler, {someFunc.someVar} would output the equivalent of someFunc("someVar);. About 10x faster and 10x safer then the above methods.

Fixed quote problem :)