From 9f02bbbba1d86910d8f59eb728825e53651fc907 Mon Sep 17 00:00:00 2001 From: Torsten Grote Date: Mon, 26 Feb 2018 15:46:51 -0300 Subject: [PATCH 1/4] Do not show splash screen when signed in --- .../org/briarproject/briar/android/AppModule.java | 1 + .../briar/android/controller/ConfigController.java | 3 +++ .../android/controller/ConfigControllerImpl.java | 6 ++++++ .../briar/android/navdrawer/NavDrawerActivity.java | 14 -------------- .../briar/android/splash/SplashScreenActivity.java | 13 +++++++++---- 5 files changed, 19 insertions(+), 18 deletions(-) diff --git a/briar-android/src/main/java/org/briarproject/briar/android/AppModule.java b/briar-android/src/main/java/org/briarproject/briar/android/AppModule.java index eba5d57ee..67af25ac6 100644 --- a/briar-android/src/main/java/org/briarproject/briar/android/AppModule.java +++ b/briar-android/src/main/java/org/briarproject/briar/android/AppModule.java @@ -94,6 +94,7 @@ public class AppModule { @Override public boolean databaseExists() { + // FIXME should not run on UiThread #620 if (!dir.isDirectory()) return false; File[] files = dir.listFiles(); return files != null && files.length > 0; diff --git a/briar-android/src/main/java/org/briarproject/briar/android/controller/ConfigController.java b/briar-android/src/main/java/org/briarproject/briar/android/controller/ConfigController.java index d6bc554f6..07b32b0e2 100644 --- a/briar-android/src/main/java/org/briarproject/briar/android/controller/ConfigController.java +++ b/briar-android/src/main/java/org/briarproject/briar/android/controller/ConfigController.java @@ -17,4 +17,7 @@ public interface ConfigController { void deleteAccount(Context ctx); boolean accountExists(); + + boolean accountSignedIn(); + } diff --git a/briar-android/src/main/java/org/briarproject/briar/android/controller/ConfigControllerImpl.java b/briar-android/src/main/java/org/briarproject/briar/android/controller/ConfigControllerImpl.java index 0af60bb98..3c1979444 100644 --- a/briar-android/src/main/java/org/briarproject/briar/android/controller/ConfigControllerImpl.java +++ b/briar-android/src/main/java/org/briarproject/briar/android/controller/ConfigControllerImpl.java @@ -52,4 +52,10 @@ public class ConfigControllerImpl implements ConfigController { String hex = getEncryptedDatabaseKey(); return hex != null && databaseConfig.databaseExists(); } + + @Override + public boolean accountSignedIn() { + return databaseConfig.getEncryptionKey() != null; + } + } diff --git a/briar-android/src/main/java/org/briarproject/briar/android/navdrawer/NavDrawerActivity.java b/briar-android/src/main/java/org/briarproject/briar/android/navdrawer/NavDrawerActivity.java index d083343e9..dcc42f6c3 100644 --- a/briar-android/src/main/java/org/briarproject/briar/android/navdrawer/NavDrawerActivity.java +++ b/briar-android/src/main/java/org/briarproject/briar/android/navdrawer/NavDrawerActivity.java @@ -46,8 +46,6 @@ import java.util.logging.Logger; import javax.inject.Inject; -import static android.os.Build.MANUFACTURER; -import static android.os.Build.VERSION.SDK_INT; import static android.support.v4.app.FragmentManager.POP_BACK_STACK_INCLUSIVE; import static android.support.v4.view.GravityCompat.START; import static android.support.v4.widget.DrawerLayout.LOCK_MODE_LOCKED_CLOSED; @@ -214,18 +212,6 @@ public class NavDrawerActivity extends BriarActivity implements public void onBackPressed() { if (drawerLayout.isDrawerOpen(START)) { drawerLayout.closeDrawer(START); - } else if (getSupportFragmentManager().getBackStackEntryCount() == 0 && - getSupportFragmentManager() - .findFragmentByTag(ContactListFragment.TAG) != null) { - if (SDK_INT == 19 && MANUFACTURER.equalsIgnoreCase("Samsung")) { - // workaround for #1116 causes splash screen to show again - super.onBackPressed(); - } else { - Intent i = new Intent(Intent.ACTION_MAIN); - i.addCategory(Intent.CATEGORY_HOME); - i.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK); - startActivity(i); - } } else if (getSupportFragmentManager().getBackStackEntryCount() == 0 && getSupportFragmentManager() .findFragmentByTag(ContactListFragment.TAG) == null) { diff --git a/briar-android/src/main/java/org/briarproject/briar/android/splash/SplashScreenActivity.java b/briar-android/src/main/java/org/briarproject/briar/android/splash/SplashScreenActivity.java index 7c19f3c78..9c4535313 100644 --- a/briar-android/src/main/java/org/briarproject/briar/android/splash/SplashScreenActivity.java +++ b/briar-android/src/main/java/org/briarproject/briar/android/splash/SplashScreenActivity.java @@ -43,10 +43,15 @@ public class SplashScreenActivity extends BaseActivity { setContentView(R.layout.splash); - new Handler().postDelayed(() -> { - startNextActivity(); - supportFinishAfterTransition(); - }, 500); + if (configController.accountSignedIn()) { + startActivity(new Intent(this, NavDrawerActivity.class)); + finish(); + } else { + new Handler().postDelayed(() -> { + startNextActivity(); + supportFinishAfterTransition(); + }, 500); + } } @Override From 80770b02162917f78a30d5dcb7a836f29588bdd9 Mon Sep 17 00:00:00 2001 From: Torsten Grote Date: Mon, 26 Feb 2018 18:15:00 -0300 Subject: [PATCH 2/4] Show a status screen when opening the database or applying migrations --- .../bramble/api/db/DatabaseComponent.java | 2 +- .../api/db/DatabaseMigrationEvent.java | 9 ++ .../bramble/api/db/MigrationListener.java | 11 +++ .../api/lifecycle/LifecycleManager.java | 14 +++ .../api/lifecycle/event/StartupEvent.java | 10 +++ .../org/briarproject/bramble/db/Database.java | 3 +- .../bramble/db/DatabaseComponentImpl.java | 6 +- .../briarproject/bramble/db/H2Database.java | 7 +- .../bramble/db/HyperSqlDatabase.java | 6 +- .../briarproject/bramble/db/JdbcDatabase.java | 10 ++- .../lifecycle/LifecycleManagerImpl.java | 23 ++++- .../bramble/db/DatabaseComponentImplTest.java | 8 +- .../bramble/db/DatabaseMigrationTest.java | 30 +++---- .../db/DatabasePerformanceComparisonTest.java | 2 +- .../bramble/db/DatabaseTraceTest.java | 2 +- .../bramble/db/JdbcDatabaseTest.java | 2 +- .../db/SingleDatabasePerformanceTest.java | 2 +- .../bramble/test/TestLifecycleModule.java | 7 ++ briar-android/src/main/AndroidManifest.xml | 5 ++ .../briar/android/BriarService.java | 7 ++ .../android/activity/ActivityComponent.java | 3 + .../android/login/OpenDatabaseActivity.java | 90 +++++++++++++++++++ .../src/main/res/drawable/startup_lock.xml | 9 ++ .../main/res/drawable/startup_migration.xml | 9 ++ .../res/layout/activity_open_database.xml | 46 ++++++++++ briar-android/src/main/res/values/strings.xml | 2 + 26 files changed, 289 insertions(+), 36 deletions(-) create mode 100644 bramble-api/src/main/java/org/briarproject/bramble/api/db/DatabaseMigrationEvent.java create mode 100644 bramble-api/src/main/java/org/briarproject/bramble/api/db/MigrationListener.java create mode 100644 bramble-api/src/main/java/org/briarproject/bramble/api/lifecycle/event/StartupEvent.java create mode 100644 briar-android/src/main/java/org/briarproject/briar/android/login/OpenDatabaseActivity.java create mode 100644 briar-android/src/main/res/drawable/startup_lock.xml create mode 100644 briar-android/src/main/res/drawable/startup_migration.xml create mode 100644 briar-android/src/main/res/layout/activity_open_database.xml diff --git a/bramble-api/src/main/java/org/briarproject/bramble/api/db/DatabaseComponent.java b/bramble-api/src/main/java/org/briarproject/bramble/api/db/DatabaseComponent.java index a76138c1f..123ce4396 100644 --- a/bramble-api/src/main/java/org/briarproject/bramble/api/db/DatabaseComponent.java +++ b/bramble-api/src/main/java/org/briarproject/bramble/api/db/DatabaseComponent.java @@ -43,7 +43,7 @@ public interface DatabaseComponent { * @throws DataTooOldException if the data uses an older schema than the * current code and cannot be migrated */ - boolean open() throws DbException; + boolean open(@Nullable MigrationListener listener) throws DbException; /** * Waits for any open transactions to finish and closes the database. diff --git a/bramble-api/src/main/java/org/briarproject/bramble/api/db/DatabaseMigrationEvent.java b/bramble-api/src/main/java/org/briarproject/bramble/api/db/DatabaseMigrationEvent.java new file mode 100644 index 000000000..7edd81fa0 --- /dev/null +++ b/bramble-api/src/main/java/org/briarproject/bramble/api/db/DatabaseMigrationEvent.java @@ -0,0 +1,9 @@ +package org.briarproject.bramble.api.db; + +import org.briarproject.bramble.api.event.Event; + +/** + * An event that is broadcast before database migrations are being applied. + */ +public class DatabaseMigrationEvent extends Event { +} diff --git a/bramble-api/src/main/java/org/briarproject/bramble/api/db/MigrationListener.java b/bramble-api/src/main/java/org/briarproject/bramble/api/db/MigrationListener.java new file mode 100644 index 000000000..79e292a75 --- /dev/null +++ b/bramble-api/src/main/java/org/briarproject/bramble/api/db/MigrationListener.java @@ -0,0 +1,11 @@ +package org.briarproject.bramble.api.db; + +public interface MigrationListener { + + /** + * This is called when a migration is started while opening the database. + * It will be called once for each migration being applied. + */ + void onMigrationRun(); + +} diff --git a/bramble-api/src/main/java/org/briarproject/bramble/api/lifecycle/LifecycleManager.java b/bramble-api/src/main/java/org/briarproject/bramble/api/lifecycle/LifecycleManager.java index b70c9dec9..95b4ac08c 100644 --- a/bramble-api/src/main/java/org/briarproject/bramble/api/lifecycle/LifecycleManager.java +++ b/bramble-api/src/main/java/org/briarproject/bramble/api/lifecycle/LifecycleManager.java @@ -29,6 +29,14 @@ public interface LifecycleManager { SUCCESS } + /** + * The state the lifecycle can be in. + * Returned by {@link #getLifecycleState()} + */ + enum LifecycleState { + STARTING, MIGRATING, RUNNING + } + /** * Registers a {@link Service} to be started and stopped. */ @@ -76,4 +84,10 @@ public interface LifecycleManager { * the {@link DatabaseComponent} to be closed before returning. */ void waitForShutdown() throws InterruptedException; + + /** + * Returns the current state of the lifecycle. + */ + LifecycleState getLifecycleState(); + } \ No newline at end of file diff --git a/bramble-api/src/main/java/org/briarproject/bramble/api/lifecycle/event/StartupEvent.java b/bramble-api/src/main/java/org/briarproject/bramble/api/lifecycle/event/StartupEvent.java new file mode 100644 index 000000000..973bd1c47 --- /dev/null +++ b/bramble-api/src/main/java/org/briarproject/bramble/api/lifecycle/event/StartupEvent.java @@ -0,0 +1,10 @@ +package org.briarproject.bramble.api.lifecycle.event; + +import org.briarproject.bramble.api.event.Event; + +/** + * An event that is broadcast when the app is starting. + * This happens after the database was opened and services were started. + */ +public class StartupEvent extends Event { +} diff --git a/bramble-core/src/main/java/org/briarproject/bramble/db/Database.java b/bramble-core/src/main/java/org/briarproject/bramble/db/Database.java index 9d1c76364..0a6e54fbd 100644 --- a/bramble-core/src/main/java/org/briarproject/bramble/db/Database.java +++ b/bramble-core/src/main/java/org/briarproject/bramble/db/Database.java @@ -6,6 +6,7 @@ import org.briarproject.bramble.api.db.DataTooNewException; import org.briarproject.bramble.api.db.DataTooOldException; import org.briarproject.bramble.api.db.DbException; import org.briarproject.bramble.api.db.Metadata; +import org.briarproject.bramble.api.db.MigrationListener; import org.briarproject.bramble.api.identity.Author; import org.briarproject.bramble.api.identity.AuthorId; import org.briarproject.bramble.api.identity.LocalAuthor; @@ -45,7 +46,7 @@ interface Database { * @throws DataTooOldException if the data uses an older schema than the * current code and cannot be migrated */ - boolean open() throws DbException; + boolean open(@Nullable MigrationListener listener) throws DbException; /** * Prevents new transactions from starting, waits for all current diff --git a/bramble-core/src/main/java/org/briarproject/bramble/db/DatabaseComponentImpl.java b/bramble-core/src/main/java/org/briarproject/bramble/db/DatabaseComponentImpl.java index af80da92b..5809c09ee 100644 --- a/bramble-core/src/main/java/org/briarproject/bramble/db/DatabaseComponentImpl.java +++ b/bramble-core/src/main/java/org/briarproject/bramble/db/DatabaseComponentImpl.java @@ -10,6 +10,7 @@ import org.briarproject.bramble.api.db.ContactExistsException; import org.briarproject.bramble.api.db.DatabaseComponent; import org.briarproject.bramble.api.db.DbException; import org.briarproject.bramble.api.db.Metadata; +import org.briarproject.bramble.api.db.MigrationListener; import org.briarproject.bramble.api.db.NoSuchContactException; import org.briarproject.bramble.api.db.NoSuchGroupException; import org.briarproject.bramble.api.db.NoSuchLocalAuthorException; @@ -100,8 +101,9 @@ class DatabaseComponentImpl implements DatabaseComponent { } @Override - public boolean open() throws DbException { - boolean reopened = db.open(); + public boolean open(@Nullable MigrationListener listener) + throws DbException { + boolean reopened = db.open(listener); shutdown.addShutdownHook(() -> { try { close(); diff --git a/bramble-core/src/main/java/org/briarproject/bramble/db/H2Database.java b/bramble-core/src/main/java/org/briarproject/bramble/db/H2Database.java index 6a8196926..1c1983e67 100644 --- a/bramble-core/src/main/java/org/briarproject/bramble/db/H2Database.java +++ b/bramble-core/src/main/java/org/briarproject/bramble/db/H2Database.java @@ -3,6 +3,7 @@ package org.briarproject.bramble.db; import org.briarproject.bramble.api.crypto.SecretKey; import org.briarproject.bramble.api.db.DatabaseConfig; import org.briarproject.bramble.api.db.DbException; +import org.briarproject.bramble.api.db.MigrationListener; import org.briarproject.bramble.api.nullsafety.NotNullByDefault; import org.briarproject.bramble.api.system.Clock; import org.briarproject.bramble.util.StringUtils; @@ -13,6 +14,7 @@ import java.sql.DriverManager; import java.sql.SQLException; import java.util.Properties; +import javax.annotation.Nullable; import javax.inject.Inject; /** @@ -42,10 +44,11 @@ class H2Database extends JdbcDatabase { } @Override - public boolean open() throws DbException { + public boolean open(@Nullable MigrationListener listener) + throws DbException { boolean reopen = config.databaseExists(); if (!reopen) config.getDatabaseDirectory().mkdirs(); - super.open("org.h2.Driver", reopen); + super.open("org.h2.Driver", reopen, listener); return reopen; } diff --git a/bramble-core/src/main/java/org/briarproject/bramble/db/HyperSqlDatabase.java b/bramble-core/src/main/java/org/briarproject/bramble/db/HyperSqlDatabase.java index 1db9248cb..6a87ededa 100644 --- a/bramble-core/src/main/java/org/briarproject/bramble/db/HyperSqlDatabase.java +++ b/bramble-core/src/main/java/org/briarproject/bramble/db/HyperSqlDatabase.java @@ -3,6 +3,7 @@ package org.briarproject.bramble.db; import org.briarproject.bramble.api.crypto.SecretKey; import org.briarproject.bramble.api.db.DatabaseConfig; import org.briarproject.bramble.api.db.DbException; +import org.briarproject.bramble.api.db.MigrationListener; import org.briarproject.bramble.api.nullsafety.NotNullByDefault; import org.briarproject.bramble.api.system.Clock; import org.briarproject.bramble.util.StringUtils; @@ -13,6 +14,7 @@ import java.sql.DriverManager; import java.sql.SQLException; import java.sql.Statement; +import javax.annotation.Nullable; import javax.inject.Inject; /** @@ -44,10 +46,10 @@ class HyperSqlDatabase extends JdbcDatabase { } @Override - public boolean open() throws DbException { + public boolean open(@Nullable MigrationListener listener) throws DbException { boolean reopen = config.databaseExists(); if (!reopen) config.getDatabaseDirectory().mkdirs(); - super.open("org.hsqldb.jdbc.JDBCDriver", reopen); + super.open("org.hsqldb.jdbc.JDBCDriver", reopen, listener); return reopen; } diff --git a/bramble-core/src/main/java/org/briarproject/bramble/db/JdbcDatabase.java b/bramble-core/src/main/java/org/briarproject/bramble/db/JdbcDatabase.java index f1f795a8c..e71f30c58 100644 --- a/bramble-core/src/main/java/org/briarproject/bramble/db/JdbcDatabase.java +++ b/bramble-core/src/main/java/org/briarproject/bramble/db/JdbcDatabase.java @@ -8,6 +8,7 @@ import org.briarproject.bramble.api.db.DataTooOldException; import org.briarproject.bramble.api.db.DbClosedException; import org.briarproject.bramble.api.db.DbException; import org.briarproject.bramble.api.db.Metadata; +import org.briarproject.bramble.api.db.MigrationListener; import org.briarproject.bramble.api.identity.Author; import org.briarproject.bramble.api.identity.AuthorId; import org.briarproject.bramble.api.identity.LocalAuthor; @@ -301,7 +302,8 @@ abstract class JdbcDatabase implements Database { this.clock = clock; } - protected void open(String driverClass, boolean reopen) throws DbException { + protected void open(String driverClass, boolean reopen, + @Nullable MigrationListener listener) throws DbException { // Load the JDBC driver try { Class.forName(driverClass); @@ -312,7 +314,7 @@ abstract class JdbcDatabase implements Database { Connection txn = startTransaction(); try { if (reopen) { - checkSchemaVersion(txn); + checkSchemaVersion(txn, listener); } else { createTables(txn); storeSchemaVersion(txn, CODE_SCHEMA_VERSION); @@ -335,7 +337,8 @@ abstract class JdbcDatabase implements Database { * @throws DataTooOldException if the data uses an older schema than the * current code and cannot be migrated */ - private void checkSchemaVersion(Connection txn) throws DbException { + private void checkSchemaVersion(Connection txn, + @Nullable MigrationListener listener) throws DbException { Settings s = getSettings(txn, DB_SETTINGS_NAMESPACE); int dataSchemaVersion = s.getInt(SCHEMA_VERSION_KEY, -1); if (dataSchemaVersion == -1) throw new DbException(); @@ -348,6 +351,7 @@ abstract class JdbcDatabase implements Database { if (start == dataSchemaVersion) { if (LOG.isLoggable(INFO)) LOG.info("Migrating from schema " + start + " to " + end); + if (listener != null) listener.onMigrationRun(); // Apply the migration m.migrate(txn); // Store the new schema version diff --git a/bramble-core/src/main/java/org/briarproject/bramble/lifecycle/LifecycleManagerImpl.java b/bramble-core/src/main/java/org/briarproject/bramble/lifecycle/LifecycleManagerImpl.java index 029170c91..6e55a8df5 100644 --- a/bramble-core/src/main/java/org/briarproject/bramble/lifecycle/LifecycleManagerImpl.java +++ b/bramble-core/src/main/java/org/briarproject/bramble/lifecycle/LifecycleManagerImpl.java @@ -5,7 +5,9 @@ import org.briarproject.bramble.api.crypto.KeyPair; import org.briarproject.bramble.api.db.DataTooNewException; import org.briarproject.bramble.api.db.DataTooOldException; import org.briarproject.bramble.api.db.DatabaseComponent; +import org.briarproject.bramble.api.db.DatabaseMigrationEvent; import org.briarproject.bramble.api.db.DbException; +import org.briarproject.bramble.api.db.MigrationListener; import org.briarproject.bramble.api.db.Transaction; import org.briarproject.bramble.api.event.EventBus; import org.briarproject.bramble.api.identity.AuthorFactory; @@ -15,6 +17,7 @@ import org.briarproject.bramble.api.lifecycle.LifecycleManager; import org.briarproject.bramble.api.lifecycle.Service; import org.briarproject.bramble.api.lifecycle.ServiceException; import org.briarproject.bramble.api.lifecycle.event.ShutdownEvent; +import org.briarproject.bramble.api.lifecycle.event.StartupEvent; import org.briarproject.bramble.api.nullsafety.NotNullByDefault; import org.briarproject.bramble.api.sync.Client; @@ -31,6 +34,9 @@ import javax.inject.Inject; import static java.util.logging.Level.INFO; import static java.util.logging.Level.WARNING; +import static org.briarproject.bramble.api.lifecycle.LifecycleManager.LifecycleState.MIGRATING; +import static org.briarproject.bramble.api.lifecycle.LifecycleManager.LifecycleState.RUNNING; +import static org.briarproject.bramble.api.lifecycle.LifecycleManager.LifecycleState.STARTING; import static org.briarproject.bramble.api.lifecycle.LifecycleManager.StartResult.ALREADY_RUNNING; import static org.briarproject.bramble.api.lifecycle.LifecycleManager.StartResult.DATA_TOO_NEW_ERROR; import static org.briarproject.bramble.api.lifecycle.LifecycleManager.StartResult.DATA_TOO_OLD_ERROR; @@ -40,7 +46,7 @@ import static org.briarproject.bramble.api.lifecycle.LifecycleManager.StartResul @ThreadSafe @NotNullByDefault -class LifecycleManagerImpl implements LifecycleManager { +class LifecycleManagerImpl implements LifecycleManager, MigrationListener { private static final Logger LOG = Logger.getLogger(LifecycleManagerImpl.class.getName()); @@ -57,6 +63,7 @@ class LifecycleManagerImpl implements LifecycleManager { private final CountDownLatch dbLatch = new CountDownLatch(1); private final CountDownLatch startupLatch = new CountDownLatch(1); private final CountDownLatch shutdownLatch = new CountDownLatch(1); + private volatile LifecycleState state = STARTING; @Inject LifecycleManagerImpl(DatabaseComponent db, EventBus eventBus, @@ -123,7 +130,7 @@ class LifecycleManagerImpl implements LifecycleManager { LOG.info("Starting services"); long start = System.currentTimeMillis(); - boolean reopened = db.open(); + boolean reopened = db.open(this); long duration = System.currentTimeMillis() - start; if (LOG.isLoggable(INFO)) { if (reopened) @@ -162,6 +169,8 @@ class LifecycleManagerImpl implements LifecycleManager { } } startupLatch.countDown(); + state = RUNNING; + eventBus.broadcast(new StartupEvent()); return SUCCESS; } catch (DataTooOldException e) { if (LOG.isLoggable(WARNING)) LOG.log(WARNING, e.toString(), e); @@ -180,6 +189,12 @@ class LifecycleManagerImpl implements LifecycleManager { } } + @Override + public void onMigrationRun() { + state = MIGRATING; + eventBus.broadcast(new DatabaseMigrationEvent()); + } + @Override public void stopServices() { try { @@ -235,4 +250,8 @@ class LifecycleManagerImpl implements LifecycleManager { shutdownLatch.await(); } + @Override + public LifecycleState getLifecycleState() { + return state; + } } diff --git a/bramble-core/src/test/java/org/briarproject/bramble/db/DatabaseComponentImplTest.java b/bramble-core/src/test/java/org/briarproject/bramble/db/DatabaseComponentImplTest.java index b2e4842db..18de0d7e8 100644 --- a/bramble-core/src/test/java/org/briarproject/bramble/db/DatabaseComponentImplTest.java +++ b/bramble-core/src/test/java/org/briarproject/bramble/db/DatabaseComponentImplTest.java @@ -134,7 +134,7 @@ public class DatabaseComponentImplTest extends BrambleMockTestCase { int shutdownHandle = 12345; context.checking(new Expectations() {{ // open() - oneOf(database).open(); + oneOf(database).open(null); will(returnValue(false)); oneOf(shutdown).addShutdownHook(with(any(Runnable.class))); will(returnValue(shutdownHandle)); @@ -201,7 +201,7 @@ public class DatabaseComponentImplTest extends BrambleMockTestCase { DatabaseComponent db = createDatabaseComponent(database, eventBus, shutdown); - assertFalse(db.open()); + assertFalse(db.open(null)); Transaction transaction = db.startTransaction(false); try { db.addLocalAuthor(transaction, localAuthor); @@ -1501,7 +1501,7 @@ public class DatabaseComponentImplTest extends BrambleMockTestCase { MessageId messageId2 = new MessageId(TestUtils.getRandomId()); context.checking(new Expectations() {{ // open() - oneOf(database).open(); + oneOf(database).open(null); will(returnValue(false)); oneOf(shutdown).addShutdownHook(with(any(Runnable.class))); will(returnValue(shutdownHandle)); @@ -1543,7 +1543,7 @@ public class DatabaseComponentImplTest extends BrambleMockTestCase { DatabaseComponent db = createDatabaseComponent(database, eventBus, shutdown); - assertFalse(db.open()); + assertFalse(db.open(null)); Transaction transaction = db.startTransaction(false); try { db.addLocalMessage(transaction, message, metadata, true); diff --git a/bramble-core/src/test/java/org/briarproject/bramble/db/DatabaseMigrationTest.java b/bramble-core/src/test/java/org/briarproject/bramble/db/DatabaseMigrationTest.java index 203f4dfd2..89bdf8a4c 100644 --- a/bramble-core/src/test/java/org/briarproject/bramble/db/DatabaseMigrationTest.java +++ b/bramble-core/src/test/java/org/briarproject/bramble/db/DatabaseMigrationTest.java @@ -62,7 +62,7 @@ public abstract class DatabaseMigrationTest extends BrambleMockTestCase { public void testDoesNotRunMigrationsWhenCreatingDatabase() throws Exception { Database db = createDatabase(singletonList(migration)); - assertFalse(db.open()); + assertFalse(db.open(null)); assertEquals(CODE_SCHEMA_VERSION, getDataSchemaVersion(db)); db.close(); } @@ -72,14 +72,14 @@ public abstract class DatabaseMigrationTest extends BrambleMockTestCase { throws Exception { // Open the DB for the first time Database db = createDatabase(asList(migration, migration1)); - assertFalse(db.open()); + assertFalse(db.open(null)); assertEquals(CODE_SCHEMA_VERSION, getDataSchemaVersion(db)); // Override the data schema version setDataSchemaVersion(db, -1); db.close(); // Reopen the DB - an exception should be thrown db = createDatabase(asList(migration, migration1)); - db.open(); + db.open(null); } @Test @@ -87,12 +87,12 @@ public abstract class DatabaseMigrationTest extends BrambleMockTestCase { throws Exception { // Open the DB for the first time Database db = createDatabase(asList(migration, migration1)); - assertFalse(db.open()); + assertFalse(db.open(null)); assertEquals(CODE_SCHEMA_VERSION, getDataSchemaVersion(db)); db.close(); // Reopen the DB - migrations should not be run db = createDatabase(asList(migration, migration1)); - assertTrue(db.open()); + assertTrue(db.open(null)); assertEquals(CODE_SCHEMA_VERSION, getDataSchemaVersion(db)); db.close(); } @@ -101,14 +101,14 @@ public abstract class DatabaseMigrationTest extends BrambleMockTestCase { public void testThrowsExceptionIfDataIsNewerThanCode() throws Exception { // Open the DB for the first time Database db = createDatabase(asList(migration, migration1)); - assertFalse(db.open()); + assertFalse(db.open(null)); assertEquals(CODE_SCHEMA_VERSION, getDataSchemaVersion(db)); // Override the data schema version setDataSchemaVersion(db, CODE_SCHEMA_VERSION + 1); db.close(); // Reopen the DB - an exception should be thrown db = createDatabase(asList(migration, migration1)); - db.open(); + db.open(null); } @Test(expected = DataTooOldException.class) @@ -116,13 +116,13 @@ public abstract class DatabaseMigrationTest extends BrambleMockTestCase { throws Exception { // Open the DB for the first time Database db = createDatabase(emptyList()); - assertFalse(db.open()); + assertFalse(db.open(null)); assertEquals(CODE_SCHEMA_VERSION, getDataSchemaVersion(db)); setDataSchemaVersion(db, CODE_SCHEMA_VERSION - 1); db.close(); // Reopen the DB - an exception should be thrown db = createDatabase(emptyList()); - db.open(); + db.open(null); } @Test(expected = DataTooOldException.class) @@ -141,14 +141,14 @@ public abstract class DatabaseMigrationTest extends BrambleMockTestCase { // Open the DB for the first time Database db = createDatabase(asList(migration, migration1)); - assertFalse(db.open()); + assertFalse(db.open(null)); assertEquals(CODE_SCHEMA_VERSION, getDataSchemaVersion(db)); // Override the data schema version setDataSchemaVersion(db, CODE_SCHEMA_VERSION - 3); db.close(); // Reopen the DB - an exception should be thrown db = createDatabase(asList(migration, migration1)); - db.open(); + db.open(null); } @Test @@ -170,14 +170,14 @@ public abstract class DatabaseMigrationTest extends BrambleMockTestCase { // Open the DB for the first time Database db = createDatabase(asList(migration, migration1)); - assertFalse(db.open()); + assertFalse(db.open(null)); assertEquals(CODE_SCHEMA_VERSION, getDataSchemaVersion(db)); // Override the data schema version setDataSchemaVersion(db, CODE_SCHEMA_VERSION - 2); db.close(); // Reopen the DB - the first migration should be run db = createDatabase(asList(migration, migration1)); - assertTrue(db.open()); + assertTrue(db.open(null)); assertEquals(CODE_SCHEMA_VERSION, getDataSchemaVersion(db)); db.close(); } @@ -202,14 +202,14 @@ public abstract class DatabaseMigrationTest extends BrambleMockTestCase { // Open the DB for the first time Database db = createDatabase(asList(migration, migration1)); - assertFalse(db.open()); + assertFalse(db.open(null)); assertEquals(CODE_SCHEMA_VERSION, getDataSchemaVersion(db)); // Override the data schema version setDataSchemaVersion(db, CODE_SCHEMA_VERSION - 2); db.close(); // Reopen the DB - both migrations should be run db = createDatabase(asList(migration, migration1)); - assertTrue(db.open()); + assertTrue(db.open(null)); assertEquals(CODE_SCHEMA_VERSION, getDataSchemaVersion(db)); db.close(); } diff --git a/bramble-core/src/test/java/org/briarproject/bramble/db/DatabasePerformanceComparisonTest.java b/bramble-core/src/test/java/org/briarproject/bramble/db/DatabasePerformanceComparisonTest.java index c2a124bb2..1807d30dc 100644 --- a/bramble-core/src/test/java/org/briarproject/bramble/db/DatabasePerformanceComparisonTest.java +++ b/bramble-core/src/test/java/org/briarproject/bramble/db/DatabasePerformanceComparisonTest.java @@ -71,7 +71,7 @@ public abstract class DatabasePerformanceComparisonTest throws DbException { Database db = createDatabase(conditionA, new TestDatabaseConfig(testDir, MAX_SIZE), new SystemClock()); - db.open(); + db.open(null); return db; } diff --git a/bramble-core/src/test/java/org/briarproject/bramble/db/DatabaseTraceTest.java b/bramble-core/src/test/java/org/briarproject/bramble/db/DatabaseTraceTest.java index a78fb5f55..f4e0daa19 100644 --- a/bramble-core/src/test/java/org/briarproject/bramble/db/DatabaseTraceTest.java +++ b/bramble-core/src/test/java/org/briarproject/bramble/db/DatabaseTraceTest.java @@ -43,7 +43,7 @@ public abstract class DatabaseTraceTest extends DatabasePerformanceTest { private Database openDatabase() throws DbException { Database db = createDatabase( new TestDatabaseConfig(testDir, MAX_SIZE), new SystemClock()); - db.open(); + db.open(null); return db; } diff --git a/bramble-core/src/test/java/org/briarproject/bramble/db/JdbcDatabaseTest.java b/bramble-core/src/test/java/org/briarproject/bramble/db/JdbcDatabaseTest.java index 32d4e5faa..81d1c9025 100644 --- a/bramble-core/src/test/java/org/briarproject/bramble/db/JdbcDatabaseTest.java +++ b/bramble-core/src/test/java/org/briarproject/bramble/db/JdbcDatabaseTest.java @@ -1700,7 +1700,7 @@ public abstract class JdbcDatabaseTest extends BrambleTestCase { Database db = createDatabase( new TestDatabaseConfig(testDir, MAX_SIZE), clock); if (!resume) TestUtils.deleteTestDirectory(testDir); - db.open(); + db.open(null); return db; } diff --git a/bramble-core/src/test/java/org/briarproject/bramble/db/SingleDatabasePerformanceTest.java b/bramble-core/src/test/java/org/briarproject/bramble/db/SingleDatabasePerformanceTest.java index 5a8364767..670c7cddb 100644 --- a/bramble-core/src/test/java/org/briarproject/bramble/db/SingleDatabasePerformanceTest.java +++ b/bramble-core/src/test/java/org/briarproject/bramble/db/SingleDatabasePerformanceTest.java @@ -40,7 +40,7 @@ public abstract class SingleDatabasePerformanceTest private Database openDatabase() throws DbException { Database db = createDatabase( new TestDatabaseConfig(testDir, MAX_SIZE), new SystemClock()); - db.open(); + db.open(null); return db; } diff --git a/bramble-core/src/test/java/org/briarproject/bramble/test/TestLifecycleModule.java b/bramble-core/src/test/java/org/briarproject/bramble/test/TestLifecycleModule.java index ee8d5115e..15943adc2 100644 --- a/bramble-core/src/test/java/org/briarproject/bramble/test/TestLifecycleModule.java +++ b/bramble-core/src/test/java/org/briarproject/bramble/test/TestLifecycleModule.java @@ -17,6 +17,8 @@ import javax.inject.Singleton; import dagger.Module; import dagger.Provides; +import static org.briarproject.bramble.api.lifecycle.LifecycleManager.LifecycleState.RUNNING; + @Module public class TestLifecycleModule { @@ -57,6 +59,11 @@ public class TestLifecycleModule { @Override public void waitForShutdown() throws InterruptedException { } + + @Override + public LifecycleState getLifecycleState() { + return RUNNING; + } }; return lifecycleManager; } diff --git a/briar-android/src/main/AndroidManifest.xml b/briar-android/src/main/AndroidManifest.xml index a2fed381f..102de1290 100644 --- a/briar-android/src/main/AndroidManifest.xml +++ b/briar-android/src/main/AndroidManifest.xml @@ -77,6 +77,11 @@ + + = 26) { NotificationManager nm = (NotificationManager) diff --git a/briar-android/src/main/java/org/briarproject/briar/android/activity/ActivityComponent.java b/briar-android/src/main/java/org/briarproject/briar/android/activity/ActivityComponent.java index 7403d01e0..2f8ca83fa 100644 --- a/briar-android/src/main/java/org/briarproject/briar/android/activity/ActivityComponent.java +++ b/briar-android/src/main/java/org/briarproject/briar/android/activity/ActivityComponent.java @@ -32,6 +32,7 @@ import org.briarproject.briar.android.keyagreement.ShowQrCodeFragment; import org.briarproject.briar.android.login.AuthorNameFragment; import org.briarproject.briar.android.login.ChangePasswordActivity; import org.briarproject.briar.android.login.DozeFragment; +import org.briarproject.briar.android.login.OpenDatabaseActivity; import org.briarproject.briar.android.login.PasswordActivity; import org.briarproject.briar.android.login.PasswordFragment; import org.briarproject.briar.android.login.SetupActivity; @@ -88,6 +89,8 @@ public interface ActivityComponent { void inject(SetupActivity activity); + void inject(OpenDatabaseActivity activity); + void inject(NavDrawerActivity activity); void inject(PasswordActivity activity); diff --git a/briar-android/src/main/java/org/briarproject/briar/android/login/OpenDatabaseActivity.java b/briar-android/src/main/java/org/briarproject/briar/android/login/OpenDatabaseActivity.java new file mode 100644 index 000000000..f197f13ec --- /dev/null +++ b/briar-android/src/main/java/org/briarproject/briar/android/login/OpenDatabaseActivity.java @@ -0,0 +1,90 @@ +package org.briarproject.briar.android.login; + +import android.os.Bundle; +import android.support.annotation.Nullable; +import android.widget.ImageView; +import android.widget.TextView; + +import org.briarproject.bramble.api.db.DatabaseMigrationEvent; +import org.briarproject.bramble.api.event.Event; +import org.briarproject.bramble.api.event.EventBus; +import org.briarproject.bramble.api.event.EventListener; +import org.briarproject.bramble.api.lifecycle.LifecycleManager; +import org.briarproject.bramble.api.lifecycle.event.StartupEvent; +import org.briarproject.briar.R; +import org.briarproject.briar.android.activity.ActivityComponent; +import org.briarproject.briar.android.activity.BaseActivity; + +import javax.annotation.ParametersAreNonnullByDefault; +import javax.inject.Inject; + +import static org.briarproject.bramble.api.lifecycle.LifecycleManager.LifecycleState.MIGRATING; +import static org.briarproject.bramble.api.lifecycle.LifecycleManager.LifecycleState.RUNNING; + +@ParametersAreNonnullByDefault +public class OpenDatabaseActivity extends BaseActivity + implements EventListener { + + @Inject + LifecycleManager lifecycleManager; + @Inject + EventBus eventBus; + + private TextView textView; + private ImageView imageView; + private boolean showingMigration = false; + + @Override + public void onCreate(@Nullable Bundle state) { + super.onCreate(state); + setContentView(R.layout.activity_open_database); + textView = findViewById(R.id.textView); + imageView = findViewById(R.id.imageView); + } + + @Override + public void injectActivity(ActivityComponent component) { + component.inject(this); + } + + @Override + public void onBackPressed() { + // do not let the user bail out of here + } + + @Override + protected void onStart() { + super.onStart(); + if (lifecycleManager.getLifecycleState() == RUNNING) { + supportFinishAfterTransition(); + } else { + if (lifecycleManager.getLifecycleState() == MIGRATING) { + showMigration(); + } + eventBus.addListener(this); + } + } + + @Override + protected void onStop() { + super.onStop(); + eventBus.removeListener(this); + } + + @Override + public void eventOccurred(Event e) { + if (e instanceof StartupEvent) { + runOnUiThreadUnlessDestroyed(this::supportFinishAfterTransition); + } else if (e instanceof DatabaseMigrationEvent) { + runOnUiThreadUnlessDestroyed(this::showMigration); + } + } + + private void showMigration() { + if (showingMigration) return; + textView.setText(R.string.startup_migrate_database); + imageView.setImageResource(R.drawable.startup_migration); + showingMigration = true; + } + +} diff --git a/briar-android/src/main/res/drawable/startup_lock.xml b/briar-android/src/main/res/drawable/startup_lock.xml new file mode 100644 index 000000000..181a64cc9 --- /dev/null +++ b/briar-android/src/main/res/drawable/startup_lock.xml @@ -0,0 +1,9 @@ + + + diff --git a/briar-android/src/main/res/drawable/startup_migration.xml b/briar-android/src/main/res/drawable/startup_migration.xml new file mode 100644 index 000000000..a5021ef0d --- /dev/null +++ b/briar-android/src/main/res/drawable/startup_migration.xml @@ -0,0 +1,9 @@ + + + diff --git a/briar-android/src/main/res/layout/activity_open_database.xml b/briar-android/src/main/res/layout/activity_open_database.xml new file mode 100644 index 000000000..ab20f17cb --- /dev/null +++ b/briar-android/src/main/res/layout/activity_open_database.xml @@ -0,0 +1,46 @@ + + + + + + + + + + \ No newline at end of file diff --git a/briar-android/src/main/res/values/strings.xml b/briar-android/src/main/res/values/strings.xml index c682069f7..14de9071b 100644 --- a/briar-android/src/main/res/values/strings.xml +++ b/briar-android/src/main/res/values/strings.xml @@ -46,6 +46,8 @@ The testing expiry date has been extended. Your account will now expire in %d days. This software has expired.\nThank you for testing! + Decrypting Database… + Upgrading Database… Open the navigation drawer From db7dbfce6820ed094527ba54dd9839f984e155a7 Mon Sep 17 00:00:00 2001 From: Torsten Grote Date: Wed, 28 Feb 2018 13:23:01 -0300 Subject: [PATCH 3/4] Start NavDrawerActivity only after database was opened and services started --- .../briar/android/BriarService.java | 6 ----- .../android/login/OpenDatabaseActivity.java | 22 ++++++++++--------- .../briar/android/login/SetupActivity.java | 3 +-- .../android/splash/SplashScreenActivity.java | 6 ++--- 4 files changed, 16 insertions(+), 21 deletions(-) diff --git a/briar-android/src/main/java/org/briarproject/briar/android/BriarService.java b/briar-android/src/main/java/org/briarproject/briar/android/BriarService.java index 2c618cf92..8e1abd66a 100644 --- a/briar-android/src/main/java/org/briarproject/briar/android/BriarService.java +++ b/briar-android/src/main/java/org/briarproject/briar/android/BriarService.java @@ -17,7 +17,6 @@ import org.briarproject.bramble.api.lifecycle.LifecycleManager; import org.briarproject.bramble.api.lifecycle.LifecycleManager.StartResult; import org.briarproject.bramble.api.system.AndroidExecutor; import org.briarproject.briar.R; -import org.briarproject.briar.android.login.OpenDatabaseActivity; import org.briarproject.briar.android.navdrawer.NavDrawerActivity; import java.util.concurrent.CountDownLatch; @@ -90,11 +89,6 @@ public class BriarService extends Service { return; } - Intent intent = - new Intent(getApplicationContext(), OpenDatabaseActivity.class); - intent.setFlags(FLAG_ACTIVITY_NEW_TASK); - startActivity(intent); - // Create notification channels if (SDK_INT >= 26) { NotificationManager nm = (NotificationManager) diff --git a/briar-android/src/main/java/org/briarproject/briar/android/login/OpenDatabaseActivity.java b/briar-android/src/main/java/org/briarproject/briar/android/login/OpenDatabaseActivity.java index f197f13ec..16c49847c 100644 --- a/briar-android/src/main/java/org/briarproject/briar/android/login/OpenDatabaseActivity.java +++ b/briar-android/src/main/java/org/briarproject/briar/android/login/OpenDatabaseActivity.java @@ -1,5 +1,6 @@ package org.briarproject.briar.android.login; +import android.content.Intent; import android.os.Bundle; import android.support.annotation.Nullable; import android.widget.ImageView; @@ -13,7 +14,8 @@ import org.briarproject.bramble.api.lifecycle.LifecycleManager; import org.briarproject.bramble.api.lifecycle.event.StartupEvent; import org.briarproject.briar.R; import org.briarproject.briar.android.activity.ActivityComponent; -import org.briarproject.briar.android.activity.BaseActivity; +import org.briarproject.briar.android.activity.BriarActivity; +import org.briarproject.briar.android.navdrawer.NavDrawerActivity; import javax.annotation.ParametersAreNonnullByDefault; import javax.inject.Inject; @@ -22,7 +24,7 @@ import static org.briarproject.bramble.api.lifecycle.LifecycleManager.LifecycleS import static org.briarproject.bramble.api.lifecycle.LifecycleManager.LifecycleState.RUNNING; @ParametersAreNonnullByDefault -public class OpenDatabaseActivity extends BaseActivity +public class OpenDatabaseActivity extends BriarActivity implements EventListener { @Inject @@ -48,15 +50,10 @@ public class OpenDatabaseActivity extends BaseActivity } @Override - public void onBackPressed() { - // do not let the user bail out of here - } - - @Override - protected void onStart() { + public void onStart() { super.onStart(); if (lifecycleManager.getLifecycleState() == RUNNING) { - supportFinishAfterTransition(); + finishAndStartApp(); } else { if (lifecycleManager.getLifecycleState() == MIGRATING) { showMigration(); @@ -74,7 +71,7 @@ public class OpenDatabaseActivity extends BaseActivity @Override public void eventOccurred(Event e) { if (e instanceof StartupEvent) { - runOnUiThreadUnlessDestroyed(this::supportFinishAfterTransition); + runOnUiThreadUnlessDestroyed(this::finishAndStartApp); } else if (e instanceof DatabaseMigrationEvent) { runOnUiThreadUnlessDestroyed(this::showMigration); } @@ -87,4 +84,9 @@ public class OpenDatabaseActivity extends BaseActivity showingMigration = true; } + private void finishAndStartApp() { + startActivity(new Intent(this, NavDrawerActivity.class)); + supportFinishAfterTransition(); + } + } diff --git a/briar-android/src/main/java/org/briarproject/briar/android/login/SetupActivity.java b/briar-android/src/main/java/org/briarproject/briar/android/login/SetupActivity.java index 17c6f522f..2b17df6ea 100644 --- a/briar-android/src/main/java/org/briarproject/briar/android/login/SetupActivity.java +++ b/briar-android/src/main/java/org/briarproject/briar/android/login/SetupActivity.java @@ -8,7 +8,6 @@ import org.briarproject.briar.R; import org.briarproject.briar.android.activity.ActivityComponent; import org.briarproject.briar.android.activity.BaseActivity; import org.briarproject.briar.android.fragment.BaseFragment.BaseFragmentListener; -import org.briarproject.briar.android.navdrawer.NavDrawerActivity; import javax.inject.Inject; @@ -48,7 +47,7 @@ public class SetupActivity extends BaseActivity } public void showApp() { - Intent i = new Intent(this, NavDrawerActivity.class); + Intent i = new Intent(this, OpenDatabaseActivity.class); i.setFlags(FLAG_ACTIVITY_NEW_TASK); startActivity(i); supportFinishAfterTransition(); diff --git a/briar-android/src/main/java/org/briarproject/briar/android/splash/SplashScreenActivity.java b/briar-android/src/main/java/org/briarproject/briar/android/splash/SplashScreenActivity.java index 9c4535313..f21f460aa 100644 --- a/briar-android/src/main/java/org/briarproject/briar/android/splash/SplashScreenActivity.java +++ b/briar-android/src/main/java/org/briarproject/briar/android/splash/SplashScreenActivity.java @@ -12,8 +12,8 @@ import org.briarproject.briar.R; import org.briarproject.briar.android.activity.ActivityComponent; import org.briarproject.briar.android.activity.BaseActivity; import org.briarproject.briar.android.controller.ConfigController; +import org.briarproject.briar.android.login.OpenDatabaseActivity; import org.briarproject.briar.android.login.SetupActivity; -import org.briarproject.briar.android.navdrawer.NavDrawerActivity; import java.util.logging.Logger; @@ -44,7 +44,7 @@ public class SplashScreenActivity extends BaseActivity { setContentView(R.layout.splash); if (configController.accountSignedIn()) { - startActivity(new Intent(this, NavDrawerActivity.class)); + startActivity(new Intent(this, OpenDatabaseActivity.class)); finish(); } else { new Handler().postDelayed(() -> { @@ -65,7 +65,7 @@ public class SplashScreenActivity extends BaseActivity { startActivity(new Intent(this, ExpiredActivity.class)); } else { if (configController.accountExists()) { - startActivity(new Intent(this, NavDrawerActivity.class)); + startActivity(new Intent(this, OpenDatabaseActivity.class)); } else { configController.deleteAccount(this); startActivity(new Intent(this, SetupActivity.class)); From 9a4f0b8e8939845c46759db1fe7e12cb204471b0 Mon Sep 17 00:00:00 2001 From: akwizgran Date: Thu, 1 Mar 2018 14:29:35 +0000 Subject: [PATCH 4/4] Add more lifecycle states, merge lifecycle events. --- .../api/db/DatabaseMigrationEvent.java | 9 ------- .../api/lifecycle/LifecycleManager.java | 7 +++++- .../api/lifecycle/event/LifecycleEvent.java | 20 +++++++++++++++ .../api/lifecycle/event/ShutdownEvent.java | 9 ------- .../api/lifecycle/event/StartupEvent.java | 10 -------- .../lifecycle/LifecycleManagerImpl.java | 24 +++++++++++------- .../bramble/sync/DuplexOutgoingSession.java | 8 +++--- .../bramble/sync/IncomingSession.java | 8 +++--- .../bramble/sync/SimplexOutgoingSession.java | 8 +++--- .../android/login/OpenDatabaseActivity.java | 25 ++++++++++--------- 10 files changed, 69 insertions(+), 59 deletions(-) delete mode 100644 bramble-api/src/main/java/org/briarproject/bramble/api/db/DatabaseMigrationEvent.java create mode 100644 bramble-api/src/main/java/org/briarproject/bramble/api/lifecycle/event/LifecycleEvent.java delete mode 100644 bramble-api/src/main/java/org/briarproject/bramble/api/lifecycle/event/ShutdownEvent.java delete mode 100644 bramble-api/src/main/java/org/briarproject/bramble/api/lifecycle/event/StartupEvent.java diff --git a/bramble-api/src/main/java/org/briarproject/bramble/api/db/DatabaseMigrationEvent.java b/bramble-api/src/main/java/org/briarproject/bramble/api/db/DatabaseMigrationEvent.java deleted file mode 100644 index 7edd81fa0..000000000 --- a/bramble-api/src/main/java/org/briarproject/bramble/api/db/DatabaseMigrationEvent.java +++ /dev/null @@ -1,9 +0,0 @@ -package org.briarproject.bramble.api.db; - -import org.briarproject.bramble.api.event.Event; - -/** - * An event that is broadcast before database migrations are being applied. - */ -public class DatabaseMigrationEvent extends Event { -} diff --git a/bramble-api/src/main/java/org/briarproject/bramble/api/lifecycle/LifecycleManager.java b/bramble-api/src/main/java/org/briarproject/bramble/api/lifecycle/LifecycleManager.java index 95b4ac08c..5a036a3b6 100644 --- a/bramble-api/src/main/java/org/briarproject/bramble/api/lifecycle/LifecycleManager.java +++ b/bramble-api/src/main/java/org/briarproject/bramble/api/lifecycle/LifecycleManager.java @@ -34,7 +34,12 @@ public interface LifecycleManager { * Returned by {@link #getLifecycleState()} */ enum LifecycleState { - STARTING, MIGRATING, RUNNING + + STARTING, MIGRATING_DATABASE, STARTING_SERVICES, RUNNING, STOPPING; + + public boolean isAfter(LifecycleState state) { + return ordinal() > state.ordinal(); + } } /** diff --git a/bramble-api/src/main/java/org/briarproject/bramble/api/lifecycle/event/LifecycleEvent.java b/bramble-api/src/main/java/org/briarproject/bramble/api/lifecycle/event/LifecycleEvent.java new file mode 100644 index 000000000..4e6370bcf --- /dev/null +++ b/bramble-api/src/main/java/org/briarproject/bramble/api/lifecycle/event/LifecycleEvent.java @@ -0,0 +1,20 @@ +package org.briarproject.bramble.api.lifecycle.event; + +import org.briarproject.bramble.api.event.Event; +import org.briarproject.bramble.api.lifecycle.LifecycleManager.LifecycleState; + +/** + * An event that is broadcast when the app enters a new lifecycle state. + */ +public class LifecycleEvent extends Event { + + private final LifecycleState state; + + public LifecycleEvent(LifecycleState state) { + this.state = state; + } + + public LifecycleState getLifecycleState() { + return state; + } +} diff --git a/bramble-api/src/main/java/org/briarproject/bramble/api/lifecycle/event/ShutdownEvent.java b/bramble-api/src/main/java/org/briarproject/bramble/api/lifecycle/event/ShutdownEvent.java deleted file mode 100644 index ba0c4d37f..000000000 --- a/bramble-api/src/main/java/org/briarproject/bramble/api/lifecycle/event/ShutdownEvent.java +++ /dev/null @@ -1,9 +0,0 @@ -package org.briarproject.bramble.api.lifecycle.event; - -import org.briarproject.bramble.api.event.Event; - -/** - * An event that is broadcast when the app is shutting down. - */ -public class ShutdownEvent extends Event { -} diff --git a/bramble-api/src/main/java/org/briarproject/bramble/api/lifecycle/event/StartupEvent.java b/bramble-api/src/main/java/org/briarproject/bramble/api/lifecycle/event/StartupEvent.java deleted file mode 100644 index 973bd1c47..000000000 --- a/bramble-api/src/main/java/org/briarproject/bramble/api/lifecycle/event/StartupEvent.java +++ /dev/null @@ -1,10 +0,0 @@ -package org.briarproject.bramble.api.lifecycle.event; - -import org.briarproject.bramble.api.event.Event; - -/** - * An event that is broadcast when the app is starting. - * This happens after the database was opened and services were started. - */ -public class StartupEvent extends Event { -} diff --git a/bramble-core/src/main/java/org/briarproject/bramble/lifecycle/LifecycleManagerImpl.java b/bramble-core/src/main/java/org/briarproject/bramble/lifecycle/LifecycleManagerImpl.java index 6e55a8df5..0f41cbf21 100644 --- a/bramble-core/src/main/java/org/briarproject/bramble/lifecycle/LifecycleManagerImpl.java +++ b/bramble-core/src/main/java/org/briarproject/bramble/lifecycle/LifecycleManagerImpl.java @@ -5,7 +5,6 @@ import org.briarproject.bramble.api.crypto.KeyPair; import org.briarproject.bramble.api.db.DataTooNewException; import org.briarproject.bramble.api.db.DataTooOldException; import org.briarproject.bramble.api.db.DatabaseComponent; -import org.briarproject.bramble.api.db.DatabaseMigrationEvent; import org.briarproject.bramble.api.db.DbException; import org.briarproject.bramble.api.db.MigrationListener; import org.briarproject.bramble.api.db.Transaction; @@ -16,8 +15,7 @@ import org.briarproject.bramble.api.identity.LocalAuthor; import org.briarproject.bramble.api.lifecycle.LifecycleManager; import org.briarproject.bramble.api.lifecycle.Service; import org.briarproject.bramble.api.lifecycle.ServiceException; -import org.briarproject.bramble.api.lifecycle.event.ShutdownEvent; -import org.briarproject.bramble.api.lifecycle.event.StartupEvent; +import org.briarproject.bramble.api.lifecycle.event.LifecycleEvent; import org.briarproject.bramble.api.nullsafety.NotNullByDefault; import org.briarproject.bramble.api.sync.Client; @@ -34,9 +32,11 @@ import javax.inject.Inject; import static java.util.logging.Level.INFO; import static java.util.logging.Level.WARNING; -import static org.briarproject.bramble.api.lifecycle.LifecycleManager.LifecycleState.MIGRATING; +import static org.briarproject.bramble.api.lifecycle.LifecycleManager.LifecycleState.MIGRATING_DATABASE; import static org.briarproject.bramble.api.lifecycle.LifecycleManager.LifecycleState.RUNNING; import static org.briarproject.bramble.api.lifecycle.LifecycleManager.LifecycleState.STARTING; +import static org.briarproject.bramble.api.lifecycle.LifecycleManager.LifecycleState.STARTING_SERVICES; +import static org.briarproject.bramble.api.lifecycle.LifecycleManager.LifecycleState.STOPPING; import static org.briarproject.bramble.api.lifecycle.LifecycleManager.StartResult.ALREADY_RUNNING; import static org.briarproject.bramble.api.lifecycle.LifecycleManager.StartResult.DATA_TOO_NEW_ERROR; import static org.briarproject.bramble.api.lifecycle.LifecycleManager.StartResult.DATA_TOO_OLD_ERROR; @@ -63,6 +63,7 @@ class LifecycleManagerImpl implements LifecycleManager, MigrationListener { private final CountDownLatch dbLatch = new CountDownLatch(1); private final CountDownLatch startupLatch = new CountDownLatch(1); private final CountDownLatch shutdownLatch = new CountDownLatch(1); + private volatile LifecycleState state = STARTING; @Inject @@ -142,7 +143,10 @@ class LifecycleManagerImpl implements LifecycleManager, MigrationListener { registerLocalAuthor(createLocalAuthor(nickname)); } + state = STARTING_SERVICES; dbLatch.countDown(); + eventBus.broadcast(new LifecycleEvent(STARTING_SERVICES)); + Transaction txn = db.startTransaction(false); try { for (Client c : clients) { @@ -168,9 +172,10 @@ class LifecycleManagerImpl implements LifecycleManager, MigrationListener { + " took " + duration + " ms"); } } - startupLatch.countDown(); + state = RUNNING; - eventBus.broadcast(new StartupEvent()); + startupLatch.countDown(); + eventBus.broadcast(new LifecycleEvent(RUNNING)); return SUCCESS; } catch (DataTooOldException e) { if (LOG.isLoggable(WARNING)) LOG.log(WARNING, e.toString(), e); @@ -191,8 +196,8 @@ class LifecycleManagerImpl implements LifecycleManager, MigrationListener { @Override public void onMigrationRun() { - state = MIGRATING; - eventBus.broadcast(new DatabaseMigrationEvent()); + state = MIGRATING_DATABASE; + eventBus.broadcast(new LifecycleEvent(MIGRATING_DATABASE)); } @Override @@ -205,7 +210,8 @@ class LifecycleManagerImpl implements LifecycleManager, MigrationListener { } try { LOG.info("Stopping services"); - eventBus.broadcast(new ShutdownEvent()); + state = STOPPING; + eventBus.broadcast(new LifecycleEvent(STOPPING)); for (Service s : services) { long start = System.currentTimeMillis(); s.stopService(); diff --git a/bramble-core/src/main/java/org/briarproject/bramble/sync/DuplexOutgoingSession.java b/bramble-core/src/main/java/org/briarproject/bramble/sync/DuplexOutgoingSession.java index 3fdabc01d..80f699a1f 100644 --- a/bramble-core/src/main/java/org/briarproject/bramble/sync/DuplexOutgoingSession.java +++ b/bramble-core/src/main/java/org/briarproject/bramble/sync/DuplexOutgoingSession.java @@ -10,7 +10,7 @@ import org.briarproject.bramble.api.event.Event; import org.briarproject.bramble.api.event.EventBus; import org.briarproject.bramble.api.event.EventListener; import org.briarproject.bramble.api.lifecycle.IoExecutor; -import org.briarproject.bramble.api.lifecycle.event.ShutdownEvent; +import org.briarproject.bramble.api.lifecycle.event.LifecycleEvent; import org.briarproject.bramble.api.nullsafety.NotNullByDefault; import org.briarproject.bramble.api.sync.Ack; import org.briarproject.bramble.api.sync.Offer; @@ -38,6 +38,7 @@ import javax.annotation.concurrent.ThreadSafe; import static java.util.concurrent.TimeUnit.MILLISECONDS; import static java.util.logging.Level.INFO; import static java.util.logging.Level.WARNING; +import static org.briarproject.bramble.api.lifecycle.LifecycleManager.LifecycleState.STOPPING; import static org.briarproject.bramble.api.sync.SyncConstants.MAX_MESSAGE_IDS; import static org.briarproject.bramble.api.sync.SyncConstants.MAX_RECORD_PAYLOAD_LENGTH; @@ -209,8 +210,9 @@ class DuplexOutgoingSession implements SyncSession, EventListener { } else if (e instanceof MessageToRequestEvent) { if (((MessageToRequestEvent) e).getContactId().equals(contactId)) generateRequest(); - } else if (e instanceof ShutdownEvent) { - interrupt(); + } else if (e instanceof LifecycleEvent) { + LifecycleEvent l = (LifecycleEvent) e; + if (l.getLifecycleState() == STOPPING) interrupt(); } } diff --git a/bramble-core/src/main/java/org/briarproject/bramble/sync/IncomingSession.java b/bramble-core/src/main/java/org/briarproject/bramble/sync/IncomingSession.java index 249d1f2c6..32eb58df4 100644 --- a/bramble-core/src/main/java/org/briarproject/bramble/sync/IncomingSession.java +++ b/bramble-core/src/main/java/org/briarproject/bramble/sync/IncomingSession.java @@ -11,7 +11,7 @@ import org.briarproject.bramble.api.event.Event; import org.briarproject.bramble.api.event.EventBus; import org.briarproject.bramble.api.event.EventListener; import org.briarproject.bramble.api.lifecycle.IoExecutor; -import org.briarproject.bramble.api.lifecycle.event.ShutdownEvent; +import org.briarproject.bramble.api.lifecycle.event.LifecycleEvent; import org.briarproject.bramble.api.nullsafety.NotNullByDefault; import org.briarproject.bramble.api.sync.Ack; import org.briarproject.bramble.api.sync.Message; @@ -27,6 +27,7 @@ import java.util.logging.Logger; import javax.annotation.concurrent.ThreadSafe; import static java.util.logging.Level.WARNING; +import static org.briarproject.bramble.api.lifecycle.LifecycleManager.LifecycleState.STOPPING; /** * An incoming {@link SyncSession}. @@ -96,8 +97,9 @@ class IncomingSession implements SyncSession, EventListener { if (e instanceof ContactRemovedEvent) { ContactRemovedEvent c = (ContactRemovedEvent) e; if (c.getContactId().equals(contactId)) interrupt(); - } else if (e instanceof ShutdownEvent) { - interrupt(); + } else if (e instanceof LifecycleEvent) { + LifecycleEvent l = (LifecycleEvent) e; + if (l.getLifecycleState() == STOPPING) interrupt(); } } diff --git a/bramble-core/src/main/java/org/briarproject/bramble/sync/SimplexOutgoingSession.java b/bramble-core/src/main/java/org/briarproject/bramble/sync/SimplexOutgoingSession.java index 3d0ecae22..b1f8198f8 100644 --- a/bramble-core/src/main/java/org/briarproject/bramble/sync/SimplexOutgoingSession.java +++ b/bramble-core/src/main/java/org/briarproject/bramble/sync/SimplexOutgoingSession.java @@ -10,7 +10,7 @@ import org.briarproject.bramble.api.event.Event; import org.briarproject.bramble.api.event.EventBus; import org.briarproject.bramble.api.event.EventListener; import org.briarproject.bramble.api.lifecycle.IoExecutor; -import org.briarproject.bramble.api.lifecycle.event.ShutdownEvent; +import org.briarproject.bramble.api.lifecycle.event.LifecycleEvent; import org.briarproject.bramble.api.nullsafety.NotNullByDefault; import org.briarproject.bramble.api.sync.Ack; import org.briarproject.bramble.api.sync.RecordWriter; @@ -28,6 +28,7 @@ import javax.annotation.concurrent.ThreadSafe; import static java.util.logging.Level.INFO; import static java.util.logging.Level.WARNING; +import static org.briarproject.bramble.api.lifecycle.LifecycleManager.LifecycleState.STOPPING; import static org.briarproject.bramble.api.sync.SyncConstants.MAX_MESSAGE_IDS; import static org.briarproject.bramble.api.sync.SyncConstants.MAX_RECORD_PAYLOAD_LENGTH; @@ -109,8 +110,9 @@ class SimplexOutgoingSession implements SyncSession, EventListener { if (e instanceof ContactRemovedEvent) { ContactRemovedEvent c = (ContactRemovedEvent) e; if (c.getContactId().equals(contactId)) interrupt(); - } else if (e instanceof ShutdownEvent) { - interrupt(); + } else if (e instanceof LifecycleEvent) { + LifecycleEvent l = (LifecycleEvent) e; + if (l.getLifecycleState() == STOPPING) interrupt(); } } diff --git a/briar-android/src/main/java/org/briarproject/briar/android/login/OpenDatabaseActivity.java b/briar-android/src/main/java/org/briarproject/briar/android/login/OpenDatabaseActivity.java index 16c49847c..d24196d32 100644 --- a/briar-android/src/main/java/org/briarproject/briar/android/login/OpenDatabaseActivity.java +++ b/briar-android/src/main/java/org/briarproject/briar/android/login/OpenDatabaseActivity.java @@ -6,12 +6,12 @@ import android.support.annotation.Nullable; import android.widget.ImageView; import android.widget.TextView; -import org.briarproject.bramble.api.db.DatabaseMigrationEvent; import org.briarproject.bramble.api.event.Event; import org.briarproject.bramble.api.event.EventBus; import org.briarproject.bramble.api.event.EventListener; import org.briarproject.bramble.api.lifecycle.LifecycleManager; -import org.briarproject.bramble.api.lifecycle.event.StartupEvent; +import org.briarproject.bramble.api.lifecycle.LifecycleManager.LifecycleState; +import org.briarproject.bramble.api.lifecycle.event.LifecycleEvent; import org.briarproject.briar.R; import org.briarproject.briar.android.activity.ActivityComponent; import org.briarproject.briar.android.activity.BriarActivity; @@ -20,8 +20,8 @@ import org.briarproject.briar.android.navdrawer.NavDrawerActivity; import javax.annotation.ParametersAreNonnullByDefault; import javax.inject.Inject; -import static org.briarproject.bramble.api.lifecycle.LifecycleManager.LifecycleState.MIGRATING; -import static org.briarproject.bramble.api.lifecycle.LifecycleManager.LifecycleState.RUNNING; +import static org.briarproject.bramble.api.lifecycle.LifecycleManager.LifecycleState.MIGRATING_DATABASE; +import static org.briarproject.bramble.api.lifecycle.LifecycleManager.LifecycleState.STARTING_SERVICES; @ParametersAreNonnullByDefault public class OpenDatabaseActivity extends BriarActivity @@ -52,12 +52,11 @@ public class OpenDatabaseActivity extends BriarActivity @Override public void onStart() { super.onStart(); - if (lifecycleManager.getLifecycleState() == RUNNING) { + LifecycleState state = lifecycleManager.getLifecycleState(); + if (state.isAfter(STARTING_SERVICES)) { finishAndStartApp(); } else { - if (lifecycleManager.getLifecycleState() == MIGRATING) { - showMigration(); - } + if (state == MIGRATING_DATABASE) showMigration(); eventBus.addListener(this); } } @@ -70,10 +69,12 @@ public class OpenDatabaseActivity extends BriarActivity @Override public void eventOccurred(Event e) { - if (e instanceof StartupEvent) { - runOnUiThreadUnlessDestroyed(this::finishAndStartApp); - } else if (e instanceof DatabaseMigrationEvent) { - runOnUiThreadUnlessDestroyed(this::showMigration); + if (e instanceof LifecycleEvent) { + LifecycleState state = ((LifecycleEvent) e).getLifecycleState(); + if (state.isAfter(STARTING_SERVICES)) + runOnUiThreadUnlessDestroyed(this::finishAndStartApp); + else if (state == MIGRATING_DATABASE) + runOnUiThreadUnlessDestroyed(this::showMigration); } }