X-Git-Url: https://git.cyclocoop.org/?a=blobdiff_plain;f=includes%2Fupload%2FUploadFromUrl.php;h=42b382750f5b61fa7d4139718336dee59f058b9b;hb=f8a2f36719ead8e5a5741d12f8fd658a7bb2a51c;hp=dce9ae3927741e3117d2a4b819f9f8bd6ec3594b;hpb=e1f61b0a7824b261ef05cda6b8591c017c632c00;p=lhc%2Fweb%2Fwiklou.git diff --git a/includes/upload/UploadFromUrl.php b/includes/upload/UploadFromUrl.php index dce9ae3927..42b382750f 100644 --- a/includes/upload/UploadFromUrl.php +++ b/includes/upload/UploadFromUrl.php @@ -1,23 +1,23 @@ isAllowed( 'upload_by_url' ) ) + if ( !$user->isAllowed( 'upload_by_url' ) ) return 'upload_by_url'; return parent::isAllowed( $user ); } @@ -33,59 +33,22 @@ class UploadFromUrl extends UploadBase { /** * Entry point for API upload - * @return bool true on success - */ - public function initialize( $name, $url, $comment, $watchList, $ignoreWarn ) { - global $wgUser; - - if( !Http::isValidURI( $url ) ) { - return Status::newFatal( 'http-invalid-url' ); - } - $params = array( - "userName" => $wgUser->getName(), - "userID" => $wgUser->getID(), - "url" => trim( $url ), - "timestamp" => wfTimestampNow(), - "comment" => $comment, - "watchlist" => $watchList, - "ignorewarnings" => $ignoreWarn); - - $title = Title::newFromText( $name ); - /* // Check whether the user has the appropriate permissions to upload anyway */ - /* $permission = $this->isAllowed( $wgUser ); */ - - /* if ( $permission !== true ) { */ - /* if ( !$wgUser->isLoggedIn() ) { */ - /* return Status::newFatal( 'uploadnologintext' ); */ - /* } else { */ - /* return Status::newFatal( 'badaccess-groups' ); */ - /* } */ - /* } */ - - /* $permErrors = $this->verifyPermissions( $wgUser ); */ - /* if ( $permErrors !== true ) { */ - /* return Status::newFatal( 'badaccess-groups' ); */ - /* } */ - - - $job = new UploadFromUrlJob( $title, $params ); - return $job->insert(); - } - - /** - * Initialize a queued download - * @param $job Job + * + * @param $name string + * @param $url string + * @param $async mixed Whether the download should be performed + * asynchronous. False for synchronous, async or async-leavemessage for + * asynchronous download. */ - public function initializeFromJob( $job ) { - global $wgTmpDirectory; - - $this->mUrl = $job->params['url']; - $this->mTempPath = tempnam( $wgTmpDirectory, 'COPYUPLOAD' ); - $this->mDesiredDestName = $job->title; - $this->comment = $job->params['comment']; - $this->watchList = $job->params['watchlist']; - $this->ignoreWarnings = $job->params['ignorewarnings']; - $this->getTitle(); + public function initialize( $name, $url, $async = false ) { + global $wgAllowAsyncCopyUploads; + + $this->mUrl = $url; + $this->mAsync = $wgAllowAsyncCopyUploads ? $async : false; + + $tempPath = $this->mAsync ? null : $this->makeTemporaryFile(); + # File size and removeTempFile will be filled in later + $this->initializePathInfo( $name, $tempPath, 0, false ); } /** @@ -94,21 +57,19 @@ class UploadFromUrl extends UploadBase { */ public function initializeFromRequest( &$request ) { $desiredDestName = $request->getText( 'wpDestFile' ); - if( !$desiredDestName ) + if ( !$desiredDestName ) $desiredDestName = $request->getText( 'wpUploadFileURL' ); return $this->initialize( $desiredDestName, $request->getVal( 'wpUploadFileURL' ), - $request->getVal( 'wpUploadDescription' ), - $request->getVal( 'wpWatchThis' ), - $request->getVal( 'wpIgnoreWarnings' ) + false ); } /** * @param $request Object: WebRequest object */ - public static function isValidRequest( $request ){ + public static function isValidRequest( $request ) { global $wgUser; $url = $request->getVal( 'wpUploadFileURL' ); @@ -116,59 +77,133 @@ class UploadFromUrl extends UploadBase { && Http::isValidURI( $url ) && $wgUser->isAllowed( 'upload_by_url' ); } + + public function fetchFile() { + if ( !Http::isValidURI( $this->mUrl ) ) { + return Status::newFatal( 'http-invalid-url' ); + } + + if ( !$this->mAsync ) { + return $this->reallyFetchFile(); + } + return Status::newGood(); + } + /** + * Create a new temporary file in the URL subdirectory of wfTempDir(). + * + * @return string Path to the file + */ + protected function makeTemporaryFile() { + return tempnam( wfTempDir(), 'URL' ); + } + /** + * Save the result of a HTTP request to the temporary file + * + * @param $req HttpRequest + * @return Status + */ private function saveTempFile( $req ) { - $filename = tempnam( wfTempDir(), 'URL' ); - if ( $filename === false ) { + if ( $this->mTempPath === false ) { return Status::newFatal( 'tmp-create-error' ); } - if ( file_put_contents( $filename, $req->getContent() ) === false ) { + if ( file_put_contents( $this->mTempPath, $req->getContent() ) === false ) { return Status::newFatal( 'tmp-write-error' ); } - $this->mTempPath = $filename; - $this->mFileSize = filesize( $filename ); + $this->mFileSize = filesize( $this->mTempPath ); return Status::newGood(); } - - public function doUpload() { - global $wgUser; - - $req = HttpRequest::factory($this->mUrl); + /** + * Download the file, save it to the temporary file and update the file + * size and set $mRemoveTempFile to true. + */ + protected function reallyFetchFile() { + $req = HttpRequest::factory( $this->mUrl ); $status = $req->execute(); - if( !$status->isOk() ) { + if ( !$status->isOk() ) { return $status; } $status = $this->saveTempFile( $req ); - $this->mRemoveTempFile = true; - - if( !$status->isOk() ) { + if ( !$status->isGood() ) { return $status; } + $this->mRemoveTempFile = true; - $v = $this->verifyUpload(); - if( $v['status'] !== UploadBase::OK ) { - return $this->convertVerifyErrorToStatus( $v['status'], $v['details'] ); - } - - // This has to come from API - /* $warnings = $this->checkForWarnings(); */ - /* if( isset($warnings) ) return $warnings; */ + return $status; + } - $file = $this->getLocalFile(); - // This comes from ApiBase - /* $watch = $this->getWatchlistValue( $this->mParams['watchlist'], $file->getTitle() ); */ + /** + * Wrapper around the parent function in order to defer verifying the + * upload until the file really has been fetched. + */ + public function verifyUpload() { + if ( $this->mAsync ) { + return array( 'status' => self::OK ); + } + return parent::verifyUpload(); + } - if ( !$status->isGood() ) { + /** + * Wrapper around the parent function in order to defer checking warnings + * until the file really has been fetched. + */ + public function checkWarnings() { + if ( $this->mAsync ) { + $this->mIgnoreWarnings = false; + return array(); + } + return parent::checkWarnings(); + } + + /** + * Wrapper around the parent function in order to defer checking protection + * until we are sure that the file can actually be uploaded + */ + public function verifyPermissions( $user ) { + if ( $this->mAsync ) { + return true; + } + return parent::verifyPermissions( $user ); + } + + /** + * Wrapper around the parent function in order to defer uploading to the + * job queue for asynchronous uploads + */ + public function performUpload( $comment, $pageText, $watch, $user ) { + if ( $this->mAsync ) { + $sessionKey = $this->insertJob( $comment, $pageText, $watch, $user ); + + $status = new Status; + $status->error( 'async', $sessionKey ); return $status; } + + return parent::performUpload( $comment, $pageText, $watch, $user ); + } - $status = $this->getLocalFile()->upload( $this->mTempPath, $this->comment, - $this->comment, File::DELETE_SOURCE, $this->mFileProps, false, $wgUser ); - - return $status; + + protected function insertJob( $comment, $pageText, $watch, $user ) { + $sessionKey = $this->getSessionKey(); + $job = new UploadFromUrlJob( $this->getTitle(), array( + 'url' => $this->mUrl, + 'comment' => $comment, + 'pageText' => $pageText, + 'watch' => $watch, + 'userName' => $user->getName(), + 'leaveMessage' => $this->mAsync == 'async-leavemessage', + 'ignoreWarnings' => $this->mIgnoreWarnings, + 'sessionId' => session_id(), + 'sessionKey' => $sessionKey, + ) ); + $job->initializeSessionData(); + $job->insert(); + return $sessionKey; } + + }