$_SERVER['REQUEST_URI'] - php

I discovered my own error, can't understand why some down voted. See first comment
SOLUTION:
if(!empty($_GET['lang']))
{
$uri = 'http'. ($_SERVER['HTTPS'] ? 's' : null) .'://'. $_SERVER['HTTP_HOST'] . $_SERVER['REQUEST_URI'];
$lang_folder = $_GET['lang'];
$ses = $_COOKIE['ccUser'];
$query = mysql_query("UPDATE ".$glob['dbprefix']."CubeCart_sessions SET lang='".$lang_folder."' WHERE sessId='".$ses."'");
header("Location:".substr($uri, 0, -8));
die();
}
where a bit of code is creating "too_many_redirects":
if(!empty($_GET['lang']))
{
$uri = 'http'. ($_SERVER['HTTPS'] ? 's' : null) .'://'. $_SERVER['HTTP_HOST'] . $_SERVER['REQUEST_URI'];
$lang_folder = $_GET['lang'];
$ses = $_COOKIE['ccUser'];
$query = mysql_query("UPDATE ".$glob['dbprefix']."CubeCart_sessions SET lang='".$lang_folder."' WHERE sessId='".$ses."'");
header("Location: $uri");
}
I need to GET the URL the visitor was and reload the page after changing the website language.
Any hints folks?

$_SERVER['REQUEST_URI'] includes ?lang=... which results in if statement being true everytime you redirect.

Related

How can I redirect without infinite loop in PHP code?

I have two WordPress sites using the multi-site function, the URLs are below:
A: sample.com
B: sample.com/en
I tried to write a code in PHP following these conditions, but when I access the RUL of A:sample.com, a browser(chrome) shows an error.
So would you mind telling me how should I solve this problem?
Thank you in advance.
the conditions for access
The first access is only to [A: sample.com]
Users whose browser language is set to Japanese access to [A:
sample.com]
All users whose browser language setting is not set to Japanese
access [B: sample.com/en]
The errors messages in the browser(chrome)
This page isn’t working
sample.com redirected you too many times.
Try clearing your cookies.
ERR_TOO_MANY_REDIRECTS
The code for adding in functions.php
<?php
$uri = $_SERVER['REQUEST_URI'];
$BASE_LANG = 'en';
if (!preg_match('/^[!-~][a-zA-Z]{2}[!-~]/', $uri)) {
$languages = explode(',', $_SERVER['HTTP_ACCEPT_LANGUAGE']);
$lang = $BASE_LANG;
if (isset($languages)) {
$browser_lamguage = $languages[0];
$base_languages = array('ja', 'en');
foreach ($base_languages as $base_language) {
if (preg_match("/^$base_language/i", $browser_lamguage)) {
$lang = $base_language;
break;
}
}
}
$url = get_site_url()."/$lang/";
if ($lang == 'ja') {
$url = get_site_url();
}
header("Location: $url");
exit();
}
?>
Development environment
CentOS (7 x86_64)
Apache (2.4.6 CentOS)
PHP (7.1.33)
wordpress(5.2.5)
Just make below change in your code:
if ($lang != 'ja') {
header("Location: $url");
exit();
}
Edited:
$uri = $_SERVER['REQUEST_URI'];
$BASE_LANG = 'en';
if (!preg_match('/^[!-~][a-zA-Z]{2}[!-~]/', $uri)) {
$languages = explode(',', $_SERVER['HTTP_ACCEPT_LANGUAGE']);
$lang = $BASE_LANG;
if (isset($languages)) {
$browser_lamguage = $languages[0];
$base_languages = array('ja', 'en');
foreach ($base_languages as $base_language) {
if (preg_match("/^$base_language/i", $browser_lamguage)) {
$lang = $base_language;
break;
}
}
}
$url = get_site_url()."/$lang/";
if ($lang != 'ja') {
header("Location: $url");
exit();
}
}

how to define a path that support HTTPS and HTTP?

