Force Download dengan PHP

Force Download yaitu istilah untuk memerintahkan membaca file dan langsung mengunduhnya, tanpa perlu langsung stream/buka di browser. Dengan force download kita dapat menyembunyikan file aslinya maupun generate file dari program (jika ada). Misalnya file PDF, jika kita gunakan berupa link saja, PDF tersebut akan terbuka dalam sebuah tab PDF reader di browser. Dengan menggunakan force download, file PDF tidak akan dibuka, melainkan langsung diunduh.

function force_download($filename = '', $data = '')
{
	if ($filename == '' || $data == '')
	{
		return false;
	}

	if (!file_exists($data))
	{
		return false;
	}

	if (false === strpos($filename, '.'))
	{
		return false;
	}

	$extension = strtolower(pathinfo(basename($filename), PATHINFO_EXTENSION));

	$mime_types = array(
		'txt' => 'text/plain',
		'htm' => 'text/html',
		'html' => 'text/html',
		'php' => 'text/html',
		'css' => 'text/css',
		'js' => 'application/javascript',
		'json' => 'application/json',
		'xml' => 'application/xml',
		'swf' => 'application/x-shockwave-flash',
		'flv' => 'video/x-flv',
		// images
		'png' => 'image/png',
		'jpe' => 'image/jpeg',
		'jpeg' => 'image/jpeg',
		'jpg' => 'image/jpeg',
		'gif' => 'image/gif',
		'bmp' => 'image/bmp',
		'ico' => 'image/vnd.microsoft.icon',
		'tiff' => 'image/tiff',
		'tif' => 'image/tiff',
		'svg' => 'image/svg+xml',
		'svgz' => 'image/svg+xml',
		// archives
		'zip' => 'application/zip',
		'rar' => 'application/x-rar-compressed',
		'exe' => 'application/x-msdownload',
		'msi' => 'application/x-msdownload',
		'cab' => 'application/vnd.ms-cab-compressed',
		// audio/video
		'mp3' => 'audio/mpeg',
		'qt' => 'video/quicktime',
		'mov' => 'video/quicktime',
		// adobe
		'pdf' => 'application/pdf',
		'psd' => 'image/vnd.adobe.photoshop',
		'ai' => 'application/postscript',
		'eps' => 'application/postscript',
		'ps' => 'application/postscript',
		// ms office
		'doc' => 'application/msword',
		'docx' => 'application/vnd.openxmlformats-officedocument.wordprocessingml.document',
		'rtf' => 'application/rtf',
		'xls' => 'application/vnd.ms-excel',
		'xlsx' => 'application/vnd.openxmlformats-officedocument.spreadsheetml.sheet',
		'ppt' => 'application/vnd.ms-powerpoint',
		'pptx' => 'application/vnd.openxmlformats-officedocument.presentationml.presentation',
		// open office
		'odt' => 'application/vnd.oasis.opendocument.text',
		'ods' => 'application/vnd.oasis.opendocument.spreadsheet',
	);

	if (!isset($mime_types[$extension]))
	{
		$mime = 'application/octet-stream';
	} else
	{
		$mime = ( is_array($mime_types[$extension]) ) ? $mime_types[$extension][0] : $mime_types[$extension];
	}

	if (strstr($_SERVER['HTTP_USER_AGENT'], "MSIE"))
	{
		header('Content-Type: "' . $mime . '"');
		header('Content-Disposition: attachment; filename="' . $filename . '"');
		header('Expires: 0');
		header('Cache-Control: must-revalidate, post-check=0, pre-check=0');
		header("Content-Transfer-Encoding: binary");
		header('Pragma: public');
		header("Content-Length: " . filesize($data));
	} else
	{
		header("Pragma: public");
		header("Expires: 0");
		header("Cache-Control: must-revalidate, post-check=0, pre-check=0");
		header("Cache-Control: private", false);
		header("Content-Type: " . $mime, true, 200);
		header('Content-Length: ' . filesize($data));
		header('Content-Disposition: attachment; filename=' . $filename);
		header("Content-Transfer-Encoding: binary");
	}
	readfile($data);
	exit;
}


About Author

Cecep Yusuf

Hi, my name is Cecep Yusuf. However, in the virtual world I am more likely to use the name Cheyuz, which is an abbreviation of two words "Cecep" and "Yusuf". I am founder of Jagocoding.com, u can view more of me in Cheyuz.com


Comment & Discussions

  • Himran Nababan
    Kalau Ukuran Size File sudah melebihi dari 4 MB, Misalnya File yang mau didownload adalah file berukuran 1 GB pasti akan berat sekali jika menggunakan fungsi readfile()

    Ada saran tidak kang kalau untuk file berukuran besar, kasusnya saya ingin membuat record log download suatu file yang berhasil di download sampai tuntas oleh users, trims banyak sebelumnya

    • Cecep Yusuf

      kalo 1 GB dalam bentuk stream seperti ini pasti bakal lama.. bagusnya sih ini generator untuk PDF ato file yang headernya tidak sampe berukuran besar. Kalo record log biasanya saya buat suatu fungsi ke halaman tertentu, kemudian redirect aja paling ya :D


    • Himran Nababan

      Redirect langsung ke lokasi file nya ya kang? nanti setelah selesai download kan tidak tau dia selesaidownload nya atau berhenti ditengah jalan (Maksud saya disini adalah bagaiman merecord berapa user yang benar-benar tuntas mendownload file tersebut).


    • Cecep Yusuf

      Ooh ya ya sorry sy salah paham.. iya klo diredirect langsung nanti tinggal copy URLnya download counter gak bakal kehitung.. kalo untuk cara lain biasanya ada sih library untuk force download, tapi ujung2nya ya pasti streaming begini, baca awal file sampe EOF.. trus ganti header.. Hmm saya juga belum kepikiran bagaimana Rapidshare dan semacamnya bisa download file berukuran GB ya.. nanti saya cari tau deh mas


  • Please LOGIN before if you want to give the comment.