public function testCloseStream() { //ensure all basic stream stuff works $sourceFile = OC::$SERVERROOT . '/tests/data/lorem.txt'; $tmpFile = \OC::$server->getTempManager()->getTemporaryFile('.txt'); $file = 'close://' . $tmpFile; $this->assertTrue(file_exists($file)); file_put_contents($file, file_get_contents($sourceFile)); $this->assertEquals(file_get_contents($sourceFile), file_get_contents($file)); unlink($file); clearstatcache(); $this->assertFalse(file_exists($file)); //test callback $tmpFile = \OC::$server->getTempManager()->getTemporaryFile('.txt'); $file = 'close://' . $tmpFile; $actual = false; $callback = function ($path) use(&$actual) { $actual = $path; }; \OC\Files\Stream\Close::registerCallback($tmpFile, $callback); $fh = fopen($file, 'w'); fwrite($fh, 'asd'); fclose($fh); $this->assertSame($tmpFile, $actual); }
public function testCloseStream() { //ensure all basic stream stuff works $sourceFile = OC::$SERVERROOT . '/tests/data/lorem.txt'; $tmpFile = OC_Helper::TmpFile('.txt'); $file = 'close://' . $tmpFile; $this->assertTrue(file_exists($file)); file_put_contents($file, file_get_contents($sourceFile)); $this->assertEquals(file_get_contents($sourceFile), file_get_contents($file)); unlink($file); clearstatcache(); $this->assertFalse(file_exists($file)); //test callback $tmpFile = OC_Helper::TmpFile('.txt'); $file = 'close://' . $tmpFile; \OC\Files\Stream\Close::registerCallback($tmpFile, array('Test_StreamWrappers', 'closeCallBack')); $fh = fopen($file, 'w'); fwrite($fh, 'asd'); try { fclose($fh); $this->fail('Expected exception'); } catch (Exception $e) { $path = $e->getMessage(); $this->assertEquals($path, $tmpFile); } }
public function fopen($path, $mode) { $path = $this->normalizePath($path); switch ($mode) { case 'r': case 'rb': try { $c = $this->getContainer(); $streamFactory = new \Guzzle\Stream\PhpStreamRequestFactory(); $streamInterface = $streamFactory->fromRequest($c->getClient()->get($c->getUrl($path))); $streamInterface->rewind(); $stream = $streamInterface->getStream(); stream_context_set_option($stream, 'swift', 'content', $streamInterface); if (!strrpos($streamInterface->getMetaData('wrapper_data')[0], '404 Not Found')) { return $stream; } return false; } catch (\Guzzle\Http\Exception\BadResponseException $e) { \OCP\Util::writeLog('files_external', $e->getMessage(), \OCP\Util::ERROR); return false; } case 'w': case 'wb': case 'a': case 'ab': case 'r+': case 'w+': case 'wb+': case 'a+': case 'x': case 'x+': case 'c': case 'c+': if (strrpos($path, '.') !== false) { $ext = substr($path, strrpos($path, '.')); } else { $ext = ''; } $tmpFile = \OCP\Files::tmpFile($ext); \OC\Files\Stream\Close::registerCallback($tmpFile, array($this, 'writeBack')); // Fetch existing file if required if ($mode[0] !== 'w' && $this->file_exists($path)) { if ($mode[0] === 'x') { // File cannot already exist return false; } $source = $this->fopen($path, 'r'); file_put_contents($tmpFile, $source); // Seek to end if required if ($mode[0] === 'a') { fseek($tmpFile, 0, SEEK_END); } } self::$tmpFiles[$tmpFile] = $path; return fopen('close://' . $tmpFile, $mode); } }
public function fopen($path, $mode) { $path = $this->normalizePath($path); switch ($mode) { case 'r': case 'rb': $stat = $this->stat($path); if (is_array($stat)) { try { return $this->objectStore->readObject($this->getURN($stat['fileid'])); } catch (\Exception $ex) { \OCP\Util::writeLog('objectstore', 'Could not get object: ' . $ex->getMessage(), \OCP\Util::ERROR); return false; } } else { return false; } case 'w': case 'wb': case 'a': case 'ab': case 'r+': case 'w+': case 'wb+': case 'a+': case 'x': case 'x+': case 'c': case 'c+': if (strrpos($path, '.') !== false) { $ext = substr($path, strrpos($path, '.')); } else { $ext = ''; } $tmpFile = \OC::$server->getTempManager()->getTemporaryFile($ext); \OC\Files\Stream\Close::registerCallback($tmpFile, array($this, 'writeBack')); if ($this->file_exists($path)) { $source = $this->fopen($path, 'r'); file_put_contents($tmpFile, $source); } self::$tmpFiles[$tmpFile] = $path; return fopen('close://' . $tmpFile, $mode); } return false; }
/** * get a file handler * * @param string $path * @param string $mode * @return resource */ function getStream($path, $mode) { if (strrpos($path, '.') !== false) { $ext = substr($path, strrpos($path, '.')); } else { $ext = ''; } $tmpFile = \OCP\Files::tmpFile($ext); if ($this->fileExists($path)) { $this->extractFile($path, $tmpFile); } elseif ($mode == 'r' or $mode == 'rb') { return false; } if ($mode == 'r' or $mode == 'rb') { return fopen($tmpFile, $mode); } else { \OC\Files\Stream\Close::registerCallback($tmpFile, array($this, 'writeBack')); self::$tempFiles[$tmpFile] = $path; return fopen('close://' . $tmpFile, $mode); } }
/** {@inheritdoc} */ public function fopen($path, $mode) { $this->init(); $path = $this->cleanPath($path); switch ($mode) { case 'r': case 'rb': try { $response = $this->httpClientService->newClient()->get($this->createBaseUri() . $this->encodePath($path), ['auth' => [$this->user, $this->password], 'stream' => true]); } catch (RequestException $e) { if ($e->getResponse() instanceof ResponseInterface && $e->getResponse()->getStatusCode() === 404) { return false; } else { throw $e; } } if ($response->getStatusCode() !== Http::STATUS_OK) { if ($response->getStatusCode() === Http::STATUS_LOCKED) { throw new \OCP\Lock\LockedException($path); } else { Util::writeLog("webdav client", 'Guzzle get returned status code ' . $response->getStatusCode(), Util::ERROR); } } return $response->getBody(); case 'w': case 'wb': case 'a': case 'ab': case 'r+': case 'w+': case 'wb+': case 'a+': case 'x': case 'x+': case 'c': case 'c+': //emulate these $tempManager = \OC::$server->getTempManager(); if (strrpos($path, '.') !== false) { $ext = substr($path, strrpos($path, '.')); } else { $ext = ''; } if ($this->file_exists($path)) { if (!$this->isUpdatable($path)) { return false; } if ($mode === 'w' or $mode === 'w+') { $tmpFile = $tempManager->getTemporaryFile($ext); } else { $tmpFile = $this->getCachedFile($path); } } else { if (!$this->isCreatable(dirname($path))) { return false; } $tmpFile = $tempManager->getTemporaryFile($ext); } Close::registerCallback($tmpFile, array($this, 'writeBack')); self::$tempFiles[$tmpFile] = $path; return fopen('close://' . $tmpFile, $mode); } }
public function fopen($path, $mode) { $path = $this->root . $path; switch ($mode) { case 'r': case 'rb': try { // slashes need to stay $encodedPath = str_replace('%2F', '/', rawurlencode(trim($path, '/'))); $downloadUrl = 'https://api-content.dropbox.com/1/files/auto/' . $encodedPath; $headers = $this->oauth->getOAuthHeader($downloadUrl, [], 'GET'); $client = \OC::$server->getHTTPClientService()->newClient(); try { $response = $client->get($downloadUrl, ['headers' => $headers, 'stream' => true]); } catch (RequestException $e) { if (!is_null($e->getResponse())) { if ($e->getResponse()->getStatusCode() === 404) { return false; } else { throw $e; } } else { throw $e; } } $handle = $response->getBody(); return RetryWrapper::wrap($handle); } catch (\Exception $exception) { \OCP\Util::writeLog('files_external', $exception->getMessage(), \OCP\Util::ERROR); return false; } case 'w': case 'wb': case 'a': case 'ab': case 'r+': case 'w+': case 'wb+': case 'a+': case 'x': case 'x+': case 'c': case 'c+': if (strrpos($path, '.') !== false) { $ext = substr($path, strrpos($path, '.')); } else { $ext = ''; } $tmpFile = \OCP\Files::tmpFile($ext); \OC\Files\Stream\Close::registerCallback($tmpFile, array($this, 'writeBack')); if ($this->file_exists($path)) { $source = $this->fopen($path, 'r'); file_put_contents($tmpFile, $source); } self::$tempFiles[$tmpFile] = $path; return fopen('close://' . $tmpFile, $mode); } return false; }
public function fopen($path, $mode) { $this->init(); switch ($mode) { case 'r': case 'rb': $obj = $this->getObject($path); if (is_null($obj)) { return false; } $fp = fopen('php://temp', 'r+'); $obj->stream($fp); rewind($fp); return $fp; case 'w': case 'wb': case 'a': case 'ab': case 'r+': case 'w+': case 'wb+': case 'a+': case 'x': case 'x+': case 'c': case 'c+': $tmpFile = $this->getTmpFile($path); \OC\Files\Stream\Close::registerCallback($tmpFile, array($this, 'writeBack')); self::$tempFiles[$tmpFile] = $path; return fopen('close://' . $tmpFile, $mode); } }
public function fopen($path, $mode) { $path = $this->normalizePath($path); switch ($mode) { case 'r': case 'rb': $tmpFile = \OC_Helper::tmpFile(); self::$tmpFiles[$tmpFile] = $path; try { $result = $this->connection->getObject(array('Bucket' => $this->bucket, 'Key' => $this->cleanKey($path), 'SaveAs' => $tmpFile)); } catch (S3Exception $e) { \OCP\Util::writeLog('files_external', $e->getMessage(), \OCP\Util::ERROR); return false; } return fopen($tmpFile, 'r'); case 'w': case 'wb': case 'a': case 'ab': case 'r+': case 'w+': case 'wb+': case 'a+': case 'x': case 'x+': case 'c': case 'c+': if (strrpos($path, '.') !== false) { $ext = substr($path, strrpos($path, '.')); } else { $ext = ''; } $tmpFile = \OC_Helper::tmpFile($ext); \OC\Files\Stream\Close::registerCallback($tmpFile, array($this, 'writeBack')); if ($this->file_exists($path)) { $source = $this->fopen($path, 'r'); file_put_contents($tmpFile, $source); } self::$tmpFiles[$tmpFile] = $path; return fopen('close://' . $tmpFile, $mode); } return false; }
public function fopen($path, $mode) { switch ($mode) { case 'r': case 'rb': case 'w': case 'wb': case 'a': case 'ab': //these are supported by the wrapper $context = stream_context_create(array('ftp' => array('overwrite' => true))); return fopen($this->constructUrl($path), $mode, false, $context); case 'r+': case 'w+': case 'wb+': case 'a+': case 'x': case 'x+': case 'c': case 'c+': //emulate these if (strrpos($path, '.') !== false) { $ext = substr($path, strrpos($path, '.')); } else { $ext = ''; } $tmpFile = \OCP\Files::tmpFile($ext); \OC\Files\Stream\Close::registerCallback($tmpFile, array($this, 'writeBack')); if ($this->file_exists($path)) { $this->getFile($path, $tmpFile); } self::$tempFiles[$tmpFile] = $path; return fopen('close://' . $tmpFile, $mode); } return false; }
public function fopen($path, $mode) { try { $absPath = $this->absPath($path); switch ($mode) { case 'r': case 'rb': if (!$this->file_exists($path)) { return false; } if (strrpos($path, '.') !== false) { $ext = substr($path, strrpos($path, '.')); } else { $ext = ''; } $tmp = \OC_Helper::tmpFile($ext); $this->getFile($absPath, $tmp); return fopen($tmp, $mode); case 'w': case 'wb': case 'a': case 'ab': case 'r+': case 'w+': case 'wb+': case 'a+': case 'x': case 'x+': case 'c': case 'c+': if (strrpos($path, '.') !== false) { $ext = substr($path, strrpos($path, '.')); } else { $ext = ''; } $tmpFile = \OC_Helper::tmpFile($ext); \OC\Files\Stream\Close::registerCallback($tmpFile, array($this, 'writeBack')); if ($this->file_exists($path)) { $this->getFile($absPath, $tmpFile); } self::$tempFiles[$tmpFile] = $absPath; return fopen('close://' . $tmpFile, $mode); } } catch (\Exception $e) { } return false; }
public function fopen($path, $mode) { $this->init(); $path = $this->cleanPath($path); switch ($mode) { case 'r': case 'rb': if (!$this->file_exists($path)) { return false; } //straight up curl instead of sabredav here, sabredav put's the entire get result in memory $curl = curl_init(); $fp = fopen('php://temp', 'r+'); curl_setopt($curl, CURLOPT_USERPWD, $this->user . ':' . $this->password); curl_setopt($curl, CURLOPT_URL, $this->createBaseUri() . str_replace(' ', '%20', $path)); curl_setopt($curl, CURLOPT_FILE, $fp); curl_setopt($curl, CURLOPT_FOLLOWLOCATION, true); curl_exec($curl); curl_close($curl); rewind($fp); return $fp; case 'w': case 'wb': case 'a': case 'ab': case 'r+': case 'w+': case 'wb+': case 'a+': case 'x': case 'x+': case 'c': case 'c+': //emulate these if (strrpos($path, '.') !== false) { $ext = substr($path, strrpos($path, '.')); } else { $ext = ''; } $tmpFile = \OCP\Files::tmpFile($ext); \OC\Files\Stream\Close::registerCallback($tmpFile, array($this, 'writeBack')); if ($this->file_exists($path)) { $this->getFile($path, $tmpFile); } self::$tempFiles[$tmpFile] = $path; return fopen('close://' . $tmpFile, $mode); } }
public function fopen($path, $mode) { $pos = strrpos($path, '.'); if ($pos !== false) { $ext = substr($path, $pos); } else { $ext = ''; } switch ($mode) { case 'r': case 'rb': $file = $this->getDriveFile($path); if ($file) { $exportLinks = $file->getExportLinks(); $mimetype = $this->getMimeType($path); $downloadUrl = null; if ($exportLinks && isset($exportLinks[$mimetype])) { $downloadUrl = $exportLinks[$mimetype]; } else { $downloadUrl = $file->getDownloadUrl(); } if (isset($downloadUrl)) { $request = new \Google_Http_Request($downloadUrl, 'GET', null, null); $httpRequest = $this->client->getAuth()->sign($request); // the library's service doesn't support streaming, so we use Guzzle instead $client = \OC::$server->getHTTPClientService()->newClient(); try { $tmpFile = \OC::$server->getTempManager()->getTemporaryFile($ext); $client->get($downloadUrl, ['headers' => $httpRequest->getRequestHeaders(), 'save_to' => $tmpFile]); } catch (RequestException $e) { if (!is_null($e->getResponse())) { if ($e->getResponse()->getStatusCode() === 404) { return false; } else { throw $e; } } else { throw $e; } } return fopen($tmpFile, 'r'); } } return false; case 'w': case 'wb': case 'a': case 'ab': case 'r+': case 'w+': case 'wb+': case 'a+': case 'x': case 'x+': case 'c': case 'c+': $tmpFile = \OCP\Files::tmpFile($ext); \OC\Files\Stream\Close::registerCallback($tmpFile, array($this, 'writeBack')); if ($this->file_exists($path)) { $source = $this->fopen($path, 'rb'); file_put_contents($tmpFile, $source); } self::$tempFiles[$tmpFile] = $path; return fopen('close://' . $tmpFile, $mode); } }
/** * get a file handler * @param string $path * @param string $mode * @return resource */ function getStream($path, $mode) { if ($mode == 'r' or $mode == 'rb') { return $this->zip->getStream($path); } else { //since we can't directly get a writable stream, //make a temp copy of the file and put it back //in the archive when the stream is closed if (strrpos($path, '.') !== false) { $ext = substr($path, strrpos($path, '.')); } else { $ext = ''; } $tmpFile = \OCP\Files::tmpFile($ext); \OC\Files\Stream\Close::registerCallback($tmpFile, array($this, 'writeBack')); if ($this->fileExists($path)) { $this->extractFile($path, $tmpFile); } self::$tempFiles[$tmpFile] = $path; return fopen('close://' . $tmpFile, $mode); } }
public function fopen($path, $mode) { switch ($mode) { case 'r': case 'rb': $entry = $this->getResource($path); if ($entry) { $extension = $this->getExtension($entry); $downloadUri = $entry->getElementsByTagName('content')->item(0)->getAttribute('src'); // TODO Non-native documents don't need these additional parameters $downloadUri .= '&exportFormat=' . $extension . '&format=' . $extension; $tmpFile = $this->sendRequest($downloadUri, 'GET', null, null, true); return fopen($tmpFile, 'r'); } case 'w': case 'wb': case 'a': case 'ab': case 'r+': case 'w+': case 'wb+': case 'a+': case 'x': case 'x+': case 'c': case 'c+': if (strrpos($path, '.') !== false) { $ext = substr($path, strrpos($path, '.')); } else { $ext = ''; } $tmpFile = \OC_Helper::tmpFile($ext); \OC\Files\Stream\Close::registerCallback($tmpFile, array($this, 'writeBack')); if ($this->file_exists($path)) { $source = $this->fopen($path, 'r'); file_put_contents($tmpFile, $source); } self::$tempFiles[$tmpFile] = $path; return fopen('close://' . $tmpFile, $mode); } return false; }
/** {@inheritdoc} */ public function fopen($path, $mode) { $this->init(); $path = $this->cleanPath($path); switch ($mode) { case 'r': case 'rb': if (!$this->file_exists($path)) { return false; } //straight up curl instead of sabredav here, sabredav put's the entire get result in memory $curl = curl_init(); $fp = fopen('php://temp', 'r+'); curl_setopt($curl, CURLOPT_USERPWD, $this->user . ':' . $this->password); curl_setopt($curl, CURLOPT_URL, $this->createBaseUri() . $this->encodePath($path)); curl_setopt($curl, CURLOPT_FILE, $fp); curl_setopt($curl, CURLOPT_FOLLOWLOCATION, true); if (defined('CURLOPT_PROTOCOLS')) { curl_setopt($curl, CURLOPT_PROTOCOLS, CURLPROTO_HTTP | CURLPROTO_HTTPS); } if (defined('CURLOPT_REDIR_PROTOCOLS')) { curl_setopt($curl, CURLOPT_REDIR_PROTOCOLS, CURLPROTO_HTTP | CURLPROTO_HTTPS); } if ($this->secure === true) { curl_setopt($curl, CURLOPT_SSL_VERIFYPEER, true); curl_setopt($curl, CURLOPT_SSL_VERIFYHOST, 2); if ($this->certPath) { curl_setopt($curl, CURLOPT_CAINFO, $this->certPath); } } curl_exec($curl); $statusCode = curl_getinfo($curl, CURLINFO_HTTP_CODE); if ($statusCode !== 200) { Util::writeLog("webdav client", 'curl GET ' . curl_getinfo($curl, CURLINFO_EFFECTIVE_URL) . ' returned status code ' . $statusCode, Util::ERROR); } curl_close($curl); rewind($fp); return $fp; case 'w': case 'wb': case 'a': case 'ab': case 'r+': case 'w+': case 'wb+': case 'a+': case 'x': case 'x+': case 'c': case 'c+': //emulate these if (strrpos($path, '.') !== false) { $ext = substr($path, strrpos($path, '.')); } else { $ext = ''; } if ($this->file_exists($path)) { if (!$this->isUpdatable($path)) { return false; } $tmpFile = $this->getCachedFile($path); } else { if (!$this->isCreatable(dirname($path))) { return false; } $tmpFile = Files::tmpFile($ext); } Close::registerCallback($tmpFile, array($this, 'writeBack')); self::$tempFiles[$tmpFile] = $path; return fopen('close://' . $tmpFile, $mode); } }
public function fopen($path, $mode) { $path = $this->root . $path; switch ($mode) { case 'r': case 'rb': $tmpFile = \OCP\Files::tmpFile(); try { $data = $this->dropbox->getFile($path); file_put_contents($tmpFile, $data); return fopen($tmpFile, 'r'); } catch (\Exception $exception) { \OCP\Util::writeLog('files_external', $exception->getMessage(), \OCP\Util::ERROR); return false; } case 'w': case 'wb': case 'a': case 'ab': case 'r+': case 'w+': case 'wb+': case 'a+': case 'x': case 'x+': case 'c': case 'c+': if (strrpos($path, '.') !== false) { $ext = substr($path, strrpos($path, '.')); } else { $ext = ''; } $tmpFile = \OCP\Files::tmpFile($ext); \OC\Files\Stream\Close::registerCallback($tmpFile, array($this, 'writeBack')); if ($this->file_exists($path)) { $source = $this->fopen($path, 'r'); file_put_contents($tmpFile, $source); } self::$tempFiles[$tmpFile] = $path; return fopen('close://' . $tmpFile, $mode); } return false; }
public function fopen($path, $mode) { $pos = strrpos($path, '.'); if ($pos !== false) { $ext = substr($path, $pos); } else { $ext = ''; } switch ($mode) { case 'r': case 'rb': $file = $this->getDriveFile($path); if ($file) { $exportLinks = $file->getExportLinks(); $mimetype = $this->getMimeType($path); $downloadUrl = null; if ($exportLinks && isset($exportLinks[$mimetype])) { $downloadUrl = $exportLinks[$mimetype]; } else { $downloadUrl = $file->getDownloadUrl(); } if (isset($downloadUrl)) { $request = new \Google_HttpRequest($downloadUrl, 'GET', null, null); $httpRequest = \Google_Client::$io->authenticatedRequest($request); if ($httpRequest->getResponseHttpCode() == 200) { $tmpFile = \OC_Helper::tmpFile($ext); $data = $httpRequest->getResponseBody(); file_put_contents($tmpFile, $data); return fopen($tmpFile, $mode); } } } return false; case 'w': case 'wb': case 'a': case 'ab': case 'r+': case 'w+': case 'wb+': case 'a+': case 'x': case 'x+': case 'c': case 'c+': $tmpFile = \OC_Helper::tmpFile($ext); \OC\Files\Stream\Close::registerCallback($tmpFile, array($this, 'writeBack')); if ($this->file_exists($path)) { $source = $this->fopen($path, 'rb'); file_put_contents($tmpFile, $source); } self::$tempFiles[$tmpFile] = $path; return fopen('close://' . $tmpFile, $mode); } }
public function fopen($path, $mode) { $path = $this->normalizePath($path); switch ($mode) { case 'r': case 'rb': $tmpFile = \OC_Helper::tmpFile(); self::$tmpFiles[$tmpFile] = $path; try { $object = $this->container->getObject($path); } catch (ClientErrorResponseException $e) { \OCP\Util::writeLog('files_external', $e->getMessage(), \OCP\Util::ERROR); return false; } catch (Exception\ObjectNotFoundException $e) { \OCP\Util::writeLog('files_external', $e->getMessage(), \OCP\Util::ERROR); return false; } try { $objectContent = $object->getContent(); $objectContent->rewind(); $stream = $objectContent->getStream(); file_put_contents($tmpFile, $stream); } catch (Exceptions\IOError $e) { \OCP\Util::writeLog('files_external', $e->getMessage(), \OCP\Util::ERROR); return false; } return fopen($tmpFile, 'r'); case 'w': case 'wb': case 'a': case 'ab': case 'r+': case 'w+': case 'wb+': case 'a+': case 'x': case 'x+': case 'c': case 'c+': if (strrpos($path, '.') !== false) { $ext = substr($path, strrpos($path, '.')); } else { $ext = ''; } $tmpFile = \OC_Helper::tmpFile($ext); \OC\Files\Stream\Close::registerCallback($tmpFile, array($this, 'writeBack')); if ($this->file_exists($path)) { $source = $this->fopen($path, 'r'); file_put_contents($tmpFile, $source); } self::$tmpFiles[$tmpFile] = $path; return fopen('close://' . $tmpFile, $mode); } }
public function fopen($path, $mode) { switch ($mode) { case 'r': case 'rb': $tmpFile = \OC_Helper::tmpFile(); $handle = fopen($tmpFile, 'w'); $response = $this->s3->get_object($this->bucket, $path, array('fileDownload' => $handle)); if ($response->isOK()) { return fopen($tmpFile, 'r'); } break; case 'w': case 'wb': case 'a': case 'ab': case 'r+': case 'w+': case 'wb+': case 'a+': case 'x': case 'x+': case 'c': case 'c+': if (strrpos($path, '.') !== false) { $ext = substr($path, strrpos($path, '.')); } else { $ext = ''; } $tmpFile = \OC_Helper::tmpFile($ext); \OC\Files\Stream\Close::registerCallback($tmpFile, array($this, 'writeBack')); if ($this->file_exists($path)) { $source = $this->fopen($path, 'r'); file_put_contents($tmpFile, $source); } self::$tempFiles[$tmpFile] = $path; return fopen('close://' . $tmpFile, $mode); } return false; }