Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Report user #8797

Merged
merged 3 commits into from
Apr 2, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions changelog.d/8796.misc
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
Add a report user action in the message bottom sheet and on the user profile page.
3 changes: 3 additions & 0 deletions library/ui-strings/src/main/res/values/strings.xml
Original file line number Diff line number Diff line change
Expand Up @@ -1953,8 +1953,11 @@
<string name="content_reported_as_spam_content">"This content was reported as spam.\n\nIf you don't want to see any more content from this user, you can ignore them to hide their messages."</string>
<string name="content_reported_as_inappropriate_title">"Reported as inappropriate"</string>
<string name="content_reported_as_inappropriate_content">"This content was reported as inappropriate.\n\nIf you don't want to see any more content from this user, you can ignore them to hide their messages."</string>
<string name="user_reported_as_inappropriate_title">"Reported user"</string>
<string name="user_reported_as_inappropriate_content">"The user has been reported.\n\nIf you don't want to see any more content from this user, you can ignore them to hide their messages."</string>

<string name="message_ignore_user">Ignore user</string>
<string name="message_report_user">Report user</string>

<string name="room_list_quick_actions_notifications_all_noisy">"All messages (noisy)"</string>
<string name="room_list_quick_actions_notifications_all">"All messages"</string>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -61,7 +61,8 @@ sealed class RoomDetailAction : VectorViewModelAction {
val senderId: String?,
val reason: String,
val spam: Boolean = false,
val inappropriate: Boolean = false
val inappropriate: Boolean = false,
val user: Boolean = false,
) : RoomDetailAction()

