1 // Copyright (c) 2011 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 CHROME_BROWSER_BOOKMARKS_BOOKMARK_CODEC_H_ 6 #define CHROME_BROWSER_BOOKMARKS_BOOKMARK_CODEC_H_ 7 8 #include <set> 9 #include <string> 10 11 #include "base/basictypes.h" 12 #include "base/md5.h" 13 #include "base/strings/string16.h" 14 15 class BookmarkModel; 16 class BookmarkNode; 17 18 namespace base { 19 class DictionaryValue; 20 class ListValue; 21 class Value; 22 } 23 24 // BookmarkCodec is responsible for encoding and decoding the BookmarkModel 25 // into JSON values. The encoded values are written to disk via the 26 // BookmarkStorage. 27 class BookmarkCodec { 28 public: 29 // Creates an instance of the codec. During decoding, if the IDs in the file 30 // are not unique, we will reassign IDs to make them unique. There are no 31 // guarantees on how the IDs are reassigned or about doing minimal 32 // reassignments to achieve uniqueness. 33 BookmarkCodec(); 34 ~BookmarkCodec(); 35 36 // Encodes the model to a JSON value. It's up to the caller to delete the 37 // returned object. This is invoked to encode the contents of the bookmark bar 38 // model and is currently a convenience to invoking Encode that takes the 39 // bookmark bar node and other folder node. 40 base::Value* Encode(BookmarkModel* model); 41 42 // Encodes the bookmark bar and other folders returning the JSON value. It's 43 // up to the caller to delete the returned object. 44 base::Value* Encode(const BookmarkNode* bookmark_bar_node, 45 const BookmarkNode* other_folder_node, 46 const BookmarkNode* mobile_folder_node, 47 const std::string& model_meta_info); 48 49 // Decodes the previously encoded value to the specified nodes as well as 50 // setting |max_node_id| to the greatest node id. Returns true on success, 51 // false otherwise. If there is an error (such as unexpected version) all 52 // children are removed from the bookmark bar and other folder nodes. On exit 53 // |max_node_id| is set to the max id of the nodes. 54 bool Decode(BookmarkNode* bb_node, 55 BookmarkNode* other_folder_node, 56 BookmarkNode* mobile_folder_node, 57 int64* max_node_id, 58 const base::Value& value); 59 60 // Returns the checksum computed during last encoding/decoding call. 61 const std::string& computed_checksum() const { return computed_checksum_; } 62 63 // Returns the checksum that's stored in the file. After a call to Encode, 64 // the computed and stored checksums are the same since the computed checksum 65 // is stored to the file. After a call to decode, the computed checksum can 66 // differ from the stored checksum if the file contents were changed by the 67 // user. 68 const std::string& stored_checksum() const { return stored_checksum_; } 69 70 // Return meta info of bookmark model root. 71 const std::string& model_meta_info() const { return model_meta_info_; } 72 73 // Returns whether the IDs were reassigned during decoding. Always returns 74 // false after encoding. 75 bool ids_reassigned() const { return ids_reassigned_; } 76 77 // Names of the various keys written to the Value. 78 static const char* kRootsKey; 79 static const char* kRootFolderNameKey; 80 static const char* kOtherBookmarkFolderNameKey; 81 static const char* kMobileBookmarkFolderNameKey; 82 static const char* kVersionKey; 83 static const char* kChecksumKey; 84 static const char* kIdKey; 85 static const char* kTypeKey; 86 static const char* kNameKey; 87 static const char* kDateAddedKey; 88 static const char* kURLKey; 89 static const char* kDateModifiedKey; 90 static const char* kChildrenKey; 91 static const char* kMetaInfo; 92 93 // Possible values for kTypeKey. 94 static const char* kTypeURL; 95 static const char* kTypeFolder; 96 97 private: 98 // Encodes node and all its children into a Value object and returns it. 99 // The caller takes ownership of the returned object. 100 base::Value* EncodeNode(const BookmarkNode* node); 101 102 // Helper to perform decoding. 103 bool DecodeHelper(BookmarkNode* bb_node, 104 BookmarkNode* other_folder_node, 105 BookmarkNode* mobile_folder_node, 106 const base::Value& value); 107 108 // Decodes the children of the specified node. Returns true on success. 109 bool DecodeChildren(const base::ListValue& child_value_list, 110 BookmarkNode* parent); 111 112 // Reassigns bookmark IDs for all nodes. 113 void ReassignIDs(BookmarkNode* bb_node, 114 BookmarkNode* other_node, 115 BookmarkNode* mobile_node); 116 117 // Helper to recursively reassign IDs. 118 void ReassignIDsHelper(BookmarkNode* node); 119 120 // Decodes the supplied node from the supplied value. Child nodes are 121 // created appropriately by way of DecodeChildren. If node is NULL a new 122 // node is created and added to parent (parent must then be non-NULL), 123 // otherwise node is used. 124 bool DecodeNode(const base::DictionaryValue& value, 125 BookmarkNode* parent, 126 BookmarkNode* node); 127 128 // Updates the check-sum with the given string. 129 void UpdateChecksum(const std::string& str); 130 void UpdateChecksum(const string16& str); 131 132 // Updates the check-sum with the given contents of URL/folder bookmark node. 133 // NOTE: These functions take in individual properties of a bookmark node 134 // instead of taking in a BookmarkNode for efficiency so that we don't convert 135 // various data-types to UTF16 strings multiple times - once for serializing 136 // and once for computing the check-sum. 137 // The url parameter should be a valid UTF8 string. 138 void UpdateChecksumWithUrlNode(const std::string& id, 139 const string16& title, 140 const std::string& url); 141 void UpdateChecksumWithFolderNode(const std::string& id, 142 const string16& title); 143 144 // Initializes/Finalizes the checksum. 145 void InitializeChecksum(); 146 void FinalizeChecksum(); 147 148 // Whether or not IDs were reassigned by the codec. 149 bool ids_reassigned_; 150 151 // Whether or not IDs are valid. This is initially true, but set to false 152 // if an id is missing or not unique. 153 bool ids_valid_; 154 155 // Contains the id of each of the nodes found in the file. Used to determine 156 // if we have duplicates. 157 std::set<int64> ids_; 158 159 // MD5 context used to compute MD5 hash of all bookmark data. 160 base::MD5Context md5_context_; 161 162 // Checksums. 163 std::string computed_checksum_; 164 std::string stored_checksum_; 165 166 // Maximum ID assigned when decoding data. 167 int64 maximum_id_; 168 169 // Meta info set on bookmark model root. 170 std::string model_meta_info_; 171 172 DISALLOW_COPY_AND_ASSIGN(BookmarkCodec); 173 }; 174 175 #endif // CHROME_BROWSER_BOOKMARKS_BOOKMARK_CODEC_H_ 176