I've a PHP document, let's say jsonarray.php.
This file returns the json_encode of an associative array when some parameters are given. I need to forbid an unwanted user to access and use this file for his own purposes.
Is this possible?
In addition, I want to specify that it is a client-side request, which I make in a JavaScript code.
if you are looking this from another PHP file, you can set BASEPATH
constant there & add the following line in top of all the files you need to protect:
defined('BASEPATH') OR exit('No direct script access allowed');
so if the file is accessed from that particular file, BASEPATH
is set & everything works. But incase of some url directly tried to access, script would terminate.
If you are calling it this from Javascript -- other option is to add nonce
token to every javascript request which is basically a randomly generated unique token that is valid for single request. see Cross-Site Request Forgery (CSRF) Prevention Cheat Sheet for more details.
here is a example taken from here:
function create_api_key(){
return base64_encode(base64_encode($this->encrypt(time().'X'.$_SERVER['REMOTE_ADDR'])));
}
function check_api_key($key,$timeout=5){
if(empty($key)){ exit('Invalid Key'); }
$keys=explode('X',$this->decrypt(base64_decode(base64_decode($key))));
if (isset($key) && isset($keys[0]) && $keys[0] >= (time()-$timeout) &&
isset($keys[1]) && $keys[1] == $_SERVER['REMOTE_ADDR']){
return true;
}else{
return false;
}
}
function encrypt($value){
$iv_size = mcrypt_get_iv_size(MCRYPT_RIJNDAEL_256, MCRYPT_MODE_ECB);
$iv = mcrypt_create_iv($iv_size, MCRYPT_RAND);
return mcrypt_encrypt(MCRYPT_RIJNDAEL_256, 'SECURE_KEY', $value, MCRYPT_MODE_ECB, $iv);
}
function decrypt($value){
$iv_size = mcrypt_get_iv_size(MCRYPT_RIJNDAEL_256, MCRYPT_MODE_ECB);
$iv = mcrypt_create_iv($iv_size, MCRYPT_RAND);
return trim(mcrypt_decrypt(MCRYPT_RIJNDAEL_256, 'SECURE_KEY', $value, MCRYPT_MODE_ECB, $iv));
}
}
$csrf = new csrf_check();
if(!empty($_GET['do'])){
$do = $_GET['do'];
switch($do){
//example.com?do=get - a key for the request
case "get":
echo $csrf->create_api_key();
break;
case "check":
//key only lasts 30 secs & validate key passed
//example.com?do=get&key=MEV6NXk4UjVRQXV5Qm1CMjBYa3RZZUhGd2M0YnFBUVF0ZkE5TFpNaElUTT0=
if(!empty($_GET['key']) && $csrf->check_api_key($_GET['key'],30)){
exit('Key valid');
}else{exit('Key invalid');}
break;
default:
exit('Request invalid');
break;
}
}
Why not just check for whatever requirements you need and if they are not met then kill the page.
die('Access Blocked');
Something as simple as requiring a specific $_GET
parameter might be enough for you -
if (isset($_GET['password']) && $_GET['password'] == "your_password"){
}else{
die('access denied!');
}
Now all you have to do to be able to access this PHP file is to add the password in to the URL :
http://yourcoolsite.com/jsonarray.php?password=your_password
I would recommend not using "password" as the key for the parameter. Rather call it something else, something slightly obfuscated so that it is not immediately apparent that it is a password.
http://yourcoolsite.com/jsonarray.php?mpwyour_password
Easiest way is to use .htaccess
to prevent users from directly viewing a file Here's two links to a find out how: Tutorial 1 Tutorial 2
Is this possible?
No.
Because as you make a request from javascript to that file it must be accessible to the browser. As you don't control the browser you can not say any longer if the javascript in th browser initiated the request or something or somebody else.