Closed Thread Icon

Topic awaiting preservation: Server-Side headaches - what is wrong with this code? (Page 1 of 1) Pages that link to <a href="https://ozoneasylum.com/backlink?for=29230" title="Pages that link to Topic awaiting preservation: Server-Side headaches - what is wrong with this code? (Page 1 of 1)" rel="nofollow" >Topic awaiting preservation: Server-Side headaches - what is wrong with this code? <span class="small">(Page 1 of 1)</span>\

 
Racketeer
Neurotic (0) Inmate
Newly admitted

From:
Insane since: May 2007

posted posted 05-23-2007 13:49

Cheers everyone!

I am adapting an existing site into a php environment. I want to do the navigation with variables and then include the appropriate content so that

www.server.net/index.php?page=services.php <- user sees the services content included on index.php

www.server.net/index.php?page=contact.php <- user sees the contact page content in index.php

As register_globals is OFF, I am using GET to obtain the $page variable:

code:
<?php 
$page = ($_GET["page"]);
if (isset($page)) {
    echo "Variable is set";
}
else {
    $page="welcome.php";
}
echo $page;
?>



This works just fine as long as the variable is set (passed on in the URL like so: /index.php?page=contact.php)

It FAILS partially however when no variable is passed in the URL like so: /index.php

The intended page content (welcome.php) displays correctly, but an ugly warning line appears at the top of the site stating:

Notice: Undefined index: page in /home/s/server.net/user/htdocs/index.php on line 12

Line 12 is this one out of the above code:

code:
$page = ($_GET["page"]);



Since it basically works fine, I would be very happy with a way to get rid of the warning message OR some alternative coding.

HEEEEELP

poi
Paranoid (IV) Inmate

From: Norway
Insane since: Jun 2002

posted posted 05-23-2007 14:00

What about checking if $_GET['page'] is set before assigning it to a variable ?

code:
$page="welcome.php";
if( isset( $_GET["page"] ) )
{
    $page = $_GET["page"];
    echo "Variable is set";
}

You could of course prefix the assignement in you line 12 by an @ but it's not the best way to go.

Racketeer
Obsessive-Compulsive (I) Inmate

From:
Insane since: May 2007

posted posted 05-23-2007 15:52

It works! Thank you very much!

My knowledge of PHP is not very profound. I thought of assigning the "standard" variable first but I read somewhere that once a variable is assigned it cannot be changed.

Thanks for your help!

Tyberius Prime
Maniac (V) Mad Scientist with Finglongers

From: Germany
Insane since: Sep 2001

posted posted 05-23-2007 16:47

now... if you're doing an include ( $_GET[["page"} ) or any variant there of, chances are
very high you've just opened a grade A security hole.

Racketeer
Obsessive-Compulsive (I) Inmate

From:
Insane since: May 2007

posted posted 05-23-2007 16:55

Well as I said, my knowledge of PHP is not very profound.

Here's the complete code:

code:
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<title>site title</title>
<style type="text/css" media="screen">
<!--
@import url("css/screen.css");
-->
</style>
<?php 
$page="welcome.php";
if( isset( $_GET["page"] ) )
{
    $page = $_GET["page"];
}
?>
</head>
<body>
<div class="container">
	
	<div class="main">

		<div class="header">
			<div class="title">
			  <a href="index.php"><img src="/img/homelink.gif" alt="home" width="958" height="90" border="0" id="vtitle" /></a>            </div>
		  <!-- close title -->
		</div><!-- close header -->
		
		<div class="content">
		<?php include $page; ?>
		</div><!-- close content -->
        
        <?php include 'sidenav.php'; ?>
				
			<div class="clearer"><span></span></div>

	</div><!-- close main -->

	<div class="footer">footer goes here</div>

</div><!-- close container -->
</body>
</html>



Is there a security hole?

Racketeer
Obsessive-Compulsive (I) Inmate

From:
Insane since: May 2007

posted posted 05-23-2007 16:57

sidenav.php

code:
<div class="sidenav">
	<h1>Services</h1>
		<ul>
        	<li><a href="index.php?page=services.php">Services</a></li>
  </ul>

	<h1>About us</h1>
		<ul>
			<li><a href="index.php?page=contact.php">Contact</a></li>
		</ul>
</div><!-- close sidenav -->

poi
Paranoid (IV) Inmate

