简体   繁体   中英

Redirect page after process complete in PHP

I have some process in page. It's downloading a file.

<?php

// getting file with CURL
        $ch = curl_init ('http://adress.com/file.csv');
    curl_setopt($ch, CURLOPT_HEADER, 0);
    curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
    curl_setopt($ch, CURLOPT_FOLLOWLOCATION, false);
    curl_setopt($ch, CURLOPT_BINARYTRANSFER,1);
    curl_setopt($ch, CURLOPT_TIMEOUT,7500);
    $rawdata=curl_exec($ch);
    curl_close ($ch);
// End Curl Process

// SAVE FILE
    $name = Rand(100000,1000000);
    $fp = fopen('files/'.$name.'.csv','w');
    fwrite($fp, $rawdata);
    fclose($fp);

// END SAVE PROCESS

// REDIRECT OTHER PAGE
       **header('Location: x.php');**
// END OF PAGE

?>

This is allright. But there is a problem. It redirects without complete process. I want to redirect after all processes are done. The file is empty when i redirect with that method.

What must I do? How can i redirect page after all processes are done? php or javascript/jquery.

Your code should be fine, and should complete the process before redirecting.

PHP runs in a single thread, so the next statement won't be executed until the previous one completes. This means that your header() line won't execute until fwrite() has finished writing the file.

In fact, setting a Location header doesn't even mean the PHP script stops. You can test this by creating a dummy file and running unlink() on it after issuing the Location header. The file will still be deleted. All that Location does is sends a new location to your browser. Your browser then retrieves the new page before the old one is done running.

I think set a callback when the header is complete is the best solution.

$ch = curl_init();
curl_setopt($ch, CURLOPT_URL, 'http://www.php.net/');

// here is the hack - Set callback function for headers
curl_setopt($ch, CURLOPT_HEADERFUNCTION, 'read_header');

curl_exec($ch);
curl_close($ch);

//Callback function for header
function read_header($ch, $string)
{   
    if (trim($string) == 'HTTP/1.1 200 OK')
        header("location: http://www.php.net"); 
}

You can set sleep(seconds) and check if it's enough for complete process.

Also you can put a simple check:

$start_size = 0;
while (1) {
   $new_file_size = filesize($filename);

   if ($start_size != $new_file_size) {
      $start_size = $new_file_size;
      sleep(30)
   } else {
      break;
   }
}

If you aren't returning the file to the client, you can do the following:

  ignore_user_abort();
  header("Content-Length: 0", true, HTTP_RESPONSE_204_NO_CONTENT);
  header("Connection: close", true);
  flush();

This will return control back to the client and close the browser connection, but the server-side process will continue to work.

However, I agree with @AgentConundrum that the header() line won't be executed until the other processes are complete.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM