1 /* 2 * Copyright (C) 2010 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License 15 */ 16 17 package android.provider; 18 19 import android.accounts.Account; 20 import android.content.ContentProviderClient; 21 import android.content.ContentProviderOperation; 22 import android.content.ContentResolver; 23 import android.content.ContentUris; 24 import android.content.ContentValues; 25 import android.content.Context; 26 import android.database.Cursor; 27 import android.graphics.BitmapFactory; 28 import android.net.Uri; 29 import android.os.RemoteException; 30 import android.util.Pair; 31 32 /** 33 * @hide 34 */ 35 public class BrowserContract { 36 /** The authority for the browser provider */ 37 public static final String AUTHORITY = "com.android.browser"; 38 39 /** A content:// style uri to the authority for the browser provider */ 40 public static final Uri AUTHORITY_URI = Uri.parse("content://" + AUTHORITY); 41 42 /** 43 * An optional insert, update or delete URI parameter that allows the caller 44 * to specify that it is a sync adapter. The default value is false. If true 45 * the dirty flag is not automatically set and the "syncToNetwork" parameter 46 * is set to false when calling 47 * {@link ContentResolver#notifyChange(android.net.Uri, android.database.ContentObserver, boolean)}. 48 */ 49 public static final String CALLER_IS_SYNCADAPTER = "caller_is_syncadapter"; 50 51 /** 52 * A parameter for use when querying any table that allows specifying a limit on the number 53 * of rows returned. 54 */ 55 public static final String PARAM_LIMIT = "limit"; 56 57 /** 58 * Generic columns for use by sync adapters. The specific functions of 59 * these columns are private to the sync adapter. Other clients of the API 60 * should not attempt to either read or write these columns. 61 */ 62 interface BaseSyncColumns { 63 /** Generic column for use by sync adapters. */ 64 public static final String SYNC1 = "sync1"; 65 /** Generic column for use by sync adapters. */ 66 public static final String SYNC2 = "sync2"; 67 /** Generic column for use by sync adapters. */ 68 public static final String SYNC3 = "sync3"; 69 /** Generic column for use by sync adapters. */ 70 public static final String SYNC4 = "sync4"; 71 /** Generic column for use by sync adapters. */ 72 public static final String SYNC5 = "sync5"; 73 } 74 75 /** 76 * Convenience definitions for use in implementing chrome bookmarks sync in the Bookmarks table. 77 */ 78 public static final class ChromeSyncColumns { 79 private ChromeSyncColumns() {} 80 81 /** The server unique ID for an item */ 82 public static final String SERVER_UNIQUE = BaseSyncColumns.SYNC3; 83 84 public static final String FOLDER_NAME_ROOT = "google_chrome"; 85 public static final String FOLDER_NAME_BOOKMARKS = "google_chrome_bookmarks"; 86 public static final String FOLDER_NAME_BOOKMARKS_BAR = "bookmark_bar"; 87 public static final String FOLDER_NAME_OTHER_BOOKMARKS = "other_bookmarks"; 88 89 /** The client unique ID for an item */ 90 public static final String CLIENT_UNIQUE = BaseSyncColumns.SYNC4; 91 } 92 93 /** 94 * Columns that appear when each row of a table belongs to a specific 95 * account, including sync information that an account may need. 96 */ 97 interface SyncColumns extends BaseSyncColumns { 98 /** 99 * The name of the account instance to which this row belongs, which when paired with 100 * {@link #ACCOUNT_TYPE} identifies a specific account. 101 * <P>Type: TEXT</P> 102 */ 103 public static final String ACCOUNT_NAME = "account_name"; 104 105 /** 106 * The type of account to which this row belongs, which when paired with 107 * {@link #ACCOUNT_NAME} identifies a specific account. 108 * <P>Type: TEXT</P> 109 */ 110 public static final String ACCOUNT_TYPE = "account_type"; 111 112 /** 113 * String that uniquely identifies this row to its source account. 114 * <P>Type: TEXT</P> 115 */ 116 public static final String SOURCE_ID = "sourceid"; 117 118 /** 119 * Version number that is updated whenever this row or its related data 120 * changes. 121 * <P>Type: INTEGER</P> 122 */ 123 public static final String VERSION = "version"; 124 125 /** 126 * Flag indicating that {@link #VERSION} has changed, and this row needs 127 * to be synchronized by its owning account. 128 * <P>Type: INTEGER (boolean)</P> 129 */ 130 public static final String DIRTY = "dirty"; 131 132 /** 133 * The time that this row was last modified by a client (msecs since the epoch). 134 * <P>Type: INTEGER</P> 135 */ 136 public static final String DATE_MODIFIED = "modified"; 137 } 138 139 interface CommonColumns { 140 /** 141 * The unique ID for a row. 142 * <P>Type: INTEGER (long)</P> 143 */ 144 public static final String _ID = "_id"; 145 146 /** 147 * The URL of the bookmark. 148 * <P>Type: TEXT (URL)</P> 149 */ 150 public static final String URL = "url"; 151 152 /** 153 * The user visible title of the bookmark. 154 * <P>Type: TEXT</P> 155 */ 156 public static final String TITLE = "title"; 157 158 /** 159 * The time that this row was created on its originating client (msecs 160 * since the epoch). 161 * <P>Type: INTEGER</P> 162 */ 163 public static final String DATE_CREATED = "created"; 164 } 165 166 interface ImageColumns { 167 /** 168 * The favicon of the bookmark, may be NULL. 169 * Must decode via {@link BitmapFactory#decodeByteArray}. 170 * <p>Type: BLOB (image)</p> 171 */ 172 public static final String FAVICON = "favicon"; 173 174 /** 175 * A thumbnail of the page,may be NULL. 176 * Must decode via {@link BitmapFactory#decodeByteArray}. 177 * <p>Type: BLOB (image)</p> 178 */ 179 public static final String THUMBNAIL = "thumbnail"; 180 181 /** 182 * The touch icon for the web page, may be NULL. 183 * Must decode via {@link BitmapFactory#decodeByteArray}. 184 * <p>Type: BLOB (image)</p> 185 * @hide 186 */ 187 public static final String TOUCH_ICON = "touch_icon"; 188 } 189 190 interface HistoryColumns { 191 /** 192 * The date the item was last visited, in milliseconds since the epoch. 193 * <p>Type: INTEGER (date in milliseconds since January 1, 1970)</p> 194 */ 195 public static final String DATE_LAST_VISITED = "date"; 196 197 /** 198 * The number of times the item has been visited. 199 * <p>Type: INTEGER</p> 200 */ 201 public static final String VISITS = "visits"; 202 203 public static final String USER_ENTERED = "user_entered"; 204 } 205 206 /** 207 * The bookmarks table, which holds the user's browser bookmarks. 208 */ 209 public static final class Bookmarks implements CommonColumns, ImageColumns, SyncColumns { 210 /** 211 * This utility class cannot be instantiated. 212 */ 213 private Bookmarks() {} 214 215 /** 216 * The content:// style URI for this table 217 */ 218 public static final Uri CONTENT_URI = Uri.withAppendedPath(AUTHORITY_URI, "bookmarks"); 219 220 /** 221 * The content:// style URI for the default folder 222 */ 223 public static final Uri CONTENT_URI_DEFAULT_FOLDER = 224 Uri.withAppendedPath(CONTENT_URI, "folder"); 225 226 /** 227 * Query parameter used to specify an account name 228 */ 229 public static final String PARAM_ACCOUNT_NAME = "acct_name"; 230 231 /** 232 * Query parameter used to specify an account type 233 */ 234 public static final String PARAM_ACCOUNT_TYPE = "acct_type"; 235 236 /** 237 * Builds a URI that points to a specific folder. 238 * @param folderId the ID of the folder to point to 239 */ 240 public static final Uri buildFolderUri(long folderId) { 241 return ContentUris.withAppendedId(CONTENT_URI_DEFAULT_FOLDER, folderId); 242 } 243 244 /** 245 * The MIME type of {@link #CONTENT_URI} providing a directory of bookmarks. 246 */ 247 public static final String CONTENT_TYPE = "vnd.android.cursor.dir/bookmark"; 248 249 /** 250 * The MIME type of a {@link #CONTENT_URI} of a single bookmark. 251 */ 252 public static final String CONTENT_ITEM_TYPE = "vnd.android.cursor.item/bookmark"; 253 254 /** 255 * Query parameter to use if you want to see deleted bookmarks that are still 256 * around on the device and haven't been synced yet. 257 * @see #IS_DELETED 258 */ 259 public static final String QUERY_PARAMETER_SHOW_DELETED = "show_deleted"; 260 261 /** 262 * Flag indicating if an item is a folder or bookmark. Non-zero values indicate 263 * a folder and zero indicates a bookmark. 264 * <P>Type: INTEGER (boolean)</P> 265 */ 266 public static final String IS_FOLDER = "folder"; 267 268 /** 269 * The ID of the parent folder. ID 0 is the root folder. 270 * <P>Type: INTEGER (reference to item in the same table)</P> 271 */ 272 public static final String PARENT = "parent"; 273 274 /** 275 * The source ID for an item's parent. Read-only. 276 * @see #PARENT 277 */ 278 public static final String PARENT_SOURCE_ID = "parent_source"; 279 280 /** 281 * The position of the bookmark in relation to it's siblings that share the same 282 * {@link #PARENT}. May be negative. 283 * <P>Type: INTEGER</P> 284 */ 285 public static final String POSITION = "position"; 286 287 /** 288 * The item that the bookmark should be inserted after. 289 * May be negative. 290 * <P>Type: INTEGER</P> 291 */ 292 public static final String INSERT_AFTER = "insert_after"; 293 294 /** 295 * The source ID for the item that the bookmark should be inserted after. Read-only. 296 * May be negative. 297 * <P>Type: INTEGER</P> 298 * @see #INSERT_AFTER 299 */ 300 public static final String INSERT_AFTER_SOURCE_ID = "insert_after_source"; 301 302 /** 303 * A flag to indicate if an item has been deleted. Queries will not return deleted 304 * entries unless you add the {@link #QUERY_PARAMETER_SHOW_DELETED} query paramter 305 * to the URI when performing your query. 306 * <p>Type: INTEGER (non-zero if the item has been deleted, zero if it hasn't) 307 * @see #QUERY_PARAMETER_SHOW_DELETED 308 */ 309 public static final String IS_DELETED = "deleted"; 310 } 311 312 /** 313 * Read-only table that lists all the accounts that are used to provide bookmarks. 314 */ 315 public static final class Accounts { 316 /** 317 * Directory under {@link Bookmarks#CONTENT_URI} 318 */ 319 public static final Uri CONTENT_URI = 320 AUTHORITY_URI.buildUpon().appendPath("accounts").build(); 321 322 /** 323 * The name of the account instance to which this row belongs, which when paired with 324 * {@link #ACCOUNT_TYPE} identifies a specific account. 325 * <P>Type: TEXT</P> 326 */ 327 public static final String ACCOUNT_NAME = "account_name"; 328 329 /** 330 * The type of account to which this row belongs, which when paired with 331 * {@link #ACCOUNT_NAME} identifies a specific account. 332 * <P>Type: TEXT</P> 333 */ 334 public static final String ACCOUNT_TYPE = "account_type"; 335 336 /** 337 * The ID of the account's root folder. This will be the ID of the folder 338 * returned when querying {@link Bookmarks#CONTENT_URI_DEFAULT_FOLDER}. 339 * <P>Type: INTEGER</P> 340 */ 341 public static final String ROOT_ID = "root_id"; 342 } 343 344 /** 345 * The history table, which holds the browsing history. 346 */ 347 public static final class History implements CommonColumns, HistoryColumns, ImageColumns { 348 /** 349 * This utility class cannot be instantiated. 350 */ 351 private History() {} 352 353 /** 354 * The content:// style URI for this table 355 */ 356 public static final Uri CONTENT_URI = Uri.withAppendedPath(AUTHORITY_URI, "history"); 357 358 /** 359 * The MIME type of {@link #CONTENT_URI} providing a directory of browser history items. 360 */ 361 public static final String CONTENT_TYPE = "vnd.android.cursor.dir/browser-history"; 362 363 /** 364 * The MIME type of a {@link #CONTENT_URI} of a single browser history item. 365 */ 366 public static final String CONTENT_ITEM_TYPE = "vnd.android.cursor.item/browser-history"; 367 } 368 369 /** 370 * The search history table. 371 * @hide 372 */ 373 public static final class Searches { 374 private Searches() {} 375 376 /** 377 * The content:// style URI for this table 378 */ 379 public static final Uri CONTENT_URI = Uri.withAppendedPath(AUTHORITY_URI, "searches"); 380 381 /** 382 * The MIME type of {@link #CONTENT_URI} providing a directory of browser search items. 383 */ 384 public static final String CONTENT_TYPE = "vnd.android.cursor.dir/searches"; 385 386 /** 387 * The MIME type of a {@link #CONTENT_URI} of a single browser search item. 388 */ 389 public static final String CONTENT_ITEM_TYPE = "vnd.android.cursor.item/searches"; 390 391 /** 392 * The unique ID for a row. 393 * <P>Type: INTEGER (long)</P> 394 */ 395 public static final String _ID = "_id"; 396 397 /** 398 * The user entered search term. 399 */ 400 public static final String SEARCH = "search"; 401 402 /** 403 * The date the search was performed, in milliseconds since the epoch. 404 * <p>Type: NUMBER (date in milliseconds since January 1, 1970)</p> 405 */ 406 public static final String DATE = "date"; 407 } 408 409 /** 410 * A table provided for sync adapters to use for storing private sync state data. 411 * 412 * @see SyncStateContract 413 */ 414 public static final class SyncState implements SyncStateContract.Columns { 415 /** 416 * This utility class cannot be instantiated 417 */ 418 private SyncState() {} 419 420 public static final String CONTENT_DIRECTORY = 421 SyncStateContract.Constants.CONTENT_DIRECTORY; 422 423 /** 424 * The content:// style URI for this table 425 */ 426 public static final Uri CONTENT_URI = 427 Uri.withAppendedPath(AUTHORITY_URI, CONTENT_DIRECTORY); 428 429 /** 430 * @see android.provider.SyncStateContract.Helpers#get 431 */ 432 public static byte[] get(ContentProviderClient provider, Account account) 433 throws RemoteException { 434 return SyncStateContract.Helpers.get(provider, CONTENT_URI, account); 435 } 436 437 /** 438 * @see android.provider.SyncStateContract.Helpers#get 439 */ 440 public static Pair<Uri, byte[]> getWithUri(ContentProviderClient provider, Account account) 441 throws RemoteException { 442 return SyncStateContract.Helpers.getWithUri(provider, CONTENT_URI, account); 443 } 444 445 /** 446 * @see android.provider.SyncStateContract.Helpers#set 447 */ 448 public static void set(ContentProviderClient provider, Account account, byte[] data) 449 throws RemoteException { 450 SyncStateContract.Helpers.set(provider, CONTENT_URI, account, data); 451 } 452 453 /** 454 * @see android.provider.SyncStateContract.Helpers#newSetOperation 455 */ 456 public static ContentProviderOperation newSetOperation(Account account, byte[] data) { 457 return SyncStateContract.Helpers.newSetOperation(CONTENT_URI, account, data); 458 } 459 } 460 461 /** 462 * Stores images for URLs. Only support query() and update(). 463 * @hide 464 */ 465 public static final class Images implements ImageColumns { 466 /** 467 * This utility class cannot be instantiated 468 */ 469 private Images() {} 470 471 /** 472 * The content:// style URI for this table 473 */ 474 public static final Uri CONTENT_URI = Uri.withAppendedPath(AUTHORITY_URI, "images"); 475 476 /** 477 * The URL the images came from. 478 * <P>Type: TEXT (URL)</P> 479 */ 480 public static final String URL = "url_key"; 481 } 482 483 /** 484 * A combined view of bookmarks and history. All bookmarks in all folders are included and 485 * no folders are included. 486 */ 487 public static final class Combined implements CommonColumns, HistoryColumns, ImageColumns { 488 /** 489 * This utility class cannot be instantiated 490 */ 491 private Combined() {} 492 493 /** 494 * The content:// style URI for this table 495 */ 496 public static final Uri CONTENT_URI = Uri.withAppendedPath(AUTHORITY_URI, "combined"); 497 498 /** 499 * Flag indicating that an item is a bookmark. A value of 1 indicates a bookmark, a value 500 * of 0 indicates a history item. 501 * <p>Type: INTEGER (boolean)</p> 502 */ 503 public static final String IS_BOOKMARK = "bookmark"; 504 } 505 506 /** 507 * A table that stores settings specific to the browser. Only support query and insert. 508 */ 509 public static final class Settings { 510 /** 511 * This utility class cannot be instantiated 512 */ 513 private Settings() {} 514 515 /** 516 * The content:// style URI for this table 517 */ 518 public static final Uri CONTENT_URI = Uri.withAppendedPath(AUTHORITY_URI, "settings"); 519 520 /** 521 * Key for a setting value. 522 */ 523 public static final String KEY = "key"; 524 525 /** 526 * Value for a setting. 527 */ 528 public static final String VALUE = "value"; 529 530 /** 531 * If set to non-0 the user has opted into bookmark sync. 532 */ 533 public static final String KEY_SYNC_ENABLED = "sync_enabled"; 534 535 /** 536 * Returns true if bookmark sync is enabled 537 */ 538 static public boolean isSyncEnabled(Context context) { 539 Cursor cursor = null; 540 try { 541 cursor = context.getContentResolver().query(CONTENT_URI, new String[] { VALUE }, 542 KEY + "=?", new String[] { KEY_SYNC_ENABLED }, null); 543 if (cursor == null || !cursor.moveToFirst()) { 544 return false; 545 } 546 return cursor.getInt(0) != 0; 547 } finally { 548 if (cursor != null) cursor.close(); 549 } 550 } 551 552 /** 553 * Sets the bookmark sync enabled setting. 554 */ 555 static public void setSyncEnabled(Context context, boolean enabled) { 556 ContentValues values = new ContentValues(); 557 values.put(KEY, KEY_SYNC_ENABLED); 558 values.put(VALUE, enabled ? 1 : 0); 559 context.getContentResolver().insert(CONTENT_URI, values); 560 } 561 } 562 } 563