Home | History | Annotate | Download | only in fileapi
      1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
      2 // Use of this source code is governed by a BSD-style license that can be
      3 // found in the LICENSE file.
      4 
      5 #include "webkit/browser/fileapi/file_system_url.h"
      6 
      7 #include <sstream>
      8 
      9 #include "base/logging.h"
     10 #include "base/strings/string_util.h"
     11 #include "net/base/escape.h"
     12 #include "webkit/common/fileapi/file_system_types.h"
     13 #include "webkit/common/fileapi/file_system_util.h"
     14 
     15 namespace fileapi {
     16 
     17 namespace {
     18 
     19 }  // namespace
     20 
     21 FileSystemURL::FileSystemURL()
     22     : is_valid_(false),
     23       mount_type_(kFileSystemTypeUnknown),
     24       type_(kFileSystemTypeUnknown),
     25       mount_option_(COPY_SYNC_OPTION_NO_SYNC) {
     26 }
     27 
     28 // static
     29 FileSystemURL FileSystemURL::CreateForTest(const GURL& url) {
     30   return FileSystemURL(url);
     31 }
     32 
     33 FileSystemURL FileSystemURL::CreateForTest(const GURL& origin,
     34                                            FileSystemType mount_type,
     35                                            const base::FilePath& virtual_path) {
     36   return FileSystemURL(origin, mount_type, virtual_path);
     37 }
     38 
     39 FileSystemURL::FileSystemURL(const GURL& url)
     40     : mount_type_(kFileSystemTypeUnknown),
     41       type_(kFileSystemTypeUnknown),
     42       mount_option_(COPY_SYNC_OPTION_NO_SYNC) {
     43   is_valid_ = ParseFileSystemSchemeURL(url, &origin_, &mount_type_,
     44                                        &virtual_path_);
     45   path_ = virtual_path_;
     46   type_ = mount_type_;
     47 }
     48 
     49 FileSystemURL::FileSystemURL(const GURL& origin,
     50                              FileSystemType mount_type,
     51                              const base::FilePath& virtual_path)
     52     : is_valid_(true),
     53       origin_(origin),
     54       mount_type_(mount_type),
     55       virtual_path_(virtual_path.NormalizePathSeparators()),
     56       type_(mount_type),
     57       path_(virtual_path.NormalizePathSeparators()),
     58       mount_option_(COPY_SYNC_OPTION_NO_SYNC) {
     59 }
     60 
     61 FileSystemURL::FileSystemURL(const GURL& origin,
     62                              FileSystemType mount_type,
     63                              const base::FilePath& virtual_path,
     64                              const std::string& mount_filesystem_id,
     65                              FileSystemType cracked_type,
     66                              const base::FilePath& cracked_path,
     67                              const std::string& filesystem_id,
     68                              const FileSystemMountOption& mount_option)
     69     : is_valid_(true),
     70       origin_(origin),
     71       mount_type_(mount_type),
     72       virtual_path_(virtual_path.NormalizePathSeparators()),
     73       mount_filesystem_id_(mount_filesystem_id),
     74       type_(cracked_type),
     75       path_(cracked_path.NormalizePathSeparators()),
     76       filesystem_id_(filesystem_id),
     77       mount_option_(mount_option) {
     78 }
     79 
     80 FileSystemURL::~FileSystemURL() {}
     81 
     82 GURL FileSystemURL::ToGURL() const {
     83   if (!is_valid_)
     84     return GURL();
     85 
     86   std::string url = GetFileSystemRootURI(origin_, mount_type_).spec();
     87   if (url.empty())
     88     return GURL();
     89 
     90   // Exactly match with DOMFileSystemBase::createFileSystemURL()'s encoding
     91   // behavior, where the path is escaped by KURL::encodeWithURLEscapeSequences
     92   // which is essentially encodeURIComponent except '/'.
     93   std::string escaped = net::EscapeQueryParamValue(
     94       virtual_path_.NormalizePathSeparatorsTo('/').AsUTF8Unsafe(),
     95       false /* use_plus */);
     96   ReplaceSubstringsAfterOffset(&escaped, 0, "%2F", "/");
     97   url.append(escaped);
     98 
     99   // Build nested GURL.
    100   return GURL(url);
    101 }
    102 
    103 std::string FileSystemURL::DebugString() const {
    104   if (!is_valid_)
    105     return "invalid filesystem: URL";
    106   std::ostringstream ss;
    107   ss << GetFileSystemRootURI(origin_, mount_type_);
    108 
    109   // filesystem_id_ will be non empty for (and only for) cracked URLs.
    110   if (!filesystem_id_.empty()) {
    111     ss << virtual_path_.value();
    112     ss << " (";
    113     ss << GetFileSystemTypeString(type_) << "@" << filesystem_id_ << ":";
    114     ss << path_.value();
    115     ss << ")";
    116   } else {
    117     ss << path_.value();
    118   }
    119   return ss.str();
    120 }
    121 
    122 bool FileSystemURL::IsParent(const FileSystemURL& child) const {
    123   return IsInSameFileSystem(child) &&
    124          path().IsParent(child.path());
    125 }
    126 
    127 bool FileSystemURL::IsInSameFileSystem(const FileSystemURL& other) const {
    128   return origin() == other.origin() &&
    129          type() == other.type() &&
    130          filesystem_id() == other.filesystem_id();
    131 }
    132 
    133 bool FileSystemURL::operator==(const FileSystemURL& that) const {
    134   return origin_ == that.origin_ &&
    135       type_ == that.type_ &&
    136       path_ == that.path_ &&
    137       filesystem_id_ == that.filesystem_id_ &&
    138       is_valid_ == that.is_valid_;
    139 }
    140 
    141 bool FileSystemURL::Comparator::operator()(const FileSystemURL& lhs,
    142                                            const FileSystemURL& rhs) const {
    143   DCHECK(lhs.is_valid_ && rhs.is_valid_);
    144   if (lhs.origin_ != rhs.origin_)
    145     return lhs.origin_ < rhs.origin_;
    146   if (lhs.type_ != rhs.type_)
    147     return lhs.type_ < rhs.type_;
    148   if (lhs.filesystem_id_ != rhs.filesystem_id_)
    149     return lhs.filesystem_id_ < rhs.filesystem_id_;
    150   return lhs.path_ < rhs.path_;
    151 }
    152 
    153 }  // namespace fileapi
    154