ad8e3d1e88e30694cac7185fba19fc525a20cd2c
[oweals/peertube.git] / server / models / server / server-blocklist.ts
1 import { BelongsTo, Column, CreatedAt, ForeignKey, Model, Scopes, Table, UpdatedAt } from 'sequelize-typescript'
2 import { AccountModel } from '../account/account'
3 import { ServerModel } from './server'
4 import { ServerBlock } from '../../../shared/models/blocklist'
5 import { getSort, searchAttribute } from '../utils'
6 import * as Bluebird from 'bluebird'
7 import { MServerBlocklist, MServerBlocklistAccountServer, MServerBlocklistFormattable } from '@server/typings/models'
8 import { Op } from 'sequelize'
9
10 enum ScopeNames {
11   WITH_ACCOUNT = 'WITH_ACCOUNT',
12   WITH_SERVER = 'WITH_SERVER'
13 }
14
15 @Scopes(() => ({
16   [ScopeNames.WITH_ACCOUNT]: {
17     include: [
18       {
19         model: AccountModel,
20         required: true
21       }
22     ]
23   },
24   [ScopeNames.WITH_SERVER]: {
25     include: [
26       {
27         model: ServerModel,
28         required: true
29       }
30     ]
31   }
32 }))
33
34 @Table({
35   tableName: 'serverBlocklist',
36   indexes: [
37     {
38       fields: [ 'accountId', 'targetServerId' ],
39       unique: true
40     },
41     {
42       fields: [ 'targetServerId' ]
43     }
44   ]
45 })
46 export class ServerBlocklistModel extends Model<ServerBlocklistModel> {
47
48   @CreatedAt
49   createdAt: Date
50
51   @UpdatedAt
52   updatedAt: Date
53
54   @ForeignKey(() => AccountModel)
55   @Column
56   accountId: number
57
58   @BelongsTo(() => AccountModel, {
59     foreignKey: {
60       name: 'accountId',
61       allowNull: false
62     },
63     onDelete: 'CASCADE'
64   })
65   ByAccount: AccountModel
66
67   @ForeignKey(() => ServerModel)
68   @Column
69   targetServerId: number
70
71   @BelongsTo(() => ServerModel, {
72     foreignKey: {
73       allowNull: false
74     },
75     onDelete: 'CASCADE'
76   })
77   BlockedServer: ServerModel
78
79   static isServerMutedByMulti (accountIds: number[], targetServerId: number) {
80     const query = {
81       attributes: [ 'accountId', 'id' ],
82       where: {
83         accountId: {
84           [Op.in]: accountIds
85         },
86         targetServerId
87       },
88       raw: true
89     }
90
91     return ServerBlocklistModel.unscoped()
92                                 .findAll(query)
93                                 .then(rows => {
94                                   const result: { [accountId: number]: boolean } = {}
95
96                                   for (const accountId of accountIds) {
97                                     result[accountId] = !!rows.find(r => r.accountId === accountId)
98                                   }
99
100                                   return result
101                                 })
102   }
103
104   static loadByAccountAndHost (accountId: number, host: string): Bluebird<MServerBlocklist> {
105     const query = {
106       where: {
107         accountId
108       },
109       include: [
110         {
111           model: ServerModel,
112           where: {
113             host
114           },
115           required: true
116         }
117       ]
118     }
119
120     return ServerBlocklistModel.findOne(query)
121   }
122
123   static listHostsBlockedBy (accountIds: number[]): Bluebird<string[]> {
124     const query = {
125       attributes: [ ],
126       where: {
127         accountId: {
128           [Op.in]: accountIds
129         }
130       },
131       include: [
132         {
133           attributes: [ 'host' ],
134           model: ServerModel.unscoped(),
135           required: true
136         }
137       ]
138     }
139
140     return ServerBlocklistModel.findAll(query)
141       .then(entries => entries.map(e => e.BlockedServer.host))
142   }
143
144   static listForApi (parameters: {
145     start: number
146     count: number
147     sort: string
148     search?: string
149     accountId: number
150   }) {
151     const { start, count, sort, search, accountId } = parameters
152
153     const query = {
154       offset: start,
155       limit: count,
156       order: getSort(sort),
157       where: {
158         accountId,
159         ...searchAttribute(search, '$BlockedServer.host$')
160       }
161     }
162
163     return ServerBlocklistModel
164       .scope([ ScopeNames.WITH_ACCOUNT, ScopeNames.WITH_SERVER ])
165       .findAndCountAll<MServerBlocklistAccountServer>(query)
166       .then(({ rows, count }) => {
167         return { total: count, data: rows }
168       })
169   }
170
171   toFormattedJSON (this: MServerBlocklistFormattable): ServerBlock {
172     return {
173       byAccount: this.ByAccount.toFormattedJSON(),
174       blockedServer: this.BlockedServer.toFormattedJSON(),
175       createdAt: this.createdAt
176     }
177   }
178 }