Committing a work on progress on improvements to the new upload code. Still needs...
[lhc/web/wiklou.git] / includes / UploadFromUrl.php
1 <?php
2
3
4 class UploadFromUrl extends UploadBase {
5 static function isAllowed( $user ) {
6 if( !$user->isAllowed( 'upload_by_url' ) )
7 return 'upload_by_url';
8 return parent::isAllowed( $user );
9 }
10 static function isEnabled() {
11 global $wgAllowCopyUploads;
12 return $wgAllowCopyUploads && parent::isEnabled();
13 }
14
15 function initialize( $name, $url ) {
16 global $wgTmpDirectory;
17 $local_file = tempnam( $wgTmpDirectory, 'WEBUPLOAD' );
18 $this-initialize( $name, $local_file, 0, true );
19
20 $this->mUrl = trim( $url );
21 }
22
23 function verifyUpload() {
24 if( stripos($this->mUrl, 'http://') !== 0 && stripos($this->mUrl, 'ftp://') !== 0 ) {
25 return array(
26 'status' => self::BEFORE_PROCESSING,
27 'error' => 'upload-proto-error',
28 );
29 }
30 $res = $this->curlCopy();
31 if( $res !== true ) {
32 return array(
33 'status' => self::BEFORE_PROCESSING,
34 'error' => $res,
35 );
36 }
37 return parent::verifyUpload();
38 }
39
40 /**
41 * Safe copy from URL
42 * Returns true if there was an error, false otherwise
43 */
44 private function curlCopy() {
45 global $wgUser, $wgOut;
46
47 # Open temporary file
48 $this->mCurlDestHandle = @fopen( $this->mTempPath, "wb" );
49 if( $this->mCurlDestHandle === false ) {
50 # Could not open temporary file to write in
51 return 'upload-file-error';
52 }
53
54 $ch = curl_init();
55 curl_setopt( $ch, CURLOPT_HTTP_VERSION, 1.0); # Probably not needed, but apparently can work around some bug
56 curl_setopt( $ch, CURLOPT_TIMEOUT, 10); # 10 seconds timeout
57 curl_setopt( $ch, CURLOPT_LOW_SPEED_LIMIT, 512); # 0.5KB per second minimum transfer speed
58 curl_setopt( $ch, CURLOPT_URL, $this->mUrl);
59 curl_setopt( $ch, CURLOPT_WRITEFUNCTION, array( $this, 'uploadCurlCallback' ) );
60 curl_exec( $ch );
61 $error = curl_errno( $ch );
62 curl_close( $ch );
63
64 fclose( $this->mCurlDestHandle );
65 unset( $this->mCurlDestHandle );
66
67 if( $error )
68 return "upload-curl-error$errornum";
69
70 return true;
71 }
72
73 /**
74 * Callback function for CURL-based web transfer
75 * Write data to file unless we've passed the length limit;
76 * if so, abort immediately.
77 * @access private
78 */
79 function uploadCurlCallback( $ch, $data ) {
80 global $wgMaxUploadSize;
81 $length = strlen( $data );
82 $this->mFileSize += $length;
83 if( $this->mFileSize > $wgMaxUploadSize ) {
84 return 0;
85 }
86 fwrite( $this->mCurlDestHandle, $data );
87 return $length;
88 }
89 }