--- a/mobile/android/base/BrowserApp.java
+++ b/mobile/android/base/BrowserApp.java
@@ -1693,17 +1693,17 @@ public class BrowserApp extends GeckoApp
} else if ("Telemetry:Gather".equals(event)) {
final BrowserDB db = getProfile().getDB();
final ContentResolver cr = getContentResolver();
Telemetry.addToHistogram("PLACES_PAGES_COUNT", db.getCount(cr, "history"));
Telemetry.addToHistogram("PLACES_BOOKMARKS_COUNT", db.getCount(cr, "bookmarks"));
Telemetry.addToHistogram("FENNEC_FAVICONS_COUNT", db.getCount(cr, "favicons"));
Telemetry.addToHistogram("FENNEC_THUMBNAILS_COUNT", db.getCount(cr, "thumbnails"));
- Telemetry.addToHistogram("FENNEC_READING_LIST_COUNT", db.getCount(getContentResolver(), "readinglist"));
+ Telemetry.addToHistogram("FENNEC_READING_LIST_COUNT", db.getReadingListAccessor().getCount(cr));
Telemetry.addToHistogram("BROWSER_IS_USER_DEFAULT", (isDefaultBrowser(Intent.ACTION_VIEW) ? 1 : 0));
if (Versions.feature16Plus) {
Telemetry.addToHistogram("BROWSER_IS_ASSIST_DEFAULT", (isDefaultBrowser(Intent.ACTION_ASSIST) ? 1 : 0));
}
} else if ("Updater:Launch".equals(event)) {
handleUpdaterLaunch();
} else if ("BrowserToolbar:Visibility".equals(event)) {
--- a/mobile/android/base/ReadingListHelper.java
+++ b/mobile/android/base/ReadingListHelper.java
@@ -4,16 +4,17 @@
package org.mozilla.gecko;
import org.json.JSONException;
import org.json.JSONObject;
import org.mozilla.gecko.db.BrowserContract.ReadingListItems;
import org.mozilla.gecko.db.BrowserDB;
import org.mozilla.gecko.db.DBUtils;
+import org.mozilla.gecko.db.ReadingListAccessor;
import org.mozilla.gecko.favicons.Favicons;
import org.mozilla.gecko.util.EventCallback;
import org.mozilla.gecko.util.NativeEventListener;
import org.mozilla.gecko.util.NativeJSObject;
import org.mozilla.gecko.util.ThreadUtils;
import org.mozilla.gecko.util.UIAsyncTask;
import android.content.ContentResolver;
@@ -25,37 +26,36 @@ import android.net.Uri;
import android.util.Log;
import android.widget.Toast;
public final class ReadingListHelper implements NativeEventListener {
private static final String LOGTAG = "GeckoReadingListHelper";
protected final Context context;
private final BrowserDB db;
-
- private final Uri readingListUriWithProfile;
+ private final ReadingListAccessor readingListAccessor;
private final ContentObserver contentObserver;
public ReadingListHelper(Context context, GeckoProfile profile) {
this.context = context;
this.db = profile.getDB();
+ this.readingListAccessor = db.getReadingListAccessor();
EventDispatcher.getInstance().registerGeckoThreadListener((NativeEventListener) this,
"Reader:AddToList", "Reader:UpdateList", "Reader:FaviconRequest", "Reader:ListStatusRequest", "Reader:RemoveFromList");
- readingListUriWithProfile = DBUtils.appendProfile(profile.getName(), ReadingListItems.CONTENT_URI);
contentObserver = new ContentObserver(null) {
@Override
public void onChange(boolean selfChange) {
fetchContent();
}
};
- context.getContentResolver().registerContentObserver(readingListUriWithProfile, false, contentObserver);
+ this.readingListAccessor.registerContentObserver(context, contentObserver);
}
public void uninit() {
EventDispatcher.getInstance().unregisterGeckoThreadListener((NativeEventListener) this,
"Reader:AddToList", "Reader:UpdateList", "Reader:FaviconRequest", "Reader:ListStatusRequest", "Reader:RemoveFromList");
context.getContentResolver().unregisterContentObserver(contentObserver);
}
@@ -99,21 +99,21 @@ public final class ReadingListHelper imp
// We can't access a NativeJSObject from the background thread, so we need to get the
// values here, even if we may not use them to insert an item into the DB.
final ContentValues values = getContentValues(message);
ThreadUtils.postToBackgroundThread(new Runnable() {
@Override
public void run() {
- if (db.isReadingListItem(cr, url)) {
+ if (readingListAccessor.isReadingListItem(cr, url)) {
showToast(R.string.reading_list_duplicate, Toast.LENGTH_SHORT);
callback.sendError("URL already in reading list: " + url);
} else {
- db.addReadingListItem(cr, values);
+ readingListAccessor.addReadingListItem(cr, values);
showToast(R.string.reading_list_added, Toast.LENGTH_SHORT);
callback.sendSuccess(url);
}
}
});
}
/**
@@ -121,17 +121,17 @@ public final class ReadingListHelper imp
*/
private void handleUpdateList(final NativeJSObject message) {
final ContentResolver cr = context.getContentResolver();
final ContentValues values = getContentValues(message);
ThreadUtils.postToBackgroundThread(new Runnable() {
@Override
public void run() {
- db.updateReadingListItem(cr, values);
+ readingListAccessor.updateReadingListItem(cr, values);
}
});
}
/**
* Creates reading list item content values from JS message.
*/
private ContentValues getContentValues(NativeJSObject message) {
@@ -187,32 +187,32 @@ public final class ReadingListHelper imp
/**
* A page can be removed from the ReadingList by panel context menu,
* or by tapping the readinglist-remove icon in the ReaderMode banner.
*/
private void handleRemoveFromList(final String url) {
ThreadUtils.postToBackgroundThread(new Runnable() {
@Override
public void run() {
- db.removeReadingListItemWithURL(context.getContentResolver(), url);
+ readingListAccessor.removeReadingListItemWithURL(context.getContentResolver(), url);
GeckoAppShell.sendEventToGecko(GeckoEvent.createBroadcastEvent("Reader:Removed", url));
showToast(R.string.page_removed, Toast.LENGTH_SHORT);
}
});
}
/**
* Gecko (ReaderMode) requests the page ReadingList status, to display
* the proper ReaderMode banner icon (readinglist-add / readinglist-remove).
*/
private void handleReadingListStatusRequest(final EventCallback callback, final String url) {
ThreadUtils.postToBackgroundThread(new Runnable() {
@Override
public void run() {
- final int inReadingList = db.isReadingListItem(context.getContentResolver(), url) ? 1 : 0;
+ final int inReadingList = readingListAccessor.isReadingListItem(context.getContentResolver(), url) ? 1 : 0;
final JSONObject json = new JSONObject();
try {
json.put("url", url);
json.put("inReadingList", inReadingList);
} catch (JSONException e) {
Log.e(LOGTAG, "JSON error - failed to return inReadingList status", e);
}
@@ -234,17 +234,17 @@ public final class ReadingListHelper imp
}
});
}
private void fetchContent() {
ThreadUtils.postToBackgroundThread(new Runnable() {
@Override
public void run() {
- final Cursor c = db.getReadingListUnfetched(context.getContentResolver());
+ final Cursor c = readingListAccessor.getReadingListUnfetched(context.getContentResolver());
try {
while (c.moveToNext()) {
JSONObject json = new JSONObject();
try {
json.put("id", c.getInt(c.getColumnIndexOrThrow(ReadingListItems._ID)));
json.put("url", c.getString(c.getColumnIndexOrThrow(ReadingListItems.URL)));
GeckoAppShell.sendEventToGecko(
GeckoEvent.createBroadcastEvent("Reader:FetchContent", json.toString()));
--- a/mobile/android/base/db/BrowserDB.java
+++ b/mobile/android/base/db/BrowserDB.java
@@ -11,17 +11,16 @@ import java.util.List;
import org.mozilla.gecko.GeckoProfile;
import org.mozilla.gecko.db.BrowserContract.ExpirePriority;
import org.mozilla.gecko.distribution.Distribution;
import org.mozilla.gecko.favicons.decoders.LoadFaviconResult;
import android.content.ContentProviderOperation;
import android.content.ContentResolver;
-import android.content.ContentValues;
import android.content.Context;
import android.database.ContentObserver;
import android.database.Cursor;
import android.graphics.drawable.BitmapDrawable;
/**
* Interface for interactions with all databases. If you want an instance
* that implements this, you should go through GeckoProfile. E.g.,
@@ -38,16 +37,17 @@ public interface BrowserDB {
public static enum FilterFlags {
EXCLUDE_PINNED_SITES
}
public abstract Searches getSearches();
public abstract TabsAccessor getTabsAccessor();
public abstract URLMetadata getURLMetadata();
+ public abstract ReadingListAccessor getReadingListAccessor();
/**
* Add default bookmarks to the database.
* Takes an offset; returns a new offset.
*/
public abstract int addDefaultBookmarks(Context context, ContentResolver cr, int offset);
/**
@@ -114,27 +114,16 @@ public interface BrowserDB {
public abstract void updateBookmark(ContentResolver cr, int id, String uri, String title, String keyword);
/**
* Can return <code>null</code>.
*/
public abstract Cursor getBookmarksInFolder(ContentResolver cr, long folderId);
/**
- * Can return <code>null</code>.
- */
- public abstract Cursor getReadingList(ContentResolver cr);
- public abstract Cursor getReadingListUnfetched(ContentResolver cr);
- public abstract boolean isReadingListItem(ContentResolver cr, String uri);
- public abstract void addReadingListItem(ContentResolver cr, ContentValues values);
- public abstract void updateReadingListItem(ContentResolver cr, ContentValues values);
- public abstract void removeReadingListItemWithURL(ContentResolver cr, String uri);
-
-
- /**
* Get the favicon from the database, if any, associated with the given favicon URL. (That is,
* the URL of the actual favicon image, not the URL of the page with which the favicon is associated.)
* @param cr The ContentResolver to use.
* @param faviconURL The URL of the favicon to fetch from the database.
* @return The decoded Bitmap from the database, if any. null if none is stored.
*/
public abstract LoadFaviconResult getFaviconForUrl(ContentResolver cr, String faviconURL);
--- a/mobile/android/base/db/LocalBrowserDB.java
+++ b/mobile/android/base/db/LocalBrowserDB.java
@@ -93,21 +93,21 @@ public class LocalBrowserDB implements B
private final Uri mBookmarksUriWithProfile;
private final Uri mParentsUriWithProfile;
private final Uri mHistoryUriWithProfile;
private final Uri mHistoryExpireUriWithProfile;
private final Uri mCombinedUriWithProfile;
private final Uri mUpdateHistoryUriWithProfile;
private final Uri mFaviconsUriWithProfile;
private final Uri mThumbnailsUriWithProfile;
- private final Uri mReadingListUriWithProfile;
private LocalSearches searches;
private LocalTabsAccessor tabsAccessor;
private LocalURLMetadata urlMetadata;
+ private LocalReadingListAccessor readingListAccessor;
private static final String[] DEFAULT_BOOKMARK_COLUMNS =
new String[] { Bookmarks._ID,
Bookmarks.GUID,
Bookmarks.URL,
Bookmarks.TITLE,
Bookmarks.TYPE,
Bookmarks.PARENT };
@@ -118,27 +118,27 @@ public class LocalBrowserDB implements B
mBookmarksUriWithProfile = DBUtils.appendProfile(profile, Bookmarks.CONTENT_URI);
mParentsUriWithProfile = DBUtils.appendProfile(profile, Bookmarks.PARENTS_CONTENT_URI);
mHistoryUriWithProfile = DBUtils.appendProfile(profile, History.CONTENT_URI);
mHistoryExpireUriWithProfile = DBUtils.appendProfile(profile, History.CONTENT_OLD_URI);
mCombinedUriWithProfile = DBUtils.appendProfile(profile, Combined.CONTENT_URI);
mFaviconsUriWithProfile = DBUtils.appendProfile(profile, Favicons.CONTENT_URI);
mThumbnailsUriWithProfile = DBUtils.appendProfile(profile, Thumbnails.CONTENT_URI);
- mReadingListUriWithProfile = DBUtils.appendProfile(profile, ReadingListItems.CONTENT_URI);
mUpdateHistoryUriWithProfile =
mHistoryUriWithProfile.buildUpon()
.appendQueryParameter(BrowserContract.PARAM_INCREMENT_VISITS, "true")
.appendQueryParameter(BrowserContract.PARAM_INSERT_IF_NEEDED, "true")
.build();
searches = new LocalSearches(mProfile);
tabsAccessor = new LocalTabsAccessor(mProfile);
urlMetadata = new LocalURLMetadata(mProfile);
+ readingListAccessor = new LocalReadingListAccessor(mProfile);
}
@Override
public Searches getSearches() {
return searches;
}
@Override
@@ -146,16 +146,21 @@ public class LocalBrowserDB implements B
return tabsAccessor;
}
@Override
public URLMetadata getURLMetadata() {
return urlMetadata;
}
+ @Override
+ public ReadingListAccessor getReadingListAccessor() {
+ return readingListAccessor;
+ }
+
/**
* Not thread safe. A helper to allocate new IDs for arbitrary strings.
*/
private static class NameCounter {
private final HashMap<String, Integer> names = new HashMap<String, Integer>();
private int counter;
private final int increment;
@@ -571,19 +576,16 @@ public class LocalBrowserDB implements B
// ignore folders, tags, keywords, separators, etc.
constraint = Bookmarks.TYPE + " = " + Bookmarks.TYPE_BOOKMARK;
} else if ("thumbnails".equals(database)) {
uri = mThumbnailsUriWithProfile;
columns = new String[] { Thumbnails._ID };
} else if ("favicons".equals(database)) {
uri = mFaviconsUriWithProfile;
columns = new String[] { Favicons._ID };
- } else if ("readinglist".equals(database)) {
- uri = mReadingListUriWithProfile;
- columns = new String[] { ReadingListItems._ID };
}
if (uri != null) {
final Cursor cursor = cr.query(uri, columns, constraint, null, null);
try {
count = cursor.getCount();
} finally {
@@ -815,36 +817,16 @@ public class LocalBrowserDB implements B
try {
return c.getCount() > 0;
} finally {
c.close();
}
}
@Override
- public boolean isReadingListItem(ContentResolver cr, String uri) {
- final Cursor c = cr.query(mReadingListUriWithProfile,
- new String[] { ReadingListItems._ID },
- ReadingListItems.URL + " = ? ",
- new String[] { uri },
- null);
-
- if (c == null) {
- Log.e(LOGTAG, "Null cursor in isReadingListItem");
- return false;
- }
-
- try {
- return c.getCount() > 0;
- } finally {
- c.close();
- }
- }
-
- @Override
public String getUrlForKeyword(ContentResolver cr, String keyword) {
final Cursor c = cr.query(mBookmarksUriWithProfile,
new String[] { Bookmarks.URL },
Bookmarks.KEYWORD + " = ?",
new String[] { keyword },
null);
try {
if (!c.moveToFirst()) {
@@ -964,80 +946,16 @@ public class LocalBrowserDB implements B
final String[] urlArgs = new String[] { uri, String.valueOf(Bookmarks.FIXED_PINNED_LIST_ID) };
final String urlEquals = Bookmarks.URL + " = ? AND " + Bookmarks.PARENT + " != ? ";
cr.delete(contentUri, urlEquals, urlArgs);
}
@Override
- public Cursor getReadingList(ContentResolver cr) {
- return cr.query(mReadingListUriWithProfile,
- ReadingListItems.DEFAULT_PROJECTION,
- null,
- null,
- null);
- }
-
- @Override
- public Cursor getReadingListUnfetched(ContentResolver cr) {
- return cr.query(mReadingListUriWithProfile,
- new String[] { ReadingListItems._ID, ReadingListItems.URL },
- ReadingListItems.CONTENT_STATUS + " = " + ReadingListItems.STATUS_UNFETCHED,
- null,
- null);
-
- }
-
- @Override
- public void addReadingListItem(ContentResolver cr, ContentValues values) {
- // Check that required fields are present.
- for (String field: ReadingListItems.REQUIRED_FIELDS) {
- if (!values.containsKey(field)) {
- throw new IllegalArgumentException("Missing required field for reading list item: " + field);
- }
- }
-
- // Clear delete flag if necessary
- values.put(ReadingListItems.IS_DELETED, 0);
-
- // Restore deleted record if possible
- final Uri insertUri = mReadingListUriWithProfile
- .buildUpon()
- .appendQueryParameter(BrowserContract.PARAM_INSERT_IF_NEEDED, "true")
- .build();
-
- final int updated = cr.update(insertUri,
- values,
- ReadingListItems.URL + " = ? ",
- new String[] { values.getAsString(ReadingListItems.URL) });
-
- debug("Updated " + updated + " rows to new modified time.");
- }
-
- @Override
- public void updateReadingListItem(ContentResolver cr, ContentValues values) {
- if (!values.containsKey(ReadingListItems._ID)) {
- throw new IllegalArgumentException("Cannot update reading list item without an ID");
- }
-
- final int updated = cr.update(mReadingListUriWithProfile,
- values,
- ReadingListItems._ID + " = ? ",
- new String[] { values.getAsString(ReadingListItems._ID) });
-
- debug("Updated " + updated + " reading list rows.");
- }
-
- @Override
- public void removeReadingListItemWithURL(ContentResolver cr, String uri) {
- cr.delete(mReadingListUriWithProfile, ReadingListItems.URL + " = ? ", new String[] { uri });
- }
-
- @Override
public void registerBookmarkObserver(ContentResolver cr, ContentObserver observer) {
cr.registerContentObserver(mBookmarksUriWithProfile, false, observer);
}
@Override
@RobocopTarget
public void updateBookmark(ContentResolver cr, int id, String uri, String title, String keyword) {
ContentValues values = new ContentValues();
new file mode 100644
--- /dev/null
+++ b/mobile/android/base/db/LocalReadingListAccessor.java
@@ -0,0 +1,128 @@
+/* This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
+
+package org.mozilla.gecko.db;
+
+import android.content.ContentResolver;
+import android.content.ContentValues;
+import android.content.Context;
+import android.database.ContentObserver;
+import android.database.Cursor;
+import android.net.Uri;
+import android.util.Log;
+
+public class LocalReadingListAccessor implements ReadingListAccessor {
+ private static final String LOG_TAG = "GeckoReadingListAcc";
+
+ private final Uri mReadingListUriWithProfile;
+
+ public LocalReadingListAccessor(final String profile) {
+ mReadingListUriWithProfile = DBUtils.appendProfile(profile, BrowserContract.ReadingListItems.CONTENT_URI);
+ }
+
+ @Override
+ public int getCount(ContentResolver cr) {
+ final String[] columns = new String[]{BrowserContract.ReadingListItems._ID};
+ final Cursor cursor = cr.query(mReadingListUriWithProfile, columns, null, null, null);
+ int count = 0;
+
+ try {
+ count = cursor.getCount();
+ } finally {
+ cursor.close();
+ }
+
+ Log.d(LOG_TAG, "Got count " + count + " for reading list.");
+ return count;
+ }
+
+ @Override
+ public Cursor getReadingList(ContentResolver cr) {
+ return cr.query(mReadingListUriWithProfile,
+ BrowserContract.ReadingListItems.DEFAULT_PROJECTION,
+ null,
+ null,
+ null);
+ }
+
+ @Override
+ public Cursor getReadingListUnfetched(ContentResolver cr) {
+ return cr.query(mReadingListUriWithProfile,
+ new String[] { BrowserContract.ReadingListItems._ID, BrowserContract.ReadingListItems.URL },
+ BrowserContract.ReadingListItems.CONTENT_STATUS + " = " + BrowserContract.ReadingListItems.STATUS_UNFETCHED,
+ null,
+ null);
+ }
+
+ @Override
+ public boolean isReadingListItem(ContentResolver cr, String uri) {
+ final Cursor c = cr.query(mReadingListUriWithProfile,
+ new String[] { BrowserContract.ReadingListItems._ID },
+ BrowserContract.ReadingListItems.URL + " = ? ",
+ new String[] { uri },
+ null);
+
+ if (c == null) {
+ Log.e(LOG_TAG, "Null cursor in isReadingListItem");
+ return false;
+ }
+
+ try {
+ return c.getCount() > 0;
+ } finally {
+ c.close();
+ }
+ }
+
+
+ @Override
+ public void addReadingListItem(ContentResolver cr, ContentValues values) {
+ // Check that required fields are present.
+ for (String field: BrowserContract.ReadingListItems.REQUIRED_FIELDS) {
+ if (!values.containsKey(field)) {
+ throw new IllegalArgumentException("Missing required field for reading list item: " + field);
+ }
+ }
+
+ // Clear delete flag if necessary
+ values.put(BrowserContract.ReadingListItems.IS_DELETED, 0);
+
+ // Restore deleted record if possible
+ final Uri insertUri = mReadingListUriWithProfile
+ .buildUpon()
+ .appendQueryParameter(BrowserContract.PARAM_INSERT_IF_NEEDED, "true")
+ .build();
+
+ final int updated = cr.update(insertUri,
+ values,
+ BrowserContract.ReadingListItems.URL + " = ? ",
+ new String[] { values.getAsString(BrowserContract.ReadingListItems.URL) });
+
+ Log.d(LOG_TAG, "Updated " + updated + " rows to new modified time.");
+ }
+
+ @Override
+ public void updateReadingListItem(ContentResolver cr, ContentValues values) {
+ if (!values.containsKey(BrowserContract.ReadingListItems._ID)) {
+ throw new IllegalArgumentException("Cannot update reading list item without an ID");
+ }
+
+ final int updated = cr.update(mReadingListUriWithProfile,
+ values,
+ BrowserContract.ReadingListItems._ID + " = ? ",
+ new String[] { values.getAsString(BrowserContract.ReadingListItems._ID) });
+
+ Log.d(LOG_TAG, "Updated " + updated + " reading list rows.");
+ }
+
+ @Override
+ public void removeReadingListItemWithURL(ContentResolver cr, String uri) {
+ cr.delete(mReadingListUriWithProfile, BrowserContract.ReadingListItems.URL + " = ? ", new String[]{uri});
+ }
+
+ @Override
+ public void registerContentObserver(Context context, ContentObserver observer) {
+ context.getContentResolver().registerContentObserver(mReadingListUriWithProfile, false, observer);
+ }
+}
new file mode 100644
--- /dev/null
+++ b/mobile/android/base/db/ReadingListAccessor.java
@@ -0,0 +1,32 @@
+/* This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
+
+package org.mozilla.gecko.db;
+
+import android.content.ContentResolver;
+import android.content.ContentValues;
+import android.content.Context;
+import android.database.ContentObserver;
+import android.database.Cursor;
+
+public interface ReadingListAccessor {
+ /**
+ * Can return <code>null</code>.
+ */
+ Cursor getReadingList(ContentResolver cr);
+
+ int getCount(ContentResolver cr);
+
+ Cursor getReadingListUnfetched(ContentResolver cr);
+
+ boolean isReadingListItem(ContentResolver cr, String uri);
+
+ void addReadingListItem(ContentResolver cr, ContentValues values);
+
+ void updateReadingListItem(ContentResolver cr, ContentValues values);
+
+ void removeReadingListItemWithURL(ContentResolver cr, String uri);
+
+ void registerContentObserver(Context context, ContentObserver observer);
+}
--- a/mobile/android/base/db/StubBrowserDB.java
+++ b/mobile/android/base/db/StubBrowserDB.java
@@ -21,16 +21,58 @@ import org.mozilla.gecko.mozglue.Robocop
import android.content.ContentProviderOperation;
import android.content.ContentResolver;
import android.content.ContentValues;
import android.content.Context;
import android.database.ContentObserver;
import android.database.Cursor;
import android.graphics.drawable.BitmapDrawable;
+class StubReadingListAccessor implements ReadingListAccessor {
+ @Override
+ public Cursor getReadingList(ContentResolver cr) {
+ return null;
+ }
+
+ @Override
+ public int getCount(ContentResolver cr) {
+ return 0;
+ }
+
+ @Override
+ public Cursor getReadingListUnfetched(ContentResolver cr) {
+ return null;
+ }
+
+ @Override
+ public boolean isReadingListItem(ContentResolver cr, String uri) {
+ return false;
+ }
+
+ @Override
+ public void addReadingListItem(ContentResolver cr, ContentValues values) {
+
+ }
+
+ @Override
+ public void updateReadingListItem(ContentResolver cr, ContentValues values) {
+
+ }
+
+ @Override
+ public void removeReadingListItemWithURL(ContentResolver cr, String uri) {
+
+ }
+
+ @Override
+ public void registerContentObserver(Context context, ContentObserver observer) {
+
+ }
+}
+
class StubSearches implements Searches {
public StubSearches() {
}
public void insert(ContentResolver cr, String query) {
}
}
@@ -86,32 +128,38 @@ class StubTabsAccessor implements TabsAc
/*
* This base implementation just stubs all methods. For the
* real implementations, see LocalBrowserDB.java.
*/
public class StubBrowserDB implements BrowserDB {
private final StubSearches searches = new StubSearches();
private final StubTabsAccessor tabsAccessor = new StubTabsAccessor();
private final StubURLMetadata urlMetadata = new StubURLMetadata();
+ private final StubReadingListAccessor readingListAccessor = new StubReadingListAccessor();
@Override
public Searches getSearches() {
return searches;
}
@Override
public TabsAccessor getTabsAccessor() {
return tabsAccessor;
}
@Override
public URLMetadata getURLMetadata() {
return urlMetadata;
}
+ @Override
+ public ReadingListAccessor getReadingListAccessor() {
+ return readingListAccessor;
+ }
+
protected static final Integer FAVICON_ID_NOT_FOUND = Integer.MIN_VALUE;
public StubBrowserDB(String profile) {
}
public void invalidate() { }
public int addDefaultBookmarks(Context context, ContentResolver cr, final int offset) {
--- a/mobile/android/base/home/HomeFragment.java
+++ b/mobile/android/base/home/HomeFragment.java
@@ -358,17 +358,17 @@ public abstract class HomeFragment exten
mDB.removeBookmarksWithURL(cr, mUrl);
break;
case HISTORY:
mDB.removeHistoryEntry(cr, mUrl);
break;
case READING_LIST:
- mDB.removeReadingListItemWithURL(cr, mUrl);
+ mDB.getReadingListAccessor().removeReadingListItemWithURL(cr, mUrl);
GeckoAppShell.sendEventToGecko(GeckoEvent.createBroadcastEvent("Reader:Removed", mUrl));
break;
default:
Log.e(LOGTAG, "Can't remove item type " + mType.toString());
break;
}
return null;
--- a/mobile/android/base/home/ReadingListPanel.java
+++ b/mobile/android/base/home/ReadingListPanel.java
@@ -10,16 +10,17 @@ import java.util.EnumSet;
import org.mozilla.gecko.GeckoProfile;
import org.mozilla.gecko.R;
import org.mozilla.gecko.ReaderModeUtils;
import org.mozilla.gecko.Telemetry;
import org.mozilla.gecko.TelemetryContract;
import org.mozilla.gecko.db.BrowserContract.ReadingListItems;
import org.mozilla.gecko.db.BrowserContract.URLColumns;
import org.mozilla.gecko.db.BrowserDB;
+import org.mozilla.gecko.db.ReadingListAccessor;
import org.mozilla.gecko.home.HomeContextMenuInfo.RemoveItemType;
import org.mozilla.gecko.home.HomePager.OnUrlOpenListener;
import android.content.Context;
import android.database.Cursor;
import android.os.Bundle;
import android.support.v4.content.Loader;
import android.support.v4.widget.CursorAdapter;
@@ -159,26 +160,26 @@ public class ReadingListPanel extends Ho
mList.setEmptyView(mEmptyView);
}
}
/**
* Cursor loader for the list of reading list items.
*/
private static class ReadingListLoader extends SimpleCursorLoader {
- private final BrowserDB mDB;
+ private final ReadingListAccessor accessor;
public ReadingListLoader(Context context) {
super(context);
- mDB = GeckoProfile.get(context).getDB();
+ accessor = GeckoProfile.get(context).getDB().getReadingListAccessor();
}
@Override
public Cursor loadCursor() {
- return mDB.getReadingList(getContext().getContentResolver());
+ return accessor.getReadingList(getContext().getContentResolver());
}
}
/**
* Cursor adapter for the list of reading list items.
*/
private class ReadingListAdapter extends CursorAdapter {
public ReadingListAdapter(Context context, Cursor cursor) {
--- a/mobile/android/base/moz.build
+++ b/mobile/android/base/moz.build
@@ -154,22 +154,24 @@ gbjar.sources += [
'db/BrowserContract.java',
'db/BrowserDatabaseHelper.java',
'db/BrowserDB.java',
'db/BrowserProvider.java',
'db/DBUtils.java',
'db/FormHistoryProvider.java',
'db/HomeProvider.java',
'db/LocalBrowserDB.java',
+ 'db/LocalReadingListAccessor.java',
'db/LocalSearches.java',
'db/LocalTabsAccessor.java',
'db/LocalURLMetadata.java',
'db/PasswordsProvider.java',
'db/PerProfileDatabaseProvider.java',
'db/PerProfileDatabases.java',
+ 'db/ReadingListAccessor.java',
'db/ReadingListProvider.java',
'db/RemoteClient.java',
'db/RemoteTab.java',
'db/Searches.java',
'db/SearchHistoryProvider.java',
'db/SharedBrowserDatabaseProvider.java',
'db/SQLiteBridgeContentProvider.java',
'db/StubBrowserDB.java',
--- a/mobile/android/base/overlays/service/sharemethods/AddToReadingList.java
+++ b/mobile/android/base/overlays/service/sharemethods/AddToReadingList.java
@@ -29,17 +29,17 @@ public class AddToReadingList extends Sh
ContentResolver resolver = context.getContentResolver();
LocalBrowserDB browserDB = new LocalBrowserDB(GeckoProfile.DEFAULT_PROFILE);
ContentValues values = new ContentValues();
values.put(Bookmarks.TITLE, shareData.title);
values.put(Bookmarks.URL, shareData.url);
- browserDB.addReadingListItem(resolver, values);
+ browserDB.getReadingListAccessor().addReadingListItem(resolver, values);
return Result.SUCCESS;
}
@Override
public String getSuccessMessage() {
return context.getResources().getString(R.string.reading_list_added);
}
--- a/mobile/android/base/overlays/ui/ShareDialog.java
+++ b/mobile/android/base/overlays/ui/ShareDialog.java
@@ -256,17 +256,17 @@ public class ShareDialog extends Locales
boolean isBookmark;
boolean isReadingListItem;
@Override
protected Void doInBackground() {
final ContentResolver contentResolver = getApplicationContext().getContentResolver();
isBookmark = browserDB.isBookmark(contentResolver, pageURL);
- isReadingListItem = browserDB.isReadingListItem(contentResolver, pageURL);
+ isReadingListItem = browserDB.getReadingListAccessor().isReadingListItem(contentResolver, pageURL);
return null;
}
@Override
protected void onPostExecute(Void aVoid) {
findViewById(R.id.overlay_share_bookmark_btn).setEnabled(!isBookmark);
findViewById(R.id.overlay_share_reading_list_btn).setEnabled(!isReadingListItem);