Retrieving a URL though an authenticating proxy using PHP - php

I am attempting to script the retrieval of an secure (password protected + https) URL trough a proxy server that requires authentication. I found many examples of how to use the 'proxy' option and how to send credentials with stream_context_create.
$url = "https://$server/$uri";
$cred = sprintf('Authorization: Basic %s\r\n', base64_encode("$user:$pass"));
$options['header']=$cred;
$options['proxy']="tcp://10.1.1.1:3128";
$params = array('http' => $options);
$ctx = stream_context_create($params);
$fp = #fopen($url, 'rb', false, $ctx);
However I did not find any where a uid/password was provided to the proxy server. I attempted to add a header manually:
$prox_cred = sprintf('Proxy-Connection: Keep-Alive\r\nProxy-Authorization: Basic %s\r\n', base64_encode("$proxy_user:$proxy_pass"));
$options['header'] .= $prox_cred;
I have root access to the proxy server and I can see my request hitting it, but when I look into the traffic I don't see my headers. I guess they are being added to the portion that gets encrypted and sent to the end server.

For some reason I didn't want to complicate things by using the cURL modules for the first time. However based on the responses I tried it and it took about 6 minutes to get things working.
if ($proxy_server != '') {
curl_setopt($ch,CURLOPT_PROXYAUTH,CURLAUTH_BASIC);
curl_setopt($ch,CURLOPT_PROXY,"$proxy_server");
if ($proxy_user != '') {
curl_setopt($ch,CURLOPT_PROXYAUTH,CURLAUTH_BASIC);
curl_setopt($ch,CURLOPT_PROXYUSERPWD,"$proxy_user:$proxy_pass");
}
}
Thanks!

Related

fopen() very slow when used in Joomla

I'm writing a authentication plugin for Joomla.
The plugin is calling an external site to verify the username and password.
The code works, but my problem is that when I'm calling fopen() from the Joomla plugin, it takes a very long time (63 seconds) for it to respond.
When running the same code on the server (but not through Joomla), the fopen() call only takes 0.1 second.
Is there any settings that Joomla can have changed, that makes the fopen() call taking so long? Or is there any other function that I should use instead of fopen()? (I have tried file_get_contents() but with the same result)
Below is the code I'm using (based on this article: http://wezfurlong.org/blog/2006/nov/http-post-from-php-without-curl/) (I don't have cURL installed so that is not an option.)
$username = "admin";
$password = "1234" ;
$verb = 'GET'
$url = "https://xxx.xxx.xxx/api.phtml/login" ;
$params = array("username"=>$username, "password"=>$password);
$params = http_build_query($params);
$url .= '?' . $params;
$cparams = array( 'http' => array( 'method' => $verb,
'ignore_errors' => true ) );
$context = stream_context_create($cparams);
$fp = fopen($url, 'rb', false, $context);
The allow_url_fopen is enabled.
Joomla! Version: Joomla! 2.5.27 Stable
PHP Version: 5.2.6-1+lenny10
I have been struggeling with this for three days now, so any help would be very appreciated!
Thanks!
Usually when we have a problem with fopen, we switch to curl and that solves the problem. In any case, check your .htaccess and your local php.ini (or .user.ini) files for the Joomla site for any restrictions on fopen.

PHP non blocking soap request

