]> git.immae.eu Git - github/Chocobozzz/PeerTube.git/blob - client/src/app/+admin/moderation/video-comment-list/video-comment-list.component.ts
Add ability to filter my videos by live
[github/Chocobozzz/PeerTube.git] / client / src / app / +admin / moderation / video-comment-list / video-comment-list.component.ts
1 import { SortMeta } from 'primeng/api'
2 import { AfterViewInit, Component, OnInit } from '@angular/core'
3 import { ActivatedRoute, Router } from '@angular/router'
4 import { AuthService, ConfirmService, MarkdownService, Notifier, RestPagination, RestTable } from '@app/core'
5 import { AdvancedInputFilter } from '@app/shared/shared-forms'
6 import { DropdownAction } from '@app/shared/shared-main'
7 import { BulkService } from '@app/shared/shared-moderation'
8 import { VideoCommentAdmin, VideoCommentService } from '@app/shared/shared-video-comment'
9 import { FeedFormat, UserRight } from '@shared/models'
10
11 @Component({
12 selector: 'my-video-comment-list',
13 templateUrl: './video-comment-list.component.html',
14 styleUrls: [ '../../../shared/shared-moderation/moderation.scss', './video-comment-list.component.scss' ]
15 })
16 export class VideoCommentListComponent extends RestTable implements OnInit, AfterViewInit {
17 baseRoute = '/admin/moderation/video-comments/list'
18
19 comments: VideoCommentAdmin[]
20 totalRecords = 0
21 sort: SortMeta = { field: 'createdAt', order: -1 }
22 pagination: RestPagination = { count: this.rowsPerPage, start: 0 }
23
24 videoCommentActions: DropdownAction<VideoCommentAdmin>[][] = []
25
26 syndicationItems = [
27 {
28 format: FeedFormat.RSS,
29 label: 'media rss 2.0',
30 url: VideoCommentService.BASE_FEEDS_URL + FeedFormat.RSS.toLowerCase()
31 },
32 {
33 format: FeedFormat.ATOM,
34 label: 'atom 1.0',
35 url: VideoCommentService.BASE_FEEDS_URL + FeedFormat.ATOM.toLowerCase()
36 },
37 {
38 format: FeedFormat.JSON,
39 label: 'json 1.0',
40 url: VideoCommentService.BASE_FEEDS_URL + FeedFormat.JSON.toLowerCase()
41 }
42 ]
43
44 selectedComments: VideoCommentAdmin[] = []
45 bulkCommentActions: DropdownAction<VideoCommentAdmin[]>[] = []
46
47 inputFilters: AdvancedInputFilter[] = [
48 {
49 queryParams: { 'search': 'local:true' },
50 label: $localize`Local comments`
51 },
52 {
53 queryParams: { 'search': 'local:false' },
54 label: $localize`Remote comments`
55 }
56 ]
57
58 get authUser () {
59 return this.auth.getUser()
60 }
61
62 constructor (
63 protected router: Router,
64 protected route: ActivatedRoute,
65 private auth: AuthService,
66 private notifier: Notifier,
67 private confirmService: ConfirmService,
68 private videoCommentService: VideoCommentService,
69 private markdownRenderer: MarkdownService,
70 private bulkService: BulkService
71 ) {
72 super()
73
74 this.videoCommentActions = [
75 [
76 {
77 label: $localize`Delete this comment`,
78 handler: comment => this.deleteComment(comment),
79 isDisplayed: () => this.authUser.hasRight(UserRight.REMOVE_ANY_VIDEO_COMMENT)
80 },
81
82 {
83 label: $localize`Delete all comments of this account`,
84 description: $localize`Comments are deleted after a few minutes`,
85 handler: comment => this.deleteUserComments(comment),
86 isDisplayed: () => this.authUser.hasRight(UserRight.REMOVE_ANY_VIDEO_COMMENT)
87 }
88 ]
89 ]
90 }
91
92 ngOnInit () {
93 this.initialize()
94 this.listenToSearchChange()
95
96 this.bulkCommentActions = [
97 {
98 label: $localize`Delete`,
99 handler: comments => this.removeComments(comments),
100 isDisplayed: () => this.authUser.hasRight(UserRight.REMOVE_ANY_VIDEO_COMMENT),
101 iconName: 'delete'
102 }
103 ]
104 }
105
106 ngAfterViewInit () {
107 if (this.search) this.setTableFilter(this.search, false)
108 }
109
110 getIdentifier () {
111 return 'VideoCommentListComponent'
112 }
113
114 toHtml (text: string) {
115 return this.markdownRenderer.textMarkdownToHTML(text, true, true)
116 }
117
118 isInSelectionMode () {
119 return this.selectedComments.length !== 0
120 }
121
122 protected loadData () {
123 this.videoCommentService.getAdminVideoComments({
124 pagination: this.pagination,
125 sort: this.sort,
126 search: this.search
127 }).subscribe(
128 async resultList => {
129 this.totalRecords = resultList.total
130
131 this.comments = []
132
133 for (const c of resultList.data) {
134 this.comments.push(
135 new VideoCommentAdmin(c, await this.toHtml(c.text))
136 )
137 }
138 },
139
140 err => this.notifier.error(err.message)
141 )
142 }
143
144 private async removeComments (comments: VideoCommentAdmin[]) {
145 const commentArgs = comments.map(c => ({ videoId: c.video.id, commentId: c.id }))
146
147 this.videoCommentService.deleteVideoComments(commentArgs).subscribe(
148 () => {
149 this.notifier.success($localize`${commentArgs.length} comments deleted.`)
150 this.loadData()
151 },
152
153 err => this.notifier.error(err.message),
154
155 () => this.selectedComments = []
156 )
157 }
158
159 private deleteComment (comment: VideoCommentAdmin) {
160 this.videoCommentService.deleteVideoComment(comment.video.id, comment.id)
161 .subscribe(
162 () => this.loadData(),
163
164 err => this.notifier.error(err.message)
165 )
166 }
167
168 private async deleteUserComments (comment: VideoCommentAdmin) {
169 const message = $localize`Do you really want to delete all comments of ${comment.by}?`
170 const res = await this.confirmService.confirm(message, $localize`Delete`)
171 if (res === false) return
172
173 const options = {
174 accountName: comment.by,
175 scope: 'instance' as 'instance'
176 }
177
178 this.bulkService.removeCommentsOf(options)
179 .subscribe(
180 () => {
181 this.notifier.success($localize`Comments of ${options.accountName} will be deleted in a few minutes`)
182 },
183
184 err => this.notifier.error(err.message)
185 )
186 }
187 }