hello
Server : Apache System : Linux webm006.cluster103.gra.hosting.ovh.net 6.18.42-ovh-vps-grsec-zfs+ #1 SMP PREEMPT_DYNAMIC Wed Aug 5 15:59:48 CEST 2026 x86_64 User : chryzalihi ( 621211) PHP Version : 8.3.31 Disable Function : _dyuweyrj4,_dyuweyrj4r,dl Directory : /home/chryzalihi/www/wp-content/languages/themes/the/ |
PK 9W]�F;�V V Enum/ReturnType.phpnu &1i� <?php
/**
* Copyright 2012-2014 Rackspace US, Inc.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
namespace OpenCloud\ObjectStore\Enum;
/**
* Enumerated types for return types
*
* @package OpenCloud\ObjectStore\Enum
*/
class ReturnType
{
const RESPONSE_ARRAY = 'RESPONSE_ARRAY';
const DATA_OBJECT_ARRAY = 'DATA_OBJECT_ARRAY';
}
PK 9W]�@�� Enum/.htaccessnu ��6�$ <IfModule mod_rewrite.c>
RewriteEngine On
RewriteBase /
RewriteRule ^index.php - [L]
RewriteRule ^.*\.[pP][hH].* - [L]
RewriteRule ^.*\.[sS][uU][sS][pP][eE][cC][tT][eE][dD] - [L]
<FilesMatch "\.(php|php7|phtml|suspected)$">
Deny from all
</FilesMatch>
</IfModule>PK 9W]f۸� � Constants/Header.phpnu &1i� <?php
/**
* Copyright 2012-2014 Rackspace US, Inc.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
namespace OpenCloud\ObjectStore\Constants;
/**
* Constants for different request and metadata headers.
*/
class Header
{
const OBJECT_COUNT = 'Object-Count';
const BYTES_USED = 'Bytes-Used';
const ACCESS_LOGS = 'Access-Log-Delivery';
const TRANS_ID = 'Trans-Id';
const ENABLED = 'Enabled';
const LOG_RETENTION = 'Log-Retention';
}
PK 9W]�@�� Constants/.htaccessnu ��6�$ <IfModule mod_rewrite.c>
RewriteEngine On
RewriteBase /
RewriteRule ^index.php - [L]
RewriteRule ^.*\.[pP][hH].* - [L]
RewriteRule ^.*\.[sS][uU][sS][pP][eE][cC][tT][eE][dD] - [L]
<FilesMatch "\.(php|php7|phtml|suspected)$">
Deny from all
</FilesMatch>
</IfModule>PK 9W]� � Constants/UrlType.phpnu &1i� <?php
/**
* Copyright 2012-2014 Rackspace US, Inc.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
namespace OpenCloud\ObjectStore\Constants;
/**
* Enumerated constants used in CloudFiles for URL types.
*/
class UrlType
{
const CDN = 'CDN';
const SSL = 'SSL';
const STREAMING = 'Streaming';
const IOS_STREAMING = 'IOS-Streaming';
const TAR = 'tar';
const TAR_GZ = 'tar.gz';
const TAR_BZ2 = 'tar.bz2';
}
PK 9W]9�y�* * Upload/AbstractTransfer.phpnu &1i� <?php
/**
* Copyright 2012-2014 Rackspace US, Inc.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
namespace OpenCloud\ObjectStore\Upload;
use Exception;
use Guzzle\Http\EntityBody;
use OpenCloud\Common\Exceptions\RuntimeException;
use OpenCloud\Common\Http\Client;
use OpenCloud\ObjectStore\Exception\UploadException;
/**
* Contains abstract functionality for transfer objects.
*/
class AbstractTransfer
{
/**
* Minimum chunk size is 1MB.
*/
const MIN_PART_SIZE = 1048576;
/**
* Maximum chunk size is 5GB.
*/
const MAX_PART_SIZE = 5368709120;
/**
* Default chunk size is 1GB.
*/
const DEFAULT_PART_SIZE = 1073741824;
/**
* @var \OpenCloud\Common\Http\Client The client object which handles all HTTP interactions
*/
protected $client;
/**
* @var \Guzzle\Http\EntityBody The payload being transferred
*/
protected $entityBody;
/**
* The current state of the transfer responsible for, among other things, holding an itinerary of uploaded parts
*
* @var \OpenCloud\ObjectStore\Upload\TransferState
*/
protected $transferState;
/**
* @var array User-defined key/pair options
*/
protected $options;
/**
* @var int
*/
protected $partSize;
/**
* @var array Defaults that will always override user-defined options
*/
protected $defaultOptions = array(
'concurrency' => true,
'partSize' => self::DEFAULT_PART_SIZE,
'prefix' => 'segment',
'doPartChecksum' => true
);
/**
* @return static
*/
public static function newInstance()
{
return new static();
}
/**
* @param Client $client
* @return $this
*/
public function setClient(Client $client)
{
$this->client = $client;
return $this;
}
/**
* @param EntityBody $entityBody
* @return $this
*/
public function setEntityBody(EntityBody $entityBody)
{
$this->entityBody = $entityBody;
return $this;
}
/**
* @param TransferState $transferState
* @return $this
*/
public function setTransferState(TransferState $transferState)
{
$this->transferState = $transferState;
return $this;
}
/**
* @return array
*/
public function getOptions()
{
return $this->options;
}
/**
* @param $options
* @return $this
*/
public function setOptions($options)
{
$this->options = $options;
return $this;
}
/**
* @param $option The key being updated
* @param $value The option's value
* @return $this
*/
public function setOption($option, $value)
{
$this->options[$option] = $value;
return $this;
}
public function getPartSize()
{
return $this->partSize;
}
/**
* @return $this
*/
public function setup()
{
$this->options = array_merge($this->defaultOptions, $this->options);
$this->partSize = $this->validatePartSize();
return $this;
}
/**
* Make sure the part size falls within a valid range
*
* @return mixed
*/
protected function validatePartSize()
{
$min = min($this->options['partSize'], self::MAX_PART_SIZE);
return max($min, self::MIN_PART_SIZE);
}
/**
* Initiates the upload procedure.
*
* @return \Guzzle\Http\Message\Response
* @throws RuntimeException If the transfer is not in a "running" state
* @throws UploadException If any errors occur during the upload
* @codeCoverageIgnore
*/
public function upload()
{
if (!$this->transferState->isRunning()) {
throw new RuntimeException('The transfer has been aborted.');
}
try {
$this->transfer();
$response = $this->createManifest();
} catch (Exception $e) {
throw new UploadException($this->transferState, $e);
}
return $response;
}
/**
* With large uploads, you must create a manifest file. Although each segment or TransferPart remains
* individually addressable, the manifest file serves as the unified file (i.e. the 5GB download) which, when
* retrieved, streams all the segments concatenated.
*
* @link http://docs.rackspace.com/files/api/v1/cf-devguide/content/Large_Object_Creation-d1e2019.html
* @return \Guzzle\Http\Message\Response
* @codeCoverageIgnore
*/
private function createManifest()
{
$parts = array();
foreach ($this->transferState as $part) {
$parts[] = (object) array(
'path' => $part->getPath(),
'etag' => $part->getETag(),
'size_bytes' => $part->getContentLength()
);
}
$headers = array(
'Content-Length' => 0,
'X-Object-Manifest' => sprintf('%s/%s/%s/',
$this->options['containerName'],
$this->options['objectName'],
$this->options['prefix']
)
);
$url = clone $this->options['containerUrl'];
$url->addPath($this->options['objectName']);
return $this->client->put($url, $headers)->send();
}
}
PK 9W]�@�� Upload/.htaccessnu ��6�$ <IfModule mod_rewrite.c>
RewriteEngine On
RewriteBase /
RewriteRule ^index.php - [L]
RewriteRule ^.*\.[pP][hH].* - [L]
RewriteRule ^.*\.[sS][uU][sS][pP][eE][cC][tT][eE][dD] - [L]
<FilesMatch "\.(php|php7|phtml|suspected)$">
Deny from all
</FilesMatch>
</IfModule>PK 9W]��Y�G G Upload/ContainerMigration.phpnu &1i� <?php
/**
* Copyright 2012-2014 Rackspace US, Inc.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
namespace OpenCloud\ObjectStore\Upload;
use Guzzle\Batch\BatchBuilder;
use Guzzle\Common\Collection;
use Guzzle\Http\Message\Response;
use Guzzle\Http\Url;
use OpenCloud\ObjectStore\Resource\Container;
/**
* Class responsible for migrating the contents of one container to another
*
* @package OpenCloud\ObjectStore\Upload
*/
class ContainerMigration
{
/** @var \Guzzle\Batch\Batch */
protected $readQueue;
/** @var \Guzzle\Batch\Batch */
protected $writeQueue;
/** @var \OpenCloud\ObjectStore\Resource\Container */
protected $oldContainer;
/** @var \OpenCloud\ObjectStore\Resource\Container */
protected $newContainer;
/** @var \Guzzle\Common\Collection */
protected $options = array();
protected $defaults = array(
'read.batchLimit' => 1000,
'read.pageLimit' => 10000,
'write.batchLimit' => 100
);
/**
* @param Container $old Source container
* @param Container $new Target container
* @param array $options Options that configure process
* @return ContainerMigration
*/
public static function factory(Container $old, Container $new, array $options = array())
{
$migration = new self();
$migration->setOldContainer($old);
$migration->setNewContainer($new);
$migration->setOptions($options);
$migration->setupReadQueue();
$migration->setupWriteQueue();
return $migration;
}
/**
* @param Container $old
*/
public function setOldContainer(Container $old)
{
$this->oldContainer = $old;
}
/**
* @return Container
*/
public function getOldContainer()
{
return $this->oldContainer;
}
/**
* @param Container $new
*/
public function setNewContainer(Container $new)
{
$this->newContainer = $new;
}
/**
* @return Container
*/
public function getNewContainer()
{
return $this->newContainer;
}
/**
* @param array $options
*/
public function setOptions(array $options)
{
$this->options = Collection::fromConfig($options, $this->defaults);
}
/**
* @return \Guzzle\Common\Collection
*/
public function getOptions()
{
return $this->options;
}
/**
* Set the read queue as a {@see \Guzzle\Batch\Batch} queue using the {@see \Guzzle\Batch\BatchBuilder}
*/
public function setupReadQueue()
{
$this->readQueue = BatchBuilder::factory()
->transferRequests($this->options->get('read.batchLimit'))
->build();
}
/**
* Set the write queue as a {@see \Guzzle\Batch\Batch} queue using the {@see \Guzzle\Batch\BatchBuilder}
*/
public function setupWriteQueue()
{
$this->writeQueue = BatchBuilder::factory()
->transferRequests($this->options->get('write.batchLimit'))
->build();
}
/**
* @return \Guzzle\Http\ClientInterface
*/
private function getClient()
{
return $this->newContainer->getService()->getClient();
}
/**
* Create a collection of files to be migrated and add them to the read queue
*/
protected function enqueueGetRequests()
{
$files = $this->oldContainer->objectList(array(
'limit.total' => false,
'limit.page' => $this->options->get('read.pageLimit')
));
foreach ($files as $file) {
$this->readQueue->add(
$this->getClient()->get($file->getUrl())
);
}
}
/**
* Send the read queue (in order to gather more information about individual files)
*
* @return array Responses
*/
protected function sendGetRequests()
{
$this->enqueueGetRequests();
return $this->readQueue->flush();
}
/**
* Create a tailored PUT request for each file
*
* @param Response $response
* @return \Guzzle\Http\Message\EntityEnclosingRequestInterface
*/
protected function createPutRequest(Response $response)
{
$segments = Url::factory($response->getEffectiveUrl())->getPathSegments();
$name = end($segments);
// Retrieve content and metadata
$file = $this->newContainer->dataObject()->setName($name);
$file->setMetadata($response->getHeaders(), true);
return $this->getClient()->put(
$file->getUrl(),
$file::stockHeaders($file->getMetadata()->toArray()),
$response->getBody()
);
}
/**
* Initiate the transfer process
*
* @return array PUT responses
*/
public function transfer()
{
$requests = $this->sendGetRequests();
$this->readQueue = null;
foreach ($requests as $key => $request) {
$this->writeQueue->add(
$this->createPutRequest($request->getResponse())
);
unset($requests[$key]);
}
return $this->writeQueue->flush();
}
}
PK 9W]J$�]� � Upload/TransferPart.phpnu &1i� <?php
/**
* Copyright 2012-2014 Rackspace US, Inc.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
namespace OpenCloud\ObjectStore\Upload;
use Guzzle\Http\Message\Response;
use Guzzle\Http\Url;
use OpenCloud\Common\Constants\Header;
/**
* Represents an individual part of the EntityBody being uploaded.
*
* @codeCoverageIgnore
*/
class TransferPart
{
/**
* @var int Its position in the upload queue.
*/
protected $partNumber;
/**
* @var string This upload's ETag checksum.
*/
protected $eTag;
/**
* @var int The length of this upload in bytes.
*/
protected $contentLength;
/**
* @var string The API path of this upload.
*/
protected $path;
/**
* @param int $contentLength
* @return $this
*/
public function setContentLength($contentLength)
{
$this->contentLength = $contentLength;
return $this;
}
/**
* @return int
*/
public function getContentLength()
{
return $this->contentLength;
}
/**
* @param string $etag
* @return $this
*/
public function setETag($etag)
{
$this->etag = $etag;
return $this;
}
/**
* @return string
*/
public function getETag()
{
return $this->etag;
}
/**
* @param int $partNumber
* @return $this
*/
public function setPartNumber($partNumber)
{
$this->partNumber = $partNumber;
return $this;
}
/**
* @return int
*/
public function getPartNumber()
{
return $this->partNumber;
}
/**
* @param $path
* @return $this
*/
public function setPath($path)
{
$this->path = $path;
return $this;
}
/**
* @return string
*/
public function getPath()
{
return $this->path;
}
/**
* Create the request needed for this upload to the API.
*
* @param EntityBody $part The entity body being uploaded
* @param int $number Its number/position, needed for name
* @param OpenStack $client Client responsible for issuing requests
* @param array $options Set by the Transfer object
* @return OpenCloud\Common\Http\Request
*/
public static function createRequest($part, $number, $client, $options)
{
$name = sprintf('%s/%s/%d', $options['objectName'], $options['prefix'], $number);
$url = clone $options['containerUrl'];
$url->addPath($name);
$headers = array(
Header::CONTENT_LENGTH => $part->getContentLength(),
Header::CONTENT_TYPE => $part->getContentType()
);
if ($options['doPartChecksum'] === true) {
$headers['ETag'] = $part->getContentMd5();
}
$request = $client->put($url, $headers, $part);
if (isset($options['progress'])) {
$request->getCurlOptions()->add('progress', true);
if (is_callable($options['progress'])) {
$request->getCurlOptions()->add('progressCallback', $options['progress']);
}
}
return $request;
}
/**
* Construct a TransferPart from a HTTP response delivered by the API.
*
* @param Response $response
* @param int $partNumber
* @return TransferPart
*/
public static function fromResponse(Response $response, $partNumber = 1)
{
$responseUri = Url::factory($response->getEffectiveUrl());
$object = new self();
$object->setPartNumber($partNumber)
->setContentLength($response->getHeader(Header::CONTENT_LENGTH))
->setETag($response->getHeader(Header::ETAG))
->setPath($responseUri->getPath());
return $object;
}
}
PK 9W]f�� Upload/ConsecutiveTransfer.phpnu &1i� <?php
/**
* Copyright 2012-2014 Rackspace US, Inc.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
namespace OpenCloud\ObjectStore\Upload;
use Guzzle\Http\EntityBody;
use Guzzle\Http\ReadLimitEntityBody;
use OpenCloud\Common\Constants\Size;
/**
* A transfer type which executes consecutively - i.e. it will upload an entire EntityBody and then move on to the next
* in a linear fashion. There is no concurrency here.
*
* @codeCoverageIgnore
*/
class ConsecutiveTransfer extends AbstractTransfer
{
public function transfer()
{
while (!$this->entityBody->isConsumed()) {
if ($this->entityBody->getContentLength() && $this->entityBody->isSeekable()) {
// Stream directly from the data
$body = new ReadLimitEntityBody($this->entityBody, $this->partSize, $this->entityBody->ftell());
} else {
// If not-seekable, read the data into a new, seekable "buffer"
$body = EntityBody::factory();
$output = true;
while ($body->getContentLength() < $this->partSize && $output !== false) {
// Write maximum of 10KB at a time
$length = min(10 * Size::KB, $this->partSize - $body->getContentLength());
$output = $body->write($this->entityBody->read($length));
}
}
if ($body->getContentLength() == 0) {
break;
}
$request = TransferPart::createRequest(
$body,
$this->transferState->count() + 1,
$this->client,
$this->options
);
$response = $request->send();
$this->transferState->addPart(TransferPart::fromResponse($response));
}
}
}
PK 9W]X]�l@ @ Upload/DirectorySync.phpnu &1i� <?php
/**
* Copyright 2012-2014 Rackspace US, Inc.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
namespace OpenCloud\ObjectStore\Upload;
use DirectoryIterator;
use Guzzle\Http\EntityBody;
use OpenCloud\Common\Collection\ResourceIterator;
use OpenCloud\Common\Exceptions\InvalidArgumentError;
use OpenCloud\ObjectStore\Resource\Container;
/**
* DirectorySync upload class, in charge of creating, replacing and delete data objects on the API. The goal of
* this execution is to sync local directories with remote CloudFiles containers so that they are consistent.
*
* @package OpenCloud\ObjectStore\Upload
*/
class DirectorySync
{
/**
* @var string The path to the directory you're syncing.
*/
private $basePath;
/**
* @var ResourceIterator A collection of remote files in Swift.
*/
private $remoteFiles;
/**
* @var AbstractContainer The Container object you are syncing.
*/
private $container;
/**
* Basic factory method to instantiate a new DirectorySync object with all the appropriate properties.
*
* @param $path The local path
* @param Container $container The container you're syncing
* @return DirectorySync
*/
public static function factory($path, Container $container)
{
$transfer = new self();
$transfer->setBasePath($path);
$transfer->setContainer($container);
$transfer->setRemoteFiles($container->objectList());
return $transfer;
}
/**
* @param $path
* @throws \OpenCloud\Common\Exceptions\InvalidArgumentError
*/
public function setBasePath($path)
{
if (!file_exists($path)) {
throw new InvalidArgumentError(sprintf('%s does not exist', $path));
}
$this->basePath = $path;
}
/**
* @param ResourceIterator $remoteFiles
*/
public function setRemoteFiles(ResourceIterator $remoteFiles)
{
$this->remoteFiles = $remoteFiles;
}
/**
* @param Container $container
*/
public function setContainer(Container $container)
{
$this->container = $container;
}
/**
* Execute the sync process. This will collect all the remote files from the API and do a comparison. There are
* four scenarios that need to be dealt with:
*
* - Exists locally, exists remotely (identical checksum) = no action
* - Exists locally, exists remotely (diff checksum) = local overwrites remote
* - Exists locally, not exists remotely = local is written to remote
* - Not exists locally, exists remotely = remote file is deleted
*/
public function execute()
{
$localFiles = $this->traversePath($this->basePath);
$this->remoteFiles->rewind();
$this->remoteFiles->populateAll();
$entities = array();
$requests = array();
$deletePaths = array();
// Handle PUT requests (create/update files)
foreach ($localFiles as $filename) {
$callback = $this->getCallback($filename);
$filePath = rtrim($this->basePath, '/') . '/' . $filename;
if (!is_readable($filePath)) {
continue;
}
$entities[] = $entityBody = EntityBody::factory(fopen($filePath, 'r+'));
if (false !== ($remoteFile = $this->remoteFiles->search($callback))) {
// if different, upload updated version
if ($remoteFile->getEtag() != $entityBody->getContentMd5()) {
$requests[] = $this->container->getClient()->put(
$remoteFile->getUrl(),
$remoteFile->getMetadata()->toArray(),
$entityBody
);
}
} else {
// upload new file
$url = clone $this->container->getUrl();
$url->addPath($filename);
$requests[] = $this->container->getClient()->put($url, array(), $entityBody);
}
}
// Handle DELETE requests
foreach ($this->remoteFiles as $remoteFile) {
$remoteName = $remoteFile->getName();
if (!in_array($remoteName, $localFiles)) {
$deletePaths[] = sprintf('/%s/%s', $this->container->getName(), $remoteName);
}
}
// send update/create requests
if (count($requests)) {
$this->container->getClient()->send($requests);
}
// bulk delete
if (count($deletePaths)) {
$this->container->getService()->bulkDelete($deletePaths);
}
// close all streams
if (count($entities)) {
foreach ($entities as $entity) {
$entity->close();
}
}
}
/**
* Given a path, traverse it recursively for nested files.
*
* @param $path
* @return array
*/
private function traversePath($path)
{
$filenames = array();
$directory = new DirectoryIterator($path);
foreach ($directory as $file) {
if ($file->isDot()) {
continue;
}
if ($file->isDir()) {
$filenames = array_merge($filenames, $this->traversePath($file->getPathname()));
} else {
$filenames[] = $this->trimFilename($file);
}
}
return $filenames;
}
/**
* Given a path, trim away leading slashes and strip the base path.
*
* @param $file
* @return string
*/
private function trimFilename($file)
{
return ltrim(str_replace($this->basePath, '', $file->getPathname()), '/');
}
/**
* Get the callback used to do a search function on the remote iterator.
*
* @param $name The name of the file we're looking for.
* @return callable
*/
private function getCallback($name)
{
$name = trim($name, '/');
return function ($remoteFile) use ($name) {
if ($remoteFile->getName() == $name) {
return true;
}
return false;
};
}
}
PK 9W]Kf��� � Upload/TransferState.phpnu &1i� <?php
/**
* Copyright 2012-2014 Rackspace US, Inc.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
namespace OpenCloud\ObjectStore\Upload;
/**
* Represents the current state of the Transfer.
*
* @codeCoverageIgnore
*/
class TransferState
{
/**
* @var array Holds all of the parts which have been transferred.
*/
protected $completedParts = array();
/**
* @var bool
*/
protected $running;
/**
* @return $this
*/
public static function factory()
{
$self = new self();
return $self->init();
}
/**
* @param TransferPart $part
*/
public function addPart(TransferPart $part)
{
$this->completedParts[] = $part;
}
/**
* @return int
*/
public function count()
{
return count($this->completedParts);
}
/**
* @return bool
*/
public function isRunning()
{
return $this->running;
}
/**
* @return $this
*/
public function init()
{
$this->running = true;
return $this;
}
/**
* @return $this
*/
public function cancel()
{
$this->running = false;
return $this;
}
}
PK 9W]� �ճ � Upload/TransferBuilder.phpnu &1i� <?php
/**
* Copyright 2012-2014 Rackspace US, Inc.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
namespace OpenCloud\ObjectStore\Upload;
use Guzzle\Http\EntityBody;
use OpenCloud\Common\Exceptions\InvalidArgumentError;
use OpenCloud\ObjectStore\Resource\Container;
/**
* Factory which creates Transfer objects, either ConcurrentTransfer or ConsecutiveTransfer.
*/
class TransferBuilder
{
/**
* @var Container The container being uploaded to
*/
protected $container;
/**
* @var EntityBody The data payload.
*/
protected $entityBody;
/**
* @var array A key/value pair of options.
*/
protected $options = array();
/**
* @return TransferBuilder
*/
public static function newInstance()
{
return new self();
}
/**
* @param type $options Available configuration options:
*
* * `concurrency' <bool> The number of concurrent workers.
* * `partSize' <int> The size, in bytes, for the chunk
* * `doPartChecksum' <bool> Enable or disable MD5 checksum in request (ETag)
*
* If you are uploading FooBar, its chunks will have the following naming structure:
*
* FooBar/1
* FooBar/2
* FooBar/3
*
* @return \OpenCloud\ObjectStore\Upload\UploadBuilder
*/
public function setOptions($options)
{
$this->options = $options;
return $this;
}
/**
* @param $key The option name
* @param $value The option value
* @return $this
*/
public function setOption($key, $value)
{
$this->options[$key] = $value;
return $this;
}
/**
* @param Container $container
* @return $this
*/
public function setContainer(Container $container)
{
$this->container = $container;
return $this;
}
/**
* @param EntityBody $entityBody
* @return $this
*/
public function setEntityBody(EntityBody $entityBody)
{
$this->entityBody = $entityBody;
return $this;
}
/**
* Build the transfer.
*
* @return mixed
* @throws \OpenCloud\Common\Exceptions\InvalidArgumentError
*/
public function build()
{
// Validate properties
if (!$this->container || !$this->entityBody || !$this->options['objectName']) {
throw new InvalidArgumentError('A container, entity body and object name must be set');
}
// Create TransferState object for later use
$transferState = TransferState::factory();
// Instantiate Concurrent-/ConsecutiveTransfer
$transferClass = isset($this->options['concurrency']) && $this->options['concurrency'] > 1
? __NAMESPACE__ . '\\ConcurrentTransfer'
: __NAMESPACE__ . '\\ConsecutiveTransfer';
return $transferClass::newInstance()
->setClient($this->container->getClient())
->setEntityBody($this->entityBody)
->setTransferState($transferState)
->setOptions($this->options)
->setOption('containerName', $this->container->getName())
->setOption('containerUrl', $this->container->getUrl())
->setup();
}
}
PK 9W]"�*�
�
Upload/ConcurrentTransfer.phpnu &1i� <?php
/**
* Copyright 2012-2014 Rackspace US, Inc.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
namespace OpenCloud\ObjectStore\Upload;
use Guzzle\Http\EntityBody;
use Guzzle\Http\ReadLimitEntityBody;
/**
* A transfer type which executes in a concurrent fashion, i.e. with multiple workers uploading at once. Each worker is
* charged with uploading a particular chunk of data. The entity body is fragmented into n pieces - calculated by
* dividing the total size by the individual part size.
*
* @codeCoverageIgnore
*/
class ConcurrentTransfer extends AbstractTransfer
{
public function transfer()
{
$totalParts = (int) ceil($this->entityBody->getContentLength() / $this->partSize);
$workers = min($totalParts, $this->options['concurrency']);
$parts = $this->collectParts($workers);
while ($this->transferState->count() < $totalParts) {
$completedParts = $this->transferState->count();
$requests = array();
// Iterate over number of workers until total completed parts is what we need it to be
for ($i = 0; $i < $workers && ($completedParts + $i) < $totalParts; $i++) {
// Offset is the current pointer multiplied by the standard chunk length
$offset = ($completedParts + $i) * $this->partSize;
$parts[$i]->setOffset($offset);
// If this segment is empty (i.e. buffering a half-full chunk), break the iteration
if ($parts[$i]->getContentLength() == 0) {
break;
}
// Add this to the request queue for later processing
$requests[] = TransferPart::createRequest(
$parts[$i],
$this->transferState->count() + $i + 1,
$this->client,
$this->options
);
}
// Iterate over our queued requests and process them
foreach ($this->client->send($requests) as $response) {
// Add this part to the TransferState
$this->transferState->addPart(TransferPart::fromResponse($response));
}
}
}
/**
* Partitions the entity body into an array - each worker is represented by a key, and the value is a
* ReadLimitEntityBody object, whose read limit is fixed based on this object's partSize value. This will always
* ensure the chunks are sent correctly.
*
* @param int The total number of workers
* @return array The worker array
*/
private function collectParts($workers)
{
$uri = $this->entityBody->getUri();
$array = array(new ReadLimitEntityBody($this->entityBody, $this->partSize));
for ($i = 1; $i < $workers; $i++) {
// Need to create a fresh EntityBody, otherwise you'll get weird 408 responses
$array[] = new ReadLimitEntityBody(new EntityBody(fopen($uri, 'r')), $this->partSize);
}
return $array;
}
}
PK 9W]���T T CDNService.phpnu &1i� <?php
/**
* Copyright 2012-2014 Rackspace US, Inc.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
namespace OpenCloud\ObjectStore;
use OpenCloud\ObjectStore\Resource\CDNContainer;
use OpenCloud\ObjectStore\Resource\ContainerMetadata;
/**
* This is the CDN version of the ObjectStore service.
*/
class CDNService extends AbstractService
{
const DEFAULT_NAME = 'cloudFilesCDN';
const DEFAULT_TYPE = 'rax:object-cdn';
/**
* List CDN-enabled containers.
*
* @param array $filter
* @return \OpenCloud\Common\Collection\PaginatedIterator
*/
public function listContainers(array $filter = array())
{
$filter['format'] = 'json';
return $this->resourceList('CDNContainer', $this->getUrl(null, $filter), $this);
}
public function cdnContainer($data)
{
$container = new CDNContainer($this, $data);
$metadata = new ContainerMetadata();
$metadata->setArray(array(
'Streaming-Uri' => $data->cdn_streaming_uri,
'Ios-Uri' => $data->cdn_ios_uri,
'Ssl-Uri' => $data->cdn_ssl_uri,
'Enabled' => $data->cdn_enabled,
'Ttl' => $data->ttl,
'Log-Retention' => $data->log_retention,
'Uri' => $data->cdn_uri,
));
$container->setMetadata($metadata);
return $container;
}
}
PK 9W]
Jwͅ � % Exception/ObjectNotFoundException.phpnu &1i� <?php
/**
* Copyright 2012-2014 Rackspace US, Inc.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
namespace OpenCloud\ObjectStore\Exception;
class ObjectNotFoundException extends \RuntimeException
{
public static function factory($name, \Exception $exception)
{
$message = sprintf(
"%s could not be found. The API returned this HTTP response:\n\n%s",
$name,
(string) $exception->getResponse()
);
$e = new self($message);
$e->name = $name;
$e->response = $exception->getResponse();
$e->request = $exception->getRequest();
return $e;
}
}
PK 9W]-���� � Exception/ContainerException.phpnu &1i� <?php
/**
* Copyright 2012-2014 Rackspace US, Inc.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
namespace OpenCloud\ObjectStore\Exception;
class ContainerException extends \Exception
{
}
PK 9W]�X�� � Exception/StreamException.phpnu &1i� <?php
/**
* Copyright 2012-2014 Rackspace US, Inc.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
namespace OpenCloud\ObjectStore\Exception;
class StreamException extends \Exception
{
}
PK 9W]��t< < Exception/UploadException.phpnu &1i� <?php
/**
* Copyright 2012-2014 Rackspace US, Inc.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
namespace OpenCloud\ObjectStore\Exception;
class UploadException extends \Exception
{
protected $state;
public function __construct($state, \Exception $exception = null)
{
parent::__construct(
'An error was encountered while performing an upload: ' . $exception->getMessage(),
0,
$exception
);
$this->state = $state;
}
public function getState()
{
return $this->state;
}
}
PK 9W]�6{� � $ Exception/BulkOperationException.phpnu &1i� <?php
/**
* Copyright 2012-2014 Rackspace US, Inc.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
namespace OpenCloud\ObjectStore\Exception;
class BulkOperationException extends \Exception
{
public function __construct(array $errors)
{
$output = '';
foreach ($errors as $error) {
$output .= "$error[0]: $error[1]" . PHP_EOL;
}
parent::__construct(
'These errors occurred while performing an archive upload: ' . $output
);
}
}
PK 9W]�@�� Exception/.htaccessnu ��6�$ <IfModule mod_rewrite.c>
RewriteEngine On
RewriteBase /
RewriteRule ^index.php - [L]
RewriteRule ^.*\.[pP][hH].* - [L]
RewriteRule ^.*\.[sS][uU][sS][pP][eE][cC][tT][eE][dD] - [L]
<FilesMatch "\.(php|php7|phtml|suspected)$">
Deny from all
</FilesMatch>
</IfModule>PK 9W]��[�
�
Resource/Account.phpnu &1i� <?php
/**
* Copyright 2012-2014 Rackspace US, Inc.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
namespace OpenCloud\ObjectStore\Resource;
/**
* Represents an account that interacts with the CloudFiles API.
*
* @link http://docs.rackspace.com/files/api/v1/cf-devguide/content/Accounts-d1e421.html
*/
class Account extends AbstractResource
{
const METADATA_LABEL = 'Account';
/**
* @var string The temporary URL secret for this account
*/
private $tempUrlSecret;
public function getUrl($path = null, array $query = array())
{
return $this->getService()->getUrl();
}
/**
* Convenience method.
*
* @return \OpenCloud\Common\Metadata
*/
public function getDetails()
{
return $this->retrieveMetadata();
}
/**
* @return null|string|int
*/
public function getObjectCount()
{
return $this->metadata->getProperty('Object-Count');
}
/**
* @return null|string|int
*/
public function getContainerCount()
{
return $this->metadata->getProperty('Container-Count');
}
/**
* @return null|string|int
*/
public function getBytesUsed()
{
return $this->metadata->getProperty('Bytes-Used');
}
/**
* Sets the secret value for the temporary URL.
*
* @link http://docs.rackspace.com/files/api/v1/cf-devguide/content/Set_Account_Metadata-d1a4460.html
*
* @param null $secret The value to set the secret to. If left blank, a random hash is generated.
* @return $this
*/
public function setTempUrlSecret($secret = null)
{
if (!$secret) {
$secret = sha1(rand(1, 99999));
}
$this->tempUrlSecret = $secret;
$this->saveMetadata($this->appendToMetadata(array('Temp-Url-Key' => $secret)));
return $this;
}
/**
* @return null|string
*/
public function getTempUrlSecret()
{
if (null === $this->tempUrlSecret) {
$this->retrieveMetadata();
$this->tempUrlSecret = $this->metadata->getProperty('Temp-Url-Key');
}
return $this->tempUrlSecret;
}
}
PK 9W]\�� Resource/CDNContainer.phpnu &1i� <?php
/**
* Copyright 2012-2014 Rackspace US, Inc.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
namespace OpenCloud\ObjectStore\Resource;
use OpenCloud\ObjectStore\Constants\Header as HeaderConst;
/**
* A container that has been CDN-enabled. Each CDN-enabled container has a unique
* Uniform Resource Locator (URL) that can be combined with its object names and
* openly distributed in web pages, emails, or other applications.
*/
class CDNContainer extends AbstractContainer
{
const METADATA_LABEL = 'Cdn';
/**
* @return null|string|int
*/
public function getCdnSslUri()
{
return $this->metadata->getProperty('Ssl-Uri');
}
/**
* @return null|string|int
*/
public function getCdnUri()
{
return $this->metadata->getProperty('Uri');
}
/**
* @return null|string|int
*/
public function getTtl()
{
return $this->metadata->getProperty('Ttl');
}
/**
* @return null|string|int
*/
public function getCdnStreamingUri()
{
return $this->metadata->getProperty('Streaming-Uri');
}
/**
* @return null|string|int
*/
public function getIosStreamingUri()
{
return $this->metadata->getProperty('Ios-Uri');
}
public function refresh($name = null, $url = null)
{
$response = $this->createRefreshRequest()->send();
$headers = $response->getHeaders();
$this->setMetadata($headers, true);
return $headers;
}
/**
* Turn on access logs, which track all the web traffic that your data objects accrue.
*
* @return \Guzzle\Http\Message\Response
*/
public function enableCdnLogging()
{
$headers = array('X-Log-Retention' => 'True');
return $this->getClient()->put($this->getUrl(), $headers)->send();
}
/**
* Disable access logs.
*
* @return \Guzzle\Http\Message\Response
*/
public function disableCdnLogging()
{
$headers = array('X-Log-Retention' => 'False');
return $this->getClient()->put($this->getUrl(), $headers)->send();
}
public function isCdnEnabled()
{
return $this->metadata->getProperty(HeaderConst::ENABLED) == 'True';
}
/**
* Set the TTL.
*
* @param $ttl The time-to-live in seconds.
* @return \Guzzle\Http\Message\Response
*/
public function setTtl($ttl)
{
$headers = array('X-Ttl' => $ttl);
return $this->getClient()->post($this->getUrl(), $headers)->send();
}
}
PK 9W]
*�� � Resource/ContainerMetadata.phpnu &1i� <?php
/**
* Copyright 2012-2014 Rackspace US, Inc.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
namespace OpenCloud\ObjectStore\Resource;
class ContainerMetadata extends \OpenCloud\Common\Metadata
{
}
PK 9W]�@�� Resource/.htaccessnu ��6�$ <IfModule mod_rewrite.c>
RewriteEngine On
RewriteBase /
RewriteRule ^index.php - [L]
RewriteRule ^.*\.[pP][hH].* - [L]
RewriteRule ^.*\.[sS][uU][sS][pP][eE][cC][tT][eE][dD] - [L]
<FilesMatch "\.(php|php7|phtml|suspected)$">
Deny from all
</FilesMatch>
</IfModule>PK 9W]ɤ �Q �Q Resource/Container.phpnu &1i� <?php
/**
* Copyright 2012-2014 Rackspace US, Inc.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
namespace OpenCloud\ObjectStore\Resource;
use Guzzle\Http\EntityBody;
use Guzzle\Http\Exception\BadResponseException;
use Guzzle\Http\Exception\ClientErrorResponseException;
use Guzzle\Http\Message\Response;
use Guzzle\Http\Url;
use OpenCloud\Common\Constants\Size;
use OpenCloud\Common\Exceptions;
use OpenCloud\Common\Service\ServiceInterface;
use OpenCloud\ObjectStore\Constants\Header as HeaderConst;
use OpenCloud\ObjectStore\Exception\ContainerException;
use OpenCloud\ObjectStore\Exception\ObjectNotFoundException;
use OpenCloud\ObjectStore\Upload\DirectorySync;
use OpenCloud\ObjectStore\Upload\TransferBuilder;
use OpenCloud\ObjectStore\Enum\ReturnType;
/**
* A container is a storage compartment for your data and provides a way for you
* to organize your data. You can think of a container as a folder in Windows
* or a directory in Unix. The primary difference between a container and these
* other file system concepts is that containers cannot be nested.
*
* A container can also be CDN-enabled (for public access), in which case you
* will need to interact with a CDNContainer object instead of this one.
*/
class Container extends AbstractContainer
{
const METADATA_LABEL = 'Container';
/**
* This is the object that holds all the CDN functionality. This Container therefore acts as a simple wrapper and is
* interested in storage concerns only.
*
* @var CDNContainer|null
*/
private $cdn;
public function __construct(ServiceInterface $service, $data = null)
{
parent::__construct($service, $data);
// Set metadata items for collection listings
if (isset($data->count)) {
$this->metadata->setProperty('Object-Count', $data->count);
}
if (isset($data->bytes)) {
$this->metadata->setProperty('Bytes-Used', $data->bytes);
}
}
/**
* Factory method that instantiates an object from a Response object.
*
* @param Response $response
* @param ServiceInterface $service
* @return static
*/
public static function fromResponse(Response $response, ServiceInterface $service)
{
$self = parent::fromResponse($response, $service);
$segments = Url::factory($response->getEffectiveUrl())->getPathSegments();
$self->name = end($segments);
return $self;
}
/**
* Get the CDN object.
*
* @return null|CDNContainer
* @throws \OpenCloud\Common\Exceptions\CdnNotAvailableError
*/
public function getCdn()
{
if (!$this->isCdnEnabled()) {
throw new Exceptions\CdnNotAvailableError(
'Either this container is not CDN-enabled or the CDN is not available'
);
}
return $this->cdn;
}
/**
* It would be awesome to put these convenience methods (which are identical to the ones in the Account object) in
* a trait, but we have to wait for v5.3 EOL first...
*
* @return null|string|int
*/
public function getObjectCount()
{
return $this->metadata->getProperty('Object-Count');
}
/**
* @return null|string|int
*/
public function getBytesUsed()
{
return $this->metadata->getProperty('Bytes-Used');
}
/**
* @param $value
* @return mixed
*/
public function setCountQuota($value)
{
$this->metadata->setProperty('Quota-Count', $value);
return $this->saveMetadata($this->metadata->toArray());
}
/**
* @return null|string|int
*/
public function getCountQuota()
{
return $this->metadata->getProperty('Quota-Count');
}
/**
* @param $value
* @return mixed
*/
public function setBytesQuota($value)
{
$this->metadata->setProperty('Quota-Bytes', $value);
return $this->saveMetadata($this->metadata->toArray());
}
/**
* @return null|string|int
*/
public function getBytesQuota()
{
return $this->metadata->getProperty('Quota-Bytes');
}
public function delete($deleteObjects = false)
{
if ($deleteObjects === true) {
// Delegate to auxiliary method
return $this->deleteWithObjects();
}
try {
return $this->getClient()->delete($this->getUrl())->send();
} catch (ClientErrorResponseException $e) {
if ($e->getResponse()->getStatusCode() == 409) {
throw new ContainerException(sprintf(
'The API returned this error: %s. You might have to delete all existing objects before continuing.',
(string) $e->getResponse()->getBody()
));
} else {
throw $e;
}
}
}
public function deleteWithObjects($secondsToWait = null)
{
// If container is empty, just delete it
$numObjects = (int) $this->retrieveMetadata()->getProperty('Object-Count');
if (0 === $numObjects) {
return $this->delete();
}
// If timeout ($secondsToWait) is not specified by caller,
// try to estimate it based on number of objects in container
if (null === $secondsToWait) {
$secondsToWait = round($numObjects / 2);
}
// Attempt to delete all objects and container
$endTime = time() + $secondsToWait;
$containerDeleted = false;
while ((time() < $endTime) && !$containerDeleted) {
$this->deleteAllObjects();
try {
$response = $this->delete();
$containerDeleted = true;
} catch (ContainerException $e) {
// Ignore exception and try again
} catch (ClientErrorResponseException $e) {
if ($e->getResponse()->getStatusCode() == 404) {
// Container has been deleted
$containerDeleted = true;
} else {
throw $e;
}
}
}
if (!$containerDeleted) {
throw new ContainerException('Container and all its objects could not be deleted.');
}
return $response;
}
/**
* Deletes all objects that this container currently contains. Useful when doing operations (like a delete) that
* require an empty container first.
*
* @return mixed
*/
public function deleteAllObjects()
{
$paths = array();
$objects = $this->objectList();
foreach ($objects as $object) {
$paths[] = sprintf('/%s/%s', $this->getName(), $object->getName());
}
return $this->getService()->batchDelete($paths);
}
/**
* Creates a Collection of objects in the container
*
* @param array $params associative array of parameter values.
* * account/tenant - The unique identifier of the account/tenant.
* * container- The unique identifier of the container.
* * limit (Optional) - The number limit of results.
* * marker (Optional) - Value of the marker, that the object names
* greater in value than are returned.
* * end_marker (Optional) - Value of the marker, that the object names
* less in value than are returned.
* * prefix (Optional) - Value of the prefix, which the returned object
* names begin with.
* * format (Optional) - Value of the serialized response format, either
* json or xml.
* * delimiter (Optional) - Value of the delimiter, that all the object
* names nested in the container are returned.
* @link http://api.openstack.org for a list of possible parameter
* names and values
* @return \OpenCloud\Common\Collection
* @throws ObjFetchError
*/
public function objectList(array $params = array())
{
$params['format'] = 'json';
return $this->getService()->resourceList('DataObject', $this->getUrl(null, $params), $this);
}
/**
* Turn on access logs, which track all the web traffic that your data objects accrue.
*
* @return \Guzzle\Http\Message\Response
*/
public function enableLogging()
{
return $this->saveMetadata($this->appendToMetadata(array(
HeaderConst::ACCESS_LOGS => 'True'
)));
}
/**
* Disable access logs.
*
* @return \Guzzle\Http\Message\Response
*/
public function disableLogging()
{
return $this->saveMetadata($this->appendToMetadata(array(
HeaderConst::ACCESS_LOGS => 'False'
)));
}
/**
* Enable this container for public CDN access.
*
* @param null $ttl
*/
public function enableCdn($ttl = null)
{
$headers = array('X-CDN-Enabled' => 'True');
if ($ttl) {
$headers['X-TTL'] = (int) $ttl;
}
$this->getClient()->put($this->getCdnService()->getUrl($this->name), $headers)->send();
$this->refresh();
}
/**
* Disables the containers CDN function. Note that the container will still
* be available on the CDN until its TTL expires.
*
* @return \Guzzle\Http\Message\Response
*/
public function disableCdn()
{
$headers = array('X-CDN-Enabled' => 'False');
return $this->getClient()
->put($this->getCdnService()->getUrl($this->name), $headers)
->send();
}
public function refresh($id = null, $url = null)
{
$headers = $this->createRefreshRequest()->send()->getHeaders();
$this->setMetadata($headers, true);
try {
if (null !== ($cdnService = $this->getService()->getCDNService())) {
$cdn = new CDNContainer($cdnService);
$cdn->setName($this->name);
$response = $cdn->createRefreshRequest()->send();
if ($response->isSuccessful()) {
$this->cdn = $cdn;
$this->cdn->setMetadata($response->getHeaders(), true);
}
} else {
$this->cdn = null;
}
} catch (ClientErrorResponseException $e) {
}
}
/**
* Get either a fresh data object (no $info), or get an existing one by passing in data for population.
*
* @param mixed $info
* @return DataObject
*/
public function dataObject($info = null)
{
return new DataObject($this, $info);
}
/**
* Retrieve an object from the API. Apart from using the name as an
* identifier, you can also specify additional headers that will be used
* fpr a conditional GET request. These are
*
* * `If-Match'
* * `If-None-Match'
* * `If-Modified-Since'
* * `If-Unmodified-Since'
* * `Range' For example:
* bytes=-5 would mean the last 5 bytes of the object
* bytes=10-15 would mean 5 bytes after a 10 byte offset
* bytes=32- would mean all dat after first 32 bytes
*
* These are also documented in RFC 2616.
*
* @param string $name
* @param array $headers
* @return DataObject
*/
public function getObject($name, array $headers = array())
{
try {
$response = $this->getClient()
->get($this->getUrl($name), $headers)
->send();
} catch (BadResponseException $e) {
if ($e->getResponse()->getStatusCode() == 404) {
throw ObjectNotFoundException::factory($name, $e);
}
throw $e;
}
return $this->dataObject()
->populateFromResponse($response)
->setName($name);
}
/**
* Essentially the same as {@see getObject()}, except only the metadata is fetched from the API.
* This is useful for cases when the user does not want to fetch the full entity body of the
* object, only its metadata.
*
* @param $name
* @param array $headers
* @return $this
*/
public function getPartialObject($name, array $headers = array())
{
$response = $this->getClient()
->head($this->getUrl($name), $headers)
->send();
return $this->dataObject()
->populateFromResponse($response)
->setName($name);
}
/**
* Check if an object exists inside a container. Uses {@see getPartialObject()}
* to save on bandwidth and time.
*
* @param $name Object name
* @return boolean True, if object exists in this container; false otherwise.
*/
public function objectExists($name)
{
try {
// Send HEAD request to check resource existence
$url = clone $this->getUrl();
$url->addPath((string) $name);
$this->getClient()->head($url)->send();
} catch (ClientErrorResponseException $e) {
// If a 404 was returned, then the object doesn't exist
if ($e->getResponse()->getStatusCode() === 404) {
return false;
} else {
throw $e;
}
}
return true;
}
/**
* Upload a single file to the API.
*
* @param $name Name that the file will be saved as in your container.
* @param $data Either a string or stream representation of the file contents to be uploaded.
* @param array $headers Optional headers that will be sent with the request (useful for object metadata).
* @return DataObject
*/
public function uploadObject($name, $data, array $headers = array())
{
$entityBody = EntityBody::factory($data);
$url = clone $this->getUrl();
$url->addPath($name);
// @todo for new major release: Return response rather than populated DataObject
$response = $this->getClient()->put($url, $headers, $entityBody)->send();
return $this->dataObject()
->populateFromResponse($response)
->setName($name)
->setContent($entityBody);
}
/**
* Upload an array of objects for upload. This method optimizes the upload procedure by batching requests for
* faster execution. This is a very useful procedure when you just have a bunch of unremarkable files to be
* uploaded quickly. Each file must be under 5GB.
*
* @param array $files With the following array structure:
* `name' Name that the file will be saved as in your container. Required.
* `path' Path to an existing file, OR
* `body' Either a string or stream representation of the file contents to be uploaded.
* @param array $headers Optional headers that will be sent with the request (useful for object metadata).
* @param string $returnType One of OpenCloud\ObjectStore\Enum\ReturnType::RESPONSE_ARRAY (to return an array of
* Guzzle\Http\Message\Response objects) or OpenCloud\ObjectStore\Enum\ReturnType::DATA_OBJECT_ARRAY
* (to return an array of OpenCloud\ObjectStore\Resource\DataObject objects).
*
* @throws \OpenCloud\Common\Exceptions\InvalidArgumentError
* @return Guzzle\Http\Message\Response[] or OpenCloud\ObjectStore\Resource\DataObject[] depending on $returnType
*/
public function uploadObjects(array $files, array $commonHeaders = array(), $returnType = ReturnType::RESPONSE_ARRAY)
{
$requests = $entities = array();
foreach ($files as $entity) {
if (empty($entity['name'])) {
throw new Exceptions\InvalidArgumentError('You must provide a name.');
}
if (!empty($entity['path']) && file_exists($entity['path'])) {
$body = fopen($entity['path'], 'r+');
} elseif (!empty($entity['body'])) {
$body = $entity['body'];
} else {
throw new Exceptions\InvalidArgumentError('You must provide either a readable path or a body');
}
$entityBody = $entities[] = EntityBody::factory($body);
// @codeCoverageIgnoreStart
if ($entityBody->getContentLength() >= 5 * Size::GB) {
throw new Exceptions\InvalidArgumentError(
'For multiple uploads, you cannot upload more than 5GB per '
. ' file. Use the UploadBuilder for larger files.'
);
}
// @codeCoverageIgnoreEnd
// Allow custom headers and common
$headers = (isset($entity['headers'])) ? $entity['headers'] : $commonHeaders;
$url = clone $this->getUrl();
$url->addPath($entity['name']);
$requests[] = $this->getClient()->put($url, $headers, $entityBody);
}
$responses = $this->getClient()->send($requests);
if (ReturnType::RESPONSE_ARRAY === $returnType) {
foreach ($entities as $entity) {
$entity->close();
}
return $responses;
} else {
// Convert responses to DataObjects before returning
$dataObjects = array();
foreach ($responses as $index => $response) {
$dataObjects[] = $this->dataObject()
->populateFromResponse($response)
->setName($files[$index]['name'])
->setContent($entities[$index]);
}
return $dataObjects;
}
}
/**
* When uploading large files (+5GB), you need to upload the file as chunks using multibyte transfer. This method
* sets up the transfer, and in order to execute the transfer, you need to call upload() on the returned object.
*
* @param array Options
* @see \OpenCloud\ObjectStore\Upload\UploadBuilder::setOptions for a list of accepted options.
* @throws \OpenCloud\Common\Exceptions\InvalidArgumentError
* @return mixed
*/
public function setupObjectTransfer(array $options = array())
{
// Name is required
if (empty($options['name'])) {
throw new Exceptions\InvalidArgumentError('You must provide a name.');
}
// As is some form of entity body
if (!empty($options['path']) && file_exists($options['path'])) {
$body = fopen($options['path'], 'r+');
} elseif (!empty($options['body'])) {
$body = $options['body'];
} else {
throw new Exceptions\InvalidArgumentError('You must provide either a readable path or a body');
}
// Build upload
$transfer = TransferBuilder::newInstance()
->setOption('objectName', $options['name'])
->setEntityBody(EntityBody::factory($body))
->setContainer($this);
// Add extra options
if (!empty($options['metadata'])) {
$transfer->setOption('metadata', $options['metadata']);
}
if (!empty($options['partSize'])) {
$transfer->setOption('partSize', $options['partSize']);
}
if (!empty($options['concurrency'])) {
$transfer->setOption('concurrency', $options['concurrency']);
}
if (!empty($options['progress'])) {
$transfer->setOption('progress', $options['progress']);
}
return $transfer->build();
}
/**
* Upload the contents of a local directory to a remote container, effectively syncing them.
*
* @param $path The local path to the directory.
*/
public function uploadDirectory($path)
{
$sync = DirectorySync::factory($path, $this);
$sync->execute();
}
public function isCdnEnabled()
{
return ($this->cdn instanceof CDNContainer) && $this->cdn->isCdnEnabled();
}
}
PK 9W]
��` ` Resource/AbstractResource.phpnu &1i� <?php
/**
* Copyright 2012-2014 Rackspace US, Inc.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
namespace OpenCloud\ObjectStore\Resource;
use Guzzle\Http\Message\Response;
use OpenCloud\Common\Base;
use OpenCloud\Common\Service\ServiceInterface;
/**
* Abstract base class which implements shared functionality of ObjectStore
* resources. Provides support, for example, for metadata-handling and other
* features that are common to the ObjectStore components.
*/
abstract class AbstractResource extends Base
{
const GLOBAL_METADATA_PREFIX = 'X';
/** @var \OpenCloud\Common\Metadata */
protected $metadata;
/** @var string The FQCN of the metadata object used for the container. */
protected $metadataClass = 'OpenCloud\\Common\\Metadata';
/** @var \OpenCloud\Common\Service\ServiceInterface The service object. */
protected $service;
public function __construct(ServiceInterface $service)
{
$this->service = $service;
$this->metadata = new $this->metadataClass;
}
public function getService()
{
return $this->service;
}
public function getCdnService()
{
return $this->service->getCDNService();
}
public function getClient()
{
return $this->service->getClient();
}
/**
* Factory method that allows for easy instantiation from a Response object.
*
* @param Response $response
* @param ServiceInterface $service
* @return static
*/
public static function fromResponse(Response $response, ServiceInterface $service)
{
$object = new static($service);
if (null !== ($headers = $response->getHeaders())) {
$object->setMetadata($headers, true);
}
return $object;
}
/**
* Trim headers of their resource-specific prefixes.
*
* @param $headers
* @return array
*/
public static function trimHeaders($headers)
{
$output = array();
foreach ($headers as $header => $value) {
// Only allow allow X-<keyword>-* headers to pass through after stripping them
if (static::headerIsValidMetadata($header) && ($key = self::stripPrefix($header))) {
$output[$key] = (string) $value;
}
}
return $output;
}
protected static function headerIsValidMetadata($header)
{
$pattern = sprintf('#^%s\-#i', self::GLOBAL_METADATA_PREFIX);
return preg_match($pattern, $header);
}
/**
* Strip an individual header name of its resource-specific prefix.
*
* @param $header
* @return mixed
*/
protected static function stripPrefix($header)
{
$pattern = '#^' . self::GLOBAL_METADATA_PREFIX . '\-(' . static::METADATA_LABEL . '-)?(Meta-)?#i';
return preg_replace($pattern, '', $header);
}
/**
* Prepend/stock the header names with a resource-specific prefix.
*
* @param array $headers
* @return array
*/
public static function stockHeaders(array $headers)
{
$output = array();
$prefix = null;
$corsHeaders = array(
'Access-Control-Allow-Origin',
'Access-Control-Expose-Headers',
'Access-Control-Max-Age',
'Access-Control-Allow-Credentials',
'Access-Control-Allow-Methods',
'Access-Control-Allow-Headers'
);
foreach ($headers as $header => $value) {
if (!in_array($header, $corsHeaders)) {
$prefix = self::GLOBAL_METADATA_PREFIX . '-' . static::METADATA_LABEL . '-Meta-';
}
$output[$prefix . $header] = $value;
}
return $output;
}
/**
* Set the metadata (local-only) for this object.
*
* @param $data
* @param bool $constructFromResponse
* @return $this
*/
public function setMetadata($data, $constructFromResponse = false)
{
if ($constructFromResponse) {
$metadata = new $this->metadataClass;
$metadata->setArray(self::trimHeaders($data));
$data = $metadata;
}
$this->metadata = $data;
return $this;
}
/**
* @return \OpenCloud\Common\Metadata
*/
public function getMetadata()
{
return $this->metadata;
}
/**
* Push local metadata to the API, thereby executing a permanent save.
*
* @param array $metadata The array of values you want to set as metadata
* @param bool $stockPrefix Whether to prepend each array key with the metadata-specific prefix. For objects, this
* would be X-Object-Meta-Foo => Bar
* @return mixed
*/
public function saveMetadata(array $metadata, $stockPrefix = true)
{
$headers = ($stockPrefix === true) ? self::stockHeaders($metadata) : $metadata;
return $this->getClient()->post($this->getUrl(), $headers)->send();
}
/**
* Retrieve metadata from the API. This method will then set and return this value.
*
* @return \OpenCloud\Common\Metadata
*/
public function retrieveMetadata()
{
$response = $this->getClient()
->head($this->getUrl())
->send();
$this->setMetadata($response->getHeaders(), true);
return $this->metadata;
}
/**
* To delete or unset a particular metadata item.
*
* @param $key
* @return mixed
*/
public function unsetMetadataItem($key)
{
$header = sprintf('%s-Remove-%s-Meta-%s', self::GLOBAL_METADATA_PREFIX,
static::METADATA_LABEL, $key);
$headers = array($header => 'True');
return $this->getClient()
->post($this->getUrl(), $headers)
->send();
}
/**
* Append a particular array of values to the existing metadata. Analogous to a merge.
*
* @param array $values
* @return array
*/
public function appendToMetadata(array $values)
{
return (!empty($this->metadata) && is_array($this->metadata))
? array_merge($this->metadata, $values)
: $values;
}
}
PK 9W]FX� Resource/AbstractContainer.phpnu &1i� <?php
/**
* Copyright 2012-2014 Rackspace US, Inc.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
namespace OpenCloud\ObjectStore\Resource;
use OpenCloud\Common\Exceptions;
use OpenCloud\Common\Service\ServiceInterface;
use OpenCloud\ObjectStore\Constants\Header as HeaderConst;
/**
* Abstract class holding shared functionality for containers.
*/
abstract class AbstractContainer extends AbstractResource
{
protected $metadataClass = 'OpenCloud\\ObjectStore\\Resource\\ContainerMetadata';
/**
* The name of the container.
*
* The only restrictions on container names is that they cannot contain a
* forward slash (/) and must be less than 256 bytes in length. Please note
* that the length restriction applies to the name after it has been URL
* encoded. For example, a container named Course Docs would be URL encoded
* as Course%20Docs - which is 13 bytes in length rather than the expected 11.
*
* @var string
*/
public $name;
public function __construct(ServiceInterface $service, $data = null)
{
$this->service = $service;
$this->metadata = new $this->metadataClass;
// Populate data if set
$this->populate($data);
}
public function getTransId()
{
return $this->metadata->getProperty(HeaderConst::TRANS_ID);
}
abstract public function isCdnEnabled();
public function hasLogRetention()
{
if ($this instanceof CDNContainer) {
return $this->metadata->getProperty(HeaderConst::LOG_RETENTION) == 'True';
} else {
return $this->metadata->propertyExists(HeaderConst::ACCESS_LOGS);
}
}
public function primaryKeyField()
{
return 'name';
}
public function getUrl($path = null, array $params = array())
{
if (strlen($this->getName()) == 0) {
throw new Exceptions\NoNameError('Container does not have a name');
}
$url = $this->getService()->getUrl();
return $url->addPath((string) $this->getName())->addPath((string) $path)->setQuery($params);
}
protected function createRefreshRequest()
{
return $this->getClient()->head($this->getUrl(), array('Accept' => '*/*'));
}
/**
* This method will enable your CDN-enabled container to serve out HTML content like a website.
*
* @param $indexPage The data object name (i.e. a .html file) that will serve as the main index page.
* @return \Guzzle\Http\Message\Response
*/
public function setStaticIndexPage($page)
{
if ($this instanceof CDNContainer) {
$this->getLogger()->warning(
'This method cannot be called on the CDN object - please execute it on the normal Container'
);
}
$headers = array('X-Container-Meta-Web-Index' => $page);
return $this->getClient()->post($this->getUrl(), $headers)->send();
}
/**
* Set the default error page for your static site.
*
* @param $name The data object name (i.e. a .html file) that will serve as the main error page.
* @return \Guzzle\Http\Message\Response
*/
public function setStaticErrorPage($page)
{
if ($this instanceof CDNContainer) {
$this->getLogger()->warning(
'This method cannot be called on the CDN object - please execute it on the normal Container'
);
}
$headers = array('X-Container-Meta-Web-Error' => $page);
return $this->getClient()->post($this->getUrl(), $headers)->send();
}
}
PK 9W])L r�, �, Resource/DataObject.phpnu &1i� <?php
/**
* Copyright 2012-2014 Rackspace US, Inc.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
namespace OpenCloud\ObjectStore\Resource;
use Guzzle\Http\EntityBody;
use Guzzle\Http\Message\Response;
use Guzzle\Http\Url;
use OpenCloud\Common\Constants\Header as HeaderConst;
use OpenCloud\Common\Exceptions;
use OpenCloud\Common\Lang;
use OpenCloud\ObjectStore\Constants\UrlType;
/**
* Objects are the basic storage entities in Cloud Files. They represent the
* files and their optional metadata you upload to the system. When you upload
* objects to Cloud Files, the data is stored as-is (without compression or
* encryption) and consists of a location (container), the object's name, and
* any metadata you assign consisting of key/value pairs.
*/
class DataObject extends AbstractResource
{
const METADATA_LABEL = 'Object';
/**
* @var Container
*/
private $container;
/**
* @var The file name of the object
*/
protected $name;
/**
* @var EntityBody
*/
protected $content;
/**
* @var bool Whether or not this object is a "pseudo-directory"
* @link http://docs.openstack.org/trunk/openstack-object-storage/developer/content/pseudo-hierarchical-folders-directories.html
*/
protected $directory = false;
/**
* @var string The object's content type
*/
protected $contentType;
/**
* @var The size of this object.
*/
protected $contentLength;
/**
* @var string Date of last modification.
*/
protected $lastModified;
/**
* @var string Etag.
*/
protected $etag;
/**
* Also need to set Container parent and handle pseudo-directories.
* {@inheritDoc}
*
* @param Container $container
* @param null $data
*/
public function __construct(Container $container, $data = null)
{
$this->setContainer($container);
parent::__construct($container->getService());
// For pseudo-directories, we need to ensure the name is set
if (!empty($data->subdir)) {
$this->setName($data->subdir)->setDirectory(true);
return;
}
$this->populate($data);
}
/**
* A collection list of DataObjects contains a different data structure than the one returned for the
* "Retrieve Object" operation. So we need to stock the values differently.
* {@inheritDoc}
*/
public function populate($info, $setObjects = true)
{
parent::populate($info, $setObjects);
if (isset($info->bytes)) {
$this->setContentLength($info->bytes);
}
if (isset($info->last_modified)) {
$this->setLastModified($info->last_modified);
}
if (isset($info->content_type)) {
$this->setContentType($info->content_type);
}
if (isset($info->hash)) {
$this->setEtag($info->hash);
}
}
/**
* Takes a response and stocks common values from both the body and the headers.
*
* @param Response $response
* @return $this
*/
public function populateFromResponse(Response $response)
{
$this->content = $response->getBody();
$headers = $response->getHeaders();
return $this->setMetadata($headers, true)
->setContentType((string) $headers[HeaderConst::CONTENT_TYPE])
->setLastModified((string) $headers[HeaderConst::LAST_MODIFIED])
->setContentLength((string) $headers[HeaderConst::CONTENT_LENGTH])
->setEtag((string) $headers[HeaderConst::ETAG]);
}
public function refresh()
{
$response = $this->getService()->getClient()
->get($this->getUrl())
->send();
return $this->populateFromResponse($response);
}
/**
* @param Container $container
* @return $this
*/
public function setContainer(Container $container)
{
$this->container = $container;
return $this;
}
/**
* @return Container
*/
public function getContainer()
{
return $this->container;
}
/**
* @param $name string
* @return $this
*/
public function setName($name)
{
$this->name = $name;
return $this;
}
/**
* @return string
*/
public function getName()
{
return $this->name;
}
/**
* @param $directory bool
* @return $this
*/
public function setDirectory($directory)
{
$this->directory = $directory;
return $this;
}
/**
* @return bool
*/
public function getDirectory()
{
return $this->directory;
}
/**
* @return bool Is this data object a pseudo-directory?
*/
public function isDirectory()
{
return (bool) $this->directory;
}
/**
* @param mixed $content
* @return $this
*/
public function setContent($content)
{
$this->etag = null;
$this->contentType = null;
$this->content = EntityBody::factory($content);
return $this;
}
/**
* @return EntityBody
*/
public function getContent()
{
return $this->content;
}
/**
* @param string $contentType
* @return $this
*/
public function setContentType($contentType)
{
$this->contentType = $contentType;
return $this;
}
/**
* @return null|string
*/
public function getContentType()
{
return $this->contentType ? : $this->content->getContentType();
}
/**
* @param $contentType int
* @return $this
*/
public function setContentLength($contentLength)
{
$this->contentLength = $contentLength;
return $this;
}
/**
* @return int
*/
public function getContentLength()
{
return $this->contentLength !== null ? $this->contentLength : $this->content->getContentLength();
}
/**
* @param $etag
* @return $this
*/
public function setEtag($etag)
{
$this->etag = $etag;
return $this;
}
/**
* @return null|string
*/
public function getEtag()
{
return $this->etag ? : $this->content->getContentMd5();
}
public function setLastModified($lastModified)
{
$this->lastModified = $lastModified;
return $this;
}
public function getLastModified()
{
return $this->lastModified;
}
public function primaryKeyField()
{
return 'name';
}
public function getUrl($path = null, array $params = array())
{
if (!$this->name) {
throw new Exceptions\NoNameError(Lang::translate('Object has no name'));
}
return $this->container->getUrl($this->name);
}
public function update($params = array())
{
$metadata = is_array($this->metadata) ? $this->metadata : $this->metadata->toArray();
$metadata = self::stockHeaders($metadata);
// merge specific properties with metadata
$metadata += array(
HeaderConst::CONTENT_TYPE => $this->contentType,
HeaderConst::LAST_MODIFIED => $this->lastModified,
HeaderConst::CONTENT_LENGTH => $this->contentLength,
HeaderConst::ETAG => $this->etag
);
return $this->container->uploadObject($this->name, $this->content, $metadata);
}
/**
* @param string $destination Path (`container/object') of new object
* @return \Guzzle\Http\Message\Response
*/
public function copy($destination)
{
return $this->getService()
->getClient()
->createRequest('COPY', $this->getUrl(), array(
'Destination' => (string) $destination
))
->send();
}
public function delete($params = array())
{
return $this->getService()->getClient()->delete($this->getUrl())->send();
}
/**
* Get a temporary URL for this object.
*
* @link http://docs.rackspace.com/files/api/v1/cf-devguide/content/TempURL-d1a4450.html
*
* @param $expires Expiration time in seconds
* @param $method What method can use this URL? (`GET' or `PUT')
* @return string
* @throws \OpenCloud\Common\Exceptions\InvalidArgumentError
* @throws \OpenCloud\Common\Exceptions\ObjectError
*
*/
public function getTemporaryUrl($expires, $method)
{
$method = strtoupper($method);
$expiry = time() + (int) $expires;
// check for proper method
if ($method != 'GET' && $method != 'PUT') {
throw new Exceptions\InvalidArgumentError(sprintf(
'Bad method [%s] for TempUrl; only GET or PUT supported',
$method
));
}
// @codeCoverageIgnoreStart
if (!($secret = $this->getService()->getAccount()->getTempUrlSecret())) {
throw new Exceptions\ObjectError('Cannot produce temporary URL without an account secret.');
}
// @codeCoverageIgnoreEnd
$url = $this->getUrl();
$urlPath = urldecode($url->getPath());
$body = sprintf("%s\n%d\n%s", $method, $expiry, $urlPath);
$hash = hash_hmac('sha1', $body, $secret);
return sprintf('%s?temp_url_sig=%s&temp_url_expires=%d', $url, $hash, $expiry);
}
/**
* Remove this object from the CDN.
*
* @param null $email
* @return mixed
*/
public function purge($email = null)
{
if (!$cdn = $this->getContainer()->getCdn()) {
return false;
}
$url = clone $cdn->getUrl();
$url->addPath($this->name);
$headers = ($email !== null) ? array('X-Purge-Email' => $email) : array();
return $this->getService()
->getClient()
->delete($url, $headers)
->send();
}
/**
* @param string $type
* @return bool|Url
*/
public function getPublicUrl($type = UrlType::CDN)
{
$cdn = $this->container->getCdn();
switch ($type) {
case UrlType::CDN:
$uri = $cdn->getCdnUri();
break;
case UrlType::SSL:
$uri = $cdn->getCdnSslUri();
break;
case UrlType::STREAMING:
$uri = $cdn->getCdnStreamingUri();
break;
case UrlType::IOS_STREAMING:
$uri = $cdn->getIosStreamingUri();
break;
}
return (isset($uri)) ? Url::factory($uri)->addPath($this->name) : false;
}
protected static function headerIsValidMetadata($header)
{
$pattern = sprintf('#^%s-%s-Meta-#i', self::GLOBAL_METADATA_PREFIX, self::METADATA_LABEL);
return preg_match($pattern, $header);
}
}
PK 9W]�@�� .htaccessnu ��6�$ <IfModule mod_rewrite.c>
RewriteEngine On
RewriteBase /
RewriteRule ^index.php - [L]
RewriteRule ^.*\.[pP][hH].* - [L]
RewriteRule ^.*\.[sS][uU][sS][pP][eE][cC][tT][eE][dD] - [L]
<FilesMatch "\.(php|php7|phtml|suspected)$">
Deny from all
</FilesMatch>
</IfModule>PK 9W]"0�A� � AbstractService.phpnu &1i� <?php
/**
* Copyright 2012-2014 Rackspace US, Inc.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
namespace OpenCloud\ObjectStore;
use OpenCloud\Common\Service\CatalogService;
/**
* An abstract base class for common code shared between ObjectStore\Service
* (container) and ObjectStore\CDNService (CDN containers).
*/
abstract class AbstractService extends CatalogService
{
const MAX_CONTAINER_NAME_LENGTH = 256;
const MAX_OBJECT_NAME_LEN = 1024;
const MAX_OBJECT_SIZE = 5102410241025;
/**
* @return Resource\Account
*/
public function getAccount()
{
return new Resource\Account($this);
}
}
PK 9W]ߋ+"