mirror of
https://github.com/nextcloud/talk-android
synced 2025-06-20 03:59:35 +01:00
Merge pull request #1922 from nextcloud/bugfix/noid/kotlinConversion5
Migrate OperationsMenuController to kotlin
This commit is contained in:
commit
4c199b1369
@ -1,808 +0,0 @@
|
|||||||
/*
|
|
||||||
* Nextcloud Talk application
|
|
||||||
*
|
|
||||||
* @author Mario Danic
|
|
||||||
* Copyright (C) 2017 Mario Danic <mario@lovelyhq.com>
|
|
||||||
*
|
|
||||||
* This program is free software: you can redistribute it and/or modify
|
|
||||||
* it under the terms of the GNU General Public License as published by
|
|
||||||
* the Free Software Foundation, either version 3 of the License, or
|
|
||||||
* at your option) any later version.
|
|
||||||
*
|
|
||||||
* This program is distributed in the hope that it will be useful,
|
|
||||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
||||||
* GNU General Public License for more details.
|
|
||||||
*
|
|
||||||
* You should have received a copy of the GNU General Public License
|
|
||||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
|
||||||
*/
|
|
||||||
|
|
||||||
package com.nextcloud.talk.controllers.bottomsheet;
|
|
||||||
|
|
||||||
import static com.nextcloud.talk.controllers.bottomsheet.ConversationOperationEnum.OPS_CODE_JOIN_ROOM;
|
|
||||||
import static com.nextcloud.talk.controllers.bottomsheet.ConversationOperationEnum.OPS_CODE_REMOVE_FAVORITE;
|
|
||||||
|
|
||||||
import android.annotation.SuppressLint;
|
|
||||||
import android.content.Intent;
|
|
||||||
import android.net.Uri;
|
|
||||||
import android.os.Bundle;
|
|
||||||
import android.text.TextUtils;
|
|
||||||
import android.util.Log;
|
|
||||||
import android.view.LayoutInflater;
|
|
||||||
import android.view.View;
|
|
||||||
import android.view.ViewGroup;
|
|
||||||
import android.widget.Button;
|
|
||||||
import android.widget.ImageView;
|
|
||||||
import android.widget.ProgressBar;
|
|
||||||
import android.widget.TextView;
|
|
||||||
|
|
||||||
import com.bluelinelabs.conductor.RouterTransaction;
|
|
||||||
import com.bluelinelabs.conductor.changehandler.HorizontalChangeHandler;
|
|
||||||
import com.bluelinelabs.logansquare.LoganSquare;
|
|
||||||
import com.nextcloud.talk.R;
|
|
||||||
import com.nextcloud.talk.api.NcApi;
|
|
||||||
import com.nextcloud.talk.application.NextcloudTalkApplication;
|
|
||||||
import com.nextcloud.talk.controllers.base.BaseController;
|
|
||||||
import com.nextcloud.talk.events.ConversationsListFetchDataEvent;
|
|
||||||
import com.nextcloud.talk.events.OpenConversationEvent;
|
|
||||||
import com.nextcloud.talk.models.RetrofitBucket;
|
|
||||||
import com.nextcloud.talk.models.database.CapabilitiesUtil;
|
|
||||||
import com.nextcloud.talk.models.database.UserEntity;
|
|
||||||
import com.nextcloud.talk.models.json.capabilities.Capabilities;
|
|
||||||
import com.nextcloud.talk.models.json.capabilities.CapabilitiesOverall;
|
|
||||||
import com.nextcloud.talk.models.json.conversations.Conversation;
|
|
||||||
import com.nextcloud.talk.models.json.conversations.RoomOverall;
|
|
||||||
import com.nextcloud.talk.models.json.generic.GenericOverall;
|
|
||||||
import com.nextcloud.talk.models.json.participants.AddParticipantOverall;
|
|
||||||
import com.nextcloud.talk.utils.ApiUtils;
|
|
||||||
import com.nextcloud.talk.utils.DisplayUtils;
|
|
||||||
import com.nextcloud.talk.utils.NoSupportedApiException;
|
|
||||||
import com.nextcloud.talk.utils.bundle.BundleKeys;
|
|
||||||
import com.nextcloud.talk.utils.database.user.UserUtils;
|
|
||||||
import com.nextcloud.talk.utils.singletons.ApplicationWideMessageHolder;
|
|
||||||
|
|
||||||
import org.greenrobot.eventbus.EventBus;
|
|
||||||
import org.parceler.Parcels;
|
|
||||||
|
|
||||||
import java.io.IOException;
|
|
||||||
import java.util.ArrayList;
|
|
||||||
|
|
||||||
import javax.inject.Inject;
|
|
||||||
|
|
||||||
import androidx.annotation.NonNull;
|
|
||||||
import autodagger.AutoInjector;
|
|
||||||
import butterknife.BindView;
|
|
||||||
import io.reactivex.Observer;
|
|
||||||
import io.reactivex.android.schedulers.AndroidSchedulers;
|
|
||||||
import io.reactivex.disposables.Disposable;
|
|
||||||
import io.reactivex.schedulers.Schedulers;
|
|
||||||
import retrofit2.HttpException;
|
|
||||||
import retrofit2.Response;
|
|
||||||
|
|
||||||
@AutoInjector(NextcloudTalkApplication.class)
|
|
||||||
public class OperationsMenuController extends BaseController {
|
|
||||||
|
|
||||||
private static final String TAG = "OperationsMenuController";
|
|
||||||
|
|
||||||
@BindView(R.id.progress_bar)
|
|
||||||
ProgressBar progressBar;
|
|
||||||
|
|
||||||
@BindView(R.id.result_image_view)
|
|
||||||
ImageView resultImageView;
|
|
||||||
|
|
||||||
@BindView(R.id.result_text_view)
|
|
||||||
TextView resultsTextView;
|
|
||||||
|
|
||||||
@BindView(R.id.ok_button)
|
|
||||||
Button okButton;
|
|
||||||
|
|
||||||
@BindView(R.id.web_button)
|
|
||||||
Button webButton;
|
|
||||||
|
|
||||||
@Inject
|
|
||||||
NcApi ncApi;
|
|
||||||
|
|
||||||
@Inject
|
|
||||||
UserUtils userUtils;
|
|
||||||
|
|
||||||
@Inject
|
|
||||||
EventBus eventBus;
|
|
||||||
|
|
||||||
private ConversationOperationEnum operation;
|
|
||||||
private Conversation conversation;
|
|
||||||
|
|
||||||
private UserEntity currentUser;
|
|
||||||
private String callPassword;
|
|
||||||
private String callUrl;
|
|
||||||
|
|
||||||
private String baseUrl;
|
|
||||||
private String conversationToken;
|
|
||||||
|
|
||||||
private Disposable disposable;
|
|
||||||
|
|
||||||
private Conversation.ConversationType conversationType;
|
|
||||||
private ArrayList<String> invitedUsers = new ArrayList<>();
|
|
||||||
private ArrayList<String> invitedGroups = new ArrayList<>();
|
|
||||||
|
|
||||||
private Capabilities serverCapabilities;
|
|
||||||
private String credentials;
|
|
||||||
private String conversationName;
|
|
||||||
|
|
||||||
public OperationsMenuController(Bundle args) {
|
|
||||||
super(args);
|
|
||||||
this.operation = (ConversationOperationEnum) args.getSerializable(BundleKeys.INSTANCE.getKEY_OPERATION_CODE());
|
|
||||||
if (args.containsKey(BundleKeys.INSTANCE.getKEY_ROOM())) {
|
|
||||||
this.conversation = Parcels.unwrap(args.getParcelable(BundleKeys.INSTANCE.getKEY_ROOM()));
|
|
||||||
}
|
|
||||||
|
|
||||||
this.callPassword = args.getString(BundleKeys.INSTANCE.getKEY_CONVERSATION_PASSWORD(), "");
|
|
||||||
this.callUrl = args.getString(BundleKeys.INSTANCE.getKEY_CALL_URL(), "");
|
|
||||||
|
|
||||||
if (args.containsKey(BundleKeys.INSTANCE.getKEY_INVITED_PARTICIPANTS())) {
|
|
||||||
this.invitedUsers = args.getStringArrayList(BundleKeys.INSTANCE.getKEY_INVITED_PARTICIPANTS());
|
|
||||||
}
|
|
||||||
|
|
||||||
if (args.containsKey(BundleKeys.INSTANCE.getKEY_INVITED_GROUP())) {
|
|
||||||
this.invitedGroups = args.getStringArrayList(BundleKeys.INSTANCE.getKEY_INVITED_GROUP());
|
|
||||||
}
|
|
||||||
|
|
||||||
if (args.containsKey(BundleKeys.INSTANCE.getKEY_CONVERSATION_TYPE())) {
|
|
||||||
this.conversationType = Parcels.unwrap(args.getParcelable(BundleKeys.INSTANCE.getKEY_CONVERSATION_TYPE()));
|
|
||||||
}
|
|
||||||
|
|
||||||
if (args.containsKey(BundleKeys.INSTANCE.getKEY_SERVER_CAPABILITIES())) {
|
|
||||||
this.serverCapabilities = Parcels.unwrap(args.getParcelable(BundleKeys.INSTANCE.getKEY_SERVER_CAPABILITIES()));
|
|
||||||
}
|
|
||||||
|
|
||||||
this.conversationName = args.getString(BundleKeys.INSTANCE.getKEY_CONVERSATION_NAME(), "");
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
@NonNull
|
|
||||||
@Override
|
|
||||||
protected View inflateView(@NonNull LayoutInflater inflater, @NonNull ViewGroup container) {
|
|
||||||
return inflater.inflate(R.layout.controller_operations_menu, container, false);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected void onViewBound(@NonNull View view) {
|
|
||||||
super.onViewBound(view);
|
|
||||||
NextcloudTalkApplication.Companion.getSharedApplication().getComponentApplication().inject(this);
|
|
||||||
|
|
||||||
currentUser = userUtils.getCurrentUser();
|
|
||||||
if (!TextUtils.isEmpty(callUrl) && callUrl.contains("/call")) {
|
|
||||||
conversationToken = callUrl.substring(callUrl.lastIndexOf("/") + 1);
|
|
||||||
if (callUrl.contains("/index.php")) {
|
|
||||||
baseUrl = callUrl.substring(0, callUrl.indexOf("/index.php"));
|
|
||||||
} else {
|
|
||||||
baseUrl = callUrl.substring(0, callUrl.indexOf("/call"));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!TextUtils.isEmpty(baseUrl) && !baseUrl.equals(currentUser.getBaseUrl())) {
|
|
||||||
if (serverCapabilities != null) {
|
|
||||||
try {
|
|
||||||
useBundledCapabilitiesForGuest();
|
|
||||||
} catch (IOException e) {
|
|
||||||
// Fall back to fetching capabilities again
|
|
||||||
fetchCapabilitiesForGuest();
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
fetchCapabilitiesForGuest();
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
processOperation();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
@SuppressLint("LongLogTag")
|
|
||||||
private void useBundledCapabilitiesForGuest() throws IOException {
|
|
||||||
currentUser = new UserEntity();
|
|
||||||
currentUser.setBaseUrl(baseUrl);
|
|
||||||
currentUser.setUserId("?");
|
|
||||||
try {
|
|
||||||
currentUser.setCapabilities(LoganSquare.serialize(serverCapabilities));
|
|
||||||
} catch (IOException e) {
|
|
||||||
Log.e("OperationsMenu", "Failed to serialize capabilities");
|
|
||||||
throw e;
|
|
||||||
}
|
|
||||||
|
|
||||||
try {
|
|
||||||
checkCapabilities(currentUser);
|
|
||||||
processOperation();
|
|
||||||
} catch (NoSupportedApiException e) {
|
|
||||||
showResultImage(false, false);
|
|
||||||
Log.d(TAG, "No supported server version found", e);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@SuppressLint("LongLogTag")
|
|
||||||
private void fetchCapabilitiesForGuest() {
|
|
||||||
ncApi.getCapabilities(null, ApiUtils.getUrlForCapabilities(baseUrl))
|
|
||||||
.subscribeOn(Schedulers.io())
|
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
|
||||||
.subscribe(new Observer<CapabilitiesOverall>() {
|
|
||||||
@Override
|
|
||||||
public void onSubscribe(@io.reactivex.annotations.NonNull Disposable d) {
|
|
||||||
}
|
|
||||||
|
|
||||||
@SuppressLint("LongLogTag")
|
|
||||||
@Override
|
|
||||||
public void onNext(@io.reactivex.annotations.NonNull CapabilitiesOverall capabilitiesOverall) {
|
|
||||||
currentUser = new UserEntity();
|
|
||||||
currentUser.setBaseUrl(baseUrl);
|
|
||||||
currentUser.setUserId("?");
|
|
||||||
try {
|
|
||||||
currentUser.setCapabilities(
|
|
||||||
LoganSquare
|
|
||||||
.serialize(
|
|
||||||
capabilitiesOverall
|
|
||||||
.getOcs()
|
|
||||||
.getData()
|
|
||||||
.getCapabilities()));
|
|
||||||
} catch (IOException e) {
|
|
||||||
Log.e("OperationsMenu", "Failed to serialize capabilities");
|
|
||||||
}
|
|
||||||
|
|
||||||
try {
|
|
||||||
checkCapabilities(currentUser);
|
|
||||||
processOperation();
|
|
||||||
} catch (NoSupportedApiException e) {
|
|
||||||
showResultImage(false, false);
|
|
||||||
Log.d(TAG, "No supported server version found", e);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@SuppressLint("LongLogTag")
|
|
||||||
@Override
|
|
||||||
public void onError(@io.reactivex.annotations.NonNull Throwable e) {
|
|
||||||
showResultImage(false, false);
|
|
||||||
Log.e(TAG, "Error fetching capabilities for guest", e);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onComplete() {
|
|
||||||
|
|
||||||
}
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
@SuppressLint("LongLogTag")
|
|
||||||
private void processOperation() {
|
|
||||||
RoomOperationsObserver roomOperationsObserver = new RoomOperationsObserver();
|
|
||||||
GenericOperationsObserver genericOperationsObserver = new GenericOperationsObserver();
|
|
||||||
|
|
||||||
if (currentUser == null) {
|
|
||||||
showResultImage(false, true);
|
|
||||||
Log.e(TAG, "Ended up in processOperation without a valid currentUser");
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
credentials = ApiUtils.getCredentials(currentUser.getUsername(), currentUser.getToken());
|
|
||||||
int apiVersion = ApiUtils.getConversationApiVersion(currentUser, new int[] {ApiUtils.APIv4, ApiUtils.APIv1});
|
|
||||||
int chatApiVersion = ApiUtils.getChatApiVersion(currentUser, new int[] {ApiUtils.APIv1});
|
|
||||||
|
|
||||||
switch (operation) {
|
|
||||||
case OPS_CODE_RENAME_ROOM:
|
|
||||||
ncApi.renameRoom(credentials, ApiUtils.getUrlForRoom(apiVersion, currentUser.getBaseUrl(),
|
|
||||||
conversation.getToken()),
|
|
||||||
conversation.getName())
|
|
||||||
.subscribeOn(Schedulers.io())
|
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
|
||||||
.retry(1)
|
|
||||||
.subscribe(genericOperationsObserver);
|
|
||||||
break;
|
|
||||||
case OPS_CODE_MAKE_PUBLIC:
|
|
||||||
ncApi.makeRoomPublic(credentials, ApiUtils.getUrlForRoomPublic(apiVersion, currentUser.getBaseUrl(),
|
|
||||||
conversation.getToken()))
|
|
||||||
.subscribeOn(Schedulers.io())
|
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
|
||||||
.retry(1)
|
|
||||||
.subscribe(genericOperationsObserver);
|
|
||||||
break;
|
|
||||||
case OPS_CODE_CHANGE_PASSWORD:
|
|
||||||
case OPS_CODE_CLEAR_PASSWORD:
|
|
||||||
case OPS_CODE_SET_PASSWORD:
|
|
||||||
String pass = "";
|
|
||||||
if (conversation.getPassword() != null) {
|
|
||||||
pass = conversation.getPassword();
|
|
||||||
}
|
|
||||||
ncApi.setPassword(credentials, ApiUtils.getUrlForRoomPassword(apiVersion, currentUser.getBaseUrl(),
|
|
||||||
conversation.getToken()), pass)
|
|
||||||
.subscribeOn(Schedulers.io())
|
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
|
||||||
.retry(1)
|
|
||||||
.subscribe(genericOperationsObserver);
|
|
||||||
break;
|
|
||||||
case OPS_CODE_MAKE_PRIVATE:
|
|
||||||
ncApi.makeRoomPrivate(credentials, ApiUtils.getUrlForRoomPublic(apiVersion,
|
|
||||||
currentUser.getBaseUrl(),
|
|
||||||
conversation.getToken()))
|
|
||||||
.subscribeOn(Schedulers.io())
|
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
|
||||||
.retry(1)
|
|
||||||
.subscribe(genericOperationsObserver);
|
|
||||||
break;
|
|
||||||
case OPS_CODE_GET_AND_JOIN_ROOM:
|
|
||||||
ncApi.getRoom(credentials, ApiUtils.getUrlForRoom(apiVersion, baseUrl, conversationToken))
|
|
||||||
.subscribeOn(Schedulers.io())
|
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
|
||||||
.retry(1)
|
|
||||||
.subscribe(new Observer<RoomOverall>() {
|
|
||||||
@Override
|
|
||||||
public void onSubscribe(@io.reactivex.annotations.NonNull Disposable d) {
|
|
||||||
disposable = d;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onNext(@io.reactivex.annotations.NonNull RoomOverall roomOverall) {
|
|
||||||
conversation = roomOverall.getOcs().getData();
|
|
||||||
if (conversation.isHasPassword() && conversation.isGuest()) {
|
|
||||||
eventBus.post(new ConversationsListFetchDataEvent());
|
|
||||||
Bundle bundle = new Bundle();
|
|
||||||
bundle.putParcelable(BundleKeys.INSTANCE.getKEY_ROOM(), Parcels.wrap(conversation));
|
|
||||||
bundle.putString(BundleKeys.INSTANCE.getKEY_CALL_URL(), callUrl);
|
|
||||||
try {
|
|
||||||
bundle.putParcelable(BundleKeys.INSTANCE.getKEY_SERVER_CAPABILITIES(),
|
|
||||||
Parcels.wrap(LoganSquare.parse(currentUser.getCapabilities(),
|
|
||||||
Capabilities.class)));
|
|
||||||
} catch (IOException e) {
|
|
||||||
Log.e(TAG, "Failed to parse capabilities for guest");
|
|
||||||
showResultImage(false, false);
|
|
||||||
}
|
|
||||||
bundle.putSerializable(BundleKeys.INSTANCE.getKEY_OPERATION_CODE(), OPS_CODE_JOIN_ROOM);
|
|
||||||
getRouter().pushController(RouterTransaction.with(new EntryMenuController(bundle))
|
|
||||||
.pushChangeHandler(new HorizontalChangeHandler())
|
|
||||||
.popChangeHandler(new HorizontalChangeHandler()));
|
|
||||||
} else if (conversation.isGuest()) {
|
|
||||||
ncApi.joinRoom(credentials, ApiUtils.getUrlForParticipantsActive(apiVersion,
|
|
||||||
baseUrl,
|
|
||||||
conversationToken), null)
|
|
||||||
.subscribeOn(Schedulers.io())
|
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
|
||||||
.subscribe(new Observer<RoomOverall>() {
|
|
||||||
@Override
|
|
||||||
public void onSubscribe(
|
|
||||||
@io.reactivex.annotations.NonNull Disposable d
|
|
||||||
) {
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onNext(
|
|
||||||
@io.reactivex.annotations.NonNull RoomOverall roomOverall
|
|
||||||
) {
|
|
||||||
conversation = roomOverall.getOcs().getData();
|
|
||||||
initiateConversation();
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onError(@io.reactivex.annotations.NonNull Throwable e) {
|
|
||||||
showResultImage(false, false);
|
|
||||||
dispose();
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onComplete() {
|
|
||||||
}
|
|
||||||
});
|
|
||||||
} else {
|
|
||||||
initiateConversation();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onError(@io.reactivex.annotations.NonNull Throwable e) {
|
|
||||||
showResultImage(false, false);
|
|
||||||
dispose();
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onComplete() {
|
|
||||||
dispose();
|
|
||||||
}
|
|
||||||
});
|
|
||||||
break;
|
|
||||||
case OPS_CODE_INVITE_USERS:
|
|
||||||
RetrofitBucket retrofitBucket;
|
|
||||||
String invite = null;
|
|
||||||
|
|
||||||
if (invitedGroups.size() > 0) {
|
|
||||||
invite = invitedGroups.get(0);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (conversationType.equals(Conversation.ConversationType.ROOM_PUBLIC_CALL)) {
|
|
||||||
retrofitBucket = ApiUtils.getRetrofitBucketForCreateRoom(apiVersion, currentUser.getBaseUrl(),
|
|
||||||
"3", null, invite, conversationName);
|
|
||||||
} else {
|
|
||||||
retrofitBucket = ApiUtils.getRetrofitBucketForCreateRoom(apiVersion, currentUser.getBaseUrl(),
|
|
||||||
"2", null, invite, conversationName);
|
|
||||||
}
|
|
||||||
|
|
||||||
ncApi.createRoom(credentials, retrofitBucket.getUrl(), retrofitBucket.getQueryMap())
|
|
||||||
.subscribeOn(Schedulers.io())
|
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
|
||||||
.retry(1)
|
|
||||||
.subscribe(new Observer<RoomOverall>() {
|
|
||||||
@Override
|
|
||||||
public void onSubscribe(@io.reactivex.annotations.NonNull Disposable d) {
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onNext(@io.reactivex.annotations.NonNull RoomOverall roomOverall) {
|
|
||||||
conversation = roomOverall.getOcs().getData();
|
|
||||||
|
|
||||||
ncApi.getRoom(credentials,
|
|
||||||
ApiUtils.getUrlForRoom(apiVersion, currentUser.getBaseUrl(),
|
|
||||||
conversation.getToken()))
|
|
||||||
.subscribeOn(Schedulers.io())
|
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
|
||||||
.subscribe(new Observer<RoomOverall>() {
|
|
||||||
@Override
|
|
||||||
public void onSubscribe(@io.reactivex.annotations.NonNull Disposable d) {
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onNext(
|
|
||||||
@io.reactivex.annotations.NonNull RoomOverall roomOverall
|
|
||||||
) {
|
|
||||||
conversation = roomOverall.getOcs().getData();
|
|
||||||
inviteUsersToAConversation();
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onError(@io.reactivex.annotations.NonNull Throwable e) {
|
|
||||||
showResultImage(false, false);
|
|
||||||
dispose();
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onComplete() {
|
|
||||||
|
|
||||||
}
|
|
||||||
});
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onError(@io.reactivex.annotations.NonNull Throwable e) {
|
|
||||||
showResultImage(false, false);
|
|
||||||
dispose();
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onComplete() {
|
|
||||||
dispose();
|
|
||||||
}
|
|
||||||
});
|
|
||||||
|
|
||||||
break;
|
|
||||||
case OPS_CODE_MARK_AS_READ:
|
|
||||||
ncApi.setChatReadMarker(credentials,
|
|
||||||
ApiUtils.getUrlForSetChatReadMarker(chatApiVersion,
|
|
||||||
currentUser.getBaseUrl(),
|
|
||||||
conversation.getToken()),
|
|
||||||
conversation.lastMessage.jsonMessageId)
|
|
||||||
.subscribeOn(Schedulers.io())
|
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
|
||||||
.retry(1)
|
|
||||||
.subscribe(genericOperationsObserver);
|
|
||||||
break;
|
|
||||||
case OPS_CODE_REMOVE_FAVORITE:
|
|
||||||
case OPS_CODE_ADD_FAVORITE:
|
|
||||||
if (operation == OPS_CODE_REMOVE_FAVORITE) {
|
|
||||||
ncApi.removeConversationFromFavorites(credentials,
|
|
||||||
ApiUtils.getUrlForRoomFavorite(apiVersion,
|
|
||||||
currentUser.getBaseUrl(),
|
|
||||||
conversation.getToken()))
|
|
||||||
.subscribeOn(Schedulers.io())
|
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
|
||||||
.retry(1)
|
|
||||||
.subscribe(genericOperationsObserver);
|
|
||||||
} else {
|
|
||||||
ncApi.addConversationToFavorites(credentials,
|
|
||||||
ApiUtils.getUrlForRoomFavorite(apiVersion,
|
|
||||||
currentUser.getBaseUrl(),
|
|
||||||
conversation.getToken()))
|
|
||||||
.subscribeOn(Schedulers.io())
|
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
|
||||||
.retry(1)
|
|
||||||
.subscribe(genericOperationsObserver);
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
case OPS_CODE_JOIN_ROOM:
|
|
||||||
ncApi.joinRoom(credentials, ApiUtils.getUrlForParticipantsActive(apiVersion,
|
|
||||||
baseUrl,
|
|
||||||
conversationToken),
|
|
||||||
callPassword)
|
|
||||||
.subscribeOn(Schedulers.io())
|
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
|
||||||
.retry(1)
|
|
||||||
.subscribe(roomOperationsObserver);
|
|
||||||
break;
|
|
||||||
default:
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private void showResultImage(boolean everythingOK, boolean isGuestSupportError) {
|
|
||||||
progressBar.setVisibility(View.GONE);
|
|
||||||
|
|
||||||
if (getResources() != null) {
|
|
||||||
if (everythingOK) {
|
|
||||||
resultImageView.setImageDrawable(DisplayUtils.getTintedDrawable(getResources(),
|
|
||||||
R.drawable.ic_check_circle_black_24dp,
|
|
||||||
R.color.nc_darkGreen));
|
|
||||||
} else {
|
|
||||||
resultImageView.setImageDrawable(DisplayUtils.getTintedDrawable(getResources(),
|
|
||||||
R.drawable.ic_cancel_black_24dp,
|
|
||||||
R.color.nc_darkRed));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
resultImageView.setVisibility(View.VISIBLE);
|
|
||||||
|
|
||||||
if (everythingOK) {
|
|
||||||
resultsTextView.setText(R.string.nc_all_ok_operation);
|
|
||||||
} else {
|
|
||||||
resultsTextView.setTextColor(getResources().getColor(R.color.nc_darkRed));
|
|
||||||
if (!isGuestSupportError) {
|
|
||||||
resultsTextView.setText(R.string.nc_failed_to_perform_operation);
|
|
||||||
} else {
|
|
||||||
resultsTextView.setText(R.string.nc_failed_signaling_settings);
|
|
||||||
webButton.setOnClickListener(v -> {
|
|
||||||
Intent browserIntent = new Intent(Intent.ACTION_VIEW, Uri.parse(callUrl));
|
|
||||||
startActivity(browserIntent);
|
|
||||||
});
|
|
||||||
webButton.setVisibility(View.VISIBLE);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
resultsTextView.setVisibility(View.VISIBLE);
|
|
||||||
if (everythingOK) {
|
|
||||||
eventBus.post(new ConversationsListFetchDataEvent());
|
|
||||||
} else {
|
|
||||||
resultImageView.setImageDrawable(DisplayUtils.getTintedDrawable(getResources(), R.drawable
|
|
||||||
.ic_cancel_black_24dp, R.color.nc_darkRed));
|
|
||||||
okButton.setOnClickListener(v -> eventBus.post(new ConversationsListFetchDataEvent()));
|
|
||||||
okButton.setVisibility(View.VISIBLE);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private void dispose() {
|
|
||||||
if (disposable != null && !disposable.isDisposed()) {
|
|
||||||
disposable.dispose();
|
|
||||||
}
|
|
||||||
|
|
||||||
disposable = null;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onDestroy() {
|
|
||||||
super.onDestroy();
|
|
||||||
dispose();
|
|
||||||
}
|
|
||||||
|
|
||||||
private void checkCapabilities(UserEntity currentUser) throws NoSupportedApiException {
|
|
||||||
ApiUtils.getConversationApiVersion(currentUser, new int[] {ApiUtils.APIv4, 1});
|
|
||||||
ApiUtils.getCallApiVersion(currentUser, new int[] {ApiUtils.APIv4, 1});
|
|
||||||
ApiUtils.getChatApiVersion(currentUser, new int[] {1});
|
|
||||||
ApiUtils.getSignalingApiVersion(currentUser, new int[] {ApiUtils.APIv3, 2, 1});
|
|
||||||
}
|
|
||||||
|
|
||||||
private void inviteUsersToAConversation() {
|
|
||||||
final ArrayList<String> localInvitedUsers = invitedUsers;
|
|
||||||
final ArrayList<String> localInvitedGroups = invitedGroups;
|
|
||||||
if (localInvitedGroups.size() > 0) {
|
|
||||||
localInvitedGroups.remove(0);
|
|
||||||
}
|
|
||||||
|
|
||||||
int apiVersion = ApiUtils.getConversationApiVersion(currentUser, new int[] {4, 1});
|
|
||||||
|
|
||||||
if (localInvitedUsers.size() > 0 || (localInvitedGroups.size() > 0 &&
|
|
||||||
CapabilitiesUtil.hasSpreedFeatureCapability(currentUser, "invite-groups-and-mails"))) {
|
|
||||||
addGroupsToConversation(localInvitedUsers, localInvitedGroups, apiVersion);
|
|
||||||
addUsersToConversation(localInvitedUsers, localInvitedGroups, apiVersion);
|
|
||||||
} else {
|
|
||||||
initiateConversation();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private void addUsersToConversation(
|
|
||||||
ArrayList<String> localInvitedUsers,
|
|
||||||
ArrayList<String> localInvitedGroups,
|
|
||||||
int apiVersion)
|
|
||||||
{
|
|
||||||
RetrofitBucket retrofitBucket;
|
|
||||||
for (int i = 0; i < localInvitedUsers.size(); i++) {
|
|
||||||
final String userId = invitedUsers.get(i);
|
|
||||||
retrofitBucket = ApiUtils.getRetrofitBucketForAddParticipant(apiVersion,
|
|
||||||
currentUser.getBaseUrl(),
|
|
||||||
conversation.getToken(),
|
|
||||||
userId);
|
|
||||||
|
|
||||||
ncApi.addParticipant(credentials, retrofitBucket.getUrl(), retrofitBucket.getQueryMap())
|
|
||||||
.subscribeOn(Schedulers.io())
|
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
|
||||||
.retry(1)
|
|
||||||
.subscribe(new Observer<AddParticipantOverall>() {
|
|
||||||
@Override
|
|
||||||
public void onSubscribe(@io.reactivex.annotations.NonNull Disposable d) {
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onNext(
|
|
||||||
@io.reactivex.annotations.NonNull AddParticipantOverall addParticipantOverall
|
|
||||||
) {
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onError(@io.reactivex.annotations.NonNull Throwable e) {
|
|
||||||
dispose();
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onComplete() {
|
|
||||||
synchronized (localInvitedUsers) {
|
|
||||||
localInvitedUsers.remove(userId);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (localInvitedGroups.size() == 0 && localInvitedUsers.size() == 0) {
|
|
||||||
initiateConversation();
|
|
||||||
}
|
|
||||||
dispose();
|
|
||||||
}
|
|
||||||
});
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private void addGroupsToConversation(
|
|
||||||
ArrayList<String> localInvitedUsers,
|
|
||||||
ArrayList<String> localInvitedGroups,
|
|
||||||
int apiVersion)
|
|
||||||
{
|
|
||||||
RetrofitBucket retrofitBucket;
|
|
||||||
if ((localInvitedGroups.size() > 0 &&
|
|
||||||
CapabilitiesUtil.hasSpreedFeatureCapability(currentUser, "invite-groups-and-mails"))) {
|
|
||||||
for (int i = 0; i < localInvitedGroups.size(); i++) {
|
|
||||||
final String groupId = localInvitedGroups.get(i);
|
|
||||||
retrofitBucket = ApiUtils.getRetrofitBucketForAddParticipantWithSource(
|
|
||||||
apiVersion,
|
|
||||||
currentUser.getBaseUrl(),
|
|
||||||
conversation.getToken(),
|
|
||||||
"groups",
|
|
||||||
groupId
|
|
||||||
);
|
|
||||||
|
|
||||||
ncApi.addParticipant(credentials, retrofitBucket.getUrl(), retrofitBucket.getQueryMap())
|
|
||||||
.subscribeOn(Schedulers.io())
|
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
|
||||||
.retry(1)
|
|
||||||
.subscribe(new Observer<AddParticipantOverall>() {
|
|
||||||
@Override
|
|
||||||
public void onSubscribe(@io.reactivex.annotations.NonNull Disposable d) {
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onNext(
|
|
||||||
@io.reactivex.annotations.NonNull AddParticipantOverall addParticipantOverall
|
|
||||||
) {
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onError(@io.reactivex.annotations.NonNull Throwable e) {
|
|
||||||
dispose();
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onComplete() {
|
|
||||||
synchronized (localInvitedGroups) {
|
|
||||||
localInvitedGroups.remove(groupId);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (localInvitedGroups.size() == 0 && localInvitedUsers.size() == 0) {
|
|
||||||
initiateConversation();
|
|
||||||
}
|
|
||||||
dispose();
|
|
||||||
}
|
|
||||||
});
|
|
||||||
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private void initiateConversation() {
|
|
||||||
eventBus.post(new ConversationsListFetchDataEvent());
|
|
||||||
|
|
||||||
Bundle bundle = new Bundle();
|
|
||||||
bundle.putString(BundleKeys.INSTANCE.getKEY_ROOM_TOKEN(), conversation.getToken());
|
|
||||||
bundle.putString(BundleKeys.INSTANCE.getKEY_ROOM_ID(), conversation.getRoomId());
|
|
||||||
bundle.putString(BundleKeys.INSTANCE.getKEY_CONVERSATION_NAME(), conversation.getDisplayName());
|
|
||||||
bundle.putParcelable(BundleKeys.INSTANCE.getKEY_USER_ENTITY(), currentUser);
|
|
||||||
bundle.putParcelable(BundleKeys.INSTANCE.getKEY_ACTIVE_CONVERSATION(), Parcels.wrap(conversation));
|
|
||||||
bundle.putString(BundleKeys.INSTANCE.getKEY_CONVERSATION_PASSWORD(), callPassword);
|
|
||||||
|
|
||||||
eventBus.post(new OpenConversationEvent(conversation, bundle));
|
|
||||||
}
|
|
||||||
|
|
||||||
private void handleObserverError(@io.reactivex.annotations.NonNull Throwable e) {
|
|
||||||
if (operation != OPS_CODE_JOIN_ROOM || !(e instanceof HttpException)) {
|
|
||||||
showResultImage(false, false);
|
|
||||||
} else {
|
|
||||||
Response<?> response = ((HttpException) e).response();
|
|
||||||
if (response != null && response.code() == 403) {
|
|
||||||
ApplicationWideMessageHolder.getInstance().setMessageType(ApplicationWideMessageHolder.MessageType.CALL_PASSWORD_WRONG);
|
|
||||||
getRouter().popCurrentController();
|
|
||||||
} else {
|
|
||||||
showResultImage(false, false);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
dispose();
|
|
||||||
}
|
|
||||||
|
|
||||||
private class GenericOperationsObserver implements Observer<GenericOverall> {
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onSubscribe(@io.reactivex.annotations.NonNull Disposable d) {
|
|
||||||
disposable = d;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onNext(@io.reactivex.annotations.NonNull GenericOverall genericOverall) {
|
|
||||||
if (operation != OPS_CODE_JOIN_ROOM) {
|
|
||||||
showResultImage(true, false);
|
|
||||||
} else {
|
|
||||||
throw new IllegalArgumentException("Unsupported operation code observed!");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onError(@io.reactivex.annotations.NonNull Throwable e) {
|
|
||||||
handleObserverError(e);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onComplete() {
|
|
||||||
dispose();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private class RoomOperationsObserver implements Observer<RoomOverall> {
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onSubscribe(@io.reactivex.annotations.NonNull Disposable d) {
|
|
||||||
disposable = d;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onNext(@io.reactivex.annotations.NonNull RoomOverall roomOverall) {
|
|
||||||
conversation = roomOverall.getOcs().getData();
|
|
||||||
if (operation != OPS_CODE_JOIN_ROOM) {
|
|
||||||
showResultImage(true, false);
|
|
||||||
} else {
|
|
||||||
conversation = roomOverall.getOcs().getData();
|
|
||||||
initiateConversation();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onError(@io.reactivex.annotations.NonNull Throwable e) {
|
|
||||||
handleObserverError(e);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onComplete() {
|
|
||||||
dispose();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public AppBarLayoutType getAppBarLayoutType() {
|
|
||||||
return AppBarLayoutType.SEARCH_BAR;
|
|
||||||
}
|
|
||||||
}
|
|
@ -0,0 +1,819 @@
|
|||||||
|
/*
|
||||||
|
* Nextcloud Talk application
|
||||||
|
*
|
||||||
|
* @author Mario Danic
|
||||||
|
* @author Andy Scherzinger
|
||||||
|
* Copyright (C) 2022 Andy Scherzinger <info@andy-scherzinger.de>
|
||||||
|
* Copyright (C) 2017 Mario Danic <mario@lovelyhq.com>
|
||||||
|
*
|
||||||
|
* This program is free software: you can redistribute it and/or modify
|
||||||
|
* it under the terms of the GNU General Public License as published by
|
||||||
|
* the Free Software Foundation, either version 3 of the License, or
|
||||||
|
* at your option) any later version.
|
||||||
|
*
|
||||||
|
* This program is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
*/
|
||||||
|
package com.nextcloud.talk.controllers.bottomsheet
|
||||||
|
|
||||||
|
import android.content.Intent
|
||||||
|
import android.net.Uri
|
||||||
|
import android.os.Bundle
|
||||||
|
import android.text.TextUtils
|
||||||
|
import android.util.Log
|
||||||
|
import android.view.View
|
||||||
|
import autodagger.AutoInjector
|
||||||
|
import com.bluelinelabs.conductor.RouterTransaction
|
||||||
|
import com.bluelinelabs.conductor.changehandler.HorizontalChangeHandler
|
||||||
|
import com.bluelinelabs.logansquare.LoganSquare
|
||||||
|
import com.nextcloud.talk.R
|
||||||
|
import com.nextcloud.talk.api.NcApi
|
||||||
|
import com.nextcloud.talk.application.NextcloudTalkApplication
|
||||||
|
import com.nextcloud.talk.application.NextcloudTalkApplication.Companion.sharedApplication
|
||||||
|
import com.nextcloud.talk.controllers.base.NewBaseController
|
||||||
|
import com.nextcloud.talk.controllers.util.viewBinding
|
||||||
|
import com.nextcloud.talk.databinding.ControllerOperationsMenuBinding
|
||||||
|
import com.nextcloud.talk.events.ConversationsListFetchDataEvent
|
||||||
|
import com.nextcloud.talk.events.OpenConversationEvent
|
||||||
|
import com.nextcloud.talk.models.RetrofitBucket
|
||||||
|
import com.nextcloud.talk.models.database.CapabilitiesUtil
|
||||||
|
import com.nextcloud.talk.models.database.UserEntity
|
||||||
|
import com.nextcloud.talk.models.json.capabilities.Capabilities
|
||||||
|
import com.nextcloud.talk.models.json.capabilities.CapabilitiesOverall
|
||||||
|
import com.nextcloud.talk.models.json.conversations.Conversation
|
||||||
|
import com.nextcloud.talk.models.json.conversations.Conversation.ConversationType
|
||||||
|
import com.nextcloud.talk.models.json.conversations.RoomOverall
|
||||||
|
import com.nextcloud.talk.models.json.generic.GenericOverall
|
||||||
|
import com.nextcloud.talk.models.json.participants.AddParticipantOverall
|
||||||
|
import com.nextcloud.talk.utils.ApiUtils
|
||||||
|
import com.nextcloud.talk.utils.DisplayUtils
|
||||||
|
import com.nextcloud.talk.utils.NoSupportedApiException
|
||||||
|
import com.nextcloud.talk.utils.bundle.BundleKeys.KEY_ACTIVE_CONVERSATION
|
||||||
|
import com.nextcloud.talk.utils.bundle.BundleKeys.KEY_CALL_URL
|
||||||
|
import com.nextcloud.talk.utils.bundle.BundleKeys.KEY_CONVERSATION_NAME
|
||||||
|
import com.nextcloud.talk.utils.bundle.BundleKeys.KEY_CONVERSATION_PASSWORD
|
||||||
|
import com.nextcloud.talk.utils.bundle.BundleKeys.KEY_CONVERSATION_TYPE
|
||||||
|
import com.nextcloud.talk.utils.bundle.BundleKeys.KEY_INVITED_GROUP
|
||||||
|
import com.nextcloud.talk.utils.bundle.BundleKeys.KEY_INVITED_PARTICIPANTS
|
||||||
|
import com.nextcloud.talk.utils.bundle.BundleKeys.KEY_OPERATION_CODE
|
||||||
|
import com.nextcloud.talk.utils.bundle.BundleKeys.KEY_ROOM
|
||||||
|
import com.nextcloud.talk.utils.bundle.BundleKeys.KEY_ROOM_ID
|
||||||
|
import com.nextcloud.talk.utils.bundle.BundleKeys.KEY_ROOM_TOKEN
|
||||||
|
import com.nextcloud.talk.utils.bundle.BundleKeys.KEY_SERVER_CAPABILITIES
|
||||||
|
import com.nextcloud.talk.utils.bundle.BundleKeys.KEY_USER_ENTITY
|
||||||
|
import com.nextcloud.talk.utils.database.user.UserUtils
|
||||||
|
import com.nextcloud.talk.utils.singletons.ApplicationWideMessageHolder
|
||||||
|
import io.reactivex.Observer
|
||||||
|
import io.reactivex.android.schedulers.AndroidSchedulers
|
||||||
|
import io.reactivex.disposables.Disposable
|
||||||
|
import io.reactivex.schedulers.Schedulers
|
||||||
|
import org.greenrobot.eventbus.EventBus
|
||||||
|
import org.parceler.Parcels
|
||||||
|
import retrofit2.HttpException
|
||||||
|
import java.io.IOException
|
||||||
|
import java.util.Collections
|
||||||
|
import javax.inject.Inject
|
||||||
|
|
||||||
|
@AutoInjector(NextcloudTalkApplication::class)
|
||||||
|
class OperationsMenuController(args: Bundle) : NewBaseController(
|
||||||
|
R.layout.controller_operations_menu,
|
||||||
|
args
|
||||||
|
) {
|
||||||
|
private val binding: ControllerOperationsMenuBinding by viewBinding(ControllerOperationsMenuBinding::bind)
|
||||||
|
|
||||||
|
@Inject
|
||||||
|
lateinit var ncApi: NcApi
|
||||||
|
|
||||||
|
@Inject
|
||||||
|
lateinit var userUtils: UserUtils
|
||||||
|
|
||||||
|
@Inject
|
||||||
|
lateinit var eventBus: EventBus
|
||||||
|
|
||||||
|
private val operation: ConversationOperationEnum?
|
||||||
|
private var conversation: Conversation? = null
|
||||||
|
private var currentUser: UserEntity? = null
|
||||||
|
private val callPassword: String
|
||||||
|
private val callUrl: String
|
||||||
|
private var baseUrl: String? = null
|
||||||
|
private var conversationToken: String? = null
|
||||||
|
private var disposable: Disposable? = null
|
||||||
|
private var conversationType: ConversationType? = null
|
||||||
|
private var invitedUsers: ArrayList<String>? = ArrayList()
|
||||||
|
private var invitedGroups: ArrayList<String>? = ArrayList()
|
||||||
|
private var serverCapabilities: Capabilities? = null
|
||||||
|
private var credentials: String? = null
|
||||||
|
private val conversationName: String
|
||||||
|
|
||||||
|
override val appBarLayoutType: AppBarLayoutType
|
||||||
|
get() = AppBarLayoutType.SEARCH_BAR
|
||||||
|
|
||||||
|
override fun onViewBound(view: View) {
|
||||||
|
super.onViewBound(view)
|
||||||
|
sharedApplication!!.componentApplication.inject(this)
|
||||||
|
currentUser = userUtils.currentUser
|
||||||
|
|
||||||
|
if (!TextUtils.isEmpty(callUrl) && callUrl.contains("/call")) {
|
||||||
|
conversationToken = callUrl.substring(callUrl.lastIndexOf("/") + 1)
|
||||||
|
if (callUrl.contains("/index.php")) {
|
||||||
|
baseUrl = callUrl.substring(0, callUrl.indexOf("/index.php"))
|
||||||
|
} else {
|
||||||
|
baseUrl = callUrl.substring(0, callUrl.indexOf("/call"))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (!TextUtils.isEmpty(baseUrl) && baseUrl != currentUser!!.baseUrl) {
|
||||||
|
if (serverCapabilities != null) {
|
||||||
|
try {
|
||||||
|
useBundledCapabilitiesForGuest()
|
||||||
|
} catch (e: IOException) {
|
||||||
|
// Fall back to fetching capabilities again
|
||||||
|
fetchCapabilitiesForGuest()
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
fetchCapabilitiesForGuest()
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
processOperation()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Throws(IOException::class)
|
||||||
|
private fun useBundledCapabilitiesForGuest() {
|
||||||
|
currentUser = UserEntity()
|
||||||
|
currentUser!!.baseUrl = baseUrl
|
||||||
|
currentUser!!.userId = "?"
|
||||||
|
try {
|
||||||
|
currentUser!!.capabilities = LoganSquare.serialize(serverCapabilities)
|
||||||
|
} catch (e: IOException) {
|
||||||
|
Log.e("OperationsMenu", "Failed to serialize capabilities")
|
||||||
|
throw e
|
||||||
|
}
|
||||||
|
try {
|
||||||
|
checkCapabilities(currentUser!!)
|
||||||
|
processOperation()
|
||||||
|
} catch (e: NoSupportedApiException) {
|
||||||
|
showResultImage(everythingOK = false, isGuestSupportError = false)
|
||||||
|
Log.d(TAG, "No supported server version found", e)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun fetchCapabilitiesForGuest() {
|
||||||
|
ncApi.getCapabilities(null, ApiUtils.getUrlForCapabilities(baseUrl))
|
||||||
|
.subscribeOn(Schedulers.io())
|
||||||
|
.observeOn(AndroidSchedulers.mainThread())
|
||||||
|
.subscribe(object : Observer<CapabilitiesOverall> {
|
||||||
|
override fun onSubscribe(d: Disposable) {
|
||||||
|
// unused atm
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onNext(capabilitiesOverall: CapabilitiesOverall) {
|
||||||
|
currentUser = UserEntity()
|
||||||
|
currentUser!!.baseUrl = baseUrl
|
||||||
|
currentUser!!.userId = "?"
|
||||||
|
try {
|
||||||
|
currentUser!!.capabilities = LoganSquare
|
||||||
|
.serialize(capabilitiesOverall.ocs!!.data!!.capabilities)
|
||||||
|
} catch (e: IOException) {
|
||||||
|
Log.e("OperationsMenu", "Failed to serialize capabilities")
|
||||||
|
}
|
||||||
|
try {
|
||||||
|
checkCapabilities(currentUser!!)
|
||||||
|
processOperation()
|
||||||
|
} catch (e: NoSupportedApiException) {
|
||||||
|
showResultImage(everythingOK = false, isGuestSupportError = false)
|
||||||
|
Log.d(TAG, "No supported server version found", e)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onError(e: Throwable) {
|
||||||
|
showResultImage(everythingOK = false, isGuestSupportError = false)
|
||||||
|
Log.e(TAG, "Error fetching capabilities for guest", e)
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onComplete() {
|
||||||
|
// unused atm
|
||||||
|
}
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
|
@Suppress("Detekt.ComplexMethod")
|
||||||
|
private fun processOperation() {
|
||||||
|
if (currentUser == null) {
|
||||||
|
showResultImage(everythingOK = false, isGuestSupportError = true)
|
||||||
|
Log.e(TAG, "Ended up in processOperation without a valid currentUser")
|
||||||
|
return
|
||||||
|
}
|
||||||
|
credentials = ApiUtils.getCredentials(currentUser!!.username, currentUser!!.token)
|
||||||
|
when (operation) {
|
||||||
|
ConversationOperationEnum.OPS_CODE_RENAME_ROOM -> operationRenameRoom()
|
||||||
|
ConversationOperationEnum.OPS_CODE_MAKE_PUBLIC -> operationMakePublic()
|
||||||
|
ConversationOperationEnum.OPS_CODE_CHANGE_PASSWORD,
|
||||||
|
ConversationOperationEnum.OPS_CODE_CLEAR_PASSWORD,
|
||||||
|
ConversationOperationEnum.OPS_CODE_SET_PASSWORD -> operationChangePassword()
|
||||||
|
ConversationOperationEnum.OPS_CODE_MAKE_PRIVATE -> operationMakePrivate()
|
||||||
|
ConversationOperationEnum.OPS_CODE_GET_AND_JOIN_ROOM -> operationGetAndJoinRoom()
|
||||||
|
ConversationOperationEnum.OPS_CODE_INVITE_USERS -> operationInviteUsers()
|
||||||
|
ConversationOperationEnum.OPS_CODE_MARK_AS_READ -> operationMarkAsRead()
|
||||||
|
ConversationOperationEnum.OPS_CODE_REMOVE_FAVORITE,
|
||||||
|
ConversationOperationEnum.OPS_CODE_ADD_FAVORITE -> operationToggleFavorite()
|
||||||
|
ConversationOperationEnum.OPS_CODE_JOIN_ROOM -> operationJoinRoom()
|
||||||
|
else -> {
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun apiVersion(): Int {
|
||||||
|
return ApiUtils.getConversationApiVersion(currentUser, intArrayOf(ApiUtils.APIv4, ApiUtils.APIv1))
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun chatApiVersion(): Int {
|
||||||
|
return ApiUtils.getChatApiVersion(currentUser, intArrayOf(ApiUtils.APIv1))
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun operationJoinRoom() {
|
||||||
|
ncApi.joinRoom(
|
||||||
|
credentials,
|
||||||
|
ApiUtils.getUrlForParticipantsActive(
|
||||||
|
apiVersion(),
|
||||||
|
baseUrl,
|
||||||
|
conversationToken
|
||||||
|
),
|
||||||
|
callPassword
|
||||||
|
)
|
||||||
|
.subscribeOn(Schedulers.io())
|
||||||
|
.observeOn(AndroidSchedulers.mainThread())
|
||||||
|
.retry(1)
|
||||||
|
.subscribe(RoomOperationsObserver())
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun operationMarkAsRead() {
|
||||||
|
ncApi.setChatReadMarker(
|
||||||
|
credentials,
|
||||||
|
ApiUtils.getUrlForSetChatReadMarker(
|
||||||
|
chatApiVersion(),
|
||||||
|
currentUser!!.baseUrl,
|
||||||
|
conversation!!.getToken()
|
||||||
|
),
|
||||||
|
conversation!!.lastMessage.jsonMessageId
|
||||||
|
)
|
||||||
|
.subscribeOn(Schedulers.io())
|
||||||
|
.observeOn(AndroidSchedulers.mainThread())
|
||||||
|
.retry(1)
|
||||||
|
.subscribe(GenericOperationsObserver())
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun operationMakePrivate() {
|
||||||
|
ncApi.makeRoomPrivate(
|
||||||
|
credentials,
|
||||||
|
ApiUtils.getUrlForRoomPublic(
|
||||||
|
apiVersion(),
|
||||||
|
currentUser!!.baseUrl,
|
||||||
|
conversation!!.getToken()
|
||||||
|
)
|
||||||
|
)
|
||||||
|
.subscribeOn(Schedulers.io())
|
||||||
|
.observeOn(AndroidSchedulers.mainThread())
|
||||||
|
.retry(1)
|
||||||
|
.subscribe(GenericOperationsObserver())
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun operationChangePassword() {
|
||||||
|
var pass: String? = ""
|
||||||
|
if (conversation!!.getPassword() != null) {
|
||||||
|
pass = conversation!!.getPassword()
|
||||||
|
}
|
||||||
|
ncApi.setPassword(
|
||||||
|
credentials,
|
||||||
|
ApiUtils.getUrlForRoomPassword(
|
||||||
|
apiVersion(),
|
||||||
|
currentUser!!.baseUrl,
|
||||||
|
conversation!!.getToken()
|
||||||
|
),
|
||||||
|
pass
|
||||||
|
)
|
||||||
|
.subscribeOn(Schedulers.io())
|
||||||
|
.observeOn(AndroidSchedulers.mainThread())
|
||||||
|
.retry(1)
|
||||||
|
.subscribe(GenericOperationsObserver())
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun operationMakePublic() {
|
||||||
|
ncApi.makeRoomPublic(
|
||||||
|
credentials,
|
||||||
|
ApiUtils.getUrlForRoomPublic(
|
||||||
|
apiVersion(),
|
||||||
|
currentUser!!.baseUrl,
|
||||||
|
conversation!!.getToken()
|
||||||
|
)
|
||||||
|
)
|
||||||
|
.subscribeOn(Schedulers.io())
|
||||||
|
.observeOn(AndroidSchedulers.mainThread())
|
||||||
|
.retry(1)
|
||||||
|
.subscribe(GenericOperationsObserver())
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun operationRenameRoom() {
|
||||||
|
ncApi.renameRoom(
|
||||||
|
credentials,
|
||||||
|
ApiUtils.getUrlForRoom(
|
||||||
|
apiVersion(),
|
||||||
|
currentUser!!.baseUrl,
|
||||||
|
conversation!!.getToken()
|
||||||
|
),
|
||||||
|
conversation!!.getName()
|
||||||
|
)
|
||||||
|
.subscribeOn(Schedulers.io())
|
||||||
|
.observeOn(AndroidSchedulers.mainThread())
|
||||||
|
.retry(1)
|
||||||
|
.subscribe(GenericOperationsObserver())
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun operationToggleFavorite() {
|
||||||
|
val genericOperationsObserver = GenericOperationsObserver()
|
||||||
|
val apiVersion = apiVersion()
|
||||||
|
if (operation === ConversationOperationEnum.OPS_CODE_REMOVE_FAVORITE) {
|
||||||
|
ncApi.removeConversationFromFavorites(
|
||||||
|
credentials,
|
||||||
|
ApiUtils.getUrlForRoomFavorite(
|
||||||
|
apiVersion,
|
||||||
|
currentUser!!.baseUrl,
|
||||||
|
conversation!!.getToken()
|
||||||
|
)
|
||||||
|
)
|
||||||
|
.subscribeOn(Schedulers.io())
|
||||||
|
.observeOn(AndroidSchedulers.mainThread())
|
||||||
|
.retry(1)
|
||||||
|
.subscribe(genericOperationsObserver)
|
||||||
|
} else {
|
||||||
|
ncApi.addConversationToFavorites(
|
||||||
|
credentials,
|
||||||
|
ApiUtils.getUrlForRoomFavorite(
|
||||||
|
apiVersion,
|
||||||
|
currentUser!!.baseUrl,
|
||||||
|
conversation!!.getToken()
|
||||||
|
)
|
||||||
|
)
|
||||||
|
.subscribeOn(Schedulers.io())
|
||||||
|
.observeOn(AndroidSchedulers.mainThread())
|
||||||
|
.retry(1)
|
||||||
|
.subscribe(genericOperationsObserver)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun operationInviteUsers() {
|
||||||
|
val retrofitBucket: RetrofitBucket
|
||||||
|
val apiVersion = apiVersion()
|
||||||
|
var invite: String? = null
|
||||||
|
if (invitedGroups!!.size > 0) {
|
||||||
|
invite = invitedGroups!![0]
|
||||||
|
}
|
||||||
|
retrofitBucket = if (conversationType == ConversationType.ROOM_PUBLIC_CALL) {
|
||||||
|
ApiUtils.getRetrofitBucketForCreateRoom(
|
||||||
|
apiVersion,
|
||||||
|
currentUser!!.baseUrl,
|
||||||
|
"3",
|
||||||
|
null,
|
||||||
|
invite,
|
||||||
|
conversationName
|
||||||
|
)
|
||||||
|
} else {
|
||||||
|
ApiUtils.getRetrofitBucketForCreateRoom(
|
||||||
|
apiVersion,
|
||||||
|
currentUser!!.baseUrl,
|
||||||
|
"2",
|
||||||
|
null,
|
||||||
|
invite,
|
||||||
|
conversationName
|
||||||
|
)
|
||||||
|
}
|
||||||
|
ncApi.createRoom(credentials, retrofitBucket.getUrl(), retrofitBucket.getQueryMap())
|
||||||
|
.subscribeOn(Schedulers.io())
|
||||||
|
.observeOn(AndroidSchedulers.mainThread())
|
||||||
|
.retry(1)
|
||||||
|
.subscribe(object : Observer<RoomOverall> {
|
||||||
|
override fun onSubscribe(d: Disposable) {
|
||||||
|
// unused atm
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onNext(roomOverall: RoomOverall) {
|
||||||
|
conversation = roomOverall.getOcs().getData()
|
||||||
|
ncApi.getRoom(
|
||||||
|
credentials,
|
||||||
|
ApiUtils.getUrlForRoom(
|
||||||
|
apiVersion, currentUser!!.baseUrl,
|
||||||
|
conversation!!.getToken()
|
||||||
|
)
|
||||||
|
)
|
||||||
|
.subscribeOn(Schedulers.io())
|
||||||
|
.observeOn(AndroidSchedulers.mainThread())
|
||||||
|
.subscribe(object : Observer<RoomOverall> {
|
||||||
|
override fun onSubscribe(d: Disposable) {
|
||||||
|
// unused atm
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onNext(
|
||||||
|
roomOverall: RoomOverall
|
||||||
|
) {
|
||||||
|
conversation = roomOverall.getOcs().getData()
|
||||||
|
inviteUsersToAConversation()
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onError(e: Throwable) {
|
||||||
|
showResultImage(everythingOK = false, isGuestSupportError = false)
|
||||||
|
dispose()
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onComplete() {
|
||||||
|
// unused atm
|
||||||
|
}
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onError(e: Throwable) {
|
||||||
|
showResultImage(everythingOK = false, isGuestSupportError = false)
|
||||||
|
dispose()
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onComplete() {
|
||||||
|
dispose()
|
||||||
|
}
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun operationGetAndJoinRoom() {
|
||||||
|
val apiVersion = apiVersion()
|
||||||
|
ncApi.getRoom(
|
||||||
|
credentials,
|
||||||
|
ApiUtils.getUrlForRoom(apiVersion, baseUrl, conversationToken)
|
||||||
|
)
|
||||||
|
.subscribeOn(Schedulers.io())
|
||||||
|
.observeOn(AndroidSchedulers.mainThread())
|
||||||
|
.retry(1)
|
||||||
|
.subscribe(object : Observer<RoomOverall> {
|
||||||
|
override fun onSubscribe(d: Disposable) {
|
||||||
|
disposable = d
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onNext(roomOverall: RoomOverall) {
|
||||||
|
conversation = roomOverall.getOcs().getData()
|
||||||
|
if (conversation!!.isHasPassword && conversation!!.isGuest) {
|
||||||
|
eventBus.post(ConversationsListFetchDataEvent())
|
||||||
|
val bundle = Bundle()
|
||||||
|
bundle.putParcelable(KEY_ROOM, Parcels.wrap(conversation))
|
||||||
|
bundle.putString(KEY_CALL_URL, callUrl)
|
||||||
|
try {
|
||||||
|
bundle.putParcelable(
|
||||||
|
KEY_SERVER_CAPABILITIES,
|
||||||
|
Parcels.wrap<Capabilities>(
|
||||||
|
LoganSquare.parse<Capabilities>(
|
||||||
|
currentUser!!.capabilities,
|
||||||
|
Capabilities::class.java
|
||||||
|
)
|
||||||
|
)
|
||||||
|
)
|
||||||
|
} catch (e: IOException) {
|
||||||
|
Log.e(TAG, "Failed to parse capabilities for guest")
|
||||||
|
showResultImage(everythingOK = false, isGuestSupportError = false)
|
||||||
|
}
|
||||||
|
bundle.putSerializable(KEY_OPERATION_CODE, ConversationOperationEnum.OPS_CODE_JOIN_ROOM)
|
||||||
|
router.pushController(
|
||||||
|
RouterTransaction.with(EntryMenuController(bundle))
|
||||||
|
.pushChangeHandler(HorizontalChangeHandler())
|
||||||
|
.popChangeHandler(HorizontalChangeHandler())
|
||||||
|
)
|
||||||
|
} else if (conversation!!.isGuest) {
|
||||||
|
ncApi.joinRoom(
|
||||||
|
credentials,
|
||||||
|
ApiUtils.getUrlForParticipantsActive(
|
||||||
|
apiVersion,
|
||||||
|
baseUrl,
|
||||||
|
conversationToken
|
||||||
|
),
|
||||||
|
null
|
||||||
|
)
|
||||||
|
.subscribeOn(Schedulers.io())
|
||||||
|
.observeOn(AndroidSchedulers.mainThread())
|
||||||
|
.subscribe(object : Observer<RoomOverall> {
|
||||||
|
override fun onSubscribe(d: Disposable) {
|
||||||
|
// unused atm
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onNext(roomOverall: RoomOverall) {
|
||||||
|
conversation = roomOverall.getOcs().getData()
|
||||||
|
initiateConversation()
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onError(e: Throwable) {
|
||||||
|
showResultImage(everythingOK = false, isGuestSupportError = false)
|
||||||
|
dispose()
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onComplete() {
|
||||||
|
// unused atm
|
||||||
|
}
|
||||||
|
})
|
||||||
|
} else {
|
||||||
|
initiateConversation()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onError(e: Throwable) {
|
||||||
|
showResultImage(everythingOK = false, isGuestSupportError = false)
|
||||||
|
dispose()
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onComplete() {
|
||||||
|
dispose()
|
||||||
|
}
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
|
@Suppress("Detekt.TooGenericExceptionCaught")
|
||||||
|
private fun showResultImage(everythingOK: Boolean, isGuestSupportError: Boolean) {
|
||||||
|
try {
|
||||||
|
binding.progressBar.visibility = View.GONE
|
||||||
|
if (resources != null) {
|
||||||
|
if (everythingOK) {
|
||||||
|
binding.resultImageView.setImageDrawable(
|
||||||
|
DisplayUtils.getTintedDrawable(
|
||||||
|
resources,
|
||||||
|
R.drawable.ic_check_circle_black_24dp,
|
||||||
|
R.color.nc_darkGreen
|
||||||
|
)
|
||||||
|
)
|
||||||
|
} else {
|
||||||
|
binding.resultImageView.setImageDrawable(
|
||||||
|
DisplayUtils.getTintedDrawable(
|
||||||
|
resources,
|
||||||
|
R.drawable.ic_cancel_black_24dp,
|
||||||
|
R.color.nc_darkRed
|
||||||
|
)
|
||||||
|
)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
binding.resultImageView.visibility = View.VISIBLE
|
||||||
|
if (everythingOK) {
|
||||||
|
binding.resultTextView.setText(R.string.nc_all_ok_operation)
|
||||||
|
} else {
|
||||||
|
binding.resultTextView.setTextColor(resources!!.getColor(R.color.nc_darkRed))
|
||||||
|
if (!isGuestSupportError) {
|
||||||
|
binding.resultTextView.setText(R.string.nc_failed_to_perform_operation)
|
||||||
|
} else {
|
||||||
|
binding.resultTextView.setText(R.string.nc_failed_signaling_settings)
|
||||||
|
binding.webButton.setOnClickListener {
|
||||||
|
val browserIntent = Intent(Intent.ACTION_VIEW, Uri.parse(callUrl))
|
||||||
|
startActivity(browserIntent)
|
||||||
|
}
|
||||||
|
binding.webButton.visibility = View.VISIBLE
|
||||||
|
}
|
||||||
|
}
|
||||||
|
binding.resultTextView.visibility = View.VISIBLE
|
||||||
|
if (everythingOK) {
|
||||||
|
eventBus!!.post(ConversationsListFetchDataEvent())
|
||||||
|
} else {
|
||||||
|
binding.resultImageView.setImageDrawable(
|
||||||
|
DisplayUtils.getTintedDrawable(
|
||||||
|
resources,
|
||||||
|
R.drawable.ic_cancel_black_24dp,
|
||||||
|
R.color.nc_darkRed
|
||||||
|
)
|
||||||
|
)
|
||||||
|
binding.okButton.setOnClickListener { v: View? -> eventBus!!.post(ConversationsListFetchDataEvent()) }
|
||||||
|
binding.okButton.visibility = View.VISIBLE
|
||||||
|
}
|
||||||
|
} catch (npe: NullPointerException) {
|
||||||
|
Log.i(TAG, "Controller already closed", npe)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun dispose() {
|
||||||
|
if (disposable != null && !disposable!!.isDisposed) {
|
||||||
|
disposable!!.dispose()
|
||||||
|
}
|
||||||
|
disposable = null
|
||||||
|
}
|
||||||
|
|
||||||
|
public override fun onDestroy() {
|
||||||
|
super.onDestroy()
|
||||||
|
dispose()
|
||||||
|
}
|
||||||
|
|
||||||
|
@kotlin.Throws(NoSupportedApiException::class)
|
||||||
|
private fun checkCapabilities(currentUser: UserEntity) {
|
||||||
|
ApiUtils.getConversationApiVersion(currentUser, intArrayOf(ApiUtils.APIv4, 1))
|
||||||
|
ApiUtils.getCallApiVersion(currentUser, intArrayOf(ApiUtils.APIv4, 1))
|
||||||
|
ApiUtils.getChatApiVersion(currentUser, intArrayOf(1))
|
||||||
|
ApiUtils.getSignalingApiVersion(currentUser, intArrayOf(ApiUtils.APIv3, 2, 1))
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun inviteUsersToAConversation() {
|
||||||
|
val localInvitedUsers = invitedUsers
|
||||||
|
val localInvitedGroups = invitedGroups
|
||||||
|
if (localInvitedGroups!!.size > 0) {
|
||||||
|
localInvitedGroups.removeAt(0)
|
||||||
|
}
|
||||||
|
val apiVersion = ApiUtils.getConversationApiVersion(currentUser, API_CONVERSATION_VERSIONS)
|
||||||
|
if (localInvitedUsers!!.size > 0 || localInvitedGroups.size > 0 &&
|
||||||
|
CapabilitiesUtil.hasSpreedFeatureCapability(currentUser, "invite-groups-and-mails")
|
||||||
|
) {
|
||||||
|
addGroupsToConversation(localInvitedUsers, localInvitedGroups, apiVersion)
|
||||||
|
addUsersToConversation(localInvitedUsers, localInvitedGroups, apiVersion)
|
||||||
|
} else {
|
||||||
|
initiateConversation()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun addUsersToConversation(
|
||||||
|
localInvitedUsers: ArrayList<String>?,
|
||||||
|
localInvitedGroups: ArrayList<String>?,
|
||||||
|
apiVersion: Int
|
||||||
|
) {
|
||||||
|
var retrofitBucket: RetrofitBucket
|
||||||
|
for (i in localInvitedUsers!!.indices) {
|
||||||
|
val userId = invitedUsers!![i]
|
||||||
|
retrofitBucket = ApiUtils.getRetrofitBucketForAddParticipant(
|
||||||
|
apiVersion,
|
||||||
|
currentUser!!.baseUrl,
|
||||||
|
conversation!!.getToken(),
|
||||||
|
userId
|
||||||
|
)
|
||||||
|
ncApi.addParticipant(credentials, retrofitBucket.getUrl(), retrofitBucket.getQueryMap())
|
||||||
|
.subscribeOn(Schedulers.io())
|
||||||
|
.observeOn(AndroidSchedulers.mainThread())
|
||||||
|
.retry(1)
|
||||||
|
.subscribe(object : Observer<AddParticipantOverall> {
|
||||||
|
override fun onSubscribe(d: Disposable) {
|
||||||
|
// unused atm
|
||||||
|
}
|
||||||
|
override fun onNext(addParticipantOverall: AddParticipantOverall) {
|
||||||
|
// unused atm
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onError(e: Throwable) {
|
||||||
|
dispose()
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onComplete() {
|
||||||
|
Collections.synchronizedList(localInvitedUsers).remove(userId)
|
||||||
|
if (localInvitedGroups!!.size == 0 && localInvitedUsers.size == 0) {
|
||||||
|
initiateConversation()
|
||||||
|
}
|
||||||
|
dispose()
|
||||||
|
}
|
||||||
|
})
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun addGroupsToConversation(
|
||||||
|
localInvitedUsers: ArrayList<String>?,
|
||||||
|
localInvitedGroups: ArrayList<String>?,
|
||||||
|
apiVersion: Int
|
||||||
|
) {
|
||||||
|
var retrofitBucket: RetrofitBucket
|
||||||
|
if (localInvitedGroups!!.size > 0 &&
|
||||||
|
CapabilitiesUtil.hasSpreedFeatureCapability(currentUser, "invite-groups-and-mails")
|
||||||
|
) {
|
||||||
|
for (i in localInvitedGroups.indices) {
|
||||||
|
val groupId = localInvitedGroups[i]
|
||||||
|
retrofitBucket = ApiUtils.getRetrofitBucketForAddParticipantWithSource(
|
||||||
|
apiVersion,
|
||||||
|
currentUser!!.baseUrl,
|
||||||
|
conversation!!.getToken(),
|
||||||
|
"groups",
|
||||||
|
groupId
|
||||||
|
)
|
||||||
|
ncApi.addParticipant(credentials, retrofitBucket.getUrl(), retrofitBucket.getQueryMap())
|
||||||
|
.subscribeOn(Schedulers.io())
|
||||||
|
.observeOn(AndroidSchedulers.mainThread())
|
||||||
|
.retry(1)
|
||||||
|
.subscribe(object : Observer<AddParticipantOverall> {
|
||||||
|
override fun onSubscribe(d: Disposable) {
|
||||||
|
// unused atm
|
||||||
|
}
|
||||||
|
override fun onNext(addParticipantOverall: AddParticipantOverall) {
|
||||||
|
// unused atm
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onError(e: Throwable) {
|
||||||
|
dispose()
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onComplete() {
|
||||||
|
Collections.synchronizedList(localInvitedGroups).remove(groupId)
|
||||||
|
if (localInvitedGroups.size == 0 && localInvitedUsers!!.size == 0) {
|
||||||
|
initiateConversation()
|
||||||
|
}
|
||||||
|
dispose()
|
||||||
|
}
|
||||||
|
})
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun initiateConversation() {
|
||||||
|
eventBus.post(ConversationsListFetchDataEvent())
|
||||||
|
val bundle = Bundle()
|
||||||
|
bundle.putString(KEY_ROOM_TOKEN, conversation!!.getToken())
|
||||||
|
bundle.putString(KEY_ROOM_ID, conversation!!.getRoomId())
|
||||||
|
bundle.putString(KEY_CONVERSATION_NAME, conversation!!.getDisplayName())
|
||||||
|
bundle.putParcelable(KEY_USER_ENTITY, currentUser)
|
||||||
|
bundle.putParcelable(KEY_ACTIVE_CONVERSATION, Parcels.wrap(conversation))
|
||||||
|
bundle.putString(KEY_CONVERSATION_PASSWORD, callPassword)
|
||||||
|
eventBus.post(OpenConversationEvent(conversation, bundle))
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun handleObserverError(e: Throwable) {
|
||||||
|
if (operation !== ConversationOperationEnum.OPS_CODE_JOIN_ROOM || e !is HttpException) {
|
||||||
|
showResultImage(everythingOK = false, isGuestSupportError = false)
|
||||||
|
} else {
|
||||||
|
val response = e.response()
|
||||||
|
if (response != null && response.code() == FORBIDDEN) {
|
||||||
|
ApplicationWideMessageHolder.getInstance()
|
||||||
|
.setMessageType(ApplicationWideMessageHolder.MessageType.CALL_PASSWORD_WRONG)
|
||||||
|
router.popCurrentController()
|
||||||
|
} else {
|
||||||
|
showResultImage(everythingOK = false, isGuestSupportError = false)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
dispose()
|
||||||
|
}
|
||||||
|
|
||||||
|
private inner class GenericOperationsObserver : Observer<GenericOverall> {
|
||||||
|
override fun onSubscribe(d: Disposable) {
|
||||||
|
disposable = d
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onNext(genericOverall: GenericOverall) {
|
||||||
|
if (operation !== ConversationOperationEnum.OPS_CODE_JOIN_ROOM) {
|
||||||
|
showResultImage(everythingOK = true, isGuestSupportError = false)
|
||||||
|
} else {
|
||||||
|
throw IllegalArgumentException("Unsupported operation code observed!")
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onError(e: Throwable) {
|
||||||
|
handleObserverError(e)
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onComplete() {
|
||||||
|
dispose()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private inner class RoomOperationsObserver : Observer<RoomOverall> {
|
||||||
|
override fun onSubscribe(d: Disposable) {
|
||||||
|
disposable = d
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onNext(roomOverall: RoomOverall) {
|
||||||
|
conversation = roomOverall.getOcs().getData()
|
||||||
|
if (operation !== ConversationOperationEnum.OPS_CODE_JOIN_ROOM) {
|
||||||
|
showResultImage(everythingOK = true, isGuestSupportError = false)
|
||||||
|
} else {
|
||||||
|
conversation = roomOverall.getOcs().getData()
|
||||||
|
initiateConversation()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onError(e: Throwable) {
|
||||||
|
handleObserverError(e)
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onComplete() {
|
||||||
|
dispose()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
companion object {
|
||||||
|
private const val TAG = "OperationsMenu"
|
||||||
|
private const val FORBIDDEN = 403
|
||||||
|
private val API_CONVERSATION_VERSIONS = intArrayOf(4, 1)
|
||||||
|
}
|
||||||
|
|
||||||
|
init {
|
||||||
|
operation = args.getSerializable(KEY_OPERATION_CODE) as ConversationOperationEnum?
|
||||||
|
if (args.containsKey(KEY_ROOM)) {
|
||||||
|
conversation = Parcels.unwrap(args.getParcelable(KEY_ROOM))
|
||||||
|
}
|
||||||
|
callPassword = args.getString(KEY_CONVERSATION_PASSWORD, "")
|
||||||
|
callUrl = args.getString(KEY_CALL_URL, "")
|
||||||
|
if (args.containsKey(KEY_INVITED_PARTICIPANTS)) {
|
||||||
|
invitedUsers = args.getStringArrayList(KEY_INVITED_PARTICIPANTS)
|
||||||
|
}
|
||||||
|
if (args.containsKey(KEY_INVITED_GROUP)) {
|
||||||
|
invitedGroups = args.getStringArrayList(KEY_INVITED_GROUP)
|
||||||
|
}
|
||||||
|
if (args.containsKey(KEY_CONVERSATION_TYPE)) {
|
||||||
|
conversationType = Parcels.unwrap(args.getParcelable(KEY_CONVERSATION_TYPE))
|
||||||
|
}
|
||||||
|
if (args.containsKey(KEY_SERVER_CAPABILITIES)) {
|
||||||
|
serverCapabilities = Parcels.unwrap(args.getParcelable(KEY_SERVER_CAPABILITIES))
|
||||||
|
}
|
||||||
|
conversationName = args.getString(KEY_CONVERSATION_NAME, "")
|
||||||
|
}
|
||||||
|
}
|
@ -1 +1 @@
|
|||||||
411
|
406
|
@ -1,2 +1,2 @@
|
|||||||
DO NOT TOUCH; GENERATED BY DRONE
|
DO NOT TOUCH; GENERATED BY DRONE
|
||||||
<span class="mdl-layout-title">Lint Report: 1 error and 149 warnings</span>
|
<span class="mdl-layout-title">Lint Report: 1 error and 144 warnings</span>
|
||||||
|
Loading…
Reference in New Issue
Block a user