0

strange problem, i'm opening a connection with fsockopen() to a page, that page has a header(location:xx) to the same page (i'm just refreshing the script), but it'seems that the redirect isn't working...

obviously everything is working if i'm replicating it with a browser...

some code:

CONNECTION PAGE:

$socketcon = fsockopen($_SERVER['HTTP_HOST'],80,$errorno,$errorstr,10);
if($socketcon) {
    $socketdata = "GET http://www.example.com/test2.php HTTP/1.0\r\nHost: ".$_SERVER['HTTP_HOST']."\r\nConnection: Close\r\n\r\n";
    fwrite($socketcon,$socketdata); 
    fclose($socketcon);
}

CONNECTED PAGE (test2.php):

<?
//other code (working fine)

if($_GET["AAA"]){

     //REDIRECT WORKED !

} else {
     header("location:test2.php?AAA=1");   //same page but with a get param
}
?>

the REDIRECT WORKED part never get executed...

any suggestions ?

EDIT: the connection MUST be asynchronous

NicolaPasqui
  • 1,112
  • 8
  • 17
  • Your current solution will not work anyway: as soon as the caller script ends, the connection will be dropped. I think you want AJAX. Otherwise, there's no way. You can't just magically redirect a disconnected client, unless you use JavaScript. – netcoder Aug 08 '12 at 16:15
  • The async part it's already working, the script opened with the socket is running even if i close the browser (with the caller script opened)...the problem is that i can't redirect the socket-ed script – NicolaPasqui Aug 08 '12 at 19:03
  • When your caller script ends (i.e.: at the last `?>` end tag), the socket is closed. You may think that it works, but it doesn't. And you still will have the redirection problem unless you use JavaScript. Unless you didn't formulate your question properly, and all you want is an `include`. – netcoder Aug 08 '12 at 19:08
  • I Assure you that's working, the called script sends an email every 3-4 minutes, the emails will still arrive hours after i've closed the caller script (tested hundreds of times), have a look here http://petewarden.typepad.com/searchbrowser/2008/06/how-to-post-an.html the only problem is that using sockets, the called script will never follow redirections with header manipulation – NicolaPasqui Aug 08 '12 at 22:13

3 Answers3

2

any suggestions ?

Yes, stop using a socket to do what cURL can do better ;) A header('Location: X') will actually send you a 301/303 HTTP response, which you (or the browser) should handle by making a new request. However, you don't seem to handle redirects. cURL, on the other hand, mimics browser-like functionality and it can follow redirects by using curl_setopt( $curlResource, CURLOPT_FOLLOWLOCATION, true );

Berry Langerak
  • 18,561
  • 4
  • 45
  • 58
  • i forgot an important thing, it HAS to be asynchronous, that's why i didn't use curl... – NicolaPasqui May 23 '12 at 08:57
  • @Il_pasqui If you want to continue on this path, you'll have to handle redirects yourself. By the way; PHP is executed sequentially, which means you won't have asynchronous requests anyway, unless you execute your scripts in parallel. – Berry Langerak May 23 '12 at 09:02
  • how can i handle redirects ? i mean, it's obvious that the header(location) isn't working if the page is opened by a socket...so, is there an alternative ? i just need to re-execute the script, i could try connecting again with a socket but it's a reeeally bad thing to do....thanks ! – NicolaPasqui May 23 '12 at 09:24
1

Consider Is making asynchronous HTTP requests possible with PHP? which is a similar question.

Using exec()-family functions might be a good bet if you don't need return values; you can just call curl appended by & and it'll run in the background.

If you really, truly want to do this in PHP, you can either: spawn a new process (using pcntl_fork()) or handle redirects yourself.

To handle redirects you'll need to:

  1. Determine what your response code is by looking at the first three characters read from the stream. A 200 means sucess, anything in the 300s means partial success.
  2. Once you've found a 302 (or 307) in the first three characters, search for a location header. This will match the regex /\s*location:\s*(.+)$/m, I believe.
  3. Validate that the URL you have from the location field matches your expectations and is trustworthy. It should be an absolute URL, but you'll need to check it for a safe server, safe port, safe URL and safe parameters. parse_url() may come in handy, but does not check for potential security issues.
  4. Open a new connection to the new URL matched above (or, if it's the same host and you're using HTTP 1.1 with Keep-Alive, reuse your connection) to send the appropriate data.
  5. Deal with any results/clean-up as required.

You can see this is very complex. This will also be recursive. What you're really talking about doing is writing a rudimentary HTTP parser in PHP. This is not a good idea - use cURL and find some other way to make it asynchronous.

Community
  • 1
  • 1
mjec
  • 1,817
  • 12
  • 20
0

Your connect function does not handle redirects.

If you want to support it you have to write the code yourself, or use a library like curl to make the connection.

ilanco
  • 9,581
  • 4
  • 32
  • 37