Fix unit tests to work with a singleton DBHelper instance.
The fix for the database locking bug was to have a singleton `DBHelper` instance. This breaks tests because multiple tests share the same database. The solution is to: * Hack together a static method which clears the singleton, then invoke it in the `setUp()` method for relevant test cases. * Ensure the mock context provided to the providers during the tests is able to provide a context via `getApplicationContext()`. Without this, the mock context throws an `UnsupportedOperationException` when invoking this method.
This commit is contained in:
parent
f7bbf0e282
commit
97cc279d99
@ -72,6 +72,13 @@ public abstract class FDroidProvider extends ContentProvider {
|
||||
return result;
|
||||
}
|
||||
|
||||
/**
|
||||
* Only used for testing. Not quite sure how to mock a singleton variable like this.
|
||||
*/
|
||||
public static void clearDbHelperSingleton() {
|
||||
dbHelper = null;
|
||||
}
|
||||
|
||||
private static synchronized DBHelper getOrCreateDb(Context context) {
|
||||
if (dbHelper == null) {
|
||||
Utils.debugLog(TAG, "First time accessing database, creating new helper");
|
||||
|
@ -20,6 +20,7 @@ import android.annotation.TargetApi;
|
||||
import android.content.ContentProvider;
|
||||
import android.content.ContentResolver;
|
||||
import android.content.Context;
|
||||
import android.content.ContextWrapper;
|
||||
import android.content.res.Resources;
|
||||
import android.database.DatabaseUtils;
|
||||
import android.os.Build;
|
||||
@ -136,12 +137,20 @@ public abstract class ProviderTestCase2MockContext<T extends ContentProvider> ex
|
||||
|
||||
mResolver = new MockContentResolver();
|
||||
final String filenamePrefix = "test.";
|
||||
RenamingDelegatingContext targetContextWrapper = new
|
||||
final RenamingDelegatingContext targetContextWrapper = new
|
||||
RenamingDelegatingContext(
|
||||
createMockContext(new MockContext2()), // The context that most methods are delegated to
|
||||
getContext(), // The context that file methods are delegated to
|
||||
filenamePrefix);
|
||||
mProviderContext = new IsolatedContext(mResolver, targetContextWrapper);
|
||||
|
||||
mProviderContext = new IsolatedContext(mResolver, new ContextWrapper(targetContextWrapper) {
|
||||
// The FDroidProvider class needs access to an application context in order to initialize
|
||||
// the singleton DBHelper instance.
|
||||
@Override
|
||||
public Context getApplicationContext() {
|
||||
return targetContextWrapper;
|
||||
}
|
||||
});
|
||||
|
||||
mProvider = mProviderClass.newInstance();
|
||||
mProvider.attachInfo(mProviderContext, null);
|
||||
|
@ -1,5 +1,6 @@
|
||||
package mock;
|
||||
|
||||
import android.content.Context;
|
||||
import android.content.pm.PackageManager;
|
||||
import android.content.res.Resources;
|
||||
import android.test.mock.MockContentResolver;
|
||||
@ -8,7 +9,6 @@ import android.test.mock.MockContext;
|
||||
public class MockContextSwappableComponents extends MockContext {
|
||||
|
||||
private PackageManager packageManager;
|
||||
|
||||
private Resources resources;
|
||||
private MockContentResolver contentResolver;
|
||||
|
||||
|
@ -45,6 +45,8 @@ public abstract class FDroidProviderTest<T extends FDroidProvider> extends Provi
|
||||
public void setUp() throws Exception {
|
||||
super.setUp();
|
||||
|
||||
FDroidProvider.clearDbHelperSingleton();
|
||||
|
||||
// Instantiate all providers other than the one which was already created by the base class.
|
||||
// This is because F-Droid providers tend to perform joins onto tables managed by other
|
||||
// providers, and so we need to be able to insert into those other providers for these
|
||||
|
@ -18,6 +18,7 @@ import org.fdroid.fdroid.RepoUpdater.UpdateException;
|
||||
import org.fdroid.fdroid.data.Apk;
|
||||
import org.fdroid.fdroid.data.ApkProvider;
|
||||
import org.fdroid.fdroid.data.AppProvider;
|
||||
import org.fdroid.fdroid.data.FDroidProvider;
|
||||
import org.fdroid.fdroid.data.Repo;
|
||||
import org.fdroid.fdroid.data.RepoProvider;
|
||||
import org.fdroid.fdroid.data.TempApkProvider;
|
||||
@ -122,12 +123,20 @@ public class MultiRepoUpdaterTest extends InstrumentationTestCase {
|
||||
public File getDatabasePath(String name) {
|
||||
return new File(getInstrumentation().getContext().getFilesDir(), "fdroid_test.db");
|
||||
}
|
||||
|
||||
@Override
|
||||
public Context getApplicationContext() {
|
||||
// Used by the DBHelper singleton instance.
|
||||
return this;
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setUp() throws Exception {
|
||||
super.setUp();
|
||||
|
||||
FDroidProvider.clearDbHelperSingleton();
|
||||
|
||||
context = new TestContext();
|
||||
|
||||
testFilesDir = TestUtils.getWriteableDir(getInstrumentation());
|
||||
|
Loading…
x
Reference in New Issue
Block a user