mirror of
https://github.com/nextcloud/talk-android.git
synced 2024-11-21 20:45:29 +03:00
pass spreedCapabilities instead user to CapabilitiesUtil
To support federated rooms, capabilities have to be checked from the room which now also has capabilities. If room is not federated, capabilities fromuser are still checked. This is why CapabilitiesUtil had to be refactored to accept SpreedCapabilities which can come from room or user. Other than that, many other changes were made as a result of this change. Signed-off-by: Marcel Hibbe <dev@mhibbe.de>
This commit is contained in:
parent
513127e481
commit
754b825096
101 changed files with 2115 additions and 1556 deletions
|
@ -199,7 +199,7 @@ class AccountVerificationActivity : BaseActivity() {
|
||||||
val credentials = ApiUtils.getCredentials(username, token)
|
val credentials = ApiUtils.getCredentials(username, token)
|
||||||
cookieManager.cookieStore.removeAll()
|
cookieManager.cookieStore.removeAll()
|
||||||
|
|
||||||
ncApi.getCapabilities(credentials, ApiUtils.getUrlForCapabilities(baseUrl))
|
ncApi.getCapabilities(credentials, ApiUtils.getUrlForCapabilities(baseUrl!!))
|
||||||
.subscribeOn(Schedulers.io())
|
.subscribeOn(Schedulers.io())
|
||||||
.subscribe(object : Observer<CapabilitiesOverall> {
|
.subscribe(object : Observer<CapabilitiesOverall> {
|
||||||
override fun onSubscribe(d: Disposable) {
|
override fun onSubscribe(d: Disposable) {
|
||||||
|
@ -213,7 +213,7 @@ class AccountVerificationActivity : BaseActivity() {
|
||||||
capabilitiesOverall.ocs!!.data!!.capabilities!!.spreedCapability!!.features != null &&
|
capabilitiesOverall.ocs!!.data!!.capabilities!!.spreedCapability!!.features != null &&
|
||||||
!capabilitiesOverall.ocs!!.data!!.capabilities!!.spreedCapability!!.features!!.isEmpty()
|
!capabilitiesOverall.ocs!!.data!!.capabilities!!.spreedCapability!!.features!!.isEmpty()
|
||||||
if (hasTalk) {
|
if (hasTalk) {
|
||||||
fetchProfile(credentials, capabilitiesOverall)
|
fetchProfile(credentials!!, capabilitiesOverall)
|
||||||
} else {
|
} else {
|
||||||
if (resources != null) {
|
if (resources != null) {
|
||||||
runOnUiThread {
|
runOnUiThread {
|
||||||
|
@ -305,7 +305,7 @@ class AccountVerificationActivity : BaseActivity() {
|
||||||
private fun fetchProfile(credentials: String, capabilitiesOverall: CapabilitiesOverall) {
|
private fun fetchProfile(credentials: String, capabilitiesOverall: CapabilitiesOverall) {
|
||||||
ncApi.getUserProfile(
|
ncApi.getUserProfile(
|
||||||
credentials,
|
credentials,
|
||||||
ApiUtils.getUrlForUserProfile(baseUrl)
|
ApiUtils.getUrlForUserProfile(baseUrl!!)
|
||||||
)
|
)
|
||||||
.subscribeOn(Schedulers.io())
|
.subscribeOn(Schedulers.io())
|
||||||
.subscribe(object : Observer<UserProfileOverall> {
|
.subscribe(object : Observer<UserProfileOverall> {
|
||||||
|
|
|
@ -52,7 +52,7 @@ import com.nextcloud.talk.utils.UriUtils
|
||||||
import com.nextcloud.talk.utils.bundle.BundleKeys
|
import com.nextcloud.talk.utils.bundle.BundleKeys
|
||||||
import com.nextcloud.talk.utils.bundle.BundleKeys.ADD_ADDITIONAL_ACCOUNT
|
import com.nextcloud.talk.utils.bundle.BundleKeys.ADD_ADDITIONAL_ACCOUNT
|
||||||
import com.nextcloud.talk.utils.bundle.BundleKeys.KEY_IS_ACCOUNT_IMPORT
|
import com.nextcloud.talk.utils.bundle.BundleKeys.KEY_IS_ACCOUNT_IMPORT
|
||||||
import com.nextcloud.talk.utils.database.user.CapabilitiesUtilNew
|
import com.nextcloud.talk.utils.CapabilitiesUtil
|
||||||
import com.nextcloud.talk.utils.singletons.ApplicationWideMessageHolder
|
import com.nextcloud.talk.utils.singletons.ApplicationWideMessageHolder
|
||||||
import io.reactivex.Observer
|
import io.reactivex.Observer
|
||||||
import io.reactivex.android.schedulers.AndroidSchedulers
|
import io.reactivex.android.schedulers.AndroidSchedulers
|
||||||
|
@ -336,7 +336,7 @@ class ServerSelectionActivity : BaseActivity() {
|
||||||
|
|
||||||
if (hasTalk) {
|
if (hasTalk) {
|
||||||
runOnUiThread {
|
runOnUiThread {
|
||||||
if (CapabilitiesUtilNew.isServerEOL(capabilities)) {
|
if (CapabilitiesUtil.isServerEOL(capabilitiesOverall.ocs?.data?.serverVersion?.major!!)) {
|
||||||
if (resources != null) {
|
if (resources != null) {
|
||||||
runOnUiThread {
|
runOnUiThread {
|
||||||
setErrorText(resources!!.getString(R.string.nc_settings_server_eol))
|
setErrorText(resources!!.getString(R.string.nc_settings_server_eol))
|
||||||
|
|
|
@ -110,6 +110,7 @@ import com.nextcloud.talk.ui.dialog.AudioOutputDialog
|
||||||
import com.nextcloud.talk.ui.dialog.MoreCallActionsDialog
|
import com.nextcloud.talk.ui.dialog.MoreCallActionsDialog
|
||||||
import com.nextcloud.talk.users.UserManager
|
import com.nextcloud.talk.users.UserManager
|
||||||
import com.nextcloud.talk.utils.ApiUtils
|
import com.nextcloud.talk.utils.ApiUtils
|
||||||
|
import com.nextcloud.talk.utils.SpreedFeatures
|
||||||
import com.nextcloud.talk.utils.DisplayUtils
|
import com.nextcloud.talk.utils.DisplayUtils
|
||||||
import com.nextcloud.talk.utils.NotificationUtils.cancelExistingNotificationsForRoom
|
import com.nextcloud.talk.utils.NotificationUtils.cancelExistingNotificationsForRoom
|
||||||
import com.nextcloud.talk.utils.NotificationUtils.getCallRingtoneUri
|
import com.nextcloud.talk.utils.NotificationUtils.getCallRingtoneUri
|
||||||
|
@ -131,9 +132,9 @@ 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_ROOM_TOKEN
|
||||||
import com.nextcloud.talk.utils.bundle.BundleKeys.KEY_START_CALL_AFTER_ROOM_SWITCH
|
import com.nextcloud.talk.utils.bundle.BundleKeys.KEY_START_CALL_AFTER_ROOM_SWITCH
|
||||||
import com.nextcloud.talk.utils.bundle.BundleKeys.KEY_SWITCH_TO_ROOM
|
import com.nextcloud.talk.utils.bundle.BundleKeys.KEY_SWITCH_TO_ROOM
|
||||||
import com.nextcloud.talk.utils.database.user.CapabilitiesUtilNew
|
import com.nextcloud.talk.utils.CapabilitiesUtil
|
||||||
import com.nextcloud.talk.utils.database.user.CapabilitiesUtilNew.hasSpreedFeatureCapability
|
import com.nextcloud.talk.utils.CapabilitiesUtil.hasSpreedFeatureCapability
|
||||||
import com.nextcloud.talk.utils.database.user.CapabilitiesUtilNew.isCallRecordingAvailable
|
import com.nextcloud.talk.utils.CapabilitiesUtil.isCallRecordingAvailable
|
||||||
import com.nextcloud.talk.utils.database.user.CurrentUserProviderNew
|
import com.nextcloud.talk.utils.database.user.CurrentUserProviderNew
|
||||||
import com.nextcloud.talk.utils.permissions.PlatformPermissionUtil
|
import com.nextcloud.talk.utils.permissions.PlatformPermissionUtil
|
||||||
import com.nextcloud.talk.utils.power.PowerManagerUtils
|
import com.nextcloud.talk.utils.power.PowerManagerUtils
|
||||||
|
@ -234,7 +235,7 @@ class CallActivity : CallBaseActivity() {
|
||||||
private var iceServers: MutableList<PeerConnection.IceServer>? = null
|
private var iceServers: MutableList<PeerConnection.IceServer>? = null
|
||||||
private var cameraEnumerator: CameraEnumerator? = null
|
private var cameraEnumerator: CameraEnumerator? = null
|
||||||
private var roomToken: String? = null
|
private var roomToken: String? = null
|
||||||
var conversationUser: User? = null
|
lateinit var conversationUser: User
|
||||||
private var conversationName: String? = null
|
private var conversationName: String? = null
|
||||||
private var callSession: String? = null
|
private var callSession: String? = null
|
||||||
private var localStream: MediaStream? = null
|
private var localStream: MediaStream? = null
|
||||||
|
@ -530,13 +531,13 @@ class CallActivity : CallBaseActivity() {
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
when (CapabilitiesUtilNew.getRecordingConsentType(conversationUser)) {
|
when (CapabilitiesUtil.getRecordingConsentType(conversationUser!!.capabilities!!.spreedCapability!!)) {
|
||||||
CapabilitiesUtilNew.RECORDING_CONSENT_NOT_REQUIRED -> initiateCall()
|
CapabilitiesUtil.RECORDING_CONSENT_NOT_REQUIRED -> initiateCall()
|
||||||
CapabilitiesUtilNew.RECORDING_CONSENT_REQUIRED -> askForRecordingConsent()
|
CapabilitiesUtil.RECORDING_CONSENT_REQUIRED -> askForRecordingConsent()
|
||||||
CapabilitiesUtilNew.RECORDING_CONSENT_DEPEND_ON_CONVERSATION -> {
|
CapabilitiesUtil.RECORDING_CONSENT_DEPEND_ON_CONVERSATION -> {
|
||||||
val getRoomApiVersion = ApiUtils.getConversationApiVersion(
|
val getRoomApiVersion = ApiUtils.getConversationApiVersion(
|
||||||
conversationUser,
|
conversationUser!!,
|
||||||
intArrayOf(ApiUtils.APIv4, 1)
|
intArrayOf(ApiUtils.API_V4, 1)
|
||||||
)
|
)
|
||||||
ncApi!!.getRoom(credentials, ApiUtils.getUrlForRoom(getRoomApiVersion, baseUrl, roomToken))
|
ncApi!!.getRoom(credentials, ApiUtils.getUrlForRoom(getRoomApiVersion, baseUrl, roomToken))
|
||||||
.retry(API_RETRIES)
|
.retry(API_RETRIES)
|
||||||
|
@ -571,7 +572,10 @@ class CallActivity : CallBaseActivity() {
|
||||||
|
|
||||||
override fun onResume() {
|
override fun onResume() {
|
||||||
super.onResume()
|
super.onResume()
|
||||||
if (hasSpreedFeatureCapability(conversationUser, "recording-v1") &&
|
if (hasSpreedFeatureCapability(
|
||||||
|
conversationUser.capabilities!!.spreedCapability!!,
|
||||||
|
SpreedFeatures.RECORDING_V1
|
||||||
|
) &&
|
||||||
othersInCall &&
|
othersInCall &&
|
||||||
elapsedSeconds.toInt() >= CALL_TIME_ONE_HOUR
|
elapsedSeconds.toInt() >= CALL_TIME_ONE_HOUR
|
||||||
) {
|
) {
|
||||||
|
@ -1468,7 +1472,7 @@ class CallActivity : CallBaseActivity() {
|
||||||
|
|
||||||
private fun fetchSignalingSettings() {
|
private fun fetchSignalingSettings() {
|
||||||
Log.d(TAG, "fetchSignalingSettings")
|
Log.d(TAG, "fetchSignalingSettings")
|
||||||
val apiVersion = ApiUtils.getSignalingApiVersion(conversationUser, intArrayOf(ApiUtils.APIv3, 2, 1))
|
val apiVersion = ApiUtils.getSignalingApiVersion(conversationUser, intArrayOf(ApiUtils.API_V3, 2, 1))
|
||||||
ncApi!!.getSignalingSettings(credentials, ApiUtils.getUrlForSignalingSettings(apiVersion, baseUrl))
|
ncApi!!.getSignalingSettings(credentials, ApiUtils.getUrlForSignalingSettings(apiVersion, baseUrl))
|
||||||
.subscribeOn(Schedulers.io())
|
.subscribeOn(Schedulers.io())
|
||||||
.retry(API_RETRIES)
|
.retry(API_RETRIES)
|
||||||
|
@ -1531,7 +1535,7 @@ class CallActivity : CallBaseActivity() {
|
||||||
private fun addIceServers(signalingSettingsOverall: SignalingSettingsOverall, apiVersion: Int) {
|
private fun addIceServers(signalingSettingsOverall: SignalingSettingsOverall, apiVersion: Int) {
|
||||||
if (signalingSettingsOverall.ocs!!.settings!!.stunServers != null) {
|
if (signalingSettingsOverall.ocs!!.settings!!.stunServers != null) {
|
||||||
val stunServers = signalingSettingsOverall.ocs!!.settings!!.stunServers
|
val stunServers = signalingSettingsOverall.ocs!!.settings!!.stunServers
|
||||||
if (apiVersion == ApiUtils.APIv3) {
|
if (apiVersion == ApiUtils.API_V3) {
|
||||||
for ((_, urls) in stunServers!!) {
|
for ((_, urls) in stunServers!!) {
|
||||||
if (urls != null) {
|
if (urls != null) {
|
||||||
for (url in urls) {
|
for (url in urls) {
|
||||||
|
@ -1564,7 +1568,7 @@ class CallActivity : CallBaseActivity() {
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun checkCapabilities() {
|
private fun checkCapabilities() {
|
||||||
ncApi!!.getCapabilities(credentials, ApiUtils.getUrlForCapabilities(baseUrl))
|
ncApi!!.getCapabilities(credentials, ApiUtils.getUrlForCapabilities(baseUrl!!))
|
||||||
.retry(API_RETRIES)
|
.retry(API_RETRIES)
|
||||||
.subscribeOn(Schedulers.io())
|
.subscribeOn(Schedulers.io())
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
.observeOn(AndroidSchedulers.mainThread())
|
||||||
|
@ -1600,7 +1604,7 @@ class CallActivity : CallBaseActivity() {
|
||||||
|
|
||||||
private fun joinRoomAndCall() {
|
private fun joinRoomAndCall() {
|
||||||
callSession = ApplicationWideCurrentRoomHolder.getInstance().session
|
callSession = ApplicationWideCurrentRoomHolder.getInstance().session
|
||||||
val apiVersion = ApiUtils.getConversationApiVersion(conversationUser, intArrayOf(ApiUtils.APIv4, 1))
|
val apiVersion = ApiUtils.getConversationApiVersion(conversationUser, intArrayOf(ApiUtils.API_V4, 1))
|
||||||
Log.d(TAG, "joinRoomAndCall")
|
Log.d(TAG, "joinRoomAndCall")
|
||||||
Log.d(TAG, " baseUrl= $baseUrl")
|
Log.d(TAG, " baseUrl= $baseUrl")
|
||||||
Log.d(TAG, " roomToken= $roomToken")
|
Log.d(TAG, " roomToken= $roomToken")
|
||||||
|
@ -1656,7 +1660,7 @@ class CallActivity : CallBaseActivity() {
|
||||||
fun getRoomAndContinue() {
|
fun getRoomAndContinue() {
|
||||||
val getRoomApiVersion = ApiUtils.getConversationApiVersion(
|
val getRoomApiVersion = ApiUtils.getConversationApiVersion(
|
||||||
conversationUser,
|
conversationUser,
|
||||||
intArrayOf(ApiUtils.APIv4, 1)
|
intArrayOf(ApiUtils.API_V4, 1)
|
||||||
)
|
)
|
||||||
ncApi!!.getRoom(credentials, ApiUtils.getUrlForRoom(getRoomApiVersion, baseUrl, roomToken))
|
ncApi!!.getRoom(credentials, ApiUtils.getUrlForRoom(getRoomApiVersion, baseUrl, roomToken))
|
||||||
.retry(API_RETRIES)
|
.retry(API_RETRIES)
|
||||||
|
@ -1715,10 +1719,10 @@ class CallActivity : CallBaseActivity() {
|
||||||
callParticipantList = CallParticipantList(signalingMessageReceiver)
|
callParticipantList = CallParticipantList(signalingMessageReceiver)
|
||||||
callParticipantList!!.addObserver(callParticipantListObserver)
|
callParticipantList!!.addObserver(callParticipantListObserver)
|
||||||
|
|
||||||
val apiVersion = ApiUtils.getCallApiVersion(conversationUser, intArrayOf(ApiUtils.APIv4, 1))
|
val apiVersion = ApiUtils.getCallApiVersion(conversationUser, intArrayOf(ApiUtils.API_V4, 1))
|
||||||
ncApi!!.joinCall(
|
ncApi!!.joinCall(
|
||||||
credentials,
|
credentials,
|
||||||
ApiUtils.getUrlForCall(apiVersion, baseUrl, roomToken),
|
ApiUtils.getUrlForCall(apiVersion, baseUrl, roomToken!!),
|
||||||
inCallFlag,
|
inCallFlag,
|
||||||
isCallWithoutNotification,
|
isCallWithoutNotification,
|
||||||
recordingConsentGiven
|
recordingConsentGiven
|
||||||
|
@ -1756,7 +1760,10 @@ class CallActivity : CallBaseActivity() {
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun startCallTimeCounter(callStartTime: Long?) {
|
private fun startCallTimeCounter(callStartTime: Long?) {
|
||||||
if (callStartTime != null && hasSpreedFeatureCapability(conversationUser, "recording-v1")) {
|
if (callStartTime != null && hasSpreedFeatureCapability(
|
||||||
|
conversationUser!!.capabilities!!.spreedCapability!!, SpreedFeatures.RECORDING_V1
|
||||||
|
)
|
||||||
|
) {
|
||||||
binding!!.callDuration.visibility = View.VISIBLE
|
binding!!.callDuration.visibility = View.VISIBLE
|
||||||
val currentTimeInSec = System.currentTimeMillis() / SECOND_IN_MILLIES
|
val currentTimeInSec = System.currentTimeMillis() / SECOND_IN_MILLIES
|
||||||
elapsedSeconds = currentTimeInSec - callStartTime
|
elapsedSeconds = currentTimeInSec - callStartTime
|
||||||
|
@ -1793,7 +1800,7 @@ class CallActivity : CallBaseActivity() {
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun pullSignalingMessages() {
|
private fun pullSignalingMessages() {
|
||||||
val signalingApiVersion = ApiUtils.getSignalingApiVersion(conversationUser, intArrayOf(ApiUtils.APIv3, 2, 1))
|
val signalingApiVersion = ApiUtils.getSignalingApiVersion(conversationUser, intArrayOf(ApiUtils.API_V3, 2, 1))
|
||||||
val delayOnError = AtomicInteger(0)
|
val delayOnError = AtomicInteger(0)
|
||||||
|
|
||||||
ncApi!!.pullSignalingMessages(
|
ncApi!!.pullSignalingMessages(
|
||||||
|
@ -1801,7 +1808,7 @@ class CallActivity : CallBaseActivity() {
|
||||||
ApiUtils.getUrlForSignaling(
|
ApiUtils.getUrlForSignaling(
|
||||||
signalingApiVersion,
|
signalingApiVersion,
|
||||||
baseUrl,
|
baseUrl,
|
||||||
roomToken
|
roomToken!!
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
.subscribeOn(Schedulers.io())
|
.subscribeOn(Schedulers.io())
|
||||||
|
@ -2031,12 +2038,12 @@ class CallActivity : CallBaseActivity() {
|
||||||
|
|
||||||
private fun hangupNetworkCalls(shutDownView: Boolean) {
|
private fun hangupNetworkCalls(shutDownView: Boolean) {
|
||||||
Log.d(TAG, "hangupNetworkCalls. shutDownView=$shutDownView")
|
Log.d(TAG, "hangupNetworkCalls. shutDownView=$shutDownView")
|
||||||
val apiVersion = ApiUtils.getCallApiVersion(conversationUser, intArrayOf(ApiUtils.APIv4, 1))
|
val apiVersion = ApiUtils.getCallApiVersion(conversationUser, intArrayOf(ApiUtils.API_V4, 1))
|
||||||
if (callParticipantList != null) {
|
if (callParticipantList != null) {
|
||||||
callParticipantList!!.removeObserver(callParticipantListObserver)
|
callParticipantList!!.removeObserver(callParticipantListObserver)
|
||||||
callParticipantList!!.destroy()
|
callParticipantList!!.destroy()
|
||||||
}
|
}
|
||||||
ncApi!!.leaveCall(credentials, ApiUtils.getUrlForCall(apiVersion, baseUrl, roomToken))
|
ncApi!!.leaveCall(credentials, ApiUtils.getUrlForCall(apiVersion, baseUrl, roomToken!!))
|
||||||
.subscribeOn(Schedulers.io())
|
.subscribeOn(Schedulers.io())
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
.observeOn(AndroidSchedulers.mainThread())
|
||||||
.subscribe(object : Observer<GenericOverall> {
|
.subscribe(object : Observer<GenericOverall> {
|
||||||
|
@ -2919,10 +2926,10 @@ class CallActivity : CallBaseActivity() {
|
||||||
val strings: MutableList<String> = ArrayList()
|
val strings: MutableList<String> = ArrayList()
|
||||||
val stringToSend = stringBuilder.toString()
|
val stringToSend = stringBuilder.toString()
|
||||||
strings.add(stringToSend)
|
strings.add(stringToSend)
|
||||||
val apiVersion = ApiUtils.getSignalingApiVersion(conversationUser, intArrayOf(ApiUtils.APIv3, 2, 1))
|
val apiVersion = ApiUtils.getSignalingApiVersion(conversationUser, intArrayOf(ApiUtils.API_V3, 2, 1))
|
||||||
ncApi!!.sendSignalingMessages(
|
ncApi!!.sendSignalingMessages(
|
||||||
credentials,
|
credentials,
|
||||||
ApiUtils.getUrlForSignaling(apiVersion, baseUrl, roomToken),
|
ApiUtils.getUrlForSignaling(apiVersion, baseUrl, roomToken!!),
|
||||||
strings.toString()
|
strings.toString()
|
||||||
)
|
)
|
||||||
.retry(API_RETRIES)
|
.retry(API_RETRIES)
|
||||||
|
@ -3099,12 +3106,14 @@ class CallActivity : CallBaseActivity() {
|
||||||
|
|
||||||
val isAllowedToStartOrStopRecording: Boolean
|
val isAllowedToStartOrStopRecording: Boolean
|
||||||
get() = (
|
get() = (
|
||||||
isCallRecordingAvailable(conversationUser!!) &&
|
isCallRecordingAvailable(conversationUser!!.capabilities!!.spreedCapability!!) &&
|
||||||
isModerator
|
isModerator
|
||||||
)
|
)
|
||||||
val isAllowedToRaiseHand: Boolean
|
val isAllowedToRaiseHand: Boolean
|
||||||
get() = hasSpreedFeatureCapability(conversationUser, "raise-hand") ||
|
get() = hasSpreedFeatureCapability(
|
||||||
isBreakoutRoom
|
conversationUser.capabilities!!.spreedCapability!!,
|
||||||
|
SpreedFeatures.RAISE_HAND
|
||||||
|
) || isBreakoutRoom
|
||||||
|
|
||||||
private inner class SelfVideoTouchListener : OnTouchListener {
|
private inner class SelfVideoTouchListener : OnTouchListener {
|
||||||
@SuppressLint("ClickableViewAccessibility")
|
@SuppressLint("ClickableViewAccessibility")
|
||||||
|
|
|
@ -181,7 +181,7 @@ class MainActivity : BaseActivity(), ActionBarProvider {
|
||||||
val user = userId.substringBeforeLast("@")
|
val user = userId.substringBeforeLast("@")
|
||||||
val baseUrl = userId.substringAfterLast("@")
|
val baseUrl = userId.substringAfterLast("@")
|
||||||
|
|
||||||
if (userManager.currentUser.blockingGet()?.baseUrl?.endsWith(baseUrl) == true) {
|
if (userManager.currentUser.blockingGet()?.baseUrl!!.endsWith(baseUrl) == true) {
|
||||||
startConversation(user)
|
startConversation(user)
|
||||||
} else {
|
} else {
|
||||||
Snackbar.make(
|
Snackbar.make(
|
||||||
|
@ -200,11 +200,11 @@ class MainActivity : BaseActivity(), ActionBarProvider {
|
||||||
|
|
||||||
val currentUser = userManager.currentUser.blockingGet()
|
val currentUser = userManager.currentUser.blockingGet()
|
||||||
|
|
||||||
val apiVersion = ApiUtils.getConversationApiVersion(currentUser, intArrayOf(ApiUtils.APIv4, 1))
|
val apiVersion = ApiUtils.getConversationApiVersion(currentUser, intArrayOf(ApiUtils.API_V4, 1))
|
||||||
val credentials = ApiUtils.getCredentials(currentUser?.username, currentUser?.token)
|
val credentials = ApiUtils.getCredentials(currentUser?.username, currentUser?.token)
|
||||||
val retrofitBucket = ApiUtils.getRetrofitBucketForCreateRoom(
|
val retrofitBucket = ApiUtils.getRetrofitBucketForCreateRoom(
|
||||||
apiVersion,
|
apiVersion,
|
||||||
currentUser?.baseUrl,
|
currentUser?.baseUrl!!,
|
||||||
roomType,
|
roomType,
|
||||||
null,
|
null,
|
||||||
userId,
|
userId,
|
||||||
|
|
|
@ -50,9 +50,10 @@ import com.nextcloud.talk.models.json.conversations.Conversation
|
||||||
import com.nextcloud.talk.models.json.conversations.Conversation.ConversationType
|
import com.nextcloud.talk.models.json.conversations.Conversation.ConversationType
|
||||||
import com.nextcloud.talk.ui.StatusDrawable
|
import com.nextcloud.talk.ui.StatusDrawable
|
||||||
import com.nextcloud.talk.ui.theme.ViewThemeUtils
|
import com.nextcloud.talk.ui.theme.ViewThemeUtils
|
||||||
|
import com.nextcloud.talk.utils.SpreedFeatures
|
||||||
import com.nextcloud.talk.utils.ConversationUtils
|
import com.nextcloud.talk.utils.ConversationUtils
|
||||||
import com.nextcloud.talk.utils.DisplayUtils
|
import com.nextcloud.talk.utils.DisplayUtils
|
||||||
import com.nextcloud.talk.utils.database.user.CapabilitiesUtilNew.hasSpreedFeatureCapability
|
import com.nextcloud.talk.utils.CapabilitiesUtil.hasSpreedFeatureCapability
|
||||||
import eu.davidea.flexibleadapter.FlexibleAdapter
|
import eu.davidea.flexibleadapter.FlexibleAdapter
|
||||||
import eu.davidea.flexibleadapter.items.AbstractFlexibleItem
|
import eu.davidea.flexibleadapter.items.AbstractFlexibleItem
|
||||||
import eu.davidea.flexibleadapter.items.IFilterable
|
import eu.davidea.flexibleadapter.items.IFilterable
|
||||||
|
@ -312,7 +313,7 @@ class ConversationItem(
|
||||||
if (model.type === ConversationType.ROOM_TYPE_ONE_TO_ONE_CALL) {
|
if (model.type === ConversationType.ROOM_TYPE_ONE_TO_ONE_CALL) {
|
||||||
viewThemeUtils.material.colorChipBackground(holder.binding.dialogUnreadBubble)
|
viewThemeUtils.material.colorChipBackground(holder.binding.dialogUnreadBubble)
|
||||||
} else if (model.unreadMention) {
|
} else if (model.unreadMention) {
|
||||||
if (hasSpreedFeatureCapability(user, "direct-mention-flag")) {
|
if (hasSpreedFeatureCapability(user.capabilities?.spreedCapability!!, SpreedFeatures.DIRECT_MENTION_FLAG)) {
|
||||||
if (model.unreadMentionDirect!!) {
|
if (model.unreadMentionDirect!!) {
|
||||||
viewThemeUtils.material.colorChipBackground(holder.binding.dialogUnreadBubble)
|
viewThemeUtils.material.colorChipBackground(holder.binding.dialogUnreadBubble)
|
||||||
} else {
|
} else {
|
||||||
|
|
|
@ -77,12 +77,12 @@ class CallStartedViewHolder(incomingView: View, payload: Any) :
|
||||||
val user = userManager.currentUser.blockingGet()
|
val user = userManager.currentUser.blockingGet()
|
||||||
val url: String = if (message.actorType == "guests" || message.actorType == "guest") {
|
val url: String = if (message.actorType == "guests" || message.actorType == "guest") {
|
||||||
ApiUtils.getUrlForGuestAvatar(
|
ApiUtils.getUrlForGuestAvatar(
|
||||||
user!!.baseUrl,
|
user!!.baseUrl!!,
|
||||||
message.actorDisplayName,
|
message.actorDisplayName,
|
||||||
true
|
true
|
||||||
)
|
)
|
||||||
} else {
|
} else {
|
||||||
ApiUtils.getUrlForAvatar(user!!.baseUrl, message.actorDisplayName, false)
|
ApiUtils.getUrlForAvatar(user!!.baseUrl!!, message.actorDisplayName, false)
|
||||||
}
|
}
|
||||||
|
|
||||||
val imageRequest: ImageRequest = ImageRequest.Builder(context)
|
val imageRequest: ImageRequest = ImageRequest.Builder(context)
|
||||||
|
|
|
@ -188,7 +188,7 @@ class IncomingLinkPreviewMessageViewHolder(incomingView: View, payload: Any) :
|
||||||
binding.messageQuote.quotedMessageImage.load(it) {
|
binding.messageQuote.quotedMessageImage.load(it) {
|
||||||
addHeader(
|
addHeader(
|
||||||
"Authorization",
|
"Authorization",
|
||||||
ApiUtils.getCredentials(message.activeUser!!.username, message.activeUser!!.token)
|
ApiUtils.getCredentials(message.activeUser!!.username, message.activeUser!!.token)!!
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
} ?: run {
|
} ?: run {
|
||||||
|
|
|
@ -172,7 +172,7 @@ class IncomingLocationMessageViewHolder(incomingView: View, payload: Any) :
|
||||||
binding.messageQuote.quotedMessageImage.load(it) {
|
binding.messageQuote.quotedMessageImage.load(it) {
|
||||||
addHeader(
|
addHeader(
|
||||||
"Authorization",
|
"Authorization",
|
||||||
ApiUtils.getCredentials(message.activeUser!!.username, message.activeUser!!.token)
|
ApiUtils.getCredentials(message.activeUser!!.username, message.activeUser!!.token)!!
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
} ?: run {
|
} ?: run {
|
||||||
|
|
|
@ -195,7 +195,7 @@ class IncomingPollMessageViewHolder(incomingView: View, payload: Any) :
|
||||||
binding.messageQuote.quotedMessageImage.load(it) {
|
binding.messageQuote.quotedMessageImage.load(it) {
|
||||||
addHeader(
|
addHeader(
|
||||||
"Authorization",
|
"Authorization",
|
||||||
ApiUtils.getCredentials(message.activeUser!!.username, message.activeUser!!.token)
|
ApiUtils.getCredentials(message.activeUser!!.username, message.activeUser!!.token)!!
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
} ?: run {
|
} ?: run {
|
||||||
|
|
|
@ -197,7 +197,7 @@ class IncomingTextMessageViewHolder(itemView: View, payload: Any) :
|
||||||
binding.messageQuote.quotedMessageImage.load(it) {
|
binding.messageQuote.quotedMessageImage.load(it) {
|
||||||
addHeader(
|
addHeader(
|
||||||
"Authorization",
|
"Authorization",
|
||||||
ApiUtils.getCredentials(message.activeUser!!.username, message.activeUser!!.token)
|
ApiUtils.getCredentials(message.activeUser!!.username, message.activeUser!!.token)!!
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
} ?: run {
|
} ?: run {
|
||||||
|
|
|
@ -301,7 +301,7 @@ class IncomingVoiceMessageViewHolder(incomingView: View, payload: Any) :
|
||||||
binding.messageQuote.quotedMessageImage.load(it) {
|
binding.messageQuote.quotedMessageImage.load(it) {
|
||||||
addHeader(
|
addHeader(
|
||||||
"Authorization",
|
"Authorization",
|
||||||
ApiUtils.getCredentials(message.activeUser!!.username, message.activeUser!!.token)
|
ApiUtils.getCredentials(message.activeUser!!.username, message.activeUser!!.token)!!
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
} ?: run {
|
} ?: run {
|
||||||
|
|
|
@ -45,8 +45,8 @@ class LinkPreview {
|
||||||
binding.referenceThumbImage.setImageDrawable(null)
|
binding.referenceThumbImage.setImageDrawable(null)
|
||||||
|
|
||||||
if (!message.extractedUrlToPreview.isNullOrEmpty()) {
|
if (!message.extractedUrlToPreview.isNullOrEmpty()) {
|
||||||
val credentials: String = ApiUtils.getCredentials(message.activeUser?.username, message.activeUser?.token)
|
val credentials: String = ApiUtils.getCredentials(message.activeUser?.username, message.activeUser?.token)!!
|
||||||
val openGraphLink = ApiUtils.getUrlForOpenGraph(message.activeUser?.baseUrl)
|
val openGraphLink = ApiUtils.getUrlForOpenGraph(message.activeUser?.baseUrl!!)
|
||||||
ncApi.getOpenGraph(
|
ncApi.getOpenGraph(
|
||||||
credentials,
|
credentials,
|
||||||
openGraphLink,
|
openGraphLink,
|
||||||
|
|
|
@ -161,7 +161,7 @@ class OutcomingLinkPreviewMessageViewHolder(outcomingView: View, payload: Any) :
|
||||||
binding.messageQuote.quotedMessageImage.load(it) {
|
binding.messageQuote.quotedMessageImage.load(it) {
|
||||||
addHeader(
|
addHeader(
|
||||||
"Authorization",
|
"Authorization",
|
||||||
ApiUtils.getCredentials(message.activeUser!!.username, message.activeUser!!.token)
|
ApiUtils.getCredentials(message.activeUser!!.username, message.activeUser!!.token)!!
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
} ?: run {
|
} ?: run {
|
||||||
|
|
|
@ -213,7 +213,7 @@ class OutcomingLocationMessageViewHolder(incomingView: View) :
|
||||||
binding.messageQuote.quotedMessageImage.load(it) {
|
binding.messageQuote.quotedMessageImage.load(it) {
|
||||||
addHeader(
|
addHeader(
|
||||||
"Authorization",
|
"Authorization",
|
||||||
ApiUtils.getCredentials(message.activeUser!!.username, message.activeUser!!.token)
|
ApiUtils.getCredentials(message.activeUser!!.username, message.activeUser!!.token)!!
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
} ?: run {
|
} ?: run {
|
||||||
|
|
|
@ -175,7 +175,7 @@ class OutcomingPollMessageViewHolder(outcomingView: View, payload: Any) :
|
||||||
binding.messageQuote.quotedMessageImage.load(it) {
|
binding.messageQuote.quotedMessageImage.load(it) {
|
||||||
addHeader(
|
addHeader(
|
||||||
"Authorization",
|
"Authorization",
|
||||||
ApiUtils.getCredentials(message.activeUser!!.username, message.activeUser!!.token)
|
ApiUtils.getCredentials(message.activeUser!!.username, message.activeUser!!.token)!!
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
} ?: run {
|
} ?: run {
|
||||||
|
|
|
@ -170,7 +170,7 @@ class OutcomingTextMessageViewHolder(itemView: View) : OutcomingTextMessageViewH
|
||||||
binding.messageQuote.quotedMessageImage.load(it) {
|
binding.messageQuote.quotedMessageImage.load(it) {
|
||||||
addHeader(
|
addHeader(
|
||||||
"Authorization",
|
"Authorization",
|
||||||
ApiUtils.getCredentials(message.activeUser!!.username, message.activeUser!!.token)
|
ApiUtils.getCredentials(message.activeUser!!.username, message.activeUser!!.token)!!
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
} ?: run {
|
} ?: run {
|
||||||
|
|
|
@ -285,7 +285,7 @@ class OutcomingVoiceMessageViewHolder(outcomingView: View) :
|
||||||
binding.messageQuote.quotedMessageImage.load(it) {
|
binding.messageQuote.quotedMessageImage.load(it) {
|
||||||
addHeader(
|
addHeader(
|
||||||
"Authorization",
|
"Authorization",
|
||||||
ApiUtils.getCredentials(message.activeUser!!.username, message.activeUser!!.token)
|
ApiUtils.getCredentials(message.activeUser!!.username, message.activeUser!!.token)!!
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
} ?: run {
|
} ?: run {
|
||||||
|
|
|
@ -24,6 +24,7 @@
|
||||||
package com.nextcloud.talk.api;
|
package com.nextcloud.talk.api;
|
||||||
|
|
||||||
import com.nextcloud.talk.models.json.capabilities.CapabilitiesOverall;
|
import com.nextcloud.talk.models.json.capabilities.CapabilitiesOverall;
|
||||||
|
import com.nextcloud.talk.models.json.capabilities.RoomCapabilitiesOverall;
|
||||||
import com.nextcloud.talk.models.json.chat.ChatOverall;
|
import com.nextcloud.talk.models.json.chat.ChatOverall;
|
||||||
import com.nextcloud.talk.models.json.chat.ChatOverallSingleMessage;
|
import com.nextcloud.talk.models.json.chat.ChatOverallSingleMessage;
|
||||||
import com.nextcloud.talk.models.json.chat.ChatShareOverall;
|
import com.nextcloud.talk.models.json.chat.ChatShareOverall;
|
||||||
|
@ -367,6 +368,10 @@ public interface NcApi {
|
||||||
@GET
|
@GET
|
||||||
Observable<CapabilitiesOverall> getCapabilities(@Url String url);
|
Observable<CapabilitiesOverall> getCapabilities(@Url String url);
|
||||||
|
|
||||||
|
@GET
|
||||||
|
Observable<RoomCapabilitiesOverall> getRoomCapabilities(@Header("Authorization") String authorization,
|
||||||
|
@Url String url);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
QueryMap items are as follows:
|
QueryMap items are as follows:
|
||||||
- "lookIntoFuture": int (0 or 1),
|
- "lookIntoFuture": int (0 or 1),
|
||||||
|
|
|
@ -50,6 +50,7 @@ import com.nextcloud.talk.models.domain.ConversationType
|
||||||
import com.nextcloud.talk.models.json.participants.Participant
|
import com.nextcloud.talk.models.json.participants.Participant
|
||||||
import com.nextcloud.talk.users.UserManager
|
import com.nextcloud.talk.users.UserManager
|
||||||
import com.nextcloud.talk.utils.ApiUtils
|
import com.nextcloud.talk.utils.ApiUtils
|
||||||
|
import com.nextcloud.talk.utils.SpreedFeatures
|
||||||
import com.nextcloud.talk.utils.ConversationUtils
|
import com.nextcloud.talk.utils.ConversationUtils
|
||||||
import com.nextcloud.talk.utils.NotificationUtils
|
import com.nextcloud.talk.utils.NotificationUtils
|
||||||
import com.nextcloud.talk.utils.ParticipantPermissions
|
import com.nextcloud.talk.utils.ParticipantPermissions
|
||||||
|
@ -57,7 +58,7 @@ import com.nextcloud.talk.utils.bundle.BundleKeys
|
||||||
import com.nextcloud.talk.utils.bundle.BundleKeys.KEY_CALL_VOICE_ONLY
|
import com.nextcloud.talk.utils.bundle.BundleKeys.KEY_CALL_VOICE_ONLY
|
||||||
import com.nextcloud.talk.utils.bundle.BundleKeys.KEY_CONVERSATION_NAME
|
import com.nextcloud.talk.utils.bundle.BundleKeys.KEY_CONVERSATION_NAME
|
||||||
import com.nextcloud.talk.utils.bundle.BundleKeys.KEY_ROOM_TOKEN
|
import com.nextcloud.talk.utils.bundle.BundleKeys.KEY_ROOM_TOKEN
|
||||||
import com.nextcloud.talk.utils.database.user.CapabilitiesUtilNew.hasSpreedFeatureCapability
|
import com.nextcloud.talk.utils.CapabilitiesUtil.hasSpreedFeatureCapability
|
||||||
import io.reactivex.disposables.Disposable
|
import io.reactivex.disposables.Disposable
|
||||||
import okhttp3.Cache
|
import okhttp3.Cache
|
||||||
import java.io.IOException
|
import java.io.IOException
|
||||||
|
@ -148,10 +149,10 @@ class CallNotificationActivity : CallBaseActivity() {
|
||||||
|
|
||||||
private fun initObservers() {
|
private fun initObservers() {
|
||||||
val apiVersion = ApiUtils.getConversationApiVersion(
|
val apiVersion = ApiUtils.getConversationApiVersion(
|
||||||
userBeingCalled,
|
userBeingCalled!!,
|
||||||
intArrayOf(
|
intArrayOf(
|
||||||
ApiUtils.APIv4,
|
ApiUtils.API_V4,
|
||||||
ApiUtils.APIv3,
|
ApiUtils.API_V3,
|
||||||
1
|
1
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
|
@ -186,10 +187,10 @@ class CallNotificationActivity : CallBaseActivity() {
|
||||||
|
|
||||||
showAnswerControls()
|
showAnswerControls()
|
||||||
|
|
||||||
if (apiVersion >= ApiUtils.APIv3) {
|
if (apiVersion >= ApiUtils.API_V3) {
|
||||||
val hasCallFlags = hasSpreedFeatureCapability(
|
val hasCallFlags = hasSpreedFeatureCapability(
|
||||||
userBeingCalled,
|
userBeingCalled?.capabilities?.spreedCapability!!,
|
||||||
"conversation-call-flags"
|
SpreedFeatures.CONVERSATION_CALL_FLAGS
|
||||||
)
|
)
|
||||||
if (hasCallFlags) {
|
if (hasCallFlags) {
|
||||||
if (isInCallWithVideo(currentConversation!!.callFlag)) {
|
if (isInCallWithVideo(currentConversation!!.callFlag)) {
|
||||||
|
@ -243,7 +244,7 @@ class CallNotificationActivity : CallBaseActivity() {
|
||||||
originalBundle!!.putString(KEY_CONVERSATION_NAME, currentConversation!!.displayName)
|
originalBundle!!.putString(KEY_CONVERSATION_NAME, currentConversation!!.displayName)
|
||||||
|
|
||||||
val participantPermission = ParticipantPermissions(
|
val participantPermission = ParticipantPermissions(
|
||||||
userBeingCalled!!,
|
userBeingCalled!!.capabilities!!.spreedCapability!!,
|
||||||
currentConversation!!
|
currentConversation!!
|
||||||
)
|
)
|
||||||
originalBundle!!.putBoolean(
|
originalBundle!!.putBoolean(
|
||||||
|
|
|
@ -167,6 +167,7 @@ import com.nextcloud.talk.models.domain.ConversationReadOnlyState
|
||||||
import com.nextcloud.talk.models.domain.ConversationType
|
import com.nextcloud.talk.models.domain.ConversationType
|
||||||
import com.nextcloud.talk.models.domain.LobbyState
|
import com.nextcloud.talk.models.domain.LobbyState
|
||||||
import com.nextcloud.talk.models.domain.ObjectType
|
import com.nextcloud.talk.models.domain.ObjectType
|
||||||
|
import com.nextcloud.talk.models.json.capabilities.SpreedCapability
|
||||||
import com.nextcloud.talk.models.json.chat.ChatMessage
|
import com.nextcloud.talk.models.json.chat.ChatMessage
|
||||||
import com.nextcloud.talk.models.json.chat.ChatOverall
|
import com.nextcloud.talk.models.json.chat.ChatOverall
|
||||||
import com.nextcloud.talk.models.json.chat.ReadStatus
|
import com.nextcloud.talk.models.json.chat.ReadStatus
|
||||||
|
@ -192,6 +193,7 @@ import com.nextcloud.talk.ui.recyclerview.MessageSwipeActions
|
||||||
import com.nextcloud.talk.ui.recyclerview.MessageSwipeCallback
|
import com.nextcloud.talk.ui.recyclerview.MessageSwipeCallback
|
||||||
import com.nextcloud.talk.utils.ApiUtils
|
import com.nextcloud.talk.utils.ApiUtils
|
||||||
import com.nextcloud.talk.utils.AudioUtils
|
import com.nextcloud.talk.utils.AudioUtils
|
||||||
|
import com.nextcloud.talk.utils.SpreedFeatures
|
||||||
import com.nextcloud.talk.utils.ContactUtils
|
import com.nextcloud.talk.utils.ContactUtils
|
||||||
import com.nextcloud.talk.utils.ConversationUtils
|
import com.nextcloud.talk.utils.ConversationUtils
|
||||||
import com.nextcloud.talk.utils.DateConstants
|
import com.nextcloud.talk.utils.DateConstants
|
||||||
|
@ -218,7 +220,7 @@ 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_ROOM_TOKEN
|
||||||
import com.nextcloud.talk.utils.bundle.BundleKeys.KEY_START_CALL_AFTER_ROOM_SWITCH
|
import com.nextcloud.talk.utils.bundle.BundleKeys.KEY_START_CALL_AFTER_ROOM_SWITCH
|
||||||
import com.nextcloud.talk.utils.bundle.BundleKeys.KEY_SWITCH_TO_ROOM
|
import com.nextcloud.talk.utils.bundle.BundleKeys.KEY_SWITCH_TO_ROOM
|
||||||
import com.nextcloud.talk.utils.database.user.CapabilitiesUtilNew
|
import com.nextcloud.talk.utils.CapabilitiesUtil
|
||||||
import com.nextcloud.talk.utils.database.user.CurrentUserProviderNew
|
import com.nextcloud.talk.utils.database.user.CurrentUserProviderNew
|
||||||
import com.nextcloud.talk.utils.permissions.PlatformPermissionUtil
|
import com.nextcloud.talk.utils.permissions.PlatformPermissionUtil
|
||||||
import com.nextcloud.talk.utils.rx.DisposableSet
|
import com.nextcloud.talk.utils.rx.DisposableSet
|
||||||
|
@ -301,6 +303,8 @@ class ChatActivity :
|
||||||
var sessionIdAfterRoomJoined: String? = null
|
var sessionIdAfterRoomJoined: String? = null
|
||||||
lateinit var roomToken: String
|
lateinit var roomToken: String
|
||||||
var conversationUser: User? = null
|
var conversationUser: User? = null
|
||||||
|
lateinit var spreedCapabilities: SpreedCapability
|
||||||
|
var chatApiVersion: Int = 1
|
||||||
private var roomPassword: String = ""
|
private var roomPassword: String = ""
|
||||||
var credentials: String? = null
|
var credentials: String? = null
|
||||||
var currentConversation: ConversationModel? = null
|
var currentConversation: ConversationModel? = null
|
||||||
|
@ -351,6 +355,7 @@ class ChatActivity :
|
||||||
RELEASED,
|
RELEASED,
|
||||||
ERROR
|
ERROR
|
||||||
}
|
}
|
||||||
|
|
||||||
private val editableBehaviorSubject = BehaviorSubject.createDefault(false)
|
private val editableBehaviorSubject = BehaviorSubject.createDefault(false)
|
||||||
private val editedTextBehaviorSubject = BehaviorSubject.createDefault("")
|
private val editedTextBehaviorSubject = BehaviorSubject.createDefault("")
|
||||||
|
|
||||||
|
@ -541,14 +546,6 @@ class ChatActivity :
|
||||||
}
|
}
|
||||||
this.lifecycle.addObserver(AudioUtils)
|
this.lifecycle.addObserver(AudioUtils)
|
||||||
this.lifecycle.addObserver(ChatViewModel.LifeCycleObserver)
|
this.lifecycle.addObserver(ChatViewModel.LifeCycleObserver)
|
||||||
|
|
||||||
chatViewModel.refreshChatParams(
|
|
||||||
setupFieldsForPullChatMessages(
|
|
||||||
false,
|
|
||||||
0,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onStop() {
|
override fun onStop() {
|
||||||
|
@ -587,6 +584,30 @@ class ChatActivity :
|
||||||
is ChatViewModel.GetRoomSuccessState -> {
|
is ChatViewModel.GetRoomSuccessState -> {
|
||||||
currentConversation = state.conversationModel
|
currentConversation = state.conversationModel
|
||||||
logConversationInfos("GetRoomSuccessState")
|
logConversationInfos("GetRoomSuccessState")
|
||||||
|
chatViewModel.getCapabilities(conversationUser!!, roomToken, currentConversation!!)
|
||||||
|
}
|
||||||
|
|
||||||
|
is ChatViewModel.GetRoomErrorState -> {
|
||||||
|
Snackbar.make(binding.root, R.string.nc_common_error_sorry, Snackbar.LENGTH_LONG).show()
|
||||||
|
}
|
||||||
|
|
||||||
|
else -> {}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
chatViewModel.getCapabilitiesViewState.observe(this) { state ->
|
||||||
|
when (state) {
|
||||||
|
is ChatViewModel.GetCapabilitiesSuccessState -> {
|
||||||
|
spreedCapabilities = state.spreedCapabilities
|
||||||
|
chatApiVersion = ApiUtils.getChatApiVersion(spreedCapabilities, intArrayOf(1))
|
||||||
|
|
||||||
|
initMessageInputView()
|
||||||
|
|
||||||
|
if (conversationUser?.userId != "?" &&
|
||||||
|
CapabilitiesUtil.hasSpreedFeatureCapability(spreedCapabilities, SpreedFeatures.MENTION_FLAG)
|
||||||
|
) {
|
||||||
|
binding.chatToolbar.setOnClickListener { v -> showConversationInfoScreen() }
|
||||||
|
}
|
||||||
|
|
||||||
if (adapter == null) {
|
if (adapter == null) {
|
||||||
initAdapter()
|
initAdapter()
|
||||||
|
@ -597,7 +618,7 @@ class ChatActivity :
|
||||||
|
|
||||||
loadAvatarForStatusBar()
|
loadAvatarForStatusBar()
|
||||||
setActionBarTitle()
|
setActionBarTitle()
|
||||||
participantPermissions = ParticipantPermissions(conversationUser!!, currentConversation!!)
|
participantPermissions = ParticipantPermissions(spreedCapabilities, currentConversation!!)
|
||||||
|
|
||||||
setupSwipeToReply()
|
setupSwipeToReply()
|
||||||
setupMentionAutocomplete()
|
setupMentionAutocomplete()
|
||||||
|
@ -626,9 +647,17 @@ class ChatActivity :
|
||||||
},
|
},
|
||||||
delayForRecursiveCall
|
delayForRecursiveCall
|
||||||
)
|
)
|
||||||
|
|
||||||
|
chatViewModel.refreshChatParams(
|
||||||
|
setupFieldsForPullChatMessages(
|
||||||
|
false,
|
||||||
|
0,
|
||||||
|
false
|
||||||
|
)
|
||||||
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
is ChatViewModel.GetRoomErrorState -> {
|
is ChatViewModel.GetCapabilitiesErrorState -> {
|
||||||
Snackbar.make(binding.root, R.string.nc_common_error_sorry, Snackbar.LENGTH_LONG).show()
|
Snackbar.make(binding.root, R.string.nc_common_error_sorry, Snackbar.LENGTH_LONG).show()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -716,6 +745,7 @@ class ChatActivity :
|
||||||
}
|
}
|
||||||
binding.messagesListView.smoothScrollToPosition(0)
|
binding.messagesListView.smoothScrollToPosition(0)
|
||||||
}
|
}
|
||||||
|
|
||||||
is ChatViewModel.SendChatMessageErrorState -> {
|
is ChatViewModel.SendChatMessageErrorState -> {
|
||||||
if (state.e is HttpException) {
|
if (state.e is HttpException) {
|
||||||
val code = state.e.code()
|
val code = state.e.code()
|
||||||
|
@ -730,6 +760,7 @@ class ChatActivity :
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
else -> {}
|
else -> {}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -753,9 +784,11 @@ class ChatActivity :
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
is ChatViewModel.DeleteChatMessageErrorState -> {
|
is ChatViewModel.DeleteChatMessageErrorState -> {
|
||||||
Snackbar.make(binding.root, R.string.nc_common_error_sorry, Snackbar.LENGTH_LONG).show()
|
Snackbar.make(binding.root, R.string.nc_common_error_sorry, Snackbar.LENGTH_LONG).show()
|
||||||
}
|
}
|
||||||
|
|
||||||
else -> {}
|
else -> {}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -774,24 +807,22 @@ class ChatActivity :
|
||||||
startActivity(chatIntent)
|
startActivity(chatIntent)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
is ChatViewModel.CreateRoomErrorState -> {
|
is ChatViewModel.CreateRoomErrorState -> {
|
||||||
Snackbar.make(binding.root, R.string.nc_common_error_sorry, Snackbar.LENGTH_LONG).show()
|
Snackbar.make(binding.root, R.string.nc_common_error_sorry, Snackbar.LENGTH_LONG).show()
|
||||||
}
|
}
|
||||||
|
|
||||||
else -> {}
|
else -> {}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
var apiVersion = 1
|
chatViewModel.getFieldMapForChat.observe(this) { fieldMap ->
|
||||||
// FIXME this is a best guess, guests would need to get the capabilities themselves
|
if (fieldMap.isNotEmpty()) {
|
||||||
if (conversationUser != null) {
|
chatViewModel.pullChatMessages(
|
||||||
apiVersion = ApiUtils.getChatApiVersion(conversationUser, intArrayOf(1))
|
credentials!!,
|
||||||
}
|
ApiUtils.getUrlForChat(chatApiVersion, conversationUser?.baseUrl, roomToken)
|
||||||
|
)
|
||||||
chatViewModel.getFieldMapForChat.observe(this) { _ ->
|
}
|
||||||
chatViewModel.pullChatMessages(
|
|
||||||
credentials!!,
|
|
||||||
ApiUtils.getUrlForChat(apiVersion, conversationUser?.baseUrl, roomToken)
|
|
||||||
)
|
|
||||||
}
|
}
|
||||||
|
|
||||||
chatViewModel.pullChatMessageViewState.observe(this) { state ->
|
chatViewModel.pullChatMessageViewState.observe(this) { state ->
|
||||||
|
@ -865,6 +896,7 @@ class ChatActivity :
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
HTTP_CODE_NOT_MODIFIED -> {
|
HTTP_CODE_NOT_MODIFIED -> {
|
||||||
processHeaderChatLastGiven(state.response, state.lookIntoFuture)
|
processHeaderChatLastGiven(state.response, state.lookIntoFuture)
|
||||||
chatViewModel.refreshChatParams(
|
chatViewModel.refreshChatParams(
|
||||||
|
@ -875,6 +907,7 @@ class ChatActivity :
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
HTTP_CODE_PRECONDITION_FAILED -> {
|
HTTP_CODE_PRECONDITION_FAILED -> {
|
||||||
processHeaderChatLastGiven(state.response, state.lookIntoFuture)
|
processHeaderChatLastGiven(state.response, state.lookIntoFuture)
|
||||||
chatViewModel.refreshChatParams(
|
chatViewModel.refreshChatParams(
|
||||||
|
@ -885,6 +918,7 @@ class ChatActivity :
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
else -> {}
|
else -> {}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -898,12 +932,15 @@ class ChatActivity :
|
||||||
collapseSystemMessages()
|
collapseSystemMessages()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
is ChatViewModel.PullChatMessageCompleteState -> {
|
is ChatViewModel.PullChatMessageCompleteState -> {
|
||||||
Log.d(TAG, "PullChatMessageCompleted")
|
Log.d(TAG, "PullChatMessageCompleted")
|
||||||
}
|
}
|
||||||
|
|
||||||
is ChatViewModel.PullChatMessageErrorState -> {
|
is ChatViewModel.PullChatMessageErrorState -> {
|
||||||
Log.d(TAG, "PullChatMessageError")
|
Log.d(TAG, "PullChatMessageError")
|
||||||
}
|
}
|
||||||
|
|
||||||
else -> {}
|
else -> {}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -916,6 +953,7 @@ class ChatActivity :
|
||||||
state.reactionDeletedModel.emoji
|
state.reactionDeletedModel.emoji
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
else -> {}
|
else -> {}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -928,6 +966,7 @@ class ChatActivity :
|
||||||
state.reactionAddedModel.emoji
|
state.reactionAddedModel.emoji
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
else -> {}
|
else -> {}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -943,6 +982,7 @@ class ChatActivity :
|
||||||
Snackbar.LENGTH_LONG
|
Snackbar.LENGTH_LONG
|
||||||
).show()
|
).show()
|
||||||
}
|
}
|
||||||
|
|
||||||
HTTP_FORBIDDEN -> {
|
HTTP_FORBIDDEN -> {
|
||||||
Snackbar.make(
|
Snackbar.make(
|
||||||
binding.root,
|
binding.root,
|
||||||
|
@ -950,6 +990,7 @@ class ChatActivity :
|
||||||
Snackbar.LENGTH_LONG
|
Snackbar.LENGTH_LONG
|
||||||
).show()
|
).show()
|
||||||
}
|
}
|
||||||
|
|
||||||
HTTP_NOT_FOUND -> {
|
HTTP_NOT_FOUND -> {
|
||||||
Snackbar.make(
|
Snackbar.make(
|
||||||
binding.root,
|
binding.root,
|
||||||
|
@ -960,9 +1001,11 @@ class ChatActivity :
|
||||||
}
|
}
|
||||||
clearEditUI()
|
clearEditUI()
|
||||||
}
|
}
|
||||||
|
|
||||||
is ChatViewModel.EditMessageErrorState -> {
|
is ChatViewModel.EditMessageErrorState -> {
|
||||||
Snackbar.make(binding.root, R.string.nc_common_error_sorry, Snackbar.LENGTH_LONG).show()
|
Snackbar.make(binding.root, R.string.nc_common_error_sorry, Snackbar.LENGTH_LONG).show()
|
||||||
}
|
}
|
||||||
|
|
||||||
else -> {}
|
else -> {}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -980,12 +1023,6 @@ class ChatActivity :
|
||||||
webSocketInstance?.getSignalingMessageReceiver()?.addListener(localParticipantMessageListener)
|
webSocketInstance?.getSignalingMessageReceiver()?.addListener(localParticipantMessageListener)
|
||||||
webSocketInstance?.getSignalingMessageReceiver()?.addListener(conversationMessageListener)
|
webSocketInstance?.getSignalingMessageReceiver()?.addListener(conversationMessageListener)
|
||||||
|
|
||||||
if (conversationUser?.userId != "?" &&
|
|
||||||
CapabilitiesUtilNew.hasSpreedFeatureCapability(conversationUser, "mention-flag")
|
|
||||||
) {
|
|
||||||
binding.chatToolbar.setOnClickListener { v -> showConversationInfoScreen() }
|
|
||||||
}
|
|
||||||
|
|
||||||
initSmileyKeyboardToggler()
|
initSmileyKeyboardToggler()
|
||||||
|
|
||||||
themeMessageInputView()
|
themeMessageInputView()
|
||||||
|
@ -1053,7 +1090,6 @@ class ChatActivity :
|
||||||
}
|
}
|
||||||
})
|
})
|
||||||
|
|
||||||
initMessageInputView()
|
|
||||||
loadAvatarForStatusBar()
|
loadAvatarForStatusBar()
|
||||||
setActionBarTitle()
|
setActionBarTitle()
|
||||||
viewThemeUtils.material.colorToolbarOverflowIcon(binding.chatToolbar)
|
viewThemeUtils.material.colorToolbarOverflowIcon(binding.chatToolbar)
|
||||||
|
@ -1061,7 +1097,7 @@ class ChatActivity :
|
||||||
|
|
||||||
private fun initMessageInputView() {
|
private fun initMessageInputView() {
|
||||||
val filters = arrayOfNulls<InputFilter>(1)
|
val filters = arrayOfNulls<InputFilter>(1)
|
||||||
val lengthFilter = CapabilitiesUtilNew.getMessageMaxLength(conversationUser)
|
val lengthFilter = CapabilitiesUtil.getMessageMaxLength(spreedCapabilities)
|
||||||
|
|
||||||
binding.editView.editMessageView.visibility = View.GONE
|
binding.editView.editMessageView.visibility = View.GONE
|
||||||
|
|
||||||
|
@ -1160,7 +1196,7 @@ class ChatActivity :
|
||||||
clearEditUI()
|
clearEditUI()
|
||||||
}
|
}
|
||||||
|
|
||||||
if (CapabilitiesUtilNew.hasSpreedFeatureCapability(conversationUser, "silent-send")) {
|
if (CapabilitiesUtil.hasSpreedFeatureCapability(spreedCapabilities, SpreedFeatures.SILENT_SEND)) {
|
||||||
binding.messageInputView.button?.setOnLongClickListener {
|
binding.messageInputView.button?.setOnLongClickListener {
|
||||||
showSendButtonMenu()
|
showSendButtonMenu()
|
||||||
true
|
true
|
||||||
|
@ -1175,14 +1211,14 @@ class ChatActivity :
|
||||||
var apiVersion = 1
|
var apiVersion = 1
|
||||||
// FIXME Fix API checking with guests?
|
// FIXME Fix API checking with guests?
|
||||||
if (conversationUser != null) {
|
if (conversationUser != null) {
|
||||||
apiVersion = ApiUtils.getChatApiVersion(conversationUser, intArrayOf(1))
|
apiVersion = ApiUtils.getChatApiVersion(spreedCapabilities, intArrayOf(1))
|
||||||
}
|
}
|
||||||
|
|
||||||
chatViewModel.editChatMessage(
|
chatViewModel.editChatMessage(
|
||||||
credentials!!,
|
credentials!!,
|
||||||
ApiUtils.getUrlForChatMessage(
|
ApiUtils.getUrlForChatMessage(
|
||||||
apiVersion,
|
apiVersion,
|
||||||
conversationUser?.baseUrl,
|
conversationUser?.baseUrl!!,
|
||||||
roomToken,
|
roomToken,
|
||||||
message.id
|
message.id
|
||||||
),
|
),
|
||||||
|
@ -2016,7 +2052,7 @@ class ChatActivity :
|
||||||
|
|
||||||
private fun isTypingStatusEnabled(): Boolean {
|
private fun isTypingStatusEnabled(): Boolean {
|
||||||
return webSocketInstance != null &&
|
return webSocketInstance != null &&
|
||||||
!CapabilitiesUtilNew.isTypingStatusPrivate(conversationUser!!)
|
!CapabilitiesUtil.isTypingStatusPrivate(conversationUser!!)
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun setupSwipeToReply() {
|
private fun setupSwipeToReply() {
|
||||||
|
@ -2048,7 +2084,7 @@ class ChatActivity :
|
||||||
|
|
||||||
if (isOneToOneConversation()) {
|
if (isOneToOneConversation()) {
|
||||||
var url = ApiUtils.getUrlForAvatar(
|
var url = ApiUtils.getUrlForAvatar(
|
||||||
conversationUser!!.baseUrl,
|
conversationUser!!.baseUrl!!,
|
||||||
currentConversation!!.name,
|
currentConversation!!.name,
|
||||||
true
|
true
|
||||||
)
|
)
|
||||||
|
@ -2097,18 +2133,19 @@ class ChatActivity :
|
||||||
}
|
}
|
||||||
|
|
||||||
val credentials = ApiUtils.getCredentials(conversationUser!!.username, conversationUser!!.token)
|
val credentials = ApiUtils.getCredentials(conversationUser!!.username, conversationUser!!.token)
|
||||||
|
if (credentials != null) {
|
||||||
context.imageLoader.enqueue(
|
context.imageLoader.enqueue(
|
||||||
ImageRequest.Builder(context)
|
ImageRequest.Builder(context)
|
||||||
.data(url)
|
.data(url)
|
||||||
.addHeader("Authorization", credentials)
|
.addHeader("Authorization", credentials)
|
||||||
.transformations(CircleCropTransformation())
|
.transformations(CircleCropTransformation())
|
||||||
.crossfade(true)
|
.crossfade(true)
|
||||||
.target(target)
|
.target(target)
|
||||||
.memoryCachePolicy(CachePolicy.DISABLED)
|
.memoryCachePolicy(CachePolicy.DISABLED)
|
||||||
.diskCachePolicy(CachePolicy.DISABLED)
|
.diskCachePolicy(CachePolicy.DISABLED)
|
||||||
.build()
|
.build()
|
||||||
)
|
)
|
||||||
|
}
|
||||||
} else {
|
} else {
|
||||||
binding.chatToolbar.findViewById<FrameLayout>(R.id.chat_toolbar_avatar_container).visibility = View.GONE
|
binding.chatToolbar.findViewById<FrameLayout>(R.id.chat_toolbar_avatar_container).visibility = View.GONE
|
||||||
}
|
}
|
||||||
|
@ -2463,7 +2500,10 @@ class ChatActivity :
|
||||||
|
|
||||||
val baseUrl = message.activeUser!!.baseUrl
|
val baseUrl = message.activeUser!!.baseUrl
|
||||||
val userId = message.activeUser!!.userId
|
val userId = message.activeUser!!.userId
|
||||||
val attachmentFolder = CapabilitiesUtilNew.getAttachmentFolder(message.activeUser!!)
|
val attachmentFolder = CapabilitiesUtil.getAttachmentFolder(
|
||||||
|
message.activeUser!!.capabilities!!
|
||||||
|
.spreedCapability!!
|
||||||
|
)
|
||||||
val fileName = message.selectedIndividualHashMap!!["name"]
|
val fileName = message.selectedIndividualHashMap!!["name"]
|
||||||
var size = message.selectedIndividualHashMap!!["size"]
|
var size = message.selectedIndividualHashMap!!["size"]
|
||||||
if (size == null) {
|
if (size == null) {
|
||||||
|
@ -2801,16 +2841,16 @@ class ChatActivity :
|
||||||
|
|
||||||
private fun shouldShowLobby(): Boolean {
|
private fun shouldShowLobby(): Boolean {
|
||||||
if (currentConversation != null) {
|
if (currentConversation != null) {
|
||||||
return CapabilitiesUtilNew.hasSpreedFeatureCapability(conversationUser, "webinary-lobby") &&
|
return CapabilitiesUtil.hasSpreedFeatureCapability(spreedCapabilities, SpreedFeatures.WEBINARY_LOBBY) &&
|
||||||
currentConversation?.lobbyState == LobbyState.LOBBY_STATE_MODERATORS_ONLY &&
|
currentConversation?.lobbyState == LobbyState.LOBBY_STATE_MODERATORS_ONLY &&
|
||||||
!ConversationUtils.canModerate(currentConversation!!, conversationUser!!) &&
|
!ConversationUtils.canModerate(currentConversation!!, spreedCapabilities) &&
|
||||||
!participantPermissions.canIgnoreLobby()
|
!participantPermissions.canIgnoreLobby()
|
||||||
}
|
}
|
||||||
return false
|
return false
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun disableCallButtons() {
|
private fun disableCallButtons() {
|
||||||
if (CapabilitiesUtilNew.isAbleToCall(conversationUser)) {
|
if (CapabilitiesUtil.isAbleToCall(spreedCapabilities)) {
|
||||||
if (conversationVoiceCallMenuItem != null && conversationVideoMenuItem != null) {
|
if (conversationVoiceCallMenuItem != null && conversationVideoMenuItem != null) {
|
||||||
conversationVoiceCallMenuItem?.icon?.alpha = SEMI_TRANSPARENT_INT
|
conversationVoiceCallMenuItem?.icon?.alpha = SEMI_TRANSPARENT_INT
|
||||||
conversationVideoMenuItem?.icon?.alpha = SEMI_TRANSPARENT_INT
|
conversationVideoMenuItem?.icon?.alpha = SEMI_TRANSPARENT_INT
|
||||||
|
@ -2823,7 +2863,7 @@ class ChatActivity :
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun enableCallButtons() {
|
private fun enableCallButtons() {
|
||||||
if (CapabilitiesUtilNew.isAbleToCall(conversationUser)) {
|
if (CapabilitiesUtil.isAbleToCall(spreedCapabilities)) {
|
||||||
if (conversationVoiceCallMenuItem != null && conversationVideoMenuItem != null) {
|
if (conversationVoiceCallMenuItem != null && conversationVideoMenuItem != null) {
|
||||||
conversationVoiceCallMenuItem?.icon?.alpha = FULLY_OPAQUE_INT
|
conversationVoiceCallMenuItem?.icon?.alpha = FULLY_OPAQUE_INT
|
||||||
conversationVideoMenuItem?.icon?.alpha = FULLY_OPAQUE_INT
|
conversationVideoMenuItem?.icon?.alpha = FULLY_OPAQUE_INT
|
||||||
|
@ -2843,7 +2883,7 @@ class ChatActivity :
|
||||||
|
|
||||||
private fun checkLobbyState() {
|
private fun checkLobbyState() {
|
||||||
if (currentConversation != null &&
|
if (currentConversation != null &&
|
||||||
ConversationUtils.isLobbyViewApplicable(currentConversation!!, conversationUser!!)
|
ConversationUtils.isLobbyViewApplicable(currentConversation!!, spreedCapabilities)
|
||||||
) {
|
) {
|
||||||
if (shouldShowLobby()) {
|
if (shouldShowLobby()) {
|
||||||
binding.lobby.lobbyView.visibility = View.VISIBLE
|
binding.lobby.lobbyView.visibility = View.VISIBLE
|
||||||
|
@ -3252,6 +3292,7 @@ class ChatActivity :
|
||||||
|
|
||||||
val intent = Intent(this, LocationPickerActivity::class.java)
|
val intent = Intent(this, LocationPickerActivity::class.java)
|
||||||
intent.putExtra(KEY_ROOM_TOKEN, roomToken)
|
intent.putExtra(KEY_ROOM_TOKEN, roomToken)
|
||||||
|
intent.putExtra(BundleKeys.KEY_CHAT_API_VERSION, chatApiVersion)
|
||||||
startActivity(intent)
|
startActivity(intent)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -3270,7 +3311,7 @@ class ChatActivity :
|
||||||
val elevation = MENTION_AUTO_COMPLETE_ELEVATION
|
val elevation = MENTION_AUTO_COMPLETE_ELEVATION
|
||||||
resources?.let {
|
resources?.let {
|
||||||
val backgroundDrawable = ColorDrawable(it.getColor(R.color.bg_default, null))
|
val backgroundDrawable = ColorDrawable(it.getColor(R.color.bg_default, null))
|
||||||
val presenter = MentionAutocompletePresenter(this, roomToken)
|
val presenter = MentionAutocompletePresenter(this, roomToken, chatApiVersion)
|
||||||
val callback = MentionAutocompleteCallback(
|
val callback = MentionAutocompleteCallback(
|
||||||
this,
|
this,
|
||||||
conversationUser!!,
|
conversationUser!!,
|
||||||
|
@ -3430,12 +3471,6 @@ class ChatActivity :
|
||||||
|
|
||||||
if (!validSessionId()) {
|
if (!validSessionId()) {
|
||||||
Log.d(TAG, "sessionID was not valid -> joinRoom")
|
Log.d(TAG, "sessionID was not valid -> joinRoom")
|
||||||
var apiVersion = 1
|
|
||||||
// FIXME Fix API checking with guests?
|
|
||||||
if (conversationUser != null) {
|
|
||||||
apiVersion = ApiUtils.getConversationApiVersion(conversationUser, intArrayOf(ApiUtils.APIv4, 1))
|
|
||||||
}
|
|
||||||
|
|
||||||
val startNanoTime = System.nanoTime()
|
val startNanoTime = System.nanoTime()
|
||||||
Log.d(TAG, "joinRoomWithPassword - joinRoom - calling: $startNanoTime")
|
Log.d(TAG, "joinRoomWithPassword - joinRoom - calling: $startNanoTime")
|
||||||
|
|
||||||
|
@ -3458,7 +3493,7 @@ class ChatActivity :
|
||||||
var apiVersion = 1
|
var apiVersion = 1
|
||||||
// FIXME Fix API checking with guests?
|
// FIXME Fix API checking with guests?
|
||||||
if (conversationUser != null) {
|
if (conversationUser != null) {
|
||||||
apiVersion = ApiUtils.getConversationApiVersion(conversationUser, intArrayOf(ApiUtils.APIv4, 1))
|
apiVersion = ApiUtils.getConversationApiVersion(conversationUser!!, intArrayOf(ApiUtils.API_V4, 1))
|
||||||
}
|
}
|
||||||
|
|
||||||
val startNanoTime = System.nanoTime()
|
val startNanoTime = System.nanoTime()
|
||||||
|
@ -3467,7 +3502,7 @@ class ChatActivity :
|
||||||
credentials!!,
|
credentials!!,
|
||||||
ApiUtils.getUrlForParticipantsActive(
|
ApiUtils.getUrlForParticipantsActive(
|
||||||
apiVersion,
|
apiVersion,
|
||||||
conversationUser?.baseUrl,
|
conversationUser?.baseUrl!!,
|
||||||
roomToken
|
roomToken
|
||||||
),
|
),
|
||||||
funToCallWhenLeaveSuccessful
|
funToCallWhenLeaveSuccessful
|
||||||
|
@ -3513,11 +3548,9 @@ class ChatActivity :
|
||||||
|
|
||||||
private fun sendMessage(message: CharSequence, replyTo: Int?, sendWithoutNotification: Boolean) {
|
private fun sendMessage(message: CharSequence, replyTo: Int?, sendWithoutNotification: Boolean) {
|
||||||
if (conversationUser != null) {
|
if (conversationUser != null) {
|
||||||
val apiVersion = ApiUtils.getChatApiVersion(conversationUser, intArrayOf(1))
|
|
||||||
|
|
||||||
chatViewModel.sendChatMessage(
|
chatViewModel.sendChatMessage(
|
||||||
credentials!!,
|
credentials!!,
|
||||||
ApiUtils.getUrlForChat(apiVersion, conversationUser!!.baseUrl, roomToken),
|
ApiUtils.getUrlForChat(chatApiVersion, conversationUser!!.baseUrl!!, roomToken),
|
||||||
message,
|
message,
|
||||||
conversationUser!!.displayName ?: "",
|
conversationUser!!.displayName ?: "",
|
||||||
replyTo ?: 0,
|
replyTo ?: 0,
|
||||||
|
@ -3637,7 +3670,7 @@ class ChatActivity :
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (CapabilitiesUtilNew.hasSpreedFeatureCapability(conversationUser, "message-expiration")) {
|
if (CapabilitiesUtil.hasSpreedFeatureCapability(spreedCapabilities, SpreedFeatures.MESSAGE_EXPIRATION)) {
|
||||||
deleteExpiredMessages()
|
deleteExpiredMessages()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -3871,53 +3904,58 @@ class ChatActivity :
|
||||||
if (conversationUser?.userId == "?") {
|
if (conversationUser?.userId == "?") {
|
||||||
menu.removeItem(R.id.conversation_info)
|
menu.removeItem(R.id.conversation_info)
|
||||||
} else {
|
} else {
|
||||||
conversationInfoMenuItem = menu.findItem(R.id.conversation_info)
|
|
||||||
|
|
||||||
if (CapabilitiesUtilNew.hasSpreedFeatureCapability(conversationUser, "rich-object-list-media")) {
|
|
||||||
conversationSharedItemsItem = menu.findItem(R.id.shared_items)
|
|
||||||
} else {
|
|
||||||
menu.removeItem(R.id.shared_items)
|
|
||||||
}
|
|
||||||
|
|
||||||
loadAvatarForStatusBar()
|
loadAvatarForStatusBar()
|
||||||
setActionBarTitle()
|
setActionBarTitle()
|
||||||
}
|
}
|
||||||
|
|
||||||
if (CapabilitiesUtilNew.isAbleToCall(conversationUser)) {
|
|
||||||
conversationVoiceCallMenuItem = menu.findItem(R.id.conversation_voice_call)
|
|
||||||
conversationVideoMenuItem = menu.findItem(R.id.conversation_video_call)
|
|
||||||
|
|
||||||
if (CapabilitiesUtilNew.hasSpreedFeatureCapability(conversationUser, "silent-call")) {
|
|
||||||
Handler().post {
|
|
||||||
findViewById<View?>(R.id.conversation_voice_call)?.setOnLongClickListener {
|
|
||||||
showCallButtonMenu(true)
|
|
||||||
true
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
Handler().post {
|
|
||||||
findViewById<View?>(R.id.conversation_video_call)?.setOnLongClickListener {
|
|
||||||
showCallButtonMenu(false)
|
|
||||||
true
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
menu.removeItem(R.id.conversation_video_call)
|
|
||||||
menu.removeItem(R.id.conversation_voice_call)
|
|
||||||
}
|
|
||||||
return true
|
return true
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onPrepareOptionsMenu(menu: Menu): Boolean {
|
override fun onPrepareOptionsMenu(menu: Menu): Boolean {
|
||||||
super.onPrepareOptionsMenu(menu)
|
super.onPrepareOptionsMenu(menu)
|
||||||
conversationUser?.let {
|
|
||||||
if (CapabilitiesUtilNew.hasSpreedFeatureCapability(it, "read-only-rooms")) {
|
if (this::spreedCapabilities.isInitialized) {
|
||||||
|
if (CapabilitiesUtil.hasSpreedFeatureCapability(spreedCapabilities, SpreedFeatures.READ_ONLY_ROOMS)) {
|
||||||
checkShowCallButtons()
|
checkShowCallButtons()
|
||||||
}
|
}
|
||||||
|
|
||||||
val searchItem = menu.findItem(R.id.conversation_search)
|
val searchItem = menu.findItem(R.id.conversation_search)
|
||||||
searchItem.isVisible = CapabilitiesUtilNew.isUnifiedSearchAvailable(it)
|
searchItem.isVisible = CapabilitiesUtil.isUnifiedSearchAvailable(spreedCapabilities)
|
||||||
|
|
||||||
|
if (CapabilitiesUtil.hasSpreedFeatureCapability(
|
||||||
|
spreedCapabilities,
|
||||||
|
SpreedFeatures.RICH_OBJECT_LIST_MEDIA
|
||||||
|
)
|
||||||
|
) {
|
||||||
|
conversationSharedItemsItem = menu.findItem(R.id.shared_items)
|
||||||
|
} else {
|
||||||
|
menu.removeItem(R.id.shared_items)
|
||||||
|
}
|
||||||
|
|
||||||
|
if (CapabilitiesUtil.isAbleToCall(spreedCapabilities)) {
|
||||||
|
conversationVoiceCallMenuItem = menu.findItem(R.id.conversation_voice_call)
|
||||||
|
conversationVideoMenuItem = menu.findItem(R.id.conversation_video_call)
|
||||||
|
|
||||||
|
if (CapabilitiesUtil.hasSpreedFeatureCapability(spreedCapabilities, SpreedFeatures.SILENT_CALL)) {
|
||||||
|
Handler().post {
|
||||||
|
findViewById<View?>(R.id.conversation_voice_call)?.setOnLongClickListener {
|
||||||
|
showCallButtonMenu(true)
|
||||||
|
true
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
Handler().post {
|
||||||
|
findViewById<View?>(R.id.conversation_video_call)?.setOnLongClickListener {
|
||||||
|
showCallButtonMenu(false)
|
||||||
|
true
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
menu.removeItem(R.id.conversation_video_call)
|
||||||
|
menu.removeItem(R.id.conversation_voice_call)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return true
|
return true
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -4054,7 +4092,7 @@ class ChatActivity :
|
||||||
private fun startACall(isVoiceOnlyCall: Boolean, callWithoutNotification: Boolean) {
|
private fun startACall(isVoiceOnlyCall: Boolean, callWithoutNotification: Boolean) {
|
||||||
currentConversation?.let {
|
currentConversation?.let {
|
||||||
if (conversationUser != null) {
|
if (conversationUser != null) {
|
||||||
val pp = ParticipantPermissions(conversationUser!!, it)
|
val pp = ParticipantPermissions(spreedCapabilities, it)
|
||||||
if (!pp.canStartCall() && currentConversation?.hasCall == false) {
|
if (!pp.canStartCall() && currentConversation?.hasCall == false) {
|
||||||
Snackbar.make(binding.root, R.string.startCallForbidden, Snackbar.LENGTH_LONG).show()
|
Snackbar.make(binding.root, R.string.startCallForbidden, Snackbar.LENGTH_LONG).show()
|
||||||
} else {
|
} else {
|
||||||
|
@ -4074,7 +4112,7 @@ class ChatActivity :
|
||||||
bundle.putString(KEY_ROOM_TOKEN, roomToken)
|
bundle.putString(KEY_ROOM_TOKEN, roomToken)
|
||||||
bundle.putString(KEY_ROOM_ID, roomId)
|
bundle.putString(KEY_ROOM_ID, roomId)
|
||||||
bundle.putString(BundleKeys.KEY_CONVERSATION_PASSWORD, roomPassword)
|
bundle.putString(BundleKeys.KEY_CONVERSATION_PASSWORD, roomPassword)
|
||||||
bundle.putString(BundleKeys.KEY_MODIFIED_BASE_URL, conversationUser?.baseUrl)
|
bundle.putString(BundleKeys.KEY_MODIFIED_BASE_URL, conversationUser?.baseUrl!!)
|
||||||
bundle.putString(KEY_CONVERSATION_NAME, it.displayName)
|
bundle.putString(KEY_CONVERSATION_NAME, it.displayName)
|
||||||
bundle.putInt(KEY_RECORDING_STATE, it.callRecording)
|
bundle.putInt(KEY_RECORDING_STATE, it.callRecording)
|
||||||
bundle.putBoolean(KEY_IS_MODERATOR, ConversationUtils.isParticipantOwnerOrModerator(it))
|
bundle.putBoolean(KEY_IS_MODERATOR, ConversationUtils.isParticipantOwnerOrModerator(it))
|
||||||
|
@ -4147,7 +4185,8 @@ class ChatActivity :
|
||||||
conversationUser,
|
conversationUser,
|
||||||
currentConversation,
|
currentConversation,
|
||||||
isShowMessageDeletionButton(message),
|
isShowMessageDeletionButton(message),
|
||||||
participantPermissions.hasChatPermission()
|
participantPermissions.hasChatPermission(),
|
||||||
|
spreedCapabilities
|
||||||
).show()
|
).show()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -4156,7 +4195,7 @@ class ChatActivity :
|
||||||
return ChatMessage.MessageType.SYSTEM_MESSAGE == message.getCalculateMessageType()
|
return ChatMessage.MessageType.SYSTEM_MESSAGE == message.getCalculateMessageType()
|
||||||
}
|
}
|
||||||
|
|
||||||
fun deleteMessage(message: IMessage?) {
|
fun deleteMessage(message: IMessage) {
|
||||||
if (!participantPermissions.hasChatPermission()) {
|
if (!participantPermissions.hasChatPermission()) {
|
||||||
Log.w(
|
Log.w(
|
||||||
TAG,
|
TAG,
|
||||||
|
@ -4168,28 +4207,28 @@ class ChatActivity :
|
||||||
var apiVersion = 1
|
var apiVersion = 1
|
||||||
// FIXME Fix API checking with guests?
|
// FIXME Fix API checking with guests?
|
||||||
if (conversationUser != null) {
|
if (conversationUser != null) {
|
||||||
apiVersion = ApiUtils.getChatApiVersion(conversationUser, intArrayOf(1))
|
apiVersion = ApiUtils.getChatApiVersion(spreedCapabilities, intArrayOf(1))
|
||||||
}
|
}
|
||||||
|
|
||||||
chatViewModel.deleteChatMessages(
|
chatViewModel.deleteChatMessages(
|
||||||
credentials!!,
|
credentials!!,
|
||||||
ApiUtils.getUrlForChatMessage(
|
ApiUtils.getUrlForChatMessage(
|
||||||
apiVersion,
|
apiVersion,
|
||||||
conversationUser?.baseUrl,
|
conversationUser?.baseUrl!!,
|
||||||
roomToken,
|
roomToken,
|
||||||
message?.id
|
message.id!!
|
||||||
),
|
),
|
||||||
message?.id!!
|
message.id!!
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
fun replyPrivately(message: IMessage?) {
|
fun replyPrivately(message: IMessage?) {
|
||||||
val apiVersion =
|
val apiVersion =
|
||||||
ApiUtils.getConversationApiVersion(conversationUser, intArrayOf(ApiUtils.APIv4, 1))
|
ApiUtils.getConversationApiVersion(conversationUser!!, intArrayOf(ApiUtils.API_V4, 1))
|
||||||
val retrofitBucket = ApiUtils.getRetrofitBucketForCreateRoom(
|
val retrofitBucket = ApiUtils.getRetrofitBucketForCreateRoom(
|
||||||
apiVersion,
|
apiVersion,
|
||||||
conversationUser?.baseUrl,
|
conversationUser?.baseUrl!!,
|
||||||
"1",
|
"1",
|
||||||
null,
|
null,
|
||||||
message?.user?.id?.substring(INVITE_LENGTH),
|
message?.user?.id?.substring(INVITE_LENGTH),
|
||||||
|
@ -4215,10 +4254,14 @@ class ChatActivity :
|
||||||
|
|
||||||
fun remindMeLater(message: ChatMessage?) {
|
fun remindMeLater(message: ChatMessage?) {
|
||||||
Log.d(TAG, "remindMeLater called")
|
Log.d(TAG, "remindMeLater called")
|
||||||
|
|
||||||
|
val chatApiVersion = ApiUtils.getChatApiVersion(spreedCapabilities, intArrayOf(ApiUtils.API_V1, 1))
|
||||||
|
|
||||||
val newFragment: DialogFragment = DateTimePickerFragment.newInstance(
|
val newFragment: DialogFragment = DateTimePickerFragment.newInstance(
|
||||||
roomToken,
|
roomToken,
|
||||||
message!!.id,
|
message!!.id,
|
||||||
chatViewModel
|
chatViewModel,
|
||||||
|
chatApiVersion
|
||||||
)
|
)
|
||||||
newFragment.show(supportFragmentManager, DateTimePickerFragment.TAG)
|
newFragment.show(supportFragmentManager, DateTimePickerFragment.TAG)
|
||||||
}
|
}
|
||||||
|
@ -4229,8 +4272,8 @@ class ChatActivity :
|
||||||
chatViewModel.setChatReadMarker(
|
chatViewModel.setChatReadMarker(
|
||||||
credentials!!,
|
credentials!!,
|
||||||
ApiUtils.getUrlForChatReadMarker(
|
ApiUtils.getUrlForChatReadMarker(
|
||||||
ApiUtils.getChatApiVersion(conversationUser, intArrayOf(ApiUtils.APIv1)),
|
ApiUtils.getChatApiVersion(spreedCapabilities, intArrayOf(ApiUtils.API_V1)),
|
||||||
conversationUser?.baseUrl,
|
conversationUser?.baseUrl!!,
|
||||||
roomToken
|
roomToken
|
||||||
),
|
),
|
||||||
chatMessage.previousMessageId
|
chatMessage.previousMessageId
|
||||||
|
@ -4312,10 +4355,10 @@ class ChatActivity :
|
||||||
}
|
}
|
||||||
|
|
||||||
fun shareToNotes(message: ChatMessage, roomToken: String) {
|
fun shareToNotes(message: ChatMessage, roomToken: String) {
|
||||||
val apiVersion = ApiUtils.getChatApiVersion(conversationUser, intArrayOf(1))
|
val apiVersion = ApiUtils.getChatApiVersion(spreedCapabilities, intArrayOf(1))
|
||||||
val type = message.getCalculateMessageType()
|
val type = message.getCalculateMessageType()
|
||||||
var shareUri: Uri? = null
|
var shareUri: Uri? = null
|
||||||
var data: HashMap<String?, String?>?
|
val data: HashMap<String?, String?>?
|
||||||
var metaData: String = ""
|
var metaData: String = ""
|
||||||
var objectId: String = ""
|
var objectId: String = ""
|
||||||
if (message.hasFileAttachment()) {
|
if (message.hasFileAttachment()) {
|
||||||
|
@ -4335,9 +4378,9 @@ class ChatActivity :
|
||||||
} else if (message.hasGeoLocation()) {
|
} else if (message.hasGeoLocation()) {
|
||||||
data = message.messageParameters?.get("object")
|
data = message.messageParameters?.get("object")
|
||||||
objectId = data?.get("id")!!
|
objectId = data?.get("id")!!
|
||||||
val name = data.get("name")!!
|
val name = data["name"]!!
|
||||||
val lat = data.get("latitude")!!
|
val lat = data["latitude"]!!
|
||||||
val lon = data.get("longitude")!!
|
val lon = data["longitude"]!!
|
||||||
metaData =
|
metaData =
|
||||||
"{\"type\":\"geo-location\",\"id\":\"geo:$lat,$lon\",\"latitude\":\"$lat\"," +
|
"{\"type\":\"geo-location\",\"id\":\"geo:$lat,$lon\",\"latitude\":\"$lat\"," +
|
||||||
"\"longitude\":\"$lon\",\"name\":\"$name\"}"
|
"\"longitude\":\"$lon\",\"name\":\"$name\"}"
|
||||||
|
@ -4348,6 +4391,7 @@ class ChatActivity :
|
||||||
uploadFile(shareUri.toString(), true, token = roomToken)
|
uploadFile(shareUri.toString(), true, token = roomToken)
|
||||||
Snackbar.make(binding.root, R.string.nc_message_sent, Snackbar.LENGTH_SHORT).show()
|
Snackbar.make(binding.root, R.string.nc_message_sent, Snackbar.LENGTH_SHORT).show()
|
||||||
}
|
}
|
||||||
|
|
||||||
ChatMessage.MessageType.SINGLE_NC_ATTACHMENT_MESSAGE -> {
|
ChatMessage.MessageType.SINGLE_NC_ATTACHMENT_MESSAGE -> {
|
||||||
val caption = if (message.message != "{file}") message.message else ""
|
val caption = if (message.message != "{file}") message.message else ""
|
||||||
if (null != shareUri) {
|
if (null != shareUri) {
|
||||||
|
@ -4364,25 +4408,28 @@ class ChatActivity :
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
ChatMessage.MessageType.SINGLE_NC_GEOLOCATION_MESSAGE -> {
|
ChatMessage.MessageType.SINGLE_NC_GEOLOCATION_MESSAGE -> {
|
||||||
chatViewModel.shareLocationToNotes(
|
chatViewModel.shareLocationToNotes(
|
||||||
credentials!!,
|
credentials!!,
|
||||||
ApiUtils.getUrlToSendLocation(apiVersion, conversationUser!!.baseUrl, roomToken),
|
ApiUtils.getUrlToSendLocation(apiVersion, conversationUser!!.baseUrl!!, roomToken),
|
||||||
"geo-location",
|
"geo-location",
|
||||||
objectId,
|
objectId,
|
||||||
metaData
|
metaData
|
||||||
)
|
)
|
||||||
Snackbar.make(binding.root, R.string.nc_message_sent, Snackbar.LENGTH_SHORT).show()
|
Snackbar.make(binding.root, R.string.nc_message_sent, Snackbar.LENGTH_SHORT).show()
|
||||||
}
|
}
|
||||||
|
|
||||||
ChatMessage.MessageType.REGULAR_TEXT_MESSAGE -> {
|
ChatMessage.MessageType.REGULAR_TEXT_MESSAGE -> {
|
||||||
chatViewModel.shareToNotes(
|
chatViewModel.shareToNotes(
|
||||||
credentials!!,
|
credentials!!,
|
||||||
ApiUtils.getUrlForChat(apiVersion, conversationUser!!.baseUrl, roomToken),
|
ApiUtils.getUrlForChat(apiVersion, conversationUser!!.baseUrl!!, roomToken),
|
||||||
message.message!!,
|
message.message!!,
|
||||||
conversationUser!!.displayName!!
|
conversationUser!!.displayName!!
|
||||||
)
|
)
|
||||||
Snackbar.make(binding.root, R.string.nc_message_sent, Snackbar.LENGTH_SHORT).show()
|
Snackbar.make(binding.root, R.string.nc_message_sent, Snackbar.LENGTH_SHORT).show()
|
||||||
}
|
}
|
||||||
|
|
||||||
else -> {}
|
else -> {}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -4456,7 +4503,10 @@ class ChatActivity :
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun showMicrophoneButton(show: Boolean) {
|
private fun showMicrophoneButton(show: Boolean) {
|
||||||
if (show && CapabilitiesUtilNew.hasSpreedFeatureCapability(conversationUser, "voice-message-sharing")) {
|
if (show && CapabilitiesUtil.hasSpreedFeatureCapability(
|
||||||
|
spreedCapabilities, SpreedFeatures.VOICE_MESSAGE_SHARING
|
||||||
|
)
|
||||||
|
) {
|
||||||
Log.d(TAG, "Microphone shown")
|
Log.d(TAG, "Microphone shown")
|
||||||
binding.messageInputView.messageSendButton.visibility = View.GONE
|
binding.messageInputView.messageSendButton.visibility = View.GONE
|
||||||
binding.messageInputView.recordAudioButton.visibility = View.VISIBLE
|
binding.messageInputView.recordAudioButton.visibility = View.VISIBLE
|
||||||
|
@ -4542,7 +4592,7 @@ class ChatActivity :
|
||||||
!isUserAllowedByPrivileges -> false
|
!isUserAllowedByPrivileges -> false
|
||||||
message.systemMessageType != ChatMessage.SystemMessageType.DUMMY -> false
|
message.systemMessageType != ChatMessage.SystemMessageType.DUMMY -> false
|
||||||
message.isDeleted -> false
|
message.isDeleted -> false
|
||||||
!CapabilitiesUtilNew.hasSpreedFeatureCapability(conversationUser, "delete-messages") -> false
|
!CapabilitiesUtil.hasSpreedFeatureCapability(spreedCapabilities, SpreedFeatures.DELETE_MESSAGES) -> false
|
||||||
!participantPermissions.hasChatPermission() -> false
|
!participantPermissions.hasChatPermission() -> false
|
||||||
else -> true
|
else -> true
|
||||||
}
|
}
|
||||||
|
@ -4554,7 +4604,7 @@ class ChatActivity :
|
||||||
val isUserAllowedByPrivileges = if (message.actorId == conversationUser!!.userId) {
|
val isUserAllowedByPrivileges = if (message.actorId == conversationUser!!.userId) {
|
||||||
true
|
true
|
||||||
} else {
|
} else {
|
||||||
ConversationUtils.canModerate(currentConversation!!, conversationUser!!)
|
ConversationUtils.canModerate(currentConversation!!, spreedCapabilities)
|
||||||
}
|
}
|
||||||
return isUserAllowedByPrivileges
|
return isUserAllowedByPrivileges
|
||||||
}
|
}
|
||||||
|
@ -4628,12 +4678,12 @@ class ChatActivity :
|
||||||
var apiVersion = 1
|
var apiVersion = 1
|
||||||
// FIXME Fix API checking with guests?
|
// FIXME Fix API checking with guests?
|
||||||
if (conversationUser != null) {
|
if (conversationUser != null) {
|
||||||
apiVersion = ApiUtils.getConversationApiVersion(conversationUser, intArrayOf(ApiUtils.APIv4, 1))
|
apiVersion = ApiUtils.getConversationApiVersion(conversationUser!!, intArrayOf(ApiUtils.API_V4, 1))
|
||||||
}
|
}
|
||||||
|
|
||||||
val retrofitBucket = ApiUtils.getRetrofitBucketForCreateRoom(
|
val retrofitBucket = ApiUtils.getRetrofitBucketForCreateRoom(
|
||||||
apiVersion,
|
apiVersion,
|
||||||
conversationUser?.baseUrl,
|
conversationUser?.baseUrl!!,
|
||||||
"1",
|
"1",
|
||||||
null,
|
null,
|
||||||
userMentionClickEvent.userId,
|
userMentionClickEvent.userId,
|
||||||
|
|
|
@ -22,6 +22,7 @@ package com.nextcloud.talk.chat.data
|
||||||
|
|
||||||
import com.nextcloud.talk.data.user.model.User
|
import com.nextcloud.talk.data.user.model.User
|
||||||
import com.nextcloud.talk.models.domain.ConversationModel
|
import com.nextcloud.talk.models.domain.ConversationModel
|
||||||
|
import com.nextcloud.talk.models.json.capabilities.SpreedCapability
|
||||||
import com.nextcloud.talk.models.json.chat.ChatOverallSingleMessage
|
import com.nextcloud.talk.models.json.chat.ChatOverallSingleMessage
|
||||||
import com.nextcloud.talk.models.json.conversations.RoomOverall
|
import com.nextcloud.talk.models.json.conversations.RoomOverall
|
||||||
import com.nextcloud.talk.models.json.conversations.RoomsOverall
|
import com.nextcloud.talk.models.json.conversations.RoomsOverall
|
||||||
|
@ -33,10 +34,17 @@ import retrofit2.Response
|
||||||
@Suppress("LongParameterList", "TooManyFunctions")
|
@Suppress("LongParameterList", "TooManyFunctions")
|
||||||
interface ChatRepository {
|
interface ChatRepository {
|
||||||
fun getRoom(user: User, roomToken: String): Observable<ConversationModel>
|
fun getRoom(user: User, roomToken: String): Observable<ConversationModel>
|
||||||
|
fun getCapabilities(user: User, roomToken: String): Observable<SpreedCapability>
|
||||||
fun joinRoom(user: User, roomToken: String, roomPassword: String): Observable<ConversationModel>
|
fun joinRoom(user: User, roomToken: String, roomPassword: String): Observable<ConversationModel>
|
||||||
fun setReminder(user: User, roomToken: String, messageId: String, timeStamp: Int): Observable<Reminder>
|
fun setReminder(
|
||||||
fun getReminder(user: User, roomToken: String, messageId: String): Observable<Reminder>
|
user: User,
|
||||||
fun deleteReminder(user: User, roomToken: String, messageId: String): Observable<GenericOverall>
|
roomToken: String,
|
||||||
|
messageId: String,
|
||||||
|
timeStamp: Int,
|
||||||
|
chatApiVersion: Int
|
||||||
|
): Observable<Reminder>
|
||||||
|
fun getReminder(user: User, roomToken: String, messageId: String, apiVersion: Int): Observable<Reminder>
|
||||||
|
fun deleteReminder(user: User, roomToken: String, messageId: String, apiVersion: Int): Observable<GenericOverall>
|
||||||
fun shareToNotes(
|
fun shareToNotes(
|
||||||
credentials: String,
|
credentials: String,
|
||||||
url: String,
|
url: String,
|
||||||
|
|
|
@ -24,6 +24,7 @@ import com.nextcloud.talk.api.NcApi
|
||||||
import com.nextcloud.talk.chat.data.ChatRepository
|
import com.nextcloud.talk.chat.data.ChatRepository
|
||||||
import com.nextcloud.talk.data.user.model.User
|
import com.nextcloud.talk.data.user.model.User
|
||||||
import com.nextcloud.talk.models.domain.ConversationModel
|
import com.nextcloud.talk.models.domain.ConversationModel
|
||||||
|
import com.nextcloud.talk.models.json.capabilities.SpreedCapability
|
||||||
import com.nextcloud.talk.models.json.chat.ChatOverallSingleMessage
|
import com.nextcloud.talk.models.json.chat.ChatOverallSingleMessage
|
||||||
import com.nextcloud.talk.models.json.conversations.RoomOverall
|
import com.nextcloud.talk.models.json.conversations.RoomOverall
|
||||||
import com.nextcloud.talk.models.json.conversations.RoomsOverall
|
import com.nextcloud.talk.models.json.conversations.RoomsOverall
|
||||||
|
@ -35,55 +36,78 @@ import retrofit2.Response
|
||||||
|
|
||||||
class NetworkChatRepositoryImpl(private val ncApi: NcApi) : ChatRepository {
|
class NetworkChatRepositoryImpl(private val ncApi: NcApi) : ChatRepository {
|
||||||
override fun getRoom(user: User, roomToken: String): Observable<ConversationModel> {
|
override fun getRoom(user: User, roomToken: String): Observable<ConversationModel> {
|
||||||
val credentials: String = ApiUtils.getCredentials(user.username, user.token)
|
val credentials: String = ApiUtils.getCredentials(user.username, user.token)!!
|
||||||
val apiVersion = ApiUtils.getConversationApiVersion(user, intArrayOf(ApiUtils.APIv4, ApiUtils.APIv3, 1))
|
val apiVersion = ApiUtils.getConversationApiVersion(user, intArrayOf(ApiUtils.API_V4, ApiUtils.API_V3, 1))
|
||||||
|
|
||||||
return ncApi.getRoom(
|
return ncApi.getRoom(
|
||||||
credentials,
|
credentials,
|
||||||
ApiUtils.getUrlForRoom(apiVersion, user.baseUrl, roomToken)
|
ApiUtils.getUrlForRoom(apiVersion, user.baseUrl!!, roomToken)
|
||||||
).map { ConversationModel.mapToConversationModel(it.ocs?.data!!) }
|
).map { ConversationModel.mapToConversationModel(it.ocs?.data!!) }
|
||||||
}
|
}
|
||||||
|
|
||||||
|
override fun getCapabilities(user: User, roomToken: String): Observable<SpreedCapability> {
|
||||||
|
val credentials: String = ApiUtils.getCredentials(user.username, user.token)!!
|
||||||
|
val apiVersion = ApiUtils.getConversationApiVersion(user, intArrayOf(ApiUtils.API_V4, ApiUtils.API_V3, 1))
|
||||||
|
|
||||||
|
return ncApi.getRoomCapabilities(
|
||||||
|
credentials,
|
||||||
|
ApiUtils.getUrlForRoomCapabilities(apiVersion, user.baseUrl!!, roomToken)
|
||||||
|
).map { it.ocs?.data }
|
||||||
|
}
|
||||||
|
|
||||||
override fun joinRoom(user: User, roomToken: String, roomPassword: String): Observable<ConversationModel> {
|
override fun joinRoom(user: User, roomToken: String, roomPassword: String): Observable<ConversationModel> {
|
||||||
val credentials: String = ApiUtils.getCredentials(user.username, user.token)
|
val credentials: String = ApiUtils.getCredentials(user.username, user.token)!!
|
||||||
val apiVersion = ApiUtils.getConversationApiVersion(user, intArrayOf(ApiUtils.APIv4, 1))
|
val apiVersion = ApiUtils.getConversationApiVersion(user, intArrayOf(ApiUtils.API_V4, 1))
|
||||||
|
|
||||||
return ncApi.joinRoom(
|
return ncApi.joinRoom(
|
||||||
credentials,
|
credentials,
|
||||||
ApiUtils.getUrlForParticipantsActive(apiVersion, user.baseUrl, roomToken),
|
ApiUtils.getUrlForParticipantsActive(apiVersion, user.baseUrl!!, roomToken),
|
||||||
roomPassword
|
roomPassword
|
||||||
).map { ConversationModel.mapToConversationModel(it.ocs?.data!!) }
|
).map { ConversationModel.mapToConversationModel(it.ocs?.data!!) }
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun setReminder(user: User, roomToken: String, messageId: String, timeStamp: Int): Observable<Reminder> {
|
override fun setReminder(
|
||||||
val credentials: String = ApiUtils.getCredentials(user.username, user.token)
|
user: User,
|
||||||
val apiVersion = ApiUtils.getChatApiVersion(user, intArrayOf(ApiUtils.APIv1, 1))
|
roomToken: String,
|
||||||
|
messageId: String,
|
||||||
|
timeStamp: Int,
|
||||||
|
chatApiVersion: Int
|
||||||
|
): Observable<Reminder> {
|
||||||
|
val credentials: String = ApiUtils.getCredentials(user.username, user.token)!!
|
||||||
return ncApi.setReminder(
|
return ncApi.setReminder(
|
||||||
credentials,
|
credentials,
|
||||||
ApiUtils.getUrlForReminder(user, roomToken, messageId, apiVersion),
|
ApiUtils.getUrlForReminder(user, roomToken, messageId, chatApiVersion),
|
||||||
timeStamp
|
timeStamp
|
||||||
).map {
|
).map {
|
||||||
it.ocs!!.data
|
it.ocs!!.data
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun getReminder(user: User, roomToken: String, messageId: String): Observable<Reminder> {
|
override fun getReminder(
|
||||||
val credentials: String = ApiUtils.getCredentials(user.username, user.token)
|
user: User,
|
||||||
val apiVersion = ApiUtils.getChatApiVersion(user, intArrayOf(ApiUtils.APIv1, 1))
|
roomToken: String,
|
||||||
|
messageId: String,
|
||||||
|
chatApiVersion: Int
|
||||||
|
): Observable<Reminder> {
|
||||||
|
val credentials: String = ApiUtils.getCredentials(user.username, user.token)!!
|
||||||
return ncApi.getReminder(
|
return ncApi.getReminder(
|
||||||
credentials,
|
credentials,
|
||||||
ApiUtils.getUrlForReminder(user, roomToken, messageId, apiVersion)
|
ApiUtils.getUrlForReminder(user, roomToken, messageId, chatApiVersion)
|
||||||
).map {
|
).map {
|
||||||
it.ocs!!.data
|
it.ocs!!.data
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun deleteReminder(user: User, roomToken: String, messageId: String): Observable<GenericOverall> {
|
override fun deleteReminder(
|
||||||
val credentials: String = ApiUtils.getCredentials(user.username, user.token)
|
user: User,
|
||||||
val apiVersion = ApiUtils.getChatApiVersion(user, intArrayOf(ApiUtils.APIv1, 1))
|
roomToken: String,
|
||||||
|
messageId: String,
|
||||||
|
chatApiVersion: Int
|
||||||
|
): Observable<GenericOverall> {
|
||||||
|
val credentials: String = ApiUtils.getCredentials(user.username, user.token)!!
|
||||||
return ncApi.deleteReminder(
|
return ncApi.deleteReminder(
|
||||||
credentials,
|
credentials,
|
||||||
ApiUtils.getUrlForReminder(user, roomToken, messageId, apiVersion)
|
ApiUtils.getUrlForReminder(user, roomToken, messageId, chatApiVersion)
|
||||||
).map {
|
).map {
|
||||||
it
|
it
|
||||||
}
|
}
|
||||||
|
|
|
@ -31,6 +31,7 @@ import com.nextcloud.talk.data.user.model.User
|
||||||
import com.nextcloud.talk.models.domain.ConversationModel
|
import com.nextcloud.talk.models.domain.ConversationModel
|
||||||
import com.nextcloud.talk.models.domain.ReactionAddedModel
|
import com.nextcloud.talk.models.domain.ReactionAddedModel
|
||||||
import com.nextcloud.talk.models.domain.ReactionDeletedModel
|
import com.nextcloud.talk.models.domain.ReactionDeletedModel
|
||||||
|
import com.nextcloud.talk.models.json.capabilities.SpreedCapability
|
||||||
import com.nextcloud.talk.models.json.chat.ChatMessage
|
import com.nextcloud.talk.models.json.chat.ChatMessage
|
||||||
import com.nextcloud.talk.models.json.chat.ChatOverallSingleMessage
|
import com.nextcloud.talk.models.json.chat.ChatOverallSingleMessage
|
||||||
import com.nextcloud.talk.models.json.conversations.RoomOverall
|
import com.nextcloud.talk.models.json.conversations.RoomOverall
|
||||||
|
@ -105,6 +106,14 @@ class ChatViewModel @Inject constructor(
|
||||||
val getRoomViewState: LiveData<ViewState>
|
val getRoomViewState: LiveData<ViewState>
|
||||||
get() = _getRoomViewState
|
get() = _getRoomViewState
|
||||||
|
|
||||||
|
object GetCapabilitiesStartState : ViewState
|
||||||
|
object GetCapabilitiesErrorState : ViewState
|
||||||
|
open class GetCapabilitiesSuccessState(val spreedCapabilities: SpreedCapability) : ViewState
|
||||||
|
|
||||||
|
private val _getCapabilitiesViewState: MutableLiveData<ViewState> = MutableLiveData(GetCapabilitiesStartState)
|
||||||
|
val getCapabilitiesViewState: LiveData<ViewState>
|
||||||
|
get() = _getCapabilitiesViewState
|
||||||
|
|
||||||
object JoinRoomStartState : ViewState
|
object JoinRoomStartState : ViewState
|
||||||
object JoinRoomErrorState : ViewState
|
object JoinRoomErrorState : ViewState
|
||||||
open class JoinRoomSuccessState(val conversationModel: ConversationModel) : ViewState
|
open class JoinRoomSuccessState(val conversationModel: ConversationModel) : ViewState
|
||||||
|
@ -184,6 +193,36 @@ class ChatViewModel @Inject constructor(
|
||||||
?.subscribe(GetRoomObserver())
|
?.subscribe(GetRoomObserver())
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fun getCapabilities(user: User, token: String, conversationModel: ConversationModel) {
|
||||||
|
_getCapabilitiesViewState.value = GetCapabilitiesStartState
|
||||||
|
|
||||||
|
if (conversationModel.remoteServer.isNullOrEmpty()) {
|
||||||
|
_getCapabilitiesViewState.value = GetCapabilitiesSuccessState(user.capabilities!!.spreedCapability!!)
|
||||||
|
} else {
|
||||||
|
chatRepository.getCapabilities(user, token)
|
||||||
|
.subscribeOn(Schedulers.io())
|
||||||
|
?.observeOn(AndroidSchedulers.mainThread())
|
||||||
|
?.subscribe(object : Observer<SpreedCapability> {
|
||||||
|
override fun onSubscribe(d: Disposable) {
|
||||||
|
LifeCycleObserver.disposableSet.add(d)
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onNext(spreedCapabilities: SpreedCapability) {
|
||||||
|
_getCapabilitiesViewState.value = GetCapabilitiesSuccessState(spreedCapabilities)
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onError(e: Throwable) {
|
||||||
|
Log.e(TAG, "Error when fetching spreed capabilities", e)
|
||||||
|
_getCapabilitiesViewState.value = GetCapabilitiesErrorState
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onComplete() {
|
||||||
|
// unused atm
|
||||||
|
}
|
||||||
|
})
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
fun joinRoom(user: User, token: String, roomPassword: String) {
|
fun joinRoom(user: User, token: String, roomPassword: String) {
|
||||||
_joinRoomViewState.value = JoinRoomStartState
|
_joinRoomViewState.value = JoinRoomStartState
|
||||||
chatRepository.joinRoom(user, token, roomPassword)
|
chatRepository.joinRoom(user, token, roomPassword)
|
||||||
|
@ -193,6 +232,43 @@ class ChatViewModel @Inject constructor(
|
||||||
?.subscribe(JoinRoomObserver())
|
?.subscribe(JoinRoomObserver())
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fun setReminder(user: User, roomToken: String, messageId: String, timestamp: Int, chatApiVersion: Int) {
|
||||||
|
chatRepository.setReminder(user, roomToken, messageId, timestamp, chatApiVersion)
|
||||||
|
.subscribeOn(Schedulers.io())
|
||||||
|
?.observeOn(AndroidSchedulers.mainThread())
|
||||||
|
?.subscribe(SetReminderObserver())
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getReminder(user: User, roomToken: String, messageId: String, chatApiVersion: Int) {
|
||||||
|
chatRepository.getReminder(user, roomToken, messageId, chatApiVersion)
|
||||||
|
.subscribeOn(Schedulers.io())
|
||||||
|
?.observeOn(AndroidSchedulers.mainThread())
|
||||||
|
?.subscribe(GetReminderObserver())
|
||||||
|
}
|
||||||
|
|
||||||
|
fun deleteReminder(user: User, roomToken: String, messageId: String, chatApiVersion: Int) {
|
||||||
|
chatRepository.deleteReminder(user, roomToken, messageId, chatApiVersion)
|
||||||
|
.subscribeOn(Schedulers.io())
|
||||||
|
?.observeOn(AndroidSchedulers.mainThread())
|
||||||
|
?.subscribe(object : Observer<GenericOverall> {
|
||||||
|
override fun onSubscribe(d: Disposable) {
|
||||||
|
LifeCycleObserver.disposableSet.add(d)
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onNext(genericOverall: GenericOverall) {
|
||||||
|
_getReminderExistState.value = GetReminderStartState
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onError(e: Throwable) {
|
||||||
|
Log.d(TAG, "Error when deleting reminder", e)
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onComplete() {
|
||||||
|
// unused atm
|
||||||
|
}
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
fun leaveRoom(credentials: String, url: String, funToCallWhenLeaveSuccessful: (() -> Unit)?) {
|
fun leaveRoom(credentials: String, url: String, funToCallWhenLeaveSuccessful: (() -> Unit)?) {
|
||||||
val startNanoTime = System.nanoTime()
|
val startNanoTime = System.nanoTime()
|
||||||
chatRepository.leaveRoom(credentials, url)
|
chatRepository.leaveRoom(credentials, url)
|
||||||
|
@ -357,43 +433,6 @@ class ChatViewModel @Inject constructor(
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
fun setReminder(user: User, roomToken: String, messageId: String, timestamp: Int) {
|
|
||||||
chatRepository.setReminder(user, roomToken, messageId, timestamp)
|
|
||||||
.subscribeOn(Schedulers.io())
|
|
||||||
?.observeOn(AndroidSchedulers.mainThread())
|
|
||||||
?.subscribe(SetReminderObserver())
|
|
||||||
}
|
|
||||||
|
|
||||||
fun getReminder(user: User, roomToken: String, messageId: String) {
|
|
||||||
chatRepository.getReminder(user, roomToken, messageId)
|
|
||||||
.subscribeOn(Schedulers.io())
|
|
||||||
?.observeOn(AndroidSchedulers.mainThread())
|
|
||||||
?.subscribe(GetReminderObserver())
|
|
||||||
}
|
|
||||||
|
|
||||||
fun deleteReminder(user: User, roomToken: String, messageId: String) {
|
|
||||||
chatRepository.deleteReminder(user, roomToken, messageId)
|
|
||||||
.subscribeOn(Schedulers.io())
|
|
||||||
?.observeOn(AndroidSchedulers.mainThread())
|
|
||||||
?.subscribe(object : Observer<GenericOverall> {
|
|
||||||
override fun onSubscribe(d: Disposable) {
|
|
||||||
LifeCycleObserver.disposableSet.add(d)
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun onNext(genericOverall: GenericOverall) {
|
|
||||||
_getReminderExistState.value = GetReminderStartState
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun onError(e: Throwable) {
|
|
||||||
Log.d(TAG, "Error when deleting reminder $e")
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun onComplete() {
|
|
||||||
// unused atm
|
|
||||||
}
|
|
||||||
})
|
|
||||||
}
|
|
||||||
|
|
||||||
fun shareToNotes(credentials: String, url: String, message: String, displayName: String) {
|
fun shareToNotes(credentials: String, url: String, message: String, displayName: String) {
|
||||||
chatRepository.shareToNotes(credentials, url, message, displayName)
|
chatRepository.shareToNotes(credentials, url, message, displayName)
|
||||||
.subscribeOn(Schedulers.io())
|
.subscribeOn(Schedulers.io())
|
||||||
|
@ -522,7 +561,7 @@ class ChatViewModel @Inject constructor(
|
||||||
|
|
||||||
inner class GetRoomObserver : Observer<ConversationModel> {
|
inner class GetRoomObserver : Observer<ConversationModel> {
|
||||||
override fun onSubscribe(d: Disposable) {
|
override fun onSubscribe(d: Disposable) {
|
||||||
LifeCycleObserver.disposableSet.add(d)
|
// unused atm
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onNext(conversationModel: ConversationModel) {
|
override fun onNext(conversationModel: ConversationModel) {
|
||||||
|
|
|
@ -65,7 +65,7 @@ class ReadFolderListingOperation(okHttpClient: OkHttpClient, currentUser: User,
|
||||||
ApiUtils.getCredentials(
|
ApiUtils.getCredentials(
|
||||||
currentUser.username,
|
currentUser.username,
|
||||||
currentUser.token
|
currentUser.token
|
||||||
),
|
)!!,
|
||||||
"Authorization"
|
"Authorization"
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
|
|
|
@ -68,9 +68,10 @@ import com.nextcloud.talk.models.json.participants.Participant
|
||||||
import com.nextcloud.talk.openconversations.ListOpenConversationsActivity
|
import com.nextcloud.talk.openconversations.ListOpenConversationsActivity
|
||||||
import com.nextcloud.talk.users.UserManager
|
import com.nextcloud.talk.users.UserManager
|
||||||
import com.nextcloud.talk.utils.ApiUtils
|
import com.nextcloud.talk.utils.ApiUtils
|
||||||
|
import com.nextcloud.talk.utils.SpreedFeatures
|
||||||
import com.nextcloud.talk.utils.UserIdUtils.getIdForUser
|
import com.nextcloud.talk.utils.UserIdUtils.getIdForUser
|
||||||
import com.nextcloud.talk.utils.bundle.BundleKeys
|
import com.nextcloud.talk.utils.bundle.BundleKeys
|
||||||
import com.nextcloud.talk.utils.database.user.CapabilitiesUtilNew
|
import com.nextcloud.talk.utils.CapabilitiesUtil
|
||||||
import eu.davidea.flexibleadapter.FlexibleAdapter
|
import eu.davidea.flexibleadapter.FlexibleAdapter
|
||||||
import eu.davidea.flexibleadapter.SelectableAdapter
|
import eu.davidea.flexibleadapter.SelectableAdapter
|
||||||
import eu.davidea.flexibleadapter.common.SmoothScrollLinearLayoutManager
|
import eu.davidea.flexibleadapter.common.SmoothScrollLinearLayoutManager
|
||||||
|
@ -318,10 +319,10 @@ class ContactsActivity :
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun createRoom(roomType: String, sourceType: String?, userId: String) {
|
private fun createRoom(roomType: String, sourceType: String?, userId: String) {
|
||||||
val apiVersion: Int = ApiUtils.getConversationApiVersion(currentUser, intArrayOf(ApiUtils.APIv4, 1))
|
val apiVersion: Int = ApiUtils.getConversationApiVersion(currentUser!!, intArrayOf(ApiUtils.API_V4, 1))
|
||||||
val retrofitBucket: RetrofitBucket = ApiUtils.getRetrofitBucketForCreateRoom(
|
val retrofitBucket: RetrofitBucket = ApiUtils.getRetrofitBucketForCreateRoom(
|
||||||
apiVersion,
|
apiVersion,
|
||||||
currentUser!!.baseUrl,
|
currentUser!!.baseUrl!!,
|
||||||
roomType,
|
roomType,
|
||||||
sourceType,
|
sourceType,
|
||||||
userId,
|
userId,
|
||||||
|
@ -438,7 +439,7 @@ class ContactsActivity :
|
||||||
userHeaderItems = HashMap()
|
userHeaderItems = HashMap()
|
||||||
val query = adapter!!.getFilter(String::class.java)
|
val query = adapter!!.getFilter(String::class.java)
|
||||||
val retrofitBucket: RetrofitBucket =
|
val retrofitBucket: RetrofitBucket =
|
||||||
ApiUtils.getRetrofitBucketForContactsSearchFor14(currentUser!!.baseUrl, query)
|
ApiUtils.getRetrofitBucketForContactsSearchFor14(currentUser!!.baseUrl!!, query)
|
||||||
val modifiedQueryMap: HashMap<String, Any?> = HashMap(retrofitBucket.queryMap)
|
val modifiedQueryMap: HashMap<String, Any?> = HashMap(retrofitBucket.queryMap)
|
||||||
modifiedQueryMap["limit"] = CONTACTS_BATCH_SIZE
|
modifiedQueryMap["limit"] = CONTACTS_BATCH_SIZE
|
||||||
if (isAddingParticipantsView) {
|
if (isAddingParticipantsView) {
|
||||||
|
@ -450,13 +451,21 @@ class ContactsActivity :
|
||||||
if (!isAddingParticipantsView) {
|
if (!isAddingParticipantsView) {
|
||||||
// groups
|
// groups
|
||||||
shareTypesList.add("1")
|
shareTypesList.add("1")
|
||||||
} else if (CapabilitiesUtilNew.hasSpreedFeatureCapability(currentUser, "invite-groups-and-mails")) {
|
} else if (CapabilitiesUtil.hasSpreedFeatureCapability(
|
||||||
|
currentUser?.capabilities?.spreedCapability!!,
|
||||||
|
SpreedFeatures.INVITE_GROUPS_AND_MAILS
|
||||||
|
)
|
||||||
|
) {
|
||||||
// groups
|
// groups
|
||||||
shareTypesList.add("1")
|
shareTypesList.add("1")
|
||||||
// emails
|
// emails
|
||||||
shareTypesList.add("4")
|
shareTypesList.add("4")
|
||||||
}
|
}
|
||||||
if (CapabilitiesUtilNew.hasSpreedFeatureCapability(currentUser, "circles-support")) {
|
if (CapabilitiesUtil.hasSpreedFeatureCapability(
|
||||||
|
currentUser?.capabilities?.spreedCapability!!,
|
||||||
|
SpreedFeatures.CIRCLES_SUPPORT
|
||||||
|
)
|
||||||
|
) {
|
||||||
// circles
|
// circles
|
||||||
shareTypesList.add("7")
|
shareTypesList.add("7")
|
||||||
}
|
}
|
||||||
|
@ -745,8 +754,12 @@ class ContactsActivity :
|
||||||
private fun updateSelection(contactItem: ContactItem) {
|
private fun updateSelection(contactItem: ContactItem) {
|
||||||
contactItem.model.selected = !contactItem.model.selected
|
contactItem.model.selected = !contactItem.model.selected
|
||||||
updateSelectionLists(contactItem.model)
|
updateSelectionLists(contactItem.model)
|
||||||
if (CapabilitiesUtilNew.hasSpreedFeatureCapability(currentUser, "last-room-activity") &&
|
if (CapabilitiesUtil.hasSpreedFeatureCapability(
|
||||||
!CapabilitiesUtilNew.hasSpreedFeatureCapability(currentUser, "invite-groups-and-mails") &&
|
currentUser?.capabilities?.spreedCapability!!, SpreedFeatures.LAST_ROOM_ACTIVITY
|
||||||
|
) &&
|
||||||
|
!CapabilitiesUtil.hasSpreedFeatureCapability(
|
||||||
|
currentUser?.capabilities?.spreedCapability!!, SpreedFeatures.INVITE_GROUPS_AND_MAILS
|
||||||
|
) &&
|
||||||
isValidGroupSelection(contactItem, contactItem.model, adapter)
|
isValidGroupSelection(contactItem, contactItem.model, adapter)
|
||||||
) {
|
) {
|
||||||
val currentItems: List<ContactItem> = adapter?.currentItems as List<ContactItem>
|
val currentItems: List<ContactItem> = adapter?.currentItems as List<ContactItem>
|
||||||
|
@ -771,10 +784,10 @@ class ContactsActivity :
|
||||||
if ("groups" == contactItem.model.source) {
|
if ("groups" == contactItem.model.source) {
|
||||||
roomType = "2"
|
roomType = "2"
|
||||||
}
|
}
|
||||||
val apiVersion: Int = ApiUtils.getConversationApiVersion(currentUser, intArrayOf(ApiUtils.APIv4, 1))
|
val apiVersion: Int = ApiUtils.getConversationApiVersion(currentUser!!, intArrayOf(ApiUtils.API_V4, 1))
|
||||||
val retrofitBucket: RetrofitBucket = ApiUtils.getRetrofitBucketForCreateRoom(
|
val retrofitBucket: RetrofitBucket = ApiUtils.getRetrofitBucketForCreateRoom(
|
||||||
apiVersion,
|
apiVersion,
|
||||||
currentUser!!.baseUrl,
|
currentUser!!.baseUrl!!,
|
||||||
roomType,
|
roomType,
|
||||||
null,
|
null,
|
||||||
contactItem.model.calculatedActorId,
|
contactItem.model.calculatedActorId,
|
||||||
|
|
|
@ -36,16 +36,16 @@ class ConversationRepositoryImpl(private val ncApi: NcApi, currentUserProvider:
|
||||||
ConversationRepository {
|
ConversationRepository {
|
||||||
|
|
||||||
val currentUser: User = currentUserProvider.currentUser.blockingGet()
|
val currentUser: User = currentUserProvider.currentUser.blockingGet()
|
||||||
val credentials: String = ApiUtils.getCredentials(currentUser.username, currentUser.token)
|
val credentials: String = ApiUtils.getCredentials(currentUser.username, currentUser.token)!!
|
||||||
|
|
||||||
override fun renameConversation(roomToken: String, roomNameNew: String): Observable<GenericOverall> {
|
override fun renameConversation(roomToken: String, roomNameNew: String): Observable<GenericOverall> {
|
||||||
val apiVersion = ApiUtils.getConversationApiVersion(currentUser, intArrayOf(ApiUtils.APIv4, ApiUtils.APIv1))
|
val apiVersion = ApiUtils.getConversationApiVersion(currentUser, intArrayOf(ApiUtils.API_V4, ApiUtils.API_V1))
|
||||||
|
|
||||||
return ncApi.renameRoom(
|
return ncApi.renameRoom(
|
||||||
credentials,
|
credentials,
|
||||||
ApiUtils.getUrlForRoom(
|
ApiUtils.getUrlForRoom(
|
||||||
apiVersion,
|
apiVersion,
|
||||||
currentUser.baseUrl,
|
currentUser.baseUrl!!,
|
||||||
roomToken
|
roomToken
|
||||||
),
|
),
|
||||||
roomNameNew
|
roomNameNew
|
||||||
|
@ -59,12 +59,12 @@ class ConversationRepositoryImpl(private val ncApi: NcApi, currentUserProvider:
|
||||||
roomName: String,
|
roomName: String,
|
||||||
conversationType: Conversation.ConversationType?
|
conversationType: Conversation.ConversationType?
|
||||||
): Observable<RoomOverall> {
|
): Observable<RoomOverall> {
|
||||||
val apiVersion = ApiUtils.getConversationApiVersion(currentUser, intArrayOf(ApiUtils.APIv4, ApiUtils.APIv1))
|
val apiVersion = ApiUtils.getConversationApiVersion(currentUser, intArrayOf(ApiUtils.API_V4, ApiUtils.API_V1))
|
||||||
|
|
||||||
val retrofitBucket: RetrofitBucket = if (conversationType == Conversation.ConversationType.ROOM_PUBLIC_CALL) {
|
val retrofitBucket: RetrofitBucket = if (conversationType == Conversation.ConversationType.ROOM_PUBLIC_CALL) {
|
||||||
ApiUtils.getRetrofitBucketForCreateRoom(
|
ApiUtils.getRetrofitBucketForCreateRoom(
|
||||||
apiVersion,
|
apiVersion,
|
||||||
currentUser.baseUrl,
|
currentUser.baseUrl!!,
|
||||||
ROOM_TYPE_PUBLIC,
|
ROOM_TYPE_PUBLIC,
|
||||||
null,
|
null,
|
||||||
null,
|
null,
|
||||||
|
@ -73,7 +73,7 @@ class ConversationRepositoryImpl(private val ncApi: NcApi, currentUserProvider:
|
||||||
} else {
|
} else {
|
||||||
ApiUtils.getRetrofitBucketForCreateRoom(
|
ApiUtils.getRetrofitBucketForCreateRoom(
|
||||||
apiVersion,
|
apiVersion,
|
||||||
currentUser.baseUrl,
|
currentUser.baseUrl!!,
|
||||||
ROOM_TYPE_GROUP,
|
ROOM_TYPE_GROUP,
|
||||||
null,
|
null,
|
||||||
null,
|
null,
|
||||||
|
|
|
@ -40,6 +40,7 @@ import android.view.View
|
||||||
import android.view.View.GONE
|
import android.view.View.GONE
|
||||||
import android.view.View.VISIBLE
|
import android.view.View.VISIBLE
|
||||||
import androidx.appcompat.app.AlertDialog
|
import androidx.appcompat.app.AlertDialog
|
||||||
|
import androidx.lifecycle.ViewModelProvider
|
||||||
import androidx.work.Data
|
import androidx.work.Data
|
||||||
import androidx.work.OneTimeWorkRequest
|
import androidx.work.OneTimeWorkRequest
|
||||||
import androidx.work.WorkManager
|
import androidx.work.WorkManager
|
||||||
|
@ -61,6 +62,7 @@ import com.nextcloud.talk.bottomsheet.items.BasicListItemWithImage
|
||||||
import com.nextcloud.talk.bottomsheet.items.listItemsWithImage
|
import com.nextcloud.talk.bottomsheet.items.listItemsWithImage
|
||||||
import com.nextcloud.talk.contacts.ContactsActivity
|
import com.nextcloud.talk.contacts.ContactsActivity
|
||||||
import com.nextcloud.talk.conversationinfoedit.ConversationInfoEditActivity
|
import com.nextcloud.talk.conversationinfoedit.ConversationInfoEditActivity
|
||||||
|
import com.nextcloud.talk.conversationinfo.viewmodel.ConversationInfoViewModel
|
||||||
import com.nextcloud.talk.data.user.model.User
|
import com.nextcloud.talk.data.user.model.User
|
||||||
import com.nextcloud.talk.databinding.ActivityConversationInfoBinding
|
import com.nextcloud.talk.databinding.ActivityConversationInfoBinding
|
||||||
import com.nextcloud.talk.events.EventStatus
|
import com.nextcloud.talk.events.EventStatus
|
||||||
|
@ -71,9 +73,11 @@ import com.nextcloud.talk.extensions.loadUserAvatar
|
||||||
import com.nextcloud.talk.jobs.DeleteConversationWorker
|
import com.nextcloud.talk.jobs.DeleteConversationWorker
|
||||||
import com.nextcloud.talk.jobs.LeaveConversationWorker
|
import com.nextcloud.talk.jobs.LeaveConversationWorker
|
||||||
import com.nextcloud.talk.models.domain.ConversationModel
|
import com.nextcloud.talk.models.domain.ConversationModel
|
||||||
import com.nextcloud.talk.models.json.conversations.Conversation
|
import com.nextcloud.talk.models.domain.ConversationType
|
||||||
import com.nextcloud.talk.models.json.conversations.RoomOverall
|
import com.nextcloud.talk.models.domain.LobbyState
|
||||||
import com.nextcloud.talk.models.json.converters.EnumNotificationLevelConverter
|
import com.nextcloud.talk.models.domain.NotificationLevel
|
||||||
|
import com.nextcloud.talk.models.domain.converters.DomainEnumNotificationLevelConverter
|
||||||
|
import com.nextcloud.talk.models.json.capabilities.SpreedCapability
|
||||||
import com.nextcloud.talk.models.json.generic.GenericOverall
|
import com.nextcloud.talk.models.json.generic.GenericOverall
|
||||||
import com.nextcloud.talk.models.json.participants.Participant
|
import com.nextcloud.talk.models.json.participants.Participant
|
||||||
import com.nextcloud.talk.models.json.participants.Participant.ActorType.CIRCLES
|
import com.nextcloud.talk.models.json.participants.Participant.ActorType.CIRCLES
|
||||||
|
@ -83,11 +87,12 @@ import com.nextcloud.talk.models.json.participants.ParticipantsOverall
|
||||||
import com.nextcloud.talk.repositories.conversations.ConversationsRepository
|
import com.nextcloud.talk.repositories.conversations.ConversationsRepository
|
||||||
import com.nextcloud.talk.shareditems.activities.SharedItemsActivity
|
import com.nextcloud.talk.shareditems.activities.SharedItemsActivity
|
||||||
import com.nextcloud.talk.utils.ApiUtils
|
import com.nextcloud.talk.utils.ApiUtils
|
||||||
|
import com.nextcloud.talk.utils.SpreedFeatures
|
||||||
import com.nextcloud.talk.utils.ConversationUtils
|
import com.nextcloud.talk.utils.ConversationUtils
|
||||||
import com.nextcloud.talk.utils.DateConstants
|
import com.nextcloud.talk.utils.DateConstants
|
||||||
import com.nextcloud.talk.utils.DateUtils
|
import com.nextcloud.talk.utils.DateUtils
|
||||||
import com.nextcloud.talk.utils.bundle.BundleKeys
|
import com.nextcloud.talk.utils.bundle.BundleKeys
|
||||||
import com.nextcloud.talk.utils.database.user.CapabilitiesUtilNew
|
import com.nextcloud.talk.utils.CapabilitiesUtil
|
||||||
import com.nextcloud.talk.utils.database.user.CurrentUserProviderNew
|
import com.nextcloud.talk.utils.database.user.CurrentUserProviderNew
|
||||||
import com.nextcloud.talk.utils.preferences.preferencestorage.DatabaseStorageModule
|
import com.nextcloud.talk.utils.preferences.preferencestorage.DatabaseStorageModule
|
||||||
import eu.davidea.flexibleadapter.FlexibleAdapter
|
import eu.davidea.flexibleadapter.FlexibleAdapter
|
||||||
|
@ -109,6 +114,9 @@ class ConversationInfoActivity :
|
||||||
FlexibleAdapter.OnItemClickListener {
|
FlexibleAdapter.OnItemClickListener {
|
||||||
private lateinit var binding: ActivityConversationInfoBinding
|
private lateinit var binding: ActivityConversationInfoBinding
|
||||||
|
|
||||||
|
@Inject
|
||||||
|
lateinit var viewModelFactory: ViewModelProvider.Factory
|
||||||
|
|
||||||
@Inject
|
@Inject
|
||||||
lateinit var ncApi: NcApi
|
lateinit var ncApi: NcApi
|
||||||
|
|
||||||
|
@ -121,6 +129,10 @@ class ConversationInfoActivity :
|
||||||
@Inject
|
@Inject
|
||||||
lateinit var dateUtils: DateUtils
|
lateinit var dateUtils: DateUtils
|
||||||
|
|
||||||
|
lateinit var viewModel: ConversationInfoViewModel
|
||||||
|
|
||||||
|
private lateinit var spreedCapabilities: SpreedCapability
|
||||||
|
|
||||||
private lateinit var conversationToken: String
|
private lateinit var conversationToken: String
|
||||||
private lateinit var conversationUser: User
|
private lateinit var conversationUser: User
|
||||||
private var hasAvatarSpacing: Boolean = false
|
private var hasAvatarSpacing: Boolean = false
|
||||||
|
@ -129,7 +141,9 @@ class ConversationInfoActivity :
|
||||||
private var participantsDisposable: Disposable? = null
|
private var participantsDisposable: Disposable? = null
|
||||||
|
|
||||||
private var databaseStorageModule: DatabaseStorageModule? = null
|
private var databaseStorageModule: DatabaseStorageModule? = null
|
||||||
private var conversation: Conversation? = null
|
|
||||||
|
// private var conversation: Conversation? = null
|
||||||
|
private var conversation: ConversationModel? = null
|
||||||
|
|
||||||
private var adapter: FlexibleAdapter<ParticipantItem>? = null
|
private var adapter: FlexibleAdapter<ParticipantItem>? = null
|
||||||
private var userItems: MutableList<ParticipantItem> = ArrayList()
|
private var userItems: MutableList<ParticipantItem> = ArrayList()
|
||||||
|
@ -157,11 +171,26 @@ class ConversationInfoActivity :
|
||||||
setContentView(binding.root)
|
setContentView(binding.root)
|
||||||
setupSystemColors()
|
setupSystemColors()
|
||||||
|
|
||||||
|
viewModel =
|
||||||
|
ViewModelProvider(this, viewModelFactory)[ConversationInfoViewModel::class.java]
|
||||||
|
|
||||||
conversationUser = currentUserProvider.currentUser.blockingGet()
|
conversationUser = currentUserProvider.currentUser.blockingGet()
|
||||||
|
|
||||||
conversationToken = intent.getStringExtra(BundleKeys.KEY_ROOM_TOKEN)!!
|
conversationToken = intent.getStringExtra(BundleKeys.KEY_ROOM_TOKEN)!!
|
||||||
hasAvatarSpacing = intent.getBooleanExtra(BundleKeys.KEY_ROOM_ONE_TO_ONE, false)
|
hasAvatarSpacing = intent.getBooleanExtra(BundleKeys.KEY_ROOM_ONE_TO_ONE, false)
|
||||||
credentials = ApiUtils.getCredentials(conversationUser.username, conversationUser.token)
|
credentials = ApiUtils.getCredentials(conversationUser.username, conversationUser.token)!!
|
||||||
|
|
||||||
|
initObservers()
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onStart() {
|
||||||
|
super.onStart()
|
||||||
|
this.lifecycle.addObserver(ConversationInfoViewModel.LifeCycleObserver)
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onStop() {
|
||||||
|
super.onStop()
|
||||||
|
this.lifecycle.removeObserver(ConversationInfoViewModel.LifeCycleObserver)
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onResume() {
|
override fun onResume() {
|
||||||
|
@ -176,13 +205,7 @@ class ConversationInfoActivity :
|
||||||
binding.clearConversationHistory.setOnClickListener { showClearHistoryDialog() }
|
binding.clearConversationHistory.setOnClickListener { showClearHistoryDialog() }
|
||||||
binding.addParticipantsAction.setOnClickListener { addParticipants() }
|
binding.addParticipantsAction.setOnClickListener { addParticipants() }
|
||||||
|
|
||||||
if (CapabilitiesUtilNew.hasSpreedFeatureCapability(conversationUser, "rich-object-list-media")) {
|
viewModel.getRoom(conversationUser, conversationToken)
|
||||||
binding.sharedItemsButton.setOnClickListener { showSharedItems() }
|
|
||||||
} else {
|
|
||||||
binding.sharedItems.visibility = GONE
|
|
||||||
}
|
|
||||||
|
|
||||||
fetchRoomInfo()
|
|
||||||
|
|
||||||
themeTextViews()
|
themeTextViews()
|
||||||
themeSwitchPreferences()
|
themeSwitchPreferences()
|
||||||
|
@ -192,6 +215,35 @@ class ConversationInfoActivity :
|
||||||
binding.progressBar.let { viewThemeUtils.platform.colorCircularProgressBar(it, ColorRole.PRIMARY) }
|
binding.progressBar.let { viewThemeUtils.platform.colorCircularProgressBar(it, ColorRole.PRIMARY) }
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private fun initObservers() {
|
||||||
|
viewModel.viewState.observe(this) { state ->
|
||||||
|
when (state) {
|
||||||
|
is ConversationInfoViewModel.GetRoomSuccessState -> {
|
||||||
|
conversation = state.conversationModel
|
||||||
|
viewModel.getCapabilities(conversationUser, conversationToken, conversation!!)
|
||||||
|
}
|
||||||
|
|
||||||
|
is ConversationInfoViewModel.GetRoomErrorState -> {
|
||||||
|
Snackbar.make(binding.root, R.string.nc_common_error_sorry, Snackbar.LENGTH_LONG).show()
|
||||||
|
}
|
||||||
|
|
||||||
|
else -> {}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
viewModel.getCapabilitiesViewState.observe(this) { state ->
|
||||||
|
when (state) {
|
||||||
|
is ConversationInfoViewModel.GetCapabilitiesSuccessState -> {
|
||||||
|
spreedCapabilities = state.spreedCapabilities
|
||||||
|
|
||||||
|
handleConversation()
|
||||||
|
}
|
||||||
|
|
||||||
|
else -> {}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
private fun setupActionBar() {
|
private fun setupActionBar() {
|
||||||
setSupportActionBar(binding.conversationInfoToolbar)
|
setSupportActionBar(binding.conversationInfoToolbar)
|
||||||
binding.conversationInfoToolbar.setNavigationOnClickListener {
|
binding.conversationInfoToolbar.setNavigationOnClickListener {
|
||||||
|
@ -217,7 +269,7 @@ class ConversationInfoActivity :
|
||||||
fun showOptionsMenu() {
|
fun showOptionsMenu() {
|
||||||
if (::optionsMenu.isInitialized) {
|
if (::optionsMenu.isInitialized) {
|
||||||
optionsMenu.clear()
|
optionsMenu.clear()
|
||||||
if (CapabilitiesUtilNew.isConversationAvatarEndpointAvailable(conversationUser)) {
|
if (CapabilitiesUtil.hasSpreedFeatureCapability(spreedCapabilities, SpreedFeatures.AVATAR)) {
|
||||||
menuInflater.inflate(R.menu.menu_conversation_info, optionsMenu)
|
menuInflater.inflate(R.menu.menu_conversation_info, optionsMenu)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -273,19 +325,22 @@ class ConversationInfoActivity :
|
||||||
intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP)
|
intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP)
|
||||||
intent.putExtra(BundleKeys.KEY_CONVERSATION_NAME, conversation?.displayName)
|
intent.putExtra(BundleKeys.KEY_CONVERSATION_NAME, conversation?.displayName)
|
||||||
intent.putExtra(BundleKeys.KEY_ROOM_TOKEN, conversationToken)
|
intent.putExtra(BundleKeys.KEY_ROOM_TOKEN, conversationToken)
|
||||||
intent.putExtra(SharedItemsActivity.KEY_USER_IS_OWNER_OR_MODERATOR, conversation?.isParticipantOwnerOrModerator)
|
intent.putExtra(
|
||||||
|
SharedItemsActivity.KEY_USER_IS_OWNER_OR_MODERATOR,
|
||||||
|
ConversationUtils.isParticipantOwnerOrModerator(conversation!!)
|
||||||
|
)
|
||||||
startActivity(intent)
|
startActivity(intent)
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun setupWebinaryView() {
|
private fun setupWebinaryView() {
|
||||||
if (CapabilitiesUtilNew.hasSpreedFeatureCapability(conversationUser, "webinary-lobby") &&
|
if (CapabilitiesUtil.hasSpreedFeatureCapability(spreedCapabilities, SpreedFeatures.WEBINARY_LOBBY) &&
|
||||||
webinaryRoomType(conversation!!) &&
|
webinaryRoomType(conversation!!) &&
|
||||||
conversation!!.canModerate(conversationUser)
|
ConversationUtils.canModerate(conversation!!, spreedCapabilities)
|
||||||
) {
|
) {
|
||||||
binding.webinarInfoView.webinarSettings.visibility = VISIBLE
|
binding.webinarInfoView.webinarSettings.visibility = VISIBLE
|
||||||
|
|
||||||
val isLobbyOpenToModeratorsOnly =
|
val isLobbyOpenToModeratorsOnly =
|
||||||
conversation!!.lobbyState == Conversation.LobbyState.LOBBY_STATE_MODERATORS_ONLY
|
conversation!!.lobbyState == LobbyState.LOBBY_STATE_MODERATORS_ONLY
|
||||||
binding.webinarInfoView.lobbySwitch.isChecked = isLobbyOpenToModeratorsOnly
|
binding.webinarInfoView.lobbySwitch.isChecked = isLobbyOpenToModeratorsOnly
|
||||||
|
|
||||||
reconfigureLobbyTimerView()
|
reconfigureLobbyTimerView()
|
||||||
|
@ -320,9 +375,9 @@ class ConversationInfoActivity :
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun webinaryRoomType(conversation: Conversation): Boolean {
|
private fun webinaryRoomType(conversation: ConversationModel): Boolean {
|
||||||
return conversation.type == Conversation.ConversationType.ROOM_GROUP_CALL ||
|
return conversation.type == ConversationType.ROOM_GROUP_CALL ||
|
||||||
conversation.type == Conversation.ConversationType.ROOM_PUBLIC_CALL
|
conversation.type == ConversationType.ROOM_PUBLIC_CALL
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun reconfigureLobbyTimerView(dateTime: Calendar? = null) {
|
private fun reconfigureLobbyTimerView(dateTime: Calendar? = null) {
|
||||||
|
@ -337,9 +392,9 @@ class ConversationInfoActivity :
|
||||||
}
|
}
|
||||||
|
|
||||||
conversation!!.lobbyState = if (isChecked) {
|
conversation!!.lobbyState = if (isChecked) {
|
||||||
Conversation.LobbyState.LOBBY_STATE_MODERATORS_ONLY
|
LobbyState.LOBBY_STATE_MODERATORS_ONLY
|
||||||
} else {
|
} else {
|
||||||
Conversation.LobbyState.LOBBY_STATE_ALL_PARTICIPANTS
|
LobbyState.LOBBY_STATE_ALL_PARTICIPANTS
|
||||||
}
|
}
|
||||||
|
|
||||||
if (
|
if (
|
||||||
|
@ -370,11 +425,11 @@ class ConversationInfoActivity :
|
||||||
0
|
0
|
||||||
}
|
}
|
||||||
|
|
||||||
val apiVersion = ApiUtils.getConversationApiVersion(conversationUser, intArrayOf(ApiUtils.APIv4, 1))
|
val apiVersion = ApiUtils.getConversationApiVersion(conversationUser, intArrayOf(ApiUtils.API_V4, 1))
|
||||||
|
|
||||||
ncApi.setLobbyForConversation(
|
ncApi.setLobbyForConversation(
|
||||||
ApiUtils.getCredentials(conversationUser.username, conversationUser.token),
|
ApiUtils.getCredentials(conversationUser.username, conversationUser.token),
|
||||||
ApiUtils.getUrlForRoomWebinaryLobby(apiVersion, conversationUser.baseUrl, conversation!!.token),
|
ApiUtils.getUrlForRoomWebinaryLobby(apiVersion, conversationUser.baseUrl!!, conversation!!.token),
|
||||||
state,
|
state,
|
||||||
conversation!!.lobbyTimer
|
conversation!!.lobbyTimer
|
||||||
)
|
)
|
||||||
|
@ -487,7 +542,7 @@ class ConversationInfoActivity :
|
||||||
|
|
||||||
private fun getListOfParticipants() {
|
private fun getListOfParticipants() {
|
||||||
// FIXME Fix API checking with guests?
|
// FIXME Fix API checking with guests?
|
||||||
val apiVersion: Int = ApiUtils.getConversationApiVersion(conversationUser, intArrayOf(ApiUtils.APIv4, 1))
|
val apiVersion: Int = ApiUtils.getConversationApiVersion(conversationUser, intArrayOf(ApiUtils.API_V4, 1))
|
||||||
|
|
||||||
val fieldMap = HashMap<String, Boolean>()
|
val fieldMap = HashMap<String, Boolean>()
|
||||||
fieldMap["includeStatus"] = true
|
fieldMap["includeStatus"] = true
|
||||||
|
@ -496,7 +551,7 @@ class ConversationInfoActivity :
|
||||||
credentials,
|
credentials,
|
||||||
ApiUtils.getUrlForParticipants(
|
ApiUtils.getUrlForParticipants(
|
||||||
apiVersion,
|
apiVersion,
|
||||||
conversationUser.baseUrl,
|
conversationUser.baseUrl!!,
|
||||||
conversationToken
|
conversationToken
|
||||||
),
|
),
|
||||||
fieldMap
|
fieldMap
|
||||||
|
@ -586,11 +641,11 @@ class ConversationInfoActivity :
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun clearHistory() {
|
private fun clearHistory() {
|
||||||
val apiVersion = ApiUtils.getChatApiVersion(conversationUser, intArrayOf(1))
|
val apiVersion = ApiUtils.getChatApiVersion(spreedCapabilities, intArrayOf(1))
|
||||||
|
|
||||||
ncApi.clearChatHistory(
|
ncApi.clearChatHistory(
|
||||||
credentials,
|
credentials,
|
||||||
ApiUtils.getUrlForChat(apiVersion, conversationUser.baseUrl, conversationToken)
|
ApiUtils.getUrlForChat(apiVersion, conversationUser.baseUrl!!, conversationToken)
|
||||||
)
|
)
|
||||||
?.subscribeOn(Schedulers.io())
|
?.subscribeOn(Schedulers.io())
|
||||||
?.observeOn(AndroidSchedulers.mainThread())
|
?.observeOn(AndroidSchedulers.mainThread())
|
||||||
|
@ -631,123 +686,99 @@ class ConversationInfoActivity :
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun fetchRoomInfo() {
|
@Suppress("LongMethod")
|
||||||
val apiVersion: Int
|
private fun handleConversation() {
|
||||||
// FIXME Fix API checking with guests?
|
val conversationCopy = conversation!!
|
||||||
apiVersion = ApiUtils.getConversationApiVersion(conversationUser, intArrayOf(ApiUtils.APIv4, 1))
|
|
||||||
|
|
||||||
ncApi.getRoom(credentials, ApiUtils.getUrlForRoom(apiVersion, conversationUser.baseUrl, conversationToken))
|
if (CapabilitiesUtil.hasSpreedFeatureCapability(spreedCapabilities, SpreedFeatures.RICH_OBJECT_LIST_MEDIA)) {
|
||||||
?.subscribeOn(Schedulers.io())
|
binding.sharedItemsButton.setOnClickListener { showSharedItems() }
|
||||||
?.observeOn(AndroidSchedulers.mainThread())
|
} else {
|
||||||
?.subscribe(object : Observer<RoomOverall> {
|
binding.sharedItems.visibility = GONE
|
||||||
override fun onSubscribe(d: Disposable) {
|
}
|
||||||
roomDisposable = d
|
|
||||||
}
|
|
||||||
|
|
||||||
@Suppress("Detekt.TooGenericExceptionCaught")
|
if (ConversationUtils.canModerate(conversationCopy, spreedCapabilities)) {
|
||||||
override fun onNext(roomOverall: RoomOverall) {
|
binding.addParticipantsAction.visibility = VISIBLE
|
||||||
conversation = roomOverall.ocs!!.data
|
if (CapabilitiesUtil.hasSpreedFeatureCapability(
|
||||||
|
spreedCapabilities,
|
||||||
|
SpreedFeatures.CLEAR_HISTORY
|
||||||
|
)
|
||||||
|
) {
|
||||||
|
binding.clearConversationHistory.visibility = VISIBLE
|
||||||
|
} else {
|
||||||
|
binding.clearConversationHistory.visibility = GONE
|
||||||
|
}
|
||||||
|
showOptionsMenu()
|
||||||
|
} else {
|
||||||
|
binding.addParticipantsAction.visibility = GONE
|
||||||
|
|
||||||
val conversationCopy = conversation
|
if (ConversationUtils.isNoteToSelfConversation(conversation)) {
|
||||||
|
binding.notificationSettingsView.notificationSettings.visibility = VISIBLE
|
||||||
|
} else {
|
||||||
|
binding.clearConversationHistory.visibility = GONE
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
if (conversationCopy!!.canModerate(conversationUser)) {
|
if (!isDestroyed) {
|
||||||
binding.addParticipantsAction.visibility = VISIBLE
|
binding.dangerZoneOptions.visibility = VISIBLE
|
||||||
if (CapabilitiesUtilNew.hasSpreedFeatureCapability(
|
|
||||||
conversationUser,
|
|
||||||
"clear-history"
|
|
||||||
)
|
|
||||||
) {
|
|
||||||
binding.clearConversationHistory.visibility = VISIBLE
|
|
||||||
} else {
|
|
||||||
binding.clearConversationHistory.visibility = GONE
|
|
||||||
}
|
|
||||||
showOptionsMenu()
|
|
||||||
} else {
|
|
||||||
binding.addParticipantsAction.visibility = GONE
|
|
||||||
|
|
||||||
if (ConversationUtils.isNoteToSelfConversation(
|
setupWebinaryView()
|
||||||
ConversationModel.mapToConversationModel(conversation!!)
|
|
||||||
)
|
|
||||||
) {
|
|
||||||
binding.notificationSettingsView.notificationSettings.visibility = VISIBLE
|
|
||||||
} else {
|
|
||||||
binding.clearConversationHistory.visibility = GONE
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!isDestroyed) {
|
if (ConversationUtils.canLeave(conversation!!)) {
|
||||||
binding.dangerZoneOptions.visibility = VISIBLE
|
binding.leaveConversationAction.visibility = GONE
|
||||||
|
} else {
|
||||||
|
binding.leaveConversationAction.visibility = VISIBLE
|
||||||
|
}
|
||||||
|
|
||||||
setupWebinaryView()
|
if (ConversationUtils.canDelete(conversation!!, spreedCapabilities)) {
|
||||||
|
binding.deleteConversationAction.visibility = GONE
|
||||||
|
} else {
|
||||||
|
binding.deleteConversationAction.visibility = VISIBLE
|
||||||
|
}
|
||||||
|
|
||||||
if (!conversation!!.canLeave()) {
|
if (ConversationType.ROOM_SYSTEM == conversation!!.type) {
|
||||||
binding.leaveConversationAction.visibility = GONE
|
binding.notificationSettingsView.callNotificationsSwitch.visibility = GONE
|
||||||
} else {
|
}
|
||||||
binding.leaveConversationAction.visibility = VISIBLE
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!conversation!!.canDelete(conversationUser)) {
|
if (conversation!!.notificationCalls === null) {
|
||||||
binding.deleteConversationAction.visibility = GONE
|
binding.notificationSettingsView.callNotificationsSwitch.visibility = GONE
|
||||||
} else {
|
} else {
|
||||||
binding.deleteConversationAction.visibility = VISIBLE
|
binding.notificationSettingsView.callNotificationsSwitch.isChecked =
|
||||||
}
|
(conversationCopy.notificationCalls == 1)
|
||||||
|
}
|
||||||
|
|
||||||
if (Conversation.ConversationType.ROOM_SYSTEM == conversation!!.type) {
|
getListOfParticipants()
|
||||||
binding.notificationSettingsView.callNotificationsSwitch.visibility = GONE
|
|
||||||
}
|
|
||||||
|
|
||||||
if (conversation!!.notificationCalls === null) {
|
binding.progressBar.visibility = GONE
|
||||||
binding.notificationSettingsView.callNotificationsSwitch.visibility = GONE
|
|
||||||
} else {
|
|
||||||
binding.notificationSettingsView.callNotificationsSwitch.isChecked =
|
|
||||||
(conversationCopy.notificationCalls == 1)
|
|
||||||
}
|
|
||||||
|
|
||||||
getListOfParticipants()
|
binding.conversationInfoName.visibility = VISIBLE
|
||||||
|
|
||||||
binding.progressBar.visibility = GONE
|
binding.displayNameText.text = conversation!!.displayName
|
||||||
|
|
||||||
binding.conversationInfoName.visibility = VISIBLE
|
if (conversation!!.description != null && conversation!!.description!!.isNotEmpty()) {
|
||||||
|
binding.descriptionText.text = conversation!!.description
|
||||||
|
binding.conversationDescription.visibility = VISIBLE
|
||||||
|
}
|
||||||
|
|
||||||
binding.displayNameText.text = conversation!!.displayName
|
loadConversationAvatar()
|
||||||
|
adjustNotificationLevelUI()
|
||||||
|
initRecordingConsentOption()
|
||||||
|
initExpiringMessageOption()
|
||||||
|
|
||||||
if (conversation!!.description != null && conversation!!.description!!.isNotEmpty()) {
|
binding.let {
|
||||||
binding.descriptionText.text = conversation!!.description
|
GuestAccessHelper(
|
||||||
binding.conversationDescription.visibility = VISIBLE
|
this@ConversationInfoActivity,
|
||||||
}
|
it,
|
||||||
|
conversation!!,
|
||||||
loadConversationAvatar()
|
spreedCapabilities,
|
||||||
adjustNotificationLevelUI()
|
conversationUser
|
||||||
initRecordingConsentOption()
|
).setupGuestAccess()
|
||||||
initExpiringMessageOption()
|
}
|
||||||
|
if (ConversationUtils.isNoteToSelfConversation(conversation!!)) {
|
||||||
binding.let {
|
binding.notificationSettingsView.notificationSettings.visibility = GONE
|
||||||
GuestAccessHelper(
|
} else {
|
||||||
this@ConversationInfoActivity,
|
binding.notificationSettingsView.notificationSettings.visibility = VISIBLE
|
||||||
it,
|
}
|
||||||
conversation!!,
|
}
|
||||||
conversationUser
|
|
||||||
).setupGuestAccess()
|
|
||||||
}
|
|
||||||
if (ConversationUtils.isNoteToSelfConversation(
|
|
||||||
ConversationModel.mapToConversationModel(conversation!!)
|
|
||||||
)
|
|
||||||
) {
|
|
||||||
binding.notificationSettingsView.notificationSettings.visibility = GONE
|
|
||||||
} else {
|
|
||||||
binding.notificationSettingsView.notificationSettings.visibility = VISIBLE
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun onError(e: Throwable) {
|
|
||||||
Log.e(TAG, "failed to fetch room info", e)
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun onComplete() {
|
|
||||||
roomDisposable!!.dispose()
|
|
||||||
}
|
|
||||||
})
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun initRecordingConsentOption() {
|
private fun initRecordingConsentOption() {
|
||||||
|
@ -781,13 +812,13 @@ class ConversationInfoActivity :
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (conversation!!.isParticipantOwnerOrModerator &&
|
if (ConversationUtils.isParticipantOwnerOrModerator(conversation!!) &&
|
||||||
!ConversationUtils.isNoteToSelfConversation(ConversationModel.mapToConversationModel(conversation!!))
|
!ConversationUtils.isNoteToSelfConversation(conversation!!)
|
||||||
) {
|
) {
|
||||||
when (CapabilitiesUtilNew.getRecordingConsentType(conversationUser)) {
|
when (CapabilitiesUtil.getRecordingConsentType(spreedCapabilities)) {
|
||||||
CapabilitiesUtilNew.RECORDING_CONSENT_NOT_REQUIRED -> hide()
|
CapabilitiesUtil.RECORDING_CONSENT_NOT_REQUIRED -> hide()
|
||||||
CapabilitiesUtilNew.RECORDING_CONSENT_REQUIRED -> showAlwaysRequiredInfo()
|
CapabilitiesUtil.RECORDING_CONSENT_REQUIRED -> showAlwaysRequiredInfo()
|
||||||
CapabilitiesUtilNew.RECORDING_CONSENT_DEPEND_ON_CONVERSATION -> showSwitch()
|
CapabilitiesUtil.RECORDING_CONSENT_DEPEND_ON_CONVERSATION -> showSwitch()
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
hide()
|
hide()
|
||||||
|
@ -801,11 +832,11 @@ class ConversationInfoActivity :
|
||||||
RECORDING_CONSENT_NOT_REQUIRED_FOR_CONVERSATION
|
RECORDING_CONSENT_NOT_REQUIRED_FOR_CONVERSATION
|
||||||
}
|
}
|
||||||
|
|
||||||
val apiVersion = ApiUtils.getConversationApiVersion(conversationUser, intArrayOf(ApiUtils.APIv4, 1))
|
val apiVersion = ApiUtils.getConversationApiVersion(conversationUser, intArrayOf(ApiUtils.API_V4, 1))
|
||||||
|
|
||||||
ncApi.setRecordingConsent(
|
ncApi.setRecordingConsent(
|
||||||
ApiUtils.getCredentials(conversationUser.username, conversationUser.token),
|
ApiUtils.getCredentials(conversationUser.username, conversationUser.token),
|
||||||
ApiUtils.getUrlForRecordingConsent(apiVersion, conversationUser.baseUrl, conversation!!.token),
|
ApiUtils.getUrlForRecordingConsent(apiVersion, conversationUser.baseUrl!!, conversation!!.token),
|
||||||
state
|
state
|
||||||
)
|
)
|
||||||
?.subscribeOn(Schedulers.io())
|
?.subscribeOn(Schedulers.io())
|
||||||
|
@ -831,8 +862,8 @@ class ConversationInfoActivity :
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun initExpiringMessageOption() {
|
private fun initExpiringMessageOption() {
|
||||||
if (conversation!!.isParticipantOwnerOrModerator &&
|
if (ConversationUtils.isParticipantOwnerOrModerator(conversation!!) &&
|
||||||
CapabilitiesUtilNew.hasSpreedFeatureCapability(conversationUser, "message-expiration")
|
CapabilitiesUtil.hasSpreedFeatureCapability(spreedCapabilities, SpreedFeatures.MESSAGE_EXPIRATION)
|
||||||
) {
|
) {
|
||||||
databaseStorageModule?.setMessageExpiration(conversation!!.messageExpiration)
|
databaseStorageModule?.setMessageExpiration(conversation!!.messageExpiration)
|
||||||
val value = databaseStorageModule!!.getString("conversation_settings_dropdown", "")
|
val value = databaseStorageModule!!.getString("conversation_settings_dropdown", "")
|
||||||
|
@ -855,13 +886,16 @@ class ConversationInfoActivity :
|
||||||
|
|
||||||
private fun adjustNotificationLevelUI() {
|
private fun adjustNotificationLevelUI() {
|
||||||
if (conversation != null) {
|
if (conversation != null) {
|
||||||
if (CapabilitiesUtilNew.hasSpreedFeatureCapability(conversationUser, "notification-levels")) {
|
if (CapabilitiesUtil.hasSpreedFeatureCapability(spreedCapabilities, SpreedFeatures.NOTIFICATION_LEVELS)) {
|
||||||
binding.notificationSettingsView.conversationInfoMessageNotificationsDropdown.isEnabled = true
|
binding.notificationSettingsView.conversationInfoMessageNotificationsDropdown.isEnabled = true
|
||||||
binding.notificationSettingsView.conversationInfoMessageNotificationsDropdown.alpha = 1.0f
|
binding.notificationSettingsView.conversationInfoMessageNotificationsDropdown.alpha = 1.0f
|
||||||
|
|
||||||
if (conversation!!.notificationLevel != Conversation.NotificationLevel.DEFAULT) {
|
if (conversation!!.notificationLevel != NotificationLevel.DEFAULT) {
|
||||||
val stringValue: String =
|
val stringValue: String =
|
||||||
when (EnumNotificationLevelConverter().convertToInt(conversation!!.notificationLevel)) {
|
when (
|
||||||
|
DomainEnumNotificationLevelConverter()
|
||||||
|
.convertToInt(conversation!!.notificationLevel!!)
|
||||||
|
) {
|
||||||
NOTIFICATION_LEVEL_ALWAYS -> resources.getString(R.string.nc_notify_me_always)
|
NOTIFICATION_LEVEL_ALWAYS -> resources.getString(R.string.nc_notify_me_always)
|
||||||
NOTIFICATION_LEVEL_MENTION -> resources.getString(R.string.nc_notify_me_mention)
|
NOTIFICATION_LEVEL_MENTION -> resources.getString(R.string.nc_notify_me_mention)
|
||||||
NOTIFICATION_LEVEL_NEVER -> resources.getString(R.string.nc_notify_me_never)
|
NOTIFICATION_LEVEL_NEVER -> resources.getString(R.string.nc_notify_me_never)
|
||||||
|
@ -885,9 +919,9 @@ class ConversationInfoActivity :
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun setProperNotificationValue(conversation: Conversation?) {
|
private fun setProperNotificationValue(conversation: ConversationModel?) {
|
||||||
if (conversation!!.type == Conversation.ConversationType.ROOM_TYPE_ONE_TO_ONE_CALL) {
|
if (conversation!!.type == ConversationType.ROOM_TYPE_ONE_TO_ONE_CALL) {
|
||||||
if (CapabilitiesUtilNew.hasSpreedFeatureCapability(conversationUser, "mention-flag")) {
|
if (CapabilitiesUtil.hasSpreedFeatureCapability(spreedCapabilities, SpreedFeatures.MENTION_FLAG)) {
|
||||||
binding.notificationSettingsView.conversationInfoMessageNotificationsDropdown.setText(
|
binding.notificationSettingsView.conversationInfoMessageNotificationsDropdown.setText(
|
||||||
resources.getString(R.string.nc_notify_me_always)
|
resources.getString(R.string.nc_notify_me_always)
|
||||||
)
|
)
|
||||||
|
@ -905,7 +939,7 @@ class ConversationInfoActivity :
|
||||||
|
|
||||||
private fun loadConversationAvatar() {
|
private fun loadConversationAvatar() {
|
||||||
when (conversation!!.type) {
|
when (conversation!!.type) {
|
||||||
Conversation.ConversationType.ROOM_TYPE_ONE_TO_ONE_CALL -> if (!TextUtils.isEmpty(conversation!!.name)) {
|
ConversationType.ROOM_TYPE_ONE_TO_ONE_CALL -> if (!TextUtils.isEmpty(conversation!!.name)) {
|
||||||
conversation!!.name?.let {
|
conversation!!.name?.let {
|
||||||
binding.avatarImage.loadUserAvatar(
|
binding.avatarImage.loadUserAvatar(
|
||||||
conversationUser,
|
conversationUser,
|
||||||
|
@ -916,7 +950,7 @@ class ConversationInfoActivity :
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
Conversation.ConversationType.ROOM_GROUP_CALL, Conversation.ConversationType.ROOM_PUBLIC_CALL -> {
|
ConversationType.ROOM_GROUP_CALL, ConversationType.ROOM_PUBLIC_CALL -> {
|
||||||
binding.avatarImage.loadConversationAvatar(
|
binding.avatarImage.loadConversationAvatar(
|
||||||
conversationUser,
|
conversationUser,
|
||||||
conversation!!,
|
conversation!!,
|
||||||
|
@ -925,15 +959,12 @@ class ConversationInfoActivity :
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
Conversation.ConversationType.ROOM_SYSTEM -> {
|
ConversationType.ROOM_SYSTEM -> {
|
||||||
binding.avatarImage.loadSystemAvatar()
|
binding.avatarImage.loadSystemAvatar()
|
||||||
}
|
}
|
||||||
|
|
||||||
Conversation.ConversationType.DUMMY -> {
|
ConversationType.DUMMY -> {
|
||||||
if (ConversationUtils.isNoteToSelfConversation(
|
if (ConversationUtils.isNoteToSelfConversation(conversation!!)) {
|
||||||
ConversationModel.mapToConversationModel(conversation!!)
|
|
||||||
)
|
|
||||||
) {
|
|
||||||
binding.avatarImage.loadNoteToSelfAvatar()
|
binding.avatarImage.loadNoteToSelfAvatar()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -971,7 +1002,7 @@ class ConversationInfoActivity :
|
||||||
credentials,
|
credentials,
|
||||||
ApiUtils.getUrlForRoomModerators(
|
ApiUtils.getUrlForRoomModerators(
|
||||||
apiVersion,
|
apiVersion,
|
||||||
conversationUser.baseUrl,
|
conversationUser.baseUrl!!,
|
||||||
conversation!!.token
|
conversation!!.token
|
||||||
),
|
),
|
||||||
participant.attendeeId
|
participant.attendeeId
|
||||||
|
@ -986,7 +1017,7 @@ class ConversationInfoActivity :
|
||||||
credentials,
|
credentials,
|
||||||
ApiUtils.getUrlForRoomModerators(
|
ApiUtils.getUrlForRoomModerators(
|
||||||
apiVersion,
|
apiVersion,
|
||||||
conversationUser.baseUrl,
|
conversationUser.baseUrl!!,
|
||||||
conversation!!.token
|
conversation!!.token
|
||||||
),
|
),
|
||||||
participant.attendeeId
|
participant.attendeeId
|
||||||
|
@ -1022,7 +1053,7 @@ class ConversationInfoActivity :
|
||||||
credentials,
|
credentials,
|
||||||
ApiUtils.getUrlForRoomModerators(
|
ApiUtils.getUrlForRoomModerators(
|
||||||
apiVersion,
|
apiVersion,
|
||||||
conversationUser.baseUrl,
|
conversationUser.baseUrl!!,
|
||||||
conversation!!.token
|
conversation!!.token
|
||||||
),
|
),
|
||||||
participant.userId
|
participant.userId
|
||||||
|
@ -1035,7 +1066,7 @@ class ConversationInfoActivity :
|
||||||
credentials,
|
credentials,
|
||||||
ApiUtils.getUrlForRoomModerators(
|
ApiUtils.getUrlForRoomModerators(
|
||||||
apiVersion,
|
apiVersion,
|
||||||
conversationUser.baseUrl,
|
conversationUser.baseUrl!!,
|
||||||
conversation!!.token
|
conversation!!.token
|
||||||
),
|
),
|
||||||
participant.userId
|
participant.userId
|
||||||
|
@ -1047,12 +1078,12 @@ class ConversationInfoActivity :
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun removeAttendeeFromConversation(apiVersion: Int, participant: Participant) {
|
private fun removeAttendeeFromConversation(apiVersion: Int, participant: Participant) {
|
||||||
if (apiVersion >= ApiUtils.APIv4) {
|
if (apiVersion >= ApiUtils.API_V4) {
|
||||||
ncApi.removeAttendeeFromConversation(
|
ncApi.removeAttendeeFromConversation(
|
||||||
credentials,
|
credentials,
|
||||||
ApiUtils.getUrlForAttendees(
|
ApiUtils.getUrlForAttendees(
|
||||||
apiVersion,
|
apiVersion,
|
||||||
conversationUser.baseUrl,
|
conversationUser.baseUrl!!,
|
||||||
conversation!!.token
|
conversation!!.token
|
||||||
),
|
),
|
||||||
participant.attendeeId
|
participant.attendeeId
|
||||||
|
@ -1084,7 +1115,7 @@ class ConversationInfoActivity :
|
||||||
ncApi.removeParticipantFromConversation(
|
ncApi.removeParticipantFromConversation(
|
||||||
credentials,
|
credentials,
|
||||||
ApiUtils.getUrlForRemovingParticipantFromConversation(
|
ApiUtils.getUrlForRemovingParticipantFromConversation(
|
||||||
conversationUser.baseUrl,
|
conversationUser.baseUrl!!,
|
||||||
conversation!!.token,
|
conversation!!.token,
|
||||||
true
|
true
|
||||||
),
|
),
|
||||||
|
@ -1114,7 +1145,7 @@ class ConversationInfoActivity :
|
||||||
ncApi.removeParticipantFromConversation(
|
ncApi.removeParticipantFromConversation(
|
||||||
credentials,
|
credentials,
|
||||||
ApiUtils.getUrlForRemovingParticipantFromConversation(
|
ApiUtils.getUrlForRemovingParticipantFromConversation(
|
||||||
conversationUser.baseUrl,
|
conversationUser.baseUrl!!,
|
||||||
conversation!!.token,
|
conversation!!.token,
|
||||||
false
|
false
|
||||||
),
|
),
|
||||||
|
@ -1146,14 +1177,14 @@ class ConversationInfoActivity :
|
||||||
|
|
||||||
@SuppressLint("CheckResult")
|
@SuppressLint("CheckResult")
|
||||||
override fun onItemClick(view: View?, position: Int): Boolean {
|
override fun onItemClick(view: View?, position: Int): Boolean {
|
||||||
if (!conversation!!.canModerate(conversationUser)) {
|
if (ConversationUtils.canModerate(conversation!!, spreedCapabilities)) {
|
||||||
return true
|
return true
|
||||||
}
|
}
|
||||||
|
|
||||||
val userItem = adapter?.getItem(position) as ParticipantItem
|
val userItem = adapter?.getItem(position) as ParticipantItem
|
||||||
val participant = userItem.model
|
val participant = userItem.model
|
||||||
|
|
||||||
val apiVersion = ApiUtils.getConversationApiVersion(conversationUser, intArrayOf(ApiUtils.APIv4, 1))
|
val apiVersion = ApiUtils.getConversationApiVersion(conversationUser, intArrayOf(ApiUtils.API_V4, 1))
|
||||||
|
|
||||||
if (participant.calculatedActorType == USERS && participant.calculatedActorId == conversationUser.userId) {
|
if (participant.calculatedActorType == USERS && participant.calculatedActorId == conversationUser.userId) {
|
||||||
if (participant.attendeePin?.isNotEmpty() == true) {
|
if (participant.attendeePin?.isNotEmpty() == true) {
|
||||||
|
@ -1277,7 +1308,7 @@ class ConversationInfoActivity :
|
||||||
// Pin, nothing to do
|
// Pin, nothing to do
|
||||||
} else if (actionToTrigger == 1) {
|
} else if (actionToTrigger == 1) {
|
||||||
// Promote/demote
|
// Promote/demote
|
||||||
if (apiVersion >= ApiUtils.APIv4) {
|
if (apiVersion >= ApiUtils.API_V4) {
|
||||||
toggleModeratorStatus(apiVersion, participant)
|
toggleModeratorStatus(apiVersion, participant)
|
||||||
} else {
|
} else {
|
||||||
toggleModeratorStatusLegacy(apiVersion, participant)
|
toggleModeratorStatusLegacy(apiVersion, participant)
|
||||||
|
|
|
@ -11,8 +11,11 @@ import com.nextcloud.talk.R
|
||||||
import com.nextcloud.talk.data.user.model.User
|
import com.nextcloud.talk.data.user.model.User
|
||||||
import com.nextcloud.talk.databinding.ActivityConversationInfoBinding
|
import com.nextcloud.talk.databinding.ActivityConversationInfoBinding
|
||||||
import com.nextcloud.talk.databinding.DialogPasswordBinding
|
import com.nextcloud.talk.databinding.DialogPasswordBinding
|
||||||
import com.nextcloud.talk.models.json.conversations.Conversation
|
import com.nextcloud.talk.models.domain.ConversationModel
|
||||||
|
import com.nextcloud.talk.models.domain.ConversationType
|
||||||
|
import com.nextcloud.talk.models.json.capabilities.SpreedCapability
|
||||||
import com.nextcloud.talk.repositories.conversations.ConversationsRepository
|
import com.nextcloud.talk.repositories.conversations.ConversationsRepository
|
||||||
|
import com.nextcloud.talk.utils.ConversationUtils
|
||||||
import com.nextcloud.talk.utils.Mimetype
|
import com.nextcloud.talk.utils.Mimetype
|
||||||
import com.nextcloud.talk.utils.ShareUtils
|
import com.nextcloud.talk.utils.ShareUtils
|
||||||
import io.reactivex.Observer
|
import io.reactivex.Observer
|
||||||
|
@ -23,7 +26,8 @@ import io.reactivex.schedulers.Schedulers
|
||||||
class GuestAccessHelper(
|
class GuestAccessHelper(
|
||||||
private val activity: ConversationInfoActivity,
|
private val activity: ConversationInfoActivity,
|
||||||
private val binding: ActivityConversationInfoBinding,
|
private val binding: ActivityConversationInfoBinding,
|
||||||
private val conversation: Conversation,
|
private val conversation: ConversationModel,
|
||||||
|
private val spreedCapabilities: SpreedCapability,
|
||||||
private val conversationUser: User
|
private val conversationUser: User
|
||||||
) {
|
) {
|
||||||
|
|
||||||
|
@ -32,13 +36,13 @@ class GuestAccessHelper(
|
||||||
private val context = activity.context
|
private val context = activity.context
|
||||||
|
|
||||||
fun setupGuestAccess() {
|
fun setupGuestAccess() {
|
||||||
if (conversation.canModerate(conversationUser)) {
|
if (ConversationUtils.canModerate(conversation, spreedCapabilities)) {
|
||||||
binding.guestAccessView.guestAccessSettings.visibility = View.VISIBLE
|
binding.guestAccessView.guestAccessSettings.visibility = View.VISIBLE
|
||||||
} else {
|
} else {
|
||||||
binding.guestAccessView.guestAccessSettings.visibility = View.GONE
|
binding.guestAccessView.guestAccessSettings.visibility = View.GONE
|
||||||
}
|
}
|
||||||
|
|
||||||
if (conversation.type == Conversation.ConversationType.ROOM_PUBLIC_CALL) {
|
if (conversation.type == ConversationType.ROOM_PUBLIC_CALL) {
|
||||||
binding.guestAccessView.allowGuestsSwitch.isChecked = true
|
binding.guestAccessView.allowGuestsSwitch.isChecked = true
|
||||||
showAllOptions()
|
showAllOptions()
|
||||||
if (conversation.hasPassword) {
|
if (conversation.hasPassword) {
|
||||||
|
|
|
@ -0,0 +1,142 @@
|
||||||
|
/*
|
||||||
|
* Nextcloud Talk application
|
||||||
|
*
|
||||||
|
* @author Marcel Hibbe
|
||||||
|
* Copyright (C) 2023 Marcel Hibbe <dev@mhibbe.de>
|
||||||
|
*
|
||||||
|
* 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.conversationinfo.viewmodel
|
||||||
|
|
||||||
|
import android.util.Log
|
||||||
|
import androidx.lifecycle.DefaultLifecycleObserver
|
||||||
|
import androidx.lifecycle.LifecycleOwner
|
||||||
|
import androidx.lifecycle.LiveData
|
||||||
|
import androidx.lifecycle.MutableLiveData
|
||||||
|
import androidx.lifecycle.ViewModel
|
||||||
|
import com.nextcloud.talk.chat.data.ChatRepository
|
||||||
|
import com.nextcloud.talk.data.user.model.User
|
||||||
|
import com.nextcloud.talk.models.domain.ConversationModel
|
||||||
|
import com.nextcloud.talk.models.json.capabilities.SpreedCapability
|
||||||
|
import io.reactivex.Observer
|
||||||
|
import io.reactivex.android.schedulers.AndroidSchedulers
|
||||||
|
import io.reactivex.disposables.Disposable
|
||||||
|
import io.reactivex.schedulers.Schedulers
|
||||||
|
import javax.inject.Inject
|
||||||
|
|
||||||
|
class ConversationInfoViewModel @Inject constructor(
|
||||||
|
private val chatRepository: ChatRepository
|
||||||
|
) : ViewModel() {
|
||||||
|
|
||||||
|
object LifeCycleObserver : DefaultLifecycleObserver {
|
||||||
|
enum class LifeCycleFlag {
|
||||||
|
PAUSED,
|
||||||
|
RESUMED
|
||||||
|
}
|
||||||
|
lateinit var currentLifeCycleFlag: LifeCycleFlag
|
||||||
|
public val disposableSet = mutableSetOf<Disposable>()
|
||||||
|
|
||||||
|
override fun onResume(owner: LifecycleOwner) {
|
||||||
|
super.onResume(owner)
|
||||||
|
currentLifeCycleFlag = LifeCycleFlag.RESUMED
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onPause(owner: LifecycleOwner) {
|
||||||
|
super.onPause(owner)
|
||||||
|
currentLifeCycleFlag = LifeCycleFlag.PAUSED
|
||||||
|
disposableSet.forEach { disposable -> disposable.dispose() }
|
||||||
|
disposableSet.clear()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
sealed interface ViewState
|
||||||
|
|
||||||
|
object GetRoomStartState : ViewState
|
||||||
|
object GetRoomErrorState : ViewState
|
||||||
|
open class GetRoomSuccessState(val conversationModel: ConversationModel) : ViewState
|
||||||
|
|
||||||
|
private val _viewState: MutableLiveData<ViewState> = MutableLiveData(GetRoomStartState)
|
||||||
|
val viewState: LiveData<ViewState>
|
||||||
|
get() = _viewState
|
||||||
|
|
||||||
|
object GetCapabilitiesStartState : ViewState
|
||||||
|
object GetCapabilitiesErrorState : ViewState
|
||||||
|
open class GetCapabilitiesSuccessState(val spreedCapabilities: SpreedCapability) : ViewState
|
||||||
|
|
||||||
|
private val _getCapabilitiesViewState: MutableLiveData<ViewState> = MutableLiveData(GetCapabilitiesStartState)
|
||||||
|
val getCapabilitiesViewState: LiveData<ViewState>
|
||||||
|
get() = _getCapabilitiesViewState
|
||||||
|
|
||||||
|
fun getRoom(user: User, token: String) {
|
||||||
|
_viewState.value = GetRoomStartState
|
||||||
|
chatRepository.getRoom(user, token)
|
||||||
|
.subscribeOn(Schedulers.io())
|
||||||
|
?.observeOn(AndroidSchedulers.mainThread())
|
||||||
|
?.subscribe(GetRoomObserver())
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getCapabilities(user: User, token: String, conversationModel: ConversationModel) {
|
||||||
|
_getCapabilitiesViewState.value = GetCapabilitiesStartState
|
||||||
|
|
||||||
|
if (conversationModel.remoteServer.isNullOrEmpty()) {
|
||||||
|
_getCapabilitiesViewState.value = GetCapabilitiesSuccessState(user.capabilities!!.spreedCapability!!)
|
||||||
|
} else {
|
||||||
|
chatRepository.getCapabilities(user, token)
|
||||||
|
.subscribeOn(Schedulers.io())
|
||||||
|
?.observeOn(AndroidSchedulers.mainThread())
|
||||||
|
?.subscribe(object : Observer<SpreedCapability> {
|
||||||
|
override fun onSubscribe(d: Disposable) {
|
||||||
|
LifeCycleObserver.disposableSet.add(d)
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onNext(spreedCapabilities: SpreedCapability) {
|
||||||
|
_getCapabilitiesViewState.value = GetCapabilitiesSuccessState(spreedCapabilities)
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onError(e: Throwable) {
|
||||||
|
Log.e(TAG, "Error when fetching spreed capabilities", e)
|
||||||
|
_getCapabilitiesViewState.value = GetCapabilitiesErrorState
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onComplete() {
|
||||||
|
// unused atm
|
||||||
|
}
|
||||||
|
})
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
inner class GetRoomObserver : Observer<ConversationModel> {
|
||||||
|
override fun onSubscribe(d: Disposable) {
|
||||||
|
// unused atm
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onNext(conversationModel: ConversationModel) {
|
||||||
|
_viewState.value = GetRoomSuccessState(conversationModel)
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onError(e: Throwable) {
|
||||||
|
Log.e(TAG, "Error when fetching room")
|
||||||
|
_viewState.value = GetRoomErrorState
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onComplete() {
|
||||||
|
// unused atm
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
companion object {
|
||||||
|
private val TAG = ConversationInfoViewModel::class.simpleName
|
||||||
|
}
|
||||||
|
}
|
|
@ -49,11 +49,12 @@ import com.nextcloud.talk.extensions.loadSystemAvatar
|
||||||
import com.nextcloud.talk.extensions.loadUserAvatar
|
import com.nextcloud.talk.extensions.loadUserAvatar
|
||||||
import com.nextcloud.talk.models.domain.ConversationModel
|
import com.nextcloud.talk.models.domain.ConversationModel
|
||||||
import com.nextcloud.talk.models.domain.ConversationType
|
import com.nextcloud.talk.models.domain.ConversationType
|
||||||
|
import com.nextcloud.talk.models.json.capabilities.SpreedCapability
|
||||||
import com.nextcloud.talk.models.json.generic.GenericOverall
|
import com.nextcloud.talk.models.json.generic.GenericOverall
|
||||||
import com.nextcloud.talk.utils.ApiUtils
|
import com.nextcloud.talk.utils.ApiUtils
|
||||||
|
import com.nextcloud.talk.utils.CapabilitiesUtil
|
||||||
import com.nextcloud.talk.utils.PickImage
|
import com.nextcloud.talk.utils.PickImage
|
||||||
import com.nextcloud.talk.utils.bundle.BundleKeys
|
import com.nextcloud.talk.utils.bundle.BundleKeys
|
||||||
import com.nextcloud.talk.utils.database.user.CapabilitiesUtilNew
|
|
||||||
import com.nextcloud.talk.utils.database.user.CurrentUserProviderNew
|
import com.nextcloud.talk.utils.database.user.CurrentUserProviderNew
|
||||||
import io.reactivex.Observer
|
import io.reactivex.Observer
|
||||||
import io.reactivex.android.schedulers.AndroidSchedulers
|
import io.reactivex.android.schedulers.AndroidSchedulers
|
||||||
|
@ -87,6 +88,8 @@ class ConversationInfoEditActivity :
|
||||||
|
|
||||||
private lateinit var pickImage: PickImage
|
private lateinit var pickImage: PickImage
|
||||||
|
|
||||||
|
private lateinit var spreedCapabilities: SpreedCapability
|
||||||
|
|
||||||
override fun onCreate(savedInstanceState: Bundle?) {
|
override fun onCreate(savedInstanceState: Bundle?) {
|
||||||
super.onCreate(savedInstanceState)
|
super.onCreate(savedInstanceState)
|
||||||
NextcloudTalkApplication.sharedApplication!!.componentApplication.inject(this)
|
NextcloudTalkApplication.sharedApplication!!.componentApplication.inject(this)
|
||||||
|
@ -110,7 +113,7 @@ class ConversationInfoEditActivity :
|
||||||
viewThemeUtils.material.colorTextInputLayout(binding.conversationNameInputLayout)
|
viewThemeUtils.material.colorTextInputLayout(binding.conversationNameInputLayout)
|
||||||
viewThemeUtils.material.colorTextInputLayout(binding.conversationDescriptionInputLayout)
|
viewThemeUtils.material.colorTextInputLayout(binding.conversationDescriptionInputLayout)
|
||||||
|
|
||||||
credentials = ApiUtils.getCredentials(conversationUser.username, conversationUser.token)
|
credentials = ApiUtils.getCredentials(conversationUser.username, conversationUser.token)!!
|
||||||
|
|
||||||
pickImage = PickImage(this, conversationUser)
|
pickImage = PickImage(this, conversationUser)
|
||||||
|
|
||||||
|
@ -127,13 +130,15 @@ class ConversationInfoEditActivity :
|
||||||
is ConversationInfoEditViewModel.GetRoomSuccessState -> {
|
is ConversationInfoEditViewModel.GetRoomSuccessState -> {
|
||||||
conversation = state.conversationModel
|
conversation = state.conversationModel
|
||||||
|
|
||||||
|
spreedCapabilities = conversationUser.capabilities!!.spreedCapability!!
|
||||||
|
|
||||||
binding.conversationName.setText(conversation!!.displayName)
|
binding.conversationName.setText(conversation!!.displayName)
|
||||||
|
|
||||||
if (conversation!!.description != null && conversation!!.description!!.isNotEmpty()) {
|
if (conversation!!.description != null && conversation!!.description!!.isNotEmpty()) {
|
||||||
binding.conversationDescription.setText(conversation!!.description)
|
binding.conversationDescription.setText(conversation!!.description)
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!CapabilitiesUtilNew.isConversationDescriptionEndpointAvailable(conversationUser)) {
|
if (!CapabilitiesUtil.isConversationDescriptionEndpointAvailable(spreedCapabilities)) {
|
||||||
binding.conversationDescription.isEnabled = false
|
binding.conversationDescription.isEnabled = false
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -221,13 +226,13 @@ class ConversationInfoEditActivity :
|
||||||
|
|
||||||
private fun saveConversationNameAndDescription() {
|
private fun saveConversationNameAndDescription() {
|
||||||
val apiVersion =
|
val apiVersion =
|
||||||
ApiUtils.getConversationApiVersion(conversationUser, intArrayOf(ApiUtils.APIv4, ApiUtils.APIv1))
|
ApiUtils.getConversationApiVersion(conversationUser, intArrayOf(ApiUtils.API_V4, ApiUtils.API_V1))
|
||||||
|
|
||||||
ncApi.renameRoom(
|
ncApi.renameRoom(
|
||||||
credentials,
|
credentials,
|
||||||
ApiUtils.getUrlForRoom(
|
ApiUtils.getUrlForRoom(
|
||||||
apiVersion,
|
apiVersion,
|
||||||
conversationUser.baseUrl,
|
conversationUser.baseUrl!!,
|
||||||
conversation!!.token
|
conversation!!.token
|
||||||
),
|
),
|
||||||
binding.conversationName.text.toString()
|
binding.conversationName.text.toString()
|
||||||
|
@ -241,7 +246,7 @@ class ConversationInfoEditActivity :
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onNext(genericOverall: GenericOverall) {
|
override fun onNext(genericOverall: GenericOverall) {
|
||||||
if (CapabilitiesUtilNew.isConversationDescriptionEndpointAvailable(conversationUser)) {
|
if (CapabilitiesUtil.isConversationDescriptionEndpointAvailable(spreedCapabilities)) {
|
||||||
saveConversationDescription()
|
saveConversationDescription()
|
||||||
} else {
|
} else {
|
||||||
finish()
|
finish()
|
||||||
|
@ -265,13 +270,13 @@ class ConversationInfoEditActivity :
|
||||||
|
|
||||||
fun saveConversationDescription() {
|
fun saveConversationDescription() {
|
||||||
val apiVersion =
|
val apiVersion =
|
||||||
ApiUtils.getConversationApiVersion(conversationUser, intArrayOf(ApiUtils.APIv4, ApiUtils.APIv1))
|
ApiUtils.getConversationApiVersion(conversationUser, intArrayOf(ApiUtils.API_V4, ApiUtils.API_V1))
|
||||||
|
|
||||||
ncApi.setConversationDescription(
|
ncApi.setConversationDescription(
|
||||||
credentials,
|
credentials,
|
||||||
ApiUtils.getUrlForConversationDescription(
|
ApiUtils.getUrlForConversationDescription(
|
||||||
apiVersion,
|
apiVersion,
|
||||||
conversationUser.baseUrl,
|
conversationUser.baseUrl!!,
|
||||||
conversation!!.token
|
conversation!!.token
|
||||||
),
|
),
|
||||||
binding.conversationDescription.text.toString()
|
binding.conversationDescription.text.toString()
|
||||||
|
|
|
@ -36,9 +36,9 @@ class ConversationInfoEditRepositoryImpl(private val ncApi: NcApi, currentUserPr
|
||||||
ConversationInfoEditRepository {
|
ConversationInfoEditRepository {
|
||||||
|
|
||||||
val currentUser: User = currentUserProvider.currentUser.blockingGet()
|
val currentUser: User = currentUserProvider.currentUser.blockingGet()
|
||||||
val credentials: String = ApiUtils.getCredentials(currentUser.username, currentUser.token)
|
val credentials: String = ApiUtils.getCredentials(currentUser.username, currentUser.token)!!
|
||||||
|
|
||||||
val apiVersion = ApiUtils.getConversationApiVersion(currentUser, intArrayOf(ApiUtils.APIv4, ApiUtils.APIv3, 1))
|
val apiVersion = ApiUtils.getConversationApiVersion(currentUser, intArrayOf(ApiUtils.API_V4, ApiUtils.API_V3, 1))
|
||||||
|
|
||||||
override fun uploadConversationAvatar(user: User, file: File, roomToken: String): Observable<ConversationModel> {
|
override fun uploadConversationAvatar(user: User, file: File, roomToken: String): Observable<ConversationModel> {
|
||||||
val builder = MultipartBody.Builder()
|
val builder = MultipartBody.Builder()
|
||||||
|
@ -56,7 +56,7 @@ class ConversationInfoEditRepositoryImpl(private val ncApi: NcApi, currentUserPr
|
||||||
|
|
||||||
return ncApi.uploadConversationAvatar(
|
return ncApi.uploadConversationAvatar(
|
||||||
credentials,
|
credentials,
|
||||||
ApiUtils.getUrlForConversationAvatar(1, user.baseUrl, roomToken),
|
ApiUtils.getUrlForConversationAvatar(1, user.baseUrl!!, roomToken),
|
||||||
filePart
|
filePart
|
||||||
).map { ConversationModel.mapToConversationModel(it.ocs?.data!!) }
|
).map { ConversationModel.mapToConversationModel(it.ocs?.data!!) }
|
||||||
}
|
}
|
||||||
|
@ -64,7 +64,7 @@ class ConversationInfoEditRepositoryImpl(private val ncApi: NcApi, currentUserPr
|
||||||
override fun deleteConversationAvatar(user: User, roomToken: String): Observable<ConversationModel> {
|
override fun deleteConversationAvatar(user: User, roomToken: String): Observable<ConversationModel> {
|
||||||
return ncApi.deleteConversationAvatar(
|
return ncApi.deleteConversationAvatar(
|
||||||
credentials,
|
credentials,
|
||||||
ApiUtils.getUrlForConversationAvatar(1, user.baseUrl, roomToken)
|
ApiUtils.getUrlForConversationAvatar(1, user.baseUrl!!, roomToken)
|
||||||
).map { ConversationModel.mapToConversationModel(it.ocs?.data!!) }
|
).map { ConversationModel.mapToConversationModel(it.ocs?.data!!) }
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -115,6 +115,7 @@ import com.nextcloud.talk.ui.dialog.ConversationsListBottomDialog
|
||||||
import com.nextcloud.talk.ui.dialog.FilterConversationFragment
|
import com.nextcloud.talk.ui.dialog.FilterConversationFragment
|
||||||
import com.nextcloud.talk.users.UserManager
|
import com.nextcloud.talk.users.UserManager
|
||||||
import com.nextcloud.talk.utils.ApiUtils
|
import com.nextcloud.talk.utils.ApiUtils
|
||||||
|
import com.nextcloud.talk.utils.SpreedFeatures
|
||||||
import com.nextcloud.talk.utils.ClosedInterfaceImpl
|
import com.nextcloud.talk.utils.ClosedInterfaceImpl
|
||||||
import com.nextcloud.talk.utils.FileUtils
|
import com.nextcloud.talk.utils.FileUtils
|
||||||
import com.nextcloud.talk.utils.Mimetype
|
import com.nextcloud.talk.utils.Mimetype
|
||||||
|
@ -130,10 +131,10 @@ import com.nextcloud.talk.utils.bundle.BundleKeys.KEY_NEW_CONVERSATION
|
||||||
import com.nextcloud.talk.utils.bundle.BundleKeys.KEY_ROOM_ID
|
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_ROOM_TOKEN
|
||||||
import com.nextcloud.talk.utils.bundle.BundleKeys.KEY_SHARED_TEXT
|
import com.nextcloud.talk.utils.bundle.BundleKeys.KEY_SHARED_TEXT
|
||||||
import com.nextcloud.talk.utils.database.user.CapabilitiesUtilNew.hasSpreedFeatureCapability
|
import com.nextcloud.talk.utils.CapabilitiesUtil.hasSpreedFeatureCapability
|
||||||
import com.nextcloud.talk.utils.database.user.CapabilitiesUtilNew.isServerEOL
|
import com.nextcloud.talk.utils.CapabilitiesUtil.isServerEOL
|
||||||
import com.nextcloud.talk.utils.database.user.CapabilitiesUtilNew.isUnifiedSearchAvailable
|
import com.nextcloud.talk.utils.CapabilitiesUtil.isUnifiedSearchAvailable
|
||||||
import com.nextcloud.talk.utils.database.user.CapabilitiesUtilNew.isUserStatusAvailable
|
import com.nextcloud.talk.utils.CapabilitiesUtil.isUserStatusAvailable
|
||||||
import com.nextcloud.talk.utils.permissions.PlatformPermissionUtil
|
import com.nextcloud.talk.utils.permissions.PlatformPermissionUtil
|
||||||
import com.nextcloud.talk.utils.power.PowerManagerUtils
|
import com.nextcloud.talk.utils.power.PowerManagerUtils
|
||||||
import com.nextcloud.talk.utils.rx.SearchViewObservable.Companion.observeSearchView
|
import com.nextcloud.talk.utils.rx.SearchViewObservable.Companion.observeSearchView
|
||||||
|
@ -283,11 +284,11 @@ class ConversationsListActivity :
|
||||||
}
|
}
|
||||||
currentUser = userManager.currentUser.blockingGet()
|
currentUser = userManager.currentUser.blockingGet()
|
||||||
if (currentUser != null) {
|
if (currentUser != null) {
|
||||||
if (isServerEOL(currentUser!!.capabilities)) {
|
if (isServerEOL(currentUser!!.serverVersion!!.major)) {
|
||||||
showServerEOLDialog()
|
showServerEOLDialog()
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
if (isUnifiedSearchAvailable(currentUser!!)) {
|
if (isUnifiedSearchAvailable(currentUser!!.capabilities!!.spreedCapability!!)) {
|
||||||
searchHelper = MessageSearchHelper(unifiedSearchRepository)
|
searchHelper = MessageSearchHelper(unifiedSearchRepository)
|
||||||
}
|
}
|
||||||
credentials = ApiUtils.getCredentials(currentUser!!.username, currentUser!!.token)
|
credentials = ApiUtils.getCredentials(currentUser!!.username, currentUser!!.token)
|
||||||
|
@ -423,7 +424,7 @@ class ConversationsListActivity :
|
||||||
private fun loadUserAvatar(target: Target) {
|
private fun loadUserAvatar(target: Target) {
|
||||||
if (currentUser != null) {
|
if (currentUser != null) {
|
||||||
val url = ApiUtils.getUrlForAvatar(
|
val url = ApiUtils.getUrlForAvatar(
|
||||||
currentUser!!.baseUrl,
|
currentUser!!.baseUrl!!,
|
||||||
currentUser!!.userId,
|
currentUser!!.userId,
|
||||||
true
|
true
|
||||||
)
|
)
|
||||||
|
@ -433,7 +434,7 @@ class ConversationsListActivity :
|
||||||
context.imageLoader.enqueue(
|
context.imageLoader.enqueue(
|
||||||
ImageRequest.Builder(context)
|
ImageRequest.Builder(context)
|
||||||
.data(url)
|
.data(url)
|
||||||
.addHeader("Authorization", credentials)
|
.addHeader("Authorization", credentials!!)
|
||||||
.placeholder(R.drawable.ic_user)
|
.placeholder(R.drawable.ic_user)
|
||||||
.transformations(CircleCropTransformation())
|
.transformations(CircleCropTransformation())
|
||||||
.crossfade(true)
|
.crossfade(true)
|
||||||
|
@ -698,7 +699,10 @@ class ConversationsListActivity :
|
||||||
isRefreshing = true
|
isRefreshing = true
|
||||||
conversationItems = ArrayList()
|
conversationItems = ArrayList()
|
||||||
conversationItemsWithHeader = ArrayList()
|
conversationItemsWithHeader = ArrayList()
|
||||||
val apiVersion = ApiUtils.getConversationApiVersion(currentUser, intArrayOf(ApiUtils.APIv4, ApiUtils.APIv3, 1))
|
val apiVersion = ApiUtils.getConversationApiVersion(
|
||||||
|
currentUser!!,
|
||||||
|
intArrayOf(ApiUtils.API_V4, ApiUtils.API_V3, 1)
|
||||||
|
)
|
||||||
val startNanoTime = System.nanoTime()
|
val startNanoTime = System.nanoTime()
|
||||||
Log.d(TAG, "fetchData - getRooms - calling: $startNanoTime")
|
Log.d(TAG, "fetchData - getRooms - calling: $startNanoTime")
|
||||||
roomsQueryDisposable = ncApi.getRooms(
|
roomsQueryDisposable = ncApi.getRooms(
|
||||||
|
@ -868,11 +872,15 @@ class ConversationsListActivity :
|
||||||
private fun fetchOpenConversations(apiVersion: Int) {
|
private fun fetchOpenConversations(apiVersion: Int) {
|
||||||
searchableConversationItems.clear()
|
searchableConversationItems.clear()
|
||||||
searchableConversationItems.addAll(conversationItemsWithHeader)
|
searchableConversationItems.addAll(conversationItemsWithHeader)
|
||||||
if (hasSpreedFeatureCapability(currentUser, "listable-rooms")) {
|
if (hasSpreedFeatureCapability(
|
||||||
|
currentUser!!.capabilities!!.spreedCapability!!,
|
||||||
|
SpreedFeatures.LISTABLE_ROOMS
|
||||||
|
)
|
||||||
|
) {
|
||||||
val openConversationItems: MutableList<AbstractFlexibleItem<*>> = ArrayList()
|
val openConversationItems: MutableList<AbstractFlexibleItem<*>> = ArrayList()
|
||||||
openConversationsQueryDisposable = ncApi.getOpenConversations(
|
openConversationsQueryDisposable = ncApi.getOpenConversations(
|
||||||
credentials,
|
credentials,
|
||||||
ApiUtils.getUrlForOpenConversations(apiVersion, currentUser!!.baseUrl)
|
ApiUtils.getUrlForOpenConversations(apiVersion, currentUser!!.baseUrl!!)
|
||||||
)
|
)
|
||||||
.subscribeOn(Schedulers.io())
|
.subscribeOn(Schedulers.io())
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
.observeOn(AndroidSchedulers.mainThread())
|
||||||
|
@ -1087,7 +1095,7 @@ class ConversationsListActivity :
|
||||||
clearMessageSearchResults()
|
clearMessageSearchResults()
|
||||||
adapter!!.setFilter(filter)
|
adapter!!.setFilter(filter)
|
||||||
adapter!!.filterItems()
|
adapter!!.filterItems()
|
||||||
if (isUnifiedSearchAvailable(currentUser!!)) {
|
if (isUnifiedSearchAvailable(currentUser!!.capabilities!!.spreedCapability!!)) {
|
||||||
startMessageSearch(filter)
|
startMessageSearch(filter)
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
|
@ -1173,7 +1181,11 @@ class ConversationsListActivity :
|
||||||
private fun handleConversation(conversation: Conversation?) {
|
private fun handleConversation(conversation: Conversation?) {
|
||||||
selectedConversation = conversation
|
selectedConversation = conversation
|
||||||
if (selectedConversation != null) {
|
if (selectedConversation != null) {
|
||||||
val hasChatPermission = ParticipantPermissions(currentUser!!, selectedConversation!!).hasChatPermission()
|
val hasChatPermission = ParticipantPermissions(
|
||||||
|
currentUser!!.capabilities!!.spreedCapability!!,
|
||||||
|
selectedConversation!!
|
||||||
|
)
|
||||||
|
.hasChatPermission()
|
||||||
if (showShareToScreen) {
|
if (showShareToScreen) {
|
||||||
if (hasChatPermission &&
|
if (hasChatPermission &&
|
||||||
!isReadOnlyConversation(selectedConversation!!) &&
|
!isReadOnlyConversation(selectedConversation!!) &&
|
||||||
|
@ -1197,7 +1209,10 @@ class ConversationsListActivity :
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun shouldShowLobby(conversation: Conversation): Boolean {
|
private fun shouldShowLobby(conversation: Conversation): Boolean {
|
||||||
val participantPermissions = ParticipantPermissions(currentUser!!, conversation)
|
val participantPermissions = ParticipantPermissions(
|
||||||
|
currentUser!!.capabilities?.spreedCapability!!,
|
||||||
|
conversation
|
||||||
|
)
|
||||||
return conversation.lobbyState == Conversation.LobbyState.LOBBY_STATE_MODERATORS_ONLY &&
|
return conversation.lobbyState == Conversation.LobbyState.LOBBY_STATE_MODERATORS_ONLY &&
|
||||||
!conversation.canModerate(currentUser!!) &&
|
!conversation.canModerate(currentUser!!) &&
|
||||||
!participantPermissions.canIgnoreLobby()
|
!participantPermissions.canIgnoreLobby()
|
||||||
|
@ -1511,7 +1526,7 @@ class ConversationsListActivity :
|
||||||
.setNegativeButton(R.string.nc_settings_reauthorize) { _, _ ->
|
.setNegativeButton(R.string.nc_settings_reauthorize) { _, _ ->
|
||||||
val intent = Intent(context, WebViewLoginActivity::class.java)
|
val intent = Intent(context, WebViewLoginActivity::class.java)
|
||||||
val bundle = Bundle()
|
val bundle = Bundle()
|
||||||
bundle.putString(BundleKeys.KEY_BASE_URL, currentUser!!.baseUrl)
|
bundle.putString(BundleKeys.KEY_BASE_URL, currentUser!!.baseUrl!!)
|
||||||
bundle.putBoolean(BundleKeys.KEY_REAUTHORIZE_ACCOUNT, true)
|
bundle.putBoolean(BundleKeys.KEY_REAUTHORIZE_ACCOUNT, true)
|
||||||
intent.putExtras(bundle)
|
intent.putExtras(bundle)
|
||||||
startActivity(intent)
|
startActivity(intent)
|
||||||
|
|
|
@ -27,6 +27,7 @@ import com.nextcloud.talk.callnotification.viewmodel.CallNotificationViewModel
|
||||||
import com.nextcloud.talk.chat.viewmodels.ChatViewModel
|
import com.nextcloud.talk.chat.viewmodels.ChatViewModel
|
||||||
import com.nextcloud.talk.conversation.viewmodel.ConversationViewModel
|
import com.nextcloud.talk.conversation.viewmodel.ConversationViewModel
|
||||||
import com.nextcloud.talk.conversation.viewmodel.RenameConversationViewModel
|
import com.nextcloud.talk.conversation.viewmodel.RenameConversationViewModel
|
||||||
|
import com.nextcloud.talk.conversationinfo.viewmodel.ConversationInfoViewModel
|
||||||
import com.nextcloud.talk.conversationinfoedit.viewmodel.ConversationInfoEditViewModel
|
import com.nextcloud.talk.conversationinfoedit.viewmodel.ConversationInfoEditViewModel
|
||||||
import com.nextcloud.talk.conversationlist.viewmodels.ConversationsListViewModel
|
import com.nextcloud.talk.conversationlist.viewmodels.ConversationsListViewModel
|
||||||
import com.nextcloud.talk.invitation.viewmodels.InvitationsViewModel
|
import com.nextcloud.talk.invitation.viewmodels.InvitationsViewModel
|
||||||
|
@ -137,6 +138,11 @@ abstract class ViewModelModule {
|
||||||
@ViewModelKey(CallNotificationViewModel::class)
|
@ViewModelKey(CallNotificationViewModel::class)
|
||||||
abstract fun callNotificationViewModel(viewModel: CallNotificationViewModel): ViewModel
|
abstract fun callNotificationViewModel(viewModel: CallNotificationViewModel): ViewModel
|
||||||
|
|
||||||
|
@Binds
|
||||||
|
@IntoMap
|
||||||
|
@ViewModelKey(ConversationInfoViewModel::class)
|
||||||
|
abstract fun conversationInfoViewModel(viewModel: ConversationInfoViewModel): ViewModel
|
||||||
|
|
||||||
@Binds
|
@Binds
|
||||||
@IntoMap
|
@IntoMap
|
||||||
@ViewModelKey(ConversationInfoEditViewModel::class)
|
@ViewModelKey(ConversationInfoEditViewModel::class)
|
||||||
|
|
|
@ -36,7 +36,7 @@ object UserMapper {
|
||||||
entity.id,
|
entity.id,
|
||||||
entity.userId,
|
entity.userId,
|
||||||
entity.username,
|
entity.username,
|
||||||
entity.baseUrl,
|
entity.baseUrl!!,
|
||||||
entity.token,
|
entity.token,
|
||||||
entity.displayName,
|
entity.displayName,
|
||||||
entity.pushConfigurationState,
|
entity.pushConfigurationState,
|
||||||
|
@ -52,8 +52,8 @@ object UserMapper {
|
||||||
|
|
||||||
fun toEntity(model: User): UserEntity {
|
fun toEntity(model: User): UserEntity {
|
||||||
val userEntity = when (val id = model.id) {
|
val userEntity = when (val id = model.id) {
|
||||||
null -> UserEntity(userId = model.userId, username = model.username, baseUrl = model.baseUrl)
|
null -> UserEntity(userId = model.userId, username = model.username, baseUrl = model.baseUrl!!)
|
||||||
else -> UserEntity(id, model.userId, model.username, model.baseUrl)
|
else -> UserEntity(id, model.userId, model.username, model.baseUrl!!)
|
||||||
}
|
}
|
||||||
userEntity.apply {
|
userEntity.apply {
|
||||||
token = model.token
|
token = model.token
|
||||||
|
|
|
@ -45,7 +45,7 @@ data class User(
|
||||||
var scheduledForDeletion: Boolean = FALSE
|
var scheduledForDeletion: Boolean = FALSE
|
||||||
) : Parcelable {
|
) : Parcelable {
|
||||||
|
|
||||||
fun getCredentials(): String = ApiUtils.getCredentials(username, token)
|
fun getCredentials(): String = ApiUtils.getCredentials(username, token)!!
|
||||||
|
|
||||||
fun hasSpreedFeatureCapability(capabilityName: String): Boolean {
|
fun hasSpreedFeatureCapability(capabilityName: String): Boolean {
|
||||||
return capabilities?.spreedCapability?.features?.contains(capabilityName) ?: false
|
return capabilities?.spreedCapability?.features?.contains(capabilityName) ?: false
|
||||||
|
|
|
@ -118,7 +118,7 @@ fun ImageView.loadUserAvatar(
|
||||||
ignoreCache: Boolean
|
ignoreCache: Boolean
|
||||||
): io.reactivex.disposables.Disposable {
|
): io.reactivex.disposables.Disposable {
|
||||||
val imageRequestUri = ApiUtils.getUrlForAvatar(
|
val imageRequestUri = ApiUtils.getUrlForAvatar(
|
||||||
user.baseUrl,
|
user.baseUrl!!,
|
||||||
avatarId,
|
avatarId,
|
||||||
requestBigSize
|
requestBigSize
|
||||||
)
|
)
|
||||||
|
@ -155,7 +155,7 @@ private fun ImageView.loadAvatarInternal(
|
||||||
user?.let {
|
user?.let {
|
||||||
addHeader(
|
addHeader(
|
||||||
"Authorization",
|
"Authorization",
|
||||||
ApiUtils.getCredentials(user.username, user.token)
|
ApiUtils.getCredentials(user.username, user.token)!!
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
transformations(CircleCropTransformation())
|
transformations(CircleCropTransformation())
|
||||||
|
@ -196,7 +196,7 @@ fun ImageView.loadThumbnail(url: String, user: User): io.reactivex.disposables.D
|
||||||
) {
|
) {
|
||||||
requestBuilder.addHeader(
|
requestBuilder.addHeader(
|
||||||
"Authorization",
|
"Authorization",
|
||||||
ApiUtils.getCredentials(user.username, user.token)
|
ApiUtils.getCredentials(user.username, user.token)!!
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -222,7 +222,7 @@ fun ImageView.loadImage(url: String, user: User, placeholder: Drawable? = null):
|
||||||
) {
|
) {
|
||||||
requestBuilder.addHeader(
|
requestBuilder.addHeader(
|
||||||
"Authorization",
|
"Authorization",
|
||||||
ApiUtils.getCredentials(user.username, user.token)
|
ApiUtils.getCredentials(user.username, user.token)!!
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -29,29 +29,29 @@ class InvitationsRepositoryImpl(private val ncApi: NcApi) :
|
||||||
InvitationsRepository {
|
InvitationsRepository {
|
||||||
|
|
||||||
override fun fetchInvitations(user: User): Observable<InvitationsModel> {
|
override fun fetchInvitations(user: User): Observable<InvitationsModel> {
|
||||||
val credentials: String = ApiUtils.getCredentials(user.username, user.token)
|
val credentials: String = ApiUtils.getCredentials(user.username, user.token)!!
|
||||||
|
|
||||||
return ncApi.getInvitations(
|
return ncApi.getInvitations(
|
||||||
credentials,
|
credentials,
|
||||||
ApiUtils.getUrlForInvitation(user.baseUrl)
|
ApiUtils.getUrlForInvitation(user.baseUrl!!)
|
||||||
).map { mapToInvitationsModel(user, it.ocs?.data!!) }
|
).map { mapToInvitationsModel(user, it.ocs?.data!!) }
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun acceptInvitation(user: User, invitation: Invitation): Observable<InvitationActionModel> {
|
override fun acceptInvitation(user: User, invitation: Invitation): Observable<InvitationActionModel> {
|
||||||
val credentials: String = ApiUtils.getCredentials(user.username, user.token)
|
val credentials: String = ApiUtils.getCredentials(user.username, user.token)!!
|
||||||
|
|
||||||
return ncApi.acceptInvitation(
|
return ncApi.acceptInvitation(
|
||||||
credentials,
|
credentials,
|
||||||
ApiUtils.getUrlForInvitationAccept(user.baseUrl, invitation.id)
|
ApiUtils.getUrlForInvitationAccept(user.baseUrl!!, invitation.id)
|
||||||
).map { InvitationActionModel(ActionEnum.ACCEPT, it.ocs?.meta?.statusCode!!, invitation) }
|
).map { InvitationActionModel(ActionEnum.ACCEPT, it.ocs?.meta?.statusCode!!, invitation) }
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun rejectInvitation(user: User, invitation: Invitation): Observable<InvitationActionModel> {
|
override fun rejectInvitation(user: User, invitation: Invitation): Observable<InvitationActionModel> {
|
||||||
val credentials: String = ApiUtils.getCredentials(user.username, user.token)
|
val credentials: String = ApiUtils.getCredentials(user.username, user.token)!!
|
||||||
|
|
||||||
return ncApi.rejectInvitation(
|
return ncApi.rejectInvitation(
|
||||||
credentials,
|
credentials,
|
||||||
ApiUtils.getUrlForInvitationReject(user.baseUrl, invitation.id)
|
ApiUtils.getUrlForInvitationReject(user.baseUrl!!, invitation.id)
|
||||||
).map { InvitationActionModel(ActionEnum.REJECT, it.ocs?.meta?.statusCode!!, invitation) }
|
).map { InvitationActionModel(ActionEnum.REJECT, it.ocs?.meta?.statusCode!!, invitation) }
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -70,7 +70,7 @@ public class AddParticipantsToConversation extends Worker {
|
||||||
data.getLong(BundleKeys.KEY_INTERNAL_USER_ID, -1))
|
data.getLong(BundleKeys.KEY_INTERNAL_USER_ID, -1))
|
||||||
.blockingGet();
|
.blockingGet();
|
||||||
|
|
||||||
int apiVersion = ApiUtils.getConversationApiVersion(user, new int[] {ApiUtils.APIv4, 1});
|
int apiVersion = ApiUtils.getConversationApiVersion(user, new int[] {ApiUtils.API_V4, 1});
|
||||||
|
|
||||||
String conversationToken = data.getString(BundleKeys.KEY_TOKEN);
|
String conversationToken = data.getString(BundleKeys.KEY_TOKEN);
|
||||||
String credentials = ApiUtils.getCredentials(user.getUsername(), user.getToken());
|
String credentials = ApiUtils.getCredentials(user.getUsername(), user.getToken());
|
||||||
|
|
|
@ -129,7 +129,7 @@ class ContactAddressBookWorker(val context: Context, workerParameters: WorkerPar
|
||||||
|
|
||||||
ncApi.searchContactsByPhoneNumber(
|
ncApi.searchContactsByPhoneNumber(
|
||||||
ApiUtils.getCredentials(currentUser.username, currentUser.token),
|
ApiUtils.getCredentials(currentUser.username, currentUser.token),
|
||||||
ApiUtils.getUrlForSearchByNumber(currentUser.baseUrl),
|
ApiUtils.getUrlForSearchByNumber(currentUser.baseUrl!!),
|
||||||
json.toRequestBody("application/json".toMediaTypeOrNull())
|
json.toRequestBody("application/json".toMediaTypeOrNull())
|
||||||
)
|
)
|
||||||
.subscribeOn(Schedulers.io())
|
.subscribeOn(Schedulers.io())
|
||||||
|
|
|
@ -80,7 +80,7 @@ public class DeleteConversationWorker extends Worker {
|
||||||
User operationUser = userManager.getUserWithId(operationUserId).blockingGet();
|
User operationUser = userManager.getUserWithId(operationUserId).blockingGet();
|
||||||
|
|
||||||
if (operationUser != null) {
|
if (operationUser != null) {
|
||||||
int apiVersion = ApiUtils.getConversationApiVersion(operationUser, new int[]{ApiUtils.APIv4, 1});
|
int apiVersion = ApiUtils.getConversationApiVersion(operationUser, new int[]{ApiUtils.API_V4, 1});
|
||||||
|
|
||||||
String credentials = ApiUtils.getCredentials(operationUser.getUsername(), operationUser.getToken());
|
String credentials = ApiUtils.getCredentials(operationUser.getUsername(), operationUser.getToken());
|
||||||
ncApi = retrofit
|
ncApi = retrofit
|
||||||
|
|
|
@ -92,7 +92,7 @@ public class LeaveConversationWorker extends Worker {
|
||||||
EventStatus.EventType.CONVERSATION_UPDATE,
|
EventStatus.EventType.CONVERSATION_UPDATE,
|
||||||
true);
|
true);
|
||||||
|
|
||||||
int apiVersion = ApiUtils.getConversationApiVersion(operationUser, new int[] {ApiUtils.APIv4, 1});
|
int apiVersion = ApiUtils.getConversationApiVersion(operationUser, new int[] {ApiUtils.API_V4, 1});
|
||||||
|
|
||||||
ncApi.removeSelfFromRoom(credentials, ApiUtils.getUrlForParticipantsSelf(apiVersion,
|
ncApi.removeSelfFromRoom(credentials, ApiUtils.getUrlForParticipantsSelf(apiVersion,
|
||||||
operationUser.getBaseUrl(),
|
operationUser.getBaseUrl(),
|
||||||
|
|
|
@ -248,7 +248,7 @@ class NotificationWorker(context: Context, workerParams: WorkerParameters) : Wor
|
||||||
|
|
||||||
val soundUri = getCallRingtoneUri(applicationContext, appPreferences)
|
val soundUri = getCallRingtoneUri(applicationContext, appPreferences)
|
||||||
val notificationChannelId = NotificationUtils.NotificationChannels.NOTIFICATION_CHANNEL_CALLS_V4.name
|
val notificationChannelId = NotificationUtils.NotificationChannels.NOTIFICATION_CHANNEL_CALLS_V4.name
|
||||||
val uri = Uri.parse(signatureVerification.user!!.baseUrl)
|
val uri = Uri.parse(signatureVerification.user!!.baseUrl!!)
|
||||||
val baseUrl = uri.host
|
val baseUrl = uri.host
|
||||||
|
|
||||||
val notification =
|
val notification =
|
||||||
|
@ -279,7 +279,7 @@ class NotificationWorker(context: Context, workerParams: WorkerParameters) : Wor
|
||||||
credentials = ApiUtils.getCredentials(
|
credentials = ApiUtils.getCredentials(
|
||||||
signatureVerification.user!!.username,
|
signatureVerification.user!!.username,
|
||||||
signatureVerification.user!!.token
|
signatureVerification.user!!.token
|
||||||
)
|
)!!
|
||||||
ncApi = retrofit!!.newBuilder().client(
|
ncApi = retrofit!!.newBuilder().client(
|
||||||
okHttpClient!!.newBuilder().cookieJar(
|
okHttpClient!!.newBuilder().cookieJar(
|
||||||
JavaNetCookieJar(
|
JavaNetCookieJar(
|
||||||
|
@ -338,7 +338,7 @@ class NotificationWorker(context: Context, workerParams: WorkerParameters) : Wor
|
||||||
ncApi.getNcNotification(
|
ncApi.getNcNotification(
|
||||||
credentials,
|
credentials,
|
||||||
ApiUtils.getUrlForNcNotificationWithId(
|
ApiUtils.getUrlForNcNotificationWithId(
|
||||||
user!!.baseUrl,
|
user!!.baseUrl!!,
|
||||||
(pushMessage.notificationId!!).toString()
|
(pushMessage.notificationId!!).toString()
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
|
@ -451,7 +451,7 @@ class NotificationWorker(context: Context, workerParams: WorkerParameters) : Wor
|
||||||
0
|
0
|
||||||
}
|
}
|
||||||
val pendingIntent = PendingIntent.getActivity(context, requestCode, intent, intentFlag)
|
val pendingIntent = PendingIntent.getActivity(context, requestCode, intent, intentFlag)
|
||||||
val uri = Uri.parse(signatureVerification.user!!.baseUrl)
|
val uri = Uri.parse(signatureVerification.user!!.baseUrl!!)
|
||||||
val baseUrl = uri.host
|
val baseUrl = uri.host
|
||||||
|
|
||||||
var contentTitle: CharSequence? = ""
|
var contentTitle: CharSequence? = ""
|
||||||
|
@ -601,12 +601,12 @@ class NotificationWorker(context: Context, workerParams: WorkerParameters) : Wor
|
||||||
val baseUrl = signatureVerification.user!!.baseUrl
|
val baseUrl = signatureVerification.user!!.baseUrl
|
||||||
val avatarUrl = if ("user" == userType) {
|
val avatarUrl = if ("user" == userType) {
|
||||||
ApiUtils.getUrlForAvatar(
|
ApiUtils.getUrlForAvatar(
|
||||||
baseUrl,
|
baseUrl!!,
|
||||||
notificationUser.id,
|
notificationUser.id,
|
||||||
false
|
false
|
||||||
)
|
)
|
||||||
} else {
|
} else {
|
||||||
ApiUtils.getUrlForGuestAvatar(baseUrl, notificationUser.name, false)
|
ApiUtils.getUrlForGuestAvatar(baseUrl!!, notificationUser.name, false)
|
||||||
}
|
}
|
||||||
person.setIcon(loadAvatarSync(avatarUrl, context!!))
|
person.setIcon(loadAvatarSync(avatarUrl, context!!))
|
||||||
}
|
}
|
||||||
|
@ -840,8 +840,8 @@ class NotificationWorker(context: Context, workerParams: WorkerParameters) : Wor
|
||||||
var inCallOnDifferentDevice = false
|
var inCallOnDifferentDevice = false
|
||||||
|
|
||||||
val apiVersion = ApiUtils.getConversationApiVersion(
|
val apiVersion = ApiUtils.getConversationApiVersion(
|
||||||
signatureVerification.user,
|
signatureVerification.user!!,
|
||||||
intArrayOf(ApiUtils.APIv4, 1)
|
intArrayOf(ApiUtils.API_V4, 1)
|
||||||
)
|
)
|
||||||
|
|
||||||
var isCallNotificationVisible = true
|
var isCallNotificationVisible = true
|
||||||
|
@ -850,8 +850,8 @@ class NotificationWorker(context: Context, workerParams: WorkerParameters) : Wor
|
||||||
credentials,
|
credentials,
|
||||||
ApiUtils.getUrlForCall(
|
ApiUtils.getUrlForCall(
|
||||||
apiVersion,
|
apiVersion,
|
||||||
signatureVerification.user!!.baseUrl,
|
signatureVerification.user!!.baseUrl!!,
|
||||||
pushMessage.id
|
pushMessage.id!!
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
.repeatWhen { completed ->
|
.repeatWhen { completed ->
|
||||||
|
@ -920,10 +920,10 @@ class NotificationWorker(context: Context, workerParams: WorkerParameters) : Wor
|
||||||
|
|
||||||
if (isOngoingCallNotificationVisible) {
|
if (isOngoingCallNotificationVisible) {
|
||||||
val apiVersion = ApiUtils.getConversationApiVersion(
|
val apiVersion = ApiUtils.getConversationApiVersion(
|
||||||
signatureVerification.user,
|
signatureVerification.user!!,
|
||||||
intArrayOf(
|
intArrayOf(
|
||||||
ApiUtils.APIv4,
|
ApiUtils.API_V4,
|
||||||
ApiUtils.APIv3,
|
ApiUtils.API_V3,
|
||||||
1
|
1
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
|
@ -931,7 +931,7 @@ class NotificationWorker(context: Context, workerParams: WorkerParameters) : Wor
|
||||||
credentials,
|
credentials,
|
||||||
ApiUtils.getUrlForRoom(
|
ApiUtils.getUrlForRoom(
|
||||||
apiVersion,
|
apiVersion,
|
||||||
signatureVerification.user?.baseUrl,
|
signatureVerification.user?.baseUrl!!,
|
||||||
pushMessage.id
|
pushMessage.id
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
|
|
|
@ -62,7 +62,7 @@ class ShareOperationWorker(context: Context, workerParams: WorkerParameters) : W
|
||||||
for (filePath in filesArray) {
|
for (filePath in filesArray) {
|
||||||
ncApi.createRemoteShare(
|
ncApi.createRemoteShare(
|
||||||
credentials,
|
credentials,
|
||||||
ApiUtils.getSharingUrl(baseUrl),
|
ApiUtils.getSharingUrl(baseUrl!!),
|
||||||
filePath,
|
filePath,
|
||||||
roomToken,
|
roomToken,
|
||||||
"10",
|
"10",
|
||||||
|
@ -87,7 +87,7 @@ class ShareOperationWorker(context: Context, workerParams: WorkerParameters) : W
|
||||||
|
|
||||||
val operationsUser = userManager.getUserWithId(userId).blockingGet()
|
val operationsUser = userManager.getUserWithId(userId).blockingGet()
|
||||||
baseUrl = operationsUser.baseUrl
|
baseUrl = operationsUser.baseUrl
|
||||||
credentials = ApiUtils.getCredentials(operationsUser.username, operationsUser.token)
|
credentials = ApiUtils.getCredentials(operationsUser.username, operationsUser.token)!!
|
||||||
}
|
}
|
||||||
|
|
||||||
companion object {
|
companion object {
|
||||||
|
|
|
@ -85,7 +85,7 @@ public class SignalingSettingsWorker extends Worker {
|
||||||
|
|
||||||
for (User user : userEntityObjectList) {
|
for (User user : userEntityObjectList) {
|
||||||
|
|
||||||
int apiVersion = ApiUtils.getSignalingApiVersion(user, new int[] {ApiUtils.APIv3, 2, 1});
|
int apiVersion = ApiUtils.getSignalingApiVersion(user, new int[] {ApiUtils.API_V3, 2, 1});
|
||||||
|
|
||||||
ncApi.getSignalingSettings(
|
ncApi.getSignalingSettings(
|
||||||
ApiUtils.getCredentials(user.getUsername(), user.getToken()),
|
ApiUtils.getCredentials(user.getUsername(), user.getToken()),
|
||||||
|
|
|
@ -56,7 +56,7 @@ import com.nextcloud.talk.utils.RemoteFileUtils
|
||||||
import com.nextcloud.talk.utils.bundle.BundleKeys.KEY_FROM_NOTIFICATION_START_CALL
|
import com.nextcloud.talk.utils.bundle.BundleKeys.KEY_FROM_NOTIFICATION_START_CALL
|
||||||
import com.nextcloud.talk.utils.bundle.BundleKeys.KEY_INTERNAL_USER_ID
|
import com.nextcloud.talk.utils.bundle.BundleKeys.KEY_INTERNAL_USER_ID
|
||||||
import com.nextcloud.talk.utils.bundle.BundleKeys.KEY_ROOM_TOKEN
|
import com.nextcloud.talk.utils.bundle.BundleKeys.KEY_ROOM_TOKEN
|
||||||
import com.nextcloud.talk.utils.database.user.CapabilitiesUtilNew
|
import com.nextcloud.talk.utils.CapabilitiesUtil
|
||||||
import com.nextcloud.talk.utils.permissions.PlatformPermissionUtil
|
import com.nextcloud.talk.utils.permissions.PlatformPermissionUtil
|
||||||
import com.nextcloud.talk.utils.preferences.AppPreferences
|
import com.nextcloud.talk.utils.preferences.AppPreferences
|
||||||
import okhttp3.MediaType.Companion.toMediaTypeOrNull
|
import okhttp3.MediaType.Companion.toMediaTypeOrNull
|
||||||
|
@ -186,7 +186,9 @@ class UploadAndShareFilesWorker(val context: Context, workerParameters: WorkerPa
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun getRemotePath(currentUser: User): String {
|
private fun getRemotePath(currentUser: User): String {
|
||||||
var remotePath = CapabilitiesUtilNew.getAttachmentFolder(currentUser)!! + "/" + fileName
|
var remotePath = CapabilitiesUtil.getAttachmentFolder(
|
||||||
|
currentUser.capabilities!!.spreedCapability!!
|
||||||
|
) + "/" + fileName
|
||||||
remotePath = RemoteFileUtils.getNewPathIfFileExists(
|
remotePath = RemoteFileUtils.getNewPathIfFileExists(
|
||||||
ncApi,
|
ncApi,
|
||||||
currentUser,
|
currentUser,
|
||||||
|
|
|
@ -64,6 +64,7 @@ class GeocodingActivity :
|
||||||
lateinit var okHttpClient: OkHttpClient
|
lateinit var okHttpClient: OkHttpClient
|
||||||
|
|
||||||
lateinit var roomToken: String
|
lateinit var roomToken: String
|
||||||
|
private var chatApiVersion: Int = 1
|
||||||
private var nominatimClient: TalkJsonNominatimClient? = null
|
private var nominatimClient: TalkJsonNominatimClient? = null
|
||||||
|
|
||||||
private var searchItem: MenuItem? = null
|
private var searchItem: MenuItem? = null
|
||||||
|
@ -86,6 +87,7 @@ class GeocodingActivity :
|
||||||
Configuration.getInstance().load(context, PreferenceManager.getDefaultSharedPreferences(context))
|
Configuration.getInstance().load(context, PreferenceManager.getDefaultSharedPreferences(context))
|
||||||
|
|
||||||
roomToken = intent.getStringExtra(BundleKeys.KEY_ROOM_TOKEN)!!
|
roomToken = intent.getStringExtra(BundleKeys.KEY_ROOM_TOKEN)!!
|
||||||
|
chatApiVersion = intent.getIntExtra(BundleKeys.KEY_CHAT_API_VERSION, 1)
|
||||||
|
|
||||||
recyclerView = findViewById(R.id.geocoding_results)
|
recyclerView = findViewById(R.id.geocoding_results)
|
||||||
recyclerView.layoutManager = LinearLayoutManager(this)
|
recyclerView.layoutManager = LinearLayoutManager(this)
|
||||||
|
@ -130,6 +132,7 @@ class GeocodingActivity :
|
||||||
val intent = Intent(this@GeocodingActivity, LocationPickerActivity::class.java)
|
val intent = Intent(this@GeocodingActivity, LocationPickerActivity::class.java)
|
||||||
intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP)
|
intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP)
|
||||||
intent.putExtra(BundleKeys.KEY_ROOM_TOKEN, roomToken)
|
intent.putExtra(BundleKeys.KEY_ROOM_TOKEN, roomToken)
|
||||||
|
intent.putExtra(BundleKeys.KEY_CHAT_API_VERSION, chatApiVersion)
|
||||||
intent.putExtra(BundleKeys.KEY_GEOCODING_RESULT, geocodingResult)
|
intent.putExtra(BundleKeys.KEY_GEOCODING_RESULT, geocodingResult)
|
||||||
startActivity(intent)
|
startActivity(intent)
|
||||||
}
|
}
|
||||||
|
@ -158,6 +161,7 @@ class GeocodingActivity :
|
||||||
val intent = Intent(this@GeocodingActivity, LocationPickerActivity::class.java)
|
val intent = Intent(this@GeocodingActivity, LocationPickerActivity::class.java)
|
||||||
intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP)
|
intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP)
|
||||||
intent.putExtra(BundleKeys.KEY_ROOM_TOKEN, roomToken)
|
intent.putExtra(BundleKeys.KEY_ROOM_TOKEN, roomToken)
|
||||||
|
intent.putExtra(BundleKeys.KEY_CHAT_API_VERSION, chatApiVersion)
|
||||||
intent.putExtra(BundleKeys.KEY_GEOCODING_RESULT, geocodingResult)
|
intent.putExtra(BundleKeys.KEY_GEOCODING_RESULT, geocodingResult)
|
||||||
startActivity(intent)
|
startActivity(intent)
|
||||||
}
|
}
|
||||||
|
@ -217,6 +221,7 @@ class GeocodingActivity :
|
||||||
val intent = Intent(context, LocationPickerActivity::class.java)
|
val intent = Intent(context, LocationPickerActivity::class.java)
|
||||||
intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP)
|
intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP)
|
||||||
intent.putExtra(BundleKeys.KEY_ROOM_TOKEN, roomToken)
|
intent.putExtra(BundleKeys.KEY_ROOM_TOKEN, roomToken)
|
||||||
|
intent.putExtra(BundleKeys.KEY_CHAT_API_VERSION, chatApiVersion)
|
||||||
startActivity(intent)
|
startActivity(intent)
|
||||||
return true
|
return true
|
||||||
}
|
}
|
||||||
|
|
|
@ -58,6 +58,7 @@ import com.nextcloud.talk.users.UserManager
|
||||||
import com.nextcloud.talk.utils.ApiUtils
|
import com.nextcloud.talk.utils.ApiUtils
|
||||||
import com.nextcloud.talk.utils.DisplayUtils
|
import com.nextcloud.talk.utils.DisplayUtils
|
||||||
import com.nextcloud.talk.utils.bundle.BundleKeys
|
import com.nextcloud.talk.utils.bundle.BundleKeys
|
||||||
|
import com.nextcloud.talk.utils.bundle.BundleKeys.KEY_CHAT_API_VERSION
|
||||||
import com.nextcloud.talk.utils.bundle.BundleKeys.KEY_GEOCODING_RESULT
|
import com.nextcloud.talk.utils.bundle.BundleKeys.KEY_GEOCODING_RESULT
|
||||||
import com.nextcloud.talk.utils.bundle.BundleKeys.KEY_ROOM_TOKEN
|
import com.nextcloud.talk.utils.bundle.BundleKeys.KEY_ROOM_TOKEN
|
||||||
import fr.dudie.nominatim.client.TalkJsonNominatimClient
|
import fr.dudie.nominatim.client.TalkJsonNominatimClient
|
||||||
|
@ -103,6 +104,7 @@ class LocationPickerActivity :
|
||||||
var nominatimClient: TalkJsonNominatimClient? = null
|
var nominatimClient: TalkJsonNominatimClient? = null
|
||||||
|
|
||||||
lateinit var roomToken: String
|
lateinit var roomToken: String
|
||||||
|
private var chatApiVersion: Int = 1
|
||||||
var geocodingResult: GeocodingResult? = null
|
var geocodingResult: GeocodingResult? = null
|
||||||
|
|
||||||
var myLocation: GeoPoint = GeoPoint(COORDINATE_ZERO, COORDINATE_ZERO)
|
var myLocation: GeoPoint = GeoPoint(COORDINATE_ZERO, COORDINATE_ZERO)
|
||||||
|
@ -130,6 +132,7 @@ class LocationPickerActivity :
|
||||||
NextcloudTalkApplication.sharedApplication!!.componentApplication.inject(this)
|
NextcloudTalkApplication.sharedApplication!!.componentApplication.inject(this)
|
||||||
|
|
||||||
roomToken = intent.getStringExtra(KEY_ROOM_TOKEN)!!
|
roomToken = intent.getStringExtra(KEY_ROOM_TOKEN)!!
|
||||||
|
chatApiVersion = intent.getIntExtra(KEY_CHAT_API_VERSION, 1)
|
||||||
geocodingResult = intent.getParcelableExtra(KEY_GEOCODING_RESULT)
|
geocodingResult = intent.getParcelableExtra(KEY_GEOCODING_RESULT)
|
||||||
|
|
||||||
if (savedInstanceState != null) {
|
if (savedInstanceState != null) {
|
||||||
|
@ -244,6 +247,7 @@ class LocationPickerActivity :
|
||||||
val intent = Intent(this, GeocodingActivity::class.java)
|
val intent = Intent(this, GeocodingActivity::class.java)
|
||||||
intent.putExtra(BundleKeys.KEY_GEOCODING_QUERY, query)
|
intent.putExtra(BundleKeys.KEY_GEOCODING_QUERY, query)
|
||||||
intent.putExtra(KEY_ROOM_TOKEN, roomToken)
|
intent.putExtra(KEY_ROOM_TOKEN, roomToken)
|
||||||
|
intent.putExtra(KEY_CHAT_API_VERSION, chatApiVersion)
|
||||||
startActivity(intent)
|
startActivity(intent)
|
||||||
}
|
}
|
||||||
return true
|
return true
|
||||||
|
@ -465,11 +469,10 @@ class LocationPickerActivity :
|
||||||
"\"longitude\":\"$selectedLon\",\"name\":\"$locationNameToShare\"}"
|
"\"longitude\":\"$selectedLon\",\"name\":\"$locationNameToShare\"}"
|
||||||
|
|
||||||
val currentUser = userManager.currentUser.blockingGet()
|
val currentUser = userManager.currentUser.blockingGet()
|
||||||
val apiVersion = ApiUtils.getChatApiVersion(currentUser, intArrayOf(1))
|
|
||||||
|
|
||||||
ncApi.sendLocation(
|
ncApi.sendLocation(
|
||||||
ApiUtils.getCredentials(currentUser.username, currentUser.token),
|
ApiUtils.getCredentials(currentUser.username, currentUser.token),
|
||||||
ApiUtils.getUrlToSendLocation(apiVersion, currentUser.baseUrl, roomToken),
|
ApiUtils.getUrlToSendLocation(chatApiVersion, currentUser.baseUrl!!, roomToken),
|
||||||
"geo-location",
|
"geo-location",
|
||||||
objectId,
|
objectId,
|
||||||
metaData
|
metaData
|
||||||
|
|
|
@ -27,5 +27,5 @@ import kotlinx.parcelize.Parcelize
|
||||||
@Parcelize
|
@Parcelize
|
||||||
data class RetrofitBucket(
|
data class RetrofitBucket(
|
||||||
var url: String? = null,
|
var url: String? = null,
|
||||||
var queryMap: Map<String, String>? = null
|
var queryMap: MutableMap<String, String>? = null
|
||||||
) : Parcelable
|
) : Parcelable
|
||||||
|
|
|
@ -3,7 +3,7 @@ package com.nextcloud.talk.models.domain
|
||||||
import com.nextcloud.talk.models.json.conversations.Conversation
|
import com.nextcloud.talk.models.json.conversations.Conversation
|
||||||
|
|
||||||
class ConversationModel(
|
class ConversationModel(
|
||||||
var roomId: String?,
|
var roomId: String? = null,
|
||||||
var token: String? = null,
|
var token: String? = null,
|
||||||
var name: String? = null,
|
var name: String? = null,
|
||||||
var displayName: String? = null,
|
var displayName: String? = null,
|
||||||
|
@ -42,7 +42,11 @@ class ConversationModel(
|
||||||
var statusClearAt: Long? = 0,
|
var statusClearAt: Long? = 0,
|
||||||
var callRecording: Int = 0,
|
var callRecording: Int = 0,
|
||||||
var avatarVersion: String? = null,
|
var avatarVersion: String? = null,
|
||||||
var hasCustomAvatar: Boolean? = null
|
var hasCustomAvatar: Boolean? = null,
|
||||||
|
var callStartTime: Long? = null,
|
||||||
|
var recordingConsentRequired: Int = 0,
|
||||||
|
var remoteServer: String? = null,
|
||||||
|
var remoteToken: String? = null
|
||||||
) {
|
) {
|
||||||
|
|
||||||
companion object {
|
companion object {
|
||||||
|
@ -95,7 +99,11 @@ class ConversationModel(
|
||||||
statusClearAt = conversation.statusClearAt,
|
statusClearAt = conversation.statusClearAt,
|
||||||
callRecording = conversation.callRecording,
|
callRecording = conversation.callRecording,
|
||||||
avatarVersion = conversation.avatarVersion,
|
avatarVersion = conversation.avatarVersion,
|
||||||
hasCustomAvatar = conversation.hasCustomAvatar
|
hasCustomAvatar = conversation.hasCustomAvatar,
|
||||||
|
callStartTime = conversation.callStartTime,
|
||||||
|
recordingConsentRequired = conversation.recordingConsentRequired,
|
||||||
|
remoteServer = conversation.remoteServer,
|
||||||
|
remoteToken = conversation.remoteToken
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -0,0 +1,45 @@
|
||||||
|
/*
|
||||||
|
* Nextcloud Talk application
|
||||||
|
*
|
||||||
|
* @author Mario Danic
|
||||||
|
* Copyright (C) 2017-2018 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.models.domain.converters
|
||||||
|
|
||||||
|
import com.bluelinelabs.logansquare.typeconverters.IntBasedTypeConverter
|
||||||
|
import com.nextcloud.talk.models.domain.NotificationLevel
|
||||||
|
|
||||||
|
class DomainEnumNotificationLevelConverter : IntBasedTypeConverter<NotificationLevel>() {
|
||||||
|
override fun getFromInt(i: Int): NotificationLevel {
|
||||||
|
return when (i) {
|
||||||
|
0 -> NotificationLevel.DEFAULT
|
||||||
|
1 -> NotificationLevel.ALWAYS
|
||||||
|
2 -> NotificationLevel.MENTION
|
||||||
|
3 -> NotificationLevel.NEVER
|
||||||
|
else -> NotificationLevel.DEFAULT
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun convertToInt(`object`: NotificationLevel): Int {
|
||||||
|
return when (`object`) {
|
||||||
|
NotificationLevel.DEFAULT -> 0
|
||||||
|
NotificationLevel.ALWAYS -> 1
|
||||||
|
NotificationLevel.MENTION -> 2
|
||||||
|
NotificationLevel.NEVER -> 3
|
||||||
|
else -> 0
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,42 @@
|
||||||
|
/*
|
||||||
|
* Nextcloud Talk application
|
||||||
|
*
|
||||||
|
* @author Mario Danic
|
||||||
|
* @author Tim Krüger
|
||||||
|
* @author Andy Scherzinger
|
||||||
|
* Copyright (C) 2022 Andy Scherzinger <info@andy-scherzinger.de>
|
||||||
|
* Copyright (C) 2022 Tim Krüger <t@timkrueger.me>
|
||||||
|
* Copyright (C) 2017-2018 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.models.json.capabilities
|
||||||
|
|
||||||
|
import android.os.Parcelable
|
||||||
|
import com.bluelinelabs.logansquare.annotation.JsonField
|
||||||
|
import com.bluelinelabs.logansquare.annotation.JsonObject
|
||||||
|
import com.nextcloud.talk.models.json.generic.GenericMeta
|
||||||
|
import kotlinx.parcelize.Parcelize
|
||||||
|
|
||||||
|
@Parcelize
|
||||||
|
@JsonObject
|
||||||
|
data class RoomCapabilitiesOCS(
|
||||||
|
@JsonField(name = ["meta"])
|
||||||
|
var meta: GenericMeta?,
|
||||||
|
@JsonField(name = ["data"])
|
||||||
|
var data: SpreedCapability?
|
||||||
|
) : Parcelable {
|
||||||
|
// This constructor is added to work with the 'com.bluelinelabs.logansquare.annotation.JsonObject'
|
||||||
|
constructor() : this(null, null)
|
||||||
|
}
|
|
@ -0,0 +1,37 @@
|
||||||
|
/*
|
||||||
|
* Nextcloud Talk application
|
||||||
|
*
|
||||||
|
* @author Mario Danic
|
||||||
|
* @author Tim Krüger
|
||||||
|
* Copyright (C) 2022 Tim Krüger <t@timkrueger.me>
|
||||||
|
* Copyright (C) 2017-2018 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.models.json.capabilities
|
||||||
|
|
||||||
|
import android.os.Parcelable
|
||||||
|
import com.bluelinelabs.logansquare.annotation.JsonField
|
||||||
|
import com.bluelinelabs.logansquare.annotation.JsonObject
|
||||||
|
import kotlinx.parcelize.Parcelize
|
||||||
|
|
||||||
|
@Parcelize
|
||||||
|
@JsonObject
|
||||||
|
data class RoomCapabilitiesOverall(
|
||||||
|
@JsonField(name = ["ocs"])
|
||||||
|
var ocs: RoomCapabilitiesOCS? = null
|
||||||
|
) : Parcelable {
|
||||||
|
// This constructor is added to work with the 'com.bluelinelabs.logansquare.annotation.JsonObject'
|
||||||
|
constructor() : this(null)
|
||||||
|
}
|
|
@ -37,7 +37,7 @@ import com.nextcloud.talk.data.user.model.User
|
||||||
import com.nextcloud.talk.models.json.chat.ChatUtils.Companion.getParsedMessage
|
import com.nextcloud.talk.models.json.chat.ChatUtils.Companion.getParsedMessage
|
||||||
import com.nextcloud.talk.models.json.converters.EnumSystemMessageTypeConverter
|
import com.nextcloud.talk.models.json.converters.EnumSystemMessageTypeConverter
|
||||||
import com.nextcloud.talk.utils.ApiUtils
|
import com.nextcloud.talk.utils.ApiUtils
|
||||||
import com.nextcloud.talk.utils.database.user.CapabilitiesUtilNew
|
import com.nextcloud.talk.utils.CapabilitiesUtil
|
||||||
import com.stfalcon.chatkit.commons.models.IUser
|
import com.stfalcon.chatkit.commons.models.IUser
|
||||||
import com.stfalcon.chatkit.commons.models.MessageContentType
|
import com.stfalcon.chatkit.commons.models.MessageContentType
|
||||||
import kotlinx.parcelize.Parcelize
|
import kotlinx.parcelize.Parcelize
|
||||||
|
@ -213,7 +213,7 @@ data class ChatMessage(
|
||||||
|
|
||||||
@Suppress("ReturnCount")
|
@Suppress("ReturnCount")
|
||||||
fun isLinkPreview(): Boolean {
|
fun isLinkPreview(): Boolean {
|
||||||
if (CapabilitiesUtilNew.isLinkPreviewAvailable(activeUser!!)) {
|
if (CapabilitiesUtil.isLinkPreviewAvailable(activeUser!!)) {
|
||||||
val regexStringFromServer = activeUser?.capabilities?.coreCapability?.referenceRegex
|
val regexStringFromServer = activeUser?.capabilities?.coreCapability?.referenceRegex
|
||||||
|
|
||||||
val regexFromServer = regexStringFromServer?.toRegex(setOf(RegexOption.MULTILINE, RegexOption.IGNORE_CASE))
|
val regexFromServer = regexStringFromServer?.toRegex(setOf(RegexOption.MULTILINE, RegexOption.IGNORE_CASE))
|
||||||
|
@ -249,8 +249,8 @@ data class ChatMessage(
|
||||||
if (!isVoiceMessage) {
|
if (!isVoiceMessage) {
|
||||||
if (activeUser != null && activeUser!!.baseUrl != null) {
|
if (activeUser != null && activeUser!!.baseUrl != null) {
|
||||||
return ApiUtils.getUrlForFilePreviewWithFileId(
|
return ApiUtils.getUrlForFilePreviewWithFileId(
|
||||||
activeUser!!.baseUrl,
|
activeUser!!.baseUrl!!,
|
||||||
individualHashMap["id"],
|
individualHashMap["id"]!!,
|
||||||
sharedApplication!!.resources.getDimensionPixelSize(R.dimen.maximum_file_preview_size)
|
sharedApplication!!.resources.getDimensionPixelSize(R.dimen.maximum_file_preview_size)
|
||||||
)
|
)
|
||||||
} else {
|
} else {
|
||||||
|
@ -413,11 +413,11 @@ data class ChatMessage(
|
||||||
null
|
null
|
||||||
}
|
}
|
||||||
actorType == "users" -> {
|
actorType == "users" -> {
|
||||||
ApiUtils.getUrlForAvatar(activeUser!!.baseUrl, actorId, true)
|
ApiUtils.getUrlForAvatar(activeUser!!.baseUrl!!, actorId, true)
|
||||||
}
|
}
|
||||||
actorType == "bridged" -> {
|
actorType == "bridged" -> {
|
||||||
ApiUtils.getUrlForAvatar(
|
ApiUtils.getUrlForAvatar(
|
||||||
activeUser!!.baseUrl,
|
activeUser!!.baseUrl!!,
|
||||||
"bridge-bot",
|
"bridge-bot",
|
||||||
true
|
true
|
||||||
)
|
)
|
||||||
|
@ -427,7 +427,7 @@ data class ChatMessage(
|
||||||
if (!TextUtils.isEmpty(actorDisplayName)) {
|
if (!TextUtils.isEmpty(actorDisplayName)) {
|
||||||
apiId = actorDisplayName
|
apiId = actorDisplayName
|
||||||
}
|
}
|
||||||
ApiUtils.getUrlForGuestAvatar(activeUser!!.baseUrl, apiId, true)
|
ApiUtils.getUrlForGuestAvatar(activeUser!!.baseUrl!!, apiId, true)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -38,8 +38,9 @@ import com.nextcloud.talk.models.json.converters.EnumParticipantTypeConverter
|
||||||
import com.nextcloud.talk.models.json.converters.EnumReadOnlyConversationConverter
|
import com.nextcloud.talk.models.json.converters.EnumReadOnlyConversationConverter
|
||||||
import com.nextcloud.talk.models.json.converters.EnumRoomTypeConverter
|
import com.nextcloud.talk.models.json.converters.EnumRoomTypeConverter
|
||||||
import com.nextcloud.talk.models.json.participants.Participant.ParticipantType
|
import com.nextcloud.talk.models.json.participants.Participant.ParticipantType
|
||||||
|
import com.nextcloud.talk.utils.SpreedFeatures
|
||||||
import com.nextcloud.talk.utils.ConversationUtils
|
import com.nextcloud.talk.utils.ConversationUtils
|
||||||
import com.nextcloud.talk.utils.database.user.CapabilitiesUtilNew
|
import com.nextcloud.talk.utils.CapabilitiesUtil
|
||||||
import kotlinx.parcelize.Parcelize
|
import kotlinx.parcelize.Parcelize
|
||||||
|
|
||||||
@Parcelize
|
@Parcelize
|
||||||
|
@ -160,7 +161,13 @@ data class Conversation(
|
||||||
var callStartTime: Long? = null,
|
var callStartTime: Long? = null,
|
||||||
|
|
||||||
@JsonField(name = ["recordingConsent"])
|
@JsonField(name = ["recordingConsent"])
|
||||||
var recordingConsentRequired: Int = 0
|
var recordingConsentRequired: Int = 0,
|
||||||
|
|
||||||
|
@JsonField(name = ["remoteServer"])
|
||||||
|
var remoteServer: String? = null,
|
||||||
|
|
||||||
|
@JsonField(name = ["remoteToken"])
|
||||||
|
var remoteToken: String? = null
|
||||||
|
|
||||||
) : Parcelable {
|
) : Parcelable {
|
||||||
// This constructor is added to work with the 'com.bluelinelabs.logansquare.annotation.JsonObject'
|
// This constructor is added to work with the 'com.bluelinelabs.logansquare.annotation.JsonObject'
|
||||||
|
@ -185,13 +192,20 @@ data class Conversation(
|
||||||
@Deprecated("Use ConversationUtil")
|
@Deprecated("Use ConversationUtil")
|
||||||
private fun isLockedOneToOne(conversationUser: User): Boolean {
|
private fun isLockedOneToOne(conversationUser: User): Boolean {
|
||||||
return type == ConversationType.ROOM_TYPE_ONE_TO_ONE_CALL &&
|
return type == ConversationType.ROOM_TYPE_ONE_TO_ONE_CALL &&
|
||||||
CapabilitiesUtilNew.hasSpreedFeatureCapability(conversationUser, "locked-one-to-one-rooms")
|
CapabilitiesUtil.hasSpreedFeatureCapability(
|
||||||
|
conversationUser.capabilities?.spreedCapability!!,
|
||||||
|
SpreedFeatures.LOCKED_ONE_TO_ONE_ROOMS
|
||||||
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
@Deprecated("Use ConversationUtil")
|
@Deprecated("Use ConversationUtil")
|
||||||
fun canModerate(conversationUser: User): Boolean {
|
fun canModerate(conversationUser: User): Boolean {
|
||||||
return isParticipantOwnerOrModerator &&
|
return isParticipantOwnerOrModerator &&
|
||||||
!isLockedOneToOne(conversationUser) &&
|
ConversationUtils.isLockedOneToOne(
|
||||||
|
ConversationModel.mapToConversationModel(this),
|
||||||
|
conversationUser
|
||||||
|
.capabilities?.spreedCapability!!
|
||||||
|
) &&
|
||||||
type != ConversationType.FORMER_ONE_TO_ONE &&
|
type != ConversationType.FORMER_ONE_TO_ONE &&
|
||||||
!ConversationUtils.isNoteToSelfConversation(ConversationModel.mapToConversationModel(this))
|
!ConversationUtils.isNoteToSelfConversation(ConversationModel.mapToConversationModel(this))
|
||||||
}
|
}
|
||||||
|
|
|
@ -31,14 +31,14 @@ class OpenConversationsRepositoryImpl(private val ncApi: NcApi, currentUserProvi
|
||||||
OpenConversationsRepository {
|
OpenConversationsRepository {
|
||||||
|
|
||||||
val currentUser: User = currentUserProvider.currentUser.blockingGet()
|
val currentUser: User = currentUserProvider.currentUser.blockingGet()
|
||||||
val credentials: String = ApiUtils.getCredentials(currentUser.username, currentUser.token)
|
val credentials: String = ApiUtils.getCredentials(currentUser.username, currentUser.token)!!
|
||||||
|
|
||||||
val apiVersion = ApiUtils.getConversationApiVersion(currentUser, intArrayOf(ApiUtils.APIv4, ApiUtils.APIv3, 1))
|
val apiVersion = ApiUtils.getConversationApiVersion(currentUser, intArrayOf(ApiUtils.API_V4, ApiUtils.API_V3, 1))
|
||||||
|
|
||||||
override fun fetchConversations(): Observable<OpenConversationsModel> {
|
override fun fetchConversations(): Observable<OpenConversationsModel> {
|
||||||
return ncApi.getOpenConversations(
|
return ncApi.getOpenConversations(
|
||||||
credentials,
|
credentials,
|
||||||
ApiUtils.getUrlForOpenConversations(apiVersion, currentUser.baseUrl)
|
ApiUtils.getUrlForOpenConversations(apiVersion, currentUser.baseUrl!!)
|
||||||
).map { mapToOpenConversationsModel(it.ocs?.data!!) }
|
).map { mapToOpenConversationsModel(it.ocs?.data!!) }
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -37,7 +37,7 @@ class PollRepositoryImpl(private val ncApi: NcApi, private val currentUserProvid
|
||||||
PollRepository {
|
PollRepository {
|
||||||
|
|
||||||
val currentUser: User = currentUserProvider.currentUser.blockingGet()
|
val currentUser: User = currentUserProvider.currentUser.blockingGet()
|
||||||
val credentials: String = ApiUtils.getCredentials(currentUser.username, currentUser.token)
|
val credentials: String = ApiUtils.getCredentials(currentUser.username, currentUser.token)!!
|
||||||
|
|
||||||
override fun createPoll(
|
override fun createPoll(
|
||||||
roomToken: String,
|
roomToken: String,
|
||||||
|
@ -49,7 +49,7 @@ class PollRepositoryImpl(private val ncApi: NcApi, private val currentUserProvid
|
||||||
return ncApi.createPoll(
|
return ncApi.createPoll(
|
||||||
credentials,
|
credentials,
|
||||||
ApiUtils.getUrlForPoll(
|
ApiUtils.getUrlForPoll(
|
||||||
currentUser.baseUrl,
|
currentUser.baseUrl!!,
|
||||||
roomToken
|
roomToken
|
||||||
),
|
),
|
||||||
question,
|
question,
|
||||||
|
@ -63,7 +63,7 @@ class PollRepositoryImpl(private val ncApi: NcApi, private val currentUserProvid
|
||||||
return ncApi.getPoll(
|
return ncApi.getPoll(
|
||||||
credentials,
|
credentials,
|
||||||
ApiUtils.getUrlForPoll(
|
ApiUtils.getUrlForPoll(
|
||||||
currentUser.baseUrl,
|
currentUser.baseUrl!!,
|
||||||
roomToken,
|
roomToken,
|
||||||
pollId
|
pollId
|
||||||
)
|
)
|
||||||
|
@ -74,7 +74,7 @@ class PollRepositoryImpl(private val ncApi: NcApi, private val currentUserProvid
|
||||||
return ncApi.votePoll(
|
return ncApi.votePoll(
|
||||||
credentials,
|
credentials,
|
||||||
ApiUtils.getUrlForPoll(
|
ApiUtils.getUrlForPoll(
|
||||||
currentUser.baseUrl,
|
currentUser.baseUrl!!,
|
||||||
roomToken,
|
roomToken,
|
||||||
pollId
|
pollId
|
||||||
),
|
),
|
||||||
|
@ -86,7 +86,7 @@ class PollRepositoryImpl(private val ncApi: NcApi, private val currentUserProvid
|
||||||
return ncApi.closePoll(
|
return ncApi.closePoll(
|
||||||
credentials,
|
credentials,
|
||||||
ApiUtils.getUrlForPoll(
|
ApiUtils.getUrlForPoll(
|
||||||
currentUser.baseUrl,
|
currentUser.baseUrl!!,
|
||||||
roomToken,
|
roomToken,
|
||||||
pollId
|
pollId
|
||||||
)
|
)
|
||||||
|
|
|
@ -77,6 +77,7 @@ public class MentionAutocompletePresenter extends RecyclerViewPresenter<Mention>
|
||||||
private Context context;
|
private Context context;
|
||||||
|
|
||||||
private String roomToken;
|
private String roomToken;
|
||||||
|
private int chatApiVersion;
|
||||||
|
|
||||||
private List<AbstractFlexibleItem> abstractFlexibleItemList = new ArrayList<>();
|
private List<AbstractFlexibleItem> abstractFlexibleItemList = new ArrayList<>();
|
||||||
|
|
||||||
|
@ -87,10 +88,11 @@ public class MentionAutocompletePresenter extends RecyclerViewPresenter<Mention>
|
||||||
currentUser = userManager.getCurrentUser().blockingGet();
|
currentUser = userManager.getCurrentUser().blockingGet();
|
||||||
}
|
}
|
||||||
|
|
||||||
public MentionAutocompletePresenter(Context context, String roomToken) {
|
public MentionAutocompletePresenter(Context context, String roomToken, int chatApiVersion) {
|
||||||
super(context);
|
super(context);
|
||||||
this.roomToken = roomToken;
|
this.roomToken = roomToken;
|
||||||
this.context = context;
|
this.context = context;
|
||||||
|
this.chatApiVersion = chatApiVersion;
|
||||||
NextcloudTalkApplication.Companion.getSharedApplication().getComponentApplication().inject(this);
|
NextcloudTalkApplication.Companion.getSharedApplication().getComponentApplication().inject(this);
|
||||||
currentUser = userManager.getCurrentUser().blockingGet();
|
currentUser = userManager.getCurrentUser().blockingGet();
|
||||||
}
|
}
|
||||||
|
@ -120,8 +122,6 @@ public class MentionAutocompletePresenter extends RecyclerViewPresenter<Mention>
|
||||||
queryString = "";
|
queryString = "";
|
||||||
}
|
}
|
||||||
|
|
||||||
int apiVersion = ApiUtils.getChatApiVersion(currentUser, new int[] {1});
|
|
||||||
|
|
||||||
adapter.setFilter(queryString);
|
adapter.setFilter(queryString);
|
||||||
|
|
||||||
Map<String, String> queryMap = new HashMap<>();
|
Map<String, String> queryMap = new HashMap<>();
|
||||||
|
@ -129,7 +129,7 @@ public class MentionAutocompletePresenter extends RecyclerViewPresenter<Mention>
|
||||||
|
|
||||||
ncApi.getMentionAutocompleteSuggestions(
|
ncApi.getMentionAutocompleteSuggestions(
|
||||||
ApiUtils.getCredentials(currentUser.getUsername(), currentUser.getToken()),
|
ApiUtils.getCredentials(currentUser.getUsername(), currentUser.getToken()),
|
||||||
ApiUtils.getUrlForMentionSuggestions(apiVersion, currentUser.getBaseUrl(), roomToken),
|
ApiUtils.getUrlForMentionSuggestions(chatApiVersion, currentUser.getBaseUrl(), roomToken),
|
||||||
queryString, 5, queryMap)
|
queryString, 5, queryMap)
|
||||||
.subscribeOn(Schedulers.io())
|
.subscribeOn(Schedulers.io())
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
.observeOn(AndroidSchedulers.mainThread())
|
||||||
|
|
|
@ -66,12 +66,13 @@ import com.nextcloud.talk.ui.dialog.ScopeDialog
|
||||||
import com.nextcloud.talk.ui.theme.ViewThemeUtils
|
import com.nextcloud.talk.ui.theme.ViewThemeUtils
|
||||||
import com.nextcloud.talk.users.UserManager
|
import com.nextcloud.talk.users.UserManager
|
||||||
import com.nextcloud.talk.utils.ApiUtils
|
import com.nextcloud.talk.utils.ApiUtils
|
||||||
|
import com.nextcloud.talk.utils.SpreedFeatures
|
||||||
import com.nextcloud.talk.utils.DisplayUtils
|
import com.nextcloud.talk.utils.DisplayUtils
|
||||||
import com.nextcloud.talk.utils.Mimetype.IMAGE_JPG
|
import com.nextcloud.talk.utils.Mimetype.IMAGE_JPG
|
||||||
import com.nextcloud.talk.utils.Mimetype.IMAGE_PREFIX_GENERIC
|
import com.nextcloud.talk.utils.Mimetype.IMAGE_PREFIX_GENERIC
|
||||||
import com.nextcloud.talk.utils.PickImage
|
import com.nextcloud.talk.utils.PickImage
|
||||||
import com.nextcloud.talk.utils.PickImage.Companion.REQUEST_PERMISSION_CAMERA
|
import com.nextcloud.talk.utils.PickImage.Companion.REQUEST_PERMISSION_CAMERA
|
||||||
import com.nextcloud.talk.utils.database.user.CapabilitiesUtilNew
|
import com.nextcloud.talk.utils.CapabilitiesUtil
|
||||||
import io.reactivex.Observer
|
import io.reactivex.Observer
|
||||||
import io.reactivex.android.schedulers.AndroidSchedulers
|
import io.reactivex.android.schedulers.AndroidSchedulers
|
||||||
import io.reactivex.disposables.Disposable
|
import io.reactivex.disposables.Disposable
|
||||||
|
@ -127,7 +128,7 @@ class ProfileActivity : BaseActivity() {
|
||||||
binding.avatarDelete.setOnClickListener {
|
binding.avatarDelete.setOnClickListener {
|
||||||
ncApi.deleteAvatar(
|
ncApi.deleteAvatar(
|
||||||
credentials,
|
credentials,
|
||||||
ApiUtils.getUrlForTempAvatar(currentUser!!.baseUrl)
|
ApiUtils.getUrlForTempAvatar(currentUser!!.baseUrl!!)
|
||||||
)
|
)
|
||||||
.subscribeOn(Schedulers.io())
|
.subscribeOn(Schedulers.io())
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
.observeOn(AndroidSchedulers.mainThread())
|
||||||
|
@ -154,7 +155,7 @@ class ProfileActivity : BaseActivity() {
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
binding.avatarImage.let { ViewCompat.setTransitionName(it, "userAvatar.transitionTag") }
|
binding.avatarImage.let { ViewCompat.setTransitionName(it, "userAvatar.transitionTag") }
|
||||||
ncApi.getUserProfile(credentials, ApiUtils.getUrlForUserProfile(currentUser!!.baseUrl))
|
ncApi.getUserProfile(credentials, ApiUtils.getUrlForUserProfile(currentUser!!.baseUrl!!))
|
||||||
.retry(DEFAULT_RETRIES)
|
.retry(DEFAULT_RETRIES)
|
||||||
.subscribeOn(Schedulers.io())
|
.subscribeOn(Schedulers.io())
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
.observeOn(AndroidSchedulers.mainThread())
|
||||||
|
@ -226,13 +227,17 @@ class ProfileActivity : BaseActivity() {
|
||||||
item.icon = ContextCompat.getDrawable(this, R.drawable.ic_check)
|
item.icon = ContextCompat.getDrawable(this, R.drawable.ic_check)
|
||||||
binding.emptyList.root.visibility = View.GONE
|
binding.emptyList.root.visibility = View.GONE
|
||||||
binding.userinfoList.visibility = View.VISIBLE
|
binding.userinfoList.visibility = View.VISIBLE
|
||||||
if (CapabilitiesUtilNew.isAvatarEndpointAvailable(currentUser!!)) {
|
if (CapabilitiesUtil.hasSpreedFeatureCapability(
|
||||||
|
currentUser!!.capabilities!!.spreedCapability!!,
|
||||||
|
SpreedFeatures.TEMP_USER_AVATAR_API
|
||||||
|
)
|
||||||
|
) {
|
||||||
// TODO later avatar can also be checked via user fields, for now it is in Talk capability
|
// TODO later avatar can also be checked via user fields, for now it is in Talk capability
|
||||||
binding.avatarButtons.visibility = View.VISIBLE
|
binding.avatarButtons.visibility = View.VISIBLE
|
||||||
}
|
}
|
||||||
ncApi.getEditableUserProfileFields(
|
ncApi.getEditableUserProfileFields(
|
||||||
ApiUtils.getCredentials(currentUser!!.username, currentUser!!.token),
|
ApiUtils.getCredentials(currentUser!!.username, currentUser!!.token),
|
||||||
ApiUtils.getUrlForUserFields(currentUser!!.baseUrl)
|
ApiUtils.getUrlForUserFields(currentUser!!.baseUrl!!)
|
||||||
)
|
)
|
||||||
.subscribeOn(Schedulers.io())
|
.subscribeOn(Schedulers.io())
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
.observeOn(AndroidSchedulers.mainThread())
|
||||||
|
@ -292,7 +297,7 @@ class ProfileActivity : BaseActivity() {
|
||||||
|
|
||||||
private fun showUserProfile() {
|
private fun showUserProfile() {
|
||||||
if (currentUser!!.baseUrl != null) {
|
if (currentUser!!.baseUrl != null) {
|
||||||
binding.userinfoBaseurl.text = Uri.parse(currentUser!!.baseUrl).host
|
binding.userinfoBaseurl.text = Uri.parse(currentUser!!.baseUrl!!).host
|
||||||
}
|
}
|
||||||
DisplayUtils.loadAvatarImage(currentUser, binding.avatarImage, false)
|
DisplayUtils.loadAvatarImage(currentUser, binding.avatarImage, false)
|
||||||
if (!TextUtils.isEmpty(userInfo?.displayName)) {
|
if (!TextUtils.isEmpty(userInfo?.displayName)) {
|
||||||
|
@ -327,10 +332,10 @@ class ProfileActivity : BaseActivity() {
|
||||||
}
|
}
|
||||||
|
|
||||||
// show edit button
|
// show edit button
|
||||||
if (CapabilitiesUtilNew.canEditScopes(currentUser!!)) {
|
if (CapabilitiesUtil.canEditScopes(currentUser!!)) {
|
||||||
ncApi.getEditableUserProfileFields(
|
ncApi.getEditableUserProfileFields(
|
||||||
ApiUtils.getCredentials(currentUser!!.username, currentUser!!.token),
|
ApiUtils.getCredentials(currentUser!!.username, currentUser!!.token),
|
||||||
ApiUtils.getUrlForUserFields(currentUser!!.baseUrl)
|
ApiUtils.getUrlForUserFields(currentUser!!.baseUrl!!)
|
||||||
)
|
)
|
||||||
.subscribeOn(Schedulers.io())
|
.subscribeOn(Schedulers.io())
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
.observeOn(AndroidSchedulers.mainThread())
|
||||||
|
@ -438,7 +443,7 @@ class ProfileActivity : BaseActivity() {
|
||||||
val credentials = ApiUtils.getCredentials(currentUser!!.username, currentUser!!.token)
|
val credentials = ApiUtils.getCredentials(currentUser!!.username, currentUser!!.token)
|
||||||
ncApi.setUserData(
|
ncApi.setUserData(
|
||||||
credentials,
|
credentials,
|
||||||
ApiUtils.getUrlForUserData(currentUser!!.baseUrl, currentUser!!.userId),
|
ApiUtils.getUrlForUserData(currentUser!!.baseUrl!!, currentUser!!.userId!!),
|
||||||
item.field.fieldName,
|
item.field.fieldName,
|
||||||
item.text
|
item.text
|
||||||
)
|
)
|
||||||
|
@ -535,7 +540,7 @@ class ProfileActivity : BaseActivity() {
|
||||||
// upload file
|
// upload file
|
||||||
ncApi.uploadAvatar(
|
ncApi.uploadAvatar(
|
||||||
ApiUtils.getCredentials(currentUser!!.username, currentUser!!.token),
|
ApiUtils.getCredentials(currentUser!!.username, currentUser!!.token),
|
||||||
ApiUtils.getUrlForTempAvatar(currentUser!!.baseUrl),
|
ApiUtils.getUrlForTempAvatar(currentUser!!.baseUrl!!),
|
||||||
filePart
|
filePart
|
||||||
)
|
)
|
||||||
.subscribeOn(Schedulers.io())
|
.subscribeOn(Schedulers.io())
|
||||||
|
@ -569,7 +574,7 @@ class ProfileActivity : BaseActivity() {
|
||||||
val credentials = ApiUtils.getCredentials(currentUser!!.username, currentUser!!.token)
|
val credentials = ApiUtils.getCredentials(currentUser!!.username, currentUser!!.token)
|
||||||
ncApi.setUserData(
|
ncApi.setUserData(
|
||||||
credentials,
|
credentials,
|
||||||
ApiUtils.getUrlForUserData(currentUser!!.baseUrl, currentUser!!.userId),
|
ApiUtils.getUrlForUserData(currentUser!!.baseUrl!!, currentUser!!.userId!!),
|
||||||
item.field.scopeName,
|
item.field.scopeName,
|
||||||
item.scope!!.name
|
item.scope!!.name
|
||||||
)
|
)
|
||||||
|
|
|
@ -31,7 +31,7 @@ class RequestAssistanceRepositoryImpl(private val ncApi: NcApi, currentUserProvi
|
||||||
RequestAssistanceRepository {
|
RequestAssistanceRepository {
|
||||||
|
|
||||||
val currentUser: User = currentUserProvider.currentUser.blockingGet()
|
val currentUser: User = currentUserProvider.currentUser.blockingGet()
|
||||||
val credentials: String = ApiUtils.getCredentials(currentUser.username, currentUser.token)
|
val credentials: String = ApiUtils.getCredentials(currentUser.username, currentUser.token)!!
|
||||||
|
|
||||||
var apiVersion = 1
|
var apiVersion = 1
|
||||||
|
|
||||||
|
|
|
@ -91,8 +91,8 @@ class DirectReplyReceiver : BroadcastReceiver() {
|
||||||
|
|
||||||
private fun sendDirectReply() {
|
private fun sendDirectReply() {
|
||||||
val credentials = ApiUtils.getCredentials(currentUser.username, currentUser.token)
|
val credentials = ApiUtils.getCredentials(currentUser.username, currentUser.token)
|
||||||
val apiVersion = ApiUtils.getChatApiVersion(currentUser, intArrayOf(1))
|
val apiVersion = ApiUtils.getChatApiVersion(currentUser.capabilities!!.spreedCapability!!, intArrayOf(1))
|
||||||
val url = ApiUtils.getUrlForChat(apiVersion, currentUser.baseUrl, roomToken)
|
val url = ApiUtils.getUrlForChat(apiVersion, currentUser.baseUrl!!, roomToken!!)
|
||||||
|
|
||||||
ncApi.sendChatMessage(credentials, url, replyMessage, currentUser.displayName, null, false)
|
ncApi.sendChatMessage(credentials, url, replyMessage, currentUser.displayName, null, false)
|
||||||
?.subscribeOn(Schedulers.io())
|
?.subscribeOn(Schedulers.io())
|
||||||
|
@ -153,7 +153,7 @@ class DirectReplyReceiver : BroadcastReceiver() {
|
||||||
|
|
||||||
// Add reply
|
// Add reply
|
||||||
Single.fromCallable {
|
Single.fromCallable {
|
||||||
val avatarUrl = ApiUtils.getUrlForAvatar(currentUser.baseUrl, currentUser.userId, false)
|
val avatarUrl = ApiUtils.getUrlForAvatar(currentUser.baseUrl!!, currentUser.userId, false)
|
||||||
val me = Person.Builder()
|
val me = Person.Builder()
|
||||||
.setName(currentUser.displayName)
|
.setName(currentUser.displayName)
|
||||||
.setIcon(NotificationUtils.loadAvatarSync(avatarUrl, context))
|
.setIcon(NotificationUtils.loadAvatarSync(avatarUrl, context))
|
||||||
|
|
|
@ -80,11 +80,11 @@ class MarkAsReadReceiver : BroadcastReceiver() {
|
||||||
|
|
||||||
private fun markAsRead() {
|
private fun markAsRead() {
|
||||||
val credentials = ApiUtils.getCredentials(currentUser.username, currentUser.token)
|
val credentials = ApiUtils.getCredentials(currentUser.username, currentUser.token)
|
||||||
val apiVersion = ApiUtils.getChatApiVersion(currentUser, intArrayOf(1))
|
val apiVersion = ApiUtils.getChatApiVersion(currentUser.capabilities!!.spreedCapability!!, intArrayOf(1))
|
||||||
val url = ApiUtils.getUrlForChatReadMarker(
|
val url = ApiUtils.getUrlForChatReadMarker(
|
||||||
apiVersion,
|
apiVersion,
|
||||||
currentUser.baseUrl,
|
currentUser.baseUrl!!,
|
||||||
roomToken
|
roomToken!!
|
||||||
)
|
)
|
||||||
|
|
||||||
ncApi.setChatReadMarker(credentials, url, messageId)
|
ncApi.setChatReadMarker(credentials, url, messageId)
|
||||||
|
|
|
@ -94,7 +94,7 @@ class RemoteFileBrowserItemsListViewHolder(
|
||||||
|
|
||||||
if (item.hasPreview) {
|
if (item.hasPreview) {
|
||||||
val path = ApiUtils.getUrlForFilePreviewWithRemotePath(
|
val path = ApiUtils.getUrlForFilePreviewWithRemotePath(
|
||||||
currentUser.baseUrl,
|
currentUser.baseUrl!!,
|
||||||
item.path,
|
item.path,
|
||||||
fileIcon.context.resources.getDimensionPixelSize(R.dimen.small_item_height)
|
fileIcon.context.resources.getDimensionPixelSize(R.dimen.small_item_height)
|
||||||
)
|
)
|
||||||
|
|
|
@ -33,7 +33,7 @@ class CallRecordingRepositoryImpl(private val ncApi: NcApi, currentUserProvider:
|
||||||
CallRecordingRepository {
|
CallRecordingRepository {
|
||||||
|
|
||||||
val currentUser: User = currentUserProvider.currentUser.blockingGet()
|
val currentUser: User = currentUserProvider.currentUser.blockingGet()
|
||||||
val credentials: String = ApiUtils.getCredentials(currentUser.username, currentUser.token)
|
val credentials: String = ApiUtils.getCredentials(currentUser.username, currentUser.token)!!
|
||||||
|
|
||||||
var apiVersion = 1
|
var apiVersion = 1
|
||||||
|
|
||||||
|
@ -42,7 +42,7 @@ class CallRecordingRepositoryImpl(private val ncApi: NcApi, currentUserProvider:
|
||||||
credentials,
|
credentials,
|
||||||
ApiUtils.getUrlForRecording(
|
ApiUtils.getUrlForRecording(
|
||||||
apiVersion,
|
apiVersion,
|
||||||
currentUser.baseUrl,
|
currentUser.baseUrl!!,
|
||||||
roomToken
|
roomToken
|
||||||
),
|
),
|
||||||
1
|
1
|
||||||
|
@ -54,7 +54,7 @@ class CallRecordingRepositoryImpl(private val ncApi: NcApi, currentUserProvider:
|
||||||
credentials,
|
credentials,
|
||||||
ApiUtils.getUrlForRecording(
|
ApiUtils.getUrlForRecording(
|
||||||
apiVersion,
|
apiVersion,
|
||||||
currentUser.baseUrl,
|
currentUser.baseUrl!!,
|
||||||
roomToken
|
roomToken
|
||||||
)
|
)
|
||||||
).map { mapToStopCallRecordingModel(it.ocs?.meta!!) }
|
).map { mapToStopCallRecordingModel(it.ocs?.meta!!) }
|
||||||
|
|
|
@ -38,12 +38,12 @@ class ConversationsRepositoryImpl(private val api: NcApi, private val userProvid
|
||||||
get() = userProvider.currentUser.blockingGet()
|
get() = userProvider.currentUser.blockingGet()
|
||||||
|
|
||||||
private val credentials: String
|
private val credentials: String
|
||||||
get() = ApiUtils.getCredentials(user.username, user.token)
|
get() = ApiUtils.getCredentials(user.username, user.token)!!
|
||||||
|
|
||||||
override fun allowGuests(token: String, allow: Boolean): Observable<AllowGuestsResult> {
|
override fun allowGuests(token: String, allow: Boolean): Observable<AllowGuestsResult> {
|
||||||
val url = ApiUtils.getUrlForRoomPublic(
|
val url = ApiUtils.getUrlForRoomPublic(
|
||||||
apiVersion(),
|
apiVersion(),
|
||||||
user.baseUrl,
|
user.baseUrl!!,
|
||||||
token
|
token
|
||||||
)
|
)
|
||||||
|
|
||||||
|
@ -100,7 +100,7 @@ class ConversationsRepositoryImpl(private val api: NcApi, private val userProvid
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun apiVersion(): Int {
|
private fun apiVersion(): Int {
|
||||||
return ApiUtils.getConversationApiVersion(user, intArrayOf(ApiUtils.APIv4))
|
return ApiUtils.getConversationApiVersion(user, intArrayOf(ApiUtils.API_V4))
|
||||||
}
|
}
|
||||||
|
|
||||||
companion object {
|
companion object {
|
||||||
|
|
|
@ -34,13 +34,13 @@ class ReactionsRepositoryImpl(private val ncApi: NcApi, currentUserProvider: Cur
|
||||||
ReactionsRepository {
|
ReactionsRepository {
|
||||||
|
|
||||||
val currentUser: User = currentUserProvider.currentUser.blockingGet()
|
val currentUser: User = currentUserProvider.currentUser.blockingGet()
|
||||||
val credentials: String = ApiUtils.getCredentials(currentUser.username, currentUser.token)
|
val credentials: String = ApiUtils.getCredentials(currentUser.username, currentUser.token)!!
|
||||||
|
|
||||||
override fun addReaction(roomToken: String, message: ChatMessage, emoji: String): Observable<ReactionAddedModel> {
|
override fun addReaction(roomToken: String, message: ChatMessage, emoji: String): Observable<ReactionAddedModel> {
|
||||||
return ncApi.sendReaction(
|
return ncApi.sendReaction(
|
||||||
credentials,
|
credentials,
|
||||||
ApiUtils.getUrlForMessageReaction(
|
ApiUtils.getUrlForMessageReaction(
|
||||||
currentUser.baseUrl,
|
currentUser.baseUrl!!,
|
||||||
roomToken,
|
roomToken,
|
||||||
message.id
|
message.id
|
||||||
),
|
),
|
||||||
|
@ -56,7 +56,7 @@ class ReactionsRepositoryImpl(private val ncApi: NcApi, currentUserProvider: Cur
|
||||||
return ncApi.deleteReaction(
|
return ncApi.deleteReaction(
|
||||||
credentials,
|
credentials,
|
||||||
ApiUtils.getUrlForMessageReaction(
|
ApiUtils.getUrlForMessageReaction(
|
||||||
currentUser.baseUrl,
|
currentUser.baseUrl!!,
|
||||||
roomToken,
|
roomToken,
|
||||||
message.id
|
message.id
|
||||||
),
|
),
|
||||||
|
|
|
@ -37,7 +37,7 @@ class UnifiedSearchRepositoryImpl(private val api: NcApi, private val userProvid
|
||||||
get() = userProvider.currentUser.blockingGet()
|
get() = userProvider.currentUser.blockingGet()
|
||||||
|
|
||||||
private val credentials: String
|
private val credentials: String
|
||||||
get() = ApiUtils.getCredentials(user.username, user.token)
|
get() = ApiUtils.getCredentials(user.username, user.token)!!
|
||||||
|
|
||||||
override fun searchMessages(
|
override fun searchMessages(
|
||||||
searchTerm: String,
|
searchTerm: String,
|
||||||
|
|
|
@ -90,6 +90,7 @@ import com.nextcloud.talk.models.json.userprofile.UserProfileOverall
|
||||||
import com.nextcloud.talk.profile.ProfileActivity
|
import com.nextcloud.talk.profile.ProfileActivity
|
||||||
import com.nextcloud.talk.users.UserManager
|
import com.nextcloud.talk.users.UserManager
|
||||||
import com.nextcloud.talk.utils.ApiUtils
|
import com.nextcloud.talk.utils.ApiUtils
|
||||||
|
import com.nextcloud.talk.utils.SpreedFeatures
|
||||||
import com.nextcloud.talk.utils.ClosedInterfaceImpl
|
import com.nextcloud.talk.utils.ClosedInterfaceImpl
|
||||||
import com.nextcloud.talk.utils.DisplayUtils
|
import com.nextcloud.talk.utils.DisplayUtils
|
||||||
import com.nextcloud.talk.utils.LoggingUtils.sendMailWithAttachment
|
import com.nextcloud.talk.utils.LoggingUtils.sendMailWithAttachment
|
||||||
|
@ -97,7 +98,7 @@ import com.nextcloud.talk.utils.NotificationUtils
|
||||||
import com.nextcloud.talk.utils.NotificationUtils.getCallRingtoneUri
|
import com.nextcloud.talk.utils.NotificationUtils.getCallRingtoneUri
|
||||||
import com.nextcloud.talk.utils.NotificationUtils.getMessageRingtoneUri
|
import com.nextcloud.talk.utils.NotificationUtils.getMessageRingtoneUri
|
||||||
import com.nextcloud.talk.utils.SecurityUtils
|
import com.nextcloud.talk.utils.SecurityUtils
|
||||||
import com.nextcloud.talk.utils.database.user.CapabilitiesUtilNew
|
import com.nextcloud.talk.utils.CapabilitiesUtil
|
||||||
import com.nextcloud.talk.utils.database.user.CurrentUserProviderNew
|
import com.nextcloud.talk.utils.database.user.CurrentUserProviderNew
|
||||||
import com.nextcloud.talk.utils.permissions.PlatformPermissionUtil
|
import com.nextcloud.talk.utils.permissions.PlatformPermissionUtil
|
||||||
import com.nextcloud.talk.utils.power.PowerManagerUtils
|
import com.nextcloud.talk.utils.power.PowerManagerUtils
|
||||||
|
@ -266,7 +267,11 @@ class SettingsActivity : BaseActivity() {
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun setupPhoneBookIntegration() {
|
private fun setupPhoneBookIntegration() {
|
||||||
if (CapabilitiesUtilNew.isPhoneBookIntegrationAvailable(currentUser!!)) {
|
if (CapabilitiesUtil.hasSpreedFeatureCapability(
|
||||||
|
currentUser?.capabilities?.spreedCapability!!,
|
||||||
|
SpreedFeatures.PHONEBOOK_SEARCH
|
||||||
|
)
|
||||||
|
) {
|
||||||
binding.settingsPhoneBookIntegration.visibility = View.VISIBLE
|
binding.settingsPhoneBookIntegration.visibility = View.VISIBLE
|
||||||
} else {
|
} else {
|
||||||
binding.settingsPhoneBookIntegration.visibility = View.GONE
|
binding.settingsPhoneBookIntegration.visibility = View.GONE
|
||||||
|
@ -507,7 +512,7 @@ class SettingsActivity : BaseActivity() {
|
||||||
var port = -1
|
var port = -1
|
||||||
val uri: URI
|
val uri: URI
|
||||||
try {
|
try {
|
||||||
uri = URI(currentUser!!.baseUrl)
|
uri = URI(currentUser!!.baseUrl!!)
|
||||||
host = uri.host
|
host = uri.host
|
||||||
port = uri.port
|
port = uri.port
|
||||||
Log.d(TAG, "uri is $uri")
|
Log.d(TAG, "uri is $uri")
|
||||||
|
@ -823,7 +828,7 @@ class SettingsActivity : BaseActivity() {
|
||||||
private fun setupProfileQueryDisposable() {
|
private fun setupProfileQueryDisposable() {
|
||||||
profileQueryDisposable = ncApi.getUserProfile(
|
profileQueryDisposable = ncApi.getUserProfile(
|
||||||
credentials,
|
credentials,
|
||||||
ApiUtils.getUrlForUserProfile(currentUser!!.baseUrl)
|
ApiUtils.getUrlForUserProfile(currentUser!!.baseUrl!!)
|
||||||
)
|
)
|
||||||
.subscribeOn(Schedulers.io())
|
.subscribeOn(Schedulers.io())
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
.observeOn(AndroidSchedulers.mainThread())
|
||||||
|
@ -854,7 +859,7 @@ class SettingsActivity : BaseActivity() {
|
||||||
|
|
||||||
private fun setupServerAgeWarning() {
|
private fun setupServerAgeWarning() {
|
||||||
when {
|
when {
|
||||||
CapabilitiesUtilNew.isServerEOL(currentUser!!.capabilities) -> {
|
CapabilitiesUtil.isServerEOL(currentUser!!.serverVersion!!.major) -> {
|
||||||
binding.serverAgeWarningText.setTextColor(ContextCompat.getColor((context), R.color.nc_darkRed))
|
binding.serverAgeWarningText.setTextColor(ContextCompat.getColor((context), R.color.nc_darkRed))
|
||||||
binding.serverAgeWarningText.setText(R.string.nc_settings_server_eol)
|
binding.serverAgeWarningText.setText(R.string.nc_settings_server_eol)
|
||||||
binding.serverAgeWarningIcon.setColorFilter(
|
binding.serverAgeWarningIcon.setColorFilter(
|
||||||
|
@ -863,7 +868,7 @@ class SettingsActivity : BaseActivity() {
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
CapabilitiesUtilNew.isServerAlmostEOL(currentUser!!) -> {
|
CapabilitiesUtil.isServerAlmostEOL(currentUser!!.serverVersion!!.major) -> {
|
||||||
binding.serverAgeWarningText.setTextColor(
|
binding.serverAgeWarningText.setTextColor(
|
||||||
ContextCompat.getColor((context), R.color.nc_darkYellow)
|
ContextCompat.getColor((context), R.color.nc_darkYellow)
|
||||||
)
|
)
|
||||||
|
@ -889,8 +894,8 @@ class SettingsActivity : BaseActivity() {
|
||||||
binding.settingsIncognitoKeyboardSwitch.visibility = View.GONE
|
binding.settingsIncognitoKeyboardSwitch.visibility = View.GONE
|
||||||
}
|
}
|
||||||
|
|
||||||
if (CapabilitiesUtilNew.isReadStatusAvailable(currentUser!!)) {
|
if (CapabilitiesUtil.isReadStatusAvailable(currentUser!!.capabilities!!.spreedCapability!!)) {
|
||||||
binding.settingsReadPrivacySwitch.isChecked = !CapabilitiesUtilNew.isReadStatusPrivate(currentUser!!)
|
binding.settingsReadPrivacySwitch.isChecked = !CapabilitiesUtil.isReadStatusPrivate(currentUser!!)
|
||||||
} else {
|
} else {
|
||||||
binding.settingsReadPrivacy.visibility = View.GONE
|
binding.settingsReadPrivacy.visibility = View.GONE
|
||||||
}
|
}
|
||||||
|
@ -954,10 +959,10 @@ class SettingsActivity : BaseActivity() {
|
||||||
private fun setupTypingStatusSetting() {
|
private fun setupTypingStatusSetting() {
|
||||||
if (currentUser!!.externalSignalingServer?.externalSignalingServer?.isNotEmpty() == true) {
|
if (currentUser!!.externalSignalingServer?.externalSignalingServer?.isNotEmpty() == true) {
|
||||||
binding.settingsTypingStatusOnlyWithHpb.visibility = View.GONE
|
binding.settingsTypingStatusOnlyWithHpb.visibility = View.GONE
|
||||||
Log.i(TAG, "Typing Status Available: ${CapabilitiesUtilNew.isTypingStatusAvailable(currentUser!!)}")
|
Log.i(TAG, "Typing Status Available: ${CapabilitiesUtil.isTypingStatusAvailable(currentUser!!)}")
|
||||||
|
|
||||||
if (CapabilitiesUtilNew.isTypingStatusAvailable(currentUser!!)) {
|
if (CapabilitiesUtil.isTypingStatusAvailable(currentUser!!)) {
|
||||||
binding.settingsTypingStatusSwitch.isChecked = !CapabilitiesUtilNew.isTypingStatusPrivate(currentUser!!)
|
binding.settingsTypingStatusSwitch.isChecked = !CapabilitiesUtil.isTypingStatusPrivate(currentUser!!)
|
||||||
} else {
|
} else {
|
||||||
binding.settingsTypingStatus.visibility = View.GONE
|
binding.settingsTypingStatus.visibility = View.GONE
|
||||||
}
|
}
|
||||||
|
@ -1209,7 +1214,7 @@ class SettingsActivity : BaseActivity() {
|
||||||
private fun checkForPhoneNumber() {
|
private fun checkForPhoneNumber() {
|
||||||
ncApi.getUserData(
|
ncApi.getUserData(
|
||||||
ApiUtils.getCredentials(currentUser!!.username, currentUser!!.token),
|
ApiUtils.getCredentials(currentUser!!.username, currentUser!!.token),
|
||||||
ApiUtils.getUrlForUserProfile(currentUser!!.baseUrl)
|
ApiUtils.getUrlForUserProfile(currentUser!!.baseUrl!!)
|
||||||
).subscribeOn(Schedulers.io())
|
).subscribeOn(Schedulers.io())
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
.observeOn(AndroidSchedulers.mainThread())
|
||||||
.subscribe(object : Observer<UserProfileOverall> {
|
.subscribe(object : Observer<UserProfileOverall> {
|
||||||
|
@ -1294,7 +1299,7 @@ class SettingsActivity : BaseActivity() {
|
||||||
val phoneNumber = textInputLayout.editText!!.text.toString()
|
val phoneNumber = textInputLayout.editText!!.text.toString()
|
||||||
ncApi.setUserData(
|
ncApi.setUserData(
|
||||||
ApiUtils.getCredentials(currentUser!!.username, currentUser!!.token),
|
ApiUtils.getCredentials(currentUser!!.username, currentUser!!.token),
|
||||||
ApiUtils.getUrlForUserData(currentUser!!.baseUrl, currentUser!!.userId),
|
ApiUtils.getUrlForUserData(currentUser!!.baseUrl!!, currentUser!!.userId!!),
|
||||||
"phone",
|
"phone",
|
||||||
phoneNumber
|
phoneNumber
|
||||||
).subscribeOn(Schedulers.io())
|
).subscribeOn(Schedulers.io())
|
||||||
|
@ -1349,7 +1354,7 @@ class SettingsActivity : BaseActivity() {
|
||||||
val json = "{\"key\": \"read_status_privacy\", \"value\" : $booleanValue}"
|
val json = "{\"key\": \"read_status_privacy\", \"value\" : $booleanValue}"
|
||||||
ncApi.setReadStatusPrivacy(
|
ncApi.setReadStatusPrivacy(
|
||||||
ApiUtils.getCredentials(currentUser!!.username, currentUser!!.token),
|
ApiUtils.getCredentials(currentUser!!.username, currentUser!!.token),
|
||||||
ApiUtils.getUrlForUserSettings(currentUser!!.baseUrl),
|
ApiUtils.getUrlForUserSettings(currentUser!!.baseUrl!!),
|
||||||
json.toRequestBody("application/json".toMediaTypeOrNull())
|
json.toRequestBody("application/json".toMediaTypeOrNull())
|
||||||
)
|
)
|
||||||
.subscribeOn(Schedulers.io())
|
.subscribeOn(Schedulers.io())
|
||||||
|
@ -1387,7 +1392,7 @@ class SettingsActivity : BaseActivity() {
|
||||||
val json = "{\"key\": \"typing_privacy\", \"value\" : $booleanValue}"
|
val json = "{\"key\": \"typing_privacy\", \"value\" : $booleanValue}"
|
||||||
ncApi.setTypingStatusPrivacy(
|
ncApi.setTypingStatusPrivacy(
|
||||||
ApiUtils.getCredentials(currentUser!!.username, currentUser!!.token),
|
ApiUtils.getCredentials(currentUser!!.username, currentUser!!.token),
|
||||||
ApiUtils.getUrlForUserSettings(currentUser!!.baseUrl),
|
ApiUtils.getUrlForUserSettings(currentUser!!.baseUrl!!),
|
||||||
json.toRequestBody("application/json".toMediaTypeOrNull())
|
json.toRequestBody("application/json".toMediaTypeOrNull())
|
||||||
)
|
)
|
||||||
.subscribeOn(Schedulers.io())
|
.subscribeOn(Schedulers.io())
|
||||||
|
|
|
@ -105,7 +105,7 @@ class SharedItemsRepositoryImpl @Inject constructor(private val ncApi: NcApi, pr
|
||||||
fileParameters["link"]!!,
|
fileParameters["link"]!!,
|
||||||
fileParameters["mimetype"]!!,
|
fileParameters["mimetype"]!!,
|
||||||
previewAvailable,
|
previewAvailable,
|
||||||
previewLink(fileParameters["id"], parameters.baseUrl)
|
previewLink(fileParameters["id"], parameters.baseUrl!!)
|
||||||
)
|
)
|
||||||
} else if (it.value.messageParameters?.containsKey("object") == true) {
|
} else if (it.value.messageParameters?.containsKey("object") == true) {
|
||||||
val objectParameters = it.value.messageParameters!!["object"]!!
|
val objectParameters = it.value.messageParameters!!["object"]!!
|
||||||
|
@ -184,7 +184,7 @@ class SharedItemsRepositoryImpl @Inject constructor(private val ncApi: NcApi, pr
|
||||||
|
|
||||||
return ncApi.getSharedItemsOverview(
|
return ncApi.getSharedItemsOverview(
|
||||||
credentials,
|
credentials,
|
||||||
ApiUtils.getUrlForChatSharedItemsOverview(1, parameters.baseUrl, parameters.roomToken),
|
ApiUtils.getUrlForChatSharedItemsOverview(1, parameters.baseUrl!!, parameters.roomToken),
|
||||||
1
|
1
|
||||||
).map {
|
).map {
|
||||||
val types = mutableSetOf<SharedItemType>()
|
val types = mutableSetOf<SharedItemType>()
|
||||||
|
@ -206,7 +206,7 @@ class SharedItemsRepositoryImpl @Inject constructor(private val ncApi: NcApi, pr
|
||||||
private fun previewLink(fileId: String?, baseUrl: String): String {
|
private fun previewLink(fileId: String?, baseUrl: String): String {
|
||||||
return ApiUtils.getUrlForFilePreviewWithFileId(
|
return ApiUtils.getUrlForFilePreviewWithFileId(
|
||||||
baseUrl,
|
baseUrl,
|
||||||
fileId,
|
fileId!!,
|
||||||
sharedApplication!!.resources.getDimensionPixelSize(R.dimen.maximum_file_preview_size)
|
sharedApplication!!.resources.getDimensionPixelSize(R.dimen.maximum_file_preview_size)
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
|
@ -37,8 +37,8 @@ class TranslateViewModel @Inject constructor(
|
||||||
|
|
||||||
fun translateMessage(toLanguage: String, fromLanguage: String?, text: String) {
|
fun translateMessage(toLanguage: String, fromLanguage: String?, text: String) {
|
||||||
val currentUser: User = userManager.currentUser.blockingGet()
|
val currentUser: User = userManager.currentUser.blockingGet()
|
||||||
val authorization: String = ApiUtils.getCredentials(currentUser.username, currentUser.token)
|
val authorization: String = ApiUtils.getCredentials(currentUser.username, currentUser.token)!!
|
||||||
val url: String = ApiUtils.getUrlForTranslation(currentUser.baseUrl)
|
val url: String = ApiUtils.getUrlForTranslation(currentUser.baseUrl!!)
|
||||||
val calculatedFromLanguage =
|
val calculatedFromLanguage =
|
||||||
if (fromLanguage == null || fromLanguage == "") {
|
if (fromLanguage == null || fromLanguage == "") {
|
||||||
null
|
null
|
||||||
|
@ -60,8 +60,8 @@ class TranslateViewModel @Inject constructor(
|
||||||
|
|
||||||
fun getLanguages() {
|
fun getLanguages() {
|
||||||
val currentUser: User = userManager.currentUser.blockingGet()
|
val currentUser: User = userManager.currentUser.blockingGet()
|
||||||
val authorization: String = ApiUtils.getCredentials(currentUser.username, currentUser.token)
|
val authorization: String = ApiUtils.getCredentials(currentUser.username, currentUser.token)!!
|
||||||
val url: String = ApiUtils.getUrlForLanguages(currentUser.baseUrl)
|
val url: String = ApiUtils.getUrlForLanguages(currentUser.baseUrl!!)
|
||||||
Log.d(TAG, "URL is: $url")
|
Log.d(TAG, "URL is: $url")
|
||||||
repository.getLanguages(authorization, url)
|
repository.getLanguages(authorization, url)
|
||||||
.subscribeOn(Schedulers.io())
|
.subscribeOn(Schedulers.io())
|
||||||
|
|
|
@ -57,7 +57,7 @@ class ProfileBottomSheet(val ncApi: NcApi, val userModel: User, val viewThemeUti
|
||||||
fun showFor(user: String, context: Context) {
|
fun showFor(user: String, context: Context) {
|
||||||
ncApi.hoverCard(
|
ncApi.hoverCard(
|
||||||
ApiUtils.getCredentials(userModel.username, userModel.token),
|
ApiUtils.getCredentials(userModel.username, userModel.token),
|
||||||
ApiUtils.getUrlForHoverCard(userModel.baseUrl, user)
|
ApiUtils.getUrlForHoverCard(userModel.baseUrl!!, user)
|
||||||
).subscribeOn(Schedulers.io()).observeOn(AndroidSchedulers.mainThread())
|
).subscribeOn(Schedulers.io()).observeOn(AndroidSchedulers.mainThread())
|
||||||
.subscribe(object : Observer<HoverCardOverall> {
|
.subscribe(object : Observer<HoverCardOverall> {
|
||||||
override fun onSubscribe(d: Disposable) {
|
override fun onSubscribe(d: Disposable) {
|
||||||
|
@ -121,10 +121,10 @@ class ProfileBottomSheet(val ncApi: NcApi, val userModel: User, val viewThemeUti
|
||||||
|
|
||||||
private fun talkTo(userId: String, context: Context) {
|
private fun talkTo(userId: String, context: Context) {
|
||||||
val apiVersion =
|
val apiVersion =
|
||||||
ApiUtils.getConversationApiVersion(userModel, intArrayOf(ApiUtils.APIv4, 1))
|
ApiUtils.getConversationApiVersion(userModel, intArrayOf(ApiUtils.API_V4, 1))
|
||||||
val retrofitBucket = ApiUtils.getRetrofitBucketForCreateRoom(
|
val retrofitBucket = ApiUtils.getRetrofitBucketForCreateRoom(
|
||||||
apiVersion,
|
apiVersion,
|
||||||
userModel.baseUrl,
|
userModel.baseUrl!!,
|
||||||
"1",
|
"1",
|
||||||
null,
|
null,
|
||||||
userId,
|
userId,
|
||||||
|
|
|
@ -35,7 +35,8 @@ import com.nextcloud.talk.application.NextcloudTalkApplication
|
||||||
import com.nextcloud.talk.chat.ChatActivity
|
import com.nextcloud.talk.chat.ChatActivity
|
||||||
import com.nextcloud.talk.databinding.DialogAttachmentBinding
|
import com.nextcloud.talk.databinding.DialogAttachmentBinding
|
||||||
import com.nextcloud.talk.ui.theme.ViewThemeUtils
|
import com.nextcloud.talk.ui.theme.ViewThemeUtils
|
||||||
import com.nextcloud.talk.utils.database.user.CapabilitiesUtilNew
|
import com.nextcloud.talk.utils.SpreedFeatures
|
||||||
|
import com.nextcloud.talk.utils.CapabilitiesUtil
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
|
|
||||||
@AutoInjector(NextcloudTalkApplication::class)
|
@AutoInjector(NextcloudTalkApplication::class)
|
||||||
|
@ -61,7 +62,7 @@ class AttachmentDialog(val activity: Activity, var chatActivity: ChatActivity) :
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun initItemsStrings() {
|
private fun initItemsStrings() {
|
||||||
var serverName = CapabilitiesUtilNew.getServerName(chatActivity.conversationUser)
|
var serverName = CapabilitiesUtil.getServerName(chatActivity.conversationUser)
|
||||||
dialogAttachmentBinding.txtAttachFileFromCloud.text = chatActivity.resources?.let {
|
dialogAttachmentBinding.txtAttachFileFromCloud.text = chatActivity.resources?.let {
|
||||||
if (serverName.isNullOrEmpty()) {
|
if (serverName.isNullOrEmpty()) {
|
||||||
serverName = it.getString(R.string.nc_server_product_name)
|
serverName = it.getString(R.string.nc_server_product_name)
|
||||||
|
@ -71,15 +72,15 @@ class AttachmentDialog(val activity: Activity, var chatActivity: ChatActivity) :
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun initItemsVisibility() {
|
private fun initItemsVisibility() {
|
||||||
if (!CapabilitiesUtilNew.hasSpreedFeatureCapability(
|
if (!CapabilitiesUtil.hasSpreedFeatureCapability(
|
||||||
chatActivity.conversationUser,
|
chatActivity.spreedCapabilities,
|
||||||
"geo-location-sharing"
|
SpreedFeatures.GEO_LOCATION_SHARING
|
||||||
)
|
)
|
||||||
) {
|
) {
|
||||||
dialogAttachmentBinding.menuShareLocation.visibility = View.GONE
|
dialogAttachmentBinding.menuShareLocation.visibility = View.GONE
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!CapabilitiesUtilNew.hasSpreedFeatureCapability(chatActivity.conversationUser, "talk-polls") ||
|
if (!CapabilitiesUtil.hasSpreedFeatureCapability(chatActivity.spreedCapabilities, SpreedFeatures.TALK_POLLS) ||
|
||||||
chatActivity.isOneToOneConversation()
|
chatActivity.isOneToOneConversation()
|
||||||
) {
|
) {
|
||||||
dialogAttachmentBinding.menuAttachPoll.visibility = View.GONE
|
dialogAttachmentBinding.menuAttachPoll.visibility = View.GONE
|
||||||
|
|
|
@ -54,7 +54,7 @@ import com.nextcloud.talk.ui.theme.ViewThemeUtils;
|
||||||
import com.nextcloud.talk.users.UserManager;
|
import com.nextcloud.talk.users.UserManager;
|
||||||
import com.nextcloud.talk.utils.ApiUtils;
|
import com.nextcloud.talk.utils.ApiUtils;
|
||||||
import com.nextcloud.talk.utils.DisplayUtils;
|
import com.nextcloud.talk.utils.DisplayUtils;
|
||||||
import com.nextcloud.talk.utils.database.user.CapabilitiesUtilNew;
|
import com.nextcloud.talk.utils.CapabilitiesUtil;
|
||||||
|
|
||||||
import java.net.CookieManager;
|
import java.net.CookieManager;
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
|
@ -262,7 +262,7 @@ public class ChooseAccountDialogFragment extends DialogFragment {
|
||||||
private void loadCurrentStatus(User user) {
|
private void loadCurrentStatus(User user) {
|
||||||
String credentials = ApiUtils.getCredentials(user.getUsername(), user.getToken());
|
String credentials = ApiUtils.getCredentials(user.getUsername(), user.getToken());
|
||||||
|
|
||||||
if (CapabilitiesUtilNew.isUserStatusAvailable(userManager.getCurrentUser().blockingGet())) {
|
if (CapabilitiesUtil.isUserStatusAvailable(userManager.getCurrentUser().blockingGet())) {
|
||||||
binding.statusView.setVisibility(View.VISIBLE);
|
binding.statusView.setVisibility(View.VISIBLE);
|
||||||
|
|
||||||
ncApi.status(credentials, ApiUtils.getUrlForStatus(user.getBaseUrl())).
|
ncApi.status(credentials, ApiUtils.getUrlForStatus(user.getBaseUrl())).
|
||||||
|
|
|
@ -89,7 +89,7 @@ class ChooseAccountShareToDialogFragment : DialogFragment() {
|
||||||
if (user != null) {
|
if (user != null) {
|
||||||
binding!!.currentAccount.userName.text = user.displayName
|
binding!!.currentAccount.userName.text = user.displayName
|
||||||
binding!!.currentAccount.ticker.visibility = View.GONE
|
binding!!.currentAccount.ticker.visibility = View.GONE
|
||||||
binding!!.currentAccount.account.text = Uri.parse(user.baseUrl).host
|
binding!!.currentAccount.account.text = Uri.parse(user.baseUrl!!).host
|
||||||
viewThemeUtils!!.platform.colorImageView(binding!!.currentAccount.accountMenu, ColorRole.PRIMARY)
|
viewThemeUtils!!.platform.colorImageView(binding!!.currentAccount.accountMenu, ColorRole.PRIMARY)
|
||||||
if (user.baseUrl != null &&
|
if (user.baseUrl != null &&
|
||||||
(user.baseUrl!!.startsWith("http://") || user.baseUrl!!.startsWith("https://"))
|
(user.baseUrl!!.startsWith("http://") || user.baseUrl!!.startsWith("https://"))
|
||||||
|
|
|
@ -46,7 +46,7 @@ import com.nextcloud.talk.users.UserManager
|
||||||
import com.nextcloud.talk.utils.ApiUtils
|
import com.nextcloud.talk.utils.ApiUtils
|
||||||
import com.nextcloud.talk.utils.bundle.BundleKeys.KEY_INTERNAL_USER_ID
|
import com.nextcloud.talk.utils.bundle.BundleKeys.KEY_INTERNAL_USER_ID
|
||||||
import com.nextcloud.talk.utils.bundle.BundleKeys.KEY_ROOM_TOKEN
|
import com.nextcloud.talk.utils.bundle.BundleKeys.KEY_ROOM_TOKEN
|
||||||
import com.nextcloud.talk.utils.database.user.CapabilitiesUtilNew
|
import com.nextcloud.talk.utils.CapabilitiesUtil
|
||||||
import io.reactivex.Observer
|
import io.reactivex.Observer
|
||||||
import io.reactivex.android.schedulers.AndroidSchedulers
|
import io.reactivex.android.schedulers.AndroidSchedulers
|
||||||
import io.reactivex.disposables.Disposable
|
import io.reactivex.disposables.Disposable
|
||||||
|
@ -86,7 +86,7 @@ class ConversationsListBottomDialog(
|
||||||
initItemsVisibility()
|
initItemsVisibility()
|
||||||
initClickListeners()
|
initClickListeners()
|
||||||
|
|
||||||
credentials = ApiUtils.getCredentials(currentUser.username, currentUser.token)
|
credentials = ApiUtils.getCredentials(currentUser.username, currentUser.token)!!
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onStart() {
|
override fun onStart() {
|
||||||
|
@ -105,7 +105,10 @@ class ConversationsListBottomDialog(
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun initItemsVisibility() {
|
private fun initItemsVisibility() {
|
||||||
val hasFavoritesCapability = CapabilitiesUtilNew.hasSpreedFeatureCapability(currentUser, "favorites")
|
val hasFavoritesCapability = CapabilitiesUtil.hasSpreedFeatureCapability(
|
||||||
|
currentUser.capabilities?.spreedCapability!!,
|
||||||
|
"favorites"
|
||||||
|
)
|
||||||
val canModerate = conversation.canModerate(currentUser)
|
val canModerate = conversation.canModerate(currentUser)
|
||||||
|
|
||||||
binding.conversationRemoveFromFavorites.visibility = setVisibleIf(
|
binding.conversationRemoveFromFavorites.visibility = setVisibleIf(
|
||||||
|
@ -116,11 +119,19 @@ class ConversationsListBottomDialog(
|
||||||
)
|
)
|
||||||
|
|
||||||
binding.conversationMarkAsRead.visibility = setVisibleIf(
|
binding.conversationMarkAsRead.visibility = setVisibleIf(
|
||||||
conversation.unreadMessages > 0 && CapabilitiesUtilNew.canSetChatReadMarker(currentUser)
|
conversation.unreadMessages > 0 && CapabilitiesUtil.hasSpreedFeatureCapability(
|
||||||
|
currentUser
|
||||||
|
.capabilities?.spreedCapability!!,
|
||||||
|
"chat-read-marker"
|
||||||
|
)
|
||||||
)
|
)
|
||||||
|
|
||||||
binding.conversationMarkAsUnread.visibility = setVisibleIf(
|
binding.conversationMarkAsUnread.visibility = setVisibleIf(
|
||||||
conversation.unreadMessages <= 0 && CapabilitiesUtilNew.canMarkRoomAsUnread(currentUser)
|
conversation.unreadMessages <= 0 && CapabilitiesUtil.hasSpreedFeatureCapability(
|
||||||
|
currentUser
|
||||||
|
.capabilities?.spreedCapability!!,
|
||||||
|
"chat-unread"
|
||||||
|
)
|
||||||
)
|
)
|
||||||
|
|
||||||
binding.conversationOperationRename.visibility = setVisibleIf(
|
binding.conversationOperationRename.visibility = setVisibleIf(
|
||||||
|
@ -178,12 +189,12 @@ class ConversationsListBottomDialog(
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun addConversationToFavorites() {
|
private fun addConversationToFavorites() {
|
||||||
val apiVersion = ApiUtils.getConversationApiVersion(currentUser, intArrayOf(ApiUtils.APIv4, ApiUtils.APIv1))
|
val apiVersion = ApiUtils.getConversationApiVersion(currentUser, intArrayOf(ApiUtils.API_V4, ApiUtils.API_V1))
|
||||||
ncApi.addConversationToFavorites(
|
ncApi.addConversationToFavorites(
|
||||||
credentials,
|
credentials,
|
||||||
ApiUtils.getUrlForRoomFavorite(
|
ApiUtils.getUrlForRoomFavorite(
|
||||||
apiVersion,
|
apiVersion,
|
||||||
currentUser.baseUrl,
|
currentUser.baseUrl!!,
|
||||||
conversation.token
|
conversation.token
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
|
@ -218,12 +229,12 @@ class ConversationsListBottomDialog(
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun removeConversationFromFavorites() {
|
private fun removeConversationFromFavorites() {
|
||||||
val apiVersion = ApiUtils.getConversationApiVersion(currentUser, intArrayOf(ApiUtils.APIv4, ApiUtils.APIv1))
|
val apiVersion = ApiUtils.getConversationApiVersion(currentUser, intArrayOf(ApiUtils.API_V4, ApiUtils.API_V1))
|
||||||
ncApi.removeConversationFromFavorites(
|
ncApi.removeConversationFromFavorites(
|
||||||
credentials,
|
credentials,
|
||||||
ApiUtils.getUrlForRoomFavorite(
|
ApiUtils.getUrlForRoomFavorite(
|
||||||
apiVersion,
|
apiVersion,
|
||||||
currentUser.baseUrl,
|
currentUser.baseUrl!!,
|
||||||
conversation.token
|
conversation.token
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
|
@ -262,8 +273,8 @@ class ConversationsListBottomDialog(
|
||||||
credentials,
|
credentials,
|
||||||
ApiUtils.getUrlForChatReadMarker(
|
ApiUtils.getUrlForChatReadMarker(
|
||||||
chatApiVersion(),
|
chatApiVersion(),
|
||||||
currentUser.baseUrl,
|
currentUser.baseUrl!!,
|
||||||
conversation.token
|
conversation.token!!
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
.subscribeOn(Schedulers.io())
|
.subscribeOn(Schedulers.io())
|
||||||
|
@ -301,8 +312,8 @@ class ConversationsListBottomDialog(
|
||||||
credentials,
|
credentials,
|
||||||
ApiUtils.getUrlForChatReadMarker(
|
ApiUtils.getUrlForChatReadMarker(
|
||||||
chatApiVersion(),
|
chatApiVersion(),
|
||||||
currentUser.baseUrl,
|
currentUser.baseUrl!!,
|
||||||
conversation.token
|
conversation.token!!
|
||||||
),
|
),
|
||||||
conversation.lastMessage!!.jsonMessageId
|
conversation.lastMessage!!.jsonMessageId
|
||||||
)
|
)
|
||||||
|
@ -396,7 +407,7 @@ class ConversationsListBottomDialog(
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun chatApiVersion(): Int {
|
private fun chatApiVersion(): Int {
|
||||||
return ApiUtils.getChatApiVersion(currentUser, intArrayOf(ApiUtils.APIv1))
|
return ApiUtils.getChatApiVersion(currentUser.capabilities!!.spreedCapability!!, intArrayOf(ApiUtils.API_V1))
|
||||||
}
|
}
|
||||||
|
|
||||||
companion object {
|
companion object {
|
||||||
|
|
|
@ -50,7 +50,8 @@ import javax.inject.Inject
|
||||||
class DateTimePickerFragment(
|
class DateTimePickerFragment(
|
||||||
token: String,
|
token: String,
|
||||||
id: String,
|
id: String,
|
||||||
chatViewModel: ChatViewModel
|
chatViewModel: ChatViewModel,
|
||||||
|
private val chatApiVersion: Int
|
||||||
) : DialogFragment() {
|
) : DialogFragment() {
|
||||||
lateinit var binding: DialogDateTimePickerBinding
|
lateinit var binding: DialogDateTimePickerBinding
|
||||||
private var dialogView: View? = null
|
private var dialogView: View? = null
|
||||||
|
@ -144,7 +145,7 @@ class DateTimePickerFragment(
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun getReminder() {
|
private fun getReminder() {
|
||||||
viewModel.getReminder(userManager.currentUser.blockingGet(), roomToken, messageId)
|
viewModel.getReminder(userManager.currentUser.blockingGet(), roomToken, messageId, chatApiVersion)
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun showDelete(value: Boolean) {
|
private fun showDelete(value: Boolean) {
|
||||||
|
@ -221,12 +222,18 @@ class DateTimePickerFragment(
|
||||||
binding.buttonClose.setOnClickListener { dismiss() }
|
binding.buttonClose.setOnClickListener { dismiss() }
|
||||||
binding.buttonSet.setOnClickListener {
|
binding.buttonSet.setOnClickListener {
|
||||||
currentTimeStamp?.let { time ->
|
currentTimeStamp?.let { time ->
|
||||||
viewModel.setReminder(userManager.currentUser.blockingGet(), roomToken, messageId, time.toInt())
|
viewModel.setReminder(
|
||||||
|
userManager.currentUser.blockingGet(),
|
||||||
|
roomToken,
|
||||||
|
messageId,
|
||||||
|
time.toInt(),
|
||||||
|
chatApiVersion
|
||||||
|
)
|
||||||
}
|
}
|
||||||
dismiss()
|
dismiss()
|
||||||
}
|
}
|
||||||
binding.buttonDelete.setOnClickListener {
|
binding.buttonDelete.setOnClickListener {
|
||||||
viewModel.deleteReminder(userManager.currentUser.blockingGet(), roomToken, messageId)
|
viewModel.deleteReminder(userManager.currentUser.blockingGet(), roomToken, messageId, chatApiVersion)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -299,11 +306,12 @@ class DateTimePickerFragment(
|
||||||
private const val HOUR_SIX_PM = 18
|
private const val HOUR_SIX_PM = 18
|
||||||
|
|
||||||
@JvmStatic
|
@JvmStatic
|
||||||
fun newInstance(token: String, id: String, chatViewModel: ChatViewModel) =
|
fun newInstance(token: String, id: String, chatViewModel: ChatViewModel, chatApiVersion: Int) =
|
||||||
DateTimePickerFragment(
|
DateTimePickerFragment(
|
||||||
token,
|
token,
|
||||||
id,
|
id,
|
||||||
chatViewModel
|
chatViewModel,
|
||||||
|
chatApiVersion
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -46,14 +46,17 @@ import com.nextcloud.talk.models.domain.ConversationReadOnlyState
|
||||||
import com.nextcloud.talk.models.domain.ConversationType
|
import com.nextcloud.talk.models.domain.ConversationType
|
||||||
import com.nextcloud.talk.models.domain.ReactionAddedModel
|
import com.nextcloud.talk.models.domain.ReactionAddedModel
|
||||||
import com.nextcloud.talk.models.domain.ReactionDeletedModel
|
import com.nextcloud.talk.models.domain.ReactionDeletedModel
|
||||||
|
import com.nextcloud.talk.models.json.capabilities.SpreedCapability
|
||||||
import com.nextcloud.talk.models.json.chat.ChatMessage
|
import com.nextcloud.talk.models.json.chat.ChatMessage
|
||||||
import com.nextcloud.talk.repositories.reactions.ReactionsRepository
|
import com.nextcloud.talk.repositories.reactions.ReactionsRepository
|
||||||
import com.nextcloud.talk.ui.theme.ViewThemeUtils
|
import com.nextcloud.talk.ui.theme.ViewThemeUtils
|
||||||
import com.nextcloud.talk.utils.ApiUtils
|
import com.nextcloud.talk.utils.ApiUtils
|
||||||
|
import com.nextcloud.talk.utils.SpreedFeatures
|
||||||
import com.nextcloud.talk.utils.ConversationUtils
|
import com.nextcloud.talk.utils.ConversationUtils
|
||||||
import com.nextcloud.talk.utils.DateConstants
|
import com.nextcloud.talk.utils.DateConstants
|
||||||
import com.nextcloud.talk.utils.DateUtils
|
import com.nextcloud.talk.utils.DateUtils
|
||||||
import com.nextcloud.talk.utils.database.user.CapabilitiesUtilNew
|
import com.nextcloud.talk.utils.CapabilitiesUtil
|
||||||
|
import com.nextcloud.talk.utils.CapabilitiesUtil.hasSpreedFeatureCapability
|
||||||
import com.vanniktech.emoji.EmojiPopup
|
import com.vanniktech.emoji.EmojiPopup
|
||||||
import com.vanniktech.emoji.EmojiTextView
|
import com.vanniktech.emoji.EmojiTextView
|
||||||
import com.vanniktech.emoji.installDisableKeyboardInput
|
import com.vanniktech.emoji.installDisableKeyboardInput
|
||||||
|
@ -72,7 +75,8 @@ class MessageActionsDialog(
|
||||||
private val user: User?,
|
private val user: User?,
|
||||||
private val currentConversation: ConversationModel?,
|
private val currentConversation: ConversationModel?,
|
||||||
private val showMessageDeletionButton: Boolean,
|
private val showMessageDeletionButton: Boolean,
|
||||||
private val hasChatPermission: Boolean
|
private val hasChatPermission: Boolean,
|
||||||
|
private val spreedCapabilities: SpreedCapability
|
||||||
) : BottomSheetDialog(chatActivity) {
|
) : BottomSheetDialog(chatActivity) {
|
||||||
|
|
||||||
@Inject
|
@Inject
|
||||||
|
@ -100,8 +104,8 @@ class MessageActionsDialog(
|
||||||
|
|
||||||
private val isUserAllowedToEdit = chatActivity.userAllowedByPrivilages(message)
|
private val isUserAllowedToEdit = chatActivity.userAllowedByPrivilages(message)
|
||||||
|
|
||||||
private val isMessageEditable = CapabilitiesUtilNew.hasSpreedFeatureCapability(
|
private val isMessageEditable = CapabilitiesUtil.hasSpreedFeatureCapability(
|
||||||
user,
|
spreedCapabilities,
|
||||||
"edit-messages"
|
"edit-messages"
|
||||||
) && messageHasRegularText && !isOlderThanTwentyFourHours && isUserAllowedToEdit
|
) && messageHasRegularText && !isOlderThanTwentyFourHours && isUserAllowedToEdit
|
||||||
|
|
||||||
|
@ -116,9 +120,9 @@ class MessageActionsDialog(
|
||||||
viewThemeUtils.platform.themeDialog(dialogMessageActionsBinding.root)
|
viewThemeUtils.platform.themeDialog(dialogMessageActionsBinding.root)
|
||||||
initEmojiBar(hasChatPermission)
|
initEmojiBar(hasChatPermission)
|
||||||
initMenuItemCopy(!message.isDeleted)
|
initMenuItemCopy(!message.isDeleted)
|
||||||
val apiVersion = ApiUtils.getConversationApiVersion(user, intArrayOf(ApiUtils.APIv4, ApiUtils.APIv3, 1))
|
val apiVersion = ApiUtils.getConversationApiVersion(user!!, intArrayOf(ApiUtils.API_V4, ApiUtils.API_V3, 1))
|
||||||
chatActivity.chatViewModel.checkForNoteToSelf(
|
chatActivity.chatViewModel.checkForNoteToSelf(
|
||||||
ApiUtils.getCredentials(user!!.username, user.token),
|
ApiUtils.getCredentials(user!!.username, user.token)!!,
|
||||||
ApiUtils.getUrlForRooms(
|
ApiUtils.getUrlForRooms(
|
||||||
apiVersion,
|
apiVersion,
|
||||||
user.baseUrl
|
user.baseUrl
|
||||||
|
@ -144,7 +148,7 @@ class MessageActionsDialog(
|
||||||
initMenuItemTranslate(
|
initMenuItemTranslate(
|
||||||
!message.isDeleted &&
|
!message.isDeleted &&
|
||||||
ChatMessage.MessageType.REGULAR_TEXT_MESSAGE == message.getCalculateMessageType() &&
|
ChatMessage.MessageType.REGULAR_TEXT_MESSAGE == message.getCalculateMessageType() &&
|
||||||
CapabilitiesUtilNew.isTranslationsSupported(user)
|
CapabilitiesUtil.isTranslationsSupported(spreedCapabilities)
|
||||||
)
|
)
|
||||||
initMenuEditorDetails(message.lastEditTimestamp != 0L && !message.isDeleted)
|
initMenuEditorDetails(message.lastEditTimestamp != 0L && !message.isDeleted)
|
||||||
initMenuReplyToMessage(message.replyable && hasChatPermission)
|
initMenuReplyToMessage(message.replyable && hasChatPermission)
|
||||||
|
@ -160,7 +164,10 @@ class MessageActionsDialog(
|
||||||
ChatMessage.MessageType.REGULAR_TEXT_MESSAGE == message.getCalculateMessageType() &&
|
ChatMessage.MessageType.REGULAR_TEXT_MESSAGE == message.getCalculateMessageType() &&
|
||||||
!(message.isDeletedCommentMessage || message.isDeleted)
|
!(message.isDeletedCommentMessage || message.isDeleted)
|
||||||
)
|
)
|
||||||
initMenuRemindMessage(!message.isDeleted && CapabilitiesUtilNew.isRemindSupported(user))
|
initMenuRemindMessage(
|
||||||
|
!message.isDeleted && CapabilitiesUtil.hasSpreedFeatureCapability
|
||||||
|
(spreedCapabilities, "remind-me-later")
|
||||||
|
)
|
||||||
initMenuMarkAsUnread(
|
initMenuMarkAsUnread(
|
||||||
message.previousMessageId > NO_PREVIOUS_MESSAGE_ID &&
|
message.previousMessageId > NO_PREVIOUS_MESSAGE_ID &&
|
||||||
ChatMessage.MessageType.SYSTEM_MESSAGE != message.getCalculateMessageType()
|
ChatMessage.MessageType.SYSTEM_MESSAGE != message.getCalculateMessageType()
|
||||||
|
@ -242,7 +249,7 @@ class MessageActionsDialog(
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun initEmojiBar(hasChatPermission: Boolean) {
|
private fun initEmojiBar(hasChatPermission: Boolean) {
|
||||||
if (CapabilitiesUtilNew.hasSpreedFeatureCapability(user, "reactions") &&
|
if (hasSpreedFeatureCapability(spreedCapabilities, SpreedFeatures.REACTIONS) &&
|
||||||
isPermitted(hasChatPermission) &&
|
isPermitted(hasChatPermission) &&
|
||||||
isReactableMessageType(message)
|
isReactableMessageType(message)
|
||||||
) {
|
) {
|
||||||
|
|
|
@ -35,7 +35,7 @@ import com.nextcloud.talk.application.NextcloudTalkApplication
|
||||||
import com.nextcloud.talk.databinding.DialogMoreCallActionsBinding
|
import com.nextcloud.talk.databinding.DialogMoreCallActionsBinding
|
||||||
import com.nextcloud.talk.raisehand.viewmodel.RaiseHandViewModel
|
import com.nextcloud.talk.raisehand.viewmodel.RaiseHandViewModel
|
||||||
import com.nextcloud.talk.ui.theme.ViewThemeUtils
|
import com.nextcloud.talk.ui.theme.ViewThemeUtils
|
||||||
import com.nextcloud.talk.utils.database.user.CapabilitiesUtilNew
|
import com.nextcloud.talk.utils.CapabilitiesUtil
|
||||||
import com.nextcloud.talk.viewmodels.CallRecordingViewModel
|
import com.nextcloud.talk.viewmodels.CallRecordingViewModel
|
||||||
import com.vanniktech.emoji.EmojiTextView
|
import com.vanniktech.emoji.EmojiTextView
|
||||||
import javax.inject.Inject
|
import javax.inject.Inject
|
||||||
|
@ -72,7 +72,7 @@ class MoreCallActionsDialog(private val callActivity: CallActivity) : BottomShee
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun initItemsVisibility() {
|
private fun initItemsVisibility() {
|
||||||
if (CapabilitiesUtilNew.isCallReactionsSupported(callActivity.conversationUser)) {
|
if (CapabilitiesUtil.isCallReactionsSupported(callActivity.conversationUser)) {
|
||||||
binding.callEmojiBar.visibility = View.VISIBLE
|
binding.callEmojiBar.visibility = View.VISIBLE
|
||||||
} else {
|
} else {
|
||||||
binding.callEmojiBar.visibility = View.GONE
|
binding.callEmojiBar.visibility = View.GONE
|
||||||
|
@ -102,7 +102,7 @@ class MoreCallActionsDialog(private val callActivity: CallActivity) : BottomShee
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun initEmojiBar() {
|
private fun initEmojiBar() {
|
||||||
if (CapabilitiesUtilNew.isCallReactionsSupported(callActivity.conversationUser)) {
|
if (CapabilitiesUtil.isCallReactionsSupported(callActivity.conversationUser)) {
|
||||||
binding.advancedCallOptionsTitle.visibility = View.GONE
|
binding.advancedCallOptionsTitle.visibility = View.GONE
|
||||||
|
|
||||||
val capabilities = callActivity.conversationUser?.capabilities
|
val capabilities = callActivity.conversationUser?.capabilities
|
||||||
|
|
|
@ -128,8 +128,8 @@ class SetStatusDialogFragment :
|
||||||
currentUser = currentUserProvider?.currentUser?.blockingGet()
|
currentUser = currentUserProvider?.currentUser?.blockingGet()
|
||||||
currentStatus = it.getParcelable(ARG_CURRENT_STATUS_PARAM)
|
currentStatus = it.getParcelable(ARG_CURRENT_STATUS_PARAM)
|
||||||
|
|
||||||
credentials = ApiUtils.getCredentials(currentUser?.username, currentUser?.token)
|
credentials = ApiUtils.getCredentials(currentUser?.username, currentUser?.token)!!
|
||||||
ncApi.getPredefinedStatuses(credentials, ApiUtils.getUrlForPredefinedStatuses(currentUser?.baseUrl))
|
ncApi.getPredefinedStatuses(credentials, ApiUtils.getUrlForPredefinedStatuses(currentUser?.baseUrl!!))
|
||||||
.subscribeOn(Schedulers.io())
|
.subscribeOn(Schedulers.io())
|
||||||
.observeOn(AndroidSchedulers.mainThread())
|
.observeOn(AndroidSchedulers.mainThread())
|
||||||
.subscribe(object : Observer<ResponseBody> {
|
.subscribe(object : Observer<ResponseBody> {
|
||||||
|
@ -369,7 +369,7 @@ class SetStatusDialogFragment :
|
||||||
|
|
||||||
private fun clearStatus() {
|
private fun clearStatus() {
|
||||||
val credentials = ApiUtils.getCredentials(currentUser?.username, currentUser?.token)
|
val credentials = ApiUtils.getCredentials(currentUser?.username, currentUser?.token)
|
||||||
ncApi.statusDeleteMessage(credentials, ApiUtils.getUrlForStatusMessage(currentUser?.baseUrl))
|
ncApi.statusDeleteMessage(credentials, ApiUtils.getUrlForStatusMessage(currentUser?.baseUrl!!))
|
||||||
.subscribeOn(Schedulers.io())
|
.subscribeOn(Schedulers.io())
|
||||||
.observeOn(AndroidSchedulers.mainThread()).subscribe(object : Observer<GenericOverall> {
|
.observeOn(AndroidSchedulers.mainThread()).subscribe(object : Observer<GenericOverall> {
|
||||||
override fun onSubscribe(d: Disposable) {
|
override fun onSubscribe(d: Disposable) {
|
||||||
|
@ -393,7 +393,7 @@ class SetStatusDialogFragment :
|
||||||
private fun setStatus(statusType: StatusType) {
|
private fun setStatus(statusType: StatusType) {
|
||||||
visualizeStatus(statusType)
|
visualizeStatus(statusType)
|
||||||
|
|
||||||
ncApi.setStatusType(credentials, ApiUtils.getUrlForSetStatusType(currentUser?.baseUrl), statusType.string)
|
ncApi.setStatusType(credentials, ApiUtils.getUrlForSetStatusType(currentUser?.baseUrl!!), statusType.string)
|
||||||
.subscribeOn(
|
.subscribeOn(
|
||||||
Schedulers
|
Schedulers
|
||||||
.io()
|
.io()
|
||||||
|
@ -468,7 +468,7 @@ class SetStatusDialogFragment :
|
||||||
) {
|
) {
|
||||||
ncApi.setCustomStatusMessage(
|
ncApi.setCustomStatusMessage(
|
||||||
credentials,
|
credentials,
|
||||||
ApiUtils.getUrlForSetCustomStatus(currentUser?.baseUrl),
|
ApiUtils.getUrlForSetCustomStatus(currentUser?.baseUrl!!),
|
||||||
statusIcon,
|
statusIcon,
|
||||||
inputText,
|
inputText,
|
||||||
clearAt
|
clearAt
|
||||||
|
@ -499,7 +499,7 @@ class SetStatusDialogFragment :
|
||||||
|
|
||||||
ncApi.setPredefinedStatusMessage(
|
ncApi.setPredefinedStatusMessage(
|
||||||
credentials,
|
credentials,
|
||||||
ApiUtils.getUrlForSetPredefinedStatus(currentUser?.baseUrl),
|
ApiUtils.getUrlForSetPredefinedStatus(currentUser?.baseUrl!!),
|
||||||
selectedPredefinedStatus!!.id,
|
selectedPredefinedStatus!!.id,
|
||||||
if (clearAt == -1L) null else clearAt
|
if (clearAt == -1L) null else clearAt
|
||||||
)
|
)
|
||||||
|
|
|
@ -154,7 +154,7 @@ class ShowReactionsDialog(
|
||||||
ncApi.getReactions(
|
ncApi.getReactions(
|
||||||
credentials,
|
credentials,
|
||||||
ApiUtils.getUrlForMessageReaction(
|
ApiUtils.getUrlForMessageReaction(
|
||||||
user?.baseUrl,
|
user?.baseUrl!!,
|
||||||
roomToken,
|
roomToken,
|
||||||
chatMessage.id
|
chatMessage.id
|
||||||
),
|
),
|
||||||
|
@ -209,7 +209,7 @@ class ShowReactionsDialog(
|
||||||
ncApi.deleteReaction(
|
ncApi.deleteReaction(
|
||||||
credentials,
|
credentials,
|
||||||
ApiUtils.getUrlForMessageReaction(
|
ApiUtils.getUrlForMessageReaction(
|
||||||
user?.baseUrl,
|
user?.baseUrl!!,
|
||||||
roomToken,
|
roomToken,
|
||||||
message.id
|
message.id
|
||||||
),
|
),
|
||||||
|
|
|
@ -81,7 +81,7 @@ class ChunkedFileUploader(
|
||||||
|
|
||||||
init {
|
init {
|
||||||
initHttpClient(okHttpClient, currentUser)
|
initHttpClient(okHttpClient, currentUser)
|
||||||
remoteChunkUrl = ApiUtils.getUrlForChunkedUpload(currentUser.baseUrl, currentUser.userId)
|
remoteChunkUrl = ApiUtils.getUrlForChunkedUpload(currentUser.baseUrl!!, currentUser.userId!!)
|
||||||
}
|
}
|
||||||
|
|
||||||
@Suppress("Detekt.TooGenericExceptionCaught")
|
@Suppress("Detekt.TooGenericExceptionCaught")
|
||||||
|
@ -295,7 +295,7 @@ class ChunkedFileUploader(
|
||||||
ApiUtils.getCredentials(
|
ApiUtils.getCredentials(
|
||||||
currentUser.username,
|
currentUser.username,
|
||||||
currentUser.token
|
currentUser.token
|
||||||
),
|
)!!,
|
||||||
"Authorization"
|
"Authorization"
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
|
@ -304,8 +304,8 @@ class ChunkedFileUploader(
|
||||||
|
|
||||||
private fun assembleChunks(uploadFolderUri: String, targetPath: String) {
|
private fun assembleChunks(uploadFolderUri: String, targetPath: String) {
|
||||||
val destinationUri: String = ApiUtils.getUrlForFileUpload(
|
val destinationUri: String = ApiUtils.getUrlForFileUpload(
|
||||||
currentUser.baseUrl,
|
currentUser.baseUrl!!,
|
||||||
currentUser.userId,
|
currentUser.userId!!,
|
||||||
targetPath
|
targetPath
|
||||||
)
|
)
|
||||||
val originUri = "$uploadFolderUri/.file"
|
val originUri = "$uploadFolderUri/.file"
|
||||||
|
|
|
@ -24,7 +24,7 @@ class FileUploader(
|
||||||
fun upload(sourceFileUri: Uri, fileName: String, remotePath: String, metaData: String?): Observable<Boolean> {
|
fun upload(sourceFileUri: Uri, fileName: String, remotePath: String, metaData: String?): Observable<Boolean> {
|
||||||
return ncApi.uploadFile(
|
return ncApi.uploadFile(
|
||||||
ApiUtils.getCredentials(currentUser.username, currentUser.token),
|
ApiUtils.getCredentials(currentUser.username, currentUser.token),
|
||||||
ApiUtils.getUrlForFileUpload(currentUser.baseUrl, currentUser.userId, remotePath),
|
ApiUtils.getUrlForFileUpload(currentUser.baseUrl!!, currentUser.userId!!, remotePath),
|
||||||
createRequestBody(sourceFileUri)
|
createRequestBody(sourceFileUri)
|
||||||
)
|
)
|
||||||
.subscribeOn(Schedulers.io())
|
.subscribeOn(Schedulers.io())
|
||||||
|
|
|
@ -69,7 +69,7 @@ object AccountUtils {
|
||||||
private fun matchAccounts(importAccount: ImportAccount, user: User): Boolean {
|
private fun matchAccounts(importAccount: ImportAccount, user: User): Boolean {
|
||||||
var accountFound = false
|
var accountFound = false
|
||||||
if (importAccount.token != null) {
|
if (importAccount.token != null) {
|
||||||
if (UriUtils.hasHttpProtocolPrefixed(importAccount.baseUrl)) {
|
if (UriUtils.hasHttpProtocolPrefixed(importAccount.baseUrl!!)) {
|
||||||
if (
|
if (
|
||||||
user.username == importAccount.username &&
|
user.username == importAccount.username &&
|
||||||
user.baseUrl == importAccount.baseUrl
|
user.baseUrl == importAccount.baseUrl
|
||||||
|
|
|
@ -1,559 +0,0 @@
|
||||||
/*
|
|
||||||
* Nextcloud Talk application
|
|
||||||
*
|
|
||||||
* @author Mario Danic
|
|
||||||
* @author Marcel Hibbe
|
|
||||||
* @author Tim Krüger
|
|
||||||
* Copyright (C) 2021 Tim Krüger <t@timkrueger.me>
|
|
||||||
* Copyright (C) 2021-2022 Marcel Hibbe <dev@mhibbe.de>
|
|
||||||
* Copyright (C) 2017-2018 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.utils;
|
|
||||||
|
|
||||||
import android.net.Uri;
|
|
||||||
import android.text.TextUtils;
|
|
||||||
import android.util.Log;
|
|
||||||
|
|
||||||
import com.nextcloud.talk.BuildConfig;
|
|
||||||
import com.nextcloud.talk.R;
|
|
||||||
import com.nextcloud.talk.application.NextcloudTalkApplication;
|
|
||||||
import com.nextcloud.talk.data.user.model.User;
|
|
||||||
import com.nextcloud.talk.models.RetrofitBucket;
|
|
||||||
import com.nextcloud.talk.utils.database.user.CapabilitiesUtilNew;
|
|
||||||
|
|
||||||
import java.nio.charset.StandardCharsets;
|
|
||||||
import java.util.HashMap;
|
|
||||||
import java.util.Map;
|
|
||||||
|
|
||||||
import androidx.annotation.NonNull;
|
|
||||||
import androidx.annotation.Nullable;
|
|
||||||
import okhttp3.Credentials;
|
|
||||||
|
|
||||||
public class ApiUtils {
|
|
||||||
public static final int APIv1 = 1;
|
|
||||||
public static final int APIv2 = 2;
|
|
||||||
public static final int APIv3 = 3;
|
|
||||||
public static final int APIv4 = 4;
|
|
||||||
public static final int AVATAR_SIZE_BIG = 512;
|
|
||||||
public static final int AVATAR_SIZE_SMALL = 64;
|
|
||||||
private static final String TAG = "ApiUtils";
|
|
||||||
private static final String ocsApiVersion = "/ocs/v2.php";
|
|
||||||
private static final String spreedApiVersion = "/apps/spreed/api/v1";
|
|
||||||
private static final String spreedApiBase = ocsApiVersion + "/apps/spreed/api/v";
|
|
||||||
|
|
||||||
private static final String userAgent = "Mozilla/5.0 (Android) Nextcloud-Talk v";
|
|
||||||
|
|
||||||
public static String getUserAgent() {
|
|
||||||
return userAgent + BuildConfig.VERSION_NAME;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @deprecated This is only supported on API v1-3, in API v4+ please use
|
|
||||||
* {@link ApiUtils#getUrlForAttendees(int, String, String)} instead.
|
|
||||||
*/
|
|
||||||
@Deprecated
|
|
||||||
public static String getUrlForRemovingParticipantFromConversation(String baseUrl, String roomToken, boolean isGuest) {
|
|
||||||
String url = getUrlForParticipants(APIv1, baseUrl, roomToken);
|
|
||||||
|
|
||||||
if (isGuest) {
|
|
||||||
url += "/guests";
|
|
||||||
}
|
|
||||||
|
|
||||||
return url;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static RetrofitBucket getRetrofitBucketForContactsSearch(String baseUrl, @Nullable String searchQuery) {
|
|
||||||
RetrofitBucket retrofitBucket = new RetrofitBucket();
|
|
||||||
retrofitBucket.setUrl(baseUrl + ocsApiVersion + "/apps/files_sharing/api/v1/sharees");
|
|
||||||
|
|
||||||
Map<String, String> queryMap = new HashMap<>();
|
|
||||||
|
|
||||||
if (searchQuery == null) {
|
|
||||||
searchQuery = "";
|
|
||||||
}
|
|
||||||
queryMap.put("format", "json");
|
|
||||||
queryMap.put("search", searchQuery);
|
|
||||||
queryMap.put("itemType", "call");
|
|
||||||
|
|
||||||
retrofitBucket.setQueryMap(queryMap);
|
|
||||||
|
|
||||||
return retrofitBucket;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForFilePreviewWithRemotePath(String baseUrl, String remotePath, int px) {
|
|
||||||
return baseUrl + "/index.php/core/preview.png?file="
|
|
||||||
+ Uri.encode(remotePath, "UTF-8")
|
|
||||||
+ "&x=" + px + "&y=" + px + "&a=1&mode=cover&forceIcon=1";
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForFilePreviewWithFileId(String baseUrl, String fileId, int px) {
|
|
||||||
return baseUrl + "/index.php/core/preview?fileId="
|
|
||||||
+ fileId + "&x=" + px + "&y=" + px + "&a=1&mode=cover&forceIcon=1";
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getSharingUrl(String baseUrl) {
|
|
||||||
return baseUrl + ocsApiVersion + "/apps/files_sharing/api/v1/shares";
|
|
||||||
}
|
|
||||||
|
|
||||||
public static RetrofitBucket getRetrofitBucketForContactsSearchFor14(String baseUrl, @Nullable String searchQuery) {
|
|
||||||
RetrofitBucket retrofitBucket = getRetrofitBucketForContactsSearch(baseUrl, searchQuery);
|
|
||||||
retrofitBucket.setUrl(baseUrl + ocsApiVersion + "/core/autocomplete/get");
|
|
||||||
|
|
||||||
retrofitBucket.getQueryMap().put("itemId", "new");
|
|
||||||
|
|
||||||
return retrofitBucket;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForCapabilities(String baseUrl) {
|
|
||||||
return baseUrl + ocsApiVersion + "/cloud/capabilities";
|
|
||||||
}
|
|
||||||
|
|
||||||
public static int getCallApiVersion(User capabilities, int[] versions) throws NoSupportedApiException {
|
|
||||||
return getConversationApiVersion(capabilities, versions);
|
|
||||||
}
|
|
||||||
|
|
||||||
public static int getConversationApiVersion(User user, int[] versions) throws NoSupportedApiException {
|
|
||||||
boolean hasApiV4 = false;
|
|
||||||
for (int version : versions) {
|
|
||||||
hasApiV4 |= version == APIv4;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!hasApiV4) {
|
|
||||||
Exception e = new Exception("Api call did not try conversation-v4 api");
|
|
||||||
Log.d(TAG, e.getMessage(), e);
|
|
||||||
}
|
|
||||||
|
|
||||||
for (int version : versions) {
|
|
||||||
if (user.hasSpreedFeatureCapability("conversation-v" + version)) {
|
|
||||||
return version;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Fallback for old API versions
|
|
||||||
if ((version == APIv1 || version == APIv2)) {
|
|
||||||
if (user.hasSpreedFeatureCapability("conversation-v2")) {
|
|
||||||
return version;
|
|
||||||
}
|
|
||||||
if (version == APIv1 &&
|
|
||||||
user.hasSpreedFeatureCapability("mention-flag") &&
|
|
||||||
!user.hasSpreedFeatureCapability("conversation-v4")) {
|
|
||||||
return version;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
throw new NoSupportedApiException();
|
|
||||||
}
|
|
||||||
|
|
||||||
public static int getSignalingApiVersion(User user, int[] versions) throws NoSupportedApiException {
|
|
||||||
for (int version : versions) {
|
|
||||||
if (CapabilitiesUtilNew.hasSpreedFeatureCapability(user, "signaling-v" + version)) {
|
|
||||||
return version;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (version == APIv2 &&
|
|
||||||
CapabilitiesUtilNew.hasSpreedFeatureCapability(user, "sip-support") &&
|
|
||||||
!CapabilitiesUtilNew.hasSpreedFeatureCapability(user, "signaling-v3")) {
|
|
||||||
return version;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (version == APIv1 &&
|
|
||||||
!CapabilitiesUtilNew.hasSpreedFeatureCapability(user, "signaling-v3")) {
|
|
||||||
// Has no capability, we just assume it is always there when there is no v3 or later
|
|
||||||
return version;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
throw new NoSupportedApiException();
|
|
||||||
}
|
|
||||||
|
|
||||||
public static int getChatApiVersion(User user, int[] versions) throws NoSupportedApiException {
|
|
||||||
for (int version : versions) {
|
|
||||||
if (version == APIv1 && CapabilitiesUtilNew.hasSpreedFeatureCapability(user, "chat-v2")) {
|
|
||||||
// Do not question that chat-v2 capability shows the availability of api/v1/ endpoint *see no evil*
|
|
||||||
return version;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
throw new NoSupportedApiException();
|
|
||||||
}
|
|
||||||
|
|
||||||
protected static String getUrlForApi(int version, String baseUrl) {
|
|
||||||
return baseUrl + spreedApiBase + version;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForRooms(int version, String baseUrl) {
|
|
||||||
return getUrlForApi(version, baseUrl) + "/room";
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForRoom(int version, String baseUrl, String token) {
|
|
||||||
return getUrlForRooms(version, baseUrl) + "/" + token;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForAttendees(int version, String baseUrl, String token) {
|
|
||||||
return getUrlForRoom(version, baseUrl, token) + "/attendees";
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForParticipants(int version, String baseUrl, String token) {
|
|
||||||
if (token == null || token.isEmpty()) {
|
|
||||||
Log.e(TAG, "token was null or empty");
|
|
||||||
}
|
|
||||||
return getUrlForRoom(version, baseUrl, token) + "/participants";
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForParticipantsActive(int version, String baseUrl, String token) {
|
|
||||||
return getUrlForParticipants(version, baseUrl, token) + "/active";
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForParticipantsSelf(int version, String baseUrl, String token) {
|
|
||||||
return getUrlForParticipants(version, baseUrl, token) + "/self";
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForParticipantsResendInvitations(int version, String baseUrl, String token) {
|
|
||||||
return getUrlForParticipants(version, baseUrl, token) + "/resend-invitations";
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForRoomFavorite(int version, String baseUrl, String token) {
|
|
||||||
return getUrlForRoom(version, baseUrl, token) + "/favorite";
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForRoomModerators(int version, String baseUrl, String token) {
|
|
||||||
return getUrlForRoom(version, baseUrl, token) + "/moderators";
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForRoomNotificationLevel(int version, String baseUrl, String token) {
|
|
||||||
return getUrlForRoom(version, baseUrl, token) + "/notify";
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForRoomPublic(int version, String baseUrl, String token) {
|
|
||||||
return getUrlForRoom(version, baseUrl, token) + "/public";
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForRoomPassword(int version, String baseUrl, String token) {
|
|
||||||
return getUrlForRoom(version, baseUrl, token) + "/password";
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForRoomReadOnlyState(int version, String baseUrl, String token) {
|
|
||||||
return getUrlForRoom(version, baseUrl, token) + "/read-only";
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForRoomWebinaryLobby(int version, String baseUrl, String token) {
|
|
||||||
return getUrlForRoom(version, baseUrl, token) + "/webinar/lobby";
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForRoomNotificationCalls(int version, String baseUrl, String token) {
|
|
||||||
return getUrlForRoom(version, baseUrl, token) + "/notify-calls";
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForCall(int version, String baseUrl, String token) {
|
|
||||||
return getUrlForApi(version, baseUrl) + "/call/" + token;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForChat(int version, String baseUrl, String token) {
|
|
||||||
return getUrlForApi(version, baseUrl) + "/chat/" + token;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForMentionSuggestions(int version, String baseUrl, String token) {
|
|
||||||
return getUrlForChat(version, baseUrl, token) + "/mentions";
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForChatMessage(int version, String baseUrl, String token, String messageId) {
|
|
||||||
return getUrlForChat(version, baseUrl, token) + "/" + messageId;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForChatSharedItems(int version, String baseUrl, String token) {
|
|
||||||
return getUrlForChat(version, baseUrl, token) + "/share";
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForChatSharedItemsOverview(int version, String baseUrl, String token) {
|
|
||||||
return getUrlForChatSharedItems(version, baseUrl, token) + "/overview";
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForSignaling(int version, String baseUrl) {
|
|
||||||
return getUrlForApi(version, baseUrl) + "/signaling";
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForSignalingBackend(int version, String baseUrl) {
|
|
||||||
return getUrlForSignaling(version, baseUrl) + "/backend";
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForSignalingSettings(int version, String baseUrl) {
|
|
||||||
return getUrlForSignaling(version, baseUrl) + "/settings";
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForSignaling(int version, String baseUrl, String token) {
|
|
||||||
return getUrlForSignaling(version, baseUrl) + "/" + token;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForOpenConversations(int version, String baseUrl) {
|
|
||||||
return getUrlForApi(version, baseUrl) + "/listed-room";
|
|
||||||
}
|
|
||||||
|
|
||||||
public static RetrofitBucket getRetrofitBucketForCreateRoom(int version, String baseUrl, String roomType,
|
|
||||||
@Nullable String source,
|
|
||||||
@Nullable String invite,
|
|
||||||
@Nullable String conversationName) {
|
|
||||||
RetrofitBucket retrofitBucket = new RetrofitBucket();
|
|
||||||
retrofitBucket.setUrl(getUrlForRooms(version, baseUrl));
|
|
||||||
Map<String, String> queryMap = new HashMap<>();
|
|
||||||
|
|
||||||
queryMap.put("roomType", roomType);
|
|
||||||
if (invite != null) {
|
|
||||||
queryMap.put("invite", invite);
|
|
||||||
}
|
|
||||||
if (source != null) {
|
|
||||||
queryMap.put("source", source);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (conversationName != null) {
|
|
||||||
queryMap.put("roomName", conversationName);
|
|
||||||
}
|
|
||||||
|
|
||||||
retrofitBucket.setQueryMap(queryMap);
|
|
||||||
|
|
||||||
return retrofitBucket;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static RetrofitBucket getRetrofitBucketForAddParticipant(int version, String baseUrl, String token, String user) {
|
|
||||||
RetrofitBucket retrofitBucket = new RetrofitBucket();
|
|
||||||
retrofitBucket.setUrl(getUrlForParticipants(version, baseUrl, token));
|
|
||||||
|
|
||||||
Map<String, String> queryMap = new HashMap<>();
|
|
||||||
|
|
||||||
queryMap.put("newParticipant", user);
|
|
||||||
|
|
||||||
retrofitBucket.setQueryMap(queryMap);
|
|
||||||
|
|
||||||
return retrofitBucket;
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
public static RetrofitBucket getRetrofitBucketForAddParticipantWithSource(
|
|
||||||
int version,
|
|
||||||
String baseUrl,
|
|
||||||
String token,
|
|
||||||
String source,
|
|
||||||
String id
|
|
||||||
) {
|
|
||||||
RetrofitBucket retrofitBucket = getRetrofitBucketForAddParticipant(version, baseUrl, token, id);
|
|
||||||
retrofitBucket.getQueryMap().put("source", source);
|
|
||||||
return retrofitBucket;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForUserProfile(String baseUrl) {
|
|
||||||
return baseUrl + ocsApiVersion + "/cloud/user";
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForUserData(String baseUrl, String userId) {
|
|
||||||
return baseUrl + ocsApiVersion + "/cloud/users/" + userId;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForUserSettings(String baseUrl) {
|
|
||||||
// FIXME Introduce API version
|
|
||||||
return baseUrl + ocsApiVersion + spreedApiVersion + "/settings/user";
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlPostfixForStatus() {
|
|
||||||
return "/status.php";
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForAvatar(String baseUrl, String name, boolean requestBigSize) {
|
|
||||||
int avatarSize = requestBigSize ? AVATAR_SIZE_BIG : AVATAR_SIZE_SMALL;
|
|
||||||
return baseUrl + "/index.php/avatar/" + Uri.encode(name) + "/" + avatarSize;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForGuestAvatar(String baseUrl, String name, boolean requestBigSize) {
|
|
||||||
int avatarSize = requestBigSize ? AVATAR_SIZE_BIG : AVATAR_SIZE_SMALL;
|
|
||||||
return baseUrl + "/index.php/avatar/guest/" + Uri.encode(name) + "/" + avatarSize;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForConversationAvatar(int version, String baseUrl, String token) {
|
|
||||||
return getUrlForRoom(version, baseUrl, token) + "/avatar";
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForConversationAvatarWithVersion(int version, String baseUrl, String token,
|
|
||||||
boolean isDark,
|
|
||||||
String avatarVersion) {
|
|
||||||
String isDarkString = "";
|
|
||||||
if (isDark) {
|
|
||||||
isDarkString = "/dark";
|
|
||||||
}
|
|
||||||
|
|
||||||
String avatarVersionString = "";
|
|
||||||
if (avatarVersion != null) {
|
|
||||||
avatarVersionString = "?avatarVersion=" + avatarVersion;
|
|
||||||
}
|
|
||||||
|
|
||||||
return getUrlForRoom(version, baseUrl, token) + "/avatar" + isDarkString + avatarVersionString;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getCredentials(String username, String token) {
|
|
||||||
if (TextUtils.isEmpty(username) && TextUtils.isEmpty(token)) {
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
return Credentials.basic(username, token, StandardCharsets.UTF_8);
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlNextcloudPush(String baseUrl) {
|
|
||||||
return baseUrl + ocsApiVersion + "/apps/notifications/api/v2/push";
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlPushProxy() {
|
|
||||||
return NextcloudTalkApplication.Companion.getSharedApplication().
|
|
||||||
getApplicationContext().getResources().getString(R.string.nc_push_server_url) + "/devices";
|
|
||||||
}
|
|
||||||
|
|
||||||
// see https://github.com/nextcloud/notifications/blob/master/docs/ocs-endpoint-v2.md
|
|
||||||
public static String getUrlForNcNotificationWithId(String baseUrl, String notificationId) {
|
|
||||||
return baseUrl + ocsApiVersion + "/apps/notifications/api/v2/notifications/" + notificationId;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForSearchByNumber(String baseUrl) {
|
|
||||||
return baseUrl + ocsApiVersion + "/cloud/users/search/by-phone";
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForFileUpload(String baseUrl, String user, String remotePath) {
|
|
||||||
return baseUrl + "/remote.php/dav/files/" + user + remotePath;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForChunkedUpload(String baseUrl, String user) {
|
|
||||||
return baseUrl + "/remote.php/dav/uploads/" + user;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForFileDownload(String baseUrl, String user, String remotePath) {
|
|
||||||
return baseUrl + "/remote.php/dav/files/" + user + "/" + remotePath;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForTempAvatar(String baseUrl) {
|
|
||||||
return baseUrl + ocsApiVersion + "/apps/spreed/temp-user-avatar";
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForUserFields(String baseUrl) {
|
|
||||||
return baseUrl + ocsApiVersion + "/cloud/user/fields";
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlToSendLocation(int version, String baseUrl, String roomToken) {
|
|
||||||
return getUrlForChat(version, baseUrl, roomToken) + "/share";
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForHoverCard(String baseUrl, String userId) {
|
|
||||||
return baseUrl + ocsApiVersion +
|
|
||||||
"/hovercard/v1/" + userId;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForChatReadMarker(int version, String baseUrl, String roomToken) {
|
|
||||||
return getUrlForChat(version, baseUrl, roomToken) + "/read";
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
* OCS Status API
|
|
||||||
*/
|
|
||||||
|
|
||||||
public static String getUrlForStatus(String baseUrl) {
|
|
||||||
return baseUrl + ocsApiVersion + "/apps/user_status/api/v1/user_status";
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForSetStatusType(String baseUrl) {
|
|
||||||
return getUrlForStatus(baseUrl) + "/status";
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForPredefinedStatuses(String baseUrl) {
|
|
||||||
return baseUrl + ocsApiVersion + "/apps/user_status/api/v1/predefined_statuses";
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForStatusMessage(String baseUrl) {
|
|
||||||
return getUrlForStatus(baseUrl) + "/message";
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForSetCustomStatus(String baseUrl) {
|
|
||||||
return baseUrl + ocsApiVersion + "/apps/user_status/api/v1/user_status/message/custom";
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForSetPredefinedStatus(String baseUrl) {
|
|
||||||
return baseUrl + ocsApiVersion + "/apps/user_status/api/v1/user_status/message/predefined";
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForUserStatuses(String baseUrl) {
|
|
||||||
return baseUrl + ocsApiVersion + "/apps/user_status/api/v1/statuses";
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForMessageReaction(String baseUrl,
|
|
||||||
String roomToken,
|
|
||||||
String messageId) {
|
|
||||||
return baseUrl + ocsApiVersion + spreedApiVersion + "/reaction/" + roomToken + "/" + messageId;
|
|
||||||
}
|
|
||||||
|
|
||||||
@NonNull
|
|
||||||
public static String getUrlForUnifiedSearch(@NonNull String baseUrl, @NonNull String providerId) {
|
|
||||||
return baseUrl + ocsApiVersion + "/search/providers/" + providerId + "/search";
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForPoll(String baseUrl,
|
|
||||||
String roomToken,
|
|
||||||
String pollId) {
|
|
||||||
return getUrlForPoll(baseUrl, roomToken) + "/" + pollId;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForPoll(String baseUrl,
|
|
||||||
String roomToken) {
|
|
||||||
return baseUrl + ocsApiVersion + spreedApiVersion + "/poll/" + roomToken;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForMessageExpiration(int version, String baseUrl, String token) {
|
|
||||||
return getUrlForRoom(version, baseUrl, token) + "/message-expiration";
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForOpenGraph(String baseUrl) {
|
|
||||||
return baseUrl + ocsApiVersion + "/references/resolve";
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForRecording(int version, String baseUrl, String token) {
|
|
||||||
return getUrlForApi(version, baseUrl) + "/recording/" + token;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForRequestAssistance(int version, String baseUrl, String token) {
|
|
||||||
return getUrlForApi(version, baseUrl) + "/breakout-rooms/" + token + "/request-assistance";
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForConversationDescription(int version, String baseUrl, String token) {
|
|
||||||
return getUrlForRoom(version, baseUrl, token) + "/description";
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForTranslation(String baseUrl) {
|
|
||||||
return baseUrl + ocsApiVersion + "/translation/translate";
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForLanguages(String baseUrl) {
|
|
||||||
return baseUrl + ocsApiVersion + "/translation/languages";
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForReminder(User user, String roomToken, String messageId, int version) {
|
|
||||||
String url = ApiUtils.getUrlForChatMessage(version, user.getBaseUrl(), roomToken, messageId);
|
|
||||||
return url + "/reminder";
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForRecordingConsent(int version, String baseUrl, String token) {
|
|
||||||
return getUrlForRoom(version, baseUrl, token) + "/recording-consent";
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForInvitation(String baseUrl) {
|
|
||||||
return baseUrl + ocsApiVersion + spreedApiVersion + "/federation/invitation";
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForInvitationAccept(String baseUrl, int id) {
|
|
||||||
return getUrlForInvitation(baseUrl) + "/" + id;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getUrlForInvitationReject(String baseUrl, int id) {
|
|
||||||
return getUrlForInvitation(baseUrl) + "/" + id;
|
|
||||||
}
|
|
||||||
}
|
|
577
app/src/main/java/com/nextcloud/talk/utils/ApiUtils.kt
Normal file
577
app/src/main/java/com/nextcloud/talk/utils/ApiUtils.kt
Normal file
|
@ -0,0 +1,577 @@
|
||||||
|
/*
|
||||||
|
* Nextcloud Talk application
|
||||||
|
*
|
||||||
|
* @author Mario Danic
|
||||||
|
* @author Marcel Hibbe
|
||||||
|
* @author Tim Krüger
|
||||||
|
* Copyright (C) 2021 Tim Krüger <t@timkrueger.me>
|
||||||
|
* Copyright (C) 2021-2022 Marcel Hibbe <dev@mhibbe.de>
|
||||||
|
* Copyright (C) 2017-2018 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.utils
|
||||||
|
|
||||||
|
import android.net.Uri
|
||||||
|
import android.text.TextUtils
|
||||||
|
import android.util.Log
|
||||||
|
import com.nextcloud.talk.BuildConfig
|
||||||
|
import com.nextcloud.talk.R
|
||||||
|
import com.nextcloud.talk.application.NextcloudTalkApplication.Companion.sharedApplication
|
||||||
|
import com.nextcloud.talk.data.user.model.User
|
||||||
|
import com.nextcloud.talk.models.RetrofitBucket
|
||||||
|
import com.nextcloud.talk.models.json.capabilities.SpreedCapability
|
||||||
|
import com.nextcloud.talk.utils.CapabilitiesUtil.hasSpreedFeatureCapability
|
||||||
|
import okhttp3.Credentials.basic
|
||||||
|
import java.nio.charset.StandardCharsets
|
||||||
|
|
||||||
|
@Suppress("TooManyFunctions")
|
||||||
|
object ApiUtils {
|
||||||
|
private val TAG = ApiUtils::class.java.simpleName
|
||||||
|
const val API_V1 = 1
|
||||||
|
private const val API_V2 = 2
|
||||||
|
const val API_V3 = 3
|
||||||
|
const val API_V4 = 4
|
||||||
|
private const val AVATAR_SIZE_BIG = 512
|
||||||
|
private const val AVATAR_SIZE_SMALL = 64
|
||||||
|
private const val OCS_API_VERSION = "/ocs/v2.php"
|
||||||
|
private const val SPREED_API_VERSION = "/apps/spreed/api/v1"
|
||||||
|
private const val SPREED_API_BASE = "$OCS_API_VERSION/apps/spreed/api/v"
|
||||||
|
|
||||||
|
@JvmStatic
|
||||||
|
val userAgent = "Mozilla/5.0 (Android) Nextcloud-Talk v"
|
||||||
|
get() = field + BuildConfig.VERSION_NAME
|
||||||
|
|
||||||
|
@Deprecated(
|
||||||
|
"This is only supported on API v1-3, in API v4+ please use " +
|
||||||
|
"{@link ApiUtils#getUrlForAttendees(int, String, String)} instead."
|
||||||
|
)
|
||||||
|
fun getUrlForRemovingParticipantFromConversation(baseUrl: String?, roomToken: String?, isGuest: Boolean): String {
|
||||||
|
var url = getUrlForParticipants(API_V1, baseUrl, roomToken)
|
||||||
|
if (isGuest) {
|
||||||
|
url += "/guests"
|
||||||
|
}
|
||||||
|
return url
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun getRetrofitBucketForContactsSearch(baseUrl: String, searchQuery: String?): RetrofitBucket {
|
||||||
|
var query = searchQuery
|
||||||
|
val retrofitBucket = RetrofitBucket()
|
||||||
|
retrofitBucket.url = "$baseUrl$OCS_API_VERSION/apps/files_sharing/api/v1/sharees"
|
||||||
|
val queryMap: MutableMap<String, String> = HashMap()
|
||||||
|
if (query == null) {
|
||||||
|
query = ""
|
||||||
|
}
|
||||||
|
queryMap["format"] = "json"
|
||||||
|
queryMap["search"] = query
|
||||||
|
queryMap["itemType"] = "call"
|
||||||
|
retrofitBucket.queryMap = queryMap
|
||||||
|
return retrofitBucket
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForFilePreviewWithRemotePath(baseUrl: String, remotePath: String?, px: Int): String {
|
||||||
|
return (
|
||||||
|
baseUrl + "/index.php/core/preview.png?file=" +
|
||||||
|
Uri.encode(remotePath, "UTF-8") +
|
||||||
|
"&x=" + px + "&y=" + px + "&a=1&mode=cover&forceIcon=1"
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForFilePreviewWithFileId(baseUrl: String, fileId: String, px: Int): String {
|
||||||
|
return (
|
||||||
|
baseUrl + "/index.php/core/preview?fileId=" +
|
||||||
|
fileId + "&x=" + px + "&y=" + px + "&a=1&mode=cover&forceIcon=1"
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getSharingUrl(baseUrl: String): String {
|
||||||
|
return "$baseUrl$OCS_API_VERSION/apps/files_sharing/api/v1/shares"
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getRetrofitBucketForContactsSearchFor14(baseUrl: String, searchQuery: String?): RetrofitBucket {
|
||||||
|
val retrofitBucket = getRetrofitBucketForContactsSearch(baseUrl, searchQuery)
|
||||||
|
retrofitBucket.url = "$baseUrl$OCS_API_VERSION/core/autocomplete/get"
|
||||||
|
retrofitBucket.queryMap?.put("itemId", "new")
|
||||||
|
return retrofitBucket
|
||||||
|
}
|
||||||
|
|
||||||
|
@JvmStatic
|
||||||
|
fun getUrlForCapabilities(baseUrl: String): String {
|
||||||
|
return "$baseUrl$OCS_API_VERSION/cloud/capabilities"
|
||||||
|
}
|
||||||
|
|
||||||
|
@Throws(NoSupportedApiException::class)
|
||||||
|
fun getCallApiVersion(capabilities: User, versions: IntArray): Int {
|
||||||
|
return getConversationApiVersion(capabilities, versions)
|
||||||
|
}
|
||||||
|
|
||||||
|
@JvmStatic
|
||||||
|
@Throws(NoSupportedApiException::class)
|
||||||
|
@Suppress("ReturnCount")
|
||||||
|
fun getConversationApiVersion(user: User, versions: IntArray): Int {
|
||||||
|
var hasApiV4 = false
|
||||||
|
for (version in versions) {
|
||||||
|
hasApiV4 = hasApiV4 or (version == API_V4)
|
||||||
|
}
|
||||||
|
if (!hasApiV4) {
|
||||||
|
val e = Exception("Api call did not try conversation-v4 api")
|
||||||
|
Log.d(TAG, e.message, e)
|
||||||
|
}
|
||||||
|
for (version in versions) {
|
||||||
|
if (user.hasSpreedFeatureCapability("conversation-v$version")) {
|
||||||
|
return version
|
||||||
|
}
|
||||||
|
|
||||||
|
// Fallback for old API versions
|
||||||
|
if (version == API_V1 || version == API_V2) {
|
||||||
|
if (user.hasSpreedFeatureCapability("conversation-v2")) {
|
||||||
|
return version
|
||||||
|
}
|
||||||
|
if (version == API_V1 &&
|
||||||
|
user.hasSpreedFeatureCapability("mention-flag") &&
|
||||||
|
!user.hasSpreedFeatureCapability("conversation-v4")
|
||||||
|
) {
|
||||||
|
return version
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
throw NoSupportedApiException()
|
||||||
|
}
|
||||||
|
|
||||||
|
@JvmStatic
|
||||||
|
@Throws(NoSupportedApiException::class)
|
||||||
|
@Suppress("ReturnCount")
|
||||||
|
fun getSignalingApiVersion(user: User, versions: IntArray): Int {
|
||||||
|
val spreedCapabilities = user.capabilities!!.spreedCapability
|
||||||
|
for (version in versions) {
|
||||||
|
if (spreedCapabilities != null) {
|
||||||
|
if (hasSpreedFeatureCapability(spreedCapabilities, "signaling-v$version")) {
|
||||||
|
return version
|
||||||
|
}
|
||||||
|
if (version == API_V2 &&
|
||||||
|
hasSpreedFeatureCapability(spreedCapabilities, "sip-support") &&
|
||||||
|
!hasSpreedFeatureCapability(spreedCapabilities, "signaling-v3")
|
||||||
|
) {
|
||||||
|
return version
|
||||||
|
}
|
||||||
|
if (version == API_V1 &&
|
||||||
|
!hasSpreedFeatureCapability(spreedCapabilities, "signaling-v3")
|
||||||
|
) {
|
||||||
|
// Has no capability, we just assume it is always there when there is no v3 or later
|
||||||
|
return version
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
throw NoSupportedApiException()
|
||||||
|
}
|
||||||
|
|
||||||
|
@JvmStatic
|
||||||
|
@Throws(NoSupportedApiException::class)
|
||||||
|
fun getChatApiVersion(spreedCapabilities: SpreedCapability, versions: IntArray): Int {
|
||||||
|
for (version in versions) {
|
||||||
|
if (version == API_V1 && hasSpreedFeatureCapability(spreedCapabilities, "chat-v2")) {
|
||||||
|
// Do not question that chat-v2 capability shows the availability of api/v1/ endpoint *see no evil*
|
||||||
|
return version
|
||||||
|
}
|
||||||
|
}
|
||||||
|
throw NoSupportedApiException()
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun getUrlForApi(version: Int, baseUrl: String?): String {
|
||||||
|
return baseUrl + SPREED_API_BASE + version
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForRooms(version: Int, baseUrl: String?): String {
|
||||||
|
return getUrlForApi(version, baseUrl) + "/room"
|
||||||
|
}
|
||||||
|
|
||||||
|
@JvmStatic
|
||||||
|
fun getUrlForRoom(version: Int, baseUrl: String?, token: String?): String {
|
||||||
|
return getUrlForRooms(version, baseUrl) + "/" + token
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForAttendees(version: Int, baseUrl: String?, token: String?): String {
|
||||||
|
return getUrlForRoom(version, baseUrl, token) + "/attendees"
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForParticipants(version: Int, baseUrl: String?, token: String?): String {
|
||||||
|
if (token.isNullOrEmpty()) {
|
||||||
|
Log.e(TAG, "token was null or empty")
|
||||||
|
}
|
||||||
|
return getUrlForRoom(version, baseUrl, token) + "/participants"
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForParticipantsActive(version: Int, baseUrl: String?, token: String?): String {
|
||||||
|
return getUrlForParticipants(version, baseUrl, token) + "/active"
|
||||||
|
}
|
||||||
|
|
||||||
|
@JvmStatic
|
||||||
|
fun getUrlForParticipantsSelf(version: Int, baseUrl: String?, token: String?): String {
|
||||||
|
return getUrlForParticipants(version, baseUrl, token) + "/self"
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForParticipantsResendInvitations(version: Int, baseUrl: String?, token: String?): String {
|
||||||
|
return getUrlForParticipants(version, baseUrl, token) + "/resend-invitations"
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForRoomFavorite(version: Int, baseUrl: String?, token: String?): String {
|
||||||
|
return getUrlForRoom(version, baseUrl, token) + "/favorite"
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForRoomModerators(version: Int, baseUrl: String?, token: String?): String {
|
||||||
|
return getUrlForRoom(version, baseUrl, token) + "/moderators"
|
||||||
|
}
|
||||||
|
|
||||||
|
@JvmStatic
|
||||||
|
fun getUrlForRoomNotificationLevel(version: Int, baseUrl: String?, token: String?): String {
|
||||||
|
return getUrlForRoom(version, baseUrl, token) + "/notify"
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForRoomPublic(version: Int, baseUrl: String?, token: String?): String {
|
||||||
|
return getUrlForRoom(version, baseUrl, token) + "/public"
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForRoomPassword(version: Int, baseUrl: String?, token: String?): String {
|
||||||
|
return getUrlForRoom(version, baseUrl, token) + "/password"
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForRoomReadOnlyState(version: Int, baseUrl: String?, token: String?): String {
|
||||||
|
return getUrlForRoom(version, baseUrl, token) + "/read-only"
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForRoomWebinaryLobby(version: Int, baseUrl: String?, token: String?): String {
|
||||||
|
return getUrlForRoom(version, baseUrl, token) + "/webinar/lobby"
|
||||||
|
}
|
||||||
|
|
||||||
|
@JvmStatic
|
||||||
|
fun getUrlForRoomNotificationCalls(version: Int, baseUrl: String?, token: String?): String {
|
||||||
|
return getUrlForRoom(version, baseUrl, token) + "/notify-calls"
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForCall(version: Int, baseUrl: String?, token: String): String {
|
||||||
|
return getUrlForApi(version, baseUrl) + "/call/" + token
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForChat(version: Int, baseUrl: String?, token: String): String {
|
||||||
|
return getUrlForApi(version, baseUrl) + "/chat/" + token
|
||||||
|
}
|
||||||
|
|
||||||
|
@JvmStatic
|
||||||
|
fun getUrlForMentionSuggestions(version: Int, baseUrl: String?, token: String): String {
|
||||||
|
return getUrlForChat(version, baseUrl, token) + "/mentions"
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForChatMessage(version: Int, baseUrl: String?, token: String, messageId: String): String {
|
||||||
|
return getUrlForChat(version, baseUrl, token) + "/" + messageId
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForChatSharedItems(version: Int, baseUrl: String?, token: String): String {
|
||||||
|
return getUrlForChat(version, baseUrl, token) + "/share"
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForChatSharedItemsOverview(version: Int, baseUrl: String?, token: String): String {
|
||||||
|
return getUrlForChatSharedItems(version, baseUrl, token) + "/overview"
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForSignaling(version: Int, baseUrl: String?): String {
|
||||||
|
return getUrlForApi(version, baseUrl) + "/signaling"
|
||||||
|
}
|
||||||
|
|
||||||
|
@JvmStatic
|
||||||
|
fun getUrlForSignalingBackend(version: Int, baseUrl: String?): String {
|
||||||
|
return getUrlForSignaling(version, baseUrl) + "/backend"
|
||||||
|
}
|
||||||
|
|
||||||
|
@JvmStatic
|
||||||
|
fun getUrlForSignalingSettings(version: Int, baseUrl: String?): String {
|
||||||
|
return getUrlForSignaling(version, baseUrl) + "/settings"
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForSignaling(version: Int, baseUrl: String?, token: String): String {
|
||||||
|
return getUrlForSignaling(version, baseUrl) + "/" + token
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForOpenConversations(version: Int, baseUrl: String?): String {
|
||||||
|
return getUrlForApi(version, baseUrl) + "/listed-room"
|
||||||
|
}
|
||||||
|
|
||||||
|
@Suppress("LongParameterList")
|
||||||
|
fun getRetrofitBucketForCreateRoom(
|
||||||
|
version: Int,
|
||||||
|
baseUrl: String?,
|
||||||
|
roomType: String,
|
||||||
|
source: String?,
|
||||||
|
invite: String?,
|
||||||
|
conversationName: String?
|
||||||
|
): RetrofitBucket {
|
||||||
|
val retrofitBucket = RetrofitBucket()
|
||||||
|
retrofitBucket.url = getUrlForRooms(version, baseUrl)
|
||||||
|
val queryMap: MutableMap<String, String> = HashMap()
|
||||||
|
queryMap["roomType"] = roomType
|
||||||
|
if (invite != null) {
|
||||||
|
queryMap["invite"] = invite
|
||||||
|
}
|
||||||
|
if (source != null) {
|
||||||
|
queryMap["source"] = source
|
||||||
|
}
|
||||||
|
if (conversationName != null) {
|
||||||
|
queryMap["roomName"] = conversationName
|
||||||
|
}
|
||||||
|
retrofitBucket.queryMap = queryMap
|
||||||
|
return retrofitBucket
|
||||||
|
}
|
||||||
|
|
||||||
|
@JvmStatic
|
||||||
|
fun getRetrofitBucketForAddParticipant(
|
||||||
|
version: Int,
|
||||||
|
baseUrl: String?,
|
||||||
|
token: String?,
|
||||||
|
user: String
|
||||||
|
): RetrofitBucket {
|
||||||
|
val retrofitBucket = RetrofitBucket()
|
||||||
|
retrofitBucket.url = getUrlForParticipants(version, baseUrl, token)
|
||||||
|
val queryMap: MutableMap<String, String> = HashMap()
|
||||||
|
queryMap["newParticipant"] = user
|
||||||
|
retrofitBucket.queryMap = queryMap
|
||||||
|
return retrofitBucket
|
||||||
|
}
|
||||||
|
|
||||||
|
@JvmStatic
|
||||||
|
fun getRetrofitBucketForAddParticipantWithSource(
|
||||||
|
version: Int,
|
||||||
|
baseUrl: String?,
|
||||||
|
token: String?,
|
||||||
|
source: String,
|
||||||
|
id: String
|
||||||
|
): RetrofitBucket {
|
||||||
|
val retrofitBucket = getRetrofitBucketForAddParticipant(version, baseUrl, token, id)
|
||||||
|
retrofitBucket.queryMap?.put("source", source)
|
||||||
|
return retrofitBucket
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForUserProfile(baseUrl: String): String {
|
||||||
|
return "$baseUrl$OCS_API_VERSION/cloud/user"
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForUserData(baseUrl: String, userId: String): String {
|
||||||
|
return "$baseUrl$OCS_API_VERSION/cloud/users/$userId"
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForUserSettings(baseUrl: String): String {
|
||||||
|
// FIXME Introduce API version
|
||||||
|
return "$baseUrl$OCS_API_VERSION$SPREED_API_VERSION/settings/user"
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlPostfixForStatus(): String {
|
||||||
|
return "/status.php"
|
||||||
|
}
|
||||||
|
|
||||||
|
@JvmStatic
|
||||||
|
fun getUrlForAvatar(baseUrl: String?, name: String?, requestBigSize: Boolean): String {
|
||||||
|
val avatarSize = if (requestBigSize) AVATAR_SIZE_BIG else AVATAR_SIZE_SMALL
|
||||||
|
return baseUrl + "/index.php/avatar/" + Uri.encode(name) + "/" + avatarSize
|
||||||
|
}
|
||||||
|
|
||||||
|
@JvmStatic
|
||||||
|
fun getUrlForGuestAvatar(baseUrl: String?, name: String?, requestBigSize: Boolean): String {
|
||||||
|
val avatarSize = if (requestBigSize) AVATAR_SIZE_BIG else AVATAR_SIZE_SMALL
|
||||||
|
return baseUrl + "/index.php/avatar/guest/" + Uri.encode(name) + "/" + avatarSize
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForConversationAvatar(version: Int, baseUrl: String?, token: String?): String {
|
||||||
|
return getUrlForRoom(version, baseUrl, token) + "/avatar"
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForConversationAvatarWithVersion(
|
||||||
|
version: Int,
|
||||||
|
baseUrl: String?,
|
||||||
|
token: String?,
|
||||||
|
isDark: Boolean,
|
||||||
|
avatarVersion: String?
|
||||||
|
): String {
|
||||||
|
var isDarkString = ""
|
||||||
|
if (isDark) {
|
||||||
|
isDarkString = "/dark"
|
||||||
|
}
|
||||||
|
var avatarVersionString = ""
|
||||||
|
if (avatarVersion != null) {
|
||||||
|
avatarVersionString = "?avatarVersion=$avatarVersion"
|
||||||
|
}
|
||||||
|
return getUrlForRoom(version, baseUrl, token) + "/avatar" + isDarkString + avatarVersionString
|
||||||
|
}
|
||||||
|
|
||||||
|
@JvmStatic
|
||||||
|
fun getCredentials(username: String?, token: String?): String? {
|
||||||
|
return if (TextUtils.isEmpty(username) && TextUtils.isEmpty(token)) {
|
||||||
|
null
|
||||||
|
} else {
|
||||||
|
basic(username!!, token!!, StandardCharsets.UTF_8)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@JvmStatic
|
||||||
|
fun getUrlNextcloudPush(baseUrl: String): String {
|
||||||
|
return "$baseUrl$OCS_API_VERSION/apps/notifications/api/v2/push"
|
||||||
|
}
|
||||||
|
|
||||||
|
@JvmStatic
|
||||||
|
fun getUrlPushProxy(): String {
|
||||||
|
return sharedApplication!!.applicationContext.resources.getString(R.string.nc_push_server_url) + "/devices"
|
||||||
|
}
|
||||||
|
|
||||||
|
// see https://github.com/nextcloud/notifications/blob/master/docs/ocs-endpoint-v2.md
|
||||||
|
fun getUrlForNcNotificationWithId(baseUrl: String, notificationId: String): String {
|
||||||
|
return "$baseUrl$OCS_API_VERSION/apps/notifications/api/v2/notifications/$notificationId"
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForSearchByNumber(baseUrl: String): String {
|
||||||
|
return "$baseUrl$OCS_API_VERSION/cloud/users/search/by-phone"
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForFileUpload(baseUrl: String, user: String, remotePath: String): String {
|
||||||
|
return "$baseUrl/remote.php/dav/files/$user$remotePath"
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForChunkedUpload(baseUrl: String, user: String): String {
|
||||||
|
return "$baseUrl/remote.php/dav/uploads/$user"
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForFileDownload(baseUrl: String, user: String, remotePath: String): String {
|
||||||
|
return "$baseUrl/remote.php/dav/files/$user/$remotePath"
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForTempAvatar(baseUrl: String): String {
|
||||||
|
return "$baseUrl$OCS_API_VERSION/apps/spreed/temp-user-avatar"
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForUserFields(baseUrl: String): String {
|
||||||
|
return "$baseUrl$OCS_API_VERSION/cloud/user/fields"
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlToSendLocation(version: Int, baseUrl: String?, roomToken: String): String {
|
||||||
|
return getUrlForChat(version, baseUrl, roomToken) + "/share"
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForHoverCard(baseUrl: String, userId: String): String {
|
||||||
|
return baseUrl + OCS_API_VERSION +
|
||||||
|
"/hovercard/v1/" + userId
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForChatReadMarker(version: Int, baseUrl: String?, roomToken: String): String {
|
||||||
|
return getUrlForChat(version, baseUrl, roomToken) + "/read"
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* OCS Status API
|
||||||
|
*/
|
||||||
|
@JvmStatic
|
||||||
|
fun getUrlForStatus(baseUrl: String): String {
|
||||||
|
return "$baseUrl$OCS_API_VERSION/apps/user_status/api/v1/user_status"
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForSetStatusType(baseUrl: String): String {
|
||||||
|
return getUrlForStatus(baseUrl) + "/status"
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForPredefinedStatuses(baseUrl: String): String {
|
||||||
|
return "$baseUrl$OCS_API_VERSION/apps/user_status/api/v1/predefined_statuses"
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForStatusMessage(baseUrl: String): String {
|
||||||
|
return getUrlForStatus(baseUrl) + "/message"
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForSetCustomStatus(baseUrl: String): String {
|
||||||
|
return "$baseUrl$OCS_API_VERSION/apps/user_status/api/v1/user_status/message/custom"
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForSetPredefinedStatus(baseUrl: String): String {
|
||||||
|
return "$baseUrl$OCS_API_VERSION/apps/user_status/api/v1/user_status/message/predefined"
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForUserStatuses(baseUrl: String): String {
|
||||||
|
return "$baseUrl$OCS_API_VERSION/apps/user_status/api/v1/statuses"
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForMessageReaction(baseUrl: String, roomToken: String, messageId: String): String {
|
||||||
|
return "$baseUrl$OCS_API_VERSION$SPREED_API_VERSION/reaction/$roomToken/$messageId"
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForUnifiedSearch(baseUrl: String, providerId: String): String {
|
||||||
|
return "$baseUrl$OCS_API_VERSION/search/providers/$providerId/search"
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForPoll(baseUrl: String, roomToken: String, pollId: String): String {
|
||||||
|
return getUrlForPoll(baseUrl, roomToken) + "/" + pollId
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForPoll(baseUrl: String, roomToken: String): String {
|
||||||
|
return "$baseUrl$OCS_API_VERSION$SPREED_API_VERSION/poll/$roomToken"
|
||||||
|
}
|
||||||
|
|
||||||
|
@JvmStatic
|
||||||
|
fun getUrlForMessageExpiration(version: Int, baseUrl: String?, token: String?): String {
|
||||||
|
return getUrlForRoom(version, baseUrl, token) + "/message-expiration"
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForOpenGraph(baseUrl: String): String {
|
||||||
|
return "$baseUrl$OCS_API_VERSION/references/resolve"
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForRecording(version: Int, baseUrl: String?, token: String): String {
|
||||||
|
return getUrlForApi(version, baseUrl) + "/recording/" + token
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForRequestAssistance(version: Int, baseUrl: String?, token: String): String {
|
||||||
|
return getUrlForApi(version, baseUrl) + "/breakout-rooms/" + token + "/request-assistance"
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForConversationDescription(version: Int, baseUrl: String?, token: String?): String {
|
||||||
|
return getUrlForRoom(version, baseUrl, token) + "/description"
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForTranslation(baseUrl: String): String {
|
||||||
|
return "$baseUrl$OCS_API_VERSION/translation/translate"
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForLanguages(baseUrl: String): String {
|
||||||
|
return "$baseUrl$OCS_API_VERSION/translation/languages"
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForReminder(user: User, roomToken: String, messageId: String, version: Int): String {
|
||||||
|
val url = getUrlForChatMessage(version, user.baseUrl!!, roomToken, messageId)
|
||||||
|
return "$url/reminder"
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForRecordingConsent(version: Int, baseUrl: String?, token: String?): String {
|
||||||
|
return getUrlForRoom(version, baseUrl, token) + "/recording-consent"
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForInvitation(baseUrl: String): String {
|
||||||
|
return baseUrl + OCS_API_VERSION + SPREED_API_VERSION + "/federation/invitation"
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForInvitationAccept(baseUrl: String, id: Int): String {
|
||||||
|
return getUrlForInvitation(baseUrl) + "/" + id
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getUrlForInvitationReject(baseUrl: String, id: Int): String {
|
||||||
|
return getUrlForInvitation(baseUrl) + "/" + id
|
||||||
|
}
|
||||||
|
|
||||||
|
@JvmStatic
|
||||||
|
fun getUrlForRoomCapabilities(version: Int, baseUrl: String?, token: String?): String {
|
||||||
|
return getUrlForRooms(version, baseUrl) + "/" + token + "/capabilities"
|
||||||
|
}
|
||||||
|
}
|
275
app/src/main/java/com/nextcloud/talk/utils/CapabilitiesUtil.kt
Normal file
275
app/src/main/java/com/nextcloud/talk/utils/CapabilitiesUtil.kt
Normal file
|
@ -0,0 +1,275 @@
|
||||||
|
/*
|
||||||
|
* Nextcloud Talk application
|
||||||
|
*
|
||||||
|
* @author Andy Scherzinger
|
||||||
|
* @author Mario Danic
|
||||||
|
* @author Marcel Hibbe
|
||||||
|
* Copyright (C) 2023-2024 Marcel Hibbe <dev@mhibbe.de>
|
||||||
|
* Copyright (C) 2021 Andy Scherzinger (info@andy-scherzinger.de)
|
||||||
|
* Copyright (C) 2017-2018 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.utils
|
||||||
|
|
||||||
|
import com.nextcloud.talk.data.user.model.User
|
||||||
|
import com.nextcloud.talk.models.json.capabilities.SpreedCapability
|
||||||
|
|
||||||
|
enum class SpreedFeatures(val value: String) {
|
||||||
|
RECORDING_V1("recording-v1"),
|
||||||
|
REACTIONS("reactions"),
|
||||||
|
RAISE_HAND("raise-hand"),
|
||||||
|
DIRECT_MENTION_FLAG("direct-mention-flag"),
|
||||||
|
CONVERSATION_CALL_FLAGS("conversation-call-flags"),
|
||||||
|
SILENT_SEND("silent-send"),
|
||||||
|
MENTION_FLAG("mention-flag"),
|
||||||
|
DELETE_MESSAGES("delete-messages"),
|
||||||
|
READ_ONLY_ROOMS("read-only-rooms"),
|
||||||
|
RICH_OBJECT_LIST_MEDIA("rich-object-list-media"),
|
||||||
|
SILENT_CALL("silent-call"),
|
||||||
|
MESSAGE_EXPIRATION("message-expiration"),
|
||||||
|
WEBINARY_LOBBY("webinary-lobby"),
|
||||||
|
VOICE_MESSAGE_SHARING("voice-message-sharing"),
|
||||||
|
INVITE_GROUPS_AND_MAILS("invite-groups-and-mails"),
|
||||||
|
CIRCLES_SUPPORT("circles-support"),
|
||||||
|
LAST_ROOM_ACTIVITY("last-room-activity"),
|
||||||
|
NOTIFICATION_LEVELS("notification-levels"),
|
||||||
|
CLEAR_HISTORY("clear-history"),
|
||||||
|
AVATAR("avatar"),
|
||||||
|
LISTABLE_ROOMS("listable-rooms"),
|
||||||
|
LOCKED_ONE_TO_ONE_ROOMS("locked-one-to-one-rooms"),
|
||||||
|
TEMP_USER_AVATAR_API("temp-user-avatar-api"),
|
||||||
|
PHONEBOOK_SEARCH("phonebook-search"),
|
||||||
|
GEO_LOCATION_SHARING("geo-location-sharing"),
|
||||||
|
TALK_POLLS("talk-polls")
|
||||||
|
}
|
||||||
|
|
||||||
|
@Suppress("TooManyFunctions")
|
||||||
|
object CapabilitiesUtil {
|
||||||
|
|
||||||
|
//region Version checks
|
||||||
|
fun isServerEOL(serverVersion: Int): Boolean {
|
||||||
|
return (serverVersion < SERVER_VERSION_MIN_SUPPORTED)
|
||||||
|
}
|
||||||
|
|
||||||
|
fun isServerAlmostEOL(serverVersion: Int): Boolean {
|
||||||
|
return (serverVersion < SERVER_VERSION_SUPPORT_WARNING)
|
||||||
|
}
|
||||||
|
|
||||||
|
// endregion
|
||||||
|
|
||||||
|
//region CoreCapabilities
|
||||||
|
|
||||||
|
@JvmStatic
|
||||||
|
fun isLinkPreviewAvailable(user: User): Boolean {
|
||||||
|
return user.capabilities?.coreCapability?.referenceApi != null &&
|
||||||
|
user.capabilities?.coreCapability?.referenceApi == "true"
|
||||||
|
}
|
||||||
|
|
||||||
|
// endregion
|
||||||
|
|
||||||
|
//region SpreedCapabilities
|
||||||
|
|
||||||
|
@JvmStatic
|
||||||
|
fun hasSpreedFeatureCapability(spreedCapabilities: SpreedCapability, spreedFeatures: SpreedFeatures): Boolean {
|
||||||
|
if (spreedCapabilities.features != null) {
|
||||||
|
return spreedCapabilities.features!!.contains(spreedFeatures.value)
|
||||||
|
}
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
|
||||||
|
@JvmStatic
|
||||||
|
@Deprecated("Add your capability to Capability enums and use hasSpreedFeatureCapability with enum.")
|
||||||
|
fun hasSpreedFeatureCapability(spreedCapabilities: SpreedCapability, capabilityName: String): Boolean {
|
||||||
|
if (spreedCapabilities.features != null) {
|
||||||
|
return spreedCapabilities.features!!.contains(capabilityName)
|
||||||
|
}
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getMessageMaxLength(spreedCapabilities: SpreedCapability): Int {
|
||||||
|
if (spreedCapabilities.config?.containsKey("chat") == true) {
|
||||||
|
val chatConfigHashMap = spreedCapabilities.config!!["chat"]
|
||||||
|
if (chatConfigHashMap?.containsKey("max-length") == true) {
|
||||||
|
val chatSize = (chatConfigHashMap["max-length"]!!.toString()).toInt()
|
||||||
|
return if (chatSize > 0) {
|
||||||
|
chatSize
|
||||||
|
} else {
|
||||||
|
DEFAULT_CHAT_SIZE
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return DEFAULT_CHAT_SIZE
|
||||||
|
}
|
||||||
|
|
||||||
|
fun isReadStatusAvailable(spreedCapabilities: SpreedCapability): Boolean {
|
||||||
|
if (spreedCapabilities.config?.containsKey("chat") == true) {
|
||||||
|
val map: Map<String, Any>? = spreedCapabilities.config!!["chat"]
|
||||||
|
return map != null && map.containsKey("read-privacy")
|
||||||
|
}
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
|
||||||
|
@JvmStatic
|
||||||
|
fun isCallRecordingAvailable(spreedCapabilities: SpreedCapability): Boolean {
|
||||||
|
if (hasSpreedFeatureCapability(spreedCapabilities, SpreedFeatures.RECORDING_V1) &&
|
||||||
|
spreedCapabilities.config?.containsKey("call") == true
|
||||||
|
) {
|
||||||
|
val map: Map<String, Any>? = spreedCapabilities.config!!["call"]
|
||||||
|
if (map != null && map.containsKey("recording")) {
|
||||||
|
return (map["recording"].toString()).toBoolean()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
|
||||||
|
@JvmStatic
|
||||||
|
fun getAttachmentFolder(spreedCapabilities: SpreedCapability): String {
|
||||||
|
if (spreedCapabilities.config?.containsKey("attachments") == true) {
|
||||||
|
val map = spreedCapabilities.config!!["attachments"]
|
||||||
|
if (map?.containsKey("folder") == true) {
|
||||||
|
return map["folder"].toString()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return "/Talk"
|
||||||
|
}
|
||||||
|
|
||||||
|
fun isConversationDescriptionEndpointAvailable(spreedCapabilities: SpreedCapability): Boolean {
|
||||||
|
return hasSpreedFeatureCapability(spreedCapabilities, "room-description")
|
||||||
|
}
|
||||||
|
|
||||||
|
fun isUnifiedSearchAvailable(spreedCapabilities: SpreedCapability): Boolean {
|
||||||
|
return hasSpreedFeatureCapability(spreedCapabilities, "unified-search")
|
||||||
|
}
|
||||||
|
|
||||||
|
fun isAbleToCall(spreedCapabilities: SpreedCapability): Boolean {
|
||||||
|
return if (
|
||||||
|
spreedCapabilities.config?.containsKey("call") == true &&
|
||||||
|
spreedCapabilities.config!!["call"] != null &&
|
||||||
|
spreedCapabilities.config!!["call"]!!.containsKey("enabled")
|
||||||
|
) {
|
||||||
|
java.lang.Boolean.parseBoolean(spreedCapabilities.config!!["call"]!!["enabled"].toString())
|
||||||
|
} else {
|
||||||
|
// older nextcloud versions without the capability can't disable the calls
|
||||||
|
true
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fun isCallReactionsSupported(user: User?): Boolean {
|
||||||
|
if (user?.capabilities != null) {
|
||||||
|
val capabilities = user.capabilities
|
||||||
|
return capabilities?.spreedCapability?.config?.containsKey("call") == true &&
|
||||||
|
capabilities.spreedCapability!!.config!!["call"] != null &&
|
||||||
|
capabilities.spreedCapability!!.config!!["call"]!!.containsKey("supported-reactions")
|
||||||
|
}
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
|
||||||
|
fun isTranslationsSupported(spreedCapabilities: SpreedCapability): Boolean {
|
||||||
|
return spreedCapabilities.config?.containsKey("chat") == true &&
|
||||||
|
spreedCapabilities.config!!["chat"] != null &&
|
||||||
|
spreedCapabilities.config!!["chat"]!!.containsKey("has-translation-providers") &&
|
||||||
|
spreedCapabilities.config!!["chat"]!!["has-translation-providers"] == true
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getRecordingConsentType(spreedCapabilities: SpreedCapability): Int {
|
||||||
|
if (
|
||||||
|
spreedCapabilities.config?.containsKey("call") == true &&
|
||||||
|
spreedCapabilities.config!!["call"] != null &&
|
||||||
|
spreedCapabilities.config!!["call"]!!.containsKey("recording-consent")
|
||||||
|
) {
|
||||||
|
return when (
|
||||||
|
spreedCapabilities.config!!["call"]!!["recording-consent"].toString()
|
||||||
|
.toInt()
|
||||||
|
) {
|
||||||
|
1 -> RECORDING_CONSENT_REQUIRED
|
||||||
|
2 -> RECORDING_CONSENT_DEPEND_ON_CONVERSATION
|
||||||
|
else -> RECORDING_CONSENT_NOT_REQUIRED
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return RECORDING_CONSENT_NOT_REQUIRED
|
||||||
|
}
|
||||||
|
|
||||||
|
// endregion
|
||||||
|
|
||||||
|
//region SpreedCapabilities that can't be used with federation as the settings for them are global
|
||||||
|
|
||||||
|
fun isReadStatusPrivate(user: User): Boolean {
|
||||||
|
if (user.capabilities?.spreedCapability?.config?.containsKey("chat") == true) {
|
||||||
|
val map = user.capabilities!!.spreedCapability!!.config!!["chat"]
|
||||||
|
if (map?.containsKey("read-privacy") == true) {
|
||||||
|
return (map["read-privacy"]!!.toString()).toInt() == 1
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
|
||||||
|
fun isTypingStatusAvailable(user: User): Boolean {
|
||||||
|
if (user.capabilities?.spreedCapability?.config?.containsKey("chat") == true) {
|
||||||
|
val map = user.capabilities!!.spreedCapability!!.config!!["chat"]
|
||||||
|
return map != null && map.containsKey("typing-privacy")
|
||||||
|
}
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
|
||||||
|
fun isTypingStatusPrivate(user: User): Boolean {
|
||||||
|
if (user.capabilities?.spreedCapability?.config?.containsKey("chat") == true) {
|
||||||
|
val map = user.capabilities!!.spreedCapability!!.config!!["chat"]
|
||||||
|
if (map?.containsKey("typing-privacy") == true) {
|
||||||
|
return (map["typing-privacy"]!!.toString()).toInt() == 1
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
|
||||||
|
// endregion
|
||||||
|
|
||||||
|
//region ThemingCapabilities
|
||||||
|
|
||||||
|
fun getServerName(user: User?): String? {
|
||||||
|
if (user?.capabilities?.themingCapability != null) {
|
||||||
|
return user.capabilities!!.themingCapability!!.name
|
||||||
|
}
|
||||||
|
return ""
|
||||||
|
}
|
||||||
|
|
||||||
|
// endregion
|
||||||
|
|
||||||
|
//region ProvisioningCapabilities
|
||||||
|
|
||||||
|
fun canEditScopes(user: User): Boolean {
|
||||||
|
return user.capabilities?.provisioningCapability?.accountPropertyScopesVersion != null &&
|
||||||
|
user.capabilities!!.provisioningCapability!!.accountPropertyScopesVersion!! > 1
|
||||||
|
}
|
||||||
|
|
||||||
|
// endregion
|
||||||
|
|
||||||
|
//region UserStatusCapabilities
|
||||||
|
|
||||||
|
@JvmStatic
|
||||||
|
fun isUserStatusAvailable(user: User): Boolean {
|
||||||
|
return user.capabilities?.userStatusCapability?.enabled == true &&
|
||||||
|
user.capabilities?.userStatusCapability?.supportsEmoji == true
|
||||||
|
}
|
||||||
|
|
||||||
|
// endregion
|
||||||
|
|
||||||
|
const val DEFAULT_CHAT_SIZE = 1000
|
||||||
|
const val RECORDING_CONSENT_NOT_REQUIRED = 0
|
||||||
|
const val RECORDING_CONSENT_REQUIRED = 1
|
||||||
|
const val RECORDING_CONSENT_DEPEND_ON_CONVERSATION = 2
|
||||||
|
private const val SERVER_VERSION_MIN_SUPPORTED = 14
|
||||||
|
private const val SERVER_VERSION_SUPPORT_WARNING = 18
|
||||||
|
}
|
|
@ -1,10 +1,9 @@
|
||||||
package com.nextcloud.talk.utils
|
package com.nextcloud.talk.utils
|
||||||
|
|
||||||
import com.nextcloud.talk.data.user.model.User
|
|
||||||
import com.nextcloud.talk.models.domain.ConversationModel
|
import com.nextcloud.talk.models.domain.ConversationModel
|
||||||
import com.nextcloud.talk.models.domain.ConversationType
|
import com.nextcloud.talk.models.domain.ConversationType
|
||||||
import com.nextcloud.talk.models.domain.ParticipantType
|
import com.nextcloud.talk.models.domain.ParticipantType
|
||||||
import com.nextcloud.talk.utils.database.user.CapabilitiesUtilNew
|
import com.nextcloud.talk.models.json.capabilities.SpreedCapability
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Nextcloud Talk application
|
* Nextcloud Talk application
|
||||||
|
@ -45,28 +44,28 @@ object ConversationUtils {
|
||||||
ParticipantType.MODERATOR == conversation.participantType
|
ParticipantType.MODERATOR == conversation.participantType
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun isLockedOneToOne(conversation: ConversationModel, conversationUser: User): Boolean {
|
fun isLockedOneToOne(conversation: ConversationModel, spreedCapabilities: SpreedCapability): Boolean {
|
||||||
return conversation.type == ConversationType.ROOM_TYPE_ONE_TO_ONE_CALL &&
|
return conversation.type == ConversationType.ROOM_TYPE_ONE_TO_ONE_CALL &&
|
||||||
CapabilitiesUtilNew.hasSpreedFeatureCapability(conversationUser, "locked-one-to-one-rooms")
|
CapabilitiesUtil.hasSpreedFeatureCapability(spreedCapabilities, "locked-one-to-one-rooms")
|
||||||
}
|
}
|
||||||
|
|
||||||
fun canModerate(conversation: ConversationModel, conversationUser: User): Boolean {
|
fun canModerate(conversation: ConversationModel, spreedCapabilities: SpreedCapability): Boolean {
|
||||||
return isParticipantOwnerOrModerator(conversation) &&
|
return isParticipantOwnerOrModerator(conversation) &&
|
||||||
!isLockedOneToOne(conversation, conversationUser) &&
|
!isLockedOneToOne(conversation, spreedCapabilities) &&
|
||||||
conversation.type != ConversationType.FORMER_ONE_TO_ONE &&
|
conversation.type != ConversationType.FORMER_ONE_TO_ONE &&
|
||||||
!isNoteToSelfConversation(conversation)
|
!isNoteToSelfConversation(conversation)
|
||||||
}
|
}
|
||||||
|
|
||||||
fun isLobbyViewApplicable(conversation: ConversationModel, conversationUser: User): Boolean {
|
fun isLobbyViewApplicable(conversation: ConversationModel, spreedCapabilities: SpreedCapability): Boolean {
|
||||||
return !canModerate(conversation, conversationUser) &&
|
return !canModerate(conversation, spreedCapabilities) &&
|
||||||
(
|
(
|
||||||
conversation.type == ConversationType.ROOM_GROUP_CALL ||
|
conversation.type == ConversationType.ROOM_GROUP_CALL ||
|
||||||
conversation.type == ConversationType.ROOM_PUBLIC_CALL
|
conversation.type == ConversationType.ROOM_PUBLIC_CALL
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
fun isNameEditable(conversation: ConversationModel, conversationUser: User): Boolean {
|
fun isNameEditable(conversation: ConversationModel, spreedCapabilities: SpreedCapability): Boolean {
|
||||||
return canModerate(conversation, conversationUser) &&
|
return canModerate(conversation, spreedCapabilities) &&
|
||||||
ConversationType.ROOM_TYPE_ONE_TO_ONE_CALL != conversation.type
|
ConversationType.ROOM_TYPE_ONE_TO_ONE_CALL != conversation.type
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -79,12 +78,12 @@ object ConversationUtils {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
fun canDelete(conversation: ConversationModel, conversationUser: User): Boolean {
|
fun canDelete(conversation: ConversationModel, spreedCapability: SpreedCapability): Boolean {
|
||||||
return if (conversation.canDeleteConversation != null) {
|
return if (conversation.canDeleteConversation != null) {
|
||||||
// Available since APIv2
|
// Available since APIv2
|
||||||
conversation.canDeleteConversation!!
|
conversation.canDeleteConversation!!
|
||||||
} else {
|
} else {
|
||||||
canModerate(conversation, conversationUser)
|
canModerate(conversation, spreedCapability)
|
||||||
// Fallback for APIv1
|
// Fallback for APIv1
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -61,7 +61,6 @@ import com.nextcloud.talk.utils.MimetypeUtils.isGif
|
||||||
import com.nextcloud.talk.utils.MimetypeUtils.isMarkdown
|
import com.nextcloud.talk.utils.MimetypeUtils.isMarkdown
|
||||||
import com.nextcloud.talk.utils.bundle.BundleKeys.KEY_ACCOUNT
|
import com.nextcloud.talk.utils.bundle.BundleKeys.KEY_ACCOUNT
|
||||||
import com.nextcloud.talk.utils.bundle.BundleKeys.KEY_FILE_ID
|
import com.nextcloud.talk.utils.bundle.BundleKeys.KEY_FILE_ID
|
||||||
import com.nextcloud.talk.utils.database.user.CapabilitiesUtilNew
|
|
||||||
import java.io.File
|
import java.io.File
|
||||||
import java.util.concurrent.ExecutionException
|
import java.util.concurrent.ExecutionException
|
||||||
|
|
||||||
|
@ -308,7 +307,7 @@ class FileViewerUtils(private val context: Context, private val user: User) {
|
||||||
.putString(DownloadFileToCacheWorker.KEY_USER_ID, user.userId)
|
.putString(DownloadFileToCacheWorker.KEY_USER_ID, user.userId)
|
||||||
.putString(
|
.putString(
|
||||||
DownloadFileToCacheWorker.KEY_ATTACHMENT_FOLDER,
|
DownloadFileToCacheWorker.KEY_ATTACHMENT_FOLDER,
|
||||||
CapabilitiesUtilNew.getAttachmentFolder(user)
|
CapabilitiesUtil.getAttachmentFolder(user.capabilities!!.spreedCapability!!)
|
||||||
)
|
)
|
||||||
.putString(DownloadFileToCacheWorker.KEY_FILE_NAME, fileInfo.fileName)
|
.putString(DownloadFileToCacheWorker.KEY_FILE_NAME, fileInfo.fileName)
|
||||||
.putString(DownloadFileToCacheWorker.KEY_FILE_PATH, path)
|
.putString(DownloadFileToCacheWorker.KEY_FILE_PATH, path)
|
||||||
|
|
|
@ -22,22 +22,21 @@
|
||||||
|
|
||||||
package com.nextcloud.talk.utils
|
package com.nextcloud.talk.utils
|
||||||
|
|
||||||
import com.nextcloud.talk.data.user.model.User
|
|
||||||
import com.nextcloud.talk.models.domain.ConversationModel
|
import com.nextcloud.talk.models.domain.ConversationModel
|
||||||
|
import com.nextcloud.talk.models.json.capabilities.SpreedCapability
|
||||||
import com.nextcloud.talk.models.json.conversations.Conversation
|
import com.nextcloud.talk.models.json.conversations.Conversation
|
||||||
import com.nextcloud.talk.utils.database.user.CapabilitiesUtilNew
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* see https://nextcloud-talk.readthedocs.io/en/latest/constants/#attendee-permissions
|
* see https://nextcloud-talk.readthedocs.io/en/latest/constants/#attendee-permissions
|
||||||
*/
|
*/
|
||||||
class ParticipantPermissions(
|
class ParticipantPermissions(
|
||||||
private val user: User,
|
private val spreedCapabilities: SpreedCapability,
|
||||||
private val conversation: ConversationModel
|
private val conversation: ConversationModel
|
||||||
) {
|
) {
|
||||||
|
|
||||||
@Deprecated("Use ChatRepository.ConversationModel")
|
@Deprecated("Use ChatRepository.ConversationModel")
|
||||||
constructor(user: User, conversation: Conversation) : this(
|
constructor(spreedCapabilities: SpreedCapability, conversation: Conversation) : this(
|
||||||
user,
|
spreedCapabilities,
|
||||||
ConversationModel.mapToConversationModel(conversation)
|
ConversationModel.mapToConversationModel(conversation)
|
||||||
)
|
)
|
||||||
|
|
||||||
|
@ -52,8 +51,8 @@ class ParticipantPermissions(
|
||||||
private val hasChatPermission = (conversation.permissions and CHAT) == CHAT
|
private val hasChatPermission = (conversation.permissions and CHAT) == CHAT
|
||||||
|
|
||||||
private fun hasConversationPermissions(): Boolean {
|
private fun hasConversationPermissions(): Boolean {
|
||||||
return CapabilitiesUtilNew.hasSpreedFeatureCapability(
|
return CapabilitiesUtil.hasSpreedFeatureCapability(
|
||||||
user,
|
spreedCapabilities,
|
||||||
"conversation-permissions"
|
"conversation-permissions"
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
@ -91,7 +90,7 @@ class ParticipantPermissions(
|
||||||
}
|
}
|
||||||
|
|
||||||
fun hasChatPermission(): Boolean {
|
fun hasChatPermission(): Boolean {
|
||||||
if (CapabilitiesUtilNew.hasSpreedFeatureCapability(user, "chat-permission")) {
|
if (CapabilitiesUtil.hasSpreedFeatureCapability(spreedCapabilities, "chat-permission")) {
|
||||||
return hasChatPermission
|
return hasChatPermission
|
||||||
}
|
}
|
||||||
// if capability is not available then the spreed version doesn't support to restrict this
|
// if capability is not available then the spreed version doesn't support to restrict this
|
||||||
|
|
|
@ -238,7 +238,7 @@ class PushUtils {
|
||||||
val credentials = ApiUtils.getCredentials(user.username, user.token)
|
val credentials = ApiUtils.getCredentials(user.username, user.token)
|
||||||
ncApi.registerDeviceForNotificationsWithNextcloud(
|
ncApi.registerDeviceForNotificationsWithNextcloud(
|
||||||
credentials,
|
credentials,
|
||||||
ApiUtils.getUrlNextcloudPush(user.baseUrl),
|
ApiUtils.getUrlNextcloudPush(user.baseUrl!!),
|
||||||
nextcloudRegisterPushMap
|
nextcloudRegisterPushMap
|
||||||
)
|
)
|
||||||
.subscribe(object : Observer<PushRegistrationOverall> {
|
.subscribe(object : Observer<PushRegistrationOverall> {
|
||||||
|
|
|
@ -53,8 +53,8 @@ object RemoteFileUtils {
|
||||||
return ncApi.checkIfFileExists(
|
return ncApi.checkIfFileExists(
|
||||||
ApiUtils.getCredentials(currentUser.username, currentUser.token),
|
ApiUtils.getCredentials(currentUser.username, currentUser.token),
|
||||||
ApiUtils.getUrlForFileUpload(
|
ApiUtils.getUrlForFileUpload(
|
||||||
currentUser.baseUrl,
|
currentUser.baseUrl!!,
|
||||||
currentUser.userId,
|
currentUser.userId!!,
|
||||||
remotePath
|
remotePath
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
|
|
|
@ -22,10 +22,10 @@ package com.nextcloud.talk.utils
|
||||||
import android.content.Context
|
import android.content.Context
|
||||||
import com.nextcloud.talk.R
|
import com.nextcloud.talk.R
|
||||||
import com.nextcloud.talk.data.user.model.User
|
import com.nextcloud.talk.data.user.model.User
|
||||||
import com.nextcloud.talk.models.json.conversations.Conversation
|
import com.nextcloud.talk.models.domain.ConversationModel
|
||||||
|
|
||||||
object ShareUtils {
|
object ShareUtils {
|
||||||
fun getStringForIntent(context: Context, user: User, conversation: Conversation?): String {
|
fun getStringForIntent(context: Context, user: User, conversation: ConversationModel?): String {
|
||||||
return String.format(
|
return String.format(
|
||||||
context.resources.getString(R.string.nc_share_text),
|
context.resources.getString(R.string.nc_share_text),
|
||||||
user.baseUrl,
|
user.baseUrl,
|
||||||
|
|
|
@ -89,4 +89,5 @@ object BundleKeys {
|
||||||
const val KEY_REAUTHORIZE_ACCOUNT = "KEY_REAUTHORIZE_ACCOUNT"
|
const val KEY_REAUTHORIZE_ACCOUNT = "KEY_REAUTHORIZE_ACCOUNT"
|
||||||
const val KEY_PASSWORD = "KEY_PASSWORD"
|
const val KEY_PASSWORD = "KEY_PASSWORD"
|
||||||
const val KEY_REMOTE_TALK_SHARE = "KEY_REMOTE_TALK_SHARE"
|
const val KEY_REMOTE_TALK_SHARE = "KEY_REMOTE_TALK_SHARE"
|
||||||
|
const val KEY_CHAT_API_VERSION = "KEY_CHAT_API_VERSION"
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,267 +0,0 @@
|
||||||
/*
|
|
||||||
* Nextcloud Talk application
|
|
||||||
*
|
|
||||||
* @author Andy Scherzinger
|
|
||||||
* @author Mario Danic
|
|
||||||
* Copyright (C) 2021 Andy Scherzinger (info@andy-scherzinger.de)
|
|
||||||
* Copyright (C) 2017-2018 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.utils.database.user
|
|
||||||
|
|
||||||
import com.nextcloud.talk.data.user.model.User
|
|
||||||
import com.nextcloud.talk.models.json.capabilities.Capabilities
|
|
||||||
|
|
||||||
@Suppress("TooManyFunctions")
|
|
||||||
object CapabilitiesUtilNew {
|
|
||||||
fun hasNotificationsCapability(user: User, capabilityName: String): Boolean {
|
|
||||||
return user.capabilities?.spreedCapability?.features?.contains(capabilityName) == true
|
|
||||||
}
|
|
||||||
|
|
||||||
fun hasExternalCapability(user: User, capabilityName: String?): Boolean {
|
|
||||||
if (user.capabilities?.externalCapability?.containsKey("v1") == true) {
|
|
||||||
return user.capabilities!!.externalCapability!!["v1"]?.contains(capabilityName!!) == true
|
|
||||||
}
|
|
||||||
return false
|
|
||||||
}
|
|
||||||
|
|
||||||
@JvmStatic
|
|
||||||
fun isServerEOL(capabilities: Capabilities?): Boolean {
|
|
||||||
// Capability is available since Talk 4 => Nextcloud 14 => Autmn 2018
|
|
||||||
return !hasSpreedFeatureCapability(capabilities, "no-ping")
|
|
||||||
}
|
|
||||||
|
|
||||||
fun isServerAlmostEOL(user: User): Boolean {
|
|
||||||
// Capability is available since Talk 8 => Nextcloud 18 => January 2020
|
|
||||||
return !hasSpreedFeatureCapability(user, "chat-replies")
|
|
||||||
}
|
|
||||||
|
|
||||||
fun canSetChatReadMarker(user: User): Boolean {
|
|
||||||
return hasSpreedFeatureCapability(user, "chat-read-marker")
|
|
||||||
}
|
|
||||||
|
|
||||||
fun canMarkRoomAsUnread(user: User): Boolean {
|
|
||||||
return hasSpreedFeatureCapability(user, "chat-unread")
|
|
||||||
}
|
|
||||||
|
|
||||||
@JvmStatic
|
|
||||||
fun hasSpreedFeatureCapability(user: User?, capabilityName: String): Boolean {
|
|
||||||
return hasSpreedFeatureCapability(user?.capabilities, capabilityName)
|
|
||||||
}
|
|
||||||
|
|
||||||
@JvmStatic
|
|
||||||
fun hasSpreedFeatureCapability(capabilities: Capabilities?, capabilityName: String): Boolean {
|
|
||||||
if (capabilities?.spreedCapability?.features != null) {
|
|
||||||
return capabilities.spreedCapability!!.features!!.contains(capabilityName)
|
|
||||||
}
|
|
||||||
return false
|
|
||||||
}
|
|
||||||
|
|
||||||
fun getMessageMaxLength(user: User?): Int {
|
|
||||||
if (user?.capabilities?.spreedCapability?.config?.containsKey("chat") == true) {
|
|
||||||
val chatConfigHashMap = user.capabilities!!.spreedCapability!!.config!!["chat"]
|
|
||||||
if (chatConfigHashMap?.containsKey("max-length") == true) {
|
|
||||||
val chatSize = (chatConfigHashMap["max-length"]!!.toString()).toInt()
|
|
||||||
return if (chatSize > 0) {
|
|
||||||
chatSize
|
|
||||||
} else {
|
|
||||||
DEFAULT_CHAT_SIZE
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return DEFAULT_CHAT_SIZE
|
|
||||||
}
|
|
||||||
|
|
||||||
fun isPhoneBookIntegrationAvailable(user: User): Boolean {
|
|
||||||
return user.capabilities?.spreedCapability?.features?.contains("phonebook-search") == true
|
|
||||||
}
|
|
||||||
|
|
||||||
fun isReadStatusAvailable(user: User): Boolean {
|
|
||||||
if (user.capabilities?.spreedCapability?.config?.containsKey("chat") == true) {
|
|
||||||
val map: Map<String, Any>? = user.capabilities!!.spreedCapability!!.config!!["chat"]
|
|
||||||
return map != null && map.containsKey("read-privacy")
|
|
||||||
}
|
|
||||||
return false
|
|
||||||
}
|
|
||||||
|
|
||||||
fun isReadStatusPrivate(user: User): Boolean {
|
|
||||||
if (user.capabilities?.spreedCapability?.config?.containsKey("chat") == true) {
|
|
||||||
val map = user.capabilities!!.spreedCapability!!.config!!["chat"]
|
|
||||||
if (map?.containsKey("read-privacy") == true) {
|
|
||||||
return (map["read-privacy"]!!.toString()).toInt() == 1
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return false
|
|
||||||
}
|
|
||||||
|
|
||||||
fun isTypingStatusAvailable(user: User): Boolean {
|
|
||||||
if (user.capabilities?.spreedCapability?.config?.containsKey("chat") == true) {
|
|
||||||
val map = user.capabilities!!.spreedCapability!!.config!!["chat"]
|
|
||||||
return map != null && map.containsKey("typing-privacy")
|
|
||||||
}
|
|
||||||
return false
|
|
||||||
}
|
|
||||||
|
|
||||||
fun isTypingStatusPrivate(user: User): Boolean {
|
|
||||||
if (user.capabilities?.spreedCapability?.config?.containsKey("chat") == true) {
|
|
||||||
val map = user.capabilities!!.spreedCapability!!.config!!["chat"]
|
|
||||||
if (map?.containsKey("typing-privacy") == true) {
|
|
||||||
return (map["typing-privacy"]!!.toString()).toInt() == 1
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return false
|
|
||||||
}
|
|
||||||
|
|
||||||
@JvmStatic
|
|
||||||
fun isCallRecordingAvailable(user: User): Boolean {
|
|
||||||
if (hasSpreedFeatureCapability(user, "recording-v1") &&
|
|
||||||
user.capabilities?.spreedCapability?.config?.containsKey("call") == true
|
|
||||||
) {
|
|
||||||
val map: Map<String, Any>? = user.capabilities!!.spreedCapability!!.config!!["call"]
|
|
||||||
if (map != null && map.containsKey("recording")) {
|
|
||||||
return (map["recording"].toString()).toBoolean()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return false
|
|
||||||
}
|
|
||||||
|
|
||||||
@JvmStatic
|
|
||||||
fun isUserStatusAvailable(user: User): Boolean {
|
|
||||||
return user.capabilities?.userStatusCapability?.enabled == true &&
|
|
||||||
user.capabilities?.userStatusCapability?.supportsEmoji == true
|
|
||||||
}
|
|
||||||
|
|
||||||
@JvmStatic
|
|
||||||
fun getAttachmentFolder(user: User): String {
|
|
||||||
if (user.capabilities?.spreedCapability?.config?.containsKey("attachments") == true) {
|
|
||||||
val map = user.capabilities!!.spreedCapability!!.config!!["attachments"]
|
|
||||||
if (map?.containsKey("folder") == true) {
|
|
||||||
return map["folder"].toString()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return "/Talk"
|
|
||||||
}
|
|
||||||
|
|
||||||
fun getServerName(user: User?): String? {
|
|
||||||
if (user?.capabilities?.themingCapability != null) {
|
|
||||||
return user.capabilities!!.themingCapability!!.name
|
|
||||||
}
|
|
||||||
return ""
|
|
||||||
}
|
|
||||||
|
|
||||||
// TODO later avatar can also be checked via user fields, for now it is in Talk capability
|
|
||||||
fun isAvatarEndpointAvailable(user: User): Boolean {
|
|
||||||
return user.capabilities?.spreedCapability?.features?.contains("temp-user-avatar-api") == true
|
|
||||||
}
|
|
||||||
|
|
||||||
fun isConversationAvatarEndpointAvailable(user: User): Boolean {
|
|
||||||
return user.capabilities?.spreedCapability?.features?.contains("avatar") == true
|
|
||||||
}
|
|
||||||
|
|
||||||
fun isConversationDescriptionEndpointAvailable(user: User): Boolean {
|
|
||||||
return user.capabilities?.spreedCapability?.features?.contains("room-description") == true
|
|
||||||
}
|
|
||||||
|
|
||||||
fun canEditScopes(user: User): Boolean {
|
|
||||||
return user.capabilities?.provisioningCapability?.accountPropertyScopesVersion != null &&
|
|
||||||
user.capabilities!!.provisioningCapability!!.accountPropertyScopesVersion!! > 1
|
|
||||||
}
|
|
||||||
|
|
||||||
fun isAbleToCall(user: User?): Boolean {
|
|
||||||
if (user?.capabilities != null) {
|
|
||||||
val capabilities = user.capabilities
|
|
||||||
return if (
|
|
||||||
capabilities?.spreedCapability?.config?.containsKey("call") == true &&
|
|
||||||
capabilities.spreedCapability!!.config!!["call"] != null &&
|
|
||||||
capabilities.spreedCapability!!.config!!["call"]!!.containsKey("enabled")
|
|
||||||
) {
|
|
||||||
java.lang.Boolean.parseBoolean(capabilities.spreedCapability!!.config!!["call"]!!["enabled"].toString())
|
|
||||||
} else {
|
|
||||||
// older nextcloud versions without the capability can't disable the calls
|
|
||||||
true
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return false
|
|
||||||
}
|
|
||||||
|
|
||||||
fun isCallReactionsSupported(user: User?): Boolean {
|
|
||||||
if (user?.capabilities != null) {
|
|
||||||
val capabilities = user.capabilities
|
|
||||||
return capabilities?.spreedCapability?.config?.containsKey("call") == true &&
|
|
||||||
capabilities.spreedCapability!!.config!!["call"] != null &&
|
|
||||||
capabilities.spreedCapability!!.config!!["call"]!!.containsKey("supported-reactions")
|
|
||||||
}
|
|
||||||
return false
|
|
||||||
}
|
|
||||||
|
|
||||||
@JvmStatic
|
|
||||||
fun isUnifiedSearchAvailable(user: User): Boolean {
|
|
||||||
return hasSpreedFeatureCapability(user, "unified-search")
|
|
||||||
}
|
|
||||||
|
|
||||||
@JvmStatic
|
|
||||||
fun isLinkPreviewAvailable(user: User): Boolean {
|
|
||||||
return user.capabilities?.coreCapability?.referenceApi != null &&
|
|
||||||
user.capabilities?.coreCapability?.referenceApi == "true"
|
|
||||||
}
|
|
||||||
|
|
||||||
fun isTranslationsSupported(user: User?): Boolean {
|
|
||||||
if (user?.capabilities != null) {
|
|
||||||
val capabilities = user.capabilities
|
|
||||||
return capabilities?.spreedCapability?.config?.containsKey("chat") == true &&
|
|
||||||
capabilities.spreedCapability!!.config!!["chat"] != null &&
|
|
||||||
capabilities.spreedCapability!!.config!!["chat"]!!.containsKey("has-translation-providers") &&
|
|
||||||
capabilities.spreedCapability!!.config!!["chat"]!!["has-translation-providers"] == true
|
|
||||||
}
|
|
||||||
|
|
||||||
return false
|
|
||||||
}
|
|
||||||
|
|
||||||
fun isRemindSupported(user: User?): Boolean {
|
|
||||||
if (user?.capabilities != null) {
|
|
||||||
val capabilities = user.capabilities
|
|
||||||
return capabilities?.spreedCapability?.features?.contains("remind-me-later") == true
|
|
||||||
}
|
|
||||||
|
|
||||||
return false
|
|
||||||
}
|
|
||||||
|
|
||||||
fun getRecordingConsentType(user: User?): Int {
|
|
||||||
if (user?.capabilities != null) {
|
|
||||||
val capabilities = user.capabilities
|
|
||||||
if (
|
|
||||||
capabilities?.spreedCapability?.config?.containsKey("call") == true &&
|
|
||||||
capabilities.spreedCapability!!.config!!["call"] != null &&
|
|
||||||
capabilities.spreedCapability!!.config!!["call"]!!.containsKey("recording-consent")
|
|
||||||
) {
|
|
||||||
return when (
|
|
||||||
capabilities.spreedCapability!!.config!!["call"]!!["recording-consent"].toString()
|
|
||||||
.toInt()
|
|
||||||
) {
|
|
||||||
1 -> RECORDING_CONSENT_REQUIRED
|
|
||||||
2 -> RECORDING_CONSENT_DEPEND_ON_CONVERSATION
|
|
||||||
else -> RECORDING_CONSENT_NOT_REQUIRED
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return RECORDING_CONSENT_NOT_REQUIRED
|
|
||||||
}
|
|
||||||
|
|
||||||
const val DEFAULT_CHAT_SIZE = 1000
|
|
||||||
const val RECORDING_CONSENT_NOT_REQUIRED = 0
|
|
||||||
const val RECORDING_CONSENT_REQUIRED = 1
|
|
||||||
const val RECORDING_CONSENT_DEPEND_ON_CONVERSATION = 2
|
|
||||||
}
|
|
|
@ -35,7 +35,7 @@ import com.nextcloud.talk.data.user.model.User;
|
||||||
import com.nextcloud.talk.models.json.generic.GenericOverall;
|
import com.nextcloud.talk.models.json.generic.GenericOverall;
|
||||||
import com.nextcloud.talk.utils.ApiUtils;
|
import com.nextcloud.talk.utils.ApiUtils;
|
||||||
import com.nextcloud.talk.utils.UserIdUtils;
|
import com.nextcloud.talk.utils.UserIdUtils;
|
||||||
import com.nextcloud.talk.utils.database.user.CapabilitiesUtilNew;
|
import com.nextcloud.talk.utils.CapabilitiesUtil;
|
||||||
|
|
||||||
import javax.inject.Inject;
|
import javax.inject.Inject;
|
||||||
|
|
||||||
|
@ -158,7 +158,8 @@ public class DatabaseStorageModule {
|
||||||
});
|
});
|
||||||
|
|
||||||
} else if ("conversation_info_message_notifications_dropdown".equals(key)) {
|
} else if ("conversation_info_message_notifications_dropdown".equals(key)) {
|
||||||
if (CapabilitiesUtilNew.hasSpreedFeatureCapability(conversationUser, "notification-levels")) {
|
if (CapabilitiesUtil.hasSpreedFeatureCapability(conversationUser.getCapabilities().getSpreedCapability(), "notification" +
|
||||||
|
"-levels")) {
|
||||||
if (TextUtils.isEmpty(messageNotificationLevel) || !messageNotificationLevel.equals(value)) {
|
if (TextUtils.isEmpty(messageNotificationLevel) || !messageNotificationLevel.equals(value)) {
|
||||||
int intValue;
|
int intValue;
|
||||||
switch (value) {
|
switch (value) {
|
||||||
|
@ -175,7 +176,7 @@ public class DatabaseStorageModule {
|
||||||
intValue = 0;
|
intValue = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
int apiVersion = ApiUtils.getConversationApiVersion(conversationUser, new int[]{ApiUtils.APIv4, 1});
|
int apiVersion = ApiUtils.getConversationApiVersion(conversationUser, new int[]{ApiUtils.API_V4, 1});
|
||||||
|
|
||||||
ncApi.setNotificationLevel(ApiUtils.getCredentials(conversationUser.getUsername(),
|
ncApi.setNotificationLevel(ApiUtils.getCredentials(conversationUser.getUsername(),
|
||||||
conversationUser.getToken()),
|
conversationUser.getToken()),
|
||||||
|
|
|
@ -25,7 +25,6 @@ import androidx.lifecycle.LiveData
|
||||||
import androidx.lifecycle.MutableLiveData
|
import androidx.lifecycle.MutableLiveData
|
||||||
import androidx.lifecycle.ViewModel
|
import androidx.lifecycle.ViewModel
|
||||||
import com.nextcloud.talk.activities.CallActivity.Companion.TAG
|
import com.nextcloud.talk.activities.CallActivity.Companion.TAG
|
||||||
import com.nextcloud.talk.location.GeocodingActivity
|
|
||||||
import fr.dudie.nominatim.client.TalkJsonNominatimClient
|
import fr.dudie.nominatim.client.TalkJsonNominatimClient
|
||||||
import fr.dudie.nominatim.model.Address
|
import fr.dudie.nominatim.model.Address
|
||||||
import kotlinx.coroutines.CoroutineScope
|
import kotlinx.coroutines.CoroutineScope
|
||||||
|
@ -70,9 +69,9 @@ class GeoCodingViewModel : ViewModel() {
|
||||||
try {
|
try {
|
||||||
val results = nominatimClient.search(query) as ArrayList<Address>
|
val results = nominatimClient.search(query) as ArrayList<Address>
|
||||||
for (address in results) {
|
for (address in results) {
|
||||||
Log.d(GeocodingActivity.TAG, address.displayName)
|
Log.d(TAG, address.displayName)
|
||||||
Log.d(GeocodingActivity.TAG, address.latitude.toString())
|
Log.d(TAG, address.latitude.toString())
|
||||||
Log.d(GeocodingActivity.TAG, address.longitude.toString())
|
Log.d(TAG, address.longitude.toString())
|
||||||
}
|
}
|
||||||
geocodingResults = results
|
geocodingResults = results
|
||||||
geocodingResultsLiveData.postValue(results)
|
geocodingResultsLiveData.postValue(results)
|
||||||
|
|
|
@ -113,7 +113,7 @@ public class WebSocketConnectionHelper {
|
||||||
}
|
}
|
||||||
|
|
||||||
HelloOverallWebSocketMessage getAssembledHelloModel(User user, String ticket) {
|
HelloOverallWebSocketMessage getAssembledHelloModel(User user, String ticket) {
|
||||||
int apiVersion = ApiUtils.getSignalingApiVersion(user, new int[]{ApiUtils.APIv3, 2, 1});
|
int apiVersion = ApiUtils.getSignalingApiVersion(user, new int[]{ApiUtils.API_V3, 2, 1});
|
||||||
|
|
||||||
HelloOverallWebSocketMessage helloOverallWebSocketMessage = new HelloOverallWebSocketMessage();
|
HelloOverallWebSocketMessage helloOverallWebSocketMessage = new HelloOverallWebSocketMessage();
|
||||||
helloOverallWebSocketMessage.setType("hello");
|
helloOverallWebSocketMessage.setType("hello");
|
||||||
|
|
|
@ -22,7 +22,7 @@
|
||||||
|
|
||||||
package com.nextcloud.talk.utils
|
package com.nextcloud.talk.utils
|
||||||
|
|
||||||
import com.nextcloud.talk.data.user.model.User
|
import com.nextcloud.talk.models.json.capabilities.SpreedCapability
|
||||||
import com.nextcloud.talk.models.json.conversations.Conversation
|
import com.nextcloud.talk.models.json.conversations.Conversation
|
||||||
import junit.framework.TestCase
|
import junit.framework.TestCase
|
||||||
import org.junit.Test
|
import org.junit.Test
|
||||||
|
@ -31,7 +31,7 @@ class ParticipantPermissionsTest : TestCase() {
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
fun test_areFlagsSet() {
|
fun test_areFlagsSet() {
|
||||||
val user = User()
|
val spreedCapability = SpreedCapability()
|
||||||
val conversation = Conversation()
|
val conversation = Conversation()
|
||||||
conversation.permissions = ParticipantPermissions.PUBLISH_SCREEN or
|
conversation.permissions = ParticipantPermissions.PUBLISH_SCREEN or
|
||||||
ParticipantPermissions.JOIN_CALL or
|
ParticipantPermissions.JOIN_CALL or
|
||||||
|
@ -39,7 +39,7 @@ class ParticipantPermissionsTest : TestCase() {
|
||||||
|
|
||||||
val attendeePermissions =
|
val attendeePermissions =
|
||||||
ParticipantPermissions(
|
ParticipantPermissions(
|
||||||
user,
|
spreedCapability,
|
||||||
conversation
|
conversation
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
|
@ -23,7 +23,7 @@ import android.content.Context
|
||||||
import android.content.res.Resources
|
import android.content.res.Resources
|
||||||
import com.nextcloud.talk.R
|
import com.nextcloud.talk.R
|
||||||
import com.nextcloud.talk.data.user.model.User
|
import com.nextcloud.talk.data.user.model.User
|
||||||
import com.nextcloud.talk.models.json.conversations.Conversation
|
import com.nextcloud.talk.models.domain.ConversationModel
|
||||||
import com.nextcloud.talk.users.UserManager
|
import com.nextcloud.talk.users.UserManager
|
||||||
import io.reactivex.Maybe
|
import io.reactivex.Maybe
|
||||||
import org.junit.Assert
|
import org.junit.Assert
|
||||||
|
@ -49,19 +49,19 @@ class ShareUtilsTest {
|
||||||
private val baseUrl = "https://my.nextcloud.com"
|
private val baseUrl = "https://my.nextcloud.com"
|
||||||
private val token = "2aotbrjr"
|
private val token = "2aotbrjr"
|
||||||
|
|
||||||
private lateinit var conversation: Conversation
|
private lateinit var conversation: ConversationModel
|
||||||
|
|
||||||
@Before
|
@Before
|
||||||
fun setUp() {
|
fun setUp() {
|
||||||
MockitoAnnotations.openMocks(this)
|
MockitoAnnotations.openMocks(this)
|
||||||
Mockito.`when`(userManager!!.currentUser).thenReturn(Maybe.just(user))
|
Mockito.`when`(userManager!!.currentUser).thenReturn(Maybe.just(user))
|
||||||
Mockito.`when`(user!!.baseUrl).thenReturn(baseUrl)
|
Mockito.`when`(user!!.baseUrl!!).thenReturn(baseUrl)
|
||||||
Mockito.`when`(context!!.resources).thenReturn(resources)
|
Mockito.`when`(context!!.resources).thenReturn(resources)
|
||||||
Mockito.`when`(resources!!.getString(R.string.nc_share_text))
|
Mockito.`when`(resources!!.getString(R.string.nc_share_text))
|
||||||
.thenReturn("Join the conversation at %1\$s/index.php/call/%2\$s")
|
.thenReturn("Join the conversation at %1\$s/index.php/call/%2\$s")
|
||||||
Mockito.`when`(resources.getString(R.string.nc_share_text_pass)).thenReturn("\nPassword: %1\$s")
|
Mockito.`when`(resources.getString(R.string.nc_share_text_pass)).thenReturn("\nPassword: %1\$s")
|
||||||
|
|
||||||
conversation = Conversation(token = token)
|
conversation = ConversationModel(token = token)
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
|
|
|
@ -1,5 +1,5 @@
|
||||||
build:
|
build:
|
||||||
maxIssues: 116
|
maxIssues: 122
|
||||||
weights:
|
weights:
|
||||||
# complexity: 2
|
# complexity: 2
|
||||||
# LongParameterList: 1
|
# LongParameterList: 1
|
||||||
|
|
|
@ -1313,8 +1313,6 @@ lQyC8nl8P5PgkEZ5CHcGymZlpzihR3ECrPJTk39Sb7D3SxCW4WrChV3kVfmLgvc=
|
||||||
-----END PGP PUBLIC KEY BLOCK-----
|
-----END PGP PUBLIC KEY BLOCK-----
|
||||||
|
|
||||||
pub C21CE653B639E41A
|
pub C21CE653B639E41A
|
||||||
uid Eric Kuck <eric@bluelinelabs.com>
|
|
||||||
|
|
||||||
sub 4F80368F9034B8D0
|
sub 4F80368F9034B8D0
|
||||||
-----BEGIN PGP PUBLIC KEY BLOCK-----
|
-----BEGIN PGP PUBLIC KEY BLOCK-----
|
||||||
Version: BCPG v1.68
|
Version: BCPG v1.68
|
||||||
|
@ -1324,21 +1322,20 @@ aBF7dud1bzw7voZo5ieGK923wUB+R9vQYd5DYfNLBHj9/TrTVCfKfUIeeEQRZYBz
|
||||||
ufYcDwi4uVx9VPj2wRhkK+lzxphvosJCNFK8Vn82oY7eHQ1RA4AEhCeE/hz8maq6
|
ufYcDwi4uVx9VPj2wRhkK+lzxphvosJCNFK8Vn82oY7eHQ1RA4AEhCeE/hz8maq6
|
||||||
NPoOPjpEN0DVnPIYdjPsdqd4UKQzkX/wMOxghz8SdcVROzUoL+9pZzx968OFuGrV
|
NPoOPjpEN0DVnPIYdjPsdqd4UKQzkX/wMOxghz8SdcVROzUoL+9pZzx968OFuGrV
|
||||||
lUD0su37S6To1IUn6WNEuy1uJTzT3Zqi0hfm31AqPxlLWDOwnuKvUJl3RObyli2k
|
lUD0su37S6To1IUn6WNEuy1uJTzT3Zqi0hfm31AqPxlLWDOwnuKvUJl3RObyli2k
|
||||||
CBtDa5xPE6GU6ZUEFUZ7qbk7iV5p8uTchKVbABEBAAG0IUVyaWMgS3VjayA8ZXJp
|
CBtDa5xPE6GU6ZUEFUZ7qbk7iV5p8uTchKVbABEBAAG5AQ0EVOQoaAEIAMQuOKxG
|
||||||
Y0BibHVlbGluZWxhYnMuY29tPrkBDQRU5ChoAQgAxC44rEZjgnJevvrzdL5vCVqC
|
Y4JyXr7683S+bwlagtViPXGey/A8Bf6b5uzW0SguRoF4oLpdfFBE/NKuBN1iItLU
|
||||||
1WI9cZ7L8DwF/pvm7NbRKC5GgXigul18UET80q4E3WIi0tTMG+pVWO+1v0dEu/Re
|
zBvqVVjvtb9HRLv0Xgf5foXO+osCYzpcEokNY76uv6tDYZ3tP9JIUmDVsndAMCdl
|
||||||
B/l+hc76iwJjOlwSiQ1jvq6/q0Nhne0/0khSYNWyd0AwJ2VZktcD93dJV4EqTm1O
|
WZLXA/d3SVeBKk5tTgpNYIoAHfxjecLJUJDEk/51GFBpuHAP0WVUgPD0hWQ2dgsR
|
||||||
Ck1gigAd/GN5wslQkMST/nUYUGm4cA/RZVSA8PSFZDZ2CxHyRyHgaOQNBUmWG2gf
|
8kch4GjkDQVJlhtoHxMVK6yQNuoiqMJDamV1noJ82MJX/GUROjGTNCTyzlMP/q+M
|
||||||
ExUrrJA26iKowkNqZXWegnzYwlf8ZRE6MZM0JPLOUw/+r4ybI8ny+/U55s2sm0XZ
|
myPJ8vv1OebNrJtF2QnCbzXWuTd0qGgvzoBlmRcdbPVJLDezJr4c52klDHmnlRWx
|
||||||
CcJvNda5N3SoaC/OgGWZFx1s9UksN7MmvhznaSUMeaeVFbGC3nu9dsQhV9RxMwAR
|
gt57vXbEIVfUcTMAEQEAAYkBHwQYAQIACQUCVOQoaAIbDAAKCRDCHOZTtjnkGnUs
|
||||||
AQABiQEfBBgBAgAJBQJU5ChoAhsMAAoJEMIc5lO2OeQadSwH/07x1foZKkFRGMlj
|
B/9O8dX6GSpBURjJY8ApqHyhkqmfX7urnjiFen8B464ZX5EsijfvesW44cCL1oSn
|
||||||
wCmofKGSqZ9fu6ueOIV6fwHjrhlfkSyKN+96xbjhwIvWhKdSmWP/AsUqRDD/mTHw
|
Uplj/wLFKkQw/5kx8GTHZYJnV5BhL7wriQy+RZUM5fTlnnqZX1YS8rMenc4/xvAF
|
||||||
ZMdlgmdXkGEvvCuJDL5FlQzl9OWeeplfVhLysx6dzj/G8AUXlfEIGBvb8Q56d5dK
|
F5XxCBgb2/EOeneXSjKSHeB+L7fmCM0vMf68vkE0wyQDrtXFSX8KF9+MjHGfiB08
|
||||||
MpId4H4vt+YIzS8x/ry+QTTDJAOu1cVJfwoX34yMcZ+IHTzly2XKi4zQ41DyfrgY
|
5ctlyouM0ONQ8n64GJQqHVp2tdEbQXT2WONSX+MUns19quymQV10YMlTWLt3Q7jc
|
||||||
lCodWna10RtBdPZY41Jf4xSezX2q7KZBXXRgyVNYu3dDuNzhJAJ6jy7eMcb6urK6
|
4SQCeo8u3jHG+rqyup+93M+bmT5liG6eHAHnGQdAXzI/z1t+3StKGHVii8Wg8Kcb
|
||||||
n73cz5uZPmWIbp4cAecZB0BfMj/PW37dK0oYdWKLxaDwpxvIV7T45Y64Md2FCC+d
|
yFe0+OWOuDHdhQgvnZwtl4e3
|
||||||
nC2Xh7c=
|
=DwNF
|
||||||
=kzY9
|
|
||||||
-----END PGP PUBLIC KEY BLOCK-----
|
-----END PGP PUBLIC KEY BLOCK-----
|
||||||
|
|
||||||
pub C488A74FCAE540C6
|
pub C488A74FCAE540C6
|
||||||
|
@ -1674,43 +1671,6 @@ fW1AkBVEk6siyL8PXfxmj9ev3H9xiQVLyJ6HpdHTLVjHjFkgNOLd
|
||||||
=R7zg
|
=R7zg
|
||||||
-----END PGP PUBLIC KEY BLOCK-----
|
-----END PGP PUBLIC KEY BLOCK-----
|
||||||
|
|
||||||
pub D041CAD2E452550F
|
|
||||||
uid Deanna <deannagarcia@google.com>
|
|
||||||
|
|
||||||
sub 5199F3DAE89C332D
|
|
||||||
-----BEGIN PGP PUBLIC KEY BLOCK-----
|
|
||||||
Version: BCPG v1.68
|
|
||||||
|
|
||||||
mQGNBGCtdhoBDADdopjDt4eUNEqLJSw1ZICSR0oq09SOVtJSaSYdF8UiXjBfL1Ds
|
|
||||||
fhTDqSv5pT2a2gLj0OU3tFhWHvINLaKKCjQnHVcFXi2LTxt+XBOjRYkFjHVisbaZ
|
|
||||||
PZ6HnTMStPrvs+hQ168vU3VfYOsOLN22j53I/Ba+FA7E0G0bqkratuT5L7BTR1mC
|
|
||||||
fqDaeisWSCllfe6EEysaFF+/1RcRy+Yt+8ZWV0FZEF7UwQvqKHcYmlkqPIn3v/8y
|
|
||||||
J/yvmzIEtCQ1F+bvJbzaROmeJf254G2Uh7IfMYEm9WlqnGwNdbIhil7bdxq8Y/0H
|
|
||||||
XbQPaESxkki7yL5JTfH/+UzdklMe+Dga273L/cgzfjV3zJJ9vR94W5ABAbGYh4ZW
|
|
||||||
aKvNnT1m4vTbEMfo4r3NF2zc+K9Ly/JNaHqkR5M4SVElvN2lsC5KNUiRvExhg+h0
|
|
||||||
mKyx61mu3gUIrC1UOmqhtx7RzQQf7ESMdzmNHY0P93lR0Ic10fyli0wfl7A6q7+q
|
|
||||||
zV2a1V2k9Yg6B9sAEQEAAbQgRGVhbm5hIDxkZWFubmFnYXJjaWFAZ29vZ2xlLmNv
|
|
||||||
bT65AY0EYK12GgEMAMgP3//QeBsTS3IrfSp3m44el96X6BWona2yo4DvVyuwqfUL
|
|
||||||
ZE+Nhj7I+kEZLrA29AOySOD/6quJ4MIJZfq/Do920Di8/10WQ00OdCM1wH7bMz2U
|
|
||||||
vcSqsr0iOgQtycuUf7JOHSTME9vqk+C3Lhn0r59AVaRdXEe6zBgNZyzZJeCr5F8w
|
|
||||||
RhglPlwvhOGs2aLEqlCxFnY4pLayQFoQyw1lDjHIXHg5JtfOHvqiNXVDcGpyKLG8
|
|
||||||
SzImp62iL4sfuA0weVIQeS9kZiQabSYKvSf3TvNXYTgmFz/vjPbYhv9LTkBroTlV
|
|
||||||
g3l+UmAxLrHVuXMx0zX3jfNNHAqUjVhPYZhnifMkmGJgLeMIVqr5Q/tx8pzyYiiO
|
|
||||||
cqQ1zDg8ubJDGRue1JjlUGdw19OvhFDs+lydukt8Mmhb0gPkBLi2syZHgYHtEooX
|
|
||||||
PLwEsJ+SynZCFhZiWj8BsWNFJpaDd8ynNeWhMAcwi3B5ZeQiZaAlV0sItxsrzvbu
|
|
||||||
4ZYZtkjAkQdsaaTWSwARAQABiQG8BBgBCgAmFiEEaWthmaKp2MKc54zA0EHK0uRS
|
|
||||||
VQ8FAmCtdhoCGwwFCQPCZwAACgkQ0EHK0uRSVQ+G7wwAvaVPDgnM+i2pGQPwq6Mk
|
|
||||||
SzhKEG4H1pvBWyYR8H9D3p/dE33IjVu3EEy1h37Nzdyp46KtASGNe3KBodSsh6gv
|
|
||||||
PlV5pNGxMNbX6fo8ZGtS83C+6uTF1cYmuO1nmi8P4+7qtcNZg4xv/ujAZIC20kem
|
|
||||||
YKDth3FvPxEXsoxY+Ns7sxgd3SqoyLhjcyoczI8uyhim5nfvvbnEd6WrdiBPBtb/
|
|
||||||
F1h/nfqdFj2TcZkAlnzGnlVlgU8J60u6zE+9VvBm0lJR73Ar55mQEwarGFPL1a3/
|
|
||||||
A7ZEeNa0Dc3Oa5sKMYtxMlGKZ0WGUoGcDWiaDEsv5YyRnaSOaXKM1NkJCR013QAr
|
|
||||||
RcHrRBPo+0/RIZVE+b8oEcmGzdL8HNwnm7e06ruZryF9LQA5YBmCKE0urigmgEvC
|
|
||||||
zZsj/fMJ+OIZcAhE7UVae48GpW2kLATxmK01oSzvizIlmN3rVz2EnjOun2iuuEpF
|
|
||||||
/lmDbjK5n1r3f8npB1l1fT5cozzQJkPVYzhBWH1KXP5X
|
|
||||||
=nh9O
|
|
||||||
-----END PGP PUBLIC KEY BLOCK-----
|
|
||||||
|
|
||||||
pub D364ABAA39A47320
|
pub D364ABAA39A47320
|
||||||
sub 3F606403DCA455C8
|
sub 3F606403DCA455C8
|
||||||
-----BEGIN PGP PUBLIC KEY BLOCK-----
|
-----BEGIN PGP PUBLIC KEY BLOCK-----
|
||||||
|
|
Some files were not shown because too many files have changed in this diff Show more
Loading…
Reference in a new issue