data class IgnoreUser(val userId: String?) : RoomDetailAction()
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -1345,6 +1345,16 @@ class TimelineFragment :
}
.show()
}
data.user -> {
MaterialAlertDialogBuilder(requireActivity(), R.style.ThemeOverlay_Vector_MaterialAlertDialog_NegativeDestructive)
.setTitle(R.string.user_reported_as_inappropriate_title)
.setMessage(R.string.user_reported_as_inappropriate_content)
.setPositiveButton(R.string.ok, null)
.setNegativeButton(R.string.block_user) { _, _ ->
timelineViewModel.handle(RoomDetailAction.IgnoreUser(data.senderId))
}
.show()
}
else -> {
MaterialAlertDialogBuilder(requireActivity(), R.style.ThemeOverlay_Vector_MaterialAlertDialog_NegativeDestructive)
.setTitle(R.string.content_reported_title)
Expand Down Expand Up @@ -1857,6 +1867,13 @@ class TimelineFragment :
is EventSharedAction.IgnoreUser -> {
action.senderId?.let { askConfirmationToIgnoreUser(it) }
}
is EventSharedAction.ReportUser -> {
timelineViewModel.handle(
RoomDetailAction.ReportContent(
action.eventId, action.senderId, "Reporting user ${action.senderId}", user = true
)
)
}
is EventSharedAction.OnUrlClicked -> {
onUrlClicked(action.url, action.title)
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -98,6 +98,9 @@ sealed class EventSharedAction(
data class IgnoreUser(val senderId: String?) :
EventSharedAction(R.string.message_ignore_user, R.drawable.ic_alert_triangle, true)

data class ReportUser(val eventId: String, val senderId: String?) :
EventSharedAction(R.string.message_report_user, R.drawable.ic_flag, true)

data class QuickReact(val eventId: String, val clickedOn: String, val add: Boolean) :
EventSharedAction(0, 0)

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -430,6 +430,12 @@ class MessageActionsViewModel @AssistedInject constructor(

add(EventSharedAction.Separator)
add(EventSharedAction.IgnoreUser(timelineEvent.root.senderId))
add(
EventSharedAction.ReportUser(
eventId = eventId,
senderId = timelineEvent.root.senderId,
)
)
}
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@ import im.vector.app.core.platform.VectorViewModelAction
sealed class RoomMemberProfileAction : VectorViewModelAction {
object RetryFetchingInfo : RoomMemberProfileAction()
object IgnoreUser : RoomMemberProfileAction()
object ReportUser : RoomMemberProfileAction()
data class BanOrUnbanUser(val reason: String?) : RoomMemberProfileAction()
data class KickUser(val reason: String?) : RoomMemberProfileAction()
object InviteUser : RoomMemberProfileAction()
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -39,6 +39,7 @@ class RoomMemberProfileController @Inject constructor(

interface Callback {
fun onIgnoreClicked()
fun onReportClicked()
fun onTapVerify()
fun onShowDeviceList()
fun onShowDeviceListNoCrossSigning()
Expand Down Expand Up @@ -225,7 +226,7 @@ class RoomMemberProfileController @Inject constructor(
title = stringProvider.getString(R.string.room_participants_action_invite),
destructive = false,
editable = false,
divider = ignoreActionTitle != null,
divider = true,
action = { callback?.onInviteClicked() }
)
}
Expand All @@ -235,10 +236,18 @@ class RoomMemberProfileController @Inject constructor(
title = ignoreActionTitle,
destructive = true,
editable = false,
divider = false,
divider = true,
action = { callback?.onIgnoreClicked() }
)
}
buildProfileAction(
id = "report",
title = stringProvider.getString(R.string.message_report_user),
destructive = true,
editable = false,
divider = false,
action = { callback?.onReportClicked() }
)
}
}

Expand Down Expand Up @@ -314,9 +323,9 @@ class RoomMemberProfileController @Inject constructor(
private fun RoomMemberProfileViewState.buildIgnoreActionTitle(): String? {
val isIgnored = isIgnored() ?: return null
return if (isIgnored) {
stringProvider.getString(R.string.unignore)
stringProvider.getString(R.string.room_participants_action_unignore_title)
} else {
stringProvider.getString(R.string.action_ignore)
stringProvider.getString(R.string.room_participants_action_ignore_title)
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -140,11 +140,20 @@ class RoomMemberProfileFragment :
is RoomMemberProfileViewEvents.OnIgnoreActionSuccess -> Unit
is RoomMemberProfileViewEvents.OnInviteActionSuccess -> Unit
RoomMemberProfileViewEvents.GoBack -> handleGoBack()
RoomMemberProfileViewEvents.OnReportActionSuccess -> handleReportSuccess()
}
}
setupLongClicks()
}

private fun handleReportSuccess() {
MaterialAlertDialogBuilder(requireContext())
.setTitle(R.string.user_reported_as_inappropriate_title)
.setMessage(R.string.user_reported_as_inappropriate_content)
.setPositiveButton(R.string.ok, null)
.show()
}

private fun setupLongClicks() {
headerViews.memberProfileNameView.copyOnLongClick()
headerViews.memberProfileIdView.copyOnLongClick()
Expand Down Expand Up @@ -301,6 +310,10 @@ class RoomMemberProfileFragment :
}
}

override fun onReportClicked() {
viewModel.handle(RoomMemberProfileAction.ReportUser)
}

override fun onTapVerify() {
viewModel.handle(RoomMemberProfileAction.VerifyUser)
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@ sealed class RoomMemberProfileViewEvents : VectorViewEvents {
data class Failure(val throwable: Throwable) : RoomMemberProfileViewEvents()

object OnIgnoreActionSuccess : RoomMemberProfileViewEvents()
object OnReportActionSuccess : RoomMemberProfileViewEvents()
object OnSetPowerLevelSuccess : RoomMemberProfileViewEvents()
object OnInviteActionSuccess : RoomMemberProfileViewEvents()
object OnKickActionSuccess : RoomMemberProfileViewEvents()
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -161,6 +161,7 @@ class RoomMemberProfileViewModel @AssistedInject constructor(
when (action) {
is RoomMemberProfileAction.RetryFetchingInfo -> handleRetryFetchProfileInfo()
is RoomMemberProfileAction.IgnoreUser -> handleIgnoreAction()
is RoomMemberProfileAction.ReportUser -> handleReportAction()
is RoomMemberProfileAction.VerifyUser -> prepareVerification()
is RoomMemberProfileAction.ShareRoomMemberProfile -> handleShareRoomMemberProfile()
is RoomMemberProfileAction.SetPowerLevel -> handleSetPowerLevel(action)
Expand All @@ -172,6 +173,25 @@ class RoomMemberProfileViewModel @AssistedInject constructor(
}
}

private fun handleReportAction() {
viewModelScope.launch {
val event = try {
// The API need an Event, use the latest Event.
val latestEventId = room?.roomSummary()?.latestPreviewableEvent?.eventId ?: return@launch
room.reportingService()
.reportContent(
eventId = latestEventId,
score = -100,
reason = "Reporting user ${initialState.userId} (eventId is not relevant)"
)
RoomMemberProfileViewEvents.OnReportActionSuccess
} catch (failure: Throwable) {
RoomMemberProfileViewEvents.Failure(failure)
}
_viewEvents.post(event)
}
}

private fun handleOpenOrCreateDm(action: RoomMemberProfileAction.OpenOrCreateDm) {
viewModelScope.launch {
_viewEvents.post(RoomMemberProfileViewEvents.Loading())
Expand Down
Loading