diff options
Diffstat (limited to 'server/models/video/video-abuse.ts')
-rw-r--r-- | server/models/video/video-abuse.ts | 210 |
1 files changed, 92 insertions, 118 deletions
diff --git a/server/models/video/video-abuse.ts b/server/models/video/video-abuse.ts index d09f5f7a1..d0ee969fb 100644 --- a/server/models/video/video-abuse.ts +++ b/server/models/video/video-abuse.ts | |||
@@ -1,142 +1,116 @@ | |||
1 | import * as Sequelize from 'sequelize' | 1 | import { AllowNull, BelongsTo, Column, CreatedAt, ForeignKey, Is, Model, Table, UpdatedAt } from 'sequelize-typescript' |
2 | 2 | import { VideoAbuseObject } from '../../../shared/models/activitypub/objects' | |
3 | import { isVideoAbuseReasonValid } from '../../helpers/custom-validators/videos' | ||
3 | import { CONFIG } from '../../initializers' | 4 | import { CONFIG } from '../../initializers' |
4 | import { isVideoAbuseReasonValid } from '../../helpers' | 5 | import { AccountModel } from '../account/account' |
5 | 6 | import { ServerModel } from '../server/server' | |
6 | import { addMethodsToModel, getSort } from '../utils' | 7 | import { getSort, throwIfNotValid } from '../utils' |
7 | import { | 8 | import { VideoModel } from './video' |
8 | VideoAbuseInstance, | 9 | |
9 | VideoAbuseAttributes, | 10 | @Table({ |
10 | 11 | tableName: 'videoAbuse', | |
11 | VideoAbuseMethods | 12 | indexes: [ |
12 | } from './video-abuse-interface' | ||
13 | import { VideoAbuseObject } from '../../../shared/models/activitypub/objects/video-abuse-object' | ||
14 | |||
15 | let VideoAbuse: Sequelize.Model<VideoAbuseInstance, VideoAbuseAttributes> | ||
16 | let toFormattedJSON: VideoAbuseMethods.ToFormattedJSON | ||
17 | let listForApi: VideoAbuseMethods.ListForApi | ||
18 | let toActivityPubObject: VideoAbuseMethods.ToActivityPubObject | ||
19 | |||
20 | export default function (sequelize: Sequelize.Sequelize, DataTypes: Sequelize.DataTypes) { | ||
21 | VideoAbuse = sequelize.define<VideoAbuseInstance, VideoAbuseAttributes>('VideoAbuse', | ||
22 | { | 13 | { |
23 | reason: { | 14 | fields: [ 'videoId' ] |
24 | type: DataTypes.STRING, | ||
25 | allowNull: false, | ||
26 | validate: { | ||
27 | reasonValid: value => { | ||
28 | const res = isVideoAbuseReasonValid(value) | ||
29 | if (res === false) throw new Error('Video abuse reason is not valid.') | ||
30 | } | ||
31 | } | ||
32 | } | ||
33 | }, | 15 | }, |
34 | { | 16 | { |
35 | indexes: [ | 17 | fields: [ 'reporterAccountId' ] |
36 | { | ||
37 | fields: [ 'videoId' ] | ||
38 | }, | ||
39 | { | ||
40 | fields: [ 'reporterAccountId' ] | ||
41 | } | ||
42 | ] | ||
43 | } | 18 | } |
44 | ) | ||
45 | |||
46 | const classMethods = [ | ||
47 | associate, | ||
48 | |||
49 | listForApi | ||
50 | ] | ||
51 | const instanceMethods = [ | ||
52 | toFormattedJSON, | ||
53 | toActivityPubObject | ||
54 | ] | 19 | ] |
55 | addMethodsToModel(VideoAbuse, classMethods, instanceMethods) | 20 | }) |
56 | 21 | export class VideoAbuseModel extends Model<VideoAbuseModel> { | |
57 | return VideoAbuse | ||
58 | } | ||
59 | |||
60 | // ------------------------------ METHODS ------------------------------ | ||
61 | |||
62 | toFormattedJSON = function (this: VideoAbuseInstance) { | ||
63 | let reporterServerHost | ||
64 | |||
65 | if (this.Account.Server) { | ||
66 | reporterServerHost = this.Account.Server.host | ||
67 | } else { | ||
68 | // It means it's our video | ||
69 | reporterServerHost = CONFIG.WEBSERVER.HOST | ||
70 | } | ||
71 | |||
72 | const json = { | ||
73 | id: this.id, | ||
74 | reason: this.reason, | ||
75 | reporterUsername: this.Account.name, | ||
76 | reporterServerHost, | ||
77 | videoId: this.Video.id, | ||
78 | videoUUID: this.Video.uuid, | ||
79 | videoName: this.Video.name, | ||
80 | createdAt: this.createdAt | ||
81 | } | ||
82 | 22 | ||
83 | return json | 23 | @AllowNull(false) |
84 | } | 24 | @Is('VideoAbuseReason', value => throwIfNotValid(value, isVideoAbuseReasonValid, 'reason')) |
25 | @Column | ||
26 | reason: string | ||
85 | 27 | ||
86 | toActivityPubObject = function (this: VideoAbuseInstance) { | 28 | @CreatedAt |
87 | const videoAbuseObject: VideoAbuseObject = { | 29 | createdAt: Date |
88 | type: 'Flag' as 'Flag', | ||
89 | content: this.reason, | ||
90 | object: this.Video.url | ||
91 | } | ||
92 | 30 | ||
93 | return videoAbuseObject | 31 | @UpdatedAt |
94 | } | 32 | updatedAt: Date |
95 | 33 | ||
96 | // ------------------------------ STATICS ------------------------------ | 34 | @ForeignKey(() => AccountModel) |
35 | @Column | ||
36 | reporterAccountId: number | ||
97 | 37 | ||
98 | function associate (models) { | 38 | @BelongsTo(() => AccountModel, { |
99 | VideoAbuse.belongsTo(models.Account, { | ||
100 | foreignKey: { | 39 | foreignKey: { |
101 | name: 'reporterAccountId', | ||
102 | allowNull: false | 40 | allowNull: false |
103 | }, | 41 | }, |
104 | onDelete: 'CASCADE' | 42 | onDelete: 'cascade' |
105 | }) | 43 | }) |
44 | Account: AccountModel | ||
45 | |||
46 | @ForeignKey(() => VideoModel) | ||
47 | @Column | ||
48 | videoId: number | ||
106 | 49 | ||
107 | VideoAbuse.belongsTo(models.Video, { | 50 | @BelongsTo(() => VideoModel, { |
108 | foreignKey: { | 51 | foreignKey: { |
109 | name: 'videoId', | ||
110 | allowNull: false | 52 | allowNull: false |
111 | }, | 53 | }, |
112 | onDelete: 'CASCADE' | 54 | onDelete: 'cascade' |
113 | }) | 55 | }) |
114 | } | 56 | Video: VideoModel |
57 | |||
58 | static listForApi (start: number, count: number, sort: string) { | ||
59 | const query = { | ||
60 | offset: start, | ||
61 | limit: count, | ||
62 | order: [ getSort(sort) ], | ||
63 | include: [ | ||
64 | { | ||
65 | model: AccountModel, | ||
66 | required: true, | ||
67 | include: [ | ||
68 | { | ||
69 | model: ServerModel, | ||
70 | required: false | ||
71 | } | ||
72 | ] | ||
73 | }, | ||
74 | { | ||
75 | model: VideoModel, | ||
76 | required: true | ||
77 | } | ||
78 | ] | ||
79 | } | ||
115 | 80 | ||
116 | listForApi = function (start: number, count: number, sort: string) { | 81 | return VideoAbuseModel.findAndCountAll(query) |
117 | const query = { | 82 | .then(({ rows, count }) => { |
118 | offset: start, | 83 | return { total: count, data: rows } |
119 | limit: count, | 84 | }) |
120 | order: [ getSort(sort) ], | ||
121 | include: [ | ||
122 | { | ||
123 | model: VideoAbuse['sequelize'].models.Account, | ||
124 | required: true, | ||
125 | include: [ | ||
126 | { | ||
127 | model: VideoAbuse['sequelize'].models.Server, | ||
128 | required: false | ||
129 | } | ||
130 | ] | ||
131 | }, | ||
132 | { | ||
133 | model: VideoAbuse['sequelize'].models.Video, | ||
134 | required: true | ||
135 | } | ||
136 | ] | ||
137 | } | 85 | } |
138 | 86 | ||
139 | return VideoAbuse.findAndCountAll(query).then(({ rows, count }) => { | 87 | toFormattedJSON () { |
140 | return { total: count, data: rows } | 88 | let reporterServerHost |
141 | }) | 89 | |
90 | if (this.Account.Server) { | ||
91 | reporterServerHost = this.Account.Server.host | ||
92 | } else { | ||
93 | // It means it's our video | ||
94 | reporterServerHost = CONFIG.WEBSERVER.HOST | ||
95 | } | ||
96 | |||
97 | return { | ||
98 | id: this.id, | ||
99 | reason: this.reason, | ||
100 | reporterUsername: this.Account.name, | ||
101 | reporterServerHost, | ||
102 | videoId: this.Video.id, | ||
103 | videoUUID: this.Video.uuid, | ||
104 | videoName: this.Video.name, | ||
105 | createdAt: this.createdAt | ||
106 | } | ||
107 | } | ||
108 | |||
109 | toActivityPubObject (): VideoAbuseObject { | ||
110 | return { | ||
111 | type: 'Flag' as 'Flag', | ||
112 | content: this.reason, | ||
113 | object: this.Video.url | ||
114 | } | ||
115 | } | ||
142 | } | 116 | } |