1// Copyright 2013 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#ifndef STORAGE_BROWSER_QUOTA_QUOTA_DATABASE_H_
6#define STORAGE_BROWSER_QUOTA_QUOTA_DATABASE_H_
7
8#include <set>
9#include <string>
10
11#include "base/basictypes.h"
12#include "base/callback.h"
13#include "base/files/file_path.h"
14#include "base/gtest_prod_util.h"
15#include "base/memory/scoped_ptr.h"
16#include "base/time/time.h"
17#include "base/timer/timer.h"
18#include "storage/browser/storage_browser_export.h"
19#include "storage/common/quota/quota_types.h"
20#include "url/gurl.h"
21
22namespace content {
23class QuotaDatabaseTest;
24}
25
26namespace sql {
27class Connection;
28class MetaTable;
29}
30
31class GURL;
32
33namespace storage {
34
35class SpecialStoragePolicy;
36
37// All the methods of this class must run on the DB thread.
38class STORAGE_EXPORT_PRIVATE QuotaDatabase {
39 public:
40  // Constants for {Get,Set}QuotaConfigValue keys.
41  static const char kDesiredAvailableSpaceKey[];
42  static const char kTemporaryQuotaOverrideKey[];
43
44  // If 'path' is empty, an in memory database will be used.
45  explicit QuotaDatabase(const base::FilePath& path);
46  ~QuotaDatabase();
47
48  void CloseConnection();
49
50  bool GetHostQuota(const std::string& host, StorageType type, int64* quota);
51  bool SetHostQuota(const std::string& host, StorageType type, int64 quota);
52  bool DeleteHostQuota(const std::string& host, StorageType type);
53
54  bool SetOriginLastAccessTime(const GURL& origin,
55                               StorageType type,
56                               base::Time last_access_time);
57
58  bool SetOriginLastModifiedTime(const GURL& origin,
59                                 StorageType type,
60                                 base::Time last_modified_time);
61
62  // Register initial |origins| info |type| to the database.
63  // This method is assumed to be called only after the installation or
64  // the database schema reset.
65  bool RegisterInitialOriginInfo(
66      const std::set<GURL>& origins, StorageType type);
67
68  bool DeleteOriginInfo(const GURL& origin, StorageType type);
69
70  bool GetQuotaConfigValue(const char* key, int64* value);
71  bool SetQuotaConfigValue(const char* key, int64 value);
72
73  // Sets |origin| to the least recently used origin of origins not included
74  // in |exceptions| and not granted the special unlimited storage right.
75  // It returns false when it failed in accessing the database.
76  // |origin| is set to empty when there is no matching origin.
77  bool GetLRUOrigin(StorageType type,
78                    const std::set<GURL>& exceptions,
79                    SpecialStoragePolicy* special_storage_policy,
80                    GURL* origin);
81
82  // Populates |origins| with the ones that have been modified since
83  // the |modified_since|.
84  bool GetOriginsModifiedSince(StorageType type,
85                               std::set<GURL>* origins,
86                               base::Time modified_since);
87
88  // Returns false if SetOriginDatabaseBootstrapped has never
89  // been called before, which means existing origins may not have been
90  // registered.
91  bool IsOriginDatabaseBootstrapped();
92  bool SetOriginDatabaseBootstrapped(bool bootstrap_flag);
93
94 private:
95  struct STORAGE_EXPORT_PRIVATE QuotaTableEntry {
96    QuotaTableEntry();
97    QuotaTableEntry(
98        const std::string& host,
99        StorageType type,
100        int64 quota);
101    std::string host;
102    StorageType type;
103    int64 quota;
104  };
105  friend STORAGE_EXPORT_PRIVATE bool operator <(
106      const QuotaTableEntry& lhs, const QuotaTableEntry& rhs);
107
108  struct STORAGE_EXPORT_PRIVATE OriginInfoTableEntry {
109    OriginInfoTableEntry();
110    OriginInfoTableEntry(
111        const GURL& origin,
112        StorageType type,
113        int used_count,
114        const base::Time& last_access_time,
115        const base::Time& last_modified_time);
116    GURL origin;
117    StorageType type;
118    int used_count;
119    base::Time last_access_time;
120    base::Time last_modified_time;
121  };
122  friend STORAGE_EXPORT_PRIVATE bool operator <(
123      const OriginInfoTableEntry& lhs, const OriginInfoTableEntry& rhs);
124
125  // Structures used for CreateSchema.
126  struct TableSchema {
127    const char* table_name;
128    const char* columns;
129  };
130  struct IndexSchema {
131    const char* index_name;
132    const char* table_name;
133    const char* columns;
134    bool unique;
135  };
136
137  typedef base::Callback<bool (const QuotaTableEntry&)> QuotaTableCallback;
138  typedef base::Callback<bool (const OriginInfoTableEntry&)>
139      OriginInfoTableCallback;
140
141  struct QuotaTableImporter;
142
143  // For long-running transactions support.  We always keep a transaction open
144  // so that multiple transactions can be batched.  They are flushed
145  // with a delay after a modification has been made.  We support neither
146  // nested transactions nor rollback (as we don't need them for now).
147  void Commit();
148  void ScheduleCommit();
149
150  bool FindOriginUsedCount(const GURL& origin,
151                           StorageType type,
152                           int* used_count);
153
154  bool LazyOpen(bool create_if_needed);
155  bool EnsureDatabaseVersion();
156  bool ResetSchema();
157  bool UpgradeSchema(int current_version);
158
159  static bool CreateSchema(
160      sql::Connection* database,
161      sql::MetaTable* meta_table,
162      int schema_version, int compatible_version,
163      const TableSchema* tables, size_t tables_size,
164      const IndexSchema* indexes, size_t indexes_size);
165
166  // |callback| may return false to stop reading data.
167  bool DumpQuotaTable(const QuotaTableCallback& callback);
168  bool DumpOriginInfoTable(const OriginInfoTableCallback& callback);
169
170  base::FilePath db_file_path_;
171
172  scoped_ptr<sql::Connection> db_;
173  scoped_ptr<sql::MetaTable> meta_table_;
174  bool is_recreating_;
175  bool is_disabled_;
176
177  base::OneShotTimer<QuotaDatabase> timer_;
178
179  friend class content::QuotaDatabaseTest;
180  friend class QuotaManager;
181
182  static const TableSchema kTables[];
183  static const IndexSchema kIndexes[];
184
185  DISALLOW_COPY_AND_ASSIGN(QuotaDatabase);
186};
187
188}  // namespace storage
189
190#endif  // STORAGE_BROWSER_QUOTA_QUOTA_DATABASE_H_
191