]> git.immae.eu Git - github/Chocobozzz/PeerTube.git/blob - server/controllers/api/accounts.ts
Implement avatar miniatures (#4639)
[github/Chocobozzz/PeerTube.git] / server / controllers / api / accounts.ts
1 import express from 'express'
2 import { pickCommonVideoQuery } from '@server/helpers/query'
3 import { ActorFollowModel } from '@server/models/actor/actor-follow'
4 import { getServerActor } from '@server/models/application/application'
5 import { guessAdditionalAttributesFromQuery } from '@server/models/video/formatter/video-format-utils'
6 import { buildNSFWFilter, getCountVideos, isUserAbleToSearchRemoteURI } from '../../helpers/express-utils'
7 import { getFormattedObjects } from '../../helpers/utils'
8 import { JobQueue } from '../../lib/job-queue'
9 import { Hooks } from '../../lib/plugins/hooks'
10 import {
11 asyncMiddleware,
12 authenticate,
13 commonVideosFiltersValidator,
14 optionalAuthenticate,
15 paginationValidator,
16 setDefaultPagination,
17 setDefaultSort,
18 setDefaultVideosSort,
19 videoPlaylistsSortValidator,
20 videoRatesSortValidator,
21 videoRatingValidator
22 } from '../../middlewares'
23 import {
24 accountNameWithHostGetValidator,
25 accountsFollowersSortValidator,
26 accountsSortValidator,
27 ensureAuthUserOwnsAccountValidator,
28 videoChannelsSortValidator,
29 videoChannelStatsValidator,
30 videosSortValidator
31 } from '../../middlewares/validators'
32 import { commonVideoPlaylistFiltersValidator, videoPlaylistsSearchValidator } from '../../middlewares/validators/videos/video-playlists'
33 import { AccountModel } from '../../models/account/account'
34 import { AccountVideoRateModel } from '../../models/account/account-video-rate'
35 import { VideoModel } from '../../models/video/video'
36 import { VideoChannelModel } from '../../models/video/video-channel'
37 import { VideoPlaylistModel } from '../../models/video/video-playlist'
38
39 const accountsRouter = express.Router()
40
41 accountsRouter.get('/',
42 paginationValidator,
43 accountsSortValidator,
44 setDefaultSort,
45 setDefaultPagination,
46 asyncMiddleware(listAccounts)
47 )
48
49 accountsRouter.get('/:accountName',
50 asyncMiddleware(accountNameWithHostGetValidator),
51 getAccount
52 )
53
54 accountsRouter.get('/:accountName/videos',
55 asyncMiddleware(accountNameWithHostGetValidator),
56 paginationValidator,
57 videosSortValidator,
58 setDefaultVideosSort,
59 setDefaultPagination,
60 optionalAuthenticate,
61 commonVideosFiltersValidator,
62 asyncMiddleware(listAccountVideos)
63 )
64
65 accountsRouter.get('/:accountName/video-channels',
66 asyncMiddleware(accountNameWithHostGetValidator),
67 videoChannelStatsValidator,
68 paginationValidator,
69 videoChannelsSortValidator,
70 setDefaultSort,
71 setDefaultPagination,
72 asyncMiddleware(listAccountChannels)
73 )
74
75 accountsRouter.get('/:accountName/video-playlists',
76 optionalAuthenticate,
77 asyncMiddleware(accountNameWithHostGetValidator),
78 paginationValidator,
79 videoPlaylistsSortValidator,
80 setDefaultSort,
81 setDefaultPagination,
82 commonVideoPlaylistFiltersValidator,
83 videoPlaylistsSearchValidator,
84 asyncMiddleware(listAccountPlaylists)
85 )
86
87 accountsRouter.get('/:accountName/ratings',
88 authenticate,
89 asyncMiddleware(accountNameWithHostGetValidator),
90 ensureAuthUserOwnsAccountValidator,
91 paginationValidator,
92 videoRatesSortValidator,
93 setDefaultSort,
94 setDefaultPagination,
95 videoRatingValidator,
96 asyncMiddleware(listAccountRatings)
97 )
98
99 accountsRouter.get('/:accountName/followers',
100 authenticate,
101 asyncMiddleware(accountNameWithHostGetValidator),
102 ensureAuthUserOwnsAccountValidator,
103 paginationValidator,
104 accountsFollowersSortValidator,
105 setDefaultSort,
106 setDefaultPagination,
107 asyncMiddleware(listAccountFollowers)
108 )
109
110 // ---------------------------------------------------------------------------
111
112 export {
113 accountsRouter
114 }
115
116 // ---------------------------------------------------------------------------
117
118 function getAccount (req: express.Request, res: express.Response) {
119 const account = res.locals.account
120
121 if (account.isOutdated()) {
122 JobQueue.Instance.createJob({ type: 'activitypub-refresher', payload: { type: 'actor', url: account.Actor.url } })
123 }
124
125 return res.json(account.toFormattedJSON())
126 }
127
128 async function listAccounts (req: express.Request, res: express.Response) {
129 const resultList = await AccountModel.listForApi(req.query.start, req.query.count, req.query.sort)
130
131 return res.json(getFormattedObjects(resultList.data, resultList.total))
132 }
133
134 async function listAccountChannels (req: express.Request, res: express.Response) {
135 const options = {
136 accountId: res.locals.account.id,
137 start: req.query.start,
138 count: req.query.count,
139 sort: req.query.sort,
140 withStats: req.query.withStats,
141 search: req.query.search
142 }
143
144 const resultList = await VideoChannelModel.listByAccountForAPI(options)
145
146 return res.json(getFormattedObjects(resultList.data, resultList.total))
147 }
148
149 async function listAccountPlaylists (req: express.Request, res: express.Response) {
150 const serverActor = await getServerActor()
151
152 // Allow users to see their private/unlisted video playlists
153 let listMyPlaylists = false
154 if (res.locals.oauth && res.locals.oauth.token.User.Account.id === res.locals.account.id) {
155 listMyPlaylists = true
156 }
157
158 const resultList = await VideoPlaylistModel.listForApi({
159 search: req.query.search,
160 followerActorId: serverActor.id,
161 start: req.query.start,
162 count: req.query.count,
163 sort: req.query.sort,
164 accountId: res.locals.account.id,
165 listMyPlaylists,
166 type: req.query.playlistType
167 })
168
169 return res.json(getFormattedObjects(resultList.data, resultList.total))
170 }
171
172 async function listAccountVideos (req: express.Request, res: express.Response) {
173 const serverActor = await getServerActor()
174
175 const account = res.locals.account
176
177 const displayOnlyForFollower = isUserAbleToSearchRemoteURI(res)
178 ? null
179 : {
180 actorId: serverActor.id,
181 orLocalVideos: true
182 }
183
184 const countVideos = getCountVideos(req)
185 const query = pickCommonVideoQuery(req.query)
186
187 const apiOptions = await Hooks.wrapObject({
188 ...query,
189
190 displayOnlyForFollower,
191 nsfw: buildNSFWFilter(res, query.nsfw),
192 accountId: account.id,
193 user: res.locals.oauth ? res.locals.oauth.token.User : undefined,
194 countVideos
195 }, 'filter:api.accounts.videos.list.params')
196
197 const resultList = await Hooks.wrapPromiseFun(
198 VideoModel.listForApi,
199 apiOptions,
200 'filter:api.accounts.videos.list.result'
201 )
202
203 return res.json(getFormattedObjects(resultList.data, resultList.total, guessAdditionalAttributesFromQuery(query)))
204 }
205
206 async function listAccountRatings (req: express.Request, res: express.Response) {
207 const account = res.locals.account
208
209 const resultList = await AccountVideoRateModel.listByAccountForApi({
210 accountId: account.id,
211 start: req.query.start,
212 count: req.query.count,
213 sort: req.query.sort,
214 type: req.query.rating
215 })
216 return res.json(getFormattedObjects(resultList.data, resultList.total))
217 }
218
219 async function listAccountFollowers (req: express.Request, res: express.Response) {
220 const account = res.locals.account
221
222 const channels = await VideoChannelModel.listAllByAccount(account.id)
223 const actorIds = [ account.actorId ].concat(channels.map(c => c.actorId))
224
225 const resultList = await ActorFollowModel.listFollowersForApi({
226 actorIds,
227 start: req.query.start,
228 count: req.query.count,
229 sort: req.query.sort,
230 search: req.query.search,
231 state: 'accepted'
232 })
233
234 return res.json(getFormattedObjects(resultList.data, resultList.total))
235 }