Wip: Work on enabling accounts from accounts fragment

This commit is contained in:
Paul Schaub 2020-05-16 17:13:51 +02:00
parent 44d066117d
commit 10ed534876
Signed by: vanitasvitae
GPG Key ID: 62BEE9264BF17311
11 changed files with 54 additions and 60 deletions

View File

@ -64,14 +64,8 @@ public class AccountsFragment extends Fragment {
}
private void observeViewModel() {
viewModel.getConnectionPool().observe(this, pool -> {
Collection<ConnectionState> connectionStateList = pool.getConnectionStates().values();
List<MercuryConnection> connections = new ArrayList<>(connectionStateList.size());
for (ConnectionState state : connectionStateList) {
connections.add(state.getConnection());
}
adapter.setValues(connections);
});
viewModel.getConnectionPool().observe(this, pool ->
adapter.setValues(new ArrayList<>(pool.getConnectionStates().values())));
}
@Override

View File

@ -7,7 +7,6 @@ import android.widget.ImageView;
import android.widget.Switch;
import android.widget.TextView;
import androidx.annotation.NonNull;
import androidx.recyclerview.widget.DiffUtil;
import androidx.recyclerview.widget.RecyclerView;
@ -18,15 +17,14 @@ import org.mercury_im.messenger.ui.avatar.AvatarDrawable;
import org.mercury_im.messenger.ui.account.AccountsFragment.OnAccountListItemClickListener;
import org.mercury_im.messenger.util.AbstractDiffCallback;
import org.mercury_im.messenger.xmpp.MercuryConnection;
import org.mercury_im.messenger.xmpp.state.ConnectionState;
import java.util.ArrayList;
import java.util.List;
import io.reactivex.android.schedulers.AndroidSchedulers;
public class AccountsRecyclerViewAdapter extends RecyclerView.Adapter<AccountsRecyclerViewAdapter.ViewHolder> {
private final List<MercuryConnection> connections = new ArrayList<>();
private final List<ConnectionState> connectionStates = new ArrayList<>();
private final OnAccountListItemClickListener onAccountClickListener;
private final AccountsViewModel viewModel;
@ -43,22 +41,23 @@ public class AccountsRecyclerViewAdapter extends RecyclerView.Adapter<AccountsRe
return new ViewHolder(view);
}
public void setValues(List<MercuryConnection> values) {
public void setValues(List<ConnectionState> values) {
DiffUtil.DiffResult diffResult = DiffUtil.calculateDiff(
new AccountsDiffCallback(values, connections), true);
connections.clear();
connections.addAll(values);
new AccountsDiffCallback(values, connectionStates), true);
connectionStates.clear();
connectionStates.addAll(values);
diffResult.dispatchUpdatesTo(this);
}
@Override
public int getItemCount() {
return connections.size();
return connectionStates.size();
}
@Override
public void onBindViewHolder(final ViewHolder holder, int position) {
MercuryConnection connection = connections.get(position);
ConnectionState state = connectionStates.get(position);
MercuryConnection connection = state.getConnection();
Account account = connection.getAccount();
holder.account = account;
@ -67,23 +66,7 @@ public class AccountsRecyclerViewAdapter extends RecyclerView.Adapter<AccountsRe
holder.enabled.setChecked(account.isEnabled());
holder.enabled.setOnCheckedChangeListener((compoundButton, checked) ->
viewModel.setAccountEnabled(account, checked));
setClickListenersOnViewHolder(holder);
}
private void setClickListenersOnViewHolder(ViewHolder holder) {
holder.mView.setOnClickListener(v -> {
if (null != onAccountClickListener) {
onAccountClickListener.onAccountListItemClick(holder.account);
}
});
holder.mView.setOnLongClickListener(v -> {
if (null != onAccountClickListener) {
onAccountClickListener.onAccountListItemLongClick(holder.account);
}
return true;
});
holder.status.setText(state.getConnectivity().toString());
}
class ViewHolder extends RecyclerView.ViewHolder {
@ -104,21 +87,22 @@ public class AccountsRecyclerViewAdapter extends RecyclerView.Adapter<AccountsRe
}
}
public class AccountsDiffCallback extends AbstractDiffCallback<MercuryConnection> {
public class AccountsDiffCallback extends AbstractDiffCallback<ConnectionState> {
public AccountsDiffCallback(List<MercuryConnection> newItems, List<MercuryConnection> oldItems) {
public AccountsDiffCallback(List<ConnectionState> newItems, List<ConnectionState> oldItems) {
super(newItems, oldItems);
}
@Override
public boolean areItemsTheSame(int oldItemPosition, int newItemPosition) {
return oldItems.get(oldItemPosition).getAccount().getId().equals(newItems.get(newItemPosition).getAccount().getId());
return oldItems.get(oldItemPosition).getConnection().getAccount().getId()
.equals(newItems.get(newItemPosition).getConnection().getAccount().getId());
}
@Override
public boolean areContentsTheSame(int oldItemPosition, int newItemPosition) {
Account oldM = oldItems.get(oldItemPosition).getAccount();
Account newM = newItems.get(newItemPosition).getAccount();
ConnectionState oldM = oldItems.get(oldItemPosition);
ConnectionState newM = newItems.get(newItemPosition);
return oldM.equals(newM);
}
}

View File

@ -10,11 +10,17 @@ import org.mercury_im.messenger.MercuryImApplication;
import org.mercury_im.messenger.Messenger;
import org.mercury_im.messenger.data.repository.AccountRepository;
import org.mercury_im.messenger.entity.Account;
import org.mercury_im.messenger.xmpp.MercuryConnection;
import org.mercury_im.messenger.xmpp.exception.InvalidCredentialsException;
import org.mercury_im.messenger.xmpp.exception.ServerUnreachableException;
import org.mercury_im.messenger.xmpp.state.ConnectionPoolState;
import javax.inject.Inject;
import io.reactivex.Scheduler;
import io.reactivex.android.schedulers.AndroidSchedulers;
import io.reactivex.disposables.CompositeDisposable;
import io.reactivex.schedulers.Schedulers;
public class AccountsViewModel extends AndroidViewModel {
@ -54,5 +60,17 @@ public class AccountsViewModel extends AndroidViewModel {
accountModel.setEnabled(enabled);
repository.upsertAccount(accountModel)
.subscribe();
MercuryConnection connection = messenger.getConnectionManager().getConnection(accountModel);
if (connection != null) {
if (enabled) {
connection.connect()
.andThen(connection.login())
.subscribeOn(Schedulers.newThread())
.observeOn(AndroidSchedulers.mainThread())
.subscribe();
} else {
connection.shutdown();
}
}
}
}

View File

@ -24,6 +24,7 @@ import java.util.logging.Logger;
import javax.inject.Inject;
import io.reactivex.Completable;
import io.reactivex.Scheduler;
import io.reactivex.android.schedulers.AndroidSchedulers;
import io.reactivex.disposables.CompositeDisposable;
import io.reactivex.schedulers.Schedulers;
@ -88,9 +89,8 @@ public class LoginViewModel extends AndroidViewModel {
account.setAddress(username.asUnescapedString());
account.setPassword(password);
MercuryConnection connection = messenger.getConnectionManager().createConnection(account);
disposable.add(Completable.fromAction(() -> {
connection.connect().login();
})
disposable.add(connection.connect()
.andThen(connection.login())
.subscribeOn(Schedulers.newThread())
.observeOn(AndroidSchedulers.mainThread())
.doOnComplete(this::signalLoginSuccessful)

View File

@ -16,6 +16,7 @@ import java.io.IOException;
import java.util.UUID;
import java.util.logging.Logger;
import io.reactivex.Completable;
import io.reactivex.Observable;
import io.reactivex.subjects.BehaviorSubject;
import lombok.Getter;
@ -48,19 +49,17 @@ public class MercuryConnection {
return state;
}
public MercuryConnection connect() throws ServerUnreachableException {
public Completable connect() {
if (getConnection().isConnected()) {
return this;
return Completable.complete();
}
doConnect();
return this;
return Completable.fromAction(this::doConnect);
}
private MercuryConnection doConnect() throws ServerUnreachableException {
private void doConnect() throws ServerUnreachableException {
AbstractXMPPConnection connection = (AbstractXMPPConnection) getConnection();
try {
connection.connect();
return this;
} catch (SmackException.EndpointConnectionException e) {
connection.disconnect();
throw new ServerUnreachableException("Cannot connect to server " + connection.getXMPPServiceDomain().asUnescapedString(), e);
@ -69,16 +68,15 @@ public class MercuryConnection {
}
}
public void login() throws ServerUnreachableException, InvalidCredentialsException {
public Completable login() {
if (getConnection().isAuthenticated()) {
return;
return Completable.complete();
}
doLogin();
return Completable.fromAction(this::doLogin);
}
private void doLogin() throws InvalidCredentialsException, ServerUnreachableException {
try {
connect();
((AbstractXMPPConnection) getConnection()).login();
} catch (SASLErrorException e) {
throw new InvalidCredentialsException("Credentials of account " + account.getId() + " are invalid.", e);

View File

@ -1,16 +1,17 @@
package org.mercury_im.messenger.xmpp.state;
import org.jivesoftware.smack.XMPPConnection;
import org.mercury_im.messenger.xmpp.MercuryConnection;
import java.util.UUID;
import lombok.EqualsAndHashCode;
import lombok.ToString;
import lombok.Value;
import lombok.With;
@Value
@ToString
@EqualsAndHashCode
public class ConnectionState {
UUID id;

View File

@ -5,11 +5,13 @@ import org.mercury_im.messenger.entity.contact.Peer;
import java.util.Set;
import lombok.Data;
import lombok.EqualsAndHashCode;
/**
* An interface that describes a group chat entity.
*/
@Data
@EqualsAndHashCode(callSuper = true)
public class GroupChat extends Chat {
Set<Peer> participants;
String roomAddress;

View File

@ -4,9 +4,7 @@ import java.util.Date;
import java.util.List;
import java.util.UUID;
import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.With;
@Data
public class Message {

View File

@ -6,7 +6,7 @@
# http://www.gradle.org/docs/current/userguide/build_environment.html
# Specifies the JVM arguments used for the daemon process.
# The setting is particularly useful for tweaking memory settings.
android.enableJetifier=true
android.enableJetifier=false
android.useAndroidX=true
org.gradle.jvmargs=-Xmx1536m
# When configured, Gradle will run in incubating parallel mode.

@ -1 +1 @@
Subproject commit e79710840be6d6b3301e078a23688eafaa06013c
Subproject commit f00acbff891ba0edd0a51e7147e0e07d0de7e4b5

View File

@ -1,7 +1,6 @@
ext {
apply from: 'libs/Smack/version.gradle'
shortVersion = 1
// Smack Versions
// Quickly switch between unique and normal releases using the toggle below