Hi guys I'm setting up mywebapplication to give unique urls for users such as uniquename.mysite.com, anotheuniqname.mysite.com etc.
I want to be able to in a php script grab the subdomain part of the url. Would be nice if I can get it as a GET variable - I think it can be done with htaccess. Any ideas?
$subdomain = substr($_SERVER['HTTP_HOST'], 0, strpos($_SERVER['HTTP_HOST'], '.'));
To make sure there's a valid subdomain:
$urlExplode = explode('.', $_SERVER['HTTP_HOST']);
if (count($urlExplode) > 2 && $urlExplode[0] !== 'www') {
$subdomain = $urlExplode[0];
}
else {
// treat as www.mysite.com or mysite.com
}
I would try this (at the beginning of your PHP code):
$_GET['subdomain'] = substr($_SERVER['SERVER_NAME'], 0, strrpos($_SERVER['SERVER_NAME'], '.'));
Explanation: strrpos find the last occurance of '.' in the accessed domain, substr then returns the string up to this position. I assigned the return value to a $_GET var so you can use it as if it were a normal URL-parameter.
Put this in your bootstrap file:
$tmp = explode(".", $_SERVER["HTTP_HOST"], 2);
$_GET["subdomain"] = $tmp[0];
Ali - don't you mean a $_SERVER variable as $_GET would be related to the querystring ??
if so, then you could try:
$_SERVER['HTTP_HOST']
jim
[edit] - see http://roshanbh.com.np/2008/05/useful-server-variables-php.html for a few examples that may help
Do you want something along the lines of:
RewriteEngine On
RewriteCond %{HTTP_HOST} ^[a-z0-9-]+\.yoursite\.com$
RewriteRule !^index\.php$ index.php [L]
you could then get the subdomain using
<?php
preg_match('/^http:\/\/([a-z0-9-]+)\.yoursite.com$', $_SERVER['HTTP_HOST'], $matches);
$_GET['username'] = $matches[1];
?>
If you really want to use mod_rewrite in your .htaccess file, you could do something like this (assuming your script is index.php in this example):
RewriteEngine On
# Prevent people from going to to index.php directly and spoofing the
# subdomain value, since this may not be a desirable action
RewriteCond %{THE_REQUEST} ^[A-Z]+\sindex\.php.*(\?|&)subdomain=
RewriteRule ^.*$ http://%{HTTP_HOST}/ [R=301,L]
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{HTTP_HOST} !^www
RewriteCond %{HTTP_HOST} ^([^\.]+)\.([^\.]+)\.([^\.]+)$
RewriteRule ^.*$ index.php?subdomain=%1
This little function will simply get your " www.website.com " or in your case " subdomain.website.com ", and then split it up in 3 parts ( 0=>"www", 1=>"website", 2=>"com" ), and then return value 1, which is either " www " or your subdomain name.
function isSubdomain()
{
$host = $_SERVER['HTTP_HOST'];
$host = explode('.',$host);
$host = (is_array($host)?$host[0]:$host);
return $host;
}
Exaple: If your website is " admin.website.com ", you will receive "admin".
Related
I am trying to achieve automatic subdomain creation. I have read a lot of tutorials including:
THIS
THIS
THIS
I understood the concept and I implemented it with success in the past for user profiles, but this is a different case and I am stuck.
What I want to do, is basically something like pen.io as functionality. A user creates a page with a password and then, that page name converts into a subdomain.
I thought of doing a function that runs on the index page of the main website and that one used afterwards in HTACCESS to have something like index.php?subdomain=test and that one to redirect to test.domain.tld
EDIT:
Here is the current implementation that works when clicking on a link, but it doesn't work when accessing the url directly from the browser:
Code used in view.php:
<?php
include('inc/config.php');
$url = filter_var($_GET['url'], FILTER_SANITIZE_STRING);
$conn = new mysqli($server, $username, $password, $database) or die ('Unable to execute query. '. mysqli_error($conn));
$query = "SELECT * FROM `pages` WHERE pageTitle = '$url'";
$result = $conn->query($query);
if($row = mysqli_fetch_array($result))
{
$title = $row['pageEditableTitle'];
$content = $row['pageContent'];
echo '<h5 class="mt-5"><mark>'.$title.'</mark></h5>
<p class="lead display-7">'.$content.'</p>';
} else {
echo '<br /><div class="alert alert-info" role="alert">Subdomain does not exist.</div>';
}
$conn->close();
?>
Code used in htaccess:
RewriteCond %{HTTP_HOST} ^(.*)\.domain\.tld
RewriteRule ^(.*)$ https://domain.tld/view.php?url=%1 [L,NC,QSA]
But this redirects www.domain.tld to domain.tld/view.php?url=www and not staying as www.domain.tld in the browser url
I presuppose that you setup a wildcard dns entry (access random.domain.tld to test it!). Then you have two options:
Correct your rewrite rules
Something like [aA-zZ] should be [a-zA-Z] and the RewriteRule should be only after the RewriteCond and not in front of it and two of them. And do you really want to force a - inside the subdomain with ([a-z0-9][-a-z0-9]+)? Maybe you should check this answer. Note: The www inside of your domain is a subdomain as well. So it would rewrite to sub.php?url=www
With the corrected rewriting random.domain.tld returns the content of random.domain.tld/sub.php?url=random. But at the moment your sub.php does not return content. Instead it returns a http redirect to the URL random.domain.tld. This means your sub.php produces an infinite loop on itself. Instead sub.php should only contain something like <?php echo $_SERVER['HTTP_HOST']; ?>.
Maybe you did not understand how URL rewriting works. Then read this answer for further explanation.
Update1
You corrected your code as follows:
RewriteCond %{HTTP_HOST} ^([a-zA-Z0-9]+)\.domain\.tld\.?(:80)?$ [NC]
RewriteRule ([a-zA-Z0-9]+) /view.php?url=$1
But it's still wrong. As I said you need to read and understand this answer. #JoachimIsaksson uses $1 and %1 in his 2nd example:
RewriteEngine on
RewriteCond %{HTTP_HOST} ^(.*)\.example\.com
RewriteRule ^(.*)$ /subdomains/%1/$1 [L,NC,QSA]
%1 is the subdomain catched through RewriteCond %{HTTP_HOST} ^(.*)\.domain\.com. And $1 is the path catched through RewriteRule ^(.*)$. You missed to use %1.
But your code can not work as you forced an unempty alphanummeric string by RewriteRule ([a-zA-Z0-9]+). But a path could contain more than that. For example a slash or question mark. And of course it could be empty as well.
And why did you add (:80)?? Do you think someone will access your domain with a specific port?
And why the last optional dot in tld\.??
At last you need to bring the flags into question. You used the NC flag. It means your rule is case-insensitive. So why do you use [a-zA-Z0-9]? As your rule is already case-insensitive it can be [a-z0-9]. And why don't you used the L and QSA flag? They are important.
Update2
Try this:
RewriteEngine on
RewriteCond %{HTTP_HOST} ^(.*)\.domain\.tld
RewriteRule .* view.php?url=%1 [L,NC,QSA]
Use PHP only
$_SERVER['HTTP_HOST'] contains your full domain. This answer explains how to extract the subdomain name:
$subdomain = array_shift((explode('.', $_SERVER['HTTP_HOST'])));
Now you are able to use your general index.php to switch between your general page or the users subdomain content:
$domain_parts = explode('.', $_SERVER['HTTP_HOST']);
// access without any subdomain (TLDs like "co.uk" would "need == 4")
if (count(domain_parts) == 3) {
$subdomain = "www";
}
else {
$subdomain = array_shift($domain_parts);
}
if ($subdomain == 'www') {
// general page
}
else {
// users page
}
i followed up multiple tutorials how to make pretty URL but never actualy make it work (prolly i didnt get something).
What i want:
From something like this:
http://www.example.com/api/v1/get.php?user=UserName&id=7Ka2la2
I want to make something like this:
http://www.example.com/UserName/get/7Ka2la2
What i did try:
As I mentioned I try to follow multiple tutorials but nothing worked for me. So i try something by my self.
//.htaccess
<IfModule mod_rewrite.c>
RewriteEngine on
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule ^ index.php [L]
</IfModule>
What it does:
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
And in my index.php file it looks like this
<?php
function parse_path() {
$path = array();
if (isset($_SERVER['REQUEST_URI'])) {
$path = explode('/', $_SERVER['REQUEST_URI']);
}
return $path;
}
$path_info = parse_path();
echo '<pre>'.print_r($path_info, true).'</pre>';
switch($path_info[1]) {
case 'get': include 'get.php';
break;
default:
include '404.php';
}
So it basicly should just split url to array and then base on URL include right file (in this example its get.php). However like this i can load a file but i have nothing in my $_GET and $_POST which make my script useless for me.
Question:
My code will somehow do what i want so base on url it load content but $_GET and $_POST will not work correctly here. So my question is did I make it wrong way? If yea how should looks the right one and if not how I can access $_GET and $_POST variabiles
You can set$_GET yourself. $_POST is unaffected by the rewrite.
Try this if you like:
<?php
function parse_path() {
$path = array();
if (isset($_SERVER['REQUEST_URI'])) {
$path = explode('/', $_SERVER['REQUEST_URI']);
}
return $path;
}
$path_info = parse_path();
echo '<pre>'.print_r($path_info, true).'</pre>';
// SET UP $_GET HERE
$_GET['user'] = $path_info[0];
$_GET['id'] = $path_info[2];
switch($path_info[1]) {
case 'get': include 'get.php';
break;
default:
include '404.php';
}
But if you can still modify the code that looks for $_GET you might want to consider not using $_GET like this, and rather set up some sort of class that contains the values.
And you also might want to consider doing your url rewriting so as to map the original request to something that has get variables.
eg
//.htaccess
<IfModule mod_rewrite.c>
RewriteEngine on
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule ^(.+)/(.+)/(.+)$ /api/v1/$2.php?user=$1&id=$3 [L]
</IfModule>
I've just realized my host URL are case-sensitive.
It means that /homepage, /Homepage and /homePage are different URLs, which is problematic.
I could force any URL to be lower-case and it would fix my problem but this is not exactly what I'm looking for.
I would like to know if I can redirect any variant of /homepage (ie:/hOMEpaGe,/HOMEPAGE,/hOmEpAgE,...) to /homePage (Note the case-sensivity)
I don't know if I'd better handle it with the server configuration or into the php file by manipulating the $_SERVER[REQUEST_URI].
Thank you for any idea on this !
Sure it might be possible to do a redirect on the Bootstrap file (index.php for example) with the combination of strtolower, stristr(), str_replace() and header() Functions like so:
<?php
// ASSUMING THE BASE URI IS KNOWN
$baseURI = "http://www.my-domain.com";
// CONVERT ALL CHARACTERS IN THE $_SERVER['REQUEST_URI'] TO LOWER-CASES
$uri = strtolower($_SERVER['REQUEST_URI']);
$rdURI = str_replace("homepage", "homePage", $uri);
// USE EITHER A SWITCH OR IF CONDITIONAL LOGIC TO SET THE URI
if(stristr($uri, "homepage")){ // REDIRECT ANY THING WITH HOMEPAGE TO: homePage
$rdURI = str_replace("homepage", "homePage", $uri);
}else if(stristr($uri, "another-uri-1")){
$rdURI = str_replace("another-uri-1", "another-URI-1", $uri);
}else if(stristr($uri, "another-uri-2")){
$rdURI = str_replace("another-uri-2", "another-URI-2", $uri);
}else if(stristr($uri, "yet-another-uri")){
$rdURI = str_replace("yet-another-uri", "yet-Another-URI", $uri);
}else{
// DEFAULT TO THE HOMEPAGE IF ALL ELSE FAIL
// THIS DECISION IS UP TO YOU AS YOU MIGHT NOT NEED IT TO WORK THIS WAY...
$rdURI = str_replace("homepage", "homePage", $uri);
}
// REDIRECT TO THE NEW URI...
header("location: " . $rdURI);
exit;
// OR REDIRECT TO THE NEW URI WITH BASE URI...
header("location: " . $baseURI . DIRECTORY_SEPARATOR . $rdURI);
exit;
It is always a better idea to handle this on a lower level than having redirects in PHP.
If order to achieve that, first you need to declare a RewriteMap
# Add RewriteMap for redirecting to lowercase URIs
<IfModule mod_rewrite.c>
RewriteMap lc int:tolower
</IfModule>
Then just create the RewriteRule to redirect uppercase URLs to lowercase ones.
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteCond %{REQUEST_URI} [A-Z]
RewriteRule ^(.*)$ ${lc:$1} [R=301,L]
Use .htaccess [NC] for case insensitive:
RewriteCond %{REQUEST_URI} /phpMyAdmin [NC]
lmgtfy: https://perishablepress.com/case-insensitive-redirectmatch/
My .htaccess is as follows:
Options +FollowSymLinks
RewriteEngine On
RewriteCond %{REQUEST_FILENAME} !-d
RewriteCond %{REQUEST_FILENAME} !-f
RewriteRule ^(.*)$ ./backend-scripts/url_parser.php
and then, handling the url redirect is the file url_parser.php which is as follows.
<?php
// open file and get its contents in a string format.
$string = file_get_contents("../json/site_map.json");
// decode the json string into an associative array.
$jsonArray = json_decode($string, TRUE);
// add trailing slash to URI if its not there.
$requestURI = $_SERVER['REQUEST_URI'];
$requestURI .= $requestURI[ strlen($requestURI) - 1 ] == "/" ? "" : "/";
// split up the URL at slashes.
$uriArray = explode('/', $requestURI);
// select the last piece of exploded array as key.
$uriKey = $uriArray[count($uriArray)-2];
// lookup the key in sitemap
// retrieve the absolute file URL.
$absPath = $jsonArray[$uriKey];
// reformulate the URL.
$path = "../$absPath";
// include the actual page.
include($path);
?>
in order to test my php code, I replaced
$requestURI = $_SERVER['REQUEST_URI'];
by the following:
$requestURI = "/welcome";
and it worked perfectly. So I'm pretty sure that there is something wrong inside my .htaccess file. How can I change that?
Change:
RewriteRule ^(.*)$ ./backend-scripts/url_parser.php
to
RewriteRule ^(.*)$ ./backend-scripts/url_parser.php?url=$1
Then change $requestURI = $_SERVER['REQUEST_URI']; to:
$requestURI = (!empty($_GET['url']))
? $_GET['url']
: ''; // no url supplied
WARNING: Do not pass user supplied values to include(). Make sure the paths are checked against a proper whitelist, otherwise a malicious user can hijack your server.
I have set up my domain to point all wildcard subdomains to my webserver. What I would like to do is to perform a rewrite url based on the value that I receive on the wildcardsubdomain.
This is a specific scenario which I am not sure how to over come.
username.mydomain.com to rewrite to mydomain.com/user.php?userid=username
&
groupname.mydomain.com to rewrite to mydomain.com/group.php?groupid=groupname
I am storing on my db on a table the types as below.
john->userid
technology->groupid
steve->userid
Macleen->userid
Sports->groupid
Would this be helpful to acheive this programatically? How can I acheive this using rewriteURL?
And I would also like to keep the URL's of the page as is till the
user navigates to another page from either user.php or group.php
Try the following:
RewriteCond %{HTTP_HOST} !^www\.mydomain\.com$ [NC]
RewriteCond %{HTTP_HOST} !^mydomain\.com$ [NC]
RewriteCond %{HTTP_HOST} ^([^\.]+)\.mydomain\.com$ [NC]
RewriteRule ^$ file.php?id=%1 [L]
You could then place some sort of id check in file.php to find out if it's a username or groupname, would only work if you had unique ids for both combined though as there's no way to seperate random.mydomain.com from random.mydomain.com.
You could then use javscript to format the url:
history.pushState({path: "url"}, "", "http://random.mydomain.com/user");
index.php :
<?php
if(preg_match('/([a-z]+).mydomain.com/i', $_SERVER['SERVER_NAME'], $matches)){
$subdomain = $matches[1];
if(YourModel::isGroupName($subdomain)){
$_GET['groupid'] = $subdomain;
require './group.php';
} else {
$_GET['userid'] = $subdomain;
require './user.php';
}
}