Bug 1046709 - Part 3: Synthesize visits when importing history from Android r=nalexander,rnewman

MozReview-Commit-ID: Fcw5lygXbem

--HG--
extra : transplant_source : %D1%D4%98%DB30%8B%E8%F7%27%3DG%DC%0C%89%0E%D6%C7%A7%F8
This commit is contained in:
Grigory Kruglov 2016-04-12 15:44:27 -07:00
Родитель 1dab7ae855
Коммит 9fed9fc7bf
2 изменённых файлов: 84 добавлений и 0 удалений

Просмотреть файл

@ -91,6 +91,11 @@ public class LocalBrowserDB implements BrowserDB {
private volatile SuggestedSites mSuggestedSites;
// Constants used when importing history data from legacy browser.
public static String HISTORY_VISITS_DATE = "date";
public static String HISTORY_VISITS_COUNT = "visits";
public static String HISTORY_VISITS_URL = "url";
private final Uri mBookmarksUriWithProfile;
private final Uri mParentsUriWithProfile;
private final Uri mHistoryUriWithProfile;
@ -1486,6 +1491,72 @@ public class LocalBrowserDB implements BrowserDB {
}
}
/**
* Utility method used by AndroidImport to insert visit data for history records that were just imported.
* Uses batch operations.
*
* @param cr <code>ContentResolver</code> used to query history table and bulkInsert visit records
* @param operations Collection of operations for queueing inserts
* @param visitsToSynthesize List of ContentValues describing visit information for each history record:
* (History URL, LAST DATE VISITED, VISIT COUNT)
*/
public void insertVisitsFromImportHistoryInBatch(ContentResolver cr,
Collection<ContentProviderOperation> operations,
ArrayList<ContentValues> visitsToSynthesize) {
// If for any reason we fail to obtain history GUID for a tuple we're processing,
// let's just ignore it. It's possible that the "best-effort" history import
// did not fully succeed, so we could be missing some of the records.
int historyGUIDCol = -1;
for (ContentValues visitsInformation : visitsToSynthesize) {
final Cursor cursor = cr.query(mHistoryUriWithProfile,
new String[] {History.GUID},
History.URL + " = ?",
new String[] {visitsInformation.getAsString(HISTORY_VISITS_URL)},
null);
if (cursor == null) {
continue;
}
final String historyGUID;
try {
if (!cursor.moveToFirst()) {
continue;
}
if (historyGUIDCol == -1) {
historyGUIDCol = cursor.getColumnIndexOrThrow(History.GUID);
}
historyGUID = cursor.getString(historyGUIDCol);
} finally {
// We "continue" on a null cursor above, so it's safe to act upon it without checking.
cursor.close();
}
if (historyGUID == null) {
continue;
}
// This fakes the individual visit records, using last visited date as the starting point.
for (int i = 0; i < visitsInformation.getAsInteger(HISTORY_VISITS_COUNT); i++) {
// We rely on database defaults for IS_LOCAL and VISIT_TYPE.
final ContentValues visitToInsert = new ContentValues();
visitToInsert.put(BrowserContract.Visits.HISTORY_GUID, historyGUID);
// Visit timestamps are stored in microseconds, while Android Browser visit timestmaps
// are in milliseconds. This is the conversion point for imports.
visitToInsert.put(BrowserContract.Visits.DATE_VISITED,
(visitsInformation.getAsLong(HISTORY_VISITS_DATE) - i) * 1000);
final ContentProviderOperation.Builder builder =
ContentProviderOperation.newInsert(BrowserContract.Visits.CONTENT_URI);
builder.withValues(visitToInsert);
// Queue the insert operation
operations.add(builder.build());
}
}
}
@Override
public void updateBookmarkInBatch(ContentResolver cr,
Collection<ContentProviderOperation> operations,

Просмотреть файл

@ -5,6 +5,7 @@
package org.mozilla.gecko.preferences;
import android.content.ContentValues;
import android.os.Build;
import org.mozilla.gecko.GeckoProfile;
import org.mozilla.gecko.db.BrowserContract;
@ -115,6 +116,7 @@ public class AndroidImport implements Runnable {
}
public void mergeHistory() {
ArrayList<ContentValues> visitsToSynthesize = new ArrayList<>();
Cursor cursor = null;
try {
cursor = query (LegacyBrowserProvider.BOOKMARKS_URI,
@ -140,6 +142,11 @@ public class AndroidImport implements Runnable {
if (data != null) {
mDB.updateFaviconInBatch(mCr, mOperations, url, null, null, data);
}
ContentValues visitData = new ContentValues();
visitData.put(LocalBrowserDB.HISTORY_VISITS_DATE, date);
visitData.put(LocalBrowserDB.HISTORY_VISITS_URL, url);
visitData.put(LocalBrowserDB.HISTORY_VISITS_COUNT, visits);
visitsToSynthesize.add(visitData);
cursor.moveToNext();
}
}
@ -149,6 +156,12 @@ public class AndroidImport implements Runnable {
}
flushBatchOperations();
// Now that we have flushed history records, we need to synthesize individual visits. We have
// gathered information about all of the visits we need to synthesize into visitsForSynthesis.
mDB.insertVisitsFromImportHistoryInBatch(mCr, mOperations, visitsToSynthesize);
flushBatchOperations();
}
protected Cursor query(Uri mainUri, Uri fallbackUri, String condition) {