From 08b0af6d4dcd36aec30774dee132a3dad38050d8 Mon Sep 17 00:00:00 2001 From: Aaron Schulz Date: Thu, 19 Apr 2012 19:57:58 -0700 Subject: [PATCH] Added getRootStoragePath() convenience function to get the root path. Also includes some whitespace cleanup. Change-Id: I40b36bd5fc4da6ee948406a385dfa5c6d90de859 --- includes/filerepo/backend/FileBackend.php | 135 ++++++++++++---------- 1 file changed, 73 insertions(+), 62 deletions(-) diff --git a/includes/filerepo/backend/FileBackend.php b/includes/filerepo/backend/FileBackend.php index 44f4d9402f..b9821bfd31 100644 --- a/includes/filerepo/backend/FileBackend.php +++ b/includes/filerepo/backend/FileBackend.php @@ -18,24 +18,24 @@ * * This class defines the methods as abstract that subclasses must implement. * Outside callers can assume that all backends will have these functions. - * + * * All "storage paths" are of the format "mwstore:////". - * The portion is a relative path that uses UNIX file system (FS) notation, - * though any particular backend may not actually be using a local filesystem. + * The portion is a relative path that uses UNIX file system (FS) notation, + * though any particular backend may not actually be using a local filesystem. * Therefore, the relative paths are only virtual. - * + * * Backend contents are stored under wiki-specific container names by default. * For legacy reasons, this has no effect for the FS backend class, and per-wiki * segregation must be done by setting the container paths appropriately. - * + * * FS-based backends are somewhat more restrictive due to the existence of real * directory files; a regular file cannot have the same name as a directory. Other * backends with virtual directories may not have this limitation. Callers should * store files in such a way that no files and directories are under the same path. - * + * * Methods should avoid throwing exceptions at all costs. * As a corollary, external dependencies should be kept to a minimum. - * + * * @ingroup FileBackend * @since 1.19 */ @@ -51,7 +51,7 @@ abstract class FileBackend { /** * Create a new backend instance from configuration. * This should only be called from within FileBackendGroup. - * + * * $config includes: * 'name' : The unique name of this backend. * This should consist of alphanumberic, '-', and '_' characters. @@ -63,7 +63,7 @@ abstract class FileBackend { * Journals simply log changes to files stored in the backend. * 'readOnly' : Write operations are disallowed if this is a non-empty string. * It should be an explanation for the backend being read-only. - * + * * @param $config Array */ public function __construct( array $config ) { @@ -89,7 +89,7 @@ abstract class FileBackend { * Get the unique backend name. * We may have multiple different backends of the same type. * For example, we can have two Swift backends using different proxies. - * + * * @return string */ final public function getName() { @@ -98,7 +98,7 @@ abstract class FileBackend { /** * Check if this backend is read-only - * + * * @return bool */ final public function isReadOnly() { @@ -107,7 +107,7 @@ abstract class FileBackend { /** * Get an explanatory message if this backend is read-only - * + * * @return string|bool Returns false if the backend is not read-only */ final public function getReadOnlyReason() { @@ -119,10 +119,10 @@ abstract class FileBackend { * Callers supply an ordered list of operations to perform as a transaction. * Files will be locked, the stat cache cleared, and then the operations attempted. * If any serious errors occur, all attempted operations will be rolled back. - * + * * $ops is an array of arrays. The outer array holds a list of operations. * Each inner array is a set of key value pairs that specify an operation. - * + * * Supported operations and their parameters: * a) Create a new file in storage with the contents of a string * array( @@ -166,7 +166,7 @@ abstract class FileBackend { * array( * 'op' => 'null', * ) - * + * * Boolean flags for operations (operation-specific): * 'ignoreMissingSource' : The operation will simply succeed and do * nothing if the source file does not exist. @@ -174,7 +174,7 @@ abstract class FileBackend { * 'overwriteSame' : An error will not be given if a file already * exists at the destination that has the same * contents as the new contents to be written there. - * + * * $opts is an associative of boolean flags, including: * 'force' : Errors that would normally cause a rollback do not. * The remaining operations are still attempted if any fail. @@ -186,19 +186,19 @@ abstract class FileBackend { * This has no effect unless the 'force' flag is set. * 'nonJournaled' : Don't log this operation batch in the file journal. * This limits the ability of recovery scripts. - * + * * Remarks on locking: * File system paths given to operations should refer to files that are * already locked or otherwise safe from modification from other processes. * Normally these files will be new temp files, which should be adequate. - * + * * Return value: * This returns a Status, which contains all warnings and fatals that occured * during the operation. The 'failCount', 'successCount', and 'success' members * will reflect each operation attempted. The status will be "OK" unless: * a) unexpected operation errors occurred (network partitions, disk full...) * b) significant operation errors occured and 'force' was not set - * + * * @param $ops Array List of operations to execute in order * @param $opts Array Batch operation options * @return Status @@ -327,10 +327,10 @@ abstract class FileBackend { * Prepare a storage directory for usage. * This will create any required containers and parent directories. * Backends using key/value stores only need to create the container. - * + * * $params include: * dir : storage directory - * + * * @param $params Array * @return Status */ @@ -352,12 +352,12 @@ abstract class FileBackend { * files whereas key/value store backends might restrict container * access to the auth user that represents end-users in web request. * This is not guaranteed to actually do anything. - * + * * $params include: * dir : storage directory * noAccess : try to deny file access * noListing : try to deny file listing - * + * * @param $params Array * @return Status */ @@ -381,10 +381,10 @@ abstract class FileBackend { * Delete a storage directory if it is empty. * Backends using key/value stores may do nothing unless the directory * is that of an empty container, in which case it should be deleted. - * + * * $params include: * dir : storage directory - * + * * @param $params Array * @return Status */ @@ -403,11 +403,11 @@ abstract class FileBackend { /** * Check if a file exists at a storage path in the backend. * This returns false if only a directory exists at the path. - * + * * $params include: * src : source storage path * latest : use the latest available data - * + * * @param $params Array * @return bool|null Returns null on failure */ @@ -415,11 +415,11 @@ abstract class FileBackend { /** * Get the last-modified timestamp of the file at a storage path. - * + * * $params include: * src : source storage path * latest : use the latest available data - * + * * @param $params Array * @return string|bool TS_MW timestamp or false on failure */ @@ -428,11 +428,11 @@ abstract class FileBackend { /** * Get the contents of a file at a storage path in the backend. * This should be avoided for potentially large files. - * + * * $params include: * src : source storage path * latest : use the latest available data - * + * * @param $params Array * @return string|bool Returns false on failure */ @@ -440,11 +440,11 @@ abstract class FileBackend { /** * Get the size (bytes) of a file at a storage path in the backend. - * + * * $params include: * src : source storage path * latest : use the latest available data - * + * * @param $params Array * @return integer|bool Returns false on failure */ @@ -457,11 +457,11 @@ abstract class FileBackend { * mtime : the last-modified timestamp (TS_MW) * size : the file size (bytes) * Additional values may be included for internal use only. - * + * * $params include: * src : source storage path * latest : use the latest available data - * + * * @param $params Array * @return Array|bool|null Returns null on failure */ @@ -469,11 +469,11 @@ abstract class FileBackend { /** * Get a SHA-1 hash of the file at a storage path in the backend. - * + * * $params include: * src : source storage path * latest : use the latest available data - * + * * @param $params Array * @return string|bool Hash string or false on failure */ @@ -482,11 +482,11 @@ abstract class FileBackend { /** * Get the properties of the file at a storage path in the backend. * Returns FSFile::placeholderProps() on failure. - * + * * $params include: * src : source storage path * latest : use the latest available data - * + * * @param $params Array * @return Array */ @@ -498,12 +498,12 @@ abstract class FileBackend { * Appropriate HTTP headers (Status, Content-Type, Content-Length) * must be sent if streaming began, while none should be sent otherwise. * Implementations should flush the output buffer before sending data. - * + * * $params include: * src : source storage path * headers : additional HTTP headers to send on success * latest : use the latest available data - * + * * @param $params Array * @return Status */ @@ -516,16 +516,16 @@ abstract class FileBackend { * The temporary copy will have the same extension as the source. * b) An original of the file at a storage path in the backend. * Temporary files may be purged when the file object falls out of scope. - * + * * Write operations should *never* be done on this file as some backends * may do internal tracking or may be instances of FileBackendMultiWrite. * In that later case, there are copies of the file that must stay in sync. * Additionally, further calls to this function may return the same file. - * + * * $params include: * src : source storage path * latest : use the latest available data - * + * * @param $params Array * @return FSFile|null Returns null on failure */ @@ -535,11 +535,11 @@ abstract class FileBackend { * Get a local copy on disk of the file at a storage path in the backend. * The temporary copy will have the same file extension as the source. * Temporary files may be purged when the file object falls out of scope. - * + * * $params include: * src : source storage path * latest : use the latest available data - * + * * @param $params Array * @return TempFSFile|null Returns null on failure */ @@ -547,14 +547,14 @@ abstract class FileBackend { /** * Get an iterator to list out all stored files under a storage directory. - * If the directory is of the form "mwstore://backend/container", + * If the directory is of the form "mwstore://backend/container", * then all files in the container should be listed. * If the directory is of form "mwstore://backend/container/dir", * then all files under that container directory should be listed. * Results should be storage paths relative to the given directory. - * + * * Storage backends with eventual consistency might return stale data. - * + * * $params include: * dir : storage path directory * @@ -574,9 +574,9 @@ abstract class FileBackend { /** * Lock the files at the given storage paths in the backend. * This will either lock all the files or none (on failure). - * + * * Callers should consider using getScopedFileLocks() instead. - * + * * @param $paths Array Storage paths * @param $type integer LockManager::LOCK_* constant * @return Status @@ -587,7 +587,7 @@ abstract class FileBackend { /** * Unlock the files at the given storage paths in the backend. - * + * * @param $paths Array Storage paths * @param $type integer LockManager::LOCK_* constant * @return Status @@ -600,10 +600,10 @@ abstract class FileBackend { * Lock the files at the given storage paths in the backend. * This will either lock all the files or none (on failure). * On failure, the status object will be updated with errors. - * + * * Once the return value goes out scope, the locks will be released and * the status updated. Unlock fatals will not change the status "OK" value. - * + * * @param $paths Array Storage paths * @param $type integer LockManager::LOCK_* constant * @param $status Status Status to update on lock/unlock @@ -613,10 +613,21 @@ abstract class FileBackend { return ScopedLock::factory( $this->lockManager, $paths, $type, $status ); } + /** + * Get the root storage path of this backend. + * All container paths are "subdirectories" of this path. + * + * @return string Storage path + * @since 1.20 + */ + final public function getRootStoragePath() { + return "mwstore://{$this->name}"; + } + /** * Check if a given path is a "mwstore://" path. * This does not do any further validation or any existence checks. - * + * * @param $path string * @return bool */ @@ -625,7 +636,7 @@ abstract class FileBackend { } /** - * Split a storage path into a backend name, a container name, + * Split a storage path into a backend name, a container name, * and a relative file path. The relative path may be the empty string. * This does not do any path normalization or traversal checks. * @@ -640,7 +651,7 @@ abstract class FileBackend { if ( count( $parts ) == 3 ) { return $parts; // e.g. "backend/container/path" } else { - return array( $parts[0], $parts[1], '' ); // e.g. "backend/container" + return array( $parts[0], $parts[1], '' ); // e.g. "backend/container" } } } @@ -650,9 +661,9 @@ abstract class FileBackend { /** * Normalize a storage path by cleaning up directory separators. * Returns null if the path is not of the format of a valid storage path. - * + * * @param $storagePath string - * @return string|null + * @return string|null */ final public static function normalizeStoragePath( $storagePath ) { list( $backend, $container, $relPath ) = self::splitStoragePath( $storagePath ); @@ -671,7 +682,7 @@ abstract class FileBackend { * Get the parent storage directory of a storage path. * This returns a path like "mwstore://backend/container", * "mwstore://backend/container/...", or null if there is no parent. - * + * * @param $storagePath string * @return string|null */ @@ -683,7 +694,7 @@ abstract class FileBackend { /** * Get the final extension from a storage or FS path - * + * * @param $path string * @return string */ @@ -728,7 +739,7 @@ abstract class FileBackend { strpos( $path, '../' ) === 0 || strpos( $path, '/./' ) !== false || strpos( $path, '/../' ) !== false - ) { + ) { return null; } } -- 2.20.1