summaryrefslogtreecommitdiffstats
path: root/chrome/browser/chromeos/drive/fileapi/file_system_backend_delegate.cc
blob: 22fb9bc601511a874c762fcde90eaf1a5c4854a6 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
// Copyright 2014 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#include "chrome/browser/chromeos/drive/fileapi/file_system_backend_delegate.h"

#include "base/bind.h"
#include "base/files/file_path.h"
#include "base/memory/scoped_ptr.h"
#include "chrome/browser/chromeos/drive/file_system_util.h"
#include "chrome/browser/chromeos/drive/fileapi/async_file_util.h"
#include "chrome/browser/chromeos/drive/fileapi/fileapi_worker.h"
#include "chrome/browser/chromeos/drive/fileapi/webkit_file_stream_reader_impl.h"
#include "chrome/browser/chromeos/drive/fileapi/webkit_file_stream_writer_impl.h"
#include "components/drive/drive_api_util.h"
#include "components/drive/file_system_interface.h"
#include "content/public/browser/browser_thread.h"
#include "storage/browser/fileapi/async_file_util.h"
#include "storage/browser/fileapi/file_stream_reader.h"
#include "storage/browser/fileapi/file_system_context.h"
#include "storage/browser/fileapi/file_system_url.h"

using content::BrowserThread;

namespace drive {
namespace {

// Called on the UI thread after GetRedirectURLForContentsOnUIThread. Obtains
// the browser URL from |entry|. |callback| will be called on the IO thread.
void GetRedirectURLForContentsOnUIThreadWithResourceEntry(
    const storage::URLCallback& callback,
    FileError error,
    scoped_ptr<ResourceEntry> entry) {
  DCHECK_CURRENTLY_ON(BrowserThread::UI);
  GURL url;
  if (error == FILE_ERROR_OK && entry->has_file_specific_info() &&
      entry->file_specific_info().is_hosted_document()) {
    url = GURL(entry->file_specific_info().alternate_url());
  }
  BrowserThread::PostTask(
      BrowserThread::IO, FROM_HERE, base::Bind(callback, url));
}

// Called on the UI thread after
// FileSystemBackendDelegate::GetRedirectURLForContents.  Requestes to obtain
// ResourceEntry for the |url|.
void GetRedirectURLForContentsOnUIThread(
    const storage::FileSystemURL& url,
    const storage::URLCallback& callback) {
  DCHECK_CURRENTLY_ON(BrowserThread::UI);
  FileSystemInterface* const file_system =
      fileapi_internal::GetFileSystemFromUrl(url);
  if (!file_system) {
    BrowserThread::PostTask(
        BrowserThread::IO, FROM_HERE, base::Bind(callback, GURL()));
    return;
  }
  const base::FilePath file_path = util::ExtractDrivePathFromFileSystemUrl(url);
  if (file_path.empty()) {
    BrowserThread::PostTask(
        BrowserThread::IO, FROM_HERE, base::Bind(callback, GURL()));
    return;
  }

  file_system->GetResourceEntry(
      file_path,
      base::Bind(&GetRedirectURLForContentsOnUIThreadWithResourceEntry,
                 callback));
}

}  // namespace

FileSystemBackendDelegate::FileSystemBackendDelegate()
    : async_file_util_(new internal::AsyncFileUtil) {
}

FileSystemBackendDelegate::~FileSystemBackendDelegate() {
}

storage::AsyncFileUtil* FileSystemBackendDelegate::GetAsyncFileUtil(
    storage::FileSystemType type) {
  DCHECK_CURRENTLY_ON(BrowserThread::IO);
  DCHECK_EQ(storage::kFileSystemTypeDrive, type);
  return async_file_util_.get();
}

scoped_ptr<storage::FileStreamReader>
FileSystemBackendDelegate::CreateFileStreamReader(
    const storage::FileSystemURL& url,
    int64_t offset,
    int64_t max_bytes_to_read,
    const base::Time& expected_modification_time,
    storage::FileSystemContext* context) {
  DCHECK_CURRENTLY_ON(BrowserThread::IO);
  DCHECK_EQ(storage::kFileSystemTypeDrive, url.type());

  base::FilePath file_path = util::ExtractDrivePathFromFileSystemUrl(url);
  if (file_path.empty())
    return scoped_ptr<storage::FileStreamReader>();

  return scoped_ptr<storage::FileStreamReader>(
      new internal::WebkitFileStreamReaderImpl(
          base::Bind(&fileapi_internal::GetFileSystemFromUrl, url),
          context->default_file_task_runner(),
          file_path,
          offset,
          expected_modification_time));
}

scoped_ptr<storage::FileStreamWriter>
FileSystemBackendDelegate::CreateFileStreamWriter(
    const storage::FileSystemURL& url,
    int64_t offset,
    storage::FileSystemContext* context) {
  DCHECK_CURRENTLY_ON(BrowserThread::IO);
  DCHECK_EQ(storage::kFileSystemTypeDrive, url.type());

  base::FilePath file_path = util::ExtractDrivePathFromFileSystemUrl(url);
  // Hosted documents don't support stream writer.
  if (file_path.empty() || util::HasHostedDocumentExtension(file_path))
    return scoped_ptr<storage::FileStreamWriter>();

  return scoped_ptr<storage::FileStreamWriter>(
      new internal::WebkitFileStreamWriterImpl(
          base::Bind(&fileapi_internal::GetFileSystemFromUrl, url),
          context->default_file_task_runner(),
          file_path,
          offset));
}

storage::WatcherManager* FileSystemBackendDelegate::GetWatcherManager(
    storage::FileSystemType type) {
  NOTIMPLEMENTED();
  return NULL;
}

void FileSystemBackendDelegate::GetRedirectURLForContents(
    const storage::FileSystemURL& url,
    const storage::URLCallback& callback) {
  DCHECK_CURRENTLY_ON(BrowserThread::IO);
  BrowserThread::PostTask(
      BrowserThread::UI,
      FROM_HERE,
      base::Bind(&GetRedirectURLForContentsOnUIThread, url, callback));
}

}  // namespace drive