Username as subdomain on laravel - php

I've set up a wildcard subdomain *.domain.com & i'm using the following .htaccess:
Options +FollowSymLinks
RewriteEngine On
RewriteBase /
RewriteCond %{HTTP_HOST} !www\.
RewriteCond %{HTTP_HOST} (.*)\.domain\.com
RewriteRule .* index.php?username=%1 [L]
Everything works perfectly.
I want to implement this method in laravel. Mainly I want to have my user's profile displayed when you go to username.domain.com. Any ideas on achieving this?

This is easy. Firstly - do NOT change the .htaccess file from the default provided by Laravel. By default all requests to your domain will be routed to your index.php file which is exactly what we want.
Then in your routes.php file just use a 'before' filter, which filters all requests to your application before anything else is done.
Route::filter('before', function()
{
// Check if we asked for a user
$server = explode('.', Request::server('HTTP_HOST'));
if (count($server) == 3)
{
// We have 3 parts of the domain - therefore a subdomain was requested
// i.e. user.domain.com
// Check if user is valid and has access - i.e. is logged in
if (Auth::user()->username === $server[0])
{
// User is logged in, and has access to this subdomain
// DO WHATEVER YOU WANT HERE WITH THE USER PROFILE
echo "your username is ".$server[0];
}
else
{
// Username is invalid, or user does not have access to this subdomain
// SHOW ERROR OR WHATEVER YOU WANT
echo "error - you do not have access to here";
}
}
else
{
// Only 2 parts of domain was requested - therefore no subdomain was requested
// i.e. domain.com
// Do nothing here - will just route normally - but you could put logic here if you want
}
});
edit: if you have a country extension (i.e. domain.com.au or domain.com.eu) then you will want to change the count($server) to check for 4, not 3

Laravel 4 has this functionality out of the box:
Route::group(array('domain' => '{account}.myapp.com'), function() {
Route::get('user/{id}', function($account, $id) {
// ...
});
});
Source

While I can't say what the full solution would be in your case, I would start with the SERVER_NAME value from the request (PHP: $_SERVER['SERVER_NAME']) such as:
$username = str_replace('.domain.com', '', Request::server('SERVER_NAME'));
Make sure you additionally clean/sanitize the username, and from there you can lookup the user from the username. Something like:
$user = User::where('username', '=', $username)->first();
Somewhere in the routes file you could conditionally define a route if the SERVER_NAME isn't www.domain.com, or domain.com, though I'm sure others can come up with a much more eloquent way for this part...

ability add subdomains like subdomain *. domain.com should be switched by your hosting provider, in the .htaccess you can not configure support of subdomains

Related

How to redirect // in Laravel 5.7?

Older version of laravel here, 5.7. I have a situation where I have a url like this http://127.0.0.1:8000//
I have a catch all of this
Route::get('{uri}', ['uses'=>'PageController#render'])->where('uri', '(.*)');
The URL that comes into the render method is ''.
I'm not quite sure the best way to take http://127.0.0.1:8000// and redirect that to http://127.0.0.1:8000.
.htaccess doesn't seem to let me redirect that either with
Redirect 301 // / or RewriteRule ^$ /? [L,R=301]
Is there any way to get around this?
thanks!
They are treated as the same resource in the browser. Anyway you can check the request URI on the server and redirect to the root path like this:
Route::get('/', function () {
// check the request URI
if($_SERVER['REQUEST_URI'] !== '/')
{
return redirect('/');
}
# The rest of the code
# ...
});

How to point a domain to a WordPress page?

