X-Git-Url: http://these/git/?a=blobdiff_plain;f=src%2Fshared%2Fcomponents%2Fperson%2Finbox.tsx;h=731667c0ddef6108f8fe1a307a4b56fdc66d5338;hb=2b1af707c3df6126b3e6890106c03c60ad49b1be;hp=b718e9acb1cf53719f3dc70c0c1b3b47f557f268;hpb=f61037f5d89f12818c8100f907a98b74e980112a;p=lemmy-ui.git diff --git a/src/shared/components/person/inbox.tsx b/src/shared/components/person/inbox.tsx index b718e9a..731667c 100644 --- a/src/shared/components/person/inbox.tsx +++ b/src/shared/components/person/inbox.tsx @@ -1,49 +1,72 @@ import { Component, linkEvent } from "inferno"; import { - BlockPersonResponse, + AddAdmin, + AddModToCommunity, + BanFromCommunity, + BanFromCommunityResponse, + BanPerson, + BanPersonResponse, + BlockPerson, + CommentId, CommentReplyResponse, CommentReplyView, CommentReportResponse, CommentResponse, CommentSortType, CommentView, + CreateComment, + CreateCommentLike, + CreateCommentReport, + CreatePrivateMessage, + CreatePrivateMessageReport, + DeleteComment, + DeletePrivateMessage, + DistinguishComment, + EditComment, + EditPrivateMessage, GetPersonMentions, GetPersonMentionsResponse, GetPrivateMessages, GetReplies, GetRepliesResponse, GetSiteResponse, + MarkCommentReplyAsRead, + MarkPersonMentionAsRead, + MarkPrivateMessageAsRead, PersonMentionResponse, PersonMentionView, - PostReportResponse, PrivateMessageReportResponse, PrivateMessageResponse, PrivateMessageView, PrivateMessagesResponse, - UserOperation, - wsJsonToRes, - wsUserOp, + PurgeComment, + PurgeItemResponse, + PurgePerson, + PurgePost, + RemoveComment, + SaveComment, + TransferCommunity, } from "lemmy-js-client"; -import { Subscription } from "rxjs"; import { i18n } from "../../i18next"; import { CommentViewType, InitialFetchRequest } from "../../interfaces"; -import { UserService, WebSocketService } from "../../services"; +import { UserService } from "../../services"; +import { FirstLoadService } from "../../services/FirstLoadService"; +import { HttpService, RequestState } from "../../services/HttpService"; import { commentsToFlatNodes, - createCommentLikeRes, - editCommentRes, + editCommentReply, + editMention, + editPrivateMessage, + editWith, enableDownvotes, fetchLimit, - isBrowser, + getCommentParentId, myAuth, + myAuthRequired, relTags, - saveCommentRes, setIsoData, - setupTippy, toast, updatePersonBlock, - wsClient, - wsSubscribe, } from "../../utils"; import { CommentNodes } from "../comment/comment-nodes"; import { CommentSortSelect } from "../common/comment-sort-select"; @@ -79,30 +102,31 @@ type ReplyType = { interface InboxState { unreadOrAll: UnreadOrAll; messageType: MessageType; - replies: CommentReplyView[]; - mentions: PersonMentionView[]; - messages: PrivateMessageView[]; - combined: ReplyType[]; + repliesRes: RequestState; + mentionsRes: RequestState; + messagesRes: RequestState; + markAllAsReadRes: RequestState; sort: CommentSortType; page: number; siteRes: GetSiteResponse; - loading: boolean; + finished: Map; + isIsomorphic: boolean; } export class Inbox extends Component { private isoData = setIsoData(this.context); - private subscription?: Subscription; state: InboxState = { unreadOrAll: UnreadOrAll.Unread, messageType: MessageType.All, - replies: [], - mentions: [], - messages: [], - combined: [], sort: "New", page: 1, siteRes: this.isoData.site_res, - loading: true, + repliesRes: { state: "empty" }, + mentionsRes: { state: "empty" }, + messagesRes: { state: "empty" }, + markAllAsReadRes: { state: "empty" }, + finished: new Map(), + isIsomorphic: false, }; constructor(props: any, context: any) { @@ -111,32 +135,48 @@ export class Inbox extends Component { this.handleSortChange = this.handleSortChange.bind(this); this.handlePageChange = this.handlePageChange.bind(this); - this.parseMessage = this.parseMessage.bind(this); - this.subscription = wsSubscribe(this.parseMessage); + this.handleCreateComment = this.handleCreateComment.bind(this); + this.handleEditComment = this.handleEditComment.bind(this); + this.handleSaveComment = this.handleSaveComment.bind(this); + this.handleBlockPerson = this.handleBlockPerson.bind(this); + this.handleDeleteComment = this.handleDeleteComment.bind(this); + this.handleRemoveComment = this.handleRemoveComment.bind(this); + this.handleCommentVote = this.handleCommentVote.bind(this); + this.handleAddModToCommunity = this.handleAddModToCommunity.bind(this); + this.handleAddAdmin = this.handleAddAdmin.bind(this); + this.handlePurgePerson = this.handlePurgePerson.bind(this); + this.handlePurgeComment = this.handlePurgeComment.bind(this); + this.handleCommentReport = this.handleCommentReport.bind(this); + this.handleDistinguishComment = this.handleDistinguishComment.bind(this); + this.handleTransferCommunity = this.handleTransferCommunity.bind(this); + this.handleCommentReplyRead = this.handleCommentReplyRead.bind(this); + this.handlePersonMentionRead = this.handlePersonMentionRead.bind(this); + this.handleBanFromCommunity = this.handleBanFromCommunity.bind(this); + this.handleBanPerson = this.handleBanPerson.bind(this); + + this.handleDeleteMessage = this.handleDeleteMessage.bind(this); + this.handleMarkMessageAsRead = this.handleMarkMessageAsRead.bind(this); + this.handleMessageReport = this.handleMessageReport.bind(this); + this.handleCreateMessage = this.handleCreateMessage.bind(this); + this.handleEditMessage = this.handleEditMessage.bind(this); // Only fetch the data if coming from another route - if (this.isoData.path == this.context.router.route.match.url) { + if (FirstLoadService.isFirstLoad) { + const [repliesRes, mentionsRes, messagesRes] = this.isoData.routeData; + this.state = { ...this.state, - replies: - (this.isoData.routeData[0] as GetRepliesResponse).replies || [], - mentions: - (this.isoData.routeData[1] as GetPersonMentionsResponse).mentions || - [], - messages: - (this.isoData.routeData[2] as PrivateMessagesResponse) - .private_messages || [], - loading: false, + repliesRes, + mentionsRes, + messagesRes, + isIsomorphic: true, }; - this.state = { ...this.state, combined: this.buildCombined() }; - } else { - this.refetch(); } } - componentWillUnmount() { - if (isBrowser()) { - this.subscription?.unsubscribe(); + async componentDidMount() { + if (!this.state.isIsomorphic) { + await this.refetch(); } } @@ -149,67 +189,94 @@ export class Inbox extends Component { : ""; } + get hasUnreads(): boolean { + if (this.state.unreadOrAll == UnreadOrAll.Unread) { + const { repliesRes, mentionsRes, messagesRes } = this.state; + const replyCount = + repliesRes.state == "success" ? repliesRes.data.replies.length : 0; + const mentionCount = + mentionsRes.state == "success" ? mentionsRes.data.mentions.length : 0; + const messageCount = + messagesRes.state == "success" + ? messagesRes.data.private_messages.length + : 0; + + return replyCount + mentionCount + messageCount > 0; + } else { + return false; + } + } + render() { const auth = myAuth(); const inboxRss = auth ? `/feeds/inbox/${auth}.xml` : undefined; return (
- {this.state.loading ? ( -
- -
- ) : ( -
-
- -
- {i18n.t("inbox")} - {inboxRss && ( - - - - - - - )} -
- {this.state.replies.length + - this.state.mentions.length + - this.state.messages.length > - 0 && - this.state.unreadOrAll == UnreadOrAll.Unread && ( - +
+
+ +
+ {i18n.t("inbox")} + {inboxRss && ( + + + + + + + )} +
+ {this.hasUnreads && ( +
+ + )} + {this.selects()} + {this.section} +
- )} +
); } + get section() { + switch (this.state.messageType) { + case MessageType.All: { + return this.all(); + } + case MessageType.Replies: { + return this.replies(); + } + case MessageType.Mentions: { + return this.mentions(); + } + case MessageType.Messages: { + return this.messages(); + } + default: { + return null; + } + } + } + unreadOrAllRadios() { return (
@@ -343,15 +410,20 @@ export class Inbox extends Component { } buildCombined(): ReplyType[] { - const replies: ReplyType[] = this.state.replies.map(r => - this.replyToReplyType(r) - ); - const mentions: ReplyType[] = this.state.mentions.map(r => - this.mentionToReplyType(r) - ); - const messages: ReplyType[] = this.state.messages.map(r => - this.messageToReplyType(r) - ); + const replies: ReplyType[] = + this.state.repliesRes.state == "success" + ? this.state.repliesRes.data.replies.map(this.replyToReplyType) + : []; + const mentions: ReplyType[] = + this.state.mentionsRes.state == "success" + ? this.state.mentionsRes.data.mentions.map(this.mentionToReplyType) + : []; + const messages: ReplyType[] = + this.state.messagesRes.state == "success" + ? this.state.messagesRes.data.private_messages.map( + this.messageToReplyType + ) + : []; return [...replies, ...mentions, ...messages].sort((a, b) => b.published.localeCompare(a.published) @@ -368,6 +440,7 @@ export class Inbox extends Component { { comment_view: i.view as CommentView, children: [], depth: 0 }, ]} viewType={CommentViewType.Flat} + finished={this.state.finished} noIndent markable showCommunity @@ -375,6 +448,24 @@ export class Inbox extends Component { enableDownvotes={enableDownvotes(this.state.siteRes)} allLanguages={this.state.siteRes.all_languages} siteLanguages={this.state.siteRes.discussion_languages} + onSaveComment={this.handleSaveComment} + onBlockPerson={this.handleBlockPerson} + onDeleteComment={this.handleDeleteComment} + onRemoveComment={this.handleRemoveComment} + onCommentVote={this.handleCommentVote} + onCommentReport={this.handleCommentReport} + onDistinguishComment={this.handleDistinguishComment} + onAddModToCommunity={this.handleAddModToCommunity} + onAddAdmin={this.handleAddAdmin} + onTransferCommunity={this.handleTransferCommunity} + onPurgeComment={this.handlePurgeComment} + onPurgePerson={this.handlePurgePerson} + onCommentReplyRead={this.handleCommentReplyRead} + onPersonMentionRead={this.handlePersonMentionRead} + onBanPersonFromCommunity={this.handleBanFromCommunity} + onBanPerson={this.handleBanPerson} + onCreateComment={this.handleCreateComment} + onEditComment={this.handleEditComment} /> ); case ReplyEnum.Mention: @@ -388,6 +479,7 @@ export class Inbox extends Component { depth: 0, }, ]} + finished={this.state.finished} viewType={CommentViewType.Flat} noIndent markable @@ -396,6 +488,24 @@ export class Inbox extends Component { enableDownvotes={enableDownvotes(this.state.siteRes)} allLanguages={this.state.siteRes.all_languages} siteLanguages={this.state.siteRes.discussion_languages} + onSaveComment={this.handleSaveComment} + onBlockPerson={this.handleBlockPerson} + onDeleteComment={this.handleDeleteComment} + onRemoveComment={this.handleRemoveComment} + onCommentVote={this.handleCommentVote} + onCommentReport={this.handleCommentReport} + onDistinguishComment={this.handleDistinguishComment} + onAddModToCommunity={this.handleAddModToCommunity} + onAddAdmin={this.handleAddAdmin} + onTransferCommunity={this.handleTransferCommunity} + onPurgeComment={this.handlePurgeComment} + onPurgePerson={this.handlePurgePerson} + onCommentReplyRead={this.handleCommentReplyRead} + onPersonMentionRead={this.handlePersonMentionRead} + onBanPersonFromCommunity={this.handleBanFromCommunity} + onBanPerson={this.handleBanPerson} + onCreateComment={this.handleCreateComment} + onEditComment={this.handleEditComment} /> ); case ReplyEnum.Message: @@ -403,6 +513,11 @@ export class Inbox extends Component { ); default: @@ -411,92 +526,184 @@ export class Inbox extends Component { } all() { - return
{this.state.combined.map(i => this.renderReplyType(i))}
; + if ( + this.state.repliesRes.state == "loading" || + this.state.mentionsRes.state == "loading" || + this.state.messagesRes.state == "loading" + ) { + return ( +
+ +
+ ); + } else { + return ( +
{this.buildCombined().map(r => this.renderReplyType(r))}
+ ); + } } replies() { - return ( -
- -
- ); + switch (this.state.repliesRes.state) { + case "loading": + return ( +
+ +
+ ); + case "success": { + const replies = this.state.repliesRes.data.replies; + return ( +
+ +
+ ); + } + } } mentions() { - return ( -
- {this.state.mentions.map(umv => ( - - ))} -
- ); + switch (this.state.mentionsRes.state) { + case "loading": + return ( +
+ +
+ ); + case "success": { + const mentions = this.state.mentionsRes.data.mentions; + return ( +
+ {mentions.map(umv => ( + + ))} +
+ ); + } + } } messages() { - return ( -
- {this.state.messages.map(pmv => ( - - ))} -
- ); + switch (this.state.messagesRes.state) { + case "loading": + return ( +
+ +
+ ); + case "success": { + const messages = this.state.messagesRes.data.private_messages; + return ( +
+ {messages.map(pmv => ( + + ))} +
+ ); + } + } } - handlePageChange(page: number) { + async handlePageChange(page: number) { this.setState({ page }); - this.refetch(); + await this.refetch(); } - handleUnreadOrAllChange(i: Inbox, event: any) { + async handleUnreadOrAllChange(i: Inbox, event: any) { i.setState({ unreadOrAll: Number(event.target.value), page: 1 }); - i.refetch(); + await i.refetch(); } - handleMessageTypeChange(i: Inbox, event: any) { + async handleMessageTypeChange(i: Inbox, event: any) { i.setState({ messageType: Number(event.target.value), page: 1 }); - i.refetch(); + await i.refetch(); } - static fetchInitialData(req: InitialFetchRequest): Promise[] { - const promises: Promise[] = []; + static fetchInitialData({ + client, + auth, + }: InitialFetchRequest): Promise[] { + const promises: Promise>[] = []; const sort: CommentSortType = "New"; - const auth = req.auth; if (auth) { // It can be /u/me, or /username/1 const repliesForm: GetReplies = { - sort: "New", + sort, unread_only: true, page: 1, limit: fetchLimit, auth, }; - promises.push(req.client.getReplies(repliesForm)); + promises.push(client.getReplies(repliesForm)); const personMentionsForm: GetPersonMentions = { sort, @@ -505,7 +712,7 @@ export class Inbox extends Component { limit: fetchLimit, auth, }; - promises.push(req.client.getPersonMentions(personMentionsForm)); + promises.push(client.getPersonMentions(personMentionsForm)); const privateMessagesForm: GetPrivateMessages = { unread_only: true, @@ -513,353 +720,350 @@ export class Inbox extends Component { limit: fetchLimit, auth, }; - promises.push(req.client.getPrivateMessages(privateMessagesForm)); + promises.push(client.getPrivateMessages(privateMessagesForm)); + } else { + promises.push( + Promise.resolve({ state: "empty" }), + Promise.resolve({ state: "empty" }), + Promise.resolve({ state: "empty" }) + ); } return promises; } - refetch() { + async refetch() { const sort = this.state.sort; const unread_only = this.state.unreadOrAll == UnreadOrAll.Unread; const page = this.state.page; const limit = fetchLimit; - const auth = myAuth(); + const auth = myAuthRequired(); - if (auth) { - const repliesForm: GetReplies = { + this.setState({ repliesRes: { state: "loading" } }); + this.setState({ + repliesRes: await HttpService.client.getReplies({ sort, unread_only, page, limit, auth, - }; - WebSocketService.Instance.send(wsClient.getReplies(repliesForm)); + }), + }); - const personMentionsForm: GetPersonMentions = { + this.setState({ mentionsRes: { state: "loading" } }); + this.setState({ + mentionsRes: await HttpService.client.getPersonMentions({ sort, unread_only, page, limit, auth, - }; - WebSocketService.Instance.send( - wsClient.getPersonMentions(personMentionsForm) - ); + }), + }); - const privateMessagesForm: GetPrivateMessages = { + this.setState({ messagesRes: { state: "loading" } }); + this.setState({ + messagesRes: await HttpService.client.getPrivateMessages({ unread_only, page, limit, auth, - }; - WebSocketService.Instance.send( - wsClient.getPrivateMessages(privateMessagesForm) - ); - } + }), + }); } - handleSortChange(val: CommentSortType) { + async handleSortChange(val: CommentSortType) { this.setState({ sort: val, page: 1 }); - this.refetch(); + await this.refetch(); } - markAllAsRead(i: Inbox) { - const auth = myAuth(); - if (auth) { - WebSocketService.Instance.send( - wsClient.markAllAsRead({ - auth, - }) - ); - i.setState({ replies: [], mentions: [], messages: [] }); - i.setState({ combined: i.buildCombined() }); - UserService.Instance.unreadInboxCountSub.next(0); - window.scrollTo(0, 0); - i.setState(i.state); + async handleMarkAllAsRead(i: Inbox) { + i.setState({ markAllAsReadRes: { state: "loading" } }); + + i.setState({ + markAllAsReadRes: await HttpService.client.markAllAsRead({ + auth: myAuthRequired(), + }), + }); + + if (i.state.markAllAsReadRes.state == "success") { + i.setState({ + repliesRes: { state: "empty" }, + mentionsRes: { state: "empty" }, + messagesRes: { state: "empty" }, + }); } } - sendUnreadCount(read: boolean) { - const urcs = UserService.Instance.unreadInboxCountSub; - if (read) { - urcs.next(urcs.getValue() - 1); - } else { - urcs.next(urcs.getValue() + 1); + async handleAddModToCommunity(form: AddModToCommunity) { + // TODO not sure what to do here + HttpService.client.addModToCommunity(form); + } + + async handlePurgePerson(form: PurgePerson) { + const purgePersonRes = await HttpService.client.purgePerson(form); + this.purgeItem(purgePersonRes); + } + + async handlePurgeComment(form: PurgeComment) { + const purgeCommentRes = await HttpService.client.purgeComment(form); + this.purgeItem(purgeCommentRes); + } + + async handlePurgePost(form: PurgePost) { + const purgeRes = await HttpService.client.purgePost(form); + this.purgeItem(purgeRes); + } + + async handleBlockPerson(form: BlockPerson) { + const blockPersonRes = await HttpService.client.blockPerson(form); + if (blockPersonRes.state == "success") { + updatePersonBlock(blockPersonRes.data); } } - parseMessage(msg: any) { - const op = wsUserOp(msg); - console.log(msg); - if (msg.error) { - toast(i18n.t(msg.error), "danger"); - return; - } else if (msg.reconnect) { - this.refetch(); - } else if (op == UserOperation.GetReplies) { - const data = wsJsonToRes(msg); - this.setState({ replies: data.replies }); - this.setState({ combined: this.buildCombined(), loading: false }); - window.scrollTo(0, 0); - setupTippy(); - } else if (op == UserOperation.GetPersonMentions) { - const data = wsJsonToRes(msg); - this.setState({ mentions: data.mentions }); - this.setState({ combined: this.buildCombined() }); - window.scrollTo(0, 0); - setupTippy(); - } else if (op == UserOperation.GetPrivateMessages) { - const data = wsJsonToRes(msg); - this.setState({ messages: data.private_messages }); - this.setState({ combined: this.buildCombined() }); - window.scrollTo(0, 0); - setupTippy(); - } else if (op == UserOperation.EditPrivateMessage) { - const data = wsJsonToRes(msg); - const found = this.state.messages.find( - m => - m.private_message.id === data.private_message_view.private_message.id - ); - if (found) { - const combinedView = this.state.combined.find( - i => i.id == data.private_message_view.private_message.id - )?.view as PrivateMessageView | undefined; - if (combinedView) { - found.private_message.content = combinedView.private_message.content = - data.private_message_view.private_message.content; - found.private_message.updated = combinedView.private_message.updated = - data.private_message_view.private_message.updated; - } + async handleCreateComment(form: CreateComment) { + const res = await HttpService.client.createComment(form); + + if (res.state === "success") { + toast(i18n.t("reply_sent")); + this.findAndUpdateComment(res); + } + + return res; + } + + async handleEditComment(form: EditComment) { + const res = await HttpService.client.editComment(form); + + if (res.state === "success") { + toast(i18n.t("edit")); + this.findAndUpdateComment(res); + } else if (res.state === "failed") { + toast(res.msg, "danger"); + } + + return res; + } + + async handleDeleteComment(form: DeleteComment) { + const res = await HttpService.client.deleteComment(form); + if (res.state == "success") { + toast(i18n.t("deleted")); + this.findAndUpdateComment(res); + } + } + + async handleRemoveComment(form: RemoveComment) { + const res = await HttpService.client.removeComment(form); + if (res.state == "success") { + toast(i18n.t("remove_comment")); + this.findAndUpdateComment(res); + } + } + + async handleSaveComment(form: SaveComment) { + const res = await HttpService.client.saveComment(form); + this.findAndUpdateComment(res); + } + + async handleCommentVote(form: CreateCommentLike) { + const res = await HttpService.client.likeComment(form); + this.findAndUpdateComment(res); + } + + async handleCommentReport(form: CreateCommentReport) { + const reportRes = await HttpService.client.createCommentReport(form); + this.reportToast(reportRes); + } + + async handleDistinguishComment(form: DistinguishComment) { + const res = await HttpService.client.distinguishComment(form); + this.findAndUpdateComment(res); + } + + async handleAddAdmin(form: AddAdmin) { + const addAdminRes = await HttpService.client.addAdmin(form); + + if (addAdminRes.state === "success") { + this.setState(s => ((s.siteRes.admins = addAdminRes.data.admins), s)); + } + } + + async handleTransferCommunity(form: TransferCommunity) { + await HttpService.client.transferCommunity(form); + toast(i18n.t("transfer_community")); + } + + async handleCommentReplyRead(form: MarkCommentReplyAsRead) { + const res = await HttpService.client.markCommentReplyAsRead(form); + this.findAndUpdateCommentReply(res); + } + + async handlePersonMentionRead(form: MarkPersonMentionAsRead) { + const res = await HttpService.client.markPersonMentionAsRead(form); + this.findAndUpdateMention(res); + } + + async handleBanFromCommunity(form: BanFromCommunity) { + const banRes = await HttpService.client.banFromCommunity(form); + this.updateBanFromCommunity(banRes); + } + + async handleBanPerson(form: BanPerson) { + const banRes = await HttpService.client.banPerson(form); + this.updateBan(banRes); + } + + async handleDeleteMessage(form: DeletePrivateMessage) { + const res = await HttpService.client.deletePrivateMessage(form); + this.findAndUpdateMessage(res); + } + + async handleEditMessage(form: EditPrivateMessage) { + const res = await HttpService.client.editPrivateMessage(form); + this.findAndUpdateMessage(res); + } + + async handleMarkMessageAsRead(form: MarkPrivateMessageAsRead) { + const res = await HttpService.client.markPrivateMessageAsRead(form); + this.findAndUpdateMessage(res); + } + + async handleMessageReport(form: CreatePrivateMessageReport) { + const res = await HttpService.client.createPrivateMessageReport(form); + this.reportToast(res); + } + + async handleCreateMessage(form: CreatePrivateMessage) { + const res = await HttpService.client.createPrivateMessage(form); + this.setState(s => { + if (s.messagesRes.state == "success" && res.state == "success") { + s.messagesRes.data.private_messages.unshift( + res.data.private_message_view + ); } - this.setState(this.state); - } else if (op == UserOperation.DeletePrivateMessage) { - const data = wsJsonToRes(msg); - const found = this.state.messages.find( - m => - m.private_message.id === data.private_message_view.private_message.id - ); - if (found) { - const combinedView = this.state.combined.find( - i => i.id == data.private_message_view.private_message.id - )?.view as PrivateMessageView | undefined; - if (combinedView) { - found.private_message.deleted = combinedView.private_message.deleted = - data.private_message_view.private_message.deleted; - found.private_message.updated = combinedView.private_message.updated = - data.private_message_view.private_message.updated; - } + + return s; + }); + } + + findAndUpdateMessage(res: RequestState) { + this.setState(s => { + if (s.messagesRes.state === "success" && res.state === "success") { + s.messagesRes.data.private_messages = editPrivateMessage( + res.data.private_message_view, + s.messagesRes.data.private_messages + ); } - this.setState(this.state); - } else if (op == UserOperation.MarkPrivateMessageAsRead) { - const data = wsJsonToRes(msg); - const found = this.state.messages.find( - m => - m.private_message.id === data.private_message_view.private_message.id - ); + return s; + }); + } - if (found) { - const combinedView = this.state.combined.find( - i => - i.id == data.private_message_view.private_message.id && - i.type_ == ReplyEnum.Message - )?.view as PrivateMessageView | undefined; - if (combinedView) { - found.private_message.updated = combinedView.private_message.updated = - data.private_message_view.private_message.updated; - - // If youre in the unread view, just remove it from the list - if ( - this.state.unreadOrAll == UnreadOrAll.Unread && - data.private_message_view.private_message.read - ) { - this.setState({ - messages: this.state.messages.filter( - r => - r.private_message.id !== - data.private_message_view.private_message.id - ), - }); - this.setState({ - combined: this.state.combined.filter( - r => r.id !== data.private_message_view.private_message.id - ), - }); - } else { - found.private_message.read = combinedView.private_message.read = - data.private_message_view.private_message.read; - } + updateBanFromCommunity(banRes: RequestState) { + // Maybe not necessary + if (banRes.state == "success") { + this.setState(s => { + if (s.repliesRes.state == "success") { + s.repliesRes.data.replies + .filter(c => c.creator.id == banRes.data.person_view.person.id) + .forEach( + c => (c.creator_banned_from_community = banRes.data.banned) + ); } - } - this.sendUnreadCount(data.private_message_view.private_message.read); - this.setState(this.state); - } else if (op == UserOperation.MarkAllAsRead) { - // Moved to be instant - } else if ( - op == UserOperation.EditComment || - op == UserOperation.DeleteComment || - op == UserOperation.RemoveComment - ) { - const data = wsJsonToRes(msg); - editCommentRes(data.comment_view, this.state.replies); - this.setState(this.state); - } else if (op == UserOperation.MarkCommentReplyAsRead) { - const data = wsJsonToRes(msg); - - const found = this.state.replies.find( - c => c.comment_reply.id == data.comment_reply_view.comment_reply.id - ); + if (s.mentionsRes.state == "success") { + s.mentionsRes.data.mentions + .filter(c => c.creator.id == banRes.data.person_view.person.id) + .forEach( + c => (c.creator_banned_from_community = banRes.data.banned) + ); + } + return s; + }); + } + } - if (found) { - const combinedView = this.state.combined.find( - i => - i.id == data.comment_reply_view.comment_reply.id && - i.type_ == ReplyEnum.Reply - )?.view as CommentReplyView | undefined; - if (combinedView) { - found.comment.content = combinedView.comment.content = - data.comment_reply_view.comment.content; - found.comment.updated = combinedView.comment.updated = - data.comment_reply_view.comment.updated; - found.comment.removed = combinedView.comment.removed = - data.comment_reply_view.comment.removed; - found.comment.deleted = combinedView.comment.deleted = - data.comment_reply_view.comment.deleted; - found.counts.upvotes = combinedView.counts.upvotes = - data.comment_reply_view.counts.upvotes; - found.counts.downvotes = combinedView.counts.downvotes = - data.comment_reply_view.counts.downvotes; - found.counts.score = combinedView.counts.score = - data.comment_reply_view.counts.score; - - // If youre in the unread view, just remove it from the list - if ( - this.state.unreadOrAll == UnreadOrAll.Unread && - data.comment_reply_view.comment_reply.read - ) { - this.setState({ - replies: this.state.replies.filter( - r => - r.comment_reply.id !== - data.comment_reply_view.comment_reply.id - ), - }); - this.setState({ - combined: this.state.combined.filter( - r => r.id !== data.comment_reply_view.comment_reply.id - ), - }); - } else { - found.comment_reply.read = combinedView.comment_reply.read = - data.comment_reply_view.comment_reply.read; - } + updateBan(banRes: RequestState) { + // Maybe not necessary + if (banRes.state == "success") { + this.setState(s => { + if (s.repliesRes.state == "success") { + s.repliesRes.data.replies + .filter(c => c.creator.id == banRes.data.person_view.person.id) + .forEach(c => (c.creator.banned = banRes.data.banned)); } - } - this.sendUnreadCount(data.comment_reply_view.comment_reply.read); - this.setState(this.state); - } else if (op == UserOperation.MarkPersonMentionAsRead) { - const data = wsJsonToRes(msg); - - // TODO this might not be correct, it might need to use the comment id - const found = this.state.mentions.find( - c => c.person_mention.id == data.person_mention_view.person_mention.id - ); + if (s.mentionsRes.state == "success") { + s.mentionsRes.data.mentions + .filter(c => c.creator.id == banRes.data.person_view.person.id) + .forEach(c => (c.creator.banned = banRes.data.banned)); + } + return s; + }); + } + } + + purgeItem(purgeRes: RequestState) { + if (purgeRes.state == "success") { + toast(i18n.t("purge_success")); + this.context.router.history.push(`/`); + } + } + + reportToast( + res: RequestState + ) { + if (res.state == "success") { + toast(i18n.t("report_created")); + } + } - if (found) { - const combinedView = this.state.combined.find( - i => - i.id == data.person_mention_view.person_mention.id && - i.type_ == ReplyEnum.Mention - )?.view as PersonMentionView | undefined; - if (combinedView) { - found.comment.content = combinedView.comment.content = - data.person_mention_view.comment.content; - found.comment.updated = combinedView.comment.updated = - data.person_mention_view.comment.updated; - found.comment.removed = combinedView.comment.removed = - data.person_mention_view.comment.removed; - found.comment.deleted = combinedView.comment.deleted = - data.person_mention_view.comment.deleted; - found.counts.upvotes = combinedView.counts.upvotes = - data.person_mention_view.counts.upvotes; - found.counts.downvotes = combinedView.counts.downvotes = - data.person_mention_view.counts.downvotes; - found.counts.score = combinedView.counts.score = - data.person_mention_view.counts.score; - - // If youre in the unread view, just remove it from the list - if ( - this.state.unreadOrAll == UnreadOrAll.Unread && - data.person_mention_view.person_mention.read - ) { - this.setState({ - mentions: this.state.mentions.filter( - r => - r.person_mention.id !== - data.person_mention_view.person_mention.id - ), - }); - this.setState({ - combined: this.state.combined.filter( - r => r.id !== data.person_mention_view.person_mention.id - ), - }); - } else { - // TODO test to make sure these mentions are getting marked as read - found.person_mention.read = combinedView.person_mention.read = - data.person_mention_view.person_mention.read; - } + // A weird case, since you have only replies and mentions, not comment responses + findAndUpdateComment(res: RequestState) { + if (res.state == "success") { + this.setState(s => { + if (s.repliesRes.state == "success") { + s.repliesRes.data.replies = editWith( + res.data.comment_view, + s.repliesRes.data.replies + ); } - } - this.sendUnreadCount(data.person_mention_view.person_mention.read); - this.setState(this.state); - } else if (op == UserOperation.CreatePrivateMessage) { - const data = wsJsonToRes(msg); - const mui = UserService.Instance.myUserInfo; - if ( - data.private_message_view.recipient.id == mui?.local_user_view.person.id - ) { - this.state.messages.unshift(data.private_message_view); - this.state.combined.unshift( - this.messageToReplyType(data.private_message_view) + if (s.mentionsRes.state == "success") { + s.mentionsRes.data.mentions = editWith( + res.data.comment_view, + s.mentionsRes.data.mentions + ); + } + // Set finished for the parent + s.finished.set( + getCommentParentId(res.data.comment_view.comment) ?? 0, + true ); - this.setState(this.state); - } - } else if (op == UserOperation.SaveComment) { - const data = wsJsonToRes(msg); - saveCommentRes(data.comment_view, this.state.replies); - this.setState(this.state); - setupTippy(); - } else if (op == UserOperation.CreateCommentLike) { - const data = wsJsonToRes(msg); - createCommentLikeRes(data.comment_view, this.state.replies); - this.setState(this.state); - } else if (op == UserOperation.BlockPerson) { - const data = wsJsonToRes(msg); - updatePersonBlock(data); - } else if (op == UserOperation.CreatePostReport) { - const data = wsJsonToRes(msg); - if (data) { - toast(i18n.t("report_created")); - } - } else if (op == UserOperation.CreateCommentReport) { - const data = wsJsonToRes(msg); - if (data) { - toast(i18n.t("report_created")); - } - } else if (op == UserOperation.CreatePrivateMessageReport) { - const data = wsJsonToRes(msg); - if (data) { - toast(i18n.t("report_created")); - } + return s; + }); } } - isMention(view: any): view is PersonMentionView { - return (view as PersonMentionView).person_mention !== undefined; + findAndUpdateCommentReply(res: RequestState) { + this.setState(s => { + if (s.repliesRes.state == "success" && res.state == "success") { + s.repliesRes.data.replies = editCommentReply( + res.data.comment_reply_view, + s.repliesRes.data.replies + ); + } + return s; + }); } - isReply(view: any): view is CommentReplyView { - return (view as CommentReplyView).comment_reply !== undefined; + findAndUpdateMention(res: RequestState) { + this.setState(s => { + if (s.mentionsRes.state == "success" && res.state == "success") { + s.mentionsRes.data.mentions = editMention( + res.data.person_mention_view, + s.mentionsRes.data.mentions + ); + } + return s; + }); } }