Page 1 of 2 12 Last
  • Jump to page:
    #1
  1. No Profile Picture
    Contributing User
    Devshed Newbie (0 - 499 posts)

    Join Date
    Jan 2005
    Posts
    58
    Rep Power
    14

    Force client to download video file instead of streaming


    I have a slight problem. I allow people to upload video files ( avi, mpg and wmv) to the server. But when they click the link to be taken to the file (filename.php?dowload=ID) which just uses header("Location:") to direct the client to download the file. avi files bring up the download box, but wmv and mpg just stream in the browser. How can I force downloading on these files?
  2. #2
  3. Forgotten Moderator
    Devshed Supreme Being (6500+ posts)

    Join Date
    Mar 2007
    Location
    Washington, USA
    Posts
    16,052
    Rep Power
    9616
    We've got a great search engine for this site. It's perfect for commonly-asked questions like yours.

    Comments on this post

    • sephers181 agrees
  4. #3
  5. No Profile Picture
    Registered User
    Devshed Newbie (0 - 499 posts)

    Join Date
    Mar 2008
    Posts
    1
    Rep Power
    0
    Originally Posted by o2pb
    I have a slight problem. I allow people to upload video files ( avi, mpg and wmv) to the server. But when they click the link to be taken to the file (filename.php?dowload=ID) which just uses header("Location:") to direct the client to download the file. avi files bring up the download box, but wmv and mpg just stream in the browser. How can I force downloading on these files?
    I really want to help you but sorry man i am not a good webdeveloper[] So i have forwarded your request to my good web developer friend.When he will give me the code i will forward it to you on the very same day.
    ----------------------------

    Comments on this post

    • requinix disagrees : first post, eh? did you really just sign up to post that?
    • JavaNinja disagrees : can someone remove this post! I hear a scam.
  6. #4
  7. Web Developer/Musician
    Devshed Regular (2000 - 2499 posts)

    Join Date
    Nov 2004
    Location
    Tennessee Mountains
    Posts
    2,424
    Rep Power
    1034
    If you are simply re-directing to the actual file, then this isn't really a PHP issue. A web browser will play content of the types that are mapped to a specific plug-in. If there is no plug-in for that type of content, then it will display the download dialog. I'm surprised that AVI isn't mapped to anything since both Quicktime and WMP plug-ins support it, but there might be a conflict there.
    Coder Central Tutorials, news and information for the programming community at large.
  8. #5
  9. No Profile Picture
    Contributing User
    Devshed Newbie (0 - 499 posts)

    Join Date
    Jan 2005
    Posts
    58
    Rep Power
    14
    Well, there is a way to force downloading, since I know some sites force download a .jpg file, which will otherwise load in any browser.
  10. #6
  11. Web Developer/Musician
    Devshed Regular (2000 - 2499 posts)

    Join Date
    Nov 2004
    Location
    Tennessee Mountains
    Posts
    2,424
    Rep Power
    1034
    Try the following

    PHP Code:
     
     
    	function getMimeType($file)
    	{
    		$nameArr = explode('.',$file);
    		$ext = $nameArr[(count($nameArr) - 1)];
    		switch(strtolower($ext))
    		{
    			case 'pdf':
    				$type = 'application/pdf';
    				break;
    			case 'jpg':
    				$type = 'image/jpeg';
    				break;
    			case 'jpeg':
    				$type = 'image/jpeg';
    				break;
    			case 'gif':
    				$type = 'image/gif';
    				break;
    			case 'mp4':
    				$type = 'application/mpeg4-generic';
    				break;
    			case 'mp3':
    				$type = 'audio/mpeg';
    				break;
    			case 'tiff':
    				$type = 'image/tiff';
    				break;
    			case 'png':
    				$type = 'image/png';
    				break;
    			case 'csv':
    				$type = 'text/csv';
    				break;
    			case 'txt':
    				$type = 'text/plain';
    				break;
    			case 'xml':
    				$type = 'text/xml';
    				break;
    			case 'html':
    				$type = 'text/html';
    				break;
    			case 'doc':
    				$type = 'application/msword';
    				break;
    			case 'zip':
    				$type = 'application/zip';
    				break;
    			case 'jpeg2000':
    				$type = 'image/jp2';
    				break;
    			case 'rtf':
    				$type = 'text/rtf';
    				break;
    			case 'mov':
    				$type = 'video/quicktime';
    				break;
    			case 'xls':
    				$type = 'application/excel';
    				break;
    			case 'ppt':
    				$type = 'application/powerpoint';
    				break;
    			case 'wav':
    				$type = 'audio/x-wav';
    				break;
    			case 'aiff':
    				$type = 'audio/aiff';
    				break;
    			case 'mid':
    				$type = 'audio/x-midi';
    				break;
    			case 'bmp':
    				$type = 'image/bmp';
    				break;
    			case 'mpeg':
    				$type = 'video/mpeg';
    				break;
    			case 'mpg':
    				$type = 'video/mpeg';
    				break;
    			case 'avi':
    				$type = 'x-msvideo';
    				break;
    			case 'pub':
    				$type = 'application/x-mspublisher';
    				break;
    			case 'sit':
    				$type = 'application/x-stuffit';
    				break;
    			case 'tar':
    				$type = 'application/x-tar';
    				break;
    			case 'ra':
    				$type = 'audio/x-pn-realaudio';
    				break;
    			case 'ram':
    				$type = 'audio/x-pn-realaudio';
    				break;
    			case 'tsv':
    				$type = 'text/tab-separated-values';
    				break;
    			case 'asf':
    				$type = 'video/x-ms-asf';
    				break;
    			case 'wma':
    				$type = 'audio/x-ms-wma';
    				break;
    			case 'wmv':
    				$type = 'video/x-ms-wmv';
    				break;
    			case 'flv':
    				$type = 'video/x-flv';
    				break;
    			case 'swf':
    				$type = 'application/x-shockwave-flash';
    				break;
    			case 'fla':
    				$type = 'application/octet-stream';
    				break;
    			default:
    				$type = 'application/octet-stream';
    				break;
    		}
    		return $type;
    	}
     
    	function downloadHeaders($file,$filelen,$mode='I')
    	{
    		// $mode: D = force download, I = attempt inline
    		$type = getMimeType($file);
    		$mode = strtoupper($mode);
    		if(isset($_SESSION))
    		{
    			session_cache_limiter('no-cache');
    		}
    		header('pragma: cache');
    		header('pragma: public');
    		header('Cache-Control: max-age=0');
    		header("Cache-Control: private",false); // required for certain browsers 
    		header('Content-Type: '.$type);
    		header("Expires: 0");
    		if($mode == 'D')
    		{
    			header('Content-Disposition: attachment; filename='.$file);
    		}
    		else
    		{
    			header('Content-Disposition: inline; filename='.$file);
    		}
    		header("Content-Transfer-Encoding: binary");
    		header('Content-Length: '.$filelen);
    	}
     
    // use example
    // full path to file
    $filepath = '/var/www/htdocs/uploads/';
    // file name
    $filename = 'mymovie.mpg';
    // file size
    $len = filesize($filepath.$filename);
    // send headers
    downloadHeaders($filename,$len,'D');
    // send file contents
    readfile($filepath,$filename);
    exit();


    The use example is simplified in that you should check that the file exists before trying to open it, and if the script serving the files gets a file name to load rather than a database id then you will have additional security concerns.
    Coder Central Tutorials, news and information for the programming community at large.
  12. #7
  13. No Profile Picture
    Contributing User
    Devshed Newbie (0 - 499 posts)

    Join Date
    Jan 2005
    Posts
    58
    Rep Power
    14
    Looked promising, but I keep getting 0kb files with the proper file name.

    It doesnt execute past
    PHP Code:
     header('Content-Disposition: attachment; filename='.$file); 
    Last edited by o2pb; March 27th, 2008 at 08:49 PM.
  14. #8
  15. Web Developer/Musician
    Devshed Regular (2000 - 2499 posts)

    Join Date
    Nov 2004
    Location
    Tennessee Mountains
    Posts
    2,424
    Rep Power
    1034
    If you aren't getting any content then the file isn't being opened. Comment out the header portion and trouble-shoot that part.
    Coder Central Tutorials, news and information for the programming community at large.
  16. #9
  17. No Profile Picture
    Contributing User
    Devshed Newbie (0 - 499 posts)

    Join Date
    Jan 2005
    Posts
    58
    Rep Power
    14
    Originally Posted by Hammer65
    If you aren't getting any content then the file isn't being opened. Comment out the header portion and trouble-shoot that part.
    the file is being opened because Im getting the filesize just fine...
  18. #10
  19. Web Developer/Musician
    Devshed Regular (2000 - 2499 posts)

    Join Date
    Nov 2004
    Location
    Tennessee Mountains
    Posts
    2,424
    Rep Power
    1034
    But can you echo the contents into the browser window? if not, then the file isn't being opened. If filesize works then you know the path is correct, but if you don't send the headers and simply echo the contents into the browser window, you should see the raw file content.
    Coder Central Tutorials, news and information for the programming community at large.
  20. #11
  21. No Profile Picture
    Contributing User
    Devshed Newbie (0 - 499 posts)

    Join Date
    Jan 2005
    Posts
    58
    Rep Power
    14
    how can I echo the contents of a video file?


    If I dont send the headers, it simply shows it embedded in the browser window, and its not playing. The files are stores in the /videos dir and I have put the path in where appropriate.... but I can get it to work. All the files (over 100mb), maybe it doesn't have enough memory?
  22. #12
  23. Web Developer/Musician
    Devshed Regular (2000 - 2499 posts)

    Join Date
    Nov 2004
    Location
    Tennessee Mountains
    Posts
    2,424
    Rep Power
    1034
    If you are using a file that ends in .php to serve up the contents of another file (no matter what it is), and don't send any special header content, then the browser couldn't possibly know that that file is anything but HTML generated by PHP. You will simply see the source of the file as if you opened it in a plain text editor.

    PHP Code:
    $filetoopen 'mymovie.avi';
    readfile($filetoopen);
    exit(); 
    or

    PHP Code:
    $filetoopen 'mymovie.avi';
    echo(
    file_get_contents($filetoopen)); 
    or

    PHP Code:
    $filetoopen 'mymovie.avi';
    $handle fopen($filetoopen,'r');
    echo(
    fread($handle));
    fclose($handle); 
    Coder Central Tutorials, news and information for the programming community at large.
  24. #13
  25. Null Pointer Exception
    Devshed Loyal (3000 - 3499 posts)

    Join Date
    Mar 2006
    Location
    america
    Posts
    3,306
    Rep Power
    1582
    I don't think you can "force" to download instead of streaming, it all depends on what the client feels like doing. However you can use php to compress the file into a zip file or something and have them download zip files, which will be downloaded.
  26. #14
  27. Web Developer/Musician
    Devshed Regular (2000 - 2499 posts)

    Join Date
    Nov 2004
    Location
    Tennessee Mountains
    Posts
    2,424
    Rep Power
    1034
    I've used the code that I posted to do that very thing with files that normally would open in the browser. If the user-agent gets the force-download header, it will bring up the download dialog. If the OP is getting 0k files, it's not the headers that are the problem.

    The browser can't magically discover the file type and handle it appropriately. It keys off of the content-type header to determine what to do with the file. If you don't change the content-type to something else, PHP will send text/html. Easily checked using something like liveHTTP headers.
    Coder Central Tutorials, news and information for the programming community at large.
  28. #15
  29. No Profile Picture
    Contributing User
    Devshed Newbie (0 - 499 posts)

    Join Date
    Jun 2006
    Posts
    262
    Rep Power
    45
    I've used very similar code to do this, as well.

    Erm... The second-to-last line of your code:

    PHP Code:
    readfile($filepath,$filename); 
    That should be a period, rather than a comma, yes?
Page 1 of 2 12 Last
  • Jump to page:

IMN logo majestic logo threadwatch logo seochat tools logo