I have a WordPress page with this structure http://mywebsite.com/page
I want my http://otherdomain.com to point to http://mywebsite.com/page but the user should see the http://otherdomain.com domain at his browser? The A record in my DNS points http://otherdomain.com and http://mywebsite.com to the same IP.
How to achieve this goal? I though about VirtualHosts but since the folder /page doesn't really exist in the server but is created dynamically by WordPress via .htaccess
How can I point my domain to the WordPress page?
After Roel answer I edited my htaccess.conf file at the WordPress Bitnami installation to add this:
RewriteEngine on
RewriteCond %{HTTP_HOST} ^otherdomain\.com.br$
RewriteRule (.*) http://www.otherdomain.com.br/$1 [R=301,L]
RewriteRule ^$ http://mywebsite.com.br/page/ [L,R=301]
The code is being called, because it adds the www to the main URL, but it's not working, because it displays contents from mywebsite.com.br and not from mywebsite.com.br/page.
I tried another code which is
RewriteEngine on
RewriteCond %{HTTP_HOST} otherdomain\.com.br [NC]
RewriteCond %{REQUEST_URI} ^/$
RewriteRule ^(.*)$ http://mywebsite.com.br/page/$1 [L]
In this case, it display the contents from http://mywebsite.com.br/pagehowever it changes my URL http://mywebsite.com.br/page as well which is not what I'm looking for, since I want to keep the user's browser at http://otherdomain.com.br
All SEO and duplicate content issues aside:
WordPress is aware of the domain it is supposed to be answering to in the database. The WordPress site itself will also redirect based on the domain name set in the WordPress dashboard (under "Settings" => "General").
This isn't going to work well using htaccess. You're actually going to want the domain name http://otherdomain.com to point to the server where mywebsite.com lives (not using a forward, but modifying the A record in your DNS). The reason is that when you rewrite the domain name, the WordPress site is also going to look for css and js files at that domain (looking for them at otherdomain.com). If you have the domain pointed to the WordPress server, this will work properly.
In order to cause WordPress to allow "answering" to multiple domains, you need to modify the code in your WordPress installation so that it will not rewrite the url to http://mywebsite.com. To do this, add the below PHP code to your WordPress theme's function.php file:
What you need to do is to add filter(s) to the relevant hooks that return the site URL, so you can modify it as you see fit:
// This will allow you to modify the site url that is stored in the db when it is requested by WP
add_filter('option_siteurl', 'my_custom_filter_siteurl', 1);
// This will allow you to modify the home page url that is stored in the db when it is requested by WP
add_filter('option_home', 'my_custom_filter_home', 1);
// Modify the site url that WP gets from the database if appropriate
function my_custom_filter_siteurl( $url_from_settings ) {
// Call our function to find out if this is a legit domain or not
$current_domain = my_custom_is_domain_valid();
// If so, use it
if ( $current_domain ) {
return "http://{$current_domain}";
// Otherwise, use the default url from settings
} else {
return $url_from_settings;
}
}
// Modify the home page url that WP gets from the database if appropriate
function my_custom_filter_home( $home_from_settings ) {
// Call our function to find out if this is a legit domain or not
$current_domain = my_custom_is_domain_valid();
// If so, use it
if ( $current_domain ) {
$base_url = "http://{$current_domain}";
// Modify / remove this as appropriate. Could be simply return $base_url;
return $base_url . "/home-page";
// Otherwise, use the default url from settings
} else {
return $home_from_settings;
}
}
// Utility function to determine URL and whether valid or not
function my_custom_is_domain_valid() {
// Create a whitelist of valid domains you want to answer to
$valid = array(
'otherdomain.com',
'mywebsite.com.br',
);
// Get the current domain name
$current_server = $_SERVER['SERVER_NAME'];
// If it's a whitelisted domain, return the domain
if ( in_array( $current_server, $valid ) ) {
return $current_server;
}
// Otherwise return false so we can use the default set in the DB
return FALSE;
}
Adding the following filters and functions will cause the desired page to appear as the home page, without the /page in the URL:
// This will allow you to modify if a page should be shown on the home page
add_filter('option_show_on_front', 'my_custom_show_on_front');
// This will allow you to modify WHICH page should be shown on the home page
add_filter('option_page_on_front', 'my_custom_page_on_front');
// Modify if a page should be shown on the home page
function my_custom_show_on_front( $default_value ) {
// We only want to do this on specific domain
$is_other_domain = my_custom_is_other_domain();
// Ensure it's the domain we want to show the specific page for
if ( $is_other_domain ) {
return 'page';
// Otherwise, use the default setting
} else {
return $default_value;
}
}
// Modify WHICH should be shown on the home page
function my_custom_page_on_front( $default_value ) {
// We only want to do this on specific domain
$is_other_domain = my_custom_is_other_domain();
// Ensure it's the domain we want to show the specific page for
if ( $is_other_domain ) {
// If it's the proper domain, set a specific page to show
// Alter the number below to be the ID of the page you want to show
return 5;
} else {
// Otherwise, use the default setting
return $default_value;
}
}
// Utility function to easily determine if the current domain is the "other" domain
function my_custom_is_other_domain() {
$current_domain = my_custom_is_domain_valid();
return ($current_domain == 'otherdomain.com') ? $current_domain : FALSE;
}
You'll need to add rewrite rules.
RewriteEngine on
RewriteCond %{HTTP_HOST} ^otherdomain\.com$
RewriteRule (.*) http://www.otherdomain.com/$1 [R=301,L]
RewriteRule ^$ http://mywebsite.com/page [L,R=301]
You shouldn't be redirecting the user to mywebsite.com with [L,R=301], rather, you should use the P flag which allows you to ask mod_rewrite to act as a proxy for the domain otherdomain.com. something like this,
RewriteRule /(.*) http://mywebsite.com/page/$1 [P]
make sure to change the css files too to the following,
RewriteRule /css/(.*) http://mywebsite.com/css/$1 [P]
which will allow all your otherwebsite.com css to become mywebsite.com css and display as otherwebsite.com/css rather than mywebsite.com/page/css
but in order to do this, you need to have mod_proxy loaded and enabled. Do however note that this will reduce performance compared to using mod_proxy directly, as it doesn't handle persistent connections or connection pooling.
Try this regex. It may not work, but it will give you some idea on where to find the solution.
Basically you need to use an external redirect from otherdomain to mywebsite and then an internal redirect from mywebsite to otherdomain. But it may cause a loop so you need to use some condition to escape it.
RewriteEngine on
RewriteCond %{ENV:REDIRECT_FINISH} !^$
RewriteRule ^ - [L]
RewriteCond %{HTTP_HOST} ^otherdomain\.com.br$ [NC]
RewriteRule ^(.*)$ http://mywebsite.com.br/page/$1 [R,L]
RewriteRule ^.*$ http://otherdomain.com.br [E=FINISH:1]

