Home | History | Annotate | Download | only in drive
      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 #ifndef GOOGLE_APIS_DRIVE_DRIVE_API_PARSER_H_
      6 #define GOOGLE_APIS_DRIVE_DRIVE_API_PARSER_H_
      7 
      8 #include <string>
      9 
     10 #include "base/compiler_specific.h"
     11 #include "base/gtest_prod_util.h"
     12 #include "base/memory/scoped_ptr.h"
     13 #include "base/memory/scoped_vector.h"
     14 #include "base/strings/string_piece.h"
     15 #include "base/time/time.h"
     16 #include "url/gurl.h"
     17 
     18 namespace base {
     19 class Value;
     20 template <class StructType>
     21 class JSONValueConverter;
     22 
     23 namespace internal {
     24 template <class NestedType>
     25 class RepeatedMessageConverter;
     26 }  // namespace internal
     27 }  // namespace base
     28 
     29 namespace google_apis {
     30 
     31 // About resource represents the account information about the current user.
     32 // https://developers.google.com/drive/v2/reference/about
     33 class AboutResource {
     34  public:
     35   AboutResource();
     36   ~AboutResource();
     37 
     38   // Registers the mapping between JSON field names and the members in this
     39   // class.
     40   static void RegisterJSONConverter(
     41       base::JSONValueConverter<AboutResource>* converter);
     42 
     43   // Creates about resource from parsed JSON.
     44   static scoped_ptr<AboutResource> CreateFrom(const base::Value& value);
     45 
     46   // Returns the largest change ID number.
     47   int64 largest_change_id() const { return largest_change_id_; }
     48   // Returns total number of quota bytes.
     49   int64 quota_bytes_total() const { return quota_bytes_total_; }
     50   // Returns the number of quota bytes used.
     51   int64 quota_bytes_used() const { return quota_bytes_used_; }
     52   // Returns root folder ID.
     53   const std::string& root_folder_id() const { return root_folder_id_; }
     54 
     55   void set_largest_change_id(int64 largest_change_id) {
     56     largest_change_id_ = largest_change_id;
     57   }
     58   void set_quota_bytes_total(int64 quota_bytes_total) {
     59     quota_bytes_total_ = quota_bytes_total;
     60   }
     61   void set_quota_bytes_used(int64 quota_bytes_used) {
     62     quota_bytes_used_ = quota_bytes_used;
     63   }
     64   void set_root_folder_id(const std::string& root_folder_id) {
     65     root_folder_id_ = root_folder_id;
     66   }
     67 
     68  private:
     69   friend class DriveAPIParserTest;
     70   FRIEND_TEST_ALL_PREFIXES(DriveAPIParserTest, AboutResourceParser);
     71 
     72   // Parses and initializes data members from content of |value|.
     73   // Return false if parsing fails.
     74   bool Parse(const base::Value& value);
     75 
     76   int64 largest_change_id_;
     77   int64 quota_bytes_total_;
     78   int64 quota_bytes_used_;
     79   std::string root_folder_id_;
     80 
     81   // This class is copyable on purpose.
     82 };
     83 
     84 // DriveAppIcon represents an icon for Drive Application.
     85 // https://developers.google.com/drive/v2/reference/apps
     86 class DriveAppIcon {
     87  public:
     88   enum IconCategory {
     89     UNKNOWN,          // Uninitialized state.
     90     DOCUMENT,         // Icon for a file associated with the app.
     91     APPLICATION,      // Icon for the application.
     92     SHARED_DOCUMENT,  // Icon for a shared file associated with the app.
     93   };
     94 
     95   DriveAppIcon();
     96   ~DriveAppIcon();
     97 
     98   // Registers the mapping between JSON field names and the members in this
     99   // class.
    100   static void RegisterJSONConverter(
    101       base::JSONValueConverter<DriveAppIcon>* converter);
    102 
    103   // Creates drive app icon instance from parsed JSON.
    104   static scoped_ptr<DriveAppIcon> CreateFrom(const base::Value& value);
    105 
    106   // Category of the icon.
    107   IconCategory category() const { return category_; }
    108 
    109   // Size in pixels of one side of the icon (icons are always square).
    110   int icon_side_length() const { return icon_side_length_; }
    111 
    112   // Returns URL for this icon.
    113   const GURL& icon_url() const { return icon_url_; }
    114 
    115   void set_category(IconCategory category) {
    116     category_ = category;
    117   }
    118   void set_icon_side_length(int icon_side_length) {
    119     icon_side_length_ = icon_side_length;
    120   }
    121   void set_icon_url(const GURL& icon_url) {
    122     icon_url_ = icon_url;
    123   }
    124 
    125  private:
    126   // Parses and initializes data members from content of |value|.
    127   // Return false if parsing fails.
    128   bool Parse(const base::Value& value);
    129 
    130   // Extracts the icon category from the given string. Returns false and does
    131   // not change |result| when |scheme| has an unrecognizable value.
    132   static bool GetIconCategory(const base::StringPiece& category,
    133                               IconCategory* result);
    134 
    135   friend class base::internal::RepeatedMessageConverter<DriveAppIcon>;
    136   friend class AppResource;
    137 
    138   IconCategory category_;
    139   int icon_side_length_;
    140   GURL icon_url_;
    141 
    142   DISALLOW_COPY_AND_ASSIGN(DriveAppIcon);
    143 };
    144 
    145 // AppResource represents a Drive Application.
    146 // https://developers.google.com/drive/v2/reference/apps
    147 class AppResource {
    148  public:
    149   ~AppResource();
    150   AppResource();
    151 
    152   // Registers the mapping between JSON field names and the members in this
    153   // class.
    154   static void RegisterJSONConverter(
    155       base::JSONValueConverter<AppResource>* converter);
    156 
    157   // Creates app resource from parsed JSON.
    158   static scoped_ptr<AppResource> CreateFrom(const base::Value& value);
    159 
    160   // Returns application ID, which is 12-digit decimals (e.g. "123456780123").
    161   const std::string& application_id() const { return application_id_; }
    162 
    163   // Returns application name.
    164   const std::string& name() const { return name_; }
    165 
    166   // Returns the name of the type of object this application creates.
    167   // This is used for displaying in "Create" menu item for this app.
    168   // If empty, application name is used instead.
    169   const std::string& object_type() const { return object_type_; }
    170 
    171   // Returns the product ID.
    172   const std::string& product_id() const { return product_id_; }
    173 
    174   // Returns whether this application supports creating new objects.
    175   bool supports_create() const { return supports_create_; }
    176 
    177   // Returns whether this application is removable by apps.delete API.
    178   bool is_removable() const { return removable_; }
    179 
    180   // Returns the create URL, i.e., the URL for opening a new file by the app.
    181   const GURL& create_url() const { return create_url_; }
    182 
    183   // List of primary mime types supported by this WebApp. Primary status should
    184   // trigger this WebApp becoming the default handler of file instances that
    185   // have these mime types.
    186   const ScopedVector<std::string>& primary_mimetypes() const {
    187     return primary_mimetypes_;
    188   }
    189 
    190   // List of secondary mime types supported by this WebApp. Secondary status
    191   // should make this WebApp show up in "Open with..." pop-up menu of the
    192   // default action menu for file with matching mime types.
    193   const ScopedVector<std::string>& secondary_mimetypes() const {
    194     return secondary_mimetypes_;
    195   }
    196 
    197   // List of primary file extensions supported by this WebApp. Primary status
    198   // should trigger this WebApp becoming the default handler of file instances
    199   // that match these extensions.
    200   const ScopedVector<std::string>& primary_file_extensions() const {
    201     return primary_file_extensions_;
    202   }
    203 
    204   // List of secondary file extensions supported by this WebApp. Secondary
    205   // status should make this WebApp show up in "Open with..." pop-up menu of the
    206   // default action menu for file with matching extensions.
    207   const ScopedVector<std::string>& secondary_file_extensions() const {
    208     return secondary_file_extensions_;
    209   }
    210 
    211   // Returns Icons for this application.  An application can have multiple
    212   // icons for different purpose (application, document, shared document)
    213   // in several sizes.
    214   const ScopedVector<DriveAppIcon>& icons() const {
    215     return icons_;
    216   }
    217 
    218   void set_application_id(const std::string& application_id) {
    219     application_id_ = application_id;
    220   }
    221   void set_name(const std::string& name) { name_ = name; }
    222   void set_object_type(const std::string& object_type) {
    223     object_type_ = object_type;
    224   }
    225   void set_product_id(const std::string& id) { product_id_ = id; }
    226   void set_supports_create(bool supports_create) {
    227     supports_create_ = supports_create;
    228   }
    229   void set_removable(bool removable) { removable_ = removable; }
    230   void set_primary_mimetypes(
    231       ScopedVector<std::string> primary_mimetypes) {
    232     primary_mimetypes_ = primary_mimetypes.Pass();
    233   }
    234   void set_secondary_mimetypes(
    235       ScopedVector<std::string> secondary_mimetypes) {
    236     secondary_mimetypes_ = secondary_mimetypes.Pass();
    237   }
    238   void set_primary_file_extensions(
    239       ScopedVector<std::string> primary_file_extensions) {
    240     primary_file_extensions_ = primary_file_extensions.Pass();
    241   }
    242   void set_secondary_file_extensions(
    243       ScopedVector<std::string> secondary_file_extensions) {
    244     secondary_file_extensions_ = secondary_file_extensions.Pass();
    245   }
    246   void set_icons(ScopedVector<DriveAppIcon> icons) {
    247     icons_ = icons.Pass();
    248   }
    249   void set_create_url(const GURL& url) {
    250     create_url_ = url;
    251   }
    252 
    253  private:
    254   friend class base::internal::RepeatedMessageConverter<AppResource>;
    255   friend class AppList;
    256 
    257   // Parses and initializes data members from content of |value|.
    258   // Return false if parsing fails.
    259   bool Parse(const base::Value& value);
    260 
    261   std::string application_id_;
    262   std::string name_;
    263   std::string object_type_;
    264   std::string product_id_;
    265   bool supports_create_;
    266   bool removable_;
    267   GURL create_url_;
    268   ScopedVector<std::string> primary_mimetypes_;
    269   ScopedVector<std::string> secondary_mimetypes_;
    270   ScopedVector<std::string> primary_file_extensions_;
    271   ScopedVector<std::string> secondary_file_extensions_;
    272   ScopedVector<DriveAppIcon> icons_;
    273 
    274   DISALLOW_COPY_AND_ASSIGN(AppResource);
    275 };
    276 
    277 // AppList represents a list of Drive Applications.
    278 // https://developers.google.com/drive/v2/reference/apps/list
    279 class AppList {
    280  public:
    281   AppList();
    282   ~AppList();
    283 
    284   // Registers the mapping between JSON field names and the members in this
    285   // class.
    286   static void RegisterJSONConverter(
    287       base::JSONValueConverter<AppList>* converter);
    288 
    289   // Creates app list from parsed JSON.
    290   static scoped_ptr<AppList> CreateFrom(const base::Value& value);
    291 
    292   // ETag for this resource.
    293   const std::string& etag() const { return etag_; }
    294 
    295   // Returns a vector of applications.
    296   const ScopedVector<AppResource>& items() const { return items_; }
    297 
    298   void set_etag(const std::string& etag) {
    299     etag_ = etag;
    300   }
    301   void set_items(ScopedVector<AppResource> items) {
    302     items_ = items.Pass();
    303   }
    304 
    305  private:
    306   friend class DriveAPIParserTest;
    307   FRIEND_TEST_ALL_PREFIXES(DriveAPIParserTest, AppListParser);
    308 
    309   // Parses and initializes data members from content of |value|.
    310   // Return false if parsing fails.
    311   bool Parse(const base::Value& value);
    312 
    313   std::string etag_;
    314   ScopedVector<AppResource> items_;
    315 
    316   DISALLOW_COPY_AND_ASSIGN(AppList);
    317 };
    318 
    319 // ParentReference represents a directory.
    320 // https://developers.google.com/drive/v2/reference/parents
    321 class ParentReference {
    322  public:
    323   ParentReference();
    324   ~ParentReference();
    325 
    326   // Registers the mapping between JSON field names and the members in this
    327   // class.
    328   static void RegisterJSONConverter(
    329       base::JSONValueConverter<ParentReference>* converter);
    330 
    331   // Creates parent reference from parsed JSON.
    332   static scoped_ptr<ParentReference> CreateFrom(const base::Value& value);
    333 
    334   // Returns the file id of the reference.
    335   const std::string& file_id() const { return file_id_; }
    336 
    337   // Returns the URL for the parent in Drive.
    338   const GURL& parent_link() const { return parent_link_; }
    339 
    340   void set_file_id(const std::string& file_id) { file_id_ = file_id; }
    341   void set_parent_link(const GURL& parent_link) {
    342     parent_link_ = parent_link;
    343   }
    344 
    345  private:
    346   // Parses and initializes data members from content of |value|.
    347   // Return false if parsing fails.
    348   bool Parse(const base::Value& value);
    349 
    350   std::string file_id_;
    351   GURL parent_link_;
    352 };
    353 
    354 // FileLabels represents labels for file or folder.
    355 // https://developers.google.com/drive/v2/reference/files
    356 class FileLabels {
    357  public:
    358   FileLabels();
    359   ~FileLabels();
    360 
    361   // Registers the mapping between JSON field names and the members in this
    362   // class.
    363   static void RegisterJSONConverter(
    364       base::JSONValueConverter<FileLabels>* converter);
    365 
    366   // Creates about resource from parsed JSON.
    367   static scoped_ptr<FileLabels> CreateFrom(const base::Value& value);
    368 
    369   // Whether this file has been trashed.
    370   bool is_trashed() const { return trashed_; }
    371 
    372   void set_trashed(bool trashed) { trashed_ = trashed; }
    373 
    374  private:
    375   friend class FileResource;
    376 
    377   // Parses and initializes data members from content of |value|.
    378   // Return false if parsing fails.
    379   bool Parse(const base::Value& value);
    380 
    381   bool trashed_;
    382 };
    383 
    384 // ImageMediaMetadata represents image metadata for a file.
    385 // https://developers.google.com/drive/v2/reference/files
    386 class ImageMediaMetadata {
    387  public:
    388   ImageMediaMetadata();
    389   ~ImageMediaMetadata();
    390 
    391   // Registers the mapping between JSON field names and the members in this
    392   // class.
    393   static void RegisterJSONConverter(
    394       base::JSONValueConverter<ImageMediaMetadata>* converter);
    395 
    396   // Creates about resource from parsed JSON.
    397   static scoped_ptr<ImageMediaMetadata> CreateFrom(const base::Value& value);
    398 
    399   // Width of the image in pixels.
    400   int width() const { return width_; }
    401   // Height of the image in pixels.
    402   int height() const { return height_; }
    403   // Rotation of the image in clockwise degrees.
    404   int rotation() const { return rotation_; }
    405 
    406   void set_width(int width) { width_ = width; }
    407   void set_height(int height) { height_ = height; }
    408   void set_rotation(int rotation) { rotation_ = rotation; }
    409 
    410  private:
    411   friend class FileResource;
    412 
    413   // Parses and initializes data members from content of |value|.
    414   // Return false if parsing fails.
    415   bool Parse(const base::Value& value);
    416 
    417   int width_;
    418   int height_;
    419   int rotation_;
    420 };
    421 
    422 
    423 // FileResource represents a file or folder metadata in Drive.
    424 // https://developers.google.com/drive/v2/reference/files
    425 class FileResource {
    426  public:
    427   // Link to open a file resource on a web app with |app_id|.
    428   struct OpenWithLink {
    429     std::string app_id;
    430     GURL open_url;
    431   };
    432 
    433   FileResource();
    434   ~FileResource();
    435 
    436   // Registers the mapping between JSON field names and the members in this
    437   // class.
    438   static void RegisterJSONConverter(
    439       base::JSONValueConverter<FileResource>* converter);
    440 
    441   // Creates file resource from parsed JSON.
    442   static scoped_ptr<FileResource> CreateFrom(const base::Value& value);
    443 
    444   // Returns true if this is a directory.
    445   // Note: "folder" is used elsewhere in this file to match Drive API reference,
    446   // but outside this file we use "directory" to match HTML5 filesystem API.
    447   bool IsDirectory() const;
    448 
    449   // Returns true if this is a hosted document.
    450   // A hosted document is a document in one of Google Docs formats (Documents,
    451   // Spreadsheets, Slides, ...) whose content is not exposed via the API. It is
    452   // available only as |alternate_link()| to the document hosted on the server.
    453   bool IsHostedDocument() const;
    454 
    455   // Returns file ID.  This is unique in all files in Google Drive.
    456   const std::string& file_id() const { return file_id_; }
    457 
    458   // Returns ETag for this file.
    459   const std::string& etag() const { return etag_; }
    460 
    461   // Returns the title of this file.
    462   const std::string& title() const { return title_; }
    463 
    464   // Returns MIME type of this file.
    465   const std::string& mime_type() const { return mime_type_; }
    466 
    467   // Returns labels for this file.
    468   const FileLabels& labels() const { return labels_; }
    469 
    470   // Returns image media metadata for this file.
    471   const ImageMediaMetadata& image_media_metadata() const {
    472     return image_media_metadata_;
    473   }
    474 
    475   // Returns created time of this file.
    476   const base::Time& created_date() const { return created_date_; }
    477 
    478   // Returns modified time of this file.
    479   const base::Time& modified_date() const { return modified_date_; }
    480 
    481   // Returns last access time by the user.
    482   const base::Time& last_viewed_by_me_date() const {
    483     return last_viewed_by_me_date_;
    484   }
    485 
    486   // Returns time when the file was shared with the user.
    487   const base::Time& shared_with_me_date() const {
    488     return shared_with_me_date_;
    489   }
    490 
    491   // Returns the 'shared' attribute of the file.
    492   bool shared() const { return shared_; }
    493 
    494   // Returns MD5 checksum of this file.
    495   const std::string& md5_checksum() const { return md5_checksum_; }
    496 
    497   // Returns the size of this file in bytes.
    498   int64 file_size() const { return file_size_; }
    499 
    500   // Return the link to open the file in Google editor or viewer.
    501   // E.g. Google Document, Google Spreadsheet.
    502   const GURL& alternate_link() const { return alternate_link_; }
    503 
    504   // Returns parent references (directories) of this file.
    505   const std::vector<ParentReference>& parents() const { return parents_; }
    506 
    507   // Returns the list of links to open the resource with a web app.
    508   const std::vector<OpenWithLink>& open_with_links() const {
    509     return open_with_links_;
    510   }
    511 
    512   void set_file_id(const std::string& file_id) {
    513     file_id_ = file_id;
    514   }
    515   void set_etag(const std::string& etag) {
    516     etag_ = etag;
    517   }
    518   void set_title(const std::string& title) {
    519     title_ = title;
    520   }
    521   void set_mime_type(const std::string& mime_type) {
    522     mime_type_ = mime_type;
    523   }
    524   FileLabels* mutable_labels() {
    525     return &labels_;
    526   }
    527   ImageMediaMetadata* mutable_image_media_metadata() {
    528     return &image_media_metadata_;
    529   }
    530   void set_created_date(const base::Time& created_date) {
    531     created_date_ = created_date;
    532   }
    533   void set_modified_date(const base::Time& modified_date) {
    534     modified_date_ = modified_date;
    535   }
    536   void set_last_viewed_by_me_date(const base::Time& last_viewed_by_me_date) {
    537     last_viewed_by_me_date_ = last_viewed_by_me_date;
    538   }
    539   void set_shared_with_me_date(const base::Time& shared_with_me_date) {
    540     shared_with_me_date_ = shared_with_me_date;
    541   }
    542   void set_shared(bool shared) {
    543     shared_ = shared;
    544   }
    545   void set_md5_checksum(const std::string& md5_checksum) {
    546     md5_checksum_ = md5_checksum;
    547   }
    548   void set_file_size(int64 file_size) {
    549     file_size_ = file_size;
    550   }
    551   void set_alternate_link(const GURL& alternate_link) {
    552     alternate_link_ = alternate_link;
    553   }
    554   std::vector<ParentReference>* mutable_parents() { return &parents_; }
    555   std::vector<OpenWithLink>* mutable_open_with_links() {
    556     return &open_with_links_;
    557   }
    558 
    559  private:
    560   friend class base::internal::RepeatedMessageConverter<FileResource>;
    561   friend class ChangeResource;
    562   friend class FileList;
    563 
    564   // Parses and initializes data members from content of |value|.
    565   // Return false if parsing fails.
    566   bool Parse(const base::Value& value);
    567 
    568   std::string file_id_;
    569   std::string etag_;
    570   std::string title_;
    571   std::string mime_type_;
    572   FileLabels labels_;
    573   ImageMediaMetadata image_media_metadata_;
    574   base::Time created_date_;
    575   base::Time modified_date_;
    576   base::Time last_viewed_by_me_date_;
    577   base::Time shared_with_me_date_;
    578   bool shared_;
    579   std::string md5_checksum_;
    580   int64 file_size_;
    581   GURL alternate_link_;
    582   std::vector<ParentReference> parents_;
    583   std::vector<OpenWithLink> open_with_links_;
    584 };
    585 
    586 // FileList represents a collection of files and folders.
    587 // https://developers.google.com/drive/v2/reference/files/list
    588 class FileList {
    589  public:
    590   FileList();
    591   ~FileList();
    592 
    593   // Registers the mapping between JSON field names and the members in this
    594   // class.
    595   static void RegisterJSONConverter(
    596       base::JSONValueConverter<FileList>* converter);
    597 
    598   // Returns true if the |value| has kind field for FileList.
    599   static bool HasFileListKind(const base::Value& value);
    600 
    601   // Creates file list from parsed JSON.
    602   static scoped_ptr<FileList> CreateFrom(const base::Value& value);
    603 
    604   // Returns a link to the next page of files.  The URL includes the next page
    605   // token.
    606   const GURL& next_link() const { return next_link_; }
    607 
    608   // Returns a set of files in this list.
    609   const ScopedVector<FileResource>& items() const { return items_; }
    610   ScopedVector<FileResource>* mutable_items() { return &items_; }
    611 
    612   void set_next_link(const GURL& next_link) {
    613     next_link_ = next_link;
    614   }
    615 
    616  private:
    617   friend class DriveAPIParserTest;
    618   FRIEND_TEST_ALL_PREFIXES(DriveAPIParserTest, FileListParser);
    619 
    620   // Parses and initializes data members from content of |value|.
    621   // Return false if parsing fails.
    622   bool Parse(const base::Value& value);
    623 
    624   GURL next_link_;
    625   ScopedVector<FileResource> items_;
    626 
    627   DISALLOW_COPY_AND_ASSIGN(FileList);
    628 };
    629 
    630 // ChangeResource represents a change in a file.
    631 // https://developers.google.com/drive/v2/reference/changes
    632 class ChangeResource {
    633  public:
    634   ChangeResource();
    635   ~ChangeResource();
    636 
    637   // Registers the mapping between JSON field names and the members in this
    638   // class.
    639   static void RegisterJSONConverter(
    640       base::JSONValueConverter<ChangeResource>* converter);
    641 
    642   // Creates change resource from parsed JSON.
    643   static scoped_ptr<ChangeResource> CreateFrom(const base::Value& value);
    644 
    645   // Returns change ID for this change.  This is a monotonically increasing
    646   // number.
    647   int64 change_id() const { return change_id_; }
    648 
    649   // Returns a string file ID for corresponding file of the change.
    650   const std::string& file_id() const { return file_id_; }
    651 
    652   // Returns true if this file is deleted in the change.
    653   bool is_deleted() const { return deleted_; }
    654 
    655   // Returns FileResource of the file which the change refers to.
    656   const FileResource* file() const { return file_.get(); }
    657   FileResource* mutable_file() { return file_.get(); }
    658 
    659   // Returns the time of this modification.
    660   const base::Time& modification_date() const { return modification_date_; }
    661 
    662   void set_change_id(int64 change_id) {
    663     change_id_ = change_id;
    664   }
    665   void set_file_id(const std::string& file_id) {
    666     file_id_ = file_id;
    667   }
    668   void set_deleted(bool deleted) {
    669     deleted_ = deleted;
    670   }
    671   void set_file(scoped_ptr<FileResource> file) {
    672     file_ = file.Pass();
    673   }
    674   void set_modification_date(const base::Time& modification_date) {
    675     modification_date_ = modification_date;
    676   }
    677 
    678  private:
    679   friend class base::internal::RepeatedMessageConverter<ChangeResource>;
    680   friend class ChangeList;
    681 
    682   // Parses and initializes data members from content of |value|.
    683   // Return false if parsing fails.
    684   bool Parse(const base::Value& value);
    685 
    686   int64 change_id_;
    687   std::string file_id_;
    688   bool deleted_;
    689   scoped_ptr<FileResource> file_;
    690   base::Time modification_date_;
    691 
    692   DISALLOW_COPY_AND_ASSIGN(ChangeResource);
    693 };
    694 
    695 // ChangeList represents a set of changes in the drive.
    696 // https://developers.google.com/drive/v2/reference/changes/list
    697 class ChangeList {
    698  public:
    699   ChangeList();
    700   ~ChangeList();
    701 
    702   // Registers the mapping between JSON field names and the members in this
    703   // class.
    704   static void RegisterJSONConverter(
    705       base::JSONValueConverter<ChangeList>* converter);
    706 
    707   // Returns true if the |value| has kind field for ChangeList.
    708   static bool HasChangeListKind(const base::Value& value);
    709 
    710   // Creates change list from parsed JSON.
    711   static scoped_ptr<ChangeList> CreateFrom(const base::Value& value);
    712 
    713   // Returns a link to the next page of files.  The URL includes the next page
    714   // token.
    715   const GURL& next_link() const { return next_link_; }
    716 
    717   // Returns the largest change ID number.
    718   int64 largest_change_id() const { return largest_change_id_; }
    719 
    720   // Returns a set of changes in this list.
    721   const ScopedVector<ChangeResource>& items() const { return items_; }
    722   ScopedVector<ChangeResource>* mutable_items() { return &items_; }
    723 
    724   void set_next_link(const GURL& next_link) {
    725     next_link_ = next_link;
    726   }
    727   void set_largest_change_id(int64 largest_change_id) {
    728     largest_change_id_ = largest_change_id;
    729   }
    730 
    731  private:
    732   friend class DriveAPIParserTest;
    733   FRIEND_TEST_ALL_PREFIXES(DriveAPIParserTest, ChangeListParser);
    734 
    735   // Parses and initializes data members from content of |value|.
    736   // Return false if parsing fails.
    737   bool Parse(const base::Value& value);
    738 
    739   GURL next_link_;
    740   int64 largest_change_id_;
    741   ScopedVector<ChangeResource> items_;
    742 
    743   DISALLOW_COPY_AND_ASSIGN(ChangeList);
    744 };
    745 
    746 }  // namespace google_apis
    747 
    748 #endif  // GOOGLE_APIS_DRIVE_DRIVE_API_PARSER_H_
    749