diff --git a/briar-android/src/org/briarproject/android/BaseActivity.java b/briar-android/src/org/briarproject/android/BaseActivity.java index fa3671b5013b9fe29f2823d09719d0a578ec88bf..a144adb9e7e969d9b12b55acdf2cc8177fbb4d2b 100644 --- a/briar-android/src/org/briarproject/android/BaseActivity.java +++ b/briar-android/src/org/briarproject/android/BaseActivity.java @@ -12,7 +12,6 @@ import java.util.ArrayList; import java.util.List; import static android.view.WindowManager.LayoutParams.FLAG_SECURE; -import static android.view.inputmethod.InputMethodManager.SHOW_FORCED; import static android.view.inputmethod.InputMethodManager.SHOW_IMPLICIT; import static org.briarproject.android.TestingConstants.PREVENT_SCREENSHOTS; @@ -62,18 +61,18 @@ public abstract class BaseActivity extends AppCompatActivity } @Override - protected void onResume() { - super.onResume(); + protected void onStart() { + super.onStart(); for (ActivityLifecycleController alc : lifecycleControllers) { - alc.onActivityResume(); + alc.onActivityStart(); } } @Override - protected void onPause() { - super.onPause(); + protected void onStop() { + super.onStop(); for (ActivityLifecycleController alc : lifecycleControllers) { - alc.onActivityPause(); + alc.onActivityStop(); } } diff --git a/briar-android/src/org/briarproject/android/BriarActivity.java b/briar-android/src/org/briarproject/android/BriarActivity.java index 4c01808af7cba45255b7d091657471145c1d3112..c0bda36a8a722b6526e075fa7bf73ea2526f1544 100644 --- a/briar-android/src/org/briarproject/android/BriarActivity.java +++ b/briar-android/src/org/briarproject/android/BriarActivity.java @@ -34,10 +34,11 @@ public abstract class BriarActivity extends BaseActivity { Logger.getLogger(BriarActivity.class.getName()); @Inject - protected BriarController briarController; - // TODO remove this when the deprecated method runOnDbThread is removed + BriarController briarController; + + @Deprecated @Inject - protected DbController dbController; + DbController dbController; @Override protected void onActivityResult(int request, int result, Intent data) { @@ -49,8 +50,8 @@ public abstract class BriarActivity extends BaseActivity { } @Override - public void onResume() { - super.onResume(); + public void onStart() { + super.onStart(); if (!briarController.hasEncryptionKey() && !isFinishing()) { Intent i = new Intent(this, PasswordActivity.class); i.setFlags(FLAG_ACTIVITY_NO_ANIMATION | FLAG_ACTIVITY_SINGLE_TOP); diff --git a/briar-android/src/org/briarproject/android/NavDrawerActivity.java b/briar-android/src/org/briarproject/android/NavDrawerActivity.java index 751700559ebc95d966a558eb0e4ad39458d51fea..5d69216a75ed1eafb08890864033c8b93587a399 100644 --- a/briar-android/src/org/briarproject/android/NavDrawerActivity.java +++ b/briar-android/src/org/briarproject/android/NavDrawerActivity.java @@ -141,8 +141,8 @@ public class NavDrawerActivity extends BriarFragmentActivity implements } @Override - public void onResume() { - super.onResume(); + public void onStart() { + super.onStart(); updateTransports(); } diff --git a/briar-android/src/org/briarproject/android/blogs/BaseControllerImpl.java b/briar-android/src/org/briarproject/android/blogs/BaseControllerImpl.java index 0015bc111e22d70032ce92114a1839cac71db4b5..7ff91c18bde74948718295728c12630f3b1483e4 100644 --- a/briar-android/src/org/briarproject/android/blogs/BaseControllerImpl.java +++ b/briar-android/src/org/briarproject/android/blogs/BaseControllerImpl.java @@ -12,8 +12,6 @@ import org.briarproject.api.blogs.BlogManager; import org.briarproject.api.blogs.BlogPostHeader; import org.briarproject.api.db.DatabaseExecutor; import org.briarproject.api.db.DbException; -import org.briarproject.api.event.BlogPostAddedEvent; -import org.briarproject.api.event.Event; import org.briarproject.api.event.EventBus; import org.briarproject.api.event.EventListener; import org.briarproject.api.identity.IdentityManager; @@ -47,7 +45,7 @@ abstract class BaseControllerImpl extends DbControllerImpl private final Map<MessageId, BlogPostHeader> headerCache = new ConcurrentHashMap<>(); - protected volatile OnBlogPostAddedListener listener; + private volatile OnBlogPostAddedListener listener; BaseControllerImpl(@DatabaseExecutor Executor dbExecutor, LifecycleManager lifecycleManager, EventBus eventBus, @@ -63,9 +61,7 @@ abstract class BaseControllerImpl extends DbControllerImpl @Override @CallSuper public void onStart() { - if (listener == null) - throw new IllegalStateException( - "OnBlogPostAddedListener needs to be attached"); + if (listener == null) throw new IllegalStateException(); eventBus.addListener(this); } @@ -75,26 +71,30 @@ abstract class BaseControllerImpl extends DbControllerImpl eventBus.removeListener(this); } - @Override - @CallSuper - public void eventOccurred(Event e) { - if (e instanceof BlogPostAddedEvent) { - final BlogPostAddedEvent b = (BlogPostAddedEvent) e; - LOG.info("New blog post added"); - listener.runOnUiThreadUnlessDestroyed(new Runnable() { - @Override - public void run() { - listener.onBlogPostAdded(b.getHeader(), b.isLocal()); - } - }); - } - } - @Override public void setOnBlogPostAddedListener(OnBlogPostAddedListener listener) { this.listener = listener; } + void onBlogPostAdded(final BlogPostHeader h, final boolean local) { + listener.runOnUiThreadUnlessDestroyed(new Runnable() { + @Override + public void run() { + listener.onBlogPostAdded(h, local); + } + }); + } + + void onBlogRemoved() { + listener.runOnUiThreadUnlessDestroyed(new Runnable() { + @Override + public void run() { + listener.onBlogRemoved(); + } + }); + } + + @Override public void loadBlogPosts(final GroupId groupId, final ResultExceptionHandler<Collection<BlogPostItem>, DbException> handler) { diff --git a/briar-android/src/org/briarproject/android/blogs/BlogControllerImpl.java b/briar-android/src/org/briarproject/android/blogs/BlogControllerImpl.java index 5394821f8751dce0fc439445c3ca645434026b56..64cee65a5b89d45644f6fab5674e5398b0e05e10 100644 --- a/briar-android/src/org/briarproject/android/blogs/BlogControllerImpl.java +++ b/briar-android/src/org/briarproject/android/blogs/BlogControllerImpl.java @@ -26,6 +26,7 @@ import java.util.logging.Logger; import javax.inject.Inject; +import static java.util.logging.Level.INFO; import static java.util.logging.Level.WARNING; public class BlogControllerImpl extends BaseControllerImpl @@ -50,15 +51,15 @@ public class BlogControllerImpl extends BaseControllerImpl } @Override - public void onActivityResume() { - super.onStart(); // TODO: Should be called when activity starts. #609 + public void onActivityStart() { + super.onStart(); notificationManager.blockNotification(groupId); notificationManager.clearBlogPostNotification(groupId); } @Override - public void onActivityPause() { - super.onStop(); // TODO: Should be called when activity stops. #609 + public void onActivityStop() { + super.onStop(); notificationManager.unblockNotification(groupId); } @@ -75,20 +76,16 @@ public class BlogControllerImpl extends BaseControllerImpl public void eventOccurred(Event e) { if (groupId == null) throw new IllegalStateException(); if (e instanceof BlogPostAddedEvent) { - BlogPostAddedEvent s = (BlogPostAddedEvent) e; - if (s.getGroupId().equals(groupId)) { - super.eventOccurred(e); + BlogPostAddedEvent b = (BlogPostAddedEvent) e; + if (b.getGroupId().equals(groupId)) { + LOG.info("Blog post added"); + onBlogPostAdded(b.getHeader(), b.isLocal()); } } else if (e instanceof GroupRemovedEvent) { - GroupRemovedEvent s = (GroupRemovedEvent) e; - if (s.getGroup().getId().equals(groupId)) { + GroupRemovedEvent g = (GroupRemovedEvent) e; + if (g.getGroup().getId().equals(groupId)) { LOG.info("Blog removed"); - listener.runOnUiThreadUnlessDestroyed(new Runnable() { - @Override - public void run() { - listener.onBlogRemoved(); - } - }); + onBlogRemoved(); } } } @@ -115,11 +112,15 @@ public class BlogControllerImpl extends BaseControllerImpl @Override public void run() { try { + long now = System.currentTimeMillis(); LocalAuthor a = identityManager.getLocalAuthor(); Blog b = blogManager.getBlog(groupId); boolean ours = a.getId().equals(b.getAuthor().getId()); boolean removable = blogManager.canBeRemoved(groupId); BlogItem blog = new BlogItem(b, ours, removable); + long duration = System.currentTimeMillis() - now; + if (LOG.isLoggable(INFO)) + LOG.info("Loading blog took " + duration + " ms"); handler.onResult(blog); } catch (DbException e) { if (LOG.isLoggable(WARNING)) @@ -138,8 +139,12 @@ public class BlogControllerImpl extends BaseControllerImpl @Override public void run() { try { + long now = System.currentTimeMillis(); Blog b = blogManager.getBlog(groupId); blogManager.removeBlog(b); + long duration = System.currentTimeMillis() - now; + if (LOG.isLoggable(INFO)) + LOG.info("Removing blog took " + duration + " ms"); handler.onResult(null); } catch (DbException e) { if (LOG.isLoggable(WARNING)) diff --git a/briar-android/src/org/briarproject/android/blogs/BlogFragment.java b/briar-android/src/org/briarproject/android/blogs/BlogFragment.java index 25d266c312050286eeeb69289005f19930edb29e..eb655209108c6a290394c31c3fc3241d4f711c12 100644 --- a/briar-android/src/org/briarproject/android/blogs/BlogFragment.java +++ b/briar-android/src/org/briarproject/android/blogs/BlogFragment.java @@ -123,18 +123,13 @@ public class BlogFragment extends BaseFragment implements public void onStart() { super.onStart(); loadBlog(); - } - - @Override - public void onResume() { - super.onResume(); loadBlogPosts(false); list.startPeriodicUpdate(); } @Override - public void onPause() { - super.onPause(); + public void onStop() { + super.onStop(); list.stopPeriodicUpdate(); } @@ -215,9 +210,11 @@ public class BlogFragment extends BaseFragment implements adapter.add(post); if (local) { list.scrollToPosition(0); - displaySnackbar(R.string.blogs_blog_post_created, false); + displaySnackbar(R.string.blogs_blog_post_created, + false); } else { - displaySnackbar(R.string.blogs_blog_post_received, true); + displaySnackbar(R.string.blogs_blog_post_received, + true); } } @@ -236,11 +233,11 @@ public class BlogFragment extends BaseFragment implements listener) { @Override public void onResultUi(Collection<BlogPostItem> posts) { - if (posts.size() > 0) { + if (posts.isEmpty()) { + list.showData(); + } else { adapter.addAll(posts); if (reload) list.scrollToPosition(0); - } else { - list.showData(); } } diff --git a/briar-android/src/org/briarproject/android/blogs/FeedController.java b/briar-android/src/org/briarproject/android/blogs/FeedController.java index e2934f49fd67757128d0dc521f020d86953fcb4a..90015b066f6a17f9a79dc76c1d8dd66e6fc04cde 100644 --- a/briar-android/src/org/briarproject/android/blogs/FeedController.java +++ b/briar-android/src/org/briarproject/android/blogs/FeedController.java @@ -1,7 +1,6 @@ package org.briarproject.android.blogs; import org.briarproject.android.controller.handler.ResultExceptionHandler; -import org.briarproject.android.controller.handler.ResultHandler; import org.briarproject.api.blogs.Blog; import org.briarproject.api.db.DbException; @@ -12,6 +11,6 @@ public interface FeedController extends BaseController { void loadBlogPosts( ResultExceptionHandler<Collection<BlogPostItem>, DbException> handler); - void loadPersonalBlog(ResultHandler<Blog> resultHandler); + void loadPersonalBlog(ResultExceptionHandler<Blog, DbException> handler); } diff --git a/briar-android/src/org/briarproject/android/blogs/FeedControllerImpl.java b/briar-android/src/org/briarproject/android/blogs/FeedControllerImpl.java index 0d85144d8dd08e5389cfe62019216d876493fd6e..faf626b5462e281dd83e95e61a52f7eda29e6fa3 100644 --- a/briar-android/src/org/briarproject/android/blogs/FeedControllerImpl.java +++ b/briar-android/src/org/briarproject/android/blogs/FeedControllerImpl.java @@ -2,14 +2,16 @@ package org.briarproject.android.blogs; import org.briarproject.android.api.AndroidNotificationManager; import org.briarproject.android.controller.handler.ResultExceptionHandler; -import org.briarproject.android.controller.handler.ResultHandler; import org.briarproject.api.blogs.Blog; import org.briarproject.api.blogs.BlogManager; import org.briarproject.api.db.DatabaseExecutor; import org.briarproject.api.db.DbException; import org.briarproject.api.db.NoSuchGroupException; import org.briarproject.api.db.NoSuchMessageException; +import org.briarproject.api.event.BlogPostAddedEvent; +import org.briarproject.api.event.Event; import org.briarproject.api.event.EventBus; +import org.briarproject.api.event.GroupRemovedEvent; import org.briarproject.api.identity.Author; import org.briarproject.api.identity.IdentityManager; import org.briarproject.api.lifecycle.LifecycleManager; @@ -52,15 +54,28 @@ public class FeedControllerImpl extends BaseControllerImpl notificationManager.unblockAllBlogPostNotifications(); } + @Override + public void eventOccurred(Event e) { + if (e instanceof BlogPostAddedEvent) { + BlogPostAddedEvent b = (BlogPostAddedEvent) e; + LOG.info("Blog post added"); + onBlogPostAdded(b.getHeader(), b.isLocal()); + } else if (e instanceof GroupRemovedEvent) { + GroupRemovedEvent g = (GroupRemovedEvent) e; + if (g.getGroup().getClientId().equals(blogManager.getClientId())) { + LOG.info("Blog removed"); + onBlogRemoved(); + } + } + } + @Override public void loadBlogPosts( final ResultExceptionHandler<Collection<BlogPostItem>, DbException> handler) { - LOG.info("Loading all blog posts..."); runOnDbThread(new Runnable() { @Override public void run() { try { - // load blog posts long now = System.currentTimeMillis(); Collection<BlogPostItem> posts = new ArrayList<>(); for (Blog b : blogManager.getBlogs()) { @@ -85,24 +100,23 @@ public class FeedControllerImpl extends BaseControllerImpl } @Override - public void loadPersonalBlog(final ResultHandler<Blog> resultHandler) { - LOG.info("Loading personal blog..."); + public void loadPersonalBlog( + final ResultExceptionHandler<Blog, DbException> handler) { runOnDbThread(new Runnable() { @Override public void run() { try { - // load blog posts long now = System.currentTimeMillis(); Author a = identityManager.getLocalAuthor(); Blog b = blogManager.getPersonalBlog(a); long duration = System.currentTimeMillis() - now; if (LOG.isLoggable(INFO)) - LOG.info("Loading pers. blog took " + duration + " ms"); - resultHandler.onResult(b); + LOG.info("Loading blog took " + duration + " ms"); + handler.onResult(b); } catch (DbException e) { if (LOG.isLoggable(WARNING)) LOG.log(WARNING, e.toString(), e); - resultHandler.onResult(null); + handler.onException(e); } } }); diff --git a/briar-android/src/org/briarproject/android/blogs/FeedFragment.java b/briar-android/src/org/briarproject/android/blogs/FeedFragment.java index d07a800d59a6bbe61b5de4b0e453e68326b2ece9..6f960d3c128a310de26d699dbe8919c7f910c100 100644 --- a/briar-android/src/org/briarproject/android/blogs/FeedFragment.java +++ b/briar-android/src/org/briarproject/android/blogs/FeedFragment.java @@ -20,7 +20,6 @@ import org.briarproject.android.ActivityComponent; import org.briarproject.android.blogs.BaseController.OnBlogPostAddedListener; import org.briarproject.android.blogs.BlogPostAdapter.OnBlogPostClickListener; import org.briarproject.android.controller.handler.UiResultExceptionHandler; -import org.briarproject.android.controller.handler.UiResultHandler; import org.briarproject.android.fragment.BaseFragment; import org.briarproject.android.view.BriarRecyclerView; import org.briarproject.api.blogs.Blog; @@ -99,40 +98,56 @@ public class FeedFragment extends BaseFragment implements public void onStart() { super.onStart(); feedController.onStart(); + loadPersonalBlog(); + loadBlogPosts(false); + } + + @Override + public void onStop() { + super.onStop(); + feedController.onStop(); + adapter.clear(); + list.showProgressBar(); + list.stopPeriodicUpdate(); + // TODO save list position in database/preferences? + } + + private void loadPersonalBlog() { feedController.loadPersonalBlog( - new UiResultHandler<Blog>(listener) { + new UiResultExceptionHandler<Blog, DbException>(listener) { @Override public void onResultUi(Blog b) { personalBlog = b; } + + @Override + public void onExceptionUi(DbException exception) { + // TODO: Decide how to handle errors in the UI + finish(); + } }); + } + + private void loadBlogPosts(final boolean clear) { feedController.loadBlogPosts( new UiResultExceptionHandler<Collection<BlogPostItem>, DbException>( listener) { @Override public void onResultUi(Collection<BlogPostItem> posts) { - if (posts.isEmpty()) { - list.showData(); - } else { - adapter.addAll(posts); - } + if (clear) adapter.setItems(posts); + else adapter.addAll(posts); + if (posts.isEmpty()) list.showData(); } + @Override - public void onExceptionUi(DbException exception) { - // TODO + public void onExceptionUi(DbException e) { + // TODO: Decide how to handle errors in the UI + finish(); } }); list.startPeriodicUpdate(); } - @Override - public void onStop() { - super.onStop(); - feedController.onStop(); - list.stopPeriodicUpdate(); - // TODO save list position in database/preferences? - } - @Override public void onCreateOptionsMenu(Menu menu, MenuInflater inflater) { inflater.inflate(R.menu.blogs_feed_actions, menu); @@ -185,9 +200,11 @@ public class FeedFragment extends BaseFragment implements showSnackBar(R.string.blogs_blog_post_received); } } + @Override public void onExceptionUi(DbException exception) { // TODO: Decide how to handle errors in the UI + finish(); } } ); @@ -234,6 +251,6 @@ public class FeedFragment extends BaseFragment implements @Override public void onBlogRemoved() { - finish(); + loadBlogPosts(true); } } diff --git a/briar-android/src/org/briarproject/android/blogs/RssFeedManageActivity.java b/briar-android/src/org/briarproject/android/blogs/RssFeedManageActivity.java index 2fe3ad30ccf90ac3496ef0d5989cbd4b6856e45d..0eb6df792e525221d74becf993e0ba3a20665cde 100644 --- a/briar-android/src/org/briarproject/android/blogs/RssFeedManageActivity.java +++ b/briar-android/src/org/briarproject/android/blogs/RssFeedManageActivity.java @@ -37,9 +37,7 @@ public class RssFeedManageActivity extends BriarActivity private BriarRecyclerView list; private RssFeedAdapter adapter; - - // Fields that are accessed from background threads must be volatile - private volatile GroupId groupId = null; + private GroupId groupId; @Inject @SuppressWarnings("WeakerAccess") @@ -65,11 +63,18 @@ public class RssFeedManageActivity extends BriarActivity } @Override - public void onResume() { - super.onResume(); + public void onStart() { + super.onStart(); loadFeeds(); } + @Override + public void onStop() { + super.onStop(); + adapter.clear(); + list.showProgressBar(); + } + @Override public boolean onCreateOptionsMenu(Menu menu) { MenuInflater inflater = getMenuInflater(); @@ -139,7 +144,7 @@ public class RssFeedManageActivity extends BriarActivity runOnUiThreadUnlessDestroyed(new Runnable() { @Override public void run() { - if (feeds.size() == 0) list.showData(); + if (feeds.isEmpty()) list.showData(); else adapter.addAll(feeds); } }); diff --git a/briar-android/src/org/briarproject/android/blogs/WriteBlogPostActivity.java b/briar-android/src/org/briarproject/android/blogs/WriteBlogPostActivity.java index 70d326ca42266b50da015e30191740ad786e0a2c..014f0d1f48541911a14c218008bb78fd70429165 100644 --- a/briar-android/src/org/briarproject/android/blogs/WriteBlogPostActivity.java +++ b/briar-android/src/org/briarproject/android/blogs/WriteBlogPostActivity.java @@ -94,15 +94,15 @@ public class WriteBlogPostActivity extends BriarActivity } @Override - public void onPause() { - super.onPause(); - notificationManager.unblockNotification(groupId); + public void onStart() { + super.onStart(); + notificationManager.blockNotification(groupId); } @Override - public void onResume() { - super.onResume(); - notificationManager.blockNotification(groupId); + public void onStop() { + super.onStop(); + notificationManager.unblockNotification(groupId); } @Override diff --git a/briar-android/src/org/briarproject/android/contact/BaseContactListAdapter.java b/briar-android/src/org/briarproject/android/contact/BaseContactListAdapter.java index aa48714f77f086e031054e7d5929e5b70c11ed24..cd01ad1a426faa92757372bade5fe2db41005e7f 100644 --- a/briar-android/src/org/briarproject/android/contact/BaseContactListAdapter.java +++ b/briar-android/src/org/briarproject/android/contact/BaseContactListAdapter.java @@ -13,7 +13,6 @@ import org.briarproject.R; import org.briarproject.android.util.BriarAdapter; import org.briarproject.api.contact.ContactId; import org.briarproject.api.identity.Author; -import org.briarproject.api.sync.GroupId; import org.briarproject.util.StringUtils; import im.delight.android.identicons.IdenticonDrawable; @@ -90,17 +89,6 @@ public abstract class BaseContactListAdapter<VH extends BaseContactListAdapter.B return INVALID_POSITION; // Not found } - int findItemPosition(GroupId g) { - int count = getItemCount(); - for (int i = 0; i < count; i++) { - ContactListItem item = getItemAt(i); - if (item != null && item.getGroupId().equals(g)) { - return i; - } - } - return INVALID_POSITION; // Not found - } - public static class BaseContactHolder extends RecyclerView.ViewHolder { public final ViewGroup layout; diff --git a/briar-android/src/org/briarproject/android/contact/ContactListFragment.java b/briar-android/src/org/briarproject/android/contact/ContactListFragment.java index 891bfcfbc254b38e4b3242b1e092ae8d9d39f211..d640439a68697a7da96bf0ea3aacc48eda1adb0f 100644 --- a/briar-android/src/org/briarproject/android/contact/ContactListFragment.java +++ b/briar-android/src/org/briarproject/android/contact/ContactListFragment.java @@ -170,8 +170,8 @@ public class ContactListFragment extends BaseFragment implements EventListener { } @Override - public void onResume() { - super.onResume(); + public void onStart() { + super.onStart(); notificationManager.blockAllContactNotifications(); notificationManager.clearAllContactNotifications(); eventBus.addListener(this); @@ -180,8 +180,8 @@ public class ContactListFragment extends BaseFragment implements EventListener { } @Override - public void onPause() { - super.onPause(); + public void onStop() { + super.onStop(); eventBus.removeListener(this); notificationManager.unblockAllContactNotifications(); adapter.clear(); @@ -213,10 +213,10 @@ public class ContactListFragment extends BaseFragment implements EventListener { // Continue } } - displayContacts(contacts); long duration = System.currentTimeMillis() - now; if (LOG.isLoggable(INFO)) LOG.info("Full load took " + duration + " ms"); + displayContacts(contacts); } catch (DbException e) { if (LOG.isLoggable(WARNING)) LOG.log(WARNING, e.toString(), e); @@ -229,7 +229,7 @@ public class ContactListFragment extends BaseFragment implements EventListener { listener.runOnUiThreadUnlessDestroyed(new Runnable() { @Override public void run() { - if (contacts.size() == 0) list.showData(); + if (contacts.isEmpty()) list.showData(); else adapter.addAll(contacts); } }); @@ -238,40 +238,45 @@ public class ContactListFragment extends BaseFragment implements EventListener { @Override public void eventOccurred(Event e) { if (e instanceof ContactStatusChangedEvent) { - LOG.info("Contact Status changed, reloading"); - // is also broadcast when contact was added - loadContacts(); + ContactStatusChangedEvent c = (ContactStatusChangedEvent) e; + if (c.isActive()) { + LOG.info("Contact activated, reloading"); + loadContacts(); + } else { + LOG.info("Contact deactivated, removing item"); + removeItem(c.getContactId()); + } } else if (e instanceof ContactConnectedEvent) { setConnected(((ContactConnectedEvent) e).getContactId(), true); } else if (e instanceof ContactDisconnectedEvent) { setConnected(((ContactDisconnectedEvent) e).getContactId(), false); } else if (e instanceof ContactRemovedEvent) { - LOG.info("Contact removed"); + LOG.info("Contact removed, removing item"); removeItem(((ContactRemovedEvent) e).getContactId()); } else if (e instanceof PrivateMessageReceivedEvent) { - LOG.info("Message received, update contact"); + LOG.info("Private message received, updating item"); PrivateMessageReceivedEvent p = (PrivateMessageReceivedEvent) e; PrivateMessageHeader h = p.getMessageHeader(); - updateItem(p.getGroupId(), ConversationItem.from(h)); + updateItem(p.getContactId(), ConversationItem.from(h)); } else if (e instanceof IntroductionRequestReceivedEvent) { - LOG.info("Introduction Request received, update contact"); + LOG.info("Introduction request received, updating item"); IntroductionRequestReceivedEvent m = (IntroductionRequestReceivedEvent) e; IntroductionRequest ir = m.getIntroductionRequest(); updateItem(m.getContactId(), ConversationItem.from(ir)); } else if (e instanceof IntroductionResponseReceivedEvent) { - LOG.info("Introduction Response received, update contact"); + LOG.info("Introduction response received, updating item"); IntroductionResponseReceivedEvent m = (IntroductionResponseReceivedEvent) e; IntroductionResponse ir = m.getIntroductionResponse(); updateItem(m.getContactId(), ConversationItem.from(ir)); } else if (e instanceof InvitationRequestReceivedEvent) { - LOG.info("Invitation Request received, update contact"); + LOG.info("Invitation request received, updating item"); InvitationRequestReceivedEvent m = (InvitationRequestReceivedEvent) e; InvitationRequest ir = m.getRequest(); updateItem(m.getContactId(), ConversationItem.from(ir)); } else if (e instanceof InvitationResponseReceivedEvent) { - LOG.info("Invitation Response received, update contact"); + LOG.info("Invitation response received, updating item"); InvitationResponseReceivedEvent m = (InvitationResponseReceivedEvent) e; InvitationResponse ir = m.getResponse(); @@ -293,20 +298,6 @@ public class ContactListFragment extends BaseFragment implements EventListener { }); } - private void updateItem(final GroupId g, final ConversationItem m) { - listener.runOnUiThreadUnlessDestroyed(new Runnable() { - @Override - public void run() { - int position = adapter.findItemPosition(g); - ContactListItem item = adapter.getItemAt(position); - if (item != null) { - item.addMessage(m); - adapter.updateItemAt(position, item); - } - } - }); - } - private void removeItem(final ContactId c) { listener.runOnUiThreadUnlessDestroyed(new Runnable() { @Override diff --git a/briar-android/src/org/briarproject/android/contact/ConversationActivity.java b/briar-android/src/org/briarproject/android/contact/ConversationActivity.java index 1d563ad0ce1679a7d218e911d083d3d270eb95d4..fd948d0aadca0ff38cc02730bbe007fe4d5d01d2 100644 --- a/briar-android/src/org/briarproject/android/contact/ConversationActivity.java +++ b/briar-android/src/org/briarproject/android/contact/ConversationActivity.java @@ -34,7 +34,6 @@ import org.briarproject.android.view.TextInputView; import org.briarproject.android.view.TextInputView.TextInputListener; import org.briarproject.api.FormatException; import org.briarproject.api.blogs.BlogSharingManager; -import org.briarproject.api.clients.BaseMessageHeader; import org.briarproject.api.clients.SessionId; import org.briarproject.api.contact.Contact; import org.briarproject.api.contact.ContactId; @@ -42,7 +41,6 @@ import org.briarproject.api.contact.ContactManager; import org.briarproject.api.crypto.CryptoExecutor; import org.briarproject.api.db.DbException; import org.briarproject.api.db.NoSuchContactException; -import org.briarproject.api.db.NoSuchMessageException; import org.briarproject.api.event.ContactConnectedEvent; import org.briarproject.api.event.ContactDisconnectedEvent; import org.briarproject.api.event.ContactRemovedEvent; @@ -150,7 +148,6 @@ public class ConversationActivity extends BriarActivity private volatile ContactId contactId = null; private volatile String contactName = null; private volatile byte[] contactIdenticonKey = null; - private volatile boolean connected = false; @SuppressWarnings("ConstantConditions") @Override @@ -214,18 +211,19 @@ public class ConversationActivity extends BriarActivity } @Override - public void onResume() { - super.onResume(); + public void onStart() { + super.onStart(); eventBus.addListener(this); notificationManager.blockNotification(groupId); notificationManager.clearPrivateMessageNotification(groupId); - loadData(); + loadContactDetails(); + loadMessages(); list.startPeriodicUpdate(); } @Override - public void onPause() { - super.onPause(); + public void onStop() { + super.onStop(); eventBus.removeListener(this); notificationManager.unblockNotification(groupId); list.stopPeriodicUpdate(); @@ -277,7 +275,7 @@ public class ConversationActivity extends BriarActivity finish(); } - private void loadData() { + private void loadContactDetails() { runOnDbThread(new Runnable() { @Override public void run() { @@ -291,13 +289,12 @@ public class ConversationActivity extends BriarActivity contactIdenticonKey = contact.getAuthor().getId().getBytes(); } - connected = connectionRegistry.isConnected(contactId); + boolean connected = + connectionRegistry.isConnected(contactId); long duration = System.currentTimeMillis() - now; if (LOG.isLoggable(INFO)) LOG.info("Loading contact took " + duration + " ms"); - displayContactDetails(); - // Load the messages here to make sure we have a contactId - loadMessages(); + displayContactDetails(connected); } catch (NoSuchContactException e) { finishOnUiThread(); } catch (DbException e) { @@ -308,7 +305,7 @@ public class ConversationActivity extends BriarActivity }); } - private void displayContactDetails() { + private void displayContactDetails(final boolean connected) { runOnUiThreadUnlessDestroyed(new Runnable() { @Override public void run() { @@ -359,7 +356,7 @@ public class ConversationActivity extends BriarActivity invitations.addAll(blogInvitations); long duration = System.currentTimeMillis() - now; if (LOG.isLoggable(INFO)) - LOG.info("Loading headers took " + duration + " ms"); + LOG.info("Loading messages took " + duration + " ms"); displayMessages(headers, introductions, invitations); } catch (NoSuchContactException e) { finishOnUiThread(); @@ -378,13 +375,12 @@ public class ConversationActivity extends BriarActivity @Override public void run() { textInputView.setSendButtonEnabled(true); - if (headers.isEmpty() && introductions.isEmpty() && - invitations.isEmpty()) { - // we have no messages, - // so let the list know to hide progress bar + int size = headers.size() + introductions.size() + + invitations.size(); + if (size == 0) { list.showData(); } else { - List<ConversationItem> items = new ArrayList<>(); + List<ConversationItem> items = new ArrayList<>(size); for (PrivateMessageHeader h : headers) { ConversationMessageItem item = ConversationItem.from(h); byte[] body = bodyCache.get(h.getId()); @@ -392,28 +388,26 @@ public class ConversationActivity extends BriarActivity else item.setBody(body); items.add(item); } - for (IntroductionMessage m : introductions) { - ConversationItem item; - if (m instanceof IntroductionRequest) { - item = ConversationItem - .from((IntroductionRequest) m); + for (IntroductionMessage im : introductions) { + if (im instanceof IntroductionRequest) { + IntroductionRequest ir = (IntroductionRequest) im; + items.add(ConversationItem.from(ir)); } else { - item = ConversationItem + IntroductionResponse ir = (IntroductionResponse) im; + items.add(ConversationItem .from(ConversationActivity.this, - contactName, - (IntroductionResponse) m); + contactName, ir)); } - items.add(item); } - for (InvitationMessage i : invitations) { - if (i instanceof InvitationRequest) { - InvitationRequest r = (InvitationRequest) i; - items.add(ConversationItem.from(r)); - } else if (i instanceof InvitationResponse) { - InvitationResponse r = (InvitationResponse) i; + for (InvitationMessage im : invitations) { + if (im instanceof InvitationRequest) { + InvitationRequest ir = (InvitationRequest) im; + items.add(ConversationItem.from(ir)); + } else if (im instanceof InvitationResponse) { + InvitationResponse ir = (InvitationResponse) im; items.add(ConversationItem .from(ConversationActivity.this, - contactName, r)); + contactName, ir)); } } adapter.addAll(items); @@ -435,8 +429,6 @@ public class ConversationActivity extends BriarActivity if (LOG.isLoggable(INFO)) LOG.info("Loading body took " + duration + " ms"); displayMessageBody(m, body); - } catch (NoSuchMessageException e) { - // The item will be removed when we get the event } catch (DbException e) { if (LOG.isLoggable(WARNING)) LOG.log(WARNING, e.toString(), e); @@ -496,9 +488,10 @@ public class ConversationActivity extends BriarActivity public void run() { try { long now = System.currentTimeMillis(); - for (Map.Entry<MessageId, GroupId> e : unread.entrySet()) - messagingManager - .setReadFlag(e.getValue(), e.getKey(), true); + for (Map.Entry<MessageId, GroupId> e : unread.entrySet()) { + messagingManager.setReadFlag(e.getValue(), e.getKey(), + true); + } long duration = System.currentTimeMillis() - now; if (LOG.isLoggable(INFO)) LOG.info("Marking read took " + duration + " ms"); @@ -525,7 +518,6 @@ public class ConversationActivity extends BriarActivity PrivateMessageHeader h = p.getMessageHeader(); addConversationItem(ConversationItem.from(h)); loadMessageBody(h.getId()); - markMessageReadIfNew(h); } } else if (e instanceof MessagesSentEvent) { MessagesSentEvent m = (MessagesSentEvent) e; @@ -543,15 +535,13 @@ public class ConversationActivity extends BriarActivity ContactConnectedEvent c = (ContactConnectedEvent) e; if (c.getContactId().equals(contactId)) { LOG.info("Contact connected"); - connected = true; - displayContactDetails(); + displayContactDetails(true); } } else if (e instanceof ContactDisconnectedEvent) { ContactDisconnectedEvent c = (ContactDisconnectedEvent) e; if (c.getContactId().equals(contactId)) { LOG.info("Contact disconnected"); - connected = false; - displayContactDetails(); + displayContactDetails(false); } } else if (e instanceof IntroductionRequestReceivedEvent) { IntroductionRequestReceivedEvent event = @@ -561,7 +551,6 @@ public class ConversationActivity extends BriarActivity IntroductionRequest ir = event.getIntroductionRequest(); ConversationItem item = new ConversationIntroductionInItem(ir); addConversationItem(item); - markMessageReadIfNew(ir); } } else if (e instanceof IntroductionResponseReceivedEvent) { IntroductionResponseReceivedEvent event = @@ -572,7 +561,6 @@ public class ConversationActivity extends BriarActivity ConversationItem item = ConversationItem.from(this, contactName, ir); addConversationItem(item); - markMessageReadIfNew(ir); } } else if (e instanceof InvitationRequestReceivedEvent) { InvitationRequestReceivedEvent event = @@ -582,7 +570,6 @@ public class ConversationActivity extends BriarActivity InvitationRequest ir = event.getRequest(); ConversationItem item = ConversationItem.from(ir); addConversationItem(item); - markMessageReadIfNew(ir); } } else if (e instanceof InvitationResponseReceivedEvent) { InvitationResponseReceivedEvent event = @@ -593,46 +580,10 @@ public class ConversationActivity extends BriarActivity ConversationItem item = ConversationItem.from(this, contactName, ir); addConversationItem(item); - markMessageReadIfNew(ir); } } } - private void markMessageReadIfNew(final BaseMessageHeader h) { - runOnUiThreadUnlessDestroyed(new Runnable() { - @Override - public void run() { - ConversationItem item = adapter.getLastItem(); - if (item != null) { - // Mark the message read if it's the newest message - long lastMsgTime = item.getTime(); - long newMsgTime = h.getTimestamp(); - if (newMsgTime > lastMsgTime) - markNewMessageRead(h.getGroupId(), h.getId()); - else loadMessages(); - } else { - // mark the message as read as well if it is the first one - markNewMessageRead(h.getGroupId(), h.getId()); - } - } - }); - } - - private void markNewMessageRead(final GroupId g, final MessageId m) { - runOnDbThread(new Runnable() { - @Override - public void run() { - try { - messagingManager.setReadFlag(g, m, true); - loadMessages(); - } catch (DbException e) { - if (LOG.isLoggable(WARNING)) - LOG.log(WARNING, e.toString(), e); - } - } - }); - } - private void markMessages(final Collection<MessageId> messageIds, final boolean sent, final boolean seen) { runOnUiThreadUnlessDestroyed(new Runnable() { @@ -654,7 +605,6 @@ public class ConversationActivity extends BriarActivity @Override public void onSendClick(String text) { - markMessagesRead(); if (text.equals("")) return; long timestamp = System.currentTimeMillis(); timestamp = Math.max(timestamp, getMinTimestampForNewMessage()); diff --git a/briar-android/src/org/briarproject/android/controller/ActivityLifecycleController.java b/briar-android/src/org/briarproject/android/controller/ActivityLifecycleController.java index 303f9b89b40e36fd8a90f0e3dfc06092201c47c2..96d0cf4f0201539b39c35974db08e8b7be60dacb 100644 --- a/briar-android/src/org/briarproject/android/controller/ActivityLifecycleController.java +++ b/briar-android/src/org/briarproject/android/controller/ActivityLifecycleController.java @@ -6,9 +6,9 @@ public interface ActivityLifecycleController { void onActivityCreate(Activity activity); - void onActivityResume(); + void onActivityStart(); - void onActivityPause(); + void onActivityStop(); void onActivityDestroy(); } diff --git a/briar-android/src/org/briarproject/android/controller/BriarControllerImpl.java b/briar-android/src/org/briarproject/android/controller/BriarControllerImpl.java index 459730ebd2b616224156ace7baefe430060b286a..f49d6485f7b58e4673e06f4f40e1125275e85610 100644 --- a/briar-android/src/org/briarproject/android/controller/BriarControllerImpl.java +++ b/briar-android/src/org/briarproject/android/controller/BriarControllerImpl.java @@ -19,18 +19,18 @@ public class BriarControllerImpl implements BriarController { private static final Logger LOG = Logger.getLogger(BriarControllerImpl.class.getName()); - @Inject - BriarServiceConnection serviceConnection; - @Inject - DatabaseConfig databaseConfig; - @Inject - Activity activity; + private final BriarServiceConnection serviceConnection; + private final DatabaseConfig databaseConfig; + private final Activity activity; private boolean bound = false; @Inject - public BriarControllerImpl() { - + BriarControllerImpl(BriarServiceConnection serviceConnection, + DatabaseConfig databaseConfig, Activity activity) { + this.serviceConnection = serviceConnection; + this.databaseConfig = databaseConfig; + this.activity = activity; } @Override @@ -40,13 +40,11 @@ public class BriarControllerImpl implements BriarController { } @Override - @CallSuper - public void onActivityResume() { + public void onActivityStart() { } @Override - @CallSuper - public void onActivityPause() { + public void onActivityStop() { } @Override diff --git a/briar-android/src/org/briarproject/android/controller/NavDrawerControllerImpl.java b/briar-android/src/org/briarproject/android/controller/NavDrawerControllerImpl.java index 060f77933e3993d214d548d8b8a9810e7e0b05d9..55d5d267f74c8fb16b8befdae50ee54c5ba61c48 100644 --- a/briar-android/src/org/briarproject/android/controller/NavDrawerControllerImpl.java +++ b/briar-android/src/org/briarproject/android/controller/NavDrawerControllerImpl.java @@ -57,12 +57,12 @@ public class NavDrawerControllerImpl extends DbControllerImpl } @Override - public void onActivityResume() { + public void onActivityStart() { eventBus.addListener(this); } @Override - public void onActivityPause() { + public void onActivityStop() { eventBus.removeListener(this); } diff --git a/briar-android/src/org/briarproject/android/forum/ForumActivity.java b/briar-android/src/org/briarproject/android/forum/ForumActivity.java index 81b41f99fed3dbc19467fd6ce6e56dc7c6067ee4..03ebdf438e960042e49012b49a0c3f3e9ce53eca 100644 --- a/briar-android/src/org/briarproject/android/forum/ForumActivity.java +++ b/briar-android/src/org/briarproject/android/forum/ForumActivity.java @@ -1,6 +1,7 @@ package org.briarproject.android.forum; import android.content.DialogInterface; +import android.content.DialogInterface.OnClickListener; import android.content.Intent; import android.os.Bundle; import android.support.annotation.LayoutRes; @@ -98,9 +99,8 @@ public class ForumActivity extends @Override public boolean onOptionsItemSelected(final MenuItem item) { - ActivityOptionsCompat options = - makeCustomAnimation(this, android.R.anim.slide_in_left, - android.R.anim.slide_out_right); + ActivityOptionsCompat options = makeCustomAnimation(this, + android.R.anim.slide_in_left, android.R.anim.slide_out_right); // Handle presses on the action bar items switch (item.getItemId()) { case R.id.action_forum_compose_post: @@ -110,9 +110,8 @@ public class ForumActivity extends Intent i2 = new Intent(this, ShareForumActivity.class); i2.setFlags(FLAG_ACTIVITY_CLEAR_TOP | FLAG_ACTIVITY_SINGLE_TOP); i2.putExtra(GROUP_ID, groupId.getBytes()); - ActivityCompat - .startActivityForResult(this, i2, REQUEST_FORUM_SHARED, - options.toBundle()); + ActivityCompat.startActivityForResult(this, i2, + REQUEST_FORUM_SHARED, options.toBundle()); return true; case R.id.action_forum_sharing_status: Intent i3 = new Intent(this, SharingStatusForumActivity.class); @@ -146,17 +145,14 @@ public class ForumActivity extends } private void showUnsubscribeDialog() { - DialogInterface.OnClickListener okListener = - new DialogInterface.OnClickListener() { - @Override - public void onClick(final DialogInterface dialog, - int which) { - deleteNamedGroup(); - } - }; - AlertDialog.Builder builder = - new AlertDialog.Builder(ForumActivity.this, - R.style.BriarDialogTheme); + OnClickListener okListener = new OnClickListener() { + @Override + public void onClick(final DialogInterface dialog, int which) { + deleteNamedGroup(); + } + }; + AlertDialog.Builder builder = new AlertDialog.Builder( + ForumActivity.this, R.style.BriarDialogTheme); builder.setTitle(getString(R.string.dialog_title_leave_forum)); builder.setMessage(getString(R.string.dialog_message_leave_forum)); builder.setNegativeButton(R.string.dialog_button_leave, okListener); @@ -171,14 +167,11 @@ public class ForumActivity extends @Override public void onResultUi(Void v) { Toast.makeText(ForumActivity.this, - R.string.forum_left_toast, - LENGTH_SHORT) - .show(); + R.string.forum_left_toast, LENGTH_SHORT).show(); } @Override - public void onExceptionUi( - DbException exception) { + public void onExceptionUi(DbException exception) { // TODO proper error handling finish(); } diff --git a/briar-android/src/org/briarproject/android/forum/ForumControllerImpl.java b/briar-android/src/org/briarproject/android/forum/ForumControllerImpl.java index fa62f1b292740855de64345b1b2e9866c0404dca..a0b89b0ed4aa4d9363bf20f4fb0487a3de5fc313 100644 --- a/briar-android/src/org/briarproject/android/forum/ForumControllerImpl.java +++ b/briar-android/src/org/briarproject/android/forum/ForumControllerImpl.java @@ -28,8 +28,8 @@ import java.util.logging.Logger; import javax.inject.Inject; -public class ForumControllerImpl - extends ThreadListControllerImpl<Forum, ForumItem, ForumPostHeader, ForumPost> +public class ForumControllerImpl extends + ThreadListControllerImpl<Forum, ForumItem, ForumPostHeader, ForumPost> implements ForumController { private static final Logger LOG = @@ -49,8 +49,8 @@ public class ForumControllerImpl } @Override - public void onActivityResume() { - super.onActivityResume(); + public void onActivityStart() { + super.onActivityStart(); notificationManager.clearForumPostNotification(getGroupId()); } @@ -59,7 +59,7 @@ public class ForumControllerImpl super.eventOccurred(e); if (e instanceof ForumPostReceivedEvent) { - final ForumPostReceivedEvent pe = (ForumPostReceivedEvent) e; + ForumPostReceivedEvent pe = (ForumPostReceivedEvent) e; if (pe.getGroupId().equals(getGroupId())) { LOG.info("Forum post received, adding..."); final ForumPostHeader fph = pe.getForumPostHeader(); @@ -102,9 +102,8 @@ public class ForumControllerImpl @Override protected ForumPost createLocalMessage(String body, long timestamp, @Nullable MessageId parentId, LocalAuthor author) { - return forumManager - .createLocalPost(getGroupId(), body, timestamp, parentId, - author); + return forumManager.createLocalPost(getGroupId(), body, timestamp, + parentId, author); } @Override diff --git a/briar-android/src/org/briarproject/android/forum/ForumListFragment.java b/briar-android/src/org/briarproject/android/forum/ForumListFragment.java index 1ebba8c1c327b16b23c9489e623ec4c62713784c..0edb1a0755a26c801fc92d2aca220008257835ae 100644 --- a/briar-android/src/org/briarproject/android/forum/ForumListFragment.java +++ b/briar-android/src/org/briarproject/android/forum/ForumListFragment.java @@ -111,9 +111,8 @@ public class ForumListFragment extends BaseEventFragment implements } @Override - public void onResume() { - super.onResume(); - + public void onStart() { + super.onStart(); notificationManager.blockAllForumPostNotifications(); notificationManager.clearAllForumPostNotifications(); loadForums(); @@ -122,9 +121,8 @@ public class ForumListFragment extends BaseEventFragment implements } @Override - public void onPause() { - super.onPause(); - + public void onStop() { + super.onStop(); notificationManager.unblockAllForumPostNotifications(); adapter.clear(); list.showProgressBar(); @@ -156,7 +154,6 @@ public class ForumListFragment extends BaseEventFragment implements @Override public void run() { try { - // load forums long now = System.currentTimeMillis(); Collection<ForumListItem> forums = new ArrayList<>(); for (Forum f : forumManager.getForums()) { @@ -168,10 +165,10 @@ public class ForumListFragment extends BaseEventFragment implements // Continue } } - displayForums(forums); long duration = System.currentTimeMillis() - now; if (LOG.isLoggable(INFO)) LOG.info("Full load took " + duration + " ms"); + displayForums(forums); } catch (DbException e) { if (LOG.isLoggable(WARNING)) LOG.log(WARNING, e.toString(), e); @@ -184,8 +181,8 @@ public class ForumListFragment extends BaseEventFragment implements listener.runOnUiThreadUnlessDestroyed(new Runnable() { @Override public void run() { - if (forums.size() > 0) adapter.addAll(forums); - else list.showData(); + if (forums.isEmpty()) list.showData(); + else adapter.addAll(forums); } }); } @@ -245,9 +242,10 @@ public class ForumListFragment extends BaseEventFragment implements } } else if (e instanceof ForumPostReceivedEvent) { ForumPostReceivedEvent f = (ForumPostReceivedEvent) e; - LOG.info("Forum post added, updating..."); + LOG.info("Forum post added, updating item"); updateItem(f.getGroupId(), f.getForumPostHeader()); } else if (e instanceof ForumInvitationReceivedEvent) { + LOG.info("Forum invitation received, reloading available forums"); loadAvailableForums(); } } diff --git a/briar-android/src/org/briarproject/android/fragment/BaseEventFragment.java b/briar-android/src/org/briarproject/android/fragment/BaseEventFragment.java index 69ceab43a6281a5a7ae1f0ad901697a6b2651d82..cf78840532ca486968a10c09d320a57b617d63bd 100644 --- a/briar-android/src/org/briarproject/android/fragment/BaseEventFragment.java +++ b/briar-android/src/org/briarproject/android/fragment/BaseEventFragment.java @@ -12,14 +12,14 @@ public abstract class BaseEventFragment extends BaseFragment implements protected volatile EventBus eventBus; @Override - public void onResume() { - super.onResume(); + public void onStart() { + super.onStart(); eventBus.addListener(this); } @Override - public void onPause() { - super.onPause(); + public void onStop() { + super.onStop(); eventBus.removeListener(this); } } diff --git a/briar-android/src/org/briarproject/android/fragment/BaseFragment.java b/briar-android/src/org/briarproject/android/fragment/BaseFragment.java index d671bf245c692463ea937e7d6532e831dea79278..2cb6b13e6152d89b1e118e8b2cd8494559e78b26 100644 --- a/briar-android/src/org/briarproject/android/fragment/BaseFragment.java +++ b/briar-android/src/org/briarproject/android/fragment/BaseFragment.java @@ -44,6 +44,7 @@ public abstract class BaseFragment extends Fragment public interface BaseFragmentListener extends DestroyableContext { + @Deprecated void runOnDbThread(Runnable runnable); @UiThread diff --git a/briar-android/src/org/briarproject/android/fragment/SettingsFragment.java b/briar-android/src/org/briarproject/android/fragment/SettingsFragment.java index 15c718b6709519831533590334fa7b702d860f05..a3d6551267d1cd6fca14e571e2ebeea12236c011 100644 --- a/briar-android/src/org/briarproject/android/fragment/SettingsFragment.java +++ b/briar-android/src/org/briarproject/android/fragment/SettingsFragment.java @@ -155,14 +155,14 @@ public class SettingsFragment extends PreferenceFragmentCompat } @Override - public void onResume() { - super.onResume(); + public void onStart() { + super.onStart(); eventBus.addListener(this); } @Override - public void onPause() { - super.onPause(); + public void onStop() { + super.onStop(); eventBus.removeListener(this); } diff --git a/briar-android/src/org/briarproject/android/introduction/ContactChooserAdapter.java b/briar-android/src/org/briarproject/android/introduction/ContactChooserAdapter.java index 059ab8cd11e00b8714cd1b6ec94baf97f71b2994..e291302b8e6b86323bfbd8ff587bce6854fbc8ee 100644 --- a/briar-android/src/org/briarproject/android/introduction/ContactChooserAdapter.java +++ b/briar-android/src/org/briarproject/android/introduction/ContactChooserAdapter.java @@ -1,19 +1,19 @@ package org.briarproject.android.introduction; import android.content.Context; +import android.support.annotation.UiThread; import android.view.View; import org.briarproject.android.contact.ContactListAdapter; import org.briarproject.android.contact.ContactListItem; import org.briarproject.api.identity.AuthorId; -public class ContactChooserAdapter extends ContactListAdapter { +@UiThread +class ContactChooserAdapter extends ContactListAdapter { private AuthorId localAuthorId; - public ContactChooserAdapter(Context context, - OnItemClickListener listener) { - + ContactChooserAdapter(Context context, OnItemClickListener listener) { super(context, listener); } @@ -46,7 +46,7 @@ public class ContactChooserAdapter extends ContactListAdapter { * * @param authorId The ID of the local Author */ - public void setLocalAuthor(AuthorId authorId) { + void setLocalAuthor(AuthorId authorId) { localAuthorId = authorId; notifyDataSetChanged(); } diff --git a/briar-android/src/org/briarproject/android/introduction/ContactChooserFragment.java b/briar-android/src/org/briarproject/android/introduction/ContactChooserFragment.java index b26d3a8dc05c9dbdf8911d96d13d81d116437846..888cc61e79eb48b713a61ffeba6788c759f02abb 100644 --- a/briar-android/src/org/briarproject/android/introduction/ContactChooserFragment.java +++ b/briar-android/src/org/briarproject/android/introduction/ContactChooserFragment.java @@ -45,18 +45,18 @@ public class ContactChooserFragment extends BaseFragment { private IntroductionActivity introductionActivity; private BriarRecyclerView list; private ContactChooserAdapter adapter; - private int contactId; + private ContactId contactId; // Fields that are accessed from background threads must be volatile - protected volatile Contact c1; + volatile Contact c1; @Inject - protected volatile ContactManager contactManager; + volatile ContactManager contactManager; @Inject - protected volatile IdentityManager identityManager; + volatile IdentityManager identityManager; @Inject - protected volatile ConversationManager conversationManager; + volatile ConversationManager conversationManager; @Inject - protected volatile ConnectionRegistry connectionRegistry; + volatile ConnectionRegistry connectionRegistry; public static ContactChooserFragment newInstance() { @@ -87,9 +87,7 @@ public class ContactChooserFragment extends BaseFragment { new ContactListAdapter.OnItemClickListener() { @Override public void onItemClick(View view, ContactListItem item) { - if (c1 == null) { - throw new RuntimeException("c1 not accountExists"); - } + if (c1 == null) throw new IllegalStateException(); Contact c2 = item.getContact(); if (!c1.getLocalAuthorId() .equals(c2.getLocalAuthorId())) { @@ -113,15 +111,14 @@ public class ContactChooserFragment extends BaseFragment { } @Override - public void onResume() { - super.onResume(); - + public void onStart() { + super.onStart(); loadContacts(); } @Override - public void onPause() { - super.onPause(); + public void onStop() { + super.onStop(); adapter.clear(); list.showProgressBar(); } @@ -145,7 +142,7 @@ public class ContactChooserFragment extends BaseFragment { AuthorId localAuthorId = identityManager.getLocalAuthor().getId(); for (Contact c : contactManager.getActiveContacts()) { - if (c.getId().getInt() == contactId) { + if (c.getId().equals(contactId)) { c1 = c; } else { ContactId id = c.getId(); @@ -176,7 +173,7 @@ public class ContactChooserFragment extends BaseFragment { @Override public void run() { adapter.setLocalAuthor(localAuthorId); - if (contacts.size() == 0) list.showData(); + if (contacts.isEmpty()) list.showData(); else adapter.addAll(contacts); } }); diff --git a/briar-android/src/org/briarproject/android/introduction/IntroductionActivity.java b/briar-android/src/org/briarproject/android/introduction/IntroductionActivity.java index 8c4e6465243c87fabdb56a27fab183485025dfdd..aeada3f1d1187b954a05a2b2b719bc5d8e559435 100644 --- a/briar-android/src/org/briarproject/android/introduction/IntroductionActivity.java +++ b/briar-android/src/org/briarproject/android/introduction/IntroductionActivity.java @@ -14,6 +14,7 @@ import org.briarproject.android.ActivityComponent; import org.briarproject.android.BriarActivity; import org.briarproject.android.fragment.BaseFragment; import org.briarproject.api.contact.Contact; +import org.briarproject.api.contact.ContactId; // TODO extend the BriarFragmentActivity ? public class IntroductionActivity extends BriarActivity implements @@ -21,16 +22,16 @@ public class IntroductionActivity extends BriarActivity implements public static final String CONTACT_ID = "briar.CONTACT_ID"; - private int contactId; + private ContactId contactId; @Override public void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); Intent intent = getIntent(); - contactId = intent.getIntExtra(CONTACT_ID, -1); - if (contactId == -1) - throw new IllegalArgumentException("Wrong ContactId"); + int id = intent.getIntExtra(CONTACT_ID, -1); + if (id == -1) throw new IllegalStateException("No ContactId"); + contactId = new ContactId(id); setContentView(R.layout.activity_fragment_container); @@ -75,7 +76,7 @@ public class IntroductionActivity extends BriarActivity implements } } - int getContactId() { + ContactId getContactId() { return contactId; } diff --git a/briar-android/src/org/briarproject/android/invitation/AddContactActivity.java b/briar-android/src/org/briarproject/android/invitation/AddContactActivity.java index bec5b346f6e2c1dd711febfcd23a6fb790431471..9a8f592e17243a71c1d9512aff68ca08fcd11b08 100644 --- a/briar-android/src/org/briarproject/android/invitation/AddContactActivity.java +++ b/briar-android/src/org/briarproject/android/invitation/AddContactActivity.java @@ -37,9 +37,13 @@ public class AddContactActivity extends BriarActivity private static final Logger LOG = Logger.getLogger(AddContactActivity.class.getName()); - @Inject protected CryptoComponent crypto; - @Inject protected InvitationTaskFactory invitationTaskFactory; - @Inject protected ReferenceManager referenceManager; + @Inject + CryptoComponent crypto; + @Inject + InvitationTaskFactory invitationTaskFactory; + @Inject + ReferenceManager referenceManager; + private AddContactView view = null; private InvitationTask task = null; private long taskHandle = -1; @@ -52,7 +56,8 @@ public class AddContactActivity extends BriarActivity private String contactName = null; // Fields that are accessed from background threads must be volatile - @Inject protected volatile IdentityManager identityManager; + @Inject + volatile IdentityManager identityManager; @Override public void onCreate(Bundle state) { @@ -150,8 +155,8 @@ public class AddContactActivity extends BriarActivity } @Override - public void onResume() { - super.onResume(); + public void onStart() { + super.onStart(); view.populate(); } diff --git a/briar-android/src/org/briarproject/android/keyagreement/KeyAgreementActivity.java b/briar-android/src/org/briarproject/android/keyagreement/KeyAgreementActivity.java index 8ef2764cf42ea9af3fd483057b866ad38b6bcb86..8a075f151d31e2d13ef6e746f5656eb58512ee6f 100644 --- a/briar-android/src/org/briarproject/android/keyagreement/KeyAgreementActivity.java +++ b/briar-android/src/org/briarproject/android/keyagreement/KeyAgreementActivity.java @@ -40,15 +40,13 @@ public class KeyAgreementActivity extends BriarFragmentActivity implements private static final int STEP_QR = 2; @Inject - protected EventBus eventBus; - - private Toolbar toolbar; + EventBus eventBus; // Fields that are accessed from background threads must be volatile @Inject - protected volatile ContactExchangeTask contactExchangeTask; + volatile ContactExchangeTask contactExchangeTask; @Inject - protected volatile IdentityManager identityManager; + volatile IdentityManager identityManager; @Override public void injectActivity(ActivityComponent component) { @@ -61,7 +59,7 @@ public class KeyAgreementActivity extends BriarFragmentActivity implements super.onCreate(state); setContentView(R.layout.activity_plain); - toolbar = (Toolbar) findViewById(R.id.toolbar); + Toolbar toolbar = (Toolbar) findViewById(R.id.toolbar); setSupportActionBar(toolbar); getSupportActionBar().setDisplayHomeAsUpEnabled(true); @@ -83,14 +81,14 @@ public class KeyAgreementActivity extends BriarFragmentActivity implements } @Override - public void onResume() { - super.onResume(); + public void onStart() { + super.onStart(); eventBus.addListener(this); } @Override - protected void onPause() { - super.onPause(); + protected void onStop() { + super.onStop(); eventBus.removeListener(this); } diff --git a/briar-android/src/org/briarproject/android/keyagreement/ShowQrCodeFragment.java b/briar-android/src/org/briarproject/android/keyagreement/ShowQrCodeFragment.java index cef537288c3c845d24137d380994bed35b9f93d3..fc5d286b0d0406fd017fab8cca3f071c1e8b8b5c 100644 --- a/briar-android/src/org/briarproject/android/keyagreement/ShowQrCodeFragment.java +++ b/briar-android/src/org/briarproject/android/keyagreement/ShowQrCodeFragment.java @@ -162,25 +162,16 @@ public class ShowQrCodeFragment extends BaseEventFragment } else { startListening(); } - } - @Override - public void onResume() { - super.onResume(); openCamera(); } - @Override - public void onPause() { - super.onPause(); - releaseCamera(); - } - @Override public void onStop() { super.onStop(); stopListening(); if (receiver != null) getActivity().unregisterReceiver(receiver); + releaseCamera(); } @UiThread diff --git a/briar-android/src/org/briarproject/android/panic/PanicPreferencesFragment.java b/briar-android/src/org/briarproject/android/panic/PanicPreferencesFragment.java index 094eeaac2b07300a3404637d0c218ec88feede21..f2f69739431231059f03631def954c9c27a45556 100644 --- a/briar-android/src/org/briarproject/android/panic/PanicPreferencesFragment.java +++ b/briar-android/src/org/briarproject/android/panic/PanicPreferencesFragment.java @@ -132,16 +132,16 @@ public class PanicPreferencesFragment extends PreferenceFragmentCompat } @Override - public void onResume() { - super.onResume(); + public void onStart() { + super.onStart(); getPreferenceScreen().getSharedPreferences() .registerOnSharedPreferenceChangeListener(this); showPanicApp(PanicResponder.getTriggerPackageName(getActivity())); } @Override - public void onPause() { - super.onPause(); + public void onStop() { + super.onStop(); getPreferenceScreen().getSharedPreferences() .unregisterOnSharedPreferenceChangeListener(this); } diff --git a/briar-android/src/org/briarproject/android/privategroup/conversation/GroupControllerImpl.java b/briar-android/src/org/briarproject/android/privategroup/conversation/GroupControllerImpl.java index fb0cd8ac59136aa84e4fc01910f5c5ecffb5072a..8a6644efddaebff7b71a226c7631604e28b6f284 100644 --- a/briar-android/src/org/briarproject/android/privategroup/conversation/GroupControllerImpl.java +++ b/briar-android/src/org/briarproject/android/privategroup/conversation/GroupControllerImpl.java @@ -27,8 +27,8 @@ import java.util.logging.Logger; import javax.inject.Inject; -public class GroupControllerImpl - extends ThreadListControllerImpl<PrivateGroup, GroupMessageItem, GroupMessageHeader, GroupMessage> +public class GroupControllerImpl extends + ThreadListControllerImpl<PrivateGroup, GroupMessageItem, GroupMessageHeader, GroupMessage> implements GroupController { private static final Logger LOG = @@ -48,8 +48,8 @@ public class GroupControllerImpl } @Override - public void onActivityResume() { - super.onActivityResume(); + public void onActivityStart() { + super.onActivityStart(); // TODO: Add new notification manager methods for private groups } @@ -101,9 +101,8 @@ public class GroupControllerImpl @Override protected GroupMessage createLocalMessage(String body, long timestamp, @Nullable MessageId parentId, LocalAuthor author) { - return privateGroupManager - .createLocalMessage(getGroupId(), body, timestamp, parentId, - author); + return privateGroupManager.createLocalMessage(getGroupId(), body, + timestamp, parentId, author); } @Override diff --git a/briar-android/src/org/briarproject/android/privategroup/list/GroupItem.java b/briar-android/src/org/briarproject/android/privategroup/list/GroupItem.java index 89b208b00e2638488760fc8a2fd6259099e72933..ac75f29cd57ef089b8cfc0a26306619093dccfd5 100644 --- a/briar-android/src/org/briarproject/android/privategroup/list/GroupItem.java +++ b/briar-android/src/org/briarproject/android/privategroup/list/GroupItem.java @@ -1,56 +1,51 @@ package org.briarproject.android.privategroup.list; +import org.briarproject.api.clients.MessageTracker.GroupCount; import org.briarproject.api.identity.Author; +import org.briarproject.api.nullsafety.NotNullByDefault; import org.briarproject.api.privategroup.GroupMessageHeader; import org.briarproject.api.privategroup.PrivateGroup; import org.briarproject.api.sync.GroupId; -import org.jetbrains.annotations.NotNull; // This class is not thread-safe +@NotNullByDefault class GroupItem { private final PrivateGroup privateGroup; - private int messageCount; - private long lastUpdate; - private int unreadCount; + private int messageCount, unreadCount; + private long timestamp; private boolean dissolved; - GroupItem(@NotNull PrivateGroup privateGroup, int messageCount, - long lastUpdate, int unreadCount, boolean dissolved) { - + GroupItem(PrivateGroup privateGroup, GroupCount count, boolean dissolved) { this.privateGroup = privateGroup; - this.messageCount = messageCount; - this.lastUpdate = lastUpdate; - this.unreadCount = unreadCount; + this.messageCount = count.getMsgCount(); + this.unreadCount = count.getUnreadCount(); + this.timestamp = count.getLatestMsgTime(); this.dissolved = dissolved; } void addMessageHeader(GroupMessageHeader header) { messageCount++; - if (header.getTimestamp() > lastUpdate) { - lastUpdate = header.getTimestamp(); + if (header.getTimestamp() > timestamp) { + timestamp = header.getTimestamp(); } if (!header.isRead()) { unreadCount++; } } - @NotNull PrivateGroup getPrivateGroup() { return privateGroup; } - @NotNull GroupId getId() { return privateGroup.getId(); } - @NotNull Author getCreator() { return privateGroup.getAuthor(); } - @NotNull String getName() { return privateGroup.getName(); } @@ -63,8 +58,8 @@ class GroupItem { return messageCount; } - long getLastUpdate() { - return lastUpdate; + long getTimestamp() { + return timestamp; } int getUnreadCount() { diff --git a/briar-android/src/org/briarproject/android/privategroup/list/GroupListAdapter.java b/briar-android/src/org/briarproject/android/privategroup/list/GroupListAdapter.java index bae48022a7e8599cf4bbeef00f069ee88ed7651c..b5588e3440b559f2fc38989c6b30745c1d8044ff 100644 --- a/briar-android/src/org/briarproject/android/privategroup/list/GroupListAdapter.java +++ b/briar-android/src/org/briarproject/android/privategroup/list/GroupListAdapter.java @@ -38,7 +38,7 @@ class GroupListAdapter extends BriarAdapter<GroupItem, GroupViewHolder> { public int compare(GroupItem a, GroupItem b) { if (a == b) return 0; // The group with the latest message comes first - long aTime = a.getLastUpdate(), bTime = b.getLastUpdate(); + long aTime = a.getTimestamp(), bTime = b.getTimestamp(); if (aTime > bTime) return -1; if (aTime < bTime) return 1; // Break ties by group name @@ -50,7 +50,7 @@ class GroupListAdapter extends BriarAdapter<GroupItem, GroupViewHolder> { @Override public boolean areContentsTheSame(GroupItem a, GroupItem b) { return a.getMessageCount() == b.getMessageCount() && - a.getLastUpdate() == b.getLastUpdate() && + a.getTimestamp() == b.getTimestamp() && a.getUnreadCount() == b.getUnreadCount() && a.isDissolved() == b.isDissolved(); } diff --git a/briar-android/src/org/briarproject/android/privategroup/list/GroupListController.java b/briar-android/src/org/briarproject/android/privategroup/list/GroupListController.java index 27e8c90d4a04104df35a4e26a4bff4b1c3773a97..fbe05315d01fcb316fb57ef3f74b95e27f5d107a 100644 --- a/briar-android/src/org/briarproject/android/privategroup/list/GroupListController.java +++ b/briar-android/src/org/briarproject/android/privategroup/list/GroupListController.java @@ -31,6 +31,7 @@ public interface GroupListController extends DbController { ResultExceptionHandler<Void, DbException> result); interface GroupListListener extends DestroyableContext { + @UiThread void onGroupMessageAdded(GroupMessageHeader header); diff --git a/briar-android/src/org/briarproject/android/privategroup/list/GroupListControllerImpl.java b/briar-android/src/org/briarproject/android/privategroup/list/GroupListControllerImpl.java index 9db84cdcadfa143748c975dce863815075ba0d1c..efa36fe5f2079e2bc818e0d0baad8b53e428d4c7 100644 --- a/briar-android/src/org/briarproject/android/privategroup/list/GroupListControllerImpl.java +++ b/briar-android/src/org/briarproject/android/privategroup/list/GroupListControllerImpl.java @@ -8,6 +8,7 @@ import org.briarproject.android.controller.handler.ResultExceptionHandler; import org.briarproject.api.clients.MessageTracker.GroupCount; import org.briarproject.api.db.DatabaseExecutor; import org.briarproject.api.db.DbException; +import org.briarproject.api.db.NoSuchGroupException; import org.briarproject.api.event.Event; import org.briarproject.api.event.EventBus; import org.briarproject.api.event.EventListener; @@ -16,6 +17,7 @@ import org.briarproject.api.event.GroupMessageAddedEvent; import org.briarproject.api.event.GroupRemovedEvent; import org.briarproject.api.identity.IdentityManager; import org.briarproject.api.lifecycle.LifecycleManager; +import org.briarproject.api.privategroup.GroupMessageHeader; import org.briarproject.api.privategroup.PrivateGroup; import org.briarproject.api.privategroup.PrivateGroupManager; import org.briarproject.api.sync.ClientId; @@ -29,6 +31,7 @@ import java.util.logging.Logger; import javax.inject.Inject; +import static java.util.logging.Level.INFO; import static java.util.logging.Level.WARNING; public class GroupListControllerImpl extends DbControllerImpl @@ -81,59 +84,77 @@ public class GroupListControllerImpl extends DbControllerImpl @CallSuper public void eventOccurred(Event e) { if (e instanceof GroupMessageAddedEvent) { - final GroupMessageAddedEvent m = (GroupMessageAddedEvent) e; - LOG.info("New group message added"); - listener.runOnUiThreadUnlessDestroyed(new Runnable() { - @Override - public void run() { - listener.onGroupMessageAdded(m.getHeader()); - } - }); + GroupMessageAddedEvent g = (GroupMessageAddedEvent) e; + LOG.info("Private group message added"); + onGroupMessageAdded(g.getHeader()); } else if (e instanceof GroupAddedEvent) { - final GroupAddedEvent gae = (GroupAddedEvent) e; - ClientId id = gae.getGroup().getClientId(); + GroupAddedEvent g = (GroupAddedEvent) e; + ClientId id = g.getGroup().getClientId(); if (id.equals(groupManager.getClientId())) { LOG.info("Private group added"); - listener.runOnUiThreadUnlessDestroyed(new Runnable() { - @Override - public void run() { - listener.onGroupAdded(gae.getGroup().getId()); - } - }); + onGroupAdded(g.getGroup().getId()); } } else if (e instanceof GroupRemovedEvent) { - final GroupRemovedEvent gre = (GroupRemovedEvent) e; - ClientId id = gre.getGroup().getClientId(); + GroupRemovedEvent g = (GroupRemovedEvent) e; + ClientId id = g.getGroup().getClientId(); if (id.equals(groupManager.getClientId())) { LOG.info("Private group removed"); - listener.runOnUiThreadUnlessDestroyed(new Runnable() { - @Override - public void run() { - listener.onGroupRemoved(gre.getGroup().getId()); - } - }); + onGroupRemoved(g.getGroup().getId()); } } } + private void onGroupMessageAdded(final GroupMessageHeader h) { + listener.runOnUiThreadUnlessDestroyed(new Runnable() { + @Override + public void run() { + listener.onGroupMessageAdded(h); + } + }); + } + + private void onGroupAdded(final GroupId g) { + listener.runOnUiThreadUnlessDestroyed(new Runnable() { + @Override + public void run() { + listener.onGroupAdded(g); + } + }); + } + + private void onGroupRemoved(final GroupId g) { + listener.runOnUiThreadUnlessDestroyed(new Runnable() { + @Override + public void run() { + listener.onGroupRemoved(g); + } + }); + } + @Override public void loadGroups( final ResultExceptionHandler<Collection<GroupItem>, DbException> handler) { runOnDbThread(new Runnable() { @Override public void run() { - LOG.info("Loading groups from database..."); try { + long now = System.currentTimeMillis(); Collection<PrivateGroup> groups = groupManager.getPrivateGroups(); List<GroupItem> items = new ArrayList<>(groups.size()); for (PrivateGroup g : groups) { - GroupCount c = groupManager.getGroupCount(g.getId()); - boolean dissolved = groupManager.isDissolved(g.getId()); - items.add(new GroupItem(g, c.getMsgCount(), - c.getLatestMsgTime(), c.getUnreadCount(), - dissolved)); + try { + GroupId id = g.getId(); + GroupCount count = groupManager.getGroupCount(id); + boolean dissolved = groupManager.isDissolved(id); + items.add(new GroupItem(g, count, dissolved)); + } catch (NoSuchGroupException e) { + // Continue + } } + long duration = System.currentTimeMillis() - now; + if (LOG.isLoggable(INFO)) + LOG.info("Loading groups took " + duration + " ms"); handler.onResult(items); } catch (DbException e) { if (LOG.isLoggable(WARNING)) @@ -150,9 +171,13 @@ public class GroupListControllerImpl extends DbControllerImpl runOnDbThread(new Runnable() { @Override public void run() { - LOG.info("Removing group from database..."); try { + long now = System.currentTimeMillis(); groupManager.removePrivateGroup(g); + long duration = System.currentTimeMillis() - now; + if (LOG.isLoggable(INFO)) + LOG.info("Removing group took " + duration + " ms"); + handler.onResult(null); } catch (DbException e) { if (LOG.isLoggable(WARNING)) LOG.log(WARNING, e.toString(), e); diff --git a/briar-android/src/org/briarproject/android/privategroup/list/GroupListFragment.java b/briar-android/src/org/briarproject/android/privategroup/list/GroupListFragment.java index bf773c28c654d0be47ad835c51de88d40b1e1947..a786e766c98c70ba1b1456afab2eca3de94548f2 100644 --- a/briar-android/src/org/briarproject/android/privategroup/list/GroupListFragment.java +++ b/briar-android/src/org/briarproject/android/privategroup/list/GroupListFragment.java @@ -1,6 +1,5 @@ package org.briarproject.android.privategroup.list; -import android.content.Intent; import android.os.Bundle; import android.support.annotation.Nullable; import android.support.annotation.UiThread; @@ -16,7 +15,6 @@ import org.briarproject.R; import org.briarproject.android.ActivityComponent; import org.briarproject.android.controller.handler.UiResultExceptionHandler; import org.briarproject.android.fragment.BaseFragment; -import org.briarproject.android.invitation.AddContactActivity; import org.briarproject.android.privategroup.list.GroupListController.GroupListListener; import org.briarproject.android.privategroup.list.GroupViewHolder.OnGroupRemoveClickListener; import org.briarproject.android.view.BriarRecyclerView; @@ -152,12 +150,9 @@ public class GroupListFragment extends BaseFragment implements new UiResultExceptionHandler<Collection<GroupItem>, DbException>( listener) { @Override - public void onResultUi(Collection<GroupItem> result) { - if (result.isEmpty()) { - list.showData(); - } else { - adapter.addAll(result); - } + public void onResultUi(Collection<GroupItem> groups) { + if (groups.isEmpty()) list.showData(); + else adapter.addAll(groups); } @Override diff --git a/briar-android/src/org/briarproject/android/privategroup/list/GroupViewHolder.java b/briar-android/src/org/briarproject/android/privategroup/list/GroupViewHolder.java index c7d59dd1ff12611509016cd1d77a99d17dffa4dd..7f3031aec9f66d0bacbab0ebca4b0be37a014561 100644 --- a/briar-android/src/org/briarproject/android/privategroup/list/GroupViewHolder.java +++ b/briar-android/src/org/briarproject/android/privategroup/list/GroupViewHolder.java @@ -88,7 +88,7 @@ class GroupViewHolder extends RecyclerView.ViewHolder { postCount.setTextColor( getColor(ctx, R.color.briar_text_secondary)); - long lastUpdate = group.getLastUpdate(); + long lastUpdate = group.getTimestamp(); date.setText(AndroidUtils.formatDate(ctx, lastUpdate)); date.setVisibility(VISIBLE); avatar.setProblem(false); diff --git a/briar-android/src/org/briarproject/android/report/DevReportActivity.java b/briar-android/src/org/briarproject/android/report/DevReportActivity.java index 919a0b6200a202cadc10f41f8334e38b3358a3b2..0d142757e17849f0f3069573787e6f2c91711459 100644 --- a/briar-android/src/org/briarproject/android/report/DevReportActivity.java +++ b/briar-android/src/org/briarproject/android/report/DevReportActivity.java @@ -163,8 +163,8 @@ public class DevReportActivity extends BaseCrashReportDialog } @Override - public void onResume() { - super.onResume(); + public void onStart() { + super.onStart(); if (chevron.isSelected()) refresh(); } diff --git a/briar-android/src/org/briarproject/android/sharing/ContactSelectorFragment.java b/briar-android/src/org/briarproject/android/sharing/ContactSelectorFragment.java index 8e270d6407ca27f62a3b4f2d411efa49023230a5..82db75adf15b2ad6ab70e893935628d68601cf9a 100644 --- a/briar-android/src/org/briarproject/android/sharing/ContactSelectorFragment.java +++ b/briar-android/src/org/briarproject/android/sharing/ContactSelectorFragment.java @@ -30,7 +30,6 @@ import org.briarproject.api.sync.GroupId; import java.util.ArrayList; import java.util.Collection; -import java.util.Collections; import java.util.List; import java.util.logging.Logger; @@ -57,11 +56,11 @@ public class ContactSelectorFragment extends BaseFragment implements // Fields that are accessed from background threads must be volatile @Inject - protected volatile ContactManager contactManager; + volatile ContactManager contactManager; @Inject - protected volatile IdentityManager identityManager; + volatile IdentityManager identityManager; @Inject - protected volatile ForumSharingManager forumSharingManager; + volatile ForumSharingManager forumSharingManager; private volatile GroupId groupId; @@ -91,8 +90,9 @@ public class ContactSelectorFragment extends BaseFragment implements setHasOptionsMenu(true); Bundle args = getArguments(); - groupId = new GroupId(args.getByteArray(GROUP_ID)); - if (groupId == null) throw new IllegalStateException("No GroupId"); + byte[] b = args.getByteArray(GROUP_ID); + if (b == null) throw new IllegalStateException("No GroupId"); + groupId = new GroupId(b); } @Override @@ -125,12 +125,16 @@ public class ContactSelectorFragment extends BaseFragment implements } @Override - public void onResume() { - super.onResume(); + public void onStart() { + super.onStart(); + loadContacts(selectedContacts); + } - if (selectedContacts != null) - loadContacts(Collections.unmodifiableCollection(selectedContacts)); - else loadContacts(null); + @Override + public void onStop() { + super.onStop(); + adapter.clear(); + list.showProgressBar(); } @Override @@ -202,9 +206,8 @@ public class ContactSelectorFragment extends BaseFragment implements long duration = System.currentTimeMillis() - now; if (LOG.isLoggable(INFO)) LOG.info("Load took " + duration + " ms"); - displayContacts(Collections.unmodifiableList(contacts)); + displayContacts(contacts); } catch (DbException e) { - displayContacts(Collections.<ContactListItem>emptyList()); if (LOG.isLoggable(WARNING)) LOG.log(WARNING, e.toString(), e); } @@ -216,8 +219,8 @@ public class ContactSelectorFragment extends BaseFragment implements shareActivity.runOnUiThreadUnlessDestroyed(new Runnable() { @Override public void run() { - if (!contacts.isEmpty()) adapter.addAll(contacts); - else list.showData(); + if (contacts.isEmpty()) list.showData(); + else adapter.addAll(contacts); updateMenuItem(); } }); diff --git a/briar-android/src/org/briarproject/android/sharing/InvitationsActivity.java b/briar-android/src/org/briarproject/android/sharing/InvitationsActivity.java index a6b33a0d8c601d32f06ddb3b895df849a7e6a556..fc691ac2b0f725854e3adb70a7caa7202de55b59 100644 --- a/briar-android/src/org/briarproject/android/sharing/InvitationsActivity.java +++ b/briar-android/src/org/briarproject/android/sharing/InvitationsActivity.java @@ -2,6 +2,7 @@ package org.briarproject.android.sharing; import android.content.Context; import android.os.Bundle; +import android.support.annotation.CallSuper; import android.support.v7.widget.LinearLayoutManager; import android.widget.Toast; @@ -42,7 +43,6 @@ abstract class InvitationsActivity extends BriarActivity adapter = getAdapter(this, this); - list = (BriarRecyclerView) findViewById(R.id.list); if (list != null) { list.setLayoutManager(new LinearLayoutManager(this)); @@ -51,21 +51,22 @@ abstract class InvitationsActivity extends BriarActivity } @Override - public void onResume() { - super.onResume(); + public void onStart() { + super.onStart(); eventBus.addListener(this); loadInvitations(false); } @Override - public void onPause() { - super.onPause(); + public void onStop() { + super.onStop(); eventBus.removeListener(this); adapter.clear(); list.showProgressBar(); } @Override + @CallSuper public void eventOccurred(Event e) { if (e instanceof ContactRemovedEvent) { LOG.info("Contact removed, reloading..."); @@ -110,8 +111,8 @@ abstract class InvitationsActivity extends BriarActivity LOG.info("No more invitations available, finishing"); finish(); } else { - if (clear) adapter.clear(); - adapter.addAll(invitations); + if (clear) adapter.setItems(invitations); + else adapter.addAll(invitations); } } }); diff --git a/briar-android/src/org/briarproject/android/sharing/InvitationsBlogActivity.java b/briar-android/src/org/briarproject/android/sharing/InvitationsBlogActivity.java index 58e818269f87af830749632353e88d3abbe9241a..014391d5b6a8940d0ad35109083209ab2bf679fb 100644 --- a/briar-android/src/org/briarproject/android/sharing/InvitationsBlogActivity.java +++ b/briar-android/src/org/briarproject/android/sharing/InvitationsBlogActivity.java @@ -29,9 +29,9 @@ public class InvitationsBlogActivity extends InvitationsActivity { // Fields that are accessed from background threads must be volatile @Inject - protected volatile BlogManager blogManager; + volatile BlogManager blogManager; @Inject - protected volatile BlogSharingManager blogSharingManager; + volatile BlogSharingManager blogSharingManager; @Override public void injectActivity(ActivityComponent component) { @@ -62,31 +62,34 @@ public class InvitationsBlogActivity extends InvitationsActivity { } } + @Override protected InvitationAdapter getAdapter(Context ctx, AvailableForumClickListener listener) { return new BlogInvitationAdapter(ctx, listener); } + @Override protected void loadInvitations(final boolean clear) { runOnDbThread(new Runnable() { @Override public void run() { - Collection<InvitationItem> invitations = new ArrayList<>(); try { + Collection<InvitationItem> invitations = new ArrayList<>(); long now = System.currentTimeMillis(); invitations.addAll(blogSharingManager.getInvitations()); long duration = System.currentTimeMillis() - now; if (LOG.isLoggable(INFO)) LOG.info("Load took " + duration + " ms"); + displayInvitations(invitations, clear); } catch (DbException e) { if (LOG.isLoggable(WARNING)) LOG.log(WARNING, e.toString(), e); } - displayInvitations(invitations, clear); } }); } + @Override protected void respondToInvitation(final InvitationItem item, final boolean accept) { runOnDbThread(new Runnable() { @@ -95,6 +98,7 @@ public class InvitationsBlogActivity extends InvitationsActivity { try { Blog b = (Blog) item.getShareable(); for (Contact c : item.getNewSharers()) { + // TODO: What happens if a contact has been removed? blogSharingManager.respondToInvitation(b, c, accept); } } catch (DbException e) { @@ -105,10 +109,12 @@ public class InvitationsBlogActivity extends InvitationsActivity { }); } + @Override protected int getAcceptRes() { return R.string.blogs_sharing_joined_toast; } + @Override protected int getDeclineRes() { return R.string.blogs_sharing_declined_toast; } diff --git a/briar-android/src/org/briarproject/android/sharing/InvitationsForumActivity.java b/briar-android/src/org/briarproject/android/sharing/InvitationsForumActivity.java index 51ddcc838a73f349f5c40096b6fa089cbe9bf0fb..6b5811eaac51682ddeb9c4c0ac56214b4fcf7539 100644 --- a/briar-android/src/org/briarproject/android/sharing/InvitationsForumActivity.java +++ b/briar-android/src/org/briarproject/android/sharing/InvitationsForumActivity.java @@ -29,9 +29,9 @@ public class InvitationsForumActivity extends InvitationsActivity { // Fields that are accessed from background threads must be volatile @Inject - protected volatile ForumManager forumManager; + volatile ForumManager forumManager; @Inject - protected volatile ForumSharingManager forumSharingManager; + volatile ForumSharingManager forumSharingManager; @Override public void injectActivity(ActivityComponent component) { @@ -62,31 +62,34 @@ public class InvitationsForumActivity extends InvitationsActivity { } } + @Override protected InvitationAdapter getAdapter(Context ctx, AvailableForumClickListener listener) { return new ForumInvitationAdapter(ctx, listener); } + @Override protected void loadInvitations(final boolean clear) { runOnDbThread(new Runnable() { @Override public void run() { - Collection<InvitationItem> invitations = new ArrayList<>(); try { + Collection<InvitationItem> invitations = new ArrayList<>(); long now = System.currentTimeMillis(); invitations.addAll(forumSharingManager.getInvitations()); long duration = System.currentTimeMillis() - now; if (LOG.isLoggable(INFO)) LOG.info("Load took " + duration + " ms"); + displayInvitations(invitations, clear); } catch (DbException e) { if (LOG.isLoggable(WARNING)) LOG.log(WARNING, e.toString(), e); } - displayInvitations(invitations, clear); } }); } + @Override protected void respondToInvitation(final InvitationItem item, final boolean accept) { runOnDbThread(new Runnable() { @@ -95,6 +98,7 @@ public class InvitationsForumActivity extends InvitationsActivity { try { Forum f = (Forum) item.getShareable(); for (Contact c : item.getNewSharers()) { + // TODO: What happens if a contact has been removed? forumSharingManager.respondToInvitation(f, c, accept); } } catch (DbException e) { @@ -105,10 +109,12 @@ public class InvitationsForumActivity extends InvitationsActivity { }); } + @Override protected int getAcceptRes() { return R.string.forum_joined_toast; } + @Override protected int getDeclineRes() { return R.string.forum_declined_toast; } diff --git a/briar-android/src/org/briarproject/android/sharing/SharingStatusActivity.java b/briar-android/src/org/briarproject/android/sharing/SharingStatusActivity.java index 969d525a3fdf2328ec9f0dea1358d0196da94778..377b10d71c52ead6583db71e6d44d92eb5048efa 100644 --- a/briar-android/src/org/briarproject/android/sharing/SharingStatusActivity.java +++ b/briar-android/src/org/briarproject/android/sharing/SharingStatusActivity.java @@ -63,13 +63,21 @@ abstract class SharingStatusActivity extends BriarActivity { } @Override - public void onResume() { - super.onResume(); - + public void onStart() { + super.onStart(); loadSharedBy(); loadSharedWith(); } + @Override + public void onStop() { + super.onStop(); + sharedByAdapter.clear(); + sharedByList.showProgressBar(); + sharedWithAdapter.clear(); + sharedWithList.showProgressBar(); + } + @Override public boolean onOptionsItemSelected(final MenuItem item) { // Handle presses on the action bar items @@ -97,11 +105,11 @@ abstract class SharingStatusActivity extends BriarActivity { } private void loadSharedBy() { - dbController.runOnDbThread(new Runnable() { + runOnDbThread(new Runnable() { @Override public void run() { - List<ContactListItem> contactItems = new ArrayList<>(); try { + List<ContactListItem> contactItems = new ArrayList<>(); for (Contact c : getSharedBy()) { LocalAuthor localAuthor = identityManager .getLocalAuthor(c.getLocalAuthorId()); @@ -110,11 +118,11 @@ abstract class SharingStatusActivity extends BriarActivity { groupId, new GroupCount(0, 0, 0)); contactItems.add(item); } + displaySharedBy(contactItems); } catch (DbException e) { if (LOG.isLoggable(WARNING)) LOG.log(WARNING, e.toString(), e); } - displaySharedBy(contactItems); } }); } @@ -123,21 +131,18 @@ abstract class SharingStatusActivity extends BriarActivity { runOnUiThreadUnlessDestroyed(new Runnable() { @Override public void run() { - if (contacts.isEmpty()) { - sharedByList.showData(); - } else { - sharedByAdapter.addAll(contacts); - } + if (contacts.isEmpty()) sharedByList.showData(); + else sharedByAdapter.addAll(contacts); } }); } private void loadSharedWith() { - dbController.runOnDbThread(new Runnable() { + runOnDbThread(new Runnable() { @Override public void run() { - List<ContactListItem> contactItems = new ArrayList<>(); try { + List<ContactListItem> contactItems = new ArrayList<>(); for (Contact c : getSharedWith()) { LocalAuthor localAuthor = identityManager .getLocalAuthor(c.getLocalAuthorId()); @@ -146,11 +151,11 @@ abstract class SharingStatusActivity extends BriarActivity { groupId, new GroupCount(0, 0, 0)); contactItems.add(item); } + displaySharedWith(contactItems); } catch (DbException e) { if (LOG.isLoggable(WARNING)) LOG.log(WARNING, e.toString(), e); } - displaySharedWith(contactItems); } }); } @@ -159,11 +164,8 @@ abstract class SharingStatusActivity extends BriarActivity { runOnUiThreadUnlessDestroyed(new Runnable() { @Override public void run() { - if (contacts.isEmpty()) { - sharedWithList.showData(); - } else { - sharedWithAdapter.addAll(contacts); - } + if (contacts.isEmpty()) sharedWithList.showData(); + else sharedWithAdapter.addAll(contacts); } }); } diff --git a/briar-android/src/org/briarproject/android/threaded/ThreadListActivity.java b/briar-android/src/org/briarproject/android/threaded/ThreadListActivity.java index 889399525de6ab9a880511dd43789533d65b835d..5ae9b5c6ff72b2bf6b806ac03c467274db965e37 100644 --- a/briar-android/src/org/briarproject/android/threaded/ThreadListActivity.java +++ b/briar-android/src/org/briarproject/android/threaded/ThreadListActivity.java @@ -75,7 +75,7 @@ public abstract class ThreadListActivity<G extends NamedGroup, I extends ThreadI if (state != null) { byte[] replyIdBytes = state.getByteArray(KEY_REPLY_ID); - if(replyIdBytes != null) replyId = new MessageId(replyIdBytes); + if (replyIdBytes != null) replyId = new MessageId(replyIdBytes); } loadItems(); @@ -131,35 +131,33 @@ public abstract class ThreadListActivity<G extends NamedGroup, I extends ThreadI @CallSuper @Override - public void onResume() { - super.onResume(); + public void onStart() { + super.onStart(); list.startPeriodicUpdate(); } @CallSuper @Override - public void onPause() { - super.onPause(); + public void onStop() { + super.onStop(); list.stopPeriodicUpdate(); } @Override protected void onRestoreInstanceState(Bundle savedInstanceState) { super.onRestoreInstanceState(savedInstanceState); - textInput.setVisibility( - savedInstanceState.getBoolean(KEY_INPUT_VISIBILITY) ? - VISIBLE : GONE); + boolean visible = savedInstanceState.getBoolean(KEY_INPUT_VISIBILITY); + textInput.setVisibility(visible ? VISIBLE : GONE); } @Override protected void onSaveInstanceState(Bundle outState) { super.onSaveInstanceState(outState); - outState.putBoolean(KEY_INPUT_VISIBILITY, - textInput.getVisibility() == VISIBLE); + boolean visible = textInput.getVisibility() == VISIBLE; + outState.putBoolean(KEY_INPUT_VISIBILITY, visible); ThreadItem replyItem = adapter.getReplyItem(); if (replyItem != null) { - outState.putByteArray(KEY_REPLY_ID, - replyItem.getId().getBytes()); + outState.putByteArray(KEY_REPLY_ID, replyItem.getId().getBytes()); } } diff --git a/briar-android/src/org/briarproject/android/threaded/ThreadListControllerImpl.java b/briar-android/src/org/briarproject/android/threaded/ThreadListControllerImpl.java index 7dd039dfee74575a790718b7f1010366901a6cf6..80a5b44ea2ab4a968dc897dcd5d6c6f517c7b84a 100644 --- a/briar-android/src/org/briarproject/android/threaded/ThreadListControllerImpl.java +++ b/briar-android/src/org/briarproject/android/threaded/ThreadListControllerImpl.java @@ -49,8 +49,7 @@ public abstract class ThreadListControllerImpl<G extends NamedGroup, I extends T private final EventBus eventBus; private final Clock clock; - private final Map<MessageId, String> bodyCache = - new ConcurrentHashMap<>(); + private final Map<MessageId, String> bodyCache = new ConcurrentHashMap<>(); private volatile GroupId groupId; @@ -82,14 +81,14 @@ public abstract class ThreadListControllerImpl<G extends NamedGroup, I extends T @CallSuper @Override - public void onActivityResume() { + public void onActivityStart() { notificationManager.blockNotification(getGroupId()); eventBus.addListener(this); } @CallSuper @Override - public void onActivityPause() { + public void onActivityStop() { notificationManager.unblockNotification(getGroupId()); eventBus.removeListener(this); } @@ -127,8 +126,7 @@ public abstract class ThreadListControllerImpl<G extends NamedGroup, I extends T G groupItem = loadNamedGroup(); long duration = System.currentTimeMillis() - now; if (LOG.isLoggable(INFO)) - LOG.info( - "Loading named group took " + duration + " ms"); + LOG.info("Loading group took " + duration + " ms"); handler.onResult(groupItem); } catch (DbException e) { if (LOG.isLoggable(WARNING)) @@ -149,7 +147,6 @@ public abstract class ThreadListControllerImpl<G extends NamedGroup, I extends T runOnDbThread(new Runnable() { @Override public void run() { - LOG.info("Loading items..."); try { // Load headers long now = System.currentTimeMillis(); @@ -193,8 +190,8 @@ public abstract class ThreadListControllerImpl<G extends NamedGroup, I extends T runOnDbThread(new Runnable() { @Override public void run() { - LOG.info("Loading item..."); try { + long now = System.currentTimeMillis(); String body; if (!bodyCache.containsKey(header.getId())) { body = loadMessageBody(header.getId()); @@ -202,6 +199,9 @@ public abstract class ThreadListControllerImpl<G extends NamedGroup, I extends T } else { body = bodyCache.get(header.getId()); } + long duration = System.currentTimeMillis() - now; + if (LOG.isLoggable(INFO)) + LOG.info("Loading item took " + duration + " ms"); I item = buildItem(header, body); handler.onResult(item); } catch (DbException e) { @@ -250,12 +250,16 @@ public abstract class ThreadListControllerImpl<G extends NamedGroup, I extends T @Override public void run() { try { + long now = System.currentTimeMillis(); LocalAuthor author = identityManager.getLocalAuthor(); long timestamp = getLatestTimestamp(); - timestamp = - Math.max(timestamp, clock.currentTimeMillis()); - createMessage(body, timestamp, parentId, author, - handler); + timestamp = Math.max(timestamp, clock.currentTimeMillis()); + long duration = System.currentTimeMillis() - now; + if (LOG.isLoggable(INFO)) { + LOG.info("Loading identity and timestamp took " + + duration + " ms"); + } + createMessage(body, timestamp, parentId, author, handler); } catch (DbException e) { if (LOG.isLoggable(WARNING)) LOG.log(WARNING, e.toString(), e); @@ -274,8 +278,11 @@ public abstract class ThreadListControllerImpl<G extends NamedGroup, I extends T cryptoExecutor.execute(new Runnable() { @Override public void run() { - LOG.info("Creating message..."); + long now = System.currentTimeMillis(); M msg = createLocalMessage(body, timestamp, parentId, author); + long duration = System.currentTimeMillis() - now; + if (LOG.isLoggable(INFO)) + LOG.info("Creating message took " + duration + " ms"); storePost(msg, body, handler); } }); @@ -291,7 +298,6 @@ public abstract class ThreadListControllerImpl<G extends NamedGroup, I extends T @Override public void run() { try { - LOG.info("Store message..."); long now = System.currentTimeMillis(); H header = addLocalMessage(msg); bodyCache.put(msg.getMessage().getId(), body); @@ -354,10 +360,7 @@ public abstract class ThreadListControllerImpl<G extends NamedGroup, I extends T } private void checkGroupId() { - if (groupId == null) { - throw new IllegalStateException( - "You must set the GroupId before the controller is started."); - } + if (groupId == null) throw new IllegalStateException(); } } diff --git a/briar-android/src/org/briarproject/android/util/BriarAdapter.java b/briar-android/src/org/briarproject/android/util/BriarAdapter.java index 0385c56c362027dad5ced4167a10ef574657d48d..e9e4b3dbac97de7b4067e1c31905043c46e50c7a 100644 --- a/briar-android/src/org/briarproject/android/util/BriarAdapter.java +++ b/briar-android/src/org/briarproject/android/util/BriarAdapter.java @@ -75,6 +75,13 @@ public abstract class BriarAdapter<T, V extends ViewHolder> this.items.addAll(items); } + public void setItems(Collection<T> items) { + this.items.beginBatchedUpdates(); + this.items.clear(); + this.items.addAll(items); + this.items.endBatchedUpdates(); + } + @Nullable public T getItemAt(int position) { if (position == INVALID_POSITION || position >= items.size()) { diff --git a/briar-api/src/org/briarproject/api/crypto/CryptoExecutor.java b/briar-api/src/org/briarproject/api/crypto/CryptoExecutor.java index 3d531c4e05f6c51d5f0270ae6b8fbc40b2226956..f1002e66b9d424cfbadc7199c65a42bc48911678 100644 --- a/briar-api/src/org/briarproject/api/crypto/CryptoExecutor.java +++ b/briar-api/src/org/briarproject/api/crypto/CryptoExecutor.java @@ -1,17 +1,25 @@ package org.briarproject.api.crypto; -import static java.lang.annotation.ElementType.FIELD; -import static java.lang.annotation.ElementType.METHOD; -import static java.lang.annotation.ElementType.PARAMETER; -import static java.lang.annotation.RetentionPolicy.RUNTIME; - import java.lang.annotation.Retention; import java.lang.annotation.Target; import javax.inject.Qualifier; -/** Annotation for injecting the executor for long-running crypto tasks. */ +import static java.lang.annotation.ElementType.FIELD; +import static java.lang.annotation.ElementType.METHOD; +import static java.lang.annotation.ElementType.PARAMETER; +import static java.lang.annotation.RetentionPolicy.RUNTIME; + +/** + * Annotation for injecting the executor for long-running crypto tasks. Also + * used for annotating methods that should run on the crypto executor. + * <p> + * The contract of this executor is that tasks may be run concurrently, and + * submitting a task will never block. Tasks must not run indefinitely. Tasks + * submitted during shutdown are discarded. + */ @Qualifier @Target({FIELD, METHOD, PARAMETER}) @Retention(RUNTIME) -public @interface CryptoExecutor {} +public @interface CryptoExecutor { +} diff --git a/briar-api/src/org/briarproject/api/db/DatabaseExecutor.java b/briar-api/src/org/briarproject/api/db/DatabaseExecutor.java index f682121d077dea6805e7ac4ecf99827ba3c02bab..5421f451f872684ab02305f42a0261aa87203010 100644 --- a/briar-api/src/org/briarproject/api/db/DatabaseExecutor.java +++ b/briar-api/src/org/briarproject/api/db/DatabaseExecutor.java @@ -1,21 +1,23 @@ package org.briarproject.api.db; -import static java.lang.annotation.ElementType.FIELD; -import static java.lang.annotation.ElementType.METHOD; -import static java.lang.annotation.ElementType.PARAMETER; -import static java.lang.annotation.RetentionPolicy.RUNTIME; - import java.lang.annotation.Retention; import java.lang.annotation.Target; import javax.inject.Qualifier; +import static java.lang.annotation.ElementType.FIELD; +import static java.lang.annotation.ElementType.METHOD; +import static java.lang.annotation.ElementType.PARAMETER; +import static java.lang.annotation.RetentionPolicy.RUNTIME; + /** - * Annotation for injecting the executor for database tasks. + * Annotation for injecting the executor for database tasks. Also used for + * annotating methods that should run on the database executor. * <p> - * The contract of this executor is that tasks are executed in the order - * they're submitted, tasks are not executed concurrently, and submitting a - * task will never block. + * The contract of this executor is that tasks are run in the order they're + * submitted, tasks are not run concurrently, and submitting a task will never + * block. Tasks must not run indefinitely. Tasks submitted during shutdown are + * discarded. */ @Qualifier @Target({ FIELD, METHOD, PARAMETER }) diff --git a/briar-api/src/org/briarproject/api/event/PrivateMessageReceivedEvent.java b/briar-api/src/org/briarproject/api/event/PrivateMessageReceivedEvent.java index 04f7f9164575eadc2021c2286676df01e32e87be..e1ddbfd1942494e2a3079ff4f28148142ecf62f1 100644 --- a/briar-api/src/org/briarproject/api/event/PrivateMessageReceivedEvent.java +++ b/briar-api/src/org/briarproject/api/event/PrivateMessageReceivedEvent.java @@ -1,5 +1,6 @@ package org.briarproject.api.event; +import org.briarproject.api.contact.ContactId; import org.briarproject.api.messaging.PrivateMessageHeader; import org.briarproject.api.sync.GroupId; @@ -9,11 +10,13 @@ import org.briarproject.api.sync.GroupId; public class PrivateMessageReceivedEvent extends Event { private final PrivateMessageHeader messageHeader; + private final ContactId contactId; private final GroupId groupId; public PrivateMessageReceivedEvent(PrivateMessageHeader messageHeader, - GroupId groupId) { + ContactId contactId, GroupId groupId) { this.messageHeader = messageHeader; + this.contactId = contactId; this.groupId = groupId; } @@ -21,6 +24,10 @@ public class PrivateMessageReceivedEvent extends Event { return messageHeader; } + public ContactId getContactId() { + return contactId; + } + public GroupId getGroupId() { return groupId; } diff --git a/briar-api/src/org/briarproject/api/lifecycle/IoExecutor.java b/briar-api/src/org/briarproject/api/lifecycle/IoExecutor.java index 02bc5bf875a941be136b0939a268028739a4d2f4..1bffc3c3cc73c9fa9f32b48c87e65d014c9f5b87 100644 --- a/briar-api/src/org/briarproject/api/lifecycle/IoExecutor.java +++ b/briar-api/src/org/briarproject/api/lifecycle/IoExecutor.java @@ -1,17 +1,25 @@ package org.briarproject.api.lifecycle; -import static java.lang.annotation.ElementType.FIELD; -import static java.lang.annotation.ElementType.METHOD; -import static java.lang.annotation.ElementType.PARAMETER; -import static java.lang.annotation.RetentionPolicy.RUNTIME; - import java.lang.annotation.Retention; import java.lang.annotation.Target; import javax.inject.Qualifier; -/** Annotation for injecting the executor used by long-lived IO tasks. */ +import static java.lang.annotation.ElementType.FIELD; +import static java.lang.annotation.ElementType.METHOD; +import static java.lang.annotation.ElementType.PARAMETER; +import static java.lang.annotation.RetentionPolicy.RUNTIME; + +/** + * Annotation for injecting the executor for long-running IO tasks. Also used + * for annotating methods that should run on the UI executor. + * <p> + * The contract of this executor is that tasks may be run concurrently, and + * submitting a task will never block. Tasks may run indefinitely. Tasks + * submitted during shutdown are discarded. + */ @Qualifier -@Target({ FIELD, METHOD, PARAMETER }) +@Target({FIELD, METHOD, PARAMETER}) @Retention(RUNTIME) -public @interface IoExecutor {} \ No newline at end of file +public @interface IoExecutor { +} \ No newline at end of file diff --git a/briar-core/src/org/briarproject/messaging/MessagingManagerImpl.java b/briar-core/src/org/briarproject/messaging/MessagingManagerImpl.java index 8a591849a24ca5643abf77ce54f12b2340cf8166..a8fa365cb71dcc8f0f7d2dfc705937d1543a0a10 100644 --- a/briar-core/src/org/briarproject/messaging/MessagingManagerImpl.java +++ b/briar-core/src/org/briarproject/messaging/MessagingManagerImpl.java @@ -102,10 +102,11 @@ class MessagingManagerImpl extends ConversationClientImpl boolean local = meta.getBoolean("local"); boolean read = meta.getBoolean(MSG_KEY_READ); PrivateMessageHeader header = new PrivateMessageHeader( - m.getId(), m.getGroupId(), timestamp, contentType, local, read, + m.getId(), groupId, timestamp, contentType, local, read, false, false); + ContactId contactId = getContactId(txn, groupId); PrivateMessageReceivedEvent event = new PrivateMessageReceivedEvent( - header, groupId); + header, contactId, groupId); txn.attach(event); trackIncomingMessage(txn, m); @@ -133,6 +134,17 @@ class MessagingManagerImpl extends ConversationClientImpl } } + private ContactId getContactId(Transaction txn, GroupId g) + throws DbException { + try { + BdfDictionary meta = + clientHelper.getGroupMetadataAsDictionary(txn, g); + return new ContactId(meta.getLong("contactId").intValue()); + } catch (FormatException e) { + throw new DbException(e); + } + } + @Override public ContactId getContactId(GroupId g) throws DbException { try {