Laravel route filter to specific url

I'm trying to apply route filter to a specific url. So, my file is under public directory:
/public/js/kcfinder/browse.php
My filter:
Route::filter('admin', function ()
{
if (!Sentry::check())
{
// if not logged in, redirect to login
return Redirect::to_route('admin_login');
}
elseif (!Sentry::user()->has_access('is_admin'))
{
//logout
Sentry::logout();
// has no access
return View::make('error.access_error');
}
});
Finally my pattern:
Route::filter('pattern: js/kcfinder/*', 'admin');
If I try to access
/public/js/kcfinder/browse.php
the rule does not work.
I can see whole contents of file.
If I try to acess
/public/js/kcfinder/blahblah.php
the filter works great. Because there is no file which named
blahblah.php
under the directory.
Any help would be really great!
That's because your .htaccess file says that if the request URI matches an existing file, then don't rewrite, just show/execute the file as it is.
So, you have two options:
You can create the necessary filters in your .htaccess file so that files in certain directories always get rewritten and sent to index.php.
RewriteCond %{REQUEST_URI} ^/js/kcfinder
RewriteRule \.php$ index.php [L,QSA]
This condition-and-rule set would need to be placed above the conditions that check for files and directories.
Alternatively, you can create authenticated routes in Laravel that manually fetch and execute the files. (This is not recommended as you would have to make use of eval().)
I've been down this path with trying to integrate ckfinder into Laravels auth system and ultimately found it to be too much effort. It's probably possible but my solution was simple hack. When I render the Ckeditor widget, I set a plain old session variable in PHP, then check for the existence of the session var in ckfinders auth check routine.
// When rendering widget
session_start();
$_SESSION['enable_ckeditor'] = true;
// In ckfinder somewhere
session_start();
return isset( $_SESSION['enable_ckeditor'] ) ?: $_SESSION['enable_ckeditor'];

How to access a website only from a specified IP using PHP

I need to access a site only from a specific IP address.
Is that possible using PHP.
The project is under development and some people used that and say "The site is not good". So
i like to avoid that kind of things. That's why i need this solutin.
try this:
if ($_SERVER['REMOTE_ADDR'] == "x.x.x.x")
echo "admin";
else
echo "user";
it checks the ip of user and do the action.
I would suggest to use a .htaccess file instead of adding this to your php-code:
RewriteEngine On
RewriteBase /
# IPs that are still allowed to view everything
RewriteCond %{REMOTE_ADDR} !^213.123.39.12$ [NC]
RewriteRule !^(noentry_image.jpg|favicon.ico)$ sorry_stay_out.html [L]
just put the ".htaccess" file into your root-dir of your website. Then everybody will be redirected to the sorry_stay_out.html page, that contains the noentry_image.jpg.
All visitors from the IP that is allowed will see the site as normal. You can repeat the line "RewriteCond %{REMOTE_ADDR} !^213.123.39.12$ [NC]" with different IPs as often as you want, to add additional IPs.
Alternative with just blocking:
order allow,deny
allow from 62.57.16.192
allow from 72.232.56.154
deny from all
You can use $_SERVER variables to check if the source is from the IP you're limiting to. Here are some useful function snippets ($s is just $_SERVER):
function gethostname($ip){
return gethostbyaddr($ip);}
function gethostnamepretty($ip){
$host=gethostbyaddr($ip);
$host=explode('.',$host);
$max=count($host);
return $host[$max - 2];}
function getRawRealIP($s){
if (!empty($s['HTTP_CLIENT_IP'])) //check ip from share internet
{
$ip=$s['HTTP_CLIENT_IP'];
}
elseif (!empty($s['HTTP_X_FORWARDED_FOR'])) //to check ip is pass from proxy
{
$ip=$s['HTTP_X_FORWARDED_FOR'];
}
else
{
$ip=$s['REMOTE_ADDR'];
}
return $ip;}
function checkIP($ip){
return long2ip(ip2long($ip));}
function useragent($s){
return $s['HTTP_USER_AGENT'];}

