Question

I'm working on a Drupal 7 project. I'm using a batch, implenting some operations, and showing a progress bar. in my "formulaire_finished", wich is executed at the end, as last operation of the batch, I want to download a file, and then redirect to another page, because the process is over.

However, The readfile() function use a drupal_exit(), and so my redirection isn't done.

Here is my code:

function formulaire_finished($success, $results, $operations) {
    if ($success) {
        $path = $results['infos']['path'];
        download_file($path);
        // Redirection
        drupal_goto($_SESSION['my_page'], array('query' => array('details' => '1')));
    } else {
        // An error occurred.
        // $operations contains the operations that remained unprocessed.
        $error_operation = reset($operations);
        drupal_set_message(t('An error occurred while processing @operation with arguments : @args', array('@operation' => $error_operation[0], '@args' => print_r($error_operation[0], TRUE), )));
    }
}

download function:

function download_file($path) {
    $dir = $path;
    $filename = basename($dir);
    if (strpos($_SERVER['HTTP_USER_AGENT'], 'MSIE')) {
        drupal_add_http_header('Pragma', 'public');
        drupal_add_http_header('Cache-Control', 'must-revalidate, post-check=0, pre-check=0');
    } else {
        drupal_add_http_header('Pragma', 'no-cache');
    }
    drupal_add_http_header('Expires', '0');
    drupal_add_http_header('Content-Type', 'application/vnd.ms-excel');
    drupal_add_http_header('Content-Disposition', 'attachment; filename=' . basename($dir) . ';');
    drupal_add_http_header('Content-Transfer-Encoding', 'binary');
    drupal_add_http_header('Content-Length', filesize($dir));
    readfile($dir);
    unlink($dir);
    drupal_exit();
}

All ideas are welcome.

Was it helpful?

Solution 2

I don't think you should output the file for download during the finish callback of a batch operation. You should save the file to drupal's file system and save a reference to the file. You can then download it after the batch finishes.

OTHER TIPS

In the below function , can you try to return true always from the below function.

function download_file($path) {
    $dir = $path;
    $filename = basename($dir);
    if (strpos($_SERVER['HTTP_USER_AGENT'], 'MSIE')) {
        drupal_add_http_header('Pragma', 'public');
        drupal_add_http_header('Cache-Control', 'must-revalidate, post-check=0, pre-check=0');
    } else {
        drupal_add_http_header('Pragma', 'no-cache');
    }
    drupal_add_http_header('Expires', '0');
    drupal_add_http_header('Content-Type', 'application/vnd.ms-excel');
    drupal_add_http_header('Content-Disposition', 'attachment; filename=' . basename($dir) . ';');
    drupal_add_http_header('Content-Transfer-Encoding', 'binary');
    drupal_add_http_header('Content-Length', filesize($dir));
    readfile($dir);
    unlink($dir);

    //drupal_exit();
    // Can you use simple return here
    return true;

}
Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top