Jump to content




Recent Status Updates

  • Photo
      30 Sep
    rhossis

    laptop hard disk seated beneath motherboard but with no access panel. 7 hours to replace :(

    Show comments (3)
  • Photo
      19 Sep
    Chall

    I love it when you go to write a help thread, then while writing, you reach an enlightenment, and figure it out yourself.

    Show comments (3)
View All Updates

Developed by TechBiz Xccelerator
Photo
- - - - -

Clean URLs with PHP

.htaccess php clean url seo friendly

29 replies to this topic

#1 Orjan

Orjan

    CC Mentor

  • Moderator
  • 2,918 posts
  • Location:Karlstad, Sweden
  • Programming Language:C, Java, C++, C#, PHP, JavaScript, Pascal
  • Learning:Java, C#

Posted 29 January 2013 - 07:01 PM

What is an URL and a Clean URL

Normally, a URL to a webpage could look something like this:

http://www.example.com/users/page.php?id=4578&do=edit

This is both user unfriendly, administrator unfriendly and SEO unfriendly, as it needs a lot to understand how it's working.

The url is divided into several parts:
  • http:// - scheme, protocol to be used
  • www.example.com - server address
  • /users - path
  • page.php - filename
  • ?id=4578&do=edit - parameter string
This isn't so nice. But you might have notices there are many sites out there whose don't look the same in the last three parts?

Many CMS as Wordpress and Drupal and many forum softwares provides something often called Clean URLs or SEO Friendly URLs
which could look like this:

http://www.example.com/users/4578/edit

Where all steering codes is removed, and only the real data is visible. It looks a lot nicer, isn't it? Say that we also replace the user id there with a user name, say "matthew", it could even look like this:

http://www.example.com/users/matthew/edit


How to achieve Clean URLs

You would need two things. First, you need a .htaccess file modifying how apache (and some other web server softwares, they might need extra addons to be able to run them)

Apache has a module named mod_rewrite which rewrites the URL from what is sent from the browser to what your PHP script actually gets. This is how the .htaccess should look like in this case:


<IfModule mod_rewrite.c>
  RewriteEngine on
  RewriteCond %{REQUEST_FILENAME} !-f
  RewriteCond %{REQUEST_FILENAME} !-d
  RewriteRule ^ index.php [L]
</IfModule>

Explaining the code:
  • First, check if the module is present, else, we can't do anything.
  • Turn on the Rewrite Engine
  • then it checks if the request filename isn't a file
  • and checks if it isn't a directory
  • Then, the RewriteRule makes a call to index.php, no matter what was written in the URL
  • Close the if statement
So, the effect is, that if the file or directory don't exist, we can let index.php deal with this call instead.

So, now, we need to deal with all this information in index.php instead:

To our help, PHP give us lots of information of the call in a special superglobal variable named $_SERVER

if you want to see what it contains, try to vardump($_SERVER) and you get a printout with much about the server and the call.

This is how a short index.php could look like, it contains the function parsing the path, and a short start code to create some good output


function parse_path() {
  $path = array();
  if (isset($_SERVER['REQUEST_URI'])) {
    $request_path = explode('?', $_SERVER['REQUEST_URI']);

    $path['base'] = rtrim(dirname($_SERVER['SCRIPT_NAME']), '\/');
    $path['call_utf8'] = substr(urldecode($request_path[0]), strlen($path['base']) + 1);
    $path['call'] = utf8_decode($path['call_utf8']);
    if ($path['call'] == basename($_SERVER['PHP_SELF'])) {
      $path['call'] = '';
    }
    $path['call_parts'] = explode('/', $path['call']);

    $path['query_utf8'] = urldecode($request_path[1]);
    $path['query'] = utf8_decode(urldecode($request_path[1]));
    $vars = explode('&', $path['query']);
    foreach ($vars as $var) {
      $t = explode('=', $var);
      $path['query_vars'][$t[0]] = $t[1];
    }
  }
return $path;
}

$path_info = parse_path();
echo '<pre>'.print_r($path_info, true).'</pre>';

First, we declare the function:

function parse_path() {

Then, make a clean variable as an empty array:
$path = array();
This is because if everything else fails, we can still return an empty array.

Check so the $_SERVER variable's post REQUEST_URI is set.
if (isset($_SERVER['REQUEST_URI'])) {
If it's not set, we can't use it, so then it would fail.

Now, we divide the variable on the questionmark, as that separates the "normal" URL from the parameters
$request_path = explode('?', $_SERVER['REQUEST_URI']);

Good, now, we read out the path to index.php for the script, say that your installation is under a directory, and not directly in the web root
$path['base'] = rtrim(dirname($_SERVER['SCRIPT_NAME']), '\/');
The info is saved in the array field named 'base', as it's the sites base path

substr takes out a part of the string, in this case everything after the base, which is followed by a slash ("/") which makes us add 1 to the length of the base
$path['call_utf8'] = substr(urldecode($request_path[0]), strlen($path['base']) + 1);
We save this names as utf8, as some non-ascii characters might be written

But the string to use, we decode the utf8 into ascii
$path['call'] = utf8_decode($path['call_utf8']);

As a safety precausion, if the call is the same thing as the script, we treat it as a blank call, returning the script name is usually not needed for the rest of the program, and if so, it can read it itself from the $_SERVER variable

if ($path['call'] == basename($_SERVER['PHP_SELF'])) {
$path['call'] = '';
}

We split the call into it's pieces for easy access:
$path['call_parts'] = explode('/', $path['call']);
Now, it's time to deal with the later part, the parameter list. We urldecode it:
$path['query_utf8'] = urldecode($request_path[1]);

And utf8 decode it
$path['query'] = utf8_decode(urldecode($request_path[1]));

The parameters is separated by an ampersand character, so we explode it into parts:
$vars = explode('&', $path['query']);

Now, we loop through each of the parameters
foreach ($vars as $var) {

With every parameter, we split it at the equal sign separating the key from the value:
$t = explode('=', $var);

Then, we save it as a normal array variable
$path['query_vars'][$t[0]] = $t[1];

Closing the foreach
}
closing the if
}

and now, let's return the whole array to the caller of the function:
return $path;

And we close the function declaration:
}

Now, we try our code:, call the function and store the returned info into an variable:
$path_info = parse_path();

Then, format it to a good readable output with <pre> tags and the print_r() function for a nice looking output
echo '<pre>'.print_r($path_info, true).'</pre>';

So, if we would call the web side using the URL
http://localhost/user/matthew/edit?language=en&hobbies=art&sport=football


The output should be:
Array
(
[base] => /
[call_utf8] => user/matthew/edit
[call] => user/matthew/edit
[call_parts] => Array
	 (
		 [0] => user
		 [1] => matthew
		 [2] => edit
	 )
[query_utf8] => language=en&hobbies=art&sport=football
[query] => language=en&hobbies=art&sport=football
[query_vars] => Array
	 (
		 [language] => en
		 [hobbies] => art
		 [sport] => football
	 )
)

see, now, we can use the 'call_parts' and the 'query_vars' wherever we want in our script instead of the $_GET and additional parameters you might have had before which isn't needed now, as the cleaner url can has it's fixed positions of the values instead.


How can this be used in a bigger, working web page?

The first of the call_parts is probably something deciding which part of the web page the user are on. Probably the name of the main menu title.
The second part is probably the second level menu title.

Say, your main menu has titles like
  • About us
  • Users
  • News
  • Products
Then you can very easily decide that each of these menus has a corresponding path in the call:
  • /about-us
  • /users
  • /news
  • /products
With a pretty easy switch statement, you can steer the code into a different include file:

switch($path_info['call_parts'][0]) {
  case 'about-us': include 'about.php';
    break;
  case 'users': include 'users.php';
    break;
  case 'news': include 'news.php';
    break;
  case 'products': include 'products.php';
    break;
  default:
    include 'front.php';
}
So in each of the different areas , we deal with the later parts of the call, if there are any..

This is hard coded now, but you could easily do a database select from a table, looking up which include file corresponds to which path.

And in, for example, the users.php, you can look up the $path_info['call_parts'][1] in the database to find information about the username, or id, if it's an id, to be displayed later on.

Edited by Orjan, 30 January 2013 - 11:05 AM.
corrected indention

  • 6

I'm a System developer at Redpill Linpro mainly working with SugarCRM.
Please DO NOT send mail or PM to me with programming questions, post them in the appropriate forum instead, where I and others can answer you.


#2 Ryant

Ryant

    CC Lurker

  • New Member
  • Pip
  • 9 posts
  • Location:Naga City , Camarines Sur.
  • Programming Language:Objective-C, PHP
  • Learning:Objective-C, PHP

Posted 08 March 2013 - 04:26 PM

Fantastic! this is a great post. 

 

thanks mate.


Edited by Ryant, 08 March 2013 - 04:27 PM.

  • 0

#3 SugoiReborn

SugoiReborn

    CC Lurker

  • Just Joined
  • Pip
  • 1 posts

Posted 12 March 2013 - 06:59 AM

Wow, this is a post for whom I've been looking for a long time!

I mean, I was aware of this way of making "clean URLs" before, but this one is so detailed!

I'll be trying this for sure. Thank you!


  • 0

#4 VNFox

VNFox

    CC Devotee

  • Senior Member
  • PipPipPipPipPipPip
  • 648 posts
  • Programming Language:C#, PHP
  • Learning:Assembly

Posted 12 March 2013 - 12:21 PM

great ... thanks


  • 0

www.pickmike.com
I don't just develop software. I find solutions to your business needs.


#5 Mitchell

Mitchell

    CC Resident

  • Advanced Member
  • PipPipPipPip
  • 50 posts
  • Programming Language:C
  • Learning:C

Posted 08 April 2013 - 10:58 PM

Notice how much nicer the last one looks. Clean URLs are great for 6 reasons:

  1. They look prettier
  2. They are easier to remember
  3. They help you save filespace on pages which have many links
  4. They are easier to link to, both for you and for other webbies
  5. They help cut down on typos because there is less confusion about what exactly to write and type

And the really big reason as to why you should use clean URLS:

  1. They allow search engines to spider your site.

  • 0

#6 lokilust

lokilust

    CC Lurker

  • New Member
  • Pip
  • 8 posts

Posted 24 April 2013 - 10:34 PM

What is an URL and a Clean URL

Normally, a URL to a webpage could look something like this:

 

Hello,

 

I would love to do this. Is there a full tutorial on this or am i just not getting it ?


  • 0

#7 JasonKnight

JasonKnight

    CC Addict

  • Senior Member
  • PipPipPipPipPip
  • 312 posts
  • Location:Keene, NH
  • Programming Language:C, C++, JavaScript, Delphi/Object Pascal, Pascal, Assembly, Others

Posted 25 April 2013 - 11:55 AM

Its' often interesting to see how other people go about this. A couple observations:

Is it REALLY necessary to check if $_SERVER['REQUEST_URI'] is set? I've never seen or heard of an Apache server that didn't provide it... and since mod_rewrite is Apache specific...

You seem to be storing a lot of values in the array that... well, I'm not seeing any practical reason for.

Not sure why since this is a 'one index to rule them all' method why you'd put the parse_url in as a function - unless you were doing so to avoid polluting the global scope? Ok, I could see that.

When I'm doing this on my own sites, I generally do NOT want to let directory access drop-through; users shouldn't be blindly able to browse subdirectories that might have code in them. If I were to have subdirectories people could browse, I'd give them a .htaccess overriding it instead.

But that goes with my having a different philosophy on doing this, I prefer to whitelist. The .htaccess I use does this for it's rewriteRule:


.htaccess
RewriteEngine On
RewriteRule !\.(gif|jpg|png|css|js|html|ico|zip|rar|pdf|xml|mp4|mpg|flv|swf|mkv|ogg|avi|woff|svg|eot|ttf|jar)$ index.php
It whitelists files to allow normal access to, and sends EVERY other request to index.php

Lemme see... I'll dumb down my handler to something more generic... and document (ok, I may be over-documenting this):

index.php
<?php

function die404() {
	header('HTTP/1.1 404 Not Found');
	die('
		<h1>Unable to find requested file</h1>
		<p>
			You attempted to access '.htmlspecialchars($_SERVER['REQUEST_URI']).'
			Which does not exist on this server.
		</p><p>
			Please access the <a href="/">main page of this site</a> instead.
		</p>
	');
}

/*
	replace array indexes:
	1) fix windows slashes
	2) strip up-tree ../ as possible hack attempts
*/
$URL = str_replace(
	array( '\\', '../' ),
	array( '/',  '' ),
	$_SERVER['REQUEST_URI']
);

if ($offset = strpos($URL,'?')) {
	// strip getData
	$URL = substr($URL,0,$offset);
} else if ($offset = strpos($URL,'#')) {
	/*
		Since hashes are after getData, you only need
		to strip hashes when there is no getData
	*/
	$URL = substr($URL,0,$offset);
}

/*
	the path routes below aren't just handy for stripping out
	the REQUEST_URI and looking to see if this is an attempt at
	direct file access, they're also useful for moving uploads,
	creating absolute URI's if needed, etc, etc
*/
$chop = -strlen(basename($_SERVER['SCRIPT_NAME']));
define('DOC_ROOT',substr($_SERVER['SCRIPT_FILENAME'],0,$chop));
define('URL_ROOT',substr($_SERVER['SCRIPT_NAME'],0,$chop));

// strip off the URL root from REQUEST_URI
if (URL_ROOT != '/') $URL=substr($URL,strlen(URL_ROOT));

// strip off excess slashes
$URL = trim($URL,'/');

// 404 if trying to call a real file
if (
	file_exists(DOC_ROOT.'/'.$URL) &&
	($_SERVER['SCRIPT_FILENAME'] != DOC_ROOT.$URL) &&
	 ($URL != '') &&
	 ($URL != 'index.php')
) die404();

/*
	If $url is empty of default value, set action to 'default'
	otherwise, explode $URL into an array
*/
$ACTION = (
	($URL == '') ||
	($URL == 'index.php') ||
	($URL == 'index.html')
) ? array('default') : explode('/',html_entity_decode($URL));

/*
	I strip out non word characters from $ACTION[0] as the include
	which makes sure no other oddball attempts at directory
	manipulation can be done. This means your include's basename
	can only contain a..z, A..Z, 0..9 and underscore!
	
	for example, as root this would make:
	pages/default.php
*/
$includeFile = 'pages/'.preg_replace('/[^\w]/','',$ACTION[0]).'.php';

if (is_file($includeFile)) {

	include($includeFile);
	
} else die404();
Same general idea, I just parse it differently. Also I like to have a proper 404 handler in place; you'll notice it's lying about the file being 404 in cases where the file may exist, we just want it hidden. No reason to 403/Forbidden or other responses since that would tell the user on the other end the file does exist -- better not to reveal details.

Make a directory called 'pages', make files in there like 'default.php' for the home page, 'contact.php' for the contact page... and in the global scope the $ACTIONS array contains the various bits and pieces of the request. For example if you had a test.php and accessed it as /test/best/west a print_r of the $ACTIONS array would be:
 
Array
(
    [0] => test
    [1] => best
    [2] => west
)
1
I'll put together a quick working example and toss it up on my site with a .rar of it. It's often easier to grasp when you have a complete working example in front of you.

-- edit -- updated code to match current copy at http://www.cutcodedo...ls/friendlyURL/

Edited by JasonKnight, 25 April 2013 - 09:35 PM.

  • 2
The only thing about Dreamweaver that can be considered professional grade tools are the people promoting it's use.

#8 lokilust

lokilust

    CC Lurker

  • New Member
  • Pip
  • 8 posts

Posted 25 April 2013 - 06:15 PM

Its' often interesting to see how other people go about this. A couple observations:

 

Thank you and can't wait for your tutorial.

:thumbup:


  • 0

#9 JasonKnight

JasonKnight

    CC Addict

  • Senior Member
  • PipPipPipPipPip
  • 312 posts
  • Location:Keene, NH
  • Programming Language:C, C++, JavaScript, Delphi/Object Pascal, Pascal, Assembly, Others

Posted 25 April 2013 - 09:12 PM

Ok, tossed up a live demo here:
http://www.cutcodedo...als/friendlyURL

A browsable source here:
http://www.cutcodedo.../viewableSource

A download of the demo in a nice neat .rar here:
http://www.cutcodedo...friendlyURL.rar

... and the documentation/explanation is online here:
http://www.cutcodedo...yURL/splainLucy

Which hopefully explains well enough how to go about it "my way". It does tack on a few extras like a bit of how I handle templates, mostly just to make the example 'presentable'.

Any questions, fire away. I tried to document as best I could to make it easier to understand just how it works. I also changed things up a bit from my post above, like moving the ROOT directory values into DEFINEs so they're easier to use. URL_ROOT being the important one since without that you'll find it VERY hard to make SRC or HREF attributes work properly since, well... we're passing data as directory names.

Another possibility would be to pass URL_ROOT in a BASE tag in the head... which might be a simpler approach. I'll have to play with that. If it works out I'll change the copy on the site accordingly. Praise be that CSS' url() values are relative to the CSS file's location.

Edited by JasonKnight, 25 April 2013 - 09:15 PM.

  • 1
The only thing about Dreamweaver that can be considered professional grade tools are the people promoting it's use.

#10 lokilust

lokilust

    CC Lurker

  • New Member
  • Pip
  • 8 posts

Posted 29 April 2013 - 01:45 AM

Thank you so much Sir :thumbup1:

That did it for me :thumbup:


  • 0

#11 Orjan

Orjan

    CC Mentor

  • Moderator
  • 2,918 posts
  • Location:Karlstad, Sweden
  • Programming Language:C, Java, C++, C#, PHP, JavaScript, Pascal
  • Learning:Java, C#

Posted 30 April 2013 - 02:06 PM

Its' often interesting to see how other people go about this. A couple observations:

Is it REALLY necessary to check if $_SERVER['REQUEST_URI'] is set? I've never seen or heard of an Apache server that didn't provide it... and since mod_rewrite is Apache specific...

 
Well, the mod rewrite is apache specific, but the code can be tried on other systems, and then it should handle the possibility for non existing variable. I don't think it's wrong to actually secure it a bit further. the code itself isn't so dependent that it is mod_rewrite running, you can have any other web server having anything else and the code could therefore be adapted to that server. With the newer php with all warnings enabled, you can't take any variables you haven't created yourself for granted.
 

You seem to be storing a lot of values in the array that... well, I'm not seeing any practical reason for.

 
Well, not everything is very useful, but to be a generic code, it's better to provide it all. And in some cases, you actually want to use some of the parts you call non useful, or whatever you call them., so why not.
 

Not sure why since this is a 'one index to rule them all' method why you'd put the parse_url in as a function - unless you were doing so to avoid polluting the global scope? Ok, I could see that.

 
Because this function (parse_path, not parse_url) could easily be put in a include file to be ran whenever you want to use it. And reuse it. It's easy to see where the code starts and where it ends. Easy to know which rows are important or just test rows. Also, this gives the most power to the coder, as this code don't determine specific variable names (or defines) to use. coder freedom to use the variables they want, and don't overwrites something that might been done before a call to the code.
 

When I'm doing this on my own sites, I generally do NOT want to let directory access drop-through; users shouldn't be blindly able to browse subdirectories that might have code in them. If I were to have subdirectories people could browse, I'd give them a .htaccess overriding it instead.

Well, as I said earlier, this is generic. there are pros and cons for everything. I can see usage to have access to directories, but you can do that in many ways. maybe you want to control the access via php instead of .htaccess, then this is the way to go.
 

But that goes with my having a different philosophy on doing this, I prefer to whitelist. The .htaccess I use does this for it's rewriteRule:


.htaccess

RewriteEngine On
RewriteRule !\.(gif|jpg|png|css|js|html|ico|zip|rar|pdf|xml|mp4|mpg|flv|swf|mkv|ogg|avi|woff|svg|eot|ttf|jar)$ index.php
It whitelists files to allow normal access to, and sends EVERY other request to index.php

Ok, so if I want to allow another direct access, I need to hard code it into my .htaccess. I see. User friendly? Not. But that's my philosophy. I want to be able to make a easily editable setting for this depending on what system I'm creating, nondependent of the framework.
 

Lemme see... I'll dumb down my handler to something more generic... and document (ok, I may be over-documenting this):

[...]
Same general idea, I just parse it differently. Also I like to have a proper 404 handler in place; you'll notice it's lying about the file being 404 in cases where the file may exist, we just want it hidden. No reason to 403/Forbidden or other responses since that would tell the user on the other end the file does exist -- better not to reveal details.

Yeah, you skip taking any regards to characters in any other language than english in your parsing, but of course everyone uses only pure english, or? I try to make my code as generic as possible. And yes, why not have a 404 check. but that's not what my tutorial is about. That can be added on after the call to the well separated and defined function call. Maybe from another library. 

Also, your code don't parse any GET data variables sent to the page. Even if you make a clean url, you should still be able to use GET variables if you really want to.
 

Make a directory called 'pages', make files in there like 'default.php' for the home page, 'contact.php' for the contact page... and in the global scope the $ACTIONS array contains the various bits and pieces of the request. For example if you had a test.php and accessed it as /test/best/west a print_r of the $ACTIONS array would be:

That's your preferences. Maybe some others want other preferences. I don't want to be determinant to how others should use my code. I give them an array to use and don't clutter any global space at all.
 

Array
(
    [0] => test
    [1] => best
    [2] => west
)
1
I'll put together a quick working example and toss it up on my site with a .rar of it. It's often easier to grasp when you have a complete working example in front of you.

 
yeah, sorry for not providing the files, I think it is easy enough to do this manually as it never uses more than two files, and, I don't make people overwrite their already existing .htaccess with mine.
 

-- edit -- updated code to match current copy at http://www.cutcodedo...ls/friendlyURL/

And mine is accessible directly on the screen, right in my tutorial. Which way is better, my way or your way? I can't tell as the code you serve in the isn't doing the same things my code is doing.

Hello,
 
I would love to do this. Is there a full tutorial on this or am i just not getting it ?

 

Did you read the full post? Which parts is hard to understand?


Edited by Orjan, 30 April 2013 - 02:03 PM.

  • 0

I'm a System developer at Redpill Linpro mainly working with SugarCRM.
Please DO NOT send mail or PM to me with programming questions, post them in the appropriate forum instead, where I and others can answer you.


#12 JasonKnight

JasonKnight

    CC Addict

  • Senior Member
  • PipPipPipPipPip
  • 312 posts
  • Location:Keene, NH
  • Programming Language:C, C++, JavaScript, Delphi/Object Pascal, Pascal, Assembly, Others

Posted 30 April 2013 - 04:05 PM

Well, the mod rewrite is apache specific, but the code can be tried on other systems

Excepting that in those cases what you have for code wouldn't work, so why would you even TRY to deploy THIS code there?
 

With the newer php with all warnings enabled, you can't take any variables you haven't created yourself for granted.

Perhaps... but again since it would be non-functional and would need a rewrite for other systems of doing it, what's the point of adding that check to code that you wouldn't RUN on non-apache systems without a rewrite?
 

Because this function (parse_path, not parse_url) could easily be put in a include file to be ran whenever you want to use it. And reuse it. It's easy to see where the code starts and where it ends.

IMHO too complex for a tutorial version -- you're gonna confuse/lose people on that.
 

Well, as I said earlier, this is generic. there are pros and cons for everything. I can see usage to have access to directories, but you can do that in many ways. maybe you want to control the access via php instead of .htaccess, then this is the way to go.

I think that loose/generic is where you lose people -- it's a lesson I learned the hard way back in the '90's writing tech manuals for Marstek. Assume the person learning knows nothing, fail to do that they'll learn nothing. "generic" code can be too case non-specific for the beginner to turn into a working example on their own -- which is where I think "lokilust" got lost. I'm pretty well... seasoned at this, and I'd have a hard time turning your tutorial into a working example!
 

Ok, so if I want to allow another direct access, I need to hard code it into my .htaccess. I see. User friendly? Not. But that's my philosophy. I want to be able to make a easily editable setting for this depending on what system I'm creating, nondependent of the framework.

Which is where we differ -- User friendly is good to a point, but not when it ends up leaving the barn door open. Is it REALLY so hard to whitelist allowed files? No, it isn't... anyone who can't manage that, probably has no business using these methods in the first place; and if that means "You have to be 'this' smart" to use it? OH WELL.
 

Yeah, you skip taking any regards to characters in any other language than english in your parsing, but of course everyone uses only pure english, or?

Not 100% sure what that statement has to do with the block it was quoting -- only thing I can figure is my safename routine -- and you're passing values in the URL, a subset of US-ASCII (characters 32..127) is all that's valid there in the first place, you want other language characters you'd have to have them as entities ANYWAYS! Wait? Are you referring to getData, something mine doesn't need to parse? Yeah, your next part:
 

Also, your code don't parse any GET data variables sent to the page. Even if you make a clean url, you should still be able to use GET variables if you really want to.

Don't have to with mine as $_GET is parsed normally regardless of how my redirect handles it. You send mine getdata, $_GET exists and is filled in properly. That's why I strip it clear off before parsing $_SERVER['REQUEST_URI'] as we don't need it!

You do /test/west?best=vest on mine, and $_GET['best'] will return 'vest', because of how my .htaccess method is crafted.

It might be cute to store the HASH if present though -- since you ARE correct there, more datapoints is a good thing... It's just yours seemed to be reinventing the wheel on a lot of things.

-- split -- too many quotes error? REALLY?

Having to switch to italics because of some stupid "too many quotes on merge" error in this forum software.
 

That's your preferences. Maybe some others want other preferences. I don't want to be determinant to how others should use my code. I give them an array to use and don't clutter any global space at all.

Well, that's not REALLY how I'd do it -- I'd have a singleton with getters, but that's a bit complicated for demo code for beginners.
 

yeah, sorry for not providing the files, I think it is easy enough to do this manually as it never uses more than two files, and, I don't make people overwrite their already existing .htaccess with mine.

Thing is this is a append in any case, might as well have a working demo they can integrate or work from -- Though IMHO (YMMV) this technique is too specific in function to be used as anything BUT the core of a system. Trying to mix and match or integrate it to existing code is just asking for it to be bloated, broken and insecure... Again though, YMMV. My experience says otherwise.
 

And mine is accessible directly on the screen, right in my tutorial. Which way is better, my way or your way? I can't tell as the code you serve in the isn't doing the same things my code is doing.

Which given the illegible colors, narrow little stripes, broken wordwraps of posting code on a forum, much less breaking up the code so you can't follow the logic or indents, it's HARDER to work from in my experience. That's why in addition to the .rar download there's the viewable source directory full of phps files:
http://www.cutcodedo...viewableSource/

with HEAVILY documenteds source:
http://www.cutcodedo...urce/index.phps
 

Did you read the full post? Which parts is hard to understand?

I could see how lokilush could have had issues -- A lot of what you are doing over-complicates it -- I know how to do this, and I had trouble making sense of yours. It's... very different from what I'm used to seeing, especially all that futzing around with UTF-8 encode/decode and getData parsing; something my technique doesn't even need to bother with since $_GET is preserved/working... I didn't even figure out that's what you were doing until you mentioned it separately!

It is a good point about it polluting the global namespace though -- Was thinking it might make sense to put what I have as the $ACTION array into $_GET (you can add values to $_GET), or as you did wrap it in a function, but that's the sort of thing I'd expect people to be able to figure out on their own... again real world I'd have it in a singleton with getters, the only setter being the constructor -- so that if it's called more than once it only runs the parsing code once; but I wouldn't put that in THIS tutorial except as a 'lesson 2'... which might not be a bad idea.

I think that's a lot of it, we have different expectations of what people are able to figure out on their own. Comprehension varies from person to person, which is why it helps to have different views and approaches. Yours would work for some, mine others. Really there's room for both.
  • 0
The only thing about Dreamweaver that can be considered professional grade tools are the people promoting it's use.





Powered by binpress