From: Norway
Insane since: Jun 2002

posted posted 05-23-2007 17:22

Sure there is a security hole if you don't check if $_GET['page'] points to a public page.

The following should pluck that hole:

code:
$pagesWhiteList = Array( 'welcome.php', 'foo.php', 'bar.php', 'baz.php' );

$page="welcome.php";
if( isset( $_GET["page"] ) && in_array( $_GET["page"], $pagesWhiteList ) )
{
    $page = $_GET["page"];
    echo "Variable is set";
}
//...

HTH

poi
Paranoid (IV) Inmate

From: Norway
Insane since: Jun 2002

posted posted 05-23-2007 17:35

Also you might consider doing some sort of URL rewriting. Nice URLs look more professionnal.

If you actually link directly to services.php, contact.php and so on you'll have to include the header and footer in each of these pages. No big deal.

Or you could do real URL rewriting using an .htaccess file

Or, as I tend to prefer, catch the 404 and check the $_SERVER['REQUEST_URI'] to include the header, serve the page you want and the footer. This way you can even check for typos in the REQUEST_URI. That's what I do on my site.

Racketeer
Nervous Wreck (II) Inmate

From:
Insane since: May 2007

posted posted 05-23-2007 18:03
quote:

poi said:
If you actually link directly to services.php, contact.php and so on you'll have to include the header and footer in each of these pages. No big deal.



My original idea is to use index.php as a "frameset", containing all layout and styles and then calling the content with the above include.
The original site was done in Dreamweaver with Templates. Stripping excess and redundant code alone has reduced the overall size by more than 70%! Thats why I am quite happy about doing it this way.

I have seen URLs on other sites such as

/index.php?id=4
/index.php?id=5

I understand that it works by renaming the variable $page to $id but I simply don't know how to subsitute the *.php at the end of the variable or writing a "key" list containing ids for the actual files to be included.

I have never even remotely touched the subject of URL rewriting.

(Edited by Racketeer on 05-23-2007 18:04)

Tyberius Prime
Maniac (V) Mad Scientist with Finglongers

From: Germany
Insane since: Sep 2001

posted posted 05-24-2007 11:32

framesets are not only soooo 20ieth century, the also break acessibility.

Now, that line

code:
<?php include $page; ?>



is a massive security whole that allows anybody to see any file on your server - including /etc/shadow, containing (crypted )passwords and plaintext usernames. Add in a weak password on one account, and you just have found a valid username/password combo...
(Not to mention the other attack vectors... database password files)

And what's more: if php is misconfigured, $page could be an URL, pointing to a different server, allowing the attacker to include *any* code he wants!

Now take that thing down till you have at least read the documentation on php->include before your server get's hacked ( there are automated scripts for this... and they roam the net's endlessly. Don't believe you're save just because your url hasn't been published).


Those other pages probably pull their content out of databases... and the way you phrased your sentence, also shows me that you lack a concice concept of what parts urls consist of.

To make it short ( since I got some dna prep to attend to ) - you still have a lot to learn, "young Racketeer", and our ->faq is a decent place to start.

Don't hesitate with questions - we're quite eager to help out provided you've done your homework.

So long,

->Tyberius Prime

poi
Paranoid (IV) Inmate

From: Norway
Insane since: Jun 2002

posted posted 05-24-2007 12:19

Tyberius Prime: Notice that Racketeer said "frameset", with quotes.

Racketeer: A site having pages like services.php, contact.php, welcome.php, ... seems small enough to not have to use ugly not-user-friendly-URLs.

To include the header, nav, footer, ... you can even use the Oh so convenient Apache directives:

code:
php_value auto_prepend_file /path/of/the/scriptToPrepend.php
php_value auto_append_file /path/of/the/scriptToAppend.php

HTH

Racketeer
Nervous Wreck (II) Inmate

From:
Insane since: May 2007

posted posted 05-24-2007 15:16

@Tyberius Prime

I will rethink the entire concept of using PHP at all. If I cannot use the include for security reasons then there is little reason in using PHP at all.
While I am very interested in learning PHP, I am simply lacking the time to do so. And my step by step learning by doing approach seems hardly feasible given the risks you pointed out.

@poi

I've read this tutorial http://www.yourhtmlsource.com/sitemanagement/urlrewriting.html last night so things are clearer now. It seems indeed a fine thing to do but I have yet to check whether the server supports it.

