import * as program from 'commander'
import { resolve } from 'path'
import { VideoModel } from '../server/models/video/video'
-import { initDatabaseModels } from '../server/initializers'
+import { initDatabaseModels } from '../server/initializers/database'
import { JobQueue } from '../server/lib/job-queue'
program
import * as program from 'commander'
import { VideoModel } from '../server/models/video/video'
-import { initDatabaseModels } from '../server/initializers'
+import { initDatabaseModels } from '../server/initializers/database'
import { JobQueue } from '../server/lib/job-queue'
import { computeResolutionsToTranscode } from '@server/helpers/ffmpeg-utils'
import { VideoTranscodingPayload } from '@shared/models'
import * as Promise from 'bluebird'
import * as rimraf from 'rimraf'
-import { initDatabaseModels, sequelizeTypescript } from '../../../server/initializers'
+import { initDatabaseModels, sequelizeTypescript } from '../../../server/initializers/database'
import { CONFIG } from '../../../server/initializers/config'
initDatabaseModels(true)
import { registerTSPaths } from '../../server/helpers/register-ts-paths'
registerTSPaths()
-import { initDatabaseModels, sequelizeTypescript } from '../../server/initializers'
+import { initDatabaseModels, sequelizeTypescript } from '../../server/initializers/database'
import * as Sequelize from 'sequelize'
import { join } from 'path'
import { HLS_STREAMING_PLAYLIST_DIRECTORY, STATIC_PATHS, WEBSERVER } from '@server/initializers/constants'
import { getMaxBitrate } from '../shared/models/videos'
import { VideoModel } from '../server/models/video/video'
import { optimizeOriginalVideofile } from '../server/lib/video-transcoding'
-import { initDatabaseModels } from '../server/initializers'
+import { initDatabaseModels } from '../server/initializers/database'
import { basename, dirname } from 'path'
import { copy, move, remove } from 'fs-extra'
import { createTorrentAndSetInfoHash } from '@server/helpers/webtorrent'
import { join } from 'path'
import { CONFIG } from '../server/initializers/config'
import { VideoModel } from '../server/models/video/video'
-import { initDatabaseModels } from '../server/initializers'
+import { initDatabaseModels } from '../server/initializers/database'
import { readdir, remove } from 'fs-extra'
import { VideoRedundancyModel } from '../server/models/redundancy/video-redundancy'
import * as Bluebird from 'bluebird'
registerTSPaths()
import * as program from 'commander'
-import { initDatabaseModels } from '../server/initializers'
+import { initDatabaseModels } from '../server/initializers/database'
import { UserModel } from '../server/models/account/user'
import { isUserPasswordValid } from '../server/helpers/custom-validators/users'
import { AccountModel } from '../server/models/account/account'
import { VideoChannelModel } from '../server/models/video/video-channel'
import { VideoStreamingPlaylistModel } from '../server/models/video/video-streaming-playlist'
-import { initDatabaseModels } from '../server/initializers'
+import { initDatabaseModels } from '../server/initializers/database'
import { createTorrentAndSetInfoHash } from '@server/helpers/webtorrent'
import { getServerActor } from '@server/models/application/application'
loadLanguages()
// ----------- PeerTube modules -----------
-import { installApplication } from './server/initializers'
+import { installApplication } from './server/initializers/installer'
import { Emailer } from './server/lib/emailer'
import { JobQueue } from './server/lib/job-queue'
import { VideosPreviewCache, VideosCaptionCache } from './server/lib/files-cache'
} from '../../../middlewares'
import { getFormattedObjects } from '../../../helpers/utils'
import { UserVideoHistoryModel } from '../../../models/account/user-video-history'
-import { sequelizeTypescript } from '../../../initializers'
+import { sequelizeTypescript } from '../../../initializers/database'
const myVideosHistoryRouter = express.Router()
import { UserRight, VideoAbuseCreate, VideoAbuseState } from '../../../../shared'
import { logger } from '../../../helpers/logger'
import { getFormattedObjects } from '../../../helpers/utils'
-import { sequelizeTypescript } from '../../../initializers'
+import { sequelizeTypescript } from '../../../initializers/database'
import {
asyncMiddleware,
asyncRetryTransactionMiddleware,
import * as express from 'express'
-import { UserRight, VideoBlacklistCreate, VideoBlacklistType } from '../../../../shared'
+import { blacklistVideo, unblacklistVideo } from '@server/lib/video-blacklist'
+import { UserRight, VideoBlacklistCreate } from '../../../../shared'
import { logger } from '../../../helpers/logger'
import { getFormattedObjects } from '../../../helpers/utils'
+import { sequelizeTypescript } from '../../../initializers/database'
import {
asyncMiddleware,
authenticate,
videosBlacklistUpdateValidator
} from '../../../middlewares'
import { VideoBlacklistModel } from '../../../models/video/video-blacklist'
-import { sequelizeTypescript } from '../../../initializers'
-import { Notifier } from '../../../lib/notifier'
-import { sendDeleteVideo } from '../../../lib/activitypub/send'
-import { federateVideoIfNeeded } from '../../../lib/activitypub/videos'
-import { MVideoBlacklistVideo } from '@server/typings/models'
const blacklistRouter = express.Router()
authenticate,
ensureUserHasRight(UserRight.MANAGE_VIDEO_BLACKLIST),
asyncMiddleware(videosBlacklistAddValidator),
- asyncMiddleware(addVideoToBlacklist)
+ asyncMiddleware(addVideoToBlacklistController)
)
blacklistRouter.get('/blacklist',
// ---------------------------------------------------------------------------
-async function addVideoToBlacklist (req: express.Request, res: express.Response) {
+async function addVideoToBlacklistController (req: express.Request, res: express.Response) {
const videoInstance = res.locals.videoAll
const body: VideoBlacklistCreate = req.body
- const toCreate = {
- videoId: videoInstance.id,
- unfederated: body.unfederate === true,
- reason: body.reason,
- type: VideoBlacklistType.MANUAL
- }
-
- const blacklist: MVideoBlacklistVideo = await VideoBlacklistModel.create(toCreate)
- blacklist.Video = videoInstance
-
- if (body.unfederate === true) {
- await sendDeleteVideo(videoInstance, undefined)
- }
-
- Notifier.Instance.notifyOnVideoBlacklist(blacklist)
+ await blacklistVideo(videoInstance, body)
logger.info('Video %s blacklisted.', videoInstance.uuid)
- return res.type('json').status(204).end()
+ return res.type('json').sendStatus(204)
}
async function updateVideoBlacklistController (req: express.Request, res: express.Response) {
return videoBlacklist.save({ transaction: t })
})
- return res.type('json').status(204).end()
+ return res.type('json').sendStatus(204)
}
async function listBlacklist (req: express.Request, res: express.Response) {
const videoBlacklist = res.locals.videoBlacklist
const video = res.locals.videoAll
- const videoBlacklistType = await sequelizeTypescript.transaction(async t => {
- const unfederated = videoBlacklist.unfederated
- const videoBlacklistType = videoBlacklist.type
-
- await videoBlacklist.destroy({ transaction: t })
- video.VideoBlacklist = undefined
-
- // Re federate the video
- if (unfederated === true) {
- await federateVideoIfNeeded(video, true, t)
- }
-
- return videoBlacklistType
- })
-
- Notifier.Instance.notifyOnVideoUnblacklist(video)
-
- if (videoBlacklistType === VideoBlacklistType.AUTO_BEFORE_PUBLISHED) {
- Notifier.Instance.notifyOnVideoPublishedAfterRemovedFromAutoBlacklist(video)
-
- // Delete on object so new video notifications will send
- delete video.VideoBlacklist
- Notifier.Instance.notifyOnNewVideoIfNeeded(video)
- }
+ await unblacklistVideo(videoBlacklist, video)
logger.info('Video %s removed from blacklist.', video.uuid)
- return res.type('json').status(204).end()
+ return res.type('json').sendStatus(204)
}
import { VideoCommentCreate } from '../../../../shared/models/videos/video-comment.model'
import { logger } from '../../../helpers/logger'
import { getFormattedObjects } from '../../../helpers/utils'
-import { sequelizeTypescript } from '../../../initializers'
+import { sequelizeTypescript } from '../../../initializers/database'
import { buildFormattedCommentTree, createVideoComment, markCommentAsDeleted } from '../../../lib/video-comment'
import {
asyncMiddleware,
import * as express from 'express'
import { logger } from '../../../helpers/logger'
-import { sequelizeTypescript } from '../../../initializers'
+import { sequelizeTypescript } from '../../../initializers/database'
import {
asyncMiddleware,
asyncRetryTransactionMiddleware,
+++ /dev/null
-export * from './database'
-export * from './installer'
-export * from './migrator'
import { ActivityAnnounce } from '../../../../shared/models/activitypub'
import { retryTransactionWrapper } from '../../../helpers/database-utils'
-import { sequelizeTypescript } from '../../../initializers'
+import { sequelizeTypescript } from '../../../initializers/database'
import { VideoShareModel } from '../../../models/video/video-share'
import { forwardVideoRelatedActivity } from '../send/utils'
import { getOrCreateVideoAndAccountAndChannel } from '../videos'
import { VideoCommentObject } from '../../../../shared/models/activitypub/objects/video-comment-object'
import { retryTransactionWrapper } from '../../../helpers/database-utils'
import { logger } from '../../../helpers/logger'
-import { sequelizeTypescript } from '../../../initializers'
+import { sequelizeTypescript } from '../../../initializers/database'
import { resolveThread } from '../video-comments'
import { getOrCreateVideoAndAccountAndChannel } from '../videos'
import { forwardVideoRelatedActivity } from '../send/utils'
import { ActivityDelete } from '../../../../shared/models/activitypub'
import { retryTransactionWrapper } from '../../../helpers/database-utils'
import { logger } from '../../../helpers/logger'
-import { sequelizeTypescript } from '../../../initializers'
+import { sequelizeTypescript } from '../../../initializers/database'
import { ActorModel } from '../../../models/activitypub/actor'
import { VideoModel } from '../../../models/video/video'
import { VideoCommentModel } from '../../../models/video/video-comment'
import { ActivityCreate, ActivityDislike } from '../../../../shared'
import { DislikeObject } from '../../../../shared/models/activitypub/objects'
import { retryTransactionWrapper } from '../../../helpers/database-utils'
-import { sequelizeTypescript } from '../../../initializers'
+import { sequelizeTypescript } from '../../../initializers/database'
import { AccountVideoRateModel } from '../../../models/account/account-video-rate'
import { getOrCreateVideoAndAccountAndChannel } from '../videos'
import { forwardVideoRelatedActivity } from '../send/utils'
import { VideoAbuseObject } from '../../../../shared/models/activitypub/objects'
import { retryTransactionWrapper } from '../../../helpers/database-utils'
import { logger } from '../../../helpers/logger'
-import { sequelizeTypescript } from '../../../initializers'
+import { sequelizeTypescript } from '../../../initializers/database'
import { VideoAbuseModel } from '../../../models/video/video-abuse'
import { getOrCreateVideoAndAccountAndChannel } from '../videos'
import { Notifier } from '../../notifier'
import { ActivityFollow } from '../../../../shared/models/activitypub'
import { retryTransactionWrapper } from '../../../helpers/database-utils'
import { logger } from '../../../helpers/logger'
-import { sequelizeTypescript } from '../../../initializers'
+import { sequelizeTypescript } from '../../../initializers/database'
import { ActorModel } from '../../../models/activitypub/actor'
import { ActorFollowModel } from '../../../models/activitypub/actor-follow'
import { sendAccept, sendReject } from '../send'
import { ActivityLike } from '../../../../shared/models/activitypub'
import { retryTransactionWrapper } from '../../../helpers/database-utils'
-import { sequelizeTypescript } from '../../../initializers'
+import { sequelizeTypescript } from '../../../initializers/database'
import { AccountVideoRateModel } from '../../../models/account/account-video-rate'
import { forwardVideoRelatedActivity } from '../send/utils'
import { getOrCreateVideoAndAccountAndChannel } from '../videos'
import { ActivityReject } from '../../../../shared/models/activitypub/activity'
-import { sequelizeTypescript } from '../../../initializers'
+import { sequelizeTypescript } from '../../../initializers/database'
import { ActorFollowModel } from '../../../models/activitypub/actor-follow'
import { APProcessorOptions } from '../../../typings/activitypub-processor.model'
import { MActor } from '../../../typings/models'
import { DislikeObject } from '../../../../shared/models/activitypub/objects'
import { retryTransactionWrapper } from '../../../helpers/database-utils'
import { logger } from '../../../helpers/logger'
-import { sequelizeTypescript } from '../../../initializers'
+import { sequelizeTypescript } from '../../../initializers/database'
import { AccountVideoRateModel } from '../../../models/account/account-video-rate'
import { ActorModel } from '../../../models/activitypub/actor'
import { ActorFollowModel } from '../../../models/activitypub/actor-follow'
import { ActivityPubActor } from '../../../../shared/models/activitypub/activitypub-actor'
import { resetSequelizeInstance, retryTransactionWrapper } from '../../../helpers/database-utils'
import { logger } from '../../../helpers/logger'
-import { sequelizeTypescript } from '../../../initializers'
+import { sequelizeTypescript } from '../../../initializers/database'
import { AccountModel } from '../../../models/account/account'
import { ActorModel } from '../../../models/activitypub/actor'
import { VideoChannelModel } from '../../../models/video/video-channel'
-import { sequelizeTypescript } from '../initializers'
+import { sequelizeTypescript } from '@server/initializers/database'
+import { MAccountBlocklist, MServerBlocklist } from '@server/typings/models'
import { AccountBlocklistModel } from '../models/account/account-blocklist'
import { ServerBlocklistModel } from '../models/server/server-blocklist'
-import { MAccountBlocklist, MServerBlocklist } from '@server/typings/models'
function addAccountInBlocklist (byAccountId: number, targetAccountId: number) {
return sequelizeTypescript.transaction(async t => {
import { JobQueue } from '../job-queue'
import { federateVideoIfNeeded } from '../../activitypub/videos'
import { retryTransactionWrapper } from '../../../helpers/database-utils'
-import { sequelizeTypescript } from '../../../initializers'
+import { sequelizeTypescript } from '../../../initializers/database'
import { computeResolutionsToTranscode } from '../../../helpers/ffmpeg-utils'
import { generateHlsPlaylist, mergeAudioVideofile, optimizeOriginalVideofile, transcodeNewResolution } from '../../video-transcoding'
import { Notifier } from '../../notifier'
import { buildLogger } from '@server/helpers/logger'
import { VideoModel } from '@server/models/video/video'
import { WEBSERVER } from '@server/initializers/constants'
+import { ServerModel } from '@server/models/server/server'
+import { getServerActor } from '@server/models/application/application'
+import { addServerInBlocklist, removeServerFromBlocklist, addAccountInBlocklist, removeAccountFromBlocklist } from '../blocklist'
+import { ServerBlocklistModel } from '@server/models/server/server-blocklist'
+import { AccountModel } from '@server/models/account/account'
+import { VideoBlacklistCreate } from '@shared/models'
+import { blacklistVideo, unblacklistVideo } from '../video-blacklist'
+import { VideoBlacklistModel } from '@server/models/video/video-blacklist'
+import { AccountBlocklistModel } from '@server/models/account/account-blocklist'
function buildPluginHelpers (npmName: string): PeerTubeHelpers {
const logger = buildPluginLogger(npmName)
const config = buildConfigHelpers()
+ const server = buildServerHelpers()
+
+ const moderation = buildModerationHelpers()
+
return {
logger,
database,
videos,
- config
+ config,
+ moderation,
+ server
}
}
}
}
+function buildServerHelpers () {
+ return {
+ getServerActor: () => getServerActor()
+ }
+}
+
function buildVideosHelpers () {
return {
+ loadByUrl: (url: string) => {
+ return VideoModel.loadByUrl(url)
+ },
+
removeVideo: (id: number) => {
return sequelizeTypescript.transaction(async t => {
const video = await VideoModel.loadAndPopulateAccountAndServerAndTags(id, t)
}
}
+function buildModerationHelpers () {
+ return {
+ blockServer: async (options: { byAccountId: number, hostToBlock: string }) => {
+ const serverToBlock = await ServerModel.loadOrCreateByHost(options.hostToBlock)
+
+ await addServerInBlocklist(options.byAccountId, serverToBlock.id)
+ },
+
+ unblockServer: async (options: { byAccountId: number, hostToUnblock: string }) => {
+ const serverBlock = await ServerBlocklistModel.loadByAccountAndHost(options.byAccountId, options.hostToUnblock)
+ if (!serverBlock) return
+
+ await removeServerFromBlocklist(serverBlock)
+ },
+
+ blockAccount: async (options: { byAccountId: number, handleToBlock: string }) => {
+ const accountToBlock = await AccountModel.loadByNameWithHost(options.handleToBlock)
+ if (!accountToBlock) return
+
+ await addAccountInBlocklist(options.byAccountId, accountToBlock.id)
+ },
+
+ unblockAccount: async (options: { byAccountId: number, handleToUnblock: string }) => {
+ const targetAccount = await AccountModel.loadByNameWithHost(options.handleToUnblock)
+ if (!targetAccount) return
+
+ const accountBlock = await AccountBlocklistModel.loadByAccountAndTarget(options.byAccountId, targetAccount.id)
+ if (!accountBlock) return
+
+ await removeAccountFromBlocklist(accountBlock)
+ },
+
+ blacklistVideo: async (options: { videoIdOrUUID: number | string, createOptions: VideoBlacklistCreate }) => {
+ const video = await VideoModel.loadAndPopulateAccountAndServerAndTags(options.videoIdOrUUID)
+ if (!video) return
+
+ await blacklistVideo(video, options.createOptions)
+ },
+
+ unblacklistVideo: async (options: { videoIdOrUUID: number | string }) => {
+ const video = await VideoModel.loadAndPopulateAccountAndServerAndTags(options.videoIdOrUUID)
+ if (!video) return
+
+ const videoBlacklist = await VideoBlacklistModel.loadByVideoId(video.id)
+ if (!videoBlacklist) return
+
+ await unblacklistVideo(videoBlacklist, video)
+ }
+ }
+}
+
function buildConfigHelpers () {
return {
getWebserverUrl () {
import { Transaction } from 'sequelize'
+import { sequelizeTypescript } from '@server/initializers/database'
+import {
+ MUser,
+ MVideoAccountLight,
+ MVideoBlacklist,
+ MVideoBlacklistVideo,
+ MVideoFullLight,
+ MVideoWithBlacklistLight
+} from '@server/typings/models'
+import { UserRight, VideoBlacklistCreate, VideoBlacklistType } from '../../shared/models'
+import { UserAdminFlag } from '../../shared/models/users/user-flag.model'
+import { logger } from '../helpers/logger'
import { CONFIG } from '../initializers/config'
-import { UserRight, VideoBlacklistType } from '../../shared/models'
import { VideoBlacklistModel } from '../models/video/video-blacklist'
-import { logger } from '../helpers/logger'
-import { UserAdminFlag } from '../../shared/models/users/user-flag.model'
-import { Hooks } from './plugins/hooks'
+import { sendDeleteVideo } from './activitypub/send'
+import { federateVideoIfNeeded } from './activitypub/videos'
import { Notifier } from './notifier'
-import { MUser, MVideoBlacklistVideo, MVideoWithBlacklistLight } from '@server/typings/models'
+import { Hooks } from './plugins/hooks'
async function autoBlacklistVideoIfNeeded (parameters: {
video: MVideoWithBlacklistLight
return true
}
+async function blacklistVideo (videoInstance: MVideoAccountLight, options: VideoBlacklistCreate) {
+ const blacklist: MVideoBlacklistVideo = await VideoBlacklistModel.create({
+ videoId: videoInstance.id,
+ unfederated: options.unfederate === true,
+ reason: options.reason,
+ type: VideoBlacklistType.MANUAL
+ }
+ )
+ blacklist.Video = videoInstance
+
+ if (options.unfederate === true) {
+ await sendDeleteVideo(videoInstance, undefined)
+ }
+
+ Notifier.Instance.notifyOnVideoBlacklist(blacklist)
+}
+
+async function unblacklistVideo (videoBlacklist: MVideoBlacklist, video: MVideoFullLight) {
+ const videoBlacklistType = await sequelizeTypescript.transaction(async t => {
+ const unfederated = videoBlacklist.unfederated
+ const videoBlacklistType = videoBlacklist.type
+
+ await videoBlacklist.destroy({ transaction: t })
+ video.VideoBlacklist = undefined
+
+ // Re federate the video
+ if (unfederated === true) {
+ await federateVideoIfNeeded(video, true, t)
+ }
+
+ return videoBlacklistType
+ })
+
+ Notifier.Instance.notifyOnVideoUnblacklist(video)
+
+ if (videoBlacklistType === VideoBlacklistType.AUTO_BEFORE_PUBLISHED) {
+ Notifier.Instance.notifyOnVideoPublishedAfterRemovedFromAutoBlacklist(video)
+
+ // Delete on object so new video notifications will send
+ delete video.VideoBlacklist
+ Notifier.Instance.notifyOnNewVideoIfNeeded(video)
+ }
+}
+
+// ---------------------------------------------------------------------------
+
+export {
+ autoBlacklistVideoIfNeeded,
+ blacklistVideo,
+ unblacklistVideo
+}
+
+// ---------------------------------------------------------------------------
+
function autoBlacklistNeeded (parameters: {
video: MVideoWithBlacklistLight
isRemote: boolean
return true
}
-
-// ---------------------------------------------------------------------------
-
-export {
- autoBlacklistVideoIfNeeded
-}
.end()
}
- let server = await ServerModel.loadByHost(host)
- if (!server) {
- server = await ServerModel.create({ host })
- }
+ const server = await ServerModel.loadOrCreateByHost(host)
res.locals.server = server
return ServerModel.findOne(query)
}
+ static async loadOrCreateByHost (host: string) {
+ let server = await ServerModel.loadByHost(host)
+ if (!server) server = await ServerModel.create({ host })
+
+ return server
+ }
+
isBlocked () {
return this.BlockedByAccounts && this.BlockedByAccounts.length !== 0
}
async function register ({
peertubeHelpers,
- registerHook
+ registerHook,
+ getRouter
}) {
const logger = peertubeHelpers.logger
logger.info('Hello world from plugin four')
- const username = 'root'
- const results = await peertubeHelpers.database.query(
- 'SELECT "email" from "user" WHERE "username" = $username',
- {
- type: 'SELECT',
- bind: { username }
- }
- )
+ {
+ const username = 'root'
+ const results = await peertubeHelpers.database.query(
+ 'SELECT "email" from "user" WHERE "username" = $username',
+ {
+ type: 'SELECT',
+ bind: { username }
+ }
+ )
+
+ logger.info('root email is ' + results[0]['email'])
+ }
+
+ {
+ registerHook({
+ target: 'action:api.video.viewed',
+ handler: async ({ video }) => {
+ const videoFromDB = await peertubeHelpers.videos.loadByUrl(video.url)
+ logger.info('video from DB uuid is %s.', videoFromDB.uuid)
+
+ await peertubeHelpers.videos.removeVideo(video.id)
- logger.info('root email is ' + results[0]['email'])
+ logger.info('Video deleted by plugin four.')
+ }
+ })
+ }
- registerHook({
- target: 'action:api.video.viewed',
- handler: async ({ video }) => {
- await peertubeHelpers.videos.removeVideo(video.id)
+ {
+ const serverActor = await peertubeHelpers.server.getServerActor()
+ logger.info('server actor name is %s', serverActor.preferredUsername)
+ }
- logger.info('Video deleted by plugin four.')
+ {
+ logger.info('server url is %s', peertubeHelpers.config.getWebserverUrl())
+ }
+
+ {
+ const actions = {
+ blockServer,
+ unblockServer,
+ blockAccount,
+ unblockAccount,
+ blacklist,
+ unblacklist
}
- })
+
+ const router = getRouter()
+ router.post('/commander', async (req, res) => {
+ try {
+ await actions[req.body.command](peertubeHelpers, req.body)
+
+ res.sendStatus(204)
+ } catch (err) {
+ logger.error('Error in commander.', { err })
+ res.sendStatus(500)
+ }
+ })
+ }
}
async function unregister () {
}
// ###########################################################################
+
+async function blockServer (peertubeHelpers, body) {
+ const serverActor = await peertubeHelpers.server.getServerActor()
+
+ await peertubeHelpers.moderation.blockServer({ byAccountId: serverActor.Account.id, hostToBlock: body.hostToBlock })
+}
+
+async function unblockServer (peertubeHelpers, body) {
+ const serverActor = await peertubeHelpers.server.getServerActor()
+
+ await peertubeHelpers.moderation.unblockServer({ byAccountId: serverActor.Account.id, hostToUnblock: body.hostToUnblock })
+}
+
+async function blockAccount (peertubeHelpers, body) {
+ const serverActor = await peertubeHelpers.server.getServerActor()
+
+ await peertubeHelpers.moderation.blockAccount({ byAccountId: serverActor.Account.id, handleToBlock: body.handleToBlock })
+}
+
+async function unblockAccount (peertubeHelpers, body) {
+ const serverActor = await peertubeHelpers.server.getServerActor()
+
+ await peertubeHelpers.moderation.unblockAccount({ byAccountId: serverActor.Account.id, handleToUnblock: body.handleToUnblock })
+}
+
+async function blacklist (peertubeHelpers, body) {
+ await peertubeHelpers.moderation.blacklistVideo({
+ videoIdOrUUID: body.videoUUID,
+ createOptions: body
+ })
+}
+
+async function unblacklist (peertubeHelpers, body) {
+ await peertubeHelpers.moderation.unblacklistVideo({ videoIdOrUUID: body.videoUUID })
+}
/* eslint-disable @typescript-eslint/no-unused-expressions,@typescript-eslint/require-await */
import 'mocha'
-import { cleanupTests, flushAndRunServer, ServerInfo, waitUntilLog } from '../../../shared/extra-utils/server/servers'
import {
checkVideoFilesWereRemoved,
+ doubleFollow,
getPluginTestPath,
getVideo,
installPlugin,
+ makePostBodyRequest,
setAccessTokensToServers,
uploadVideoAndGetId,
- viewVideo
+ viewVideo,
+ getVideosList,
+ waitJobs
} from '../../../shared/extra-utils'
+import { cleanupTests, flushAndRunMultipleServers, ServerInfo, waitUntilLog } from '../../../shared/extra-utils/server/servers'
+import { expect } from 'chai'
+
+function postCommand (server: ServerInfo, command: string, bodyArg?: object) {
+ const body = { command }
+ if (bodyArg) Object.assign(body, bodyArg)
+
+ return makePostBodyRequest({
+ url: server.url,
+ path: '/plugins/test-four/router/commander',
+ fields: body,
+ statusCodeExpected: 204
+ })
+}
describe('Test plugin helpers', function () {
- let server: ServerInfo
+ let servers: ServerInfo[]
before(async function () {
- this.timeout(30000)
+ this.timeout(60000)
+
+ servers = await flushAndRunMultipleServers(2)
+ await setAccessTokensToServers(servers)
- server = await flushAndRunServer(1)
- await setAccessTokensToServers([ server ])
+ await doubleFollow(servers[0], servers[1])
await installPlugin({
- url: server.url,
- accessToken: server.accessToken,
+ url: servers[0].url,
+ accessToken: servers[0].accessToken,
path: getPluginTestPath('-four')
})
})
- it('Should have logged things', async function () {
- await waitUntilLog(server, 'localhost:' + server.port + ' peertube-plugin-test-four', 1, false)
- await waitUntilLog(server, 'Hello world from plugin four', 1)
+ describe('Logger', function () {
+
+ it('Should have logged things', async function () {
+ await waitUntilLog(servers[0], 'localhost:' + servers[0].port + ' peertube-plugin-test-four', 1, false)
+ await waitUntilLog(servers[0], 'Hello world from plugin four', 1)
+ })
})
- it('Should have made a query', async function () {
- await waitUntilLog(server, `root email is admin${server.internalServerNumber}@example.com`, 1)
+ describe('Database', function () {
+
+ it('Should have made a query', async function () {
+ await waitUntilLog(servers[0], `root email is admin${servers[0].internalServerNumber}@example.com`)
+ })
+ })
+
+ describe('Config', function () {
+
+ it('Should have the correct webserver url', async function () {
+ await waitUntilLog(servers[0], `server url is http://localhost:${servers[0].port}`)
+ })
+ })
+
+ describe('Server', function () {
+
+ it('Should get the server actor', async function () {
+ await waitUntilLog(servers[0], 'server actor name is peertube')
+ })
+ })
+
+ describe('Moderation', function () {
+ let videoUUIDServer1: string
+
+ before(async function () {
+ this.timeout(15000)
+
+ {
+ const res = await uploadVideoAndGetId({ server: servers[0], videoName: 'video server 1' })
+ videoUUIDServer1 = res.uuid
+ }
+
+ {
+ await uploadVideoAndGetId({ server: servers[1], videoName: 'video server 2' })
+ }
+
+ await waitJobs(servers)
+
+ const res = await getVideosList(servers[0].url)
+ const videos = res.body.data
+
+ expect(videos).to.have.lengthOf(2)
+ })
+
+ it('Should mute server 2', async function () {
+ this.timeout(10000)
+ await postCommand(servers[0], 'blockServer', { hostToBlock: `localhost:${servers[1].port}` })
+
+ const res = await getVideosList(servers[0].url)
+ const videos = res.body.data
+
+ expect(videos).to.have.lengthOf(1)
+ expect(videos[0].name).to.equal('video server 1')
+ })
+
+ it('Should unmute server 2', async function () {
+ await postCommand(servers[0], 'unblockServer', { hostToUnblock: `localhost:${servers[1].port}` })
+
+ const res = await getVideosList(servers[0].url)
+ const videos = res.body.data
+
+ expect(videos).to.have.lengthOf(2)
+ })
+
+ it('Should mute account of server 2', async function () {
+ await postCommand(servers[0], 'blockAccount', { handleToBlock: `root@localhost:${servers[1].port}` })
+
+ const res = await getVideosList(servers[0].url)
+ const videos = res.body.data
+
+ expect(videos).to.have.lengthOf(1)
+ expect(videos[0].name).to.equal('video server 1')
+ })
+
+ it('Should unmute account of server 2', async function () {
+ await postCommand(servers[0], 'unblockAccount', { handleToUnblock: `root@localhost:${servers[1].port}` })
+
+ const res = await getVideosList(servers[0].url)
+ const videos = res.body.data
+
+ expect(videos).to.have.lengthOf(2)
+ })
+
+ it('Should blacklist video', async function () {
+ this.timeout(10000)
+
+ await postCommand(servers[0], 'blacklist', { videoUUID: videoUUIDServer1, unfederate: true })
+
+ await waitJobs(servers)
+
+ for (const server of servers) {
+ const res = await getVideosList(server.url)
+ const videos = res.body.data
+
+ expect(videos).to.have.lengthOf(1)
+ expect(videos[0].name).to.equal('video server 2')
+ }
+ })
+
+ it('Should unblacklist video', async function () {
+ this.timeout(10000)
+
+ await postCommand(servers[0], 'unblacklist', { videoUUID: videoUUIDServer1 })
+
+ await waitJobs(servers)
+
+ for (const server of servers) {
+ const res = await getVideosList(server.url)
+ const videos = res.body.data
+
+ expect(videos).to.have.lengthOf(2)
+ }
+ })
})
- it('Should remove a video after a view', async function () {
- this.timeout(20000)
+ describe('Videos', function () {
+ let videoUUID: string
+
+ before(async () => {
+ const res = await uploadVideoAndGetId({ server: servers[0], videoName: 'video1' })
+ videoUUID = res.uuid
+ })
- const videoUUID = (await uploadVideoAndGetId({ server: server, videoName: 'video1' })).uuid
+ it('Should remove a video after a view', async function () {
+ this.timeout(20000)
- // Should not throw -> video exists
- await getVideo(server.url, videoUUID)
- // Should delete the video
- await viewVideo(server.url, videoUUID)
+ // Should not throw -> video exists
+ await getVideo(servers[0].url, videoUUID)
+ // Should delete the video
+ await viewVideo(servers[0].url, videoUUID)
- await waitUntilLog(server, 'Video deleted by plugin four.', 1)
+ await waitUntilLog(servers[0], 'Video deleted by plugin four.')
- try {
- // Should throw because the video should have been deleted
- await getVideo(server.url, videoUUID)
- throw new Error('Video exists')
- } catch (err) {
- if (err.message.includes('exists')) throw err
- }
+ try {
+ // Should throw because the video should have been deleted
+ await getVideo(servers[0].url, videoUUID)
+ throw new Error('Video exists')
+ } catch (err) {
+ if (err.message.includes('exists')) throw err
+ }
- await checkVideoFilesWereRemoved(videoUUID, server.internalServerNumber)
+ await checkVideoFilesWereRemoved(videoUUID, servers[0].internalServerNumber)
+ })
+
+ it('Should have fetched the video by URL', async function () {
+ await waitUntilLog(servers[0], `video from DB uuid is ${videoUUID}`)
+ })
})
after(async function () {
- await cleanupTests([ server ])
+ await cleanupTests(servers)
})
})
-import { PluginSettingsManager } from '../../../shared/models/plugins/plugin-settings-manager.model'
-import { PluginStorageManager } from '../../../shared/models/plugins/plugin-storage-manager.model'
-import { RegisterServerHookOptions } from '../../../shared/models/plugins/register-server-hook.model'
-import { RegisterServerSettingOptions } from '../../../shared/models/plugins/register-server-setting.model'
-import { PluginVideoCategoryManager } from '../../../shared/models/plugins/plugin-video-category-manager.model'
-import { PluginVideoLanguageManager } from '../../../shared/models/plugins/plugin-video-language-manager.model'
-import { PluginVideoLicenceManager } from '../../../shared/models/plugins/plugin-video-licence-manager.model'
-import { Logger } from 'winston'
+import * as Bluebird from 'bluebird'
import { Router } from 'express'
-import { PluginVideoPrivacyManager } from '@shared/models/plugins/plugin-video-privacy-manager.model'
+import { Logger } from 'winston'
+import { ActorModel } from '@server/models/activitypub/actor'
+import { VideoBlacklistCreate } from '@shared/models'
import { PluginPlaylistPrivacyManager } from '@shared/models/plugins/plugin-playlist-privacy-manager.model'
+import { PluginVideoPrivacyManager } from '@shared/models/plugins/plugin-video-privacy-manager.model'
import {
RegisterServerAuthExternalOptions,
RegisterServerAuthExternalResult,
RegisterServerAuthPassOptions
} from '@shared/models/plugins/register-server-auth.model'
+import { PluginSettingsManager } from '../../../shared/models/plugins/plugin-settings-manager.model'
+import { PluginStorageManager } from '../../../shared/models/plugins/plugin-storage-manager.model'
+import { PluginVideoCategoryManager } from '../../../shared/models/plugins/plugin-video-category-manager.model'
+import { PluginVideoLanguageManager } from '../../../shared/models/plugins/plugin-video-language-manager.model'
+import { PluginVideoLicenceManager } from '../../../shared/models/plugins/plugin-video-licence-manager.model'
+import { RegisterServerHookOptions } from '../../../shared/models/plugins/register-server-hook.model'
+import { RegisterServerSettingOptions } from '../../../shared/models/plugins/register-server-setting.model'
+import { MVideoThumbnail } from '../models'
export type PeerTubeHelpers = {
logger: Logger
}
videos: {
+ loadByUrl: (url: string) => Bluebird<MVideoThumbnail>
+
removeVideo: (videoId: number) => Promise<void>
}
config: {
getWebserverUrl: () => string
}
+
+ moderation: {
+ blockServer: (options: { byAccountId: number, hostToBlock: string }) => Promise<void>
+ unblockServer: (options: { byAccountId: number, hostToUnblock: string }) => Promise<void>
+ blockAccount: (options: { byAccountId: number, handleToBlock: string }) => Promise<void>
+ unblockAccount: (options: { byAccountId: number, handleToUnblock: string }) => Promise<void>
+
+ blacklistVideo: (options: { videoIdOrUUID: number | string, createOptions: VideoBlacklistCreate }) => Promise<void>
+ unblacklistVideo: (options: { videoIdOrUUID: number | string }) => Promise<void>
+ }
+
+ server: {
+ getServerActor: () => Promise<ActorModel>
+ }
}
export type RegisterServerOptions = {