I have a redirect character strip script, that takes the original URL, strips the requested strings out of it (foo , bar) and then redirects to the same URL only without these strings.
It's currently set up to work with HTTP Only, as users always requests the HTTP page. But now I'm adding HTTPS, so some users will land on HTTPS. in that case, I'd like the redirect to be to the HTTPS.
How Can I do it?
I've tried simply changing:
$url = "http://$_SERVER[HTTP_HOST]$_SERVER[REQUEST_URI]";
Into:
$url = "://$_SERVER[HTTP_HOST]$_SERVER[REQUEST_URI]";
But it created an invalid request (mydomain.com//mydomain.com....)
CODE:
function unparse_url($parsed_url) {
$scheme = isset($parsed_url['scheme']) ? $parsed_url['scheme'] . '://' : '';
$host = isset($parsed_url['host']) ? $parsed_url['host'] : '';
$port = isset($parsed_url['port']) ? ':' . $parsed_url['port'] : '';
$user = isset($parsed_url['user']) ? $parsed_url['user'] : '';
$pass = isset($parsed_url['pass']) ? ':' . $parsed_url['pass'] : '';
$pass = ($user || $pass) ? "$pass#" : '';
$path = isset($parsed_url['path']) ? $parsed_url['path'] : '';
$query = !empty($parsed_url['query']) ? '?' . trim($parsed_url['query'], '&') : '';
$fragment = isset($parsed_url['fragment']) ? '#' . $parsed_url['fragment'] : '';
return "$scheme$user$pass$host$port$path$query$fragment";
}
function strip_query($url, $query_to_strip) {
$parsed = parse_url($url);
$parsed['query'] = preg_replace('/(^|&)'.$query_to_strip.'[^&]*/', '', $parsed['query']);
return unparse_url($parsed);
}
$url = "http://$_SERVER[HTTP_HOST]$_SERVER[REQUEST_URI]";
$url2 = (strip_query($url, 'foo')); # query to strip - foo
$new_url = (strip_query($url2, 'bar')); # strip also - bar
$filtered = array_filter(array_keys($_GET), function($k) {
return strpos($k, 'foo') === 0;
});
if ( !empty($filtered) ) {
$_SESSION['trackParam'] = $_GET; // #### Save original request data and url before redirection
$_SESSION['REQUEST_URI'] = $_SERVER[REQUEST_URI];
$_SESSION['redirected'] = true;
header ("Location: $new_url");
}
You can use $_SERVER['HTTPS'] to decide whether to use https in your $url:
function check_https() {
return (!empty($_SERVER['HTTPS']) && $_SERVER['HTTPS'] !== 'off')
|| $_SERVER['SERVER_PORT'] == 443;
}
$url = (check_https() ? "https" : "http")
."://$_SERVER[HTTP_HOST]$_SERVER[REQUEST_URI]";
You can check if the request is made to HTTPS and put a condition:
if( isset($_SERVER['HTTPS'] ) ) { $url= ... } else {$url= ... }

Storing Session data Fails, due to a following redirect

I want to store session data right before a 302 redirect occurs, to the same page, only without some of the original request parameters.
for example:
Visitor goes to domain.com/?ab_saveme=hey
hey value will get stored
Visitor will get redirected to domain.com/
Page will output hey
This is the code I came with, it does the redirect, but it doesn't manage to store the value (hey is not being outputed).
Without the redirect block, it does store it correct.
<?php
session_start();
session_name("hello");
$_SESSION['cache']=$_GET['ab_saveme']; // store the `saveme` value
// begin self redirect code
function unparse_url($parsed_url) {
$scheme = isset($parsed_url['scheme']) ? $parsed_url['scheme'] . '://' : '';
$host = isset($parsed_url['host']) ? $parsed_url['host'] : '';
$port = isset($parsed_url['port']) ? ':' . $parsed_url['port'] : '';
$user = isset($parsed_url['user']) ? $parsed_url['user'] : '';
$pass = isset($parsed_url['pass']) ? ':' . $parsed_url['pass'] : '';
$pass = ($user || $pass) ? "$pass#" : '';
$path = isset($parsed_url['path']) ? $parsed_url['path'] : '';
$query = !empty($parsed_url['query']) ? '?' . trim($parsed_url['query'], '&') : '';
$fragment = isset($parsed_url['fragment']) ? '#' . $parsed_url['fragment'] : '';
return "$scheme$user$pass$host$port$path$query$fragment";
}
function strip_query($url, $query_to_strip) {
$parsed = parse_url($url);
$parsed['query'] = preg_replace('/(^|&)'.$query_to_strip.'[^&]*/', '', $parsed['query']);
return unparse_url($parsed);
}
$url = "http://$_SERVER[HTTP_HOST]$_SERVER[REQUEST_URI]";
$new_url = (strip_query($url, 'ab')); # or whatever query you want to strip/keep
$filtered = array_filter(array_keys($_GET), function($k) {
return strpos($k, 'ab') === 0;
});
if ( !empty($filtered) ) {
header ("Location: $new_url");
}
// end self redirect code
echo $_SESSION['cache']; // needs to echo original `saveme` value
echo session_id();
if (is_writable(session_save_path()))
{
echo "writable";
}
?>
Edit:
Thanks to Zimmi, I noticed I was re-storing a null value.
Is the best practice to handle this is change:
$_SESSION['cache']=$_GET['ab_saveme']; // store the `saveme` value
into:
if (!empty($_GET['ab_saveme'])) {
$_SESSION['cache']=$_GET['ab_saveme']; // store the `saveme` value
}
Or is there a better way? as I might have to do this for various parameters (such as ab_1,ab_2)

If current URL equals rediectURL do nothing

Hey guys I am trying to build a redirect script in my header.
It contains a variable called $redirect that either equals 0 or 1.
What I want to do is if the variable equals 1 to redirect the user to a specified page.
That works.
The problem I am having is when it reaches the redirected URL it creates a loop.
I tried writing the following code but it does not work. What have I done wrong?
<?php
$redirect = 1;
$host = $_SERVER['HTTP_HOST'];
$self = $_SERVER['PHP_SELF'];
$query = !empty($_SERVER['QUERY_STRING']) ? $_SERVER['QUERY_STRING'] : null;
$url = !empty($query) ? "http://$host$self?$query" : "http://$host$self";
$redirectURL = '/protest/cispa.php';
if ( $redirect === 1 ) {
if ( $url === $redirectURL ) {
die();
}
else {
header("Location: $redirectURL");
exit;
}}
?>
As suggested by andrewsi I updated my code to the following at it works:
<?php
$redirect = 0;
$host = $_SERVER['HTTP_HOST'];
$self = $_SERVER['PHP_SELF'];
$query = !empty($_SERVER['QUERY_STRING']) ? $_SERVER['QUERY_STRING'] : null;
$url = $self;
$redirectURL = '/protest/cispa.php';
if ( $redirect === 1 ) {
if ( $url === $redirectURL ) {
}
else {
header("Location: $redirectURL");
exit;
}
}
?>
$url = !empty($query) ? "http://$host$self?$query" : "http://$host$self";
$redirectURL = '/protest/cispa.php';
Your $url contains a fully qualified domain name; the redirectURL is just a path. The two are never going to be equal. Try setting :
$url = $self;
(If I'm reading your code correctly)
You could stick a flag in the query string of your redirect. Then, if the flag is present, don't add the redirect.
ex;
http://www.yoursite.com/redirectedto.php?red=1
Now, if red is set, I would not add the redirect.
lee

PHP problems with current url

I use the "Current url" function to get the current link when user changing page language
$uri = explode('&', $_SERVER['REQUEST_URI']);
$uri = $uri[0];
$url = (!empty($_SERVER['HTTPS'])) ? "https://".$_SERVER['SERVER_NAME'].$uri : "http://".$_SERVER['SERVER_NAME'].$uri;
Problem is, when I have a link like this:
http://127.0.0.1/index.php?id=shop&id2=13&lang=lt
id2, of course, disappears. What can I do about this? It is possible if id2 is set to use explode with a second & or something like this?
You can use the parse_url function, here is an example:
$uri = parse_url( $_SERVER['REQUEST_URI']);
$protocol = !empty($_SERVER['HTTPS']) ? 'https://' : 'http://';
$url = $protocol . $_SERVER['SERVER_NAME'] . $_SERVER['SCRIPT_NAME'] . '?' . ( isset( $uri['query']) ? $uri['query'] : '');
I did not see in your code where you get the script's filename, so I used $_SERVER['SCRIPT_NAME'].
Edit: My mistake, I did not see that you need to manipulate / remove the last $_GET parameter. Here is an example on how to do that using a method similar to the above in conjunction with parse_str. Note that this method will work regardless of the location of the lang parameter, it does not have to be the last one in the query string.
$protocol = !empty($_SERVER['HTTPS']) ? 'https://' : 'http://';
$params = array();
if( isset( $_SERVER['QUERY_STRING']) && !empty( $_SERVER['QUERY_STRING']))
{
parse_str( $_SERVER['QUERY_STRING'], $params);
$params['lang'] = 'anything';
// unset( $params['lang']); // This will clear it from the parameters
}
// Now rebuild the new URL
$url = $protocol . $_SERVER['SERVER_NAME'] . $_SERVER['SCRIPT_NAME'] . ( !empty( $params) ? ( '?' . http_build_query( $params)) : '');
Thanks to #Yzmir Ramirez for an improvement in the second version that eliminates the extraneous call to parse_url.
$uri = explode('&', '/index.php?id=shop&id2=13&lang=lt');
$uri = $uri[0];
echo $uri; //echos /index.php?id=shop
You'll want to use
$_SERVER['QUERY_STRING']
to get just the query string. And if you want to keep all the variables, then just keep $uri set to the explode then cycle through them with a foreach.
$uri = explode('&', $_SERVER['QUERY_STRING'];
foreach ($uri as $var_val) {
$var_val = explode('=', $var_val);
$var = $var_val[0];
$val = $var_val[1];
}
Try this: http://codepad.org/cEKYTAp8
$uri = "http://127.0.0.1/index.php?id=shop&id2=13&lang=lt";
$uri = substr($uri, 0, strrpos($uri, '&'));
var_dump($uri); // output: string(41) "http://127.0.0.1/index.php?id=shop&id2=13"
Here is the code I have always used, it also supports ports.
$protocol = (!isset($_SERVER["HTTPS"]) || strtolower($_SERVER["HTTPS"]) == "off") ? "http://" : "https://";
$port = ((isset($_SERVER["SERVER_PORT"]) &&
// http:// protocol defaults to port 80
(($_SERVER["SERVER_PORT"] != "80" && $protocol == "http://") ||
// https:// protocol defaults to port 443
($_SERVER["SERVER_PORT"] != "443" && $protocol == "https://")) &&
// Port is not in http host (port is followed by : at end of address)
strpos($_SERVER["HTTP_HOST"], ":") === false) ? ":" . $_SERVER["SERVER_PORT"] : '');
return $protocol . $_SERVER["HTTP_HOST"] . $port . $_SERVER["REQUEST_URI"];

Categories