And the prepend and append looks interesting too. One learns new things every day!

poi
Paranoid (IV) Inmate

From: Norway
Insane since: Jun 2002

posted posted 05-24-2007 16:38

you CAN use PHP! Just be careful. Check my code snippet with the $pagesWhiteList variable to see an easy way to pluck the security canyon you had.

Racketeer
Nervous Wreck (II) Inmate

From:
Insane since: May 2007

posted posted 05-24-2007 17:32
quote:

poi said:

you CAN use PHP! Just be careful. Check my code snippet with the $pagesWhiteList variable to see an easy way to pluck the security canyon you had.



I did in fact integrate your fix for the security hole. Thank you for that. But does that fix the <?php include $page; ?> issue mentioned by Tyberius Prime?

poi
Paranoid (IV) Inmate

From: Norway
Insane since: Jun 2002

posted posted 05-24-2007 18:05

Of course it does since it only allows $page to take a value that is in the $pagesWhiteList array, and falls back to "welcome.php"

Tyberius Prime
Maniac (V) Mad Scientist with Finglongers

From: Germany
Insane since: Sep 2001

posted posted 05-24-2007 18:14

yep, a whitelist as poi suggested is just the way to go ( sorry if I hadn't read all of this thread before pointing this hole out - but it's important to educate people (not just you, but the largish amount of lurkers we have ) .

So long,

->Tyberius Prime

Racketeer
Nervous Wreck (II) Inmate

From:
Insane since: May 2007

posted posted 05-25-2007 21:50

Har har, I dug into the subject of URL rewriting and I must say: I love it!

Not everything seems to work however...

The custom 404 page works!

This...

code:
RewriteEngine on
RewriteRule ^(.*)\.html$ $1.php



also works!

But this (really useful)...

code:
RewriteEngine on
RewriteRule ^/contact.html$ /index.php?page=contact.php



doesn't work!

Tyberius Prime
Maniac (V) Mad Scientist with Finglongers

From: Germany
Insane since: Sep 2001

posted posted 05-25-2007 23:41

those are regexps... try escaping the . (by writing \. ) , so that it really means 'dot'.

Also, try appending [R] - that should get you a redirect that's visible in the browser - if you don't get it, the problem lies with the first part of the expression.

Racketeer
Nervous Wreck (II) Inmate

From:
Insane since: May 2007

posted posted 05-28-2007 17:50

Thanks Tyberius! It needed the +FollowSymlinks option activated.

It now works just fine! PHP, includes, url rewriting all smooth! I've learned a lot!

The only issue I just noticed is that of course all pages have the same title now.

My idea is to add another PHP variable to the url rewriting part in .htaccess and echoing that in the title. Is that feasible? Is there a better solution?

(Edited by Racketeer on 05-28-2007 17:50)

Racketeer
Nervous Wreck (II) Inmate

From:
Insane since: May 2007

posted posted 05-28-2007 21:19

Success!

code:
<title>
<?php $title="Company Name Limited"; if(isset( $_GET["title"]))
    {
	$title = $_GET["title"];
    print "$title - Company Name Limited";
    }
	else {print $title;}
  ?>
</title>



...works just fine!

What I wanted to achieve is that when someone calls the initial index page of the site, the title should say:

Company Name Limited

And when someone calls the contact page, the title should say:

Contact - Company Name Limited


The title variable is generated in .htaccess like so:

code:
RewriteRule ^contact\.html$ index.php?page=contact.php&title=Contact



My problem now is:

How can I pass a varibale consisiting of two words?

So that the title says About us - Company Name Limited. I've tried putting the title variable in ' ' or " " but it seems not to work. Also the trick in combining them with %20 doesn't work (it passes the variable but displays it with a 0 instead of a space: About0us - Company Name Limited

EDIT: I have unsuccessfully tried:

code:
RewriteRule ^contact\.html$ index.php?page=contact.php&title=About&#032;us



(Edited by Racketeer on 05-28-2007 21:20)

(Edited by Racketeer on 05-28-2007 21:25)

Racketeer
Nervous Wreck (II) Inmate

From:
Insane since: May 2007

posted posted 05-30-2007 15:36
code:
RewriteRule ^contact\.html$ index.php?page=contact.php&title=About+us



works

« BackwardsOnwards »

Show Forum Drop Down Menu