Symfony dynamic subdomains

I'm trying to match subdomains to a customer id in symfony.
i.e. i have customer1.example.com and customer2.example.com
Domains are stored in a table.
When a user goes to customer1.example.com, I would like to get the subdomain, look up the domain name in the database, once matched, it will then deploy the app config for that customer and then store the customer_Id in a global attribute so i know exactly which customer I'm dealing with througout the whole application. The virtual host will have the relevant wildcard servername.
Have you managed to achieve this, and if so, how? If not, any ideas would be a great help!
I'm thinking about using a filter to do it.
:-)
also going to be needing yo set your domain as a wildcard domain, if not you going to need to create manually each subdomain per client.
another solution that is not so symphony dependent is using a .htaccess
<IfModule mod_rewrite.c>
Options +FollowSymLinks
Options +Indexes
RewriteEngine On
RewriteBase /
RewriteCond %{HTTP_HOST} !www.domain.com$ [NC]
RewriteCond %{HTTP_HOST} ^(www.)?([a-z0-9-]+).domain.com [NC]
RewriteRule (.*) $1?sub=%2&page=$1&domain=%{HTTP_HOST} [QSA,L]
<IfModule>
that code basically will send to the requested page the subdomain, the domain and the page requested. then in php you can check if it is equal to your client username. and allow you also to use parked domains for your clients at the same time.
i hope it helps.
Take a look at sfDomainRoutePlugin - it does what you want. However, in its current version you don't get the Propel or DoctrineRoute functionality, which means you must manually lookup the customer based on the subdomain parameter returned from the plugin. Example:
app/frontend/config/routing.yml
# pick up the homepage
homepage:
url: /
class: sfDomainRoute
param: { module: homepage, action: index }
requirements:
sf_host: [www.example.com, example.com]
# catch subdomains for customers
customer_subdomain:
url: /
class: sfDomainRoute
param: { module: customer, action: index }
app/frontend/modules/customer/actions.class.php
public function executeIndex(sfWebRequest $request)
{
// get the subdomain parameter
$this->subdomain = $request->getParameter('subdomain');
// retrieve customer (you have to create the retrieveBySubdomain method)
$this->customer = CustomerPeer::retrieveBySubdomain($this->subdomain);
}
This is just an example, but I use a similar approach myself, and the plugin does what is advertised. Good luck.
If you're adventurous, yuo could take a look at Chapter 2 in the "More with symfony book". This would help you understand the code in sfDomainRoutePlugin.
Because you want to load different app, filter won't help. Just use the frontcontroller (index.php) to extract the subdomain, and if the app directory exists, load the app (else 404). You can even store the id in app configuration.
I'm doing something similar. Note, I haven't tried this exact setup.
$tokens = explode('.', $_SERVER['SERVER_NAME'], 2);
$app = $tokens[0] == 'www' ? 'default' : $tokens[0]; //assumes you aren't allowing www.app.example.com, change if you are
try
{
$appConfiguration = ProjectConfiguration::getApplicationConfiguration($app, 'prod', false);
}
catch(InvalidArgumentException $e) //thrown if app doesn't exist
{
$fallbackConfiguration = ProjectConfiguration::getApplicationConfiguration('default', 'prod', false);
$context = sfContext::createInstance($fallbackConfiguration);
$request = $context->getRequest();
$request->setParameter('module', 'default'); //set what route you want an invalid app to go to here
$request->setParameter('action', 'invalidApplication');
$context->dispatch();
}
if (isset($appConfiguration))
{
sfContext::createInstance($appConfiguration)->dispatch();
}

Categories