Skip to content

Commit

Permalink
Merge pull request #387 from ReseauEntourage/feat/EN-7441-Suspicious-…
Browse files Browse the repository at this point in the history
…Messages

[EN-7441] feat(Messaging): handle suspicious messages
  • Loading branch information
guillobits authored Nov 19, 2024
2 parents d99e48f + 93984f3 commit c50a27c
Show file tree
Hide file tree
Showing 7 changed files with 81 additions and 6 deletions.
2 changes: 2 additions & 0 deletions .env.dist
Original file line number Diff line number Diff line change
Expand Up @@ -72,3 +72,5 @@ MAILJET_CONTACT_EMAIL=
PUSHER_API_KEY=
ASSOCIATION_APPOINTMENT=
LINKEDIN_PARTNER_ID=
#MESSAGING
MESSAGING_FORBIDDEN_EXPRESSIONS=""
Original file line number Diff line number Diff line change
Expand Up @@ -8,10 +8,12 @@ import { useOnReportMessagingConversationFormSubmit } from './useOnReportMessagi

interface MessagingConversationReportModalProps {
conversationId: string;
content?: string | null;
}

export const MessagingConversationReportModal = ({
conversationId,
content = null,
}: MessagingConversationReportModalProps) => {
const { onSubmit } = useOnReportMessagingConversationFormSubmit(
async (conversationReportDto: ConversationReportDto) => {
Expand Down Expand Up @@ -39,10 +41,10 @@ export const MessagingConversationReportModal = ({
onSubmit: handleReportUserSubmit,
defaultValues: {
reason: '',
comment: '',
comment: content || '',
},
};
}, [handleReportUserSubmit]);
}, [content, handleReportUserSubmit]);

return <ModalEdit {...updateUserModalProps} />;
};
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,10 @@ import styled from 'styled-components';
import { COLORS } from 'src/constants/styles';

export const MessageContainer = styled.div`
display: flex;
flex-direction: column;
box-sizing: border-box;
gap: 5px;
width: 100%;
* {
margin: 0;
Expand Down Expand Up @@ -44,3 +47,15 @@ export const StyledMessage = styled.div`
background: ${COLORS.hoverBlue};
}
`;

export const StyledWarning = styled.div`
display: flex;
flex-direction: row;
gap: 5px;
align-items: center;
a {
color: ${COLORS.lightRed};
text-decoration: underline;
}
`;
Original file line number Diff line number Diff line change
@@ -1,21 +1,39 @@
/* eslint-disable react/no-danger */
import moment from 'moment';
import React from 'react';
import React, { useEffect } from 'react';
import { useSelector } from 'react-redux';
import { MessagingConversationReportModal } from '../MessagingConversationReport/MessagingConversationReportModal';
import { Message } from 'src/api/types';
import { openModal } from 'src/components/modals/Modal';
import { LucidIcon } from 'src/components/utils/Icons/LucidIcon';
import { Typography } from 'src/components/utils/Typography';
import { COLORS } from 'src/constants/styles';
import { selectCurrentUserId } from 'src/use-cases/current-user';
import { selectSelectedConversationId } from 'src/use-cases/messaging';
import { escapeHtml, linkify } from 'src/utils';
import { MessageContainer, StyledMessage } from './MessagingMessage.styles';
import { isSuspiciousMessage } from 'src/utils/SuspiciousContent';
import {
MessageContainer,
StyledMessage,
StyledWarning,
} from './MessagingMessage.styles';
import { MessagingMessageSuspiciousModal } from './MessagingMessageSuspiciousModal/MessagingMessageSuspiciousModal';

export interface MessagingMessageProps {
message: Message;
}

export const MessagingMessage = ({ message }: MessagingMessageProps) => {
const selectedConversationId = useSelector(selectSelectedConversationId);
const currentUserId = useSelector(selectCurrentUserId);
const isOwnMessage = message.author.id === currentUserId;
const [isSuspicious, setIsSuspicious] = React.useState(false);

useEffect(() => {
if (message.content) {
setIsSuspicious(isSuspiciousMessage(message.content));
}
}, [message.content]);

const handleClick = (event: React.MouseEvent<HTMLDivElement>) => {
const whitelist = process.env.LINKIFY_SAFE_DOMAINS?.split(',') || [];
Expand All @@ -35,6 +53,18 @@ export const MessagingMessage = ({ message }: MessagingMessageProps) => {
}
};

const reportMessage = () => {
const reportContent = `Le message suivant me semble suspicieux : "${message.content}"`;
if (selectedConversationId) {
openModal(
<MessagingConversationReportModal
conversationId={selectedConversationId}
content={reportContent}
/>
);
}
};

return (
<MessageContainer className={isOwnMessage ? 'own-message' : ''}>
<StyledMessage className={isOwnMessage ? 'own-message' : ''}>
Expand All @@ -45,6 +75,16 @@ export const MessagingMessage = ({ message }: MessagingMessageProps) => {
onClick={handleClick}
/>
</StyledMessage>
{!isOwnMessage && isSuspicious && (
<StyledWarning>
<LucidIcon name="TriangleAlert" color={COLORS.lightRed} />
<Typography size="small" color="lightRed">
Attention, ce message est peut-être malveillant. Nous vous
recommandons de ne pas communiquer vos coordonnées et de nous&nbsp;
<a onClick={reportMessage}>signaler ce message</a> en cas de doute
</Typography>
</StyledWarning>
)}
<p className="message-date">{moment(message.createdAt).format('LLL')}</p>
</MessageContainer>
);
Expand Down
4 changes: 3 additions & 1 deletion src/components/forms/schemas/formReportUser.ts
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@ export const formReportUser: FormSchema<{
reason: string;
comment: string;
}> = {
id: 'form-add-organization',
id: 'form-report-user',
fields: [
{
id: 'reason',
Expand All @@ -14,13 +14,15 @@ export const formReportUser: FormSchema<{
title: 'Raison du signalement *',
options: USER_REPORT_REASONS,
isRequired: true,
showLabel: true,
},
{
id: 'comment',
name: 'comment',
component: 'text-input',
title: 'Commentaire *',
isRequired: true,
showLabel: true,
},
],
};
3 changes: 2 additions & 1 deletion src/components/utils/Typography/Typography.styles.ts
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@ export interface TypographyProps {
children: React.ReactNode;
size?: 'small' | 'normal' | 'large';
weight?: 'normal' | 'bold';
color?: 'lighter' | 'light' | 'normal' | 'blue' | 'white';
color?: 'lighter' | 'light' | 'normal' | 'blue' | 'white' | 'lightRed';
variant?: 'normal' | 'italic';
center?: boolean;
}
Expand All @@ -23,6 +23,7 @@ const colors: { [K in NonNullable<TypographyProps['color']>]: string } = {
light: COLORS.darkGray,
normal: COLORS.black,
blue: COLORS.primaryBlue,
lightRed: COLORS.lightRed,
};

export const StyledTypography = styled.div<TypographyProps>`
Expand Down
13 changes: 13 additions & 0 deletions src/utils/SuspiciousContent.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
export const isSuspiciousMessage = (message: string): boolean => {
const forbiddenExpressions =
process.env.MESSAGING_FORBIDDEN_EXPRESSIONS?.split(',') || [];

if (forbiddenExpressions.length === 0) {
return false;
}
const forbiddenPattern = new RegExp(
`\\b(${forbiddenExpressions.map((expr) => expr.trim()).join('|')})\\b`,
'i'
);
return forbiddenPattern.test(message);
};

0 comments on commit c50a27c

Please sign in to comment.