diff --git a/.eslintrc.json b/.eslintrc.json deleted file mode 100644 index 510dfaf1d3..0000000000 --- a/.eslintrc.json +++ /dev/null @@ -1,33 +0,0 @@ -{ - "env": { - "browser": true, - "commonjs": true, - "es6": true, - "node": true - }, - "parserOptions": { - "ecmaFeatures": { - "jsx": true - }, - "sourceType": "module" - }, - "rules": { - "no-const-assign": 1, - "no-extra-semi": 0, - "semi": 0, - "no-fallthrough": 0, - "no-empty": 0, - "no-mixed-spaces-and-tabs": 0, - "no-redeclare": 0, - "no-this-before-super": 1, - "no-undef": 0, - "no-unreachable": 1, - "no-unused-vars": 1, - "no-use-before-define": 0, - "constructor-super": 1, - "curly": 0, - "eqeqeq": 0, - "func-names": 0, - "valid-typeof": 1 - } -} \ No newline at end of file diff --git a/api/mutations/communityMember/removeCommunityMember.js b/api/mutations/communityMember/removeCommunityMember.js index f7d991cacb..c2c19d14c6 100644 --- a/api/mutations/communityMember/removeCommunityMember.js +++ b/api/mutations/communityMember/removeCommunityMember.js @@ -11,6 +11,10 @@ import { getChannelsByUserAndCommunity } from '../../models/channel'; import { isAuthedResolver as requireAuth } from '../../utils/permissions'; import { events } from 'shared/analytics'; import { trackQueue } from 'shared/bull/queues'; +import { + getThreadNotificationStatusForUser, + updateThreadNotificationStatusForUser, +} from '../../models/usersThreads'; type Input = { input: { @@ -105,6 +109,7 @@ export default requireAuth(async (_: any, args: Input, ctx: GraphQLContext) => { communityId, user.id ); + const leaveChannelsPromises = allChannelsInCommunity.map(channel => removeMemberInChannel(channel, user.id) ); @@ -112,7 +117,33 @@ export default requireAuth(async (_: any, args: Input, ctx: GraphQLContext) => { return await Promise.all([ removeMemberInCommunity(communityId, user.id), ...leaveChannelsPromises, - ]).then(() => community); + ]) + .then(async () => { + // if the community has a watercooler and the current user has a subscription + // to it, remove the subscription + if (community.watercoolerId) { + const threadId = community.watercoolerId; + const threadNotificationStatus = await getThreadNotificationStatusForUser( + threadId, + user.id + ); + if ( + !threadNotificationStatus || + !threadNotificationStatus.receiveNotifications + ) { + return; + } + + return await updateThreadNotificationStatusForUser( + threadId, + user.id, + false + ); + } + + return; + }) + .then(() => community); } trackQueue.add({ diff --git a/athena/queues/thread-notification.js b/athena/queues/thread-notification.js index 2a2d7ebf46..58500eddf7 100644 --- a/athena/queues/thread-notification.js +++ b/athena/queues/thread-notification.js @@ -114,7 +114,7 @@ export default async (job: Job) => { footer: 'Spectrum', footer_icon: 'https://spectrum.chat/img/apple-icon-57x57-precomposed.png', - ts: incomingThread.createdAt, + ts: new Date(incomingThread.createdAt).getTime() / 1000, color: '#4400CC', actions: [ { diff --git a/package.json b/package.json index e48fde2e8f..8cfb99eb4d 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "Spectrum", - "version": "2.4.20", + "version": "2.4.21", "license": "BSD-3-Clause", "devDependencies": { "babel-cli": "^6.24.1", diff --git a/shared/notification-to-text.js b/shared/notification-to-text.js index 99a9da7659..9a44c24346 100644 --- a/shared/notification-to-text.js +++ b/shared/notification-to-text.js @@ -160,7 +160,7 @@ const formatNotification = (incomingNotification, currentUserId) => { href = `/thread/${message.threadId}`; body = - message.messageType === 'draftjs' + message.messageType.toLowerCase() === 'draftjs' ? toPlainText(toState(message.content.body)) : message.content.body; break; @@ -170,7 +170,7 @@ const formatNotification = (incomingNotification, currentUserId) => { href = `/thread/${thread.id}`; body = - thread.type === 'draftjs' + thread.type.toLowerCase() === 'draftjs' ? toPlainText(toState(thread.content.body)) : thread.content.body; break; diff --git a/src/components/badges/style.js b/src/components/badges/style.js index 0ffe1bb4fa..5486431760 100644 --- a/src/components/badges/style.js +++ b/src/components/badges/style.js @@ -4,7 +4,6 @@ import { Tooltip, Gradient } from '../globals'; export const Span = styled.span` display: inline; - align-self: center; color: ${({ theme }) => theme.text.reverse}; background-color: ${props => props.theme.text.alt}; text-transform: uppercase; diff --git a/src/components/message/authorByline.js b/src/components/message/authorByline.js index cae992406b..245c9efba9 100644 --- a/src/components/message/authorByline.js +++ b/src/components/message/authorByline.js @@ -3,7 +3,13 @@ import * as React from 'react'; import { convertTimestampToTime } from 'shared/time-formatting'; import Link from 'src/components/link'; import Badge from '../badges'; -import { Byline, Name, Username, GutterTimestamp } from './style'; +import { + Byline, + Name, + Username, + GutterTimestamp, + BadgesContainer, +} from './style'; import { UserHoverProfile } from 'src/components/hoverProfile'; import ConditionalWrap from 'src/components/conditionalWrap'; import { MessagesContext } from 'src/components/messageGroup'; @@ -26,7 +32,10 @@ export default (props: Props) => { ( - + e.stopPropagation()} @@ -40,17 +49,19 @@ export default (props: Props) => { {user.name} - {roles && - roles.map((role, index) => ( - e.stopPropagation()} - /> - ))} - {user.isPro && ( - e.stopPropagation()} /> - )} + + {roles && + roles.map((role, index) => ( + e.stopPropagation()} + /> + ))} + {user.isPro && ( + e.stopPropagation()} /> + )} + props.theme.text.default}; max-width: 100%; position: relative; + flex-wrap: wrap; + + a { + display: flex; + flex-wrap: wrap; + } + + @media (max-width: 400px) { + flex-direction: column; + align-items: flex-start; + } `; export const Name = styled.span` @@ -27,11 +38,16 @@ export const Name = styled.span` font-size: 15px; color: ${({ theme }) => theme.text.default}; margin-right: 2px; + display: flex; &:hover { color: ${({ theme }) => theme.text.default}; cursor: pointer; } + + @media (max-width: 400px) { + line-height: 1.4; + } `; export const Username = styled(Name)` @@ -39,6 +55,11 @@ export const Username = styled(Name)` margin-left: 2px; margin-right: 2px; color: ${props => props.theme.text.alt}; + display: flex; + + @media (max-width: 400px) { + line-height: 1.4; + } `; export const ActionsContainer = styled.span` @@ -108,6 +129,10 @@ export const GutterTimestamp = styled(Link)` color: ${props => props.theme.text.placeholder}; opacity: 0; ${Truncate}; + + @media (max-width: 400px) { + display: none !important; + } `; export const OuterMessageContainer = styled.div` @@ -384,3 +409,11 @@ export const QuoteWrapper = styled.div` color: ${props => props.theme.text.alt}; } `; + +export const BadgesContainer = styled.div` + display: flex; + + @media (max-width: 400px) { + margin-top: 4px; + } +`; diff --git a/src/views/directMessages/components/style.js b/src/views/directMessages/components/style.js index 240ab6870f..e1e1a82b28 100644 --- a/src/views/directMessages/components/style.js +++ b/src/views/directMessages/components/style.js @@ -283,7 +283,7 @@ export const SearchResultsDropdown = styled.ul` width: 320px; max-height: 420px; overflow-y: scroll; - z-index: ${zIndex.dropdown}; + z-index: ${zIndex.dropDown}; @media (max-width: 768px) { width: 100%;