After a user signs up on my website i need to send a soap request in a method that is not blocking to the user. If the soap server is running slow I don't want the end user to have to wait on it. Is there a way I can send the request and let my main PHP application continue to run without waiting from a response from the soap server? If not, is there a way to set a max timeout on the soap request, and handle functionality if the request is greater than a max timeout?
Edit:
I would ideally like to handle this with a max timeout for the request. I have the following:
//ini_set('default_socket_timeout', 1);
$streamOptions = array(
'http'=>array(
'timeout'=>0.01
)
);
$streamContext = stream_context_create($streamOptions);
$wsdl = 'file://' . dirname(__FILE__) . '/Service.wsdl';
try{
if ( file_get_contents( $wsdl ) ) {
$this->_soapClient = new SoapClient($wsdl,
array(
'soap_version' => SOAP_1_2,
'trace' => true,
'stream_context' => $streamContext
)
);
$auth = array('UserName' => $this->_username, 'Password' => $this->_password);
$header = new SoapHeader(self::WEB_SERVICE_URL, "WSUser", $auth);
$this->_soapClient->__setSoapHeaders(array($header));
}//if
}
catch(Exception $e){
echo "we couldnt connect". $e;
}
$this->_soapClient->GetUser();
I set the timeout to 0.01 to try and force the connection to timeout, but the request still seems to fire off. What am I doing wrong here?
I have had the same issues and have implemented solution !
I have implemented
SoapClient::__doRequest();
To allow multiple soap calls using
curl_multi_exec();
Have a look at this asynchronous-soap
Four solutions:
Use AJAX to do the SOAP -> Simplest SOAP example
Use AJAX to call a second PHP file on your server which does the SOAP (best solution imo)
Put the SOAP request to the end of your PHP file(s) (not the deluxe solution)
Use pcntl_fork() and do everything in a second process (I deprecate that, it might not work with every server configuration)
Depending on the way you implement this, PHP has plenty of timeout configurations,
for example socket_set_timeout(), or stream_set_timeout() (http://php.net/manual/en/function.stream-set-timeout.php)

How do you make a proper HTTP POST request to an API via PHP code? I'm doing something wrong

So I am trying to authenticate with a url (in a companies API) and send some information in to be checked. If the info is good, it sends me back what I need (string). If not, it sends back a string: "0". If there is an error, it sends back a string complaining the error. However, using this method from the CakePHP documentation of HttpSocket, I am being returned an HttpResponse object that is seemingly empty. It has no body, no status code, etc. What am I doing wrong? I am going to change the values because they are private for work.
App::uses('HttpSocket', 'Network/Http');
$user = 'username';
$pass = 'password';
$token = $this::_getToken($user, $pass);
$hash = $this::_getChallengeSalt($token);
$item = $this->Item->findById($id);
$url3 = 'example.url.com/api/path/to/code';
$http = new HttpSocket();
$http->configAuth('Basic', $user, $pass);
$data = array('id' => '1234', 'itemName' => $item['Item']['id'], 'hash' => $hash);
$results = $http->post($url3, $data);
i have seen your code but could not fine any mistake
but here i can suggest you to if I think you cannot talk directly HTTPS, as it is HTTP encrypted with the public certificate of the server you are connecting to. Maybe you can use some of the ssl functions in php. But, this will take you some time and frankly, there are easier things.
Just take a look at cURL (client URL), that has support for GET and POST requests, and also connecting to https servers.
let me know i can help you more.

How to obtain the returned cookie after a POST in PHP?

Let's say I have a website called (example.com) which will have a php file (example.com/call.php).
call.php will have a post method that will post to the website exampleOne.com/login.php with the right parameters. exampleOne.com will return a header with a cookie that will confirm the authentication of the user, how do I obtain the cookie or at least check if the header includes Set-Cookie in order to be informed that the user is authenticated?
If this is not clear enough please let me know in the comments and I will try my best to clear everything up.
(UPDATE 1: so the idea is that, how do I know that the other domain I am posting to has set up the cookie because the fact that the cookie has been set up (Set-cookie != null or "") means that the username and password are in fact correct)
(Update 2 so my issue is that I want to make sure that user is a member of some forum which does not have an API and I cannot authenticate to that forum because i don't have access to their records, however, that forum authenticate the user and sets a cookie if the information is right and I want to be able to see that cookie to make sure I understand that the user is authenticated - hope this helps)
You can use this code to do what you want. Pretty much you're just simulating a client when you do this by writing a HTTP request to a page and then processing the response headers that it sends back. This is also how you would build a proxy server, but that is sort of what you're doing.
Let me know if you need any help.
//
// OPEN SOCKET TO SERVER
//
$_socket = #fsockopen($host, $port, $err_no, $err_str, 30);
//
// SET REQUEST HEADERS
//
$_request_headers = '... CONSTRUCT FULL HEADERS HERE ...';
fwrite($_socket, $_request_headers);
//
// PROCESS RESPONSE HEADERS
//
$_response_headers = $_response_keys = array();
$line = fgets($_socket, 8192);
while (strspn($line, "\r\n") !== strlen($line))
{
#list($name, $value) = explode(':', $line, 2);
$name = trim($name);
$_response_headers[strtolower($name)][] = trim($value);
$_response_keys[strtolower($name)] = $name;
$line = fgets($_socket, 8192);
}
sscanf(current($_response_keys), '%s %s', $_http_version, $_response_code);
if (isset($_response_headers['set-cookie']))
{
// DO WHAT YOU WANT HERE
}
For reference, you can find similar code in PHProxy that goes into much more detail. It will create headers for you, process response headers, and more. If you find that this example doesn't do everything you need, you should reference that software.

How can i add exception?

I have a php site www.test.com.
In the index page of this site ,i am updating another site's(www.pgh.com) database by the following php code.
$url = "https://pgh.com/test.php?userID=".$userName. "&password=" .$password ;
$response = file_get_contents($url);
But,now the site www.pgh.com is down.So it also affecting my site 'www.test.com'.
So how can i add some exception or something else to this code,so that my site should work if other site is down
$response = file_get_contents($url);
if(!$response)
{
//Return error
}
From the PHP manual
Adding a timeout:
$ctx = stream_context_create(array(
'http' => array(
'timeout' => 1
)
)
);
file_get_contents("http://example.com/", 0, $ctx);
file_get_contents returns false on fail.
You have two options:
Add a timeout to the file_get_contents call using stream_get_context() (The manual has good examples; Docs for the timeout parameter here). This is not perfect, as even a one second's timeout will cause a notable pause when loading the page.
More complex but better: Use a caching mechanism. Do the file_get_contents request in a separate script that gets called frequently (e.g. every 15 minutes) using a cron job (if you have access to one). Write the result to a local file, which your actual script will read.

Categories