Check parent existance when adding/removing documents.
BUG=26212981 Change-Id: I8109e2324c027ec2182c6f521d57f3fe078a8660
This commit is contained in:
@@ -18,7 +18,6 @@ package com.android.mtp;
|
||||
|
||||
import android.content.ContentResolver;
|
||||
import android.database.Cursor;
|
||||
import android.database.sqlite.SQLiteException;
|
||||
import android.mtp.MtpObjectInfo;
|
||||
import android.net.Uri;
|
||||
import android.os.Bundle;
|
||||
@@ -262,31 +261,39 @@ class DocumentLoader {
|
||||
if (objectInfoList.length == 0 || getState() != STATE_LOADING) {
|
||||
return;
|
||||
}
|
||||
if (mNumLoaded == 0) {
|
||||
mDatabase.getMapper().startAddingDocuments(mIdentifier.mDocumentId);
|
||||
}
|
||||
try {
|
||||
try{
|
||||
if (mNumLoaded == 0) {
|
||||
mDatabase.getMapper().startAddingDocuments(mIdentifier.mDocumentId);
|
||||
}
|
||||
mDatabase.getMapper().putChildDocuments(
|
||||
mIdentifier.mDeviceId, mIdentifier.mDocumentId, objectInfoList);
|
||||
mNumLoaded += objectInfoList.length;
|
||||
} catch (SQLiteException exp) {
|
||||
mError = exp;
|
||||
mNumLoaded = 0;
|
||||
}
|
||||
if (getState() != STATE_LOADING) {
|
||||
mDatabase.getMapper().stopAddingDocuments(mIdentifier.mDocumentId);
|
||||
if (getState() != STATE_LOADING) {
|
||||
mDatabase.getMapper().stopAddingDocuments(mIdentifier.mDocumentId);
|
||||
}
|
||||
} catch (FileNotFoundException exception) {
|
||||
setErrorInternal(exception);
|
||||
}
|
||||
}
|
||||
|
||||
void setError(Exception message) {
|
||||
void setError(Exception error) {
|
||||
final int lastState = getState();
|
||||
mError = message;
|
||||
mNumLoaded = 0;
|
||||
setErrorInternal(error);
|
||||
if (lastState == STATE_LOADING) {
|
||||
mDatabase.getMapper().stopAddingDocuments(mIdentifier.mDocumentId);
|
||||
try {
|
||||
mDatabase.getMapper().stopAddingDocuments(mIdentifier.mDocumentId);
|
||||
} catch (FileNotFoundException exception) {
|
||||
setErrorInternal(exception);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void setErrorInternal(Exception error) {
|
||||
Log.e(MtpDocumentsProvider.TAG, "Error in DocumentLoader thread", error);
|
||||
mError = error;
|
||||
mNumLoaded = 0;
|
||||
}
|
||||
|
||||
private Uri createUri() {
|
||||
return DocumentsContract.buildChildDocumentsUri(
|
||||
MtpDocumentsProvider.AUTHORITY, mIdentifier.mDocumentId);
|
||||
|
||||
@@ -27,9 +27,9 @@ import android.mtp.MtpObjectInfo;
|
||||
import android.provider.DocumentsContract.Document;
|
||||
import android.provider.DocumentsContract.Root;
|
||||
|
||||
import com.android.internal.annotations.VisibleForTesting;
|
||||
import com.android.internal.util.Preconditions;
|
||||
|
||||
import java.io.FileNotFoundException;
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
|
||||
@@ -56,11 +56,12 @@ class Mapper {
|
||||
|
||||
/**
|
||||
* Puts device information to database.
|
||||
*
|
||||
* @return If device is added to the database.
|
||||
* @throws FileNotFoundException
|
||||
*/
|
||||
synchronized boolean putDeviceDocument(MtpDeviceRecord device) {
|
||||
synchronized boolean putDeviceDocument(MtpDeviceRecord device) throws FileNotFoundException {
|
||||
final SQLiteDatabase database = mDatabase.getSQLiteDatabase();
|
||||
Preconditions.checkState(mMappingMode.containsKey(/* no parent for root */ null));
|
||||
database.beginTransaction();
|
||||
try {
|
||||
final ContentValues[] valuesList = new ContentValues[1];
|
||||
@@ -69,6 +70,7 @@ class Mapper {
|
||||
extraValuesList[0] = new ContentValues();
|
||||
MtpDatabase.getDeviceDocumentValues(valuesList[0], extraValuesList[0], device);
|
||||
final boolean changed = putDocuments(
|
||||
null,
|
||||
valuesList,
|
||||
extraValuesList,
|
||||
COLUMN_PARENT_DOCUMENT_ID + " IS NULL",
|
||||
@@ -83,11 +85,14 @@ class Mapper {
|
||||
|
||||
/**
|
||||
* Puts root information to database.
|
||||
*
|
||||
* @param parentDocumentId Document ID of device document.
|
||||
* @param roots List of root information.
|
||||
* @return If roots are added or removed from the database.
|
||||
* @throws FileNotFoundException
|
||||
*/
|
||||
synchronized boolean putStorageDocuments(String parentDocumentId, MtpRoot[] roots) {
|
||||
synchronized boolean putStorageDocuments(String parentDocumentId, MtpRoot[] roots)
|
||||
throws FileNotFoundException {
|
||||
final SQLiteDatabase database = mDatabase.getSQLiteDatabase();
|
||||
database.beginTransaction();
|
||||
try {
|
||||
@@ -112,6 +117,7 @@ class Mapper {
|
||||
valuesList[i], extraValuesList[i], parentDocumentId, roots[i]);
|
||||
}
|
||||
final boolean changed = putDocuments(
|
||||
parentDocumentId,
|
||||
valuesList,
|
||||
extraValuesList,
|
||||
COLUMN_PARENT_DOCUMENT_ID + "=?",
|
||||
@@ -127,11 +133,14 @@ class Mapper {
|
||||
|
||||
/**
|
||||
* Puts document information to database.
|
||||
*
|
||||
* @param deviceId Device ID
|
||||
* @param parentId Parent document ID.
|
||||
* @param documents List of document information.
|
||||
* @throws FileNotFoundException
|
||||
*/
|
||||
synchronized void putChildDocuments(int deviceId, String parentId, MtpObjectInfo[] documents) {
|
||||
synchronized void putChildDocuments(int deviceId, String parentId, MtpObjectInfo[] documents)
|
||||
throws FileNotFoundException {
|
||||
final String mapColumn;
|
||||
Preconditions.checkState(mMappingMode.containsKey(parentId));
|
||||
switch (mMappingMode.get(parentId)) {
|
||||
@@ -151,6 +160,7 @@ class Mapper {
|
||||
valuesList[i], deviceId, parentId, documents[i]);
|
||||
}
|
||||
putDocuments(
|
||||
parentId,
|
||||
valuesList,
|
||||
null,
|
||||
COLUMN_PARENT_DOCUMENT_ID + "=?",
|
||||
@@ -181,9 +191,9 @@ class Mapper {
|
||||
* a corresponding existing row. Otherwise it does heuristic.
|
||||
*
|
||||
* @param parentDocumentId Parent document ID or NULL for root documents.
|
||||
* @throws FileNotFoundException
|
||||
*/
|
||||
void startAddingDocuments(@Nullable String parentDocumentId) {
|
||||
Preconditions.checkState(!mMappingMode.containsKey(parentDocumentId));
|
||||
void startAddingDocuments(@Nullable String parentDocumentId) throws FileNotFoundException {
|
||||
final String selection;
|
||||
final String[] args;
|
||||
if (parentDocumentId != null) {
|
||||
@@ -197,6 +207,9 @@ class Mapper {
|
||||
final SQLiteDatabase database = mDatabase.getSQLiteDatabase();
|
||||
database.beginTransaction();
|
||||
try {
|
||||
getParentOrHaltMapping(parentDocumentId);
|
||||
Preconditions.checkState(!mMappingMode.containsKey(parentDocumentId));
|
||||
|
||||
// Set all documents as invalidated.
|
||||
final ContentValues values = new ContentValues();
|
||||
values.put(COLUMN_ROW_STATE, ROW_STATE_INVALIDATED);
|
||||
@@ -224,22 +237,27 @@ class Mapper {
|
||||
* {@link #stopAddingDocuments(String)} turns the pending rows into 'valid'
|
||||
* rows. If the methods adds rows to database, it updates valueList with correct document ID.
|
||||
*
|
||||
* @param parentId Parent document ID.
|
||||
* @param valuesList Values for documents to be stored in the database.
|
||||
* @param rootExtraValuesList Values for root extra to be stored in the database.
|
||||
* @param selection SQL where closure to select rows that shares the same parent.
|
||||
* @param args Argument for selection SQL.
|
||||
* @return Whether the method adds new rows.
|
||||
* @return Whether it adds at least one new row that is not mapped with existing document ID.
|
||||
* @throws FileNotFoundException When parentId is not registered in the database.
|
||||
*/
|
||||
private boolean putDocuments(
|
||||
String parentId,
|
||||
ContentValues[] valuesList,
|
||||
@Nullable ContentValues[] rootExtraValuesList,
|
||||
String selection,
|
||||
String[] args,
|
||||
String mappingKey) {
|
||||
String mappingKey) throws FileNotFoundException {
|
||||
final SQLiteDatabase database = mDatabase.getSQLiteDatabase();
|
||||
boolean added = false;
|
||||
database.beginTransaction();
|
||||
try {
|
||||
getParentOrHaltMapping(parentId);
|
||||
Preconditions.checkState(mMappingMode.containsKey(parentId));
|
||||
for (int i = 0; i < valuesList.length; i++) {
|
||||
final ContentValues values = valuesList[i];
|
||||
final ContentValues rootExtraValues;
|
||||
@@ -298,11 +316,12 @@ class Mapper {
|
||||
* Maps 'pending' document and 'invalidated' document that shares the same column of groupKey.
|
||||
* If the database does not find corresponding 'invalidated' document, it just removes
|
||||
* 'invalidated' document from the database.
|
||||
*
|
||||
* @param parentId Parent document ID or null for root documents.
|
||||
* @return Whether the methods adds or removed visible rows.
|
||||
* @throws FileNotFoundException
|
||||
*/
|
||||
boolean stopAddingDocuments(@Nullable String parentId) {
|
||||
Preconditions.checkState(mMappingMode.containsKey(parentId));
|
||||
boolean stopAddingDocuments(@Nullable String parentId) throws FileNotFoundException {
|
||||
final String selection;
|
||||
final String[] args;
|
||||
if (parentId != null) {
|
||||
@@ -312,12 +331,15 @@ class Mapper {
|
||||
selection = COLUMN_PARENT_DOCUMENT_ID + " IS NULL";
|
||||
args = EMPTY_ARGS;
|
||||
}
|
||||
mMappingMode.remove(parentId);
|
||||
|
||||
final SQLiteDatabase database = mDatabase.getSQLiteDatabase();
|
||||
database.beginTransaction();
|
||||
try {
|
||||
boolean changed = false;
|
||||
getParentOrHaltMapping(parentId);
|
||||
Preconditions.checkState(mMappingMode.containsKey(parentId));
|
||||
mMappingMode.remove(parentId);
|
||||
|
||||
boolean changed = false;
|
||||
// Delete all invalidated rows that cannot be mapped.
|
||||
if (mDatabase.deleteDocumentsAndRootsRecursively(
|
||||
COLUMN_ROW_STATE + " = ? AND " + selection,
|
||||
@@ -331,4 +353,25 @@ class Mapper {
|
||||
database.endTransaction();
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the parent identifier from parent document ID if the parent ID is found in the
|
||||
* database. Otherwise it halts mapping and throws FileNotFoundException.
|
||||
*
|
||||
* @param parentId Parent document ID
|
||||
* @return Parent identifier
|
||||
* @throws FileNotFoundException
|
||||
*/
|
||||
private @Nullable Identifier getParentOrHaltMapping(
|
||||
@Nullable String parentId) throws FileNotFoundException {
|
||||
if (parentId == null) {
|
||||
return null;
|
||||
}
|
||||
try {
|
||||
return mDatabase.createIdentifier(parentId);
|
||||
} catch (FileNotFoundException error) {
|
||||
mMappingMode.remove(parentId);
|
||||
throw error;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -22,6 +22,7 @@ import android.os.Process;
|
||||
import android.provider.DocumentsContract;
|
||||
import android.util.Log;
|
||||
|
||||
import java.io.FileNotFoundException;
|
||||
import java.util.concurrent.CountDownLatch;
|
||||
import java.util.concurrent.ExecutorService;
|
||||
import java.util.concurrent.Executors;
|
||||
@@ -123,14 +124,22 @@ final class RootScanner {
|
||||
|
||||
// Update devices.
|
||||
final MtpDeviceRecord[] devices = mManager.getDevices();
|
||||
mDatabase.getMapper().startAddingDocuments(null /* parentDocumentId */);
|
||||
for (final MtpDeviceRecord device : devices) {
|
||||
if (mDatabase.getMapper().putDeviceDocument(device)) {
|
||||
try {
|
||||
mDatabase.getMapper().startAddingDocuments(null /* parentDocumentId */);
|
||||
for (final MtpDeviceRecord device : devices) {
|
||||
if (mDatabase.getMapper().putDeviceDocument(device)) {
|
||||
changed = true;
|
||||
}
|
||||
}
|
||||
if (mDatabase.getMapper().stopAddingDocuments(
|
||||
null /* parentDocumentId */)) {
|
||||
changed = true;
|
||||
}
|
||||
}
|
||||
if (mDatabase.getMapper().stopAddingDocuments(null /* parentDocumentId */)) {
|
||||
changed = true;
|
||||
} catch (FileNotFoundException exception) {
|
||||
// The top root (ID is null) must exist always.
|
||||
// FileNotFoundException is unexpected.
|
||||
Log.e(MtpDocumentsProvider.TAG, "Unexpected FileNotFoundException", exception);
|
||||
throw new AssertionError("Unexpected exception for the top parent", exception);
|
||||
}
|
||||
|
||||
// Update roots.
|
||||
@@ -139,12 +148,17 @@ final class RootScanner {
|
||||
if (documentId == null) {
|
||||
continue;
|
||||
}
|
||||
mDatabase.getMapper().startAddingDocuments(documentId);
|
||||
if (mDatabase.getMapper().putStorageDocuments(documentId, device.roots)) {
|
||||
changed = true;
|
||||
}
|
||||
if (mDatabase.getMapper().stopAddingDocuments(documentId)) {
|
||||
changed = true;
|
||||
try {
|
||||
mDatabase.getMapper().startAddingDocuments(documentId);
|
||||
if (mDatabase.getMapper().putStorageDocuments(documentId, device.roots)) {
|
||||
changed = true;
|
||||
}
|
||||
if (mDatabase.getMapper().stopAddingDocuments(documentId)) {
|
||||
changed = true;
|
||||
}
|
||||
} catch (FileNotFoundException exception) {
|
||||
Log.e(MtpDocumentsProvider.TAG, "Parent document is gone.", exception);
|
||||
continue;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -36,16 +36,23 @@ public class DocumentLoaderTest extends AndroidTestCase {
|
||||
private TestContentResolver mResolver;
|
||||
private DocumentLoader mLoader;
|
||||
final private Identifier mParentIdentifier = new Identifier(
|
||||
0, 0, 0, "1", MtpDatabaseConstants.DOCUMENT_TYPE_STORAGE);
|
||||
0, 0, 0, "2", MtpDatabaseConstants.DOCUMENT_TYPE_STORAGE);
|
||||
|
||||
@Override
|
||||
public void setUp() {
|
||||
public void setUp() throws Exception {
|
||||
mDatabase = new MtpDatabase(getContext(), MtpDatabaseConstants.FLAG_DATABASE_IN_MEMORY);
|
||||
mDatabase.getMapper().startAddingDocuments("deviceDocId");
|
||||
mDatabase.getMapper().putStorageDocuments("deviceDocId", new MtpRoot[] {
|
||||
|
||||
mDatabase.getMapper().startAddingDocuments(null);
|
||||
mDatabase.getMapper().putDeviceDocument(
|
||||
new MtpDeviceRecord(1, "Device", true, new MtpRoot[0], null, null));
|
||||
mDatabase.getMapper().stopAddingDocuments(null);
|
||||
|
||||
mDatabase.getMapper().startAddingDocuments("1");
|
||||
mDatabase.getMapper().putStorageDocuments("1", new MtpRoot[] {
|
||||
new MtpRoot(0, 0, "Storage", 1000, 1000, "")
|
||||
});
|
||||
mDatabase.getMapper().stopAddingDocuments("deviceDocId");
|
||||
mDatabase.getMapper().stopAddingDocuments("1");
|
||||
|
||||
mManager = new BlockableTestMtpManager(getContext());
|
||||
mResolver = new TestContentResolver();
|
||||
mLoader = new DocumentLoader(mManager, mResolver, mDatabase);
|
||||
|
||||
@@ -138,8 +138,10 @@ public class MtpDatabaseTest extends AndroidTestCase {
|
||||
}
|
||||
|
||||
public void testPutStorageDocuments() throws Exception {
|
||||
mDatabase.getMapper().startAddingDocuments("deviceDocId");
|
||||
mDatabase.getMapper().putStorageDocuments("deviceDocId", new MtpRoot[] {
|
||||
addTestDevice();
|
||||
|
||||
mDatabase.getMapper().startAddingDocuments("1");
|
||||
mDatabase.getMapper().putStorageDocuments("1", new MtpRoot[] {
|
||||
new MtpRoot(0, 1, "Storage", 1000, 2000, ""),
|
||||
new MtpRoot(0, 2, "Storage", 2000, 4000, ""),
|
||||
new MtpRoot(0, 3, "/@#%&<>Storage", 3000, 6000,"")
|
||||
@@ -150,7 +152,7 @@ public class MtpDatabaseTest extends AndroidTestCase {
|
||||
assertEquals(3, cursor.getCount());
|
||||
|
||||
cursor.moveToNext();
|
||||
assertEquals(1, getInt(cursor, COLUMN_DOCUMENT_ID));
|
||||
assertEquals(2, getInt(cursor, COLUMN_DOCUMENT_ID));
|
||||
assertEquals(0, getInt(cursor, COLUMN_DEVICE_ID));
|
||||
assertEquals(1, getInt(cursor, COLUMN_STORAGE_ID));
|
||||
assertTrue(isNull(cursor, COLUMN_OBJECT_HANDLE));
|
||||
@@ -165,11 +167,11 @@ public class MtpDatabaseTest extends AndroidTestCase {
|
||||
MtpDatabaseConstants.DOCUMENT_TYPE_STORAGE, getInt(cursor, COLUMN_DOCUMENT_TYPE));
|
||||
|
||||
cursor.moveToNext();
|
||||
assertEquals(2, getInt(cursor, COLUMN_DOCUMENT_ID));
|
||||
assertEquals(3, getInt(cursor, COLUMN_DOCUMENT_ID));
|
||||
assertEquals("Storage", getString(cursor, COLUMN_DISPLAY_NAME));
|
||||
|
||||
cursor.moveToNext();
|
||||
assertEquals(3, getInt(cursor, COLUMN_DOCUMENT_ID));
|
||||
assertEquals(4, getInt(cursor, COLUMN_DOCUMENT_ID));
|
||||
assertEquals("/@#%&<>Storage", getString(cursor, COLUMN_DISPLAY_NAME));
|
||||
|
||||
cursor.close();
|
||||
@@ -186,18 +188,21 @@ public class MtpDatabaseTest extends AndroidTestCase {
|
||||
}
|
||||
|
||||
public void testPutChildDocuments() throws Exception {
|
||||
mDatabase.getMapper().startAddingDocuments("parentId");
|
||||
mDatabase.getMapper().putChildDocuments(0, "parentId", new MtpObjectInfo[] {
|
||||
addTestDevice();
|
||||
addTestStorage("1");
|
||||
|
||||
mDatabase.getMapper().startAddingDocuments("2");
|
||||
mDatabase.getMapper().putChildDocuments(0, "2", new MtpObjectInfo[] {
|
||||
createDocument(100, "note.txt", MtpConstants.FORMAT_TEXT, 1024),
|
||||
createDocument(101, "image.jpg", MtpConstants.FORMAT_EXIF_JPEG, 2 * 1024 * 1024),
|
||||
createDocument(102, "music.mp3", MtpConstants.FORMAT_MP3, 3 * 1024 * 1024)
|
||||
});
|
||||
|
||||
final Cursor cursor = mDatabase.queryChildDocuments(COLUMN_NAMES, "parentId");
|
||||
final Cursor cursor = mDatabase.queryChildDocuments(COLUMN_NAMES, "2");
|
||||
assertEquals(3, cursor.getCount());
|
||||
|
||||
cursor.moveToNext();
|
||||
assertEquals(1, getInt(cursor, COLUMN_DOCUMENT_ID));
|
||||
assertEquals(3, getInt(cursor, COLUMN_DOCUMENT_ID));
|
||||
assertEquals(0, getInt(cursor, COLUMN_DEVICE_ID));
|
||||
assertEquals(0, getInt(cursor, COLUMN_STORAGE_ID));
|
||||
assertEquals(100, getInt(cursor, COLUMN_OBJECT_HANDLE));
|
||||
@@ -216,7 +221,7 @@ public class MtpDatabaseTest extends AndroidTestCase {
|
||||
MtpDatabaseConstants.DOCUMENT_TYPE_OBJECT, getInt(cursor, COLUMN_DOCUMENT_TYPE));
|
||||
|
||||
cursor.moveToNext();
|
||||
assertEquals(2, getInt(cursor, COLUMN_DOCUMENT_ID));
|
||||
assertEquals(4, getInt(cursor, COLUMN_DOCUMENT_ID));
|
||||
assertEquals(0, getInt(cursor, COLUMN_DEVICE_ID));
|
||||
assertEquals(0, getInt(cursor, COLUMN_STORAGE_ID));
|
||||
assertEquals(101, getInt(cursor, COLUMN_OBJECT_HANDLE));
|
||||
@@ -235,7 +240,7 @@ public class MtpDatabaseTest extends AndroidTestCase {
|
||||
MtpDatabaseConstants.DOCUMENT_TYPE_OBJECT, getInt(cursor, COLUMN_DOCUMENT_TYPE));
|
||||
|
||||
cursor.moveToNext();
|
||||
assertEquals(3, getInt(cursor, COLUMN_DOCUMENT_ID));
|
||||
assertEquals(5, getInt(cursor, COLUMN_DOCUMENT_ID));
|
||||
assertEquals(0, getInt(cursor, COLUMN_DEVICE_ID));
|
||||
assertEquals(0, getInt(cursor, COLUMN_STORAGE_ID));
|
||||
assertEquals(102, getInt(cursor, COLUMN_OBJECT_HANDLE));
|
||||
@@ -263,8 +268,10 @@ public class MtpDatabaseTest extends AndroidTestCase {
|
||||
DocumentsContract.Document.COLUMN_DISPLAY_NAME
|
||||
};
|
||||
|
||||
mDatabase.getMapper().startAddingDocuments("deviceDocId");
|
||||
mDatabase.getMapper().putStorageDocuments("deviceDocId", new MtpRoot[] {
|
||||
// Add device and two storages.
|
||||
addTestDevice();
|
||||
mDatabase.getMapper().startAddingDocuments("1");
|
||||
mDatabase.getMapper().putStorageDocuments("1", new MtpRoot[] {
|
||||
new MtpRoot(0, 100, "Storage A", 1000, 0, ""),
|
||||
new MtpRoot(0, 101, "Storage B", 1001, 0, "")
|
||||
});
|
||||
@@ -273,34 +280,37 @@ public class MtpDatabaseTest extends AndroidTestCase {
|
||||
final Cursor cursor = mDatabase.queryRootDocuments(columns);
|
||||
assertEquals(2, cursor.getCount());
|
||||
cursor.moveToNext();
|
||||
assertEquals(1, getInt(cursor, COLUMN_DOCUMENT_ID));
|
||||
assertEquals(2, getInt(cursor, COLUMN_DOCUMENT_ID));
|
||||
assertEquals(100, getInt(cursor, COLUMN_STORAGE_ID));
|
||||
assertEquals("Storage A", getString(cursor, COLUMN_DISPLAY_NAME));
|
||||
cursor.moveToNext();
|
||||
assertEquals(2, getInt(cursor, COLUMN_DOCUMENT_ID));
|
||||
assertEquals(3, getInt(cursor, COLUMN_DOCUMENT_ID));
|
||||
assertEquals(101, getInt(cursor, COLUMN_STORAGE_ID));
|
||||
assertEquals("Storage B", getString(cursor, COLUMN_DISPLAY_NAME));
|
||||
cursor.close();
|
||||
}
|
||||
|
||||
// Clear mapping and add a device.
|
||||
mDatabase.getMapper().clearMapping();
|
||||
addTestDevice();
|
||||
|
||||
{
|
||||
final Cursor cursor = mDatabase.queryRootDocuments(columns);
|
||||
assertEquals(2, cursor.getCount());
|
||||
cursor.moveToNext();
|
||||
assertEquals(1, getInt(cursor, COLUMN_DOCUMENT_ID));
|
||||
assertEquals(2, getInt(cursor, COLUMN_DOCUMENT_ID));
|
||||
assertTrue(isNull(cursor, COLUMN_STORAGE_ID));
|
||||
assertEquals("Storage A", getString(cursor, COLUMN_DISPLAY_NAME));
|
||||
cursor.moveToNext();
|
||||
assertEquals(2, getInt(cursor, COLUMN_DOCUMENT_ID));
|
||||
assertEquals(3, getInt(cursor, COLUMN_DOCUMENT_ID));
|
||||
assertTrue(isNull(cursor, COLUMN_STORAGE_ID));
|
||||
assertEquals("Storage B", getString(cursor, COLUMN_DISPLAY_NAME));
|
||||
cursor.close();
|
||||
}
|
||||
|
||||
mDatabase.getMapper().startAddingDocuments("deviceDocId");
|
||||
mDatabase.getMapper().putStorageDocuments("deviceDocId", new MtpRoot[] {
|
||||
// Add two storages, but one's name is different from previous one.
|
||||
mDatabase.getMapper().startAddingDocuments("1");
|
||||
mDatabase.getMapper().putStorageDocuments("1", new MtpRoot[] {
|
||||
new MtpRoot(0, 200, "Storage A", 2000, 0, ""),
|
||||
new MtpRoot(0, 202, "Storage C", 2002, 0, "")
|
||||
});
|
||||
@@ -309,31 +319,31 @@ public class MtpDatabaseTest extends AndroidTestCase {
|
||||
final Cursor cursor = mDatabase.queryRootDocuments(columns);
|
||||
assertEquals(3, cursor.getCount());
|
||||
cursor.moveToNext();
|
||||
assertEquals(1, getInt(cursor, COLUMN_DOCUMENT_ID));
|
||||
assertEquals(2, getInt(cursor, COLUMN_DOCUMENT_ID));
|
||||
assertEquals(200, getInt(cursor, COLUMN_STORAGE_ID));
|
||||
assertEquals("Storage A", getString(cursor, COLUMN_DISPLAY_NAME));
|
||||
cursor.moveToNext();
|
||||
assertEquals(2, getInt(cursor, COLUMN_DOCUMENT_ID));
|
||||
assertEquals(3, getInt(cursor, COLUMN_DOCUMENT_ID));
|
||||
assertTrue(isNull(cursor, COLUMN_STORAGE_ID));
|
||||
assertEquals("Storage B", getString(cursor, COLUMN_DISPLAY_NAME));
|
||||
cursor.moveToNext();
|
||||
assertEquals(3, getInt(cursor, COLUMN_DOCUMENT_ID));
|
||||
assertEquals(4, getInt(cursor, COLUMN_DOCUMENT_ID));
|
||||
assertEquals(202, getInt(cursor, COLUMN_STORAGE_ID));
|
||||
assertEquals("Storage C", getString(cursor, COLUMN_DISPLAY_NAME));
|
||||
cursor.close();
|
||||
}
|
||||
|
||||
mDatabase.getMapper().stopAddingDocuments("deviceDocId");
|
||||
mDatabase.getMapper().stopAddingDocuments("1");
|
||||
|
||||
{
|
||||
final Cursor cursor = mDatabase.queryRootDocuments(columns);
|
||||
assertEquals(2, cursor.getCount());
|
||||
cursor.moveToNext();
|
||||
assertEquals(1, getInt(cursor, COLUMN_DOCUMENT_ID));
|
||||
assertEquals(2, getInt(cursor, COLUMN_DOCUMENT_ID));
|
||||
assertEquals(200, getInt(cursor, COLUMN_STORAGE_ID));
|
||||
assertEquals("Storage A", getString(cursor, COLUMN_DISPLAY_NAME));
|
||||
cursor.moveToNext();
|
||||
assertEquals(3, getInt(cursor, COLUMN_DOCUMENT_ID));
|
||||
assertEquals(4, getInt(cursor, COLUMN_DOCUMENT_ID));
|
||||
assertEquals(202, getInt(cursor, COLUMN_STORAGE_ID));
|
||||
assertEquals("Storage C", getString(cursor, COLUMN_DISPLAY_NAME));
|
||||
cursor.close();
|
||||
@@ -346,69 +356,64 @@ public class MtpDatabaseTest extends AndroidTestCase {
|
||||
MtpDatabaseConstants.COLUMN_OBJECT_HANDLE,
|
||||
DocumentsContract.Document.COLUMN_DISPLAY_NAME
|
||||
};
|
||||
mDatabase.getMapper().startAddingDocuments("parentId");
|
||||
mDatabase.getMapper().putChildDocuments(0, "parentId", new MtpObjectInfo[] {
|
||||
|
||||
addTestDevice();
|
||||
addTestStorage("1");
|
||||
|
||||
mDatabase.getMapper().startAddingDocuments("2");
|
||||
mDatabase.getMapper().putChildDocuments(0, "2", new MtpObjectInfo[] {
|
||||
createDocument(100, "note.txt", MtpConstants.FORMAT_TEXT, 1024),
|
||||
createDocument(101, "image.jpg", MtpConstants.FORMAT_EXIF_JPEG, 2 * 1024 * 1024),
|
||||
createDocument(102, "music.mp3", MtpConstants.FORMAT_MP3, 3 * 1024 * 1024)
|
||||
});
|
||||
mDatabase.getMapper().clearMapping();
|
||||
|
||||
addTestDevice();
|
||||
addTestStorage("1");
|
||||
|
||||
{
|
||||
final Cursor cursor = mDatabase.queryChildDocuments(columns, "parentId");
|
||||
final Cursor cursor = mDatabase.queryChildDocuments(columns, "2");
|
||||
assertEquals(3, cursor.getCount());
|
||||
|
||||
cursor.moveToNext();
|
||||
assertEquals(1, getInt(cursor, COLUMN_DOCUMENT_ID));
|
||||
assertEquals(3, getInt(cursor, COLUMN_DOCUMENT_ID));
|
||||
assertTrue(isNull(cursor, COLUMN_OBJECT_HANDLE));
|
||||
assertEquals("note.txt", getString(cursor, COLUMN_DISPLAY_NAME));
|
||||
|
||||
cursor.moveToNext();
|
||||
assertEquals(2, getInt(cursor, COLUMN_DOCUMENT_ID));
|
||||
assertEquals(4, getInt(cursor, COLUMN_DOCUMENT_ID));
|
||||
assertTrue(isNull(cursor, COLUMN_OBJECT_HANDLE));
|
||||
assertEquals("image.jpg", getString(cursor, COLUMN_DISPLAY_NAME));
|
||||
|
||||
cursor.moveToNext();
|
||||
assertEquals(3, getInt(cursor, COLUMN_DOCUMENT_ID));
|
||||
assertEquals(5, getInt(cursor, COLUMN_DOCUMENT_ID));
|
||||
assertTrue(isNull(cursor, COLUMN_OBJECT_HANDLE));
|
||||
assertEquals("music.mp3", getString(cursor, COLUMN_DISPLAY_NAME));
|
||||
|
||||
cursor.close();
|
||||
}
|
||||
|
||||
mDatabase.getMapper().startAddingDocuments("parentId");
|
||||
mDatabase.getMapper().putChildDocuments(0, "parentId", new MtpObjectInfo[] {
|
||||
mDatabase.getMapper().startAddingDocuments("2");
|
||||
mDatabase.getMapper().putChildDocuments(0, "2", new MtpObjectInfo[] {
|
||||
createDocument(200, "note.txt", MtpConstants.FORMAT_TEXT, 1024),
|
||||
createDocument(203, "video.mp4", MtpConstants.FORMAT_MP4_CONTAINER, 1024),
|
||||
});
|
||||
mDatabase.getMapper().stopAddingDocuments("2");
|
||||
|
||||
{
|
||||
final Cursor cursor = mDatabase.queryChildDocuments(columns, "parentId");
|
||||
assertEquals(4, cursor.getCount());
|
||||
|
||||
cursor.moveToPosition(3);
|
||||
assertEquals(4, getInt(cursor, COLUMN_DOCUMENT_ID));
|
||||
assertEquals(203, getInt(cursor, COLUMN_OBJECT_HANDLE));
|
||||
assertEquals("video.mp4", getString(cursor, COLUMN_DISPLAY_NAME));
|
||||
|
||||
cursor.close();
|
||||
}
|
||||
|
||||
mDatabase.getMapper().stopAddingDocuments("parentId");
|
||||
|
||||
{
|
||||
final Cursor cursor = mDatabase.queryChildDocuments(columns, "parentId");
|
||||
final Cursor cursor = mDatabase.queryChildDocuments(columns, "2");
|
||||
assertEquals(2, cursor.getCount());
|
||||
|
||||
cursor.moveToNext();
|
||||
assertEquals(1, getInt(cursor, COLUMN_DOCUMENT_ID));
|
||||
assertEquals(3, getInt(cursor, COLUMN_DOCUMENT_ID));
|
||||
assertEquals(200, getInt(cursor, COLUMN_OBJECT_HANDLE));
|
||||
assertEquals("note.txt", getString(cursor, COLUMN_DISPLAY_NAME));
|
||||
|
||||
cursor.moveToNext();
|
||||
assertEquals(4, getInt(cursor, COLUMN_DOCUMENT_ID));
|
||||
assertEquals(6, getInt(cursor, COLUMN_DOCUMENT_ID));
|
||||
assertEquals(203, getInt(cursor, COLUMN_OBJECT_HANDLE));
|
||||
assertEquals("video.mp4", getString(cursor, COLUMN_DISPLAY_NAME));
|
||||
|
||||
cursor.close();
|
||||
}
|
||||
}
|
||||
@@ -424,10 +429,10 @@ public class MtpDatabaseTest extends AndroidTestCase {
|
||||
Root.COLUMN_AVAILABLE_BYTES
|
||||
};
|
||||
mDatabase.getMapper().startAddingDocuments(null);
|
||||
mDatabase.getMapper().putDeviceDocument(
|
||||
new MtpDeviceRecord(0, "Device A", true, new MtpRoot[0], null, null));
|
||||
mDatabase.getMapper().putDeviceDocument(
|
||||
new MtpDeviceRecord(1, "Device B", true, new MtpRoot[0], null, null));
|
||||
mDatabase.getMapper().putDeviceDocument(new MtpDeviceRecord(
|
||||
0, "Device A", true, new MtpRoot[0], null, null));
|
||||
mDatabase.getMapper().putDeviceDocument(new MtpDeviceRecord(
|
||||
1, "Device B", true, new MtpRoot[0], null, null));
|
||||
mDatabase.getMapper().stopAddingDocuments(null);
|
||||
|
||||
mDatabase.getMapper().startAddingDocuments("1");
|
||||
@@ -467,6 +472,13 @@ public class MtpDatabaseTest extends AndroidTestCase {
|
||||
|
||||
mDatabase.getMapper().clearMapping();
|
||||
|
||||
mDatabase.getMapper().startAddingDocuments(null);
|
||||
mDatabase.getMapper().putDeviceDocument(new MtpDeviceRecord(
|
||||
0, "Device A", true, new MtpRoot[0], null, null));
|
||||
mDatabase.getMapper().putDeviceDocument(new MtpDeviceRecord(
|
||||
1, "Device B", true, new MtpRoot[0], null, null));
|
||||
mDatabase.getMapper().stopAddingDocuments(null);
|
||||
|
||||
mDatabase.getMapper().startAddingDocuments("1");
|
||||
mDatabase.getMapper().startAddingDocuments("2");
|
||||
mDatabase.getMapper().putStorageDocuments("1", new MtpRoot[] {
|
||||
@@ -511,45 +523,71 @@ public class MtpDatabaseTest extends AndroidTestCase {
|
||||
MtpDatabaseConstants.COLUMN_OBJECT_HANDLE
|
||||
};
|
||||
|
||||
mDatabase.getMapper().startAddingDocuments("parentId1");
|
||||
mDatabase.getMapper().startAddingDocuments("parentId2");
|
||||
mDatabase.getMapper().putChildDocuments(0, "parentId1", new MtpObjectInfo[] {
|
||||
// Add device, storage, and two directories.
|
||||
addTestDevice();
|
||||
addTestStorage("1");
|
||||
mDatabase.getMapper().startAddingDocuments("2");
|
||||
mDatabase.getMapper().putChildDocuments(0, "2", new MtpObjectInfo[] {
|
||||
createDocument(50, "A", MtpConstants.FORMAT_ASSOCIATION, 0),
|
||||
createDocument(51, "B", MtpConstants.FORMAT_ASSOCIATION, 0),
|
||||
});
|
||||
mDatabase.getMapper().stopAddingDocuments("2");
|
||||
|
||||
// Put note.txt in each directory.
|
||||
mDatabase.getMapper().startAddingDocuments("3");
|
||||
mDatabase.getMapper().startAddingDocuments("4");
|
||||
mDatabase.getMapper().putChildDocuments(0, "3", new MtpObjectInfo[] {
|
||||
createDocument(100, "note.txt", MtpConstants.FORMAT_TEXT, 1024),
|
||||
});
|
||||
mDatabase.getMapper().putChildDocuments(0, "parentId2", new MtpObjectInfo[] {
|
||||
mDatabase.getMapper().putChildDocuments(0, "4", new MtpObjectInfo[] {
|
||||
createDocument(101, "note.txt", MtpConstants.FORMAT_TEXT, 1024),
|
||||
});
|
||||
|
||||
// Clear mapping.
|
||||
mDatabase.getMapper().clearMapping();
|
||||
|
||||
mDatabase.getMapper().startAddingDocuments("parentId1");
|
||||
mDatabase.getMapper().startAddingDocuments("parentId2");
|
||||
mDatabase.getMapper().putChildDocuments(0, "parentId1", new MtpObjectInfo[] {
|
||||
// Add device, storage, and two directories again.
|
||||
addTestDevice();
|
||||
addTestStorage("1");
|
||||
mDatabase.getMapper().startAddingDocuments("2");
|
||||
mDatabase.getMapper().putChildDocuments(0, "2", new MtpObjectInfo[] {
|
||||
createDocument(50, "A", MtpConstants.FORMAT_ASSOCIATION, 0),
|
||||
createDocument(51, "B", MtpConstants.FORMAT_ASSOCIATION, 0),
|
||||
});
|
||||
mDatabase.getMapper().stopAddingDocuments("2");
|
||||
|
||||
// Add note.txt in each directory again.
|
||||
mDatabase.getMapper().startAddingDocuments("3");
|
||||
mDatabase.getMapper().startAddingDocuments("4");
|
||||
mDatabase.getMapper().putChildDocuments(0, "3", new MtpObjectInfo[] {
|
||||
createDocument(200, "note.txt", MtpConstants.FORMAT_TEXT, 1024),
|
||||
});
|
||||
mDatabase.getMapper().putChildDocuments(0, "parentId2", new MtpObjectInfo[] {
|
||||
mDatabase.getMapper().putChildDocuments(0, "4", new MtpObjectInfo[] {
|
||||
createDocument(201, "note.txt", MtpConstants.FORMAT_TEXT, 1024),
|
||||
});
|
||||
mDatabase.getMapper().stopAddingDocuments("parentId1");
|
||||
mDatabase.getMapper().stopAddingDocuments("3");
|
||||
mDatabase.getMapper().stopAddingDocuments("4");
|
||||
|
||||
// Check if the two note.txt are mapped correctly.
|
||||
{
|
||||
final Cursor cursor = mDatabase.queryChildDocuments(columns, "parentId1");
|
||||
final Cursor cursor = mDatabase.queryChildDocuments(columns, "3");
|
||||
assertEquals(1, cursor.getCount());
|
||||
cursor.moveToNext();
|
||||
assertEquals(1, getInt(cursor, COLUMN_DOCUMENT_ID));
|
||||
assertEquals(5, getInt(cursor, COLUMN_DOCUMENT_ID));
|
||||
assertEquals(200, getInt(cursor, COLUMN_OBJECT_HANDLE));
|
||||
cursor.close();
|
||||
}
|
||||
{
|
||||
final Cursor cursor = mDatabase.queryChildDocuments(columns, "parentId2");
|
||||
final Cursor cursor = mDatabase.queryChildDocuments(columns, "4");
|
||||
assertEquals(1, cursor.getCount());
|
||||
cursor.moveToNext();
|
||||
assertEquals(2, getInt(cursor, COLUMN_DOCUMENT_ID));
|
||||
assertEquals(6, getInt(cursor, COLUMN_DOCUMENT_ID));
|
||||
assertEquals(201, getInt(cursor, COLUMN_OBJECT_HANDLE));
|
||||
cursor.close();
|
||||
}
|
||||
}
|
||||
|
||||
public void testClearMtpIdentifierBeforeResolveRootDocuments() {
|
||||
public void testClearMtpIdentifierBeforeResolveRootDocuments() throws Exception {
|
||||
final String[] columns = new String[] {
|
||||
DocumentsContract.Document.COLUMN_DOCUMENT_ID,
|
||||
MtpDatabaseConstants.COLUMN_STORAGE_ID,
|
||||
@@ -561,8 +599,8 @@ public class MtpDatabaseTest extends AndroidTestCase {
|
||||
};
|
||||
|
||||
mDatabase.getMapper().startAddingDocuments(null);
|
||||
mDatabase.getMapper().putDeviceDocument(
|
||||
new MtpDeviceRecord(0, "Device", false, new MtpRoot[0], null, null));
|
||||
mDatabase.getMapper().putDeviceDocument(new MtpDeviceRecord(
|
||||
0, "Device", false, new MtpRoot[0], null, null));
|
||||
mDatabase.getMapper().stopAddingDocuments(null);
|
||||
|
||||
mDatabase.getMapper().startAddingDocuments("1");
|
||||
@@ -571,12 +609,28 @@ public class MtpDatabaseTest extends AndroidTestCase {
|
||||
});
|
||||
mDatabase.getMapper().clearMapping();
|
||||
|
||||
mDatabase.getMapper().startAddingDocuments(null);
|
||||
mDatabase.getMapper().putDeviceDocument(new MtpDeviceRecord(
|
||||
0, "Device", false, new MtpRoot[0], null, null));
|
||||
mDatabase.getMapper().stopAddingDocuments(null);
|
||||
|
||||
try (final Cursor cursor = mDatabase.queryRoots(resources, rootColumns)) {
|
||||
assertEquals(1, cursor.getCount());
|
||||
cursor.moveToNext();
|
||||
assertEquals("1", getString(cursor, Root.COLUMN_ROOT_ID));
|
||||
}
|
||||
|
||||
mDatabase.getMapper().startAddingDocuments("1");
|
||||
mDatabase.getMapper().putStorageDocuments("1", new MtpRoot[] {
|
||||
new MtpRoot(0, 200, "Storage", 2000, 0, ""),
|
||||
});
|
||||
mDatabase.getMapper().clearMapping();
|
||||
|
||||
mDatabase.getMapper().startAddingDocuments(null);
|
||||
mDatabase.getMapper().putDeviceDocument(new MtpDeviceRecord(
|
||||
0, "Device", false, new MtpRoot[0], null, null));
|
||||
mDatabase.getMapper().stopAddingDocuments(null);
|
||||
|
||||
mDatabase.getMapper().startAddingDocuments("1");
|
||||
mDatabase.getMapper().putStorageDocuments("1", new MtpRoot[] {
|
||||
new MtpRoot(0, 300, "Storage", 3000, 0, ""),
|
||||
@@ -609,39 +663,47 @@ public class MtpDatabaseTest extends AndroidTestCase {
|
||||
DocumentsContract.Document.COLUMN_DISPLAY_NAME
|
||||
};
|
||||
|
||||
mDatabase.getMapper().startAddingDocuments("deviceDocId");
|
||||
mDatabase.getMapper().putStorageDocuments("deviceDocId", new MtpRoot[] {
|
||||
new MtpRoot(0, 100, "Storage", 0, 0, ""),
|
||||
});
|
||||
// Add a device and a storage.
|
||||
addTestDevice();
|
||||
addTestStorage("1");
|
||||
|
||||
// Disconnect devices.
|
||||
mDatabase.getMapper().clearMapping();
|
||||
|
||||
mDatabase.getMapper().startAddingDocuments("deviceDocId");
|
||||
mDatabase.getMapper().putStorageDocuments("deviceDocId", new MtpRoot[] {
|
||||
// Add a device and two storages that has same name.
|
||||
addTestDevice();
|
||||
mDatabase.getMapper().startAddingDocuments("1");
|
||||
mDatabase.getMapper().putStorageDocuments("1", new MtpRoot[] {
|
||||
new MtpRoot(0, 200, "Storage", 2000, 0, ""),
|
||||
new MtpRoot(0, 201, "Storage", 2001, 0, ""),
|
||||
});
|
||||
mDatabase.getMapper().stopAddingDocuments("deviceDocId");
|
||||
mDatabase.getMapper().stopAddingDocuments("1");
|
||||
|
||||
{
|
||||
final Cursor cursor = mDatabase.queryRootDocuments(columns);
|
||||
assertEquals(2, cursor.getCount());
|
||||
|
||||
// First storage reuse document ID of previous storage.
|
||||
cursor.moveToNext();
|
||||
// One reuses exisitng document ID 1.
|
||||
assertEquals(1, getInt(cursor, COLUMN_DOCUMENT_ID));
|
||||
assertEquals(2, getInt(cursor, COLUMN_DOCUMENT_ID));
|
||||
assertEquals(200, getInt(cursor, COLUMN_STORAGE_ID));
|
||||
assertEquals("Storage", getString(cursor, COLUMN_DISPLAY_NAME));
|
||||
|
||||
// Second one has new document ID.
|
||||
cursor.moveToNext();
|
||||
assertEquals(2, getInt(cursor, COLUMN_DOCUMENT_ID));
|
||||
assertEquals(3, getInt(cursor, COLUMN_DOCUMENT_ID));
|
||||
assertEquals(201, getInt(cursor, COLUMN_STORAGE_ID));
|
||||
assertEquals("Storage", getString(cursor, COLUMN_DISPLAY_NAME));
|
||||
|
||||
cursor.close();
|
||||
}
|
||||
}
|
||||
|
||||
public void testReplaceExistingRoots() {
|
||||
public void testReplaceExistingRoots() throws Exception {
|
||||
mDatabase.getMapper().startAddingDocuments(null);
|
||||
mDatabase.getMapper().putDeviceDocument(
|
||||
new MtpDeviceRecord(0, "Device", true, new MtpRoot[0], null, null));
|
||||
mDatabase.getMapper().putDeviceDocument(new MtpDeviceRecord(
|
||||
0, "Device", true, new MtpRoot[0], null, null));
|
||||
mDatabase.getMapper().stopAddingDocuments(null);
|
||||
|
||||
// The client code should be able to replace existing rows with new information.
|
||||
@@ -687,66 +749,62 @@ public class MtpDatabaseTest extends AndroidTestCase {
|
||||
}
|
||||
}
|
||||
|
||||
public void testFailToReplaceExisitingUnmappedRoots() {
|
||||
public void testFailToReplaceExisitingUnmappedRoots() throws Exception {
|
||||
// The client code should not be able to replace rows before resolving 'unmapped' rows.
|
||||
// Add one.
|
||||
mDatabase.getMapper().startAddingDocuments(null);
|
||||
mDatabase.getMapper().putDeviceDocument(
|
||||
new MtpDeviceRecord(0, "Device", true, new MtpRoot[0], null, null));
|
||||
mDatabase.getMapper().stopAddingDocuments(null);
|
||||
|
||||
addTestDevice();
|
||||
mDatabase.getMapper().startAddingDocuments("1");
|
||||
mDatabase.getMapper().putStorageDocuments("1", new MtpRoot[] {
|
||||
new MtpRoot(0, 100, "Storage A", 0, 0, ""),
|
||||
});
|
||||
mDatabase.getMapper().clearMapping();
|
||||
final Cursor oldCursor = mDatabase.queryRoots(resources, strings(Root.COLUMN_ROOT_ID));
|
||||
assertEquals(1, oldCursor.getCount());
|
||||
|
||||
// Add one.
|
||||
mDatabase.getMapper().startAddingDocuments("1");
|
||||
mDatabase.getMapper().putStorageDocuments("1", new MtpRoot[] {
|
||||
new MtpRoot(0, 101, "Storage B", 1000, 1000, ""),
|
||||
});
|
||||
// Add one more before resolving unmapped documents.
|
||||
mDatabase.getMapper().putStorageDocuments("1", new MtpRoot[] {
|
||||
new MtpRoot(0, 102, "Storage B", 1000, 1000, ""),
|
||||
});
|
||||
mDatabase.getMapper().stopAddingDocuments("1");
|
||||
addTestDevice();
|
||||
try (final Cursor oldCursor =
|
||||
mDatabase.queryRoots(resources, strings(Root.COLUMN_ROOT_ID))) {
|
||||
assertEquals(1, oldCursor.getCount());
|
||||
oldCursor.moveToNext();
|
||||
assertEquals("1", getString(oldCursor, Root.COLUMN_ROOT_ID));
|
||||
|
||||
// Because the roots shares the same name, the roots should have new IDs.
|
||||
final Cursor newCursor = mDatabase.queryChildDocuments(
|
||||
strings(Document.COLUMN_DOCUMENT_ID), "1");
|
||||
assertEquals(2, newCursor.getCount());
|
||||
oldCursor.moveToNext();
|
||||
newCursor.moveToNext();
|
||||
assertFalse(oldCursor.getString(0).equals(newCursor.getString(0)));
|
||||
newCursor.moveToNext();
|
||||
assertFalse(oldCursor.getString(0).equals(newCursor.getString(0)));
|
||||
// Add one.
|
||||
mDatabase.getMapper().startAddingDocuments("1");
|
||||
mDatabase.getMapper().putStorageDocuments("1", new MtpRoot[] {
|
||||
new MtpRoot(0, 101, "Storage B", 1000, 1000, ""),
|
||||
});
|
||||
// Add one more before resolving unmapped documents.
|
||||
mDatabase.getMapper().putStorageDocuments("1", new MtpRoot[] {
|
||||
new MtpRoot(0, 102, "Storage B", 1000, 1000, ""),
|
||||
});
|
||||
mDatabase.getMapper().stopAddingDocuments("1");
|
||||
|
||||
oldCursor.close();
|
||||
newCursor.close();
|
||||
// Because the roots shares the same name, the roots should have new IDs.
|
||||
try (final Cursor newCursor = mDatabase.queryChildDocuments(
|
||||
strings(Document.COLUMN_DOCUMENT_ID), "1")) {
|
||||
assertEquals(2, newCursor.getCount());
|
||||
newCursor.moveToNext();
|
||||
assertFalse(oldCursor.getString(0).equals(newCursor.getString(0)));
|
||||
newCursor.moveToNext();
|
||||
assertFalse(oldCursor.getString(0).equals(newCursor.getString(0)));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public void testQueryDocuments() {
|
||||
mDatabase.getMapper().startAddingDocuments("deviceDocId");
|
||||
mDatabase.getMapper().putStorageDocuments("deviceDocId", new MtpRoot[] {
|
||||
new MtpRoot(0, 100, "Storage A", 0, 0, ""),
|
||||
});
|
||||
mDatabase.getMapper().stopAddingDocuments("deviceDocId");
|
||||
public void testQueryDocuments() throws Exception {
|
||||
addTestDevice();
|
||||
addTestStorage("1");
|
||||
|
||||
final Cursor cursor = mDatabase.queryDocument("1", strings(Document.COLUMN_DISPLAY_NAME));
|
||||
final Cursor cursor = mDatabase.queryDocument("2", strings(Document.COLUMN_DISPLAY_NAME));
|
||||
assertEquals(1, cursor.getCount());
|
||||
cursor.moveToNext();
|
||||
assertEquals("Storage A", getString(cursor, Document.COLUMN_DISPLAY_NAME));
|
||||
assertEquals("Storage", getString(cursor, Document.COLUMN_DISPLAY_NAME));
|
||||
cursor.close();
|
||||
}
|
||||
|
||||
public void testQueryRoots() {
|
||||
public void testQueryRoots() throws Exception {
|
||||
// Add device document.
|
||||
mDatabase.getMapper().startAddingDocuments(null);
|
||||
mDatabase.getMapper().putDeviceDocument(
|
||||
new MtpDeviceRecord(0, "Device", false, new MtpRoot[0], null, null));
|
||||
mDatabase.getMapper().putDeviceDocument(new MtpDeviceRecord(
|
||||
0, "Device", false, new MtpRoot[0], null, null));
|
||||
mDatabase.getMapper().stopAddingDocuments(null);
|
||||
|
||||
// It the device does not have storages, it shows a device root.
|
||||
@@ -791,38 +849,12 @@ public class MtpDatabaseTest extends AndroidTestCase {
|
||||
}
|
||||
|
||||
public void testGetParentId() throws FileNotFoundException {
|
||||
mDatabase.getMapper().startAddingDocuments("deviceDocId");
|
||||
mDatabase.getMapper().putStorageDocuments("deviceDocId", new MtpRoot[] {
|
||||
new MtpRoot(0, 100, "Storage A", 0, 0, ""),
|
||||
});
|
||||
mDatabase.getMapper().stopAddingDocuments("deviceDocId");
|
||||
addTestDevice();
|
||||
|
||||
mDatabase.getMapper().startAddingDocuments("1");
|
||||
mDatabase.getMapper().putChildDocuments(
|
||||
0,
|
||||
"1",
|
||||
new MtpObjectInfo[] {
|
||||
createDocument(200, "note.txt", MtpConstants.FORMAT_TEXT, 1024),
|
||||
});
|
||||
mDatabase.getMapper().stopAddingDocuments("1");
|
||||
|
||||
assertEquals("1", mDatabase.getParentIdentifier("2").mDocumentId);
|
||||
}
|
||||
|
||||
public void testDeleteDocument() {
|
||||
mDatabase.getMapper().startAddingDocuments("deviceDocId");
|
||||
mDatabase.getMapper().putStorageDocuments("deviceDocId", new MtpRoot[] {
|
||||
mDatabase.getMapper().putStorageDocuments("1", new MtpRoot[] {
|
||||
new MtpRoot(0, 100, "Storage A", 0, 0, ""),
|
||||
});
|
||||
mDatabase.getMapper().stopAddingDocuments("deviceDocId");
|
||||
|
||||
mDatabase.getMapper().startAddingDocuments("1");
|
||||
mDatabase.getMapper().putChildDocuments(
|
||||
0,
|
||||
"1",
|
||||
new MtpObjectInfo[] {
|
||||
createDocument(200, "dir", MtpConstants.FORMAT_ASSOCIATION, 1024),
|
||||
});
|
||||
mDatabase.getMapper().stopAddingDocuments("1");
|
||||
|
||||
mDatabase.getMapper().startAddingDocuments("2");
|
||||
@@ -834,12 +866,37 @@ public class MtpDatabaseTest extends AndroidTestCase {
|
||||
});
|
||||
mDatabase.getMapper().stopAddingDocuments("2");
|
||||
|
||||
mDatabase.deleteDocument("2");
|
||||
assertEquals("2", mDatabase.getParentIdentifier("3").mDocumentId);
|
||||
}
|
||||
|
||||
public void testDeleteDocument() throws Exception {
|
||||
addTestDevice();
|
||||
addTestStorage("1");
|
||||
|
||||
mDatabase.getMapper().startAddingDocuments("2");
|
||||
mDatabase.getMapper().putChildDocuments(
|
||||
0,
|
||||
"2",
|
||||
new MtpObjectInfo[] {
|
||||
createDocument(200, "dir", MtpConstants.FORMAT_ASSOCIATION, 1024),
|
||||
});
|
||||
mDatabase.getMapper().stopAddingDocuments("2");
|
||||
|
||||
mDatabase.getMapper().startAddingDocuments("3");
|
||||
mDatabase.getMapper().putChildDocuments(
|
||||
0,
|
||||
"3",
|
||||
new MtpObjectInfo[] {
|
||||
createDocument(200, "note.txt", MtpConstants.FORMAT_TEXT, 1024),
|
||||
});
|
||||
mDatabase.getMapper().stopAddingDocuments("3");
|
||||
|
||||
mDatabase.deleteDocument("3");
|
||||
|
||||
{
|
||||
// Do not query deleted documents.
|
||||
final Cursor cursor =
|
||||
mDatabase.queryChildDocuments(strings(Document.COLUMN_DOCUMENT_ID), "1");
|
||||
mDatabase.queryChildDocuments(strings(Document.COLUMN_DOCUMENT_ID), "2");
|
||||
assertEquals(0, cursor.getCount());
|
||||
cursor.close();
|
||||
}
|
||||
@@ -847,64 +904,58 @@ public class MtpDatabaseTest extends AndroidTestCase {
|
||||
{
|
||||
// Child document should be deleted also.
|
||||
final Cursor cursor =
|
||||
mDatabase.queryDocument("3", strings(Document.COLUMN_DOCUMENT_ID));
|
||||
mDatabase.queryDocument("4", strings(Document.COLUMN_DOCUMENT_ID));
|
||||
assertEquals(0, cursor.getCount());
|
||||
cursor.close();
|
||||
}
|
||||
}
|
||||
|
||||
public void testPutNewDocument() {
|
||||
mDatabase.getMapper().startAddingDocuments("deviceDocId");
|
||||
mDatabase.getMapper().putStorageDocuments("deviceDocId", new MtpRoot[] {
|
||||
new MtpRoot(0, 100, "Storage A", 0, 0, ""),
|
||||
});
|
||||
mDatabase.getMapper().stopAddingDocuments("deviceDocId");
|
||||
public void testPutNewDocument() throws Exception {
|
||||
addTestDevice();
|
||||
addTestStorage("1");
|
||||
|
||||
assertEquals(
|
||||
"2",
|
||||
"3",
|
||||
mDatabase.putNewDocument(
|
||||
0, "1", createDocument(200, "note.txt", MtpConstants.FORMAT_TEXT, 1024)));
|
||||
0, "2", createDocument(200, "note.txt", MtpConstants.FORMAT_TEXT, 1024)));
|
||||
|
||||
{
|
||||
final Cursor cursor =
|
||||
mDatabase.queryChildDocuments(strings(Document.COLUMN_DOCUMENT_ID), "1");
|
||||
assertEquals(1, cursor.getCount());
|
||||
cursor.moveToNext();
|
||||
assertEquals("2", cursor.getString(0));
|
||||
cursor.close();
|
||||
}
|
||||
|
||||
// The new document should not be mapped with existing invalidated document.
|
||||
mDatabase.getMapper().clearMapping();
|
||||
mDatabase.getMapper().startAddingDocuments("1");
|
||||
mDatabase.putNewDocument(
|
||||
0,
|
||||
"1",
|
||||
createDocument(201, "note.txt", MtpConstants.FORMAT_TEXT, 1024));
|
||||
mDatabase.getMapper().stopAddingDocuments("1");
|
||||
|
||||
{
|
||||
final Cursor cursor =
|
||||
mDatabase.queryChildDocuments(strings(Document.COLUMN_DOCUMENT_ID), "1");
|
||||
mDatabase.queryChildDocuments(strings(Document.COLUMN_DOCUMENT_ID), "2");
|
||||
assertEquals(1, cursor.getCount());
|
||||
cursor.moveToNext();
|
||||
assertEquals("3", cursor.getString(0));
|
||||
cursor.close();
|
||||
}
|
||||
|
||||
// The new document should not be mapped with existing invalidated document.
|
||||
mDatabase.getMapper().clearMapping();
|
||||
mDatabase.getMapper().startAddingDocuments("2");
|
||||
mDatabase.putNewDocument(
|
||||
0,
|
||||
"2",
|
||||
createDocument(201, "note.txt", MtpConstants.FORMAT_TEXT, 1024));
|
||||
mDatabase.getMapper().stopAddingDocuments("2");
|
||||
|
||||
{
|
||||
final Cursor cursor =
|
||||
mDatabase.queryChildDocuments(strings(Document.COLUMN_DOCUMENT_ID), "2");
|
||||
assertEquals(1, cursor.getCount());
|
||||
cursor.moveToNext();
|
||||
assertEquals("4", cursor.getString(0));
|
||||
cursor.close();
|
||||
}
|
||||
}
|
||||
|
||||
public void testGetDocumentIdForDevice() {
|
||||
mDatabase.getMapper().startAddingDocuments(null);
|
||||
mDatabase.getMapper().putDeviceDocument(
|
||||
new MtpDeviceRecord(100, "Device", true, new MtpRoot[0], null, null));
|
||||
mDatabase.getMapper().stopAddingDocuments(null);
|
||||
assertEquals("1", mDatabase.getDocumentIdForDevice(100));
|
||||
public void testGetDocumentIdForDevice() throws Exception {
|
||||
addTestDevice();
|
||||
assertEquals("1", mDatabase.getDocumentIdForDevice(0));
|
||||
}
|
||||
|
||||
public void testGetClosedDevice() {
|
||||
public void testGetClosedDevice() throws Exception {
|
||||
mDatabase.getMapper().startAddingDocuments(null);
|
||||
mDatabase.getMapper().putDeviceDocument(new MtpDeviceRecord(
|
||||
0, "Device", /* opened is */ false , new MtpRoot[0], null, null));
|
||||
0, "Device", /* opened is */ false, new MtpRoot[0], null, null));
|
||||
mDatabase.getMapper().stopAddingDocuments(null);
|
||||
|
||||
final String[] columns = new String [] {
|
||||
@@ -920,4 +971,19 @@ public class MtpDatabaseTest extends AndroidTestCase {
|
||||
assertTrue(cursor.isNull(2));
|
||||
}
|
||||
}
|
||||
|
||||
private void addTestDevice() throws FileNotFoundException {
|
||||
mDatabase.getMapper().startAddingDocuments(null);
|
||||
mDatabase.getMapper().putDeviceDocument(new MtpDeviceRecord(
|
||||
0, "Device", /* opened is */ true, new MtpRoot[0], null, null));
|
||||
mDatabase.getMapper().stopAddingDocuments(null);
|
||||
}
|
||||
|
||||
private void addTestStorage(String parentId) throws FileNotFoundException {
|
||||
mDatabase.getMapper().startAddingDocuments(parentId);
|
||||
mDatabase.getMapper().putStorageDocuments(parentId, new MtpRoot[] {
|
||||
new MtpRoot(0, 100, "Storage", 1024, 1024, ""),
|
||||
});
|
||||
mDatabase.getMapper().stopAddingDocuments(parentId);
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user