Some refactoring.
This commit is contained in:
parent
2e98d930d3
commit
995dfa4dff
@ -5,6 +5,7 @@
|
||||
## New Features
|
||||
|
||||
* Implementing the [FEP-1970](https://codeberg.org/fediverse/fep/src/branch/main/fep/1970/fep-1970.md) draft for ActivityPub chat declaration.
|
||||
* Podcast RSS feed support (thanks to [Alecks Gates](https://github.com/agates)).
|
||||
|
||||
## 7.1.0
|
||||
|
||||
|
88
package-lock.json
generated
88
package-lock.json
generated
@ -18,7 +18,7 @@
|
||||
},
|
||||
"devDependencies": {
|
||||
"@peertube/feed": "^5.1.0",
|
||||
"@peertube/peertube-types": "^5.1.0",
|
||||
"@peertube/peertube-types": "^5.2.0",
|
||||
"@tsconfig/node12": "^1.0.9",
|
||||
"@types/async": "^3.2.9",
|
||||
"@types/express": "^4.17.13",
|
||||
@ -2571,15 +2571,16 @@
|
||||
}
|
||||
},
|
||||
"node_modules/@peertube/peertube-types": {
|
||||
"version": "5.1.0",
|
||||
"resolved": "https://registry.npmjs.org/@peertube/peertube-types/-/peertube-types-5.1.0.tgz",
|
||||
"integrity": "sha512-n0FMlKzHae/HuBXXeUd5nWUmBN+BMiyRkwftRquFqyQObwTwltqUooL+DBcjetFsRmPTObvF4kPccQ7LTLqkXQ==",
|
||||
"version": "5.2.0",
|
||||
"resolved": "https://registry.npmjs.org/@peertube/peertube-types/-/peertube-types-5.2.0.tgz",
|
||||
"integrity": "sha512-t5o/W4cF+E8FJXvFKBuGuCGU01Ad7jodyO7go//UYzgTde4CpxVJIE4G/8fKB30Kl0GCtqm2gncj31gilxZJ0g==",
|
||||
"dev": true,
|
||||
"dependencies": {
|
||||
"@aws-sdk/client-s3": "^3.190.0",
|
||||
"@node-oauth/oauth2-server": "^4.2.0",
|
||||
"@opentelemetry/api": "^1.1.0",
|
||||
"@opentelemetry/sdk-metrics": "^1.8.0",
|
||||
"@peertube/feed": "^5.1.0",
|
||||
"@types/bluebird": "^3.5.33",
|
||||
"@types/express": "4.17.9",
|
||||
"@types/fluent-ffmpeg": "^2.1.16",
|
||||
@ -2594,25 +2595,25 @@
|
||||
"bullmq": "^3.6.6",
|
||||
"execa": "^5.1.1",
|
||||
"express": "^4.18.1",
|
||||
"express-validator": "^6.4.0",
|
||||
"express-validator": "^7.0.1",
|
||||
"fluent-ffmpeg": "^2.1.0",
|
||||
"fs-extra": "^11.1.0",
|
||||
"got": "^11.8.2",
|
||||
"hpagent": "^1.0.0",
|
||||
"ioredis": "^5.2.3",
|
||||
"lru-cache": "^7.13.0",
|
||||
"lru-cache": "^9.1.1",
|
||||
"memoizee": "^0.4.14",
|
||||
"multer": "^1.4.5-lts.1",
|
||||
"parse-torrent": "^9.1.0",
|
||||
"parse-torrent": "^9",
|
||||
"reflect-metadata": "^0.1.12",
|
||||
"sequelize": "6.29.0",
|
||||
"sequelize": "6.31.1",
|
||||
"sequelize-typescript": "^2.0.0-beta.1",
|
||||
"short-uuid": "^4.2.0",
|
||||
"socket.io": "^4.5.4",
|
||||
"winston": "3.8.2"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=12.x",
|
||||
"node": ">=16.x",
|
||||
"yarn": ">=1.x"
|
||||
}
|
||||
},
|
||||
@ -2635,12 +2636,12 @@
|
||||
"dev": true
|
||||
},
|
||||
"node_modules/@peertube/peertube-types/node_modules/lru-cache": {
|
||||
"version": "7.14.1",
|
||||
"resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-7.14.1.tgz",
|
||||
"integrity": "sha512-ysxwsnTKdAx96aTRdhDOCQfDgbHnt8SK0KY8SEjO0wHinhWOFTESbjVCMPbU1uGXg/ch4lifqx0wfjOawU2+WA==",
|
||||
"version": "9.1.2",
|
||||
"resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-9.1.2.tgz",
|
||||
"integrity": "sha512-ERJq3FOzJTxBbFjZ7iDs+NiK4VI9Wz+RdrrAB8dio1oV+YvdPzUEE4QNiT2VD51DkIbCYRUUzCRkssXCHqSnKQ==",
|
||||
"dev": true,
|
||||
"engines": {
|
||||
"node": ">=12"
|
||||
"node": "14 || >=16.14"
|
||||
}
|
||||
},
|
||||
"node_modules/@sindresorhus/is": {
|
||||
@ -5749,13 +5750,13 @@
|
||||
}
|
||||
},
|
||||
"node_modules/express-validator": {
|
||||
"version": "6.14.0",
|
||||
"resolved": "https://registry.npmjs.org/express-validator/-/express-validator-6.14.0.tgz",
|
||||
"integrity": "sha512-ZWHJfnRgePp3FKRSKMtnZVnD1s8ZchWD+jSl7UMseGIqhweCo1Z9916/xXBbJAa6PrA3pUZfkOvIsHZG4ZtIMw==",
|
||||
"version": "7.0.1",
|
||||
"resolved": "https://registry.npmjs.org/express-validator/-/express-validator-7.0.1.tgz",
|
||||
"integrity": "sha512-oB+z9QOzQIE8FnlINqyIFA8eIckahC6qc8KtqLdLJcU3/phVyuhXH3bA4qzcrhme+1RYaCSwrq+TlZ/kAKIARA==",
|
||||
"dev": true,
|
||||
"dependencies": {
|
||||
"lodash": "^4.17.21",
|
||||
"validator": "^13.7.0"
|
||||
"validator": "^13.9.0"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">= 8.0.0"
|
||||
@ -8863,9 +8864,9 @@
|
||||
"dev": true
|
||||
},
|
||||
"node_modules/sequelize": {
|
||||
"version": "6.29.0",
|
||||
"resolved": "https://registry.npmjs.org/sequelize/-/sequelize-6.29.0.tgz",
|
||||
"integrity": "sha512-m8Wi90rs3NZP9coXE52c7PL4Q078nwYZXqt1IxPvgki7nOFn0p/F0eKsYDBXCPw9G8/BCEa6zZNk0DQUAT4ypA==",
|
||||
"version": "6.31.1",
|
||||
"resolved": "https://registry.npmjs.org/sequelize/-/sequelize-6.31.1.tgz",
|
||||
"integrity": "sha512-cahWtRrYLjqoZP/aurGBoaxn29qQCF4bxkAUPEQ/ozjJjt6mtL4Q113S3N39mQRmX5fgxRbli+bzZARP/N51eg==",
|
||||
"dev": true,
|
||||
"funding": [
|
||||
{
|
||||
@ -10295,9 +10296,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/validator": {
|
||||
"version": "13.7.0",
|
||||
"resolved": "https://registry.npmjs.org/validator/-/validator-13.7.0.tgz",
|
||||
"integrity": "sha512-nYXQLCBkpJ8X6ltALua9dRrZDHVYxjJ1wgskNt1lH9fzGjs3tgojGSCBjmEPwkWS1y29+DrizMTW19Pr9uB2nw==",
|
||||
"version": "13.9.0",
|
||||
"resolved": "https://registry.npmjs.org/validator/-/validator-13.9.0.tgz",
|
||||
"integrity": "sha512-B+dGG8U3fdtM0/aNK4/X8CXq/EcxU2WPrPEkJGslb47qyHsxmbggTWK0yEA4qnYVNF+nxNlN88o14hIcPmSIEA==",
|
||||
"dev": true,
|
||||
"engines": {
|
||||
"node": ">= 0.10"
|
||||
@ -12652,15 +12653,16 @@
|
||||
}
|
||||
},
|
||||
"@peertube/peertube-types": {
|
||||
"version": "5.1.0",
|
||||
"resolved": "https://registry.npmjs.org/@peertube/peertube-types/-/peertube-types-5.1.0.tgz",
|
||||
"integrity": "sha512-n0FMlKzHae/HuBXXeUd5nWUmBN+BMiyRkwftRquFqyQObwTwltqUooL+DBcjetFsRmPTObvF4kPccQ7LTLqkXQ==",
|
||||
"version": "5.2.0",
|
||||
"resolved": "https://registry.npmjs.org/@peertube/peertube-types/-/peertube-types-5.2.0.tgz",
|
||||
"integrity": "sha512-t5o/W4cF+E8FJXvFKBuGuCGU01Ad7jodyO7go//UYzgTde4CpxVJIE4G/8fKB30Kl0GCtqm2gncj31gilxZJ0g==",
|
||||
"dev": true,
|
||||
"requires": {
|
||||
"@aws-sdk/client-s3": "^3.190.0",
|
||||
"@node-oauth/oauth2-server": "^4.2.0",
|
||||
"@opentelemetry/api": "^1.1.0",
|
||||
"@opentelemetry/sdk-metrics": "^1.8.0",
|
||||
"@peertube/feed": "^5.1.0",
|
||||
"@types/bluebird": "^3.5.33",
|
||||
"@types/express": "4.17.9",
|
||||
"@types/fluent-ffmpeg": "^2.1.16",
|
||||
@ -12675,18 +12677,18 @@
|
||||
"bullmq": "^3.6.6",
|
||||
"execa": "^5.1.1",
|
||||
"express": "^4.18.1",
|
||||
"express-validator": "^6.4.0",
|
||||
"express-validator": "^7.0.1",
|
||||
"fluent-ffmpeg": "^2.1.0",
|
||||
"fs-extra": "^11.1.0",
|
||||
"got": "^11.8.2",
|
||||
"hpagent": "^1.0.0",
|
||||
"ioredis": "^5.2.3",
|
||||
"lru-cache": "^7.13.0",
|
||||
"lru-cache": "^9.1.1",
|
||||
"memoizee": "^0.4.14",
|
||||
"multer": "^1.4.5-lts.1",
|
||||
"parse-torrent": "^9.1.0",
|
||||
"parse-torrent": "^9",
|
||||
"reflect-metadata": "^0.1.12",
|
||||
"sequelize": "6.29.0",
|
||||
"sequelize": "6.31.1",
|
||||
"sequelize-typescript": "^2.0.0-beta.1",
|
||||
"short-uuid": "^4.2.0",
|
||||
"socket.io": "^4.5.4",
|
||||
@ -12712,9 +12714,9 @@
|
||||
"dev": true
|
||||
},
|
||||
"lru-cache": {
|
||||
"version": "7.14.1",
|
||||
"resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-7.14.1.tgz",
|
||||
"integrity": "sha512-ysxwsnTKdAx96aTRdhDOCQfDgbHnt8SK0KY8SEjO0wHinhWOFTESbjVCMPbU1uGXg/ch4lifqx0wfjOawU2+WA==",
|
||||
"version": "9.1.2",
|
||||
"resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-9.1.2.tgz",
|
||||
"integrity": "sha512-ERJq3FOzJTxBbFjZ7iDs+NiK4VI9Wz+RdrrAB8dio1oV+YvdPzUEE4QNiT2VD51DkIbCYRUUzCRkssXCHqSnKQ==",
|
||||
"dev": true
|
||||
}
|
||||
}
|
||||
@ -15093,13 +15095,13 @@
|
||||
}
|
||||
},
|
||||
"express-validator": {
|
||||
"version": "6.14.0",
|
||||
"resolved": "https://registry.npmjs.org/express-validator/-/express-validator-6.14.0.tgz",
|
||||
"integrity": "sha512-ZWHJfnRgePp3FKRSKMtnZVnD1s8ZchWD+jSl7UMseGIqhweCo1Z9916/xXBbJAa6PrA3pUZfkOvIsHZG4ZtIMw==",
|
||||
"version": "7.0.1",
|
||||
"resolved": "https://registry.npmjs.org/express-validator/-/express-validator-7.0.1.tgz",
|
||||
"integrity": "sha512-oB+z9QOzQIE8FnlINqyIFA8eIckahC6qc8KtqLdLJcU3/phVyuhXH3bA4qzcrhme+1RYaCSwrq+TlZ/kAKIARA==",
|
||||
"dev": true,
|
||||
"requires": {
|
||||
"lodash": "^4.17.21",
|
||||
"validator": "^13.7.0"
|
||||
"validator": "^13.9.0"
|
||||
}
|
||||
},
|
||||
"ext": {
|
||||
@ -17367,9 +17369,9 @@
|
||||
}
|
||||
},
|
||||
"sequelize": {
|
||||
"version": "6.29.0",
|
||||
"resolved": "https://registry.npmjs.org/sequelize/-/sequelize-6.29.0.tgz",
|
||||
"integrity": "sha512-m8Wi90rs3NZP9coXE52c7PL4Q078nwYZXqt1IxPvgki7nOFn0p/F0eKsYDBXCPw9G8/BCEa6zZNk0DQUAT4ypA==",
|
||||
"version": "6.31.1",
|
||||
"resolved": "https://registry.npmjs.org/sequelize/-/sequelize-6.31.1.tgz",
|
||||
"integrity": "sha512-cahWtRrYLjqoZP/aurGBoaxn29qQCF4bxkAUPEQ/ozjJjt6mtL4Q113S3N39mQRmX5fgxRbli+bzZARP/N51eg==",
|
||||
"dev": true,
|
||||
"requires": {
|
||||
"@types/debug": "^4.1.7",
|
||||
@ -18449,9 +18451,9 @@
|
||||
}
|
||||
},
|
||||
"validator": {
|
||||
"version": "13.7.0",
|
||||
"resolved": "https://registry.npmjs.org/validator/-/validator-13.7.0.tgz",
|
||||
"integrity": "sha512-nYXQLCBkpJ8X6ltALua9dRrZDHVYxjJ1wgskNt1lH9fzGjs3tgojGSCBjmEPwkWS1y29+DrizMTW19Pr9uB2nw==",
|
||||
"version": "13.9.0",
|
||||
"resolved": "https://registry.npmjs.org/validator/-/validator-13.9.0.tgz",
|
||||
"integrity": "sha512-B+dGG8U3fdtM0/aNK4/X8CXq/EcxU2WPrPEkJGslb47qyHsxmbggTWK0yEA4qnYVNF+nxNlN88o14hIcPmSIEA==",
|
||||
"dev": true
|
||||
},
|
||||
"vary": {
|
||||
|
@ -41,7 +41,7 @@
|
||||
},
|
||||
"devDependencies": {
|
||||
"@peertube/feed": "^5.1.0",
|
||||
"@peertube/peertube-types": "^5.1.0",
|
||||
"@peertube/peertube-types": "^5.2.0",
|
||||
"@tsconfig/node12": "^1.0.9",
|
||||
"@types/async": "^3.2.9",
|
||||
"@types/express": "^4.17.13",
|
||||
@ -70,7 +70,7 @@
|
||||
"yaml": "^2.2.1"
|
||||
},
|
||||
"engine": {
|
||||
"peertube": ">=5.2.0"
|
||||
"peertube": ">=4.2.0"
|
||||
},
|
||||
"engines": {
|
||||
"npm": ">=7"
|
||||
|
87
server/lib/rss/init.ts
Normal file
87
server/lib/rss/init.ts
Normal file
@ -0,0 +1,87 @@
|
||||
import type { RegisterServerOptions, Video } from '@peertube/peertube-types'
|
||||
import type { CustomTag } from '@peertube/feed/lib/typings'
|
||||
import { videoHasWebchat } from '../../../shared/lib/video'
|
||||
import { fillVideoCustomFields } from '../custom-fields'
|
||||
import { getProsodyDomain } from '../prosody/config/domain'
|
||||
import { getPublicChatUri } from '../uri/webchat'
|
||||
|
||||
async function initRSS (options: RegisterServerOptions): Promise<void> {
|
||||
const logger = options.peertubeHelpers.logger
|
||||
const registerHook = options.registerHook
|
||||
logger.info('Registring RSS hooks...')
|
||||
|
||||
registerHook({
|
||||
target: 'filter:feed.podcast.video.create-custom-tags.result',
|
||||
handler: async (
|
||||
result: CustomTag[], { video, liveItem }: { video: Video, liveItem: boolean }
|
||||
): Promise<CustomTag[]> => {
|
||||
if (!liveItem) {
|
||||
// Note: the Podcast RSS feed specification does not handle chats for non-live.
|
||||
// So we just return here.
|
||||
return result
|
||||
}
|
||||
|
||||
// FIXME: calling getSettings for each RSS entry is not optimal.
|
||||
// Settings should be cached somewhere on the plugin level.
|
||||
// (i already have some plans to do something for this)
|
||||
const settings = await options.settingsManager.getSettings([
|
||||
'chat-per-live-video',
|
||||
'chat-all-lives',
|
||||
'chat-all-non-lives',
|
||||
'chat-videos-list',
|
||||
'prosody-room-type',
|
||||
'federation-dont-publish-remotely',
|
||||
'prosody-room-allow-s2s',
|
||||
'prosody-s2s-port'
|
||||
])
|
||||
|
||||
if (settings['federation-dont-publish-remotely']) {
|
||||
// Chat must not be published to the outer world.
|
||||
return result
|
||||
}
|
||||
|
||||
await fillVideoCustomFields(options, video)
|
||||
const hasChat = await videoHasWebchat({
|
||||
'chat-per-live-video': !!settings['chat-per-live-video'],
|
||||
'chat-all-lives': !!settings['chat-all-lives'],
|
||||
'chat-all-non-lives': !!settings['chat-all-non-lives'],
|
||||
'chat-videos-list': settings['chat-videos-list'] as string
|
||||
}, video)
|
||||
|
||||
if (!hasChat) {
|
||||
logger.debug(`Video uuid=${video.uuid} has not livechat, no need to add podcast:chat tag.`)
|
||||
return result
|
||||
}
|
||||
|
||||
const prosodyDomain = await getProsodyDomain(options)
|
||||
const podcastChat: any = {
|
||||
name: 'podcast:chat',
|
||||
attributes: {
|
||||
server: prosodyDomain,
|
||||
protocol: 'xmpp',
|
||||
// space: will be added only if external XMPP connections are available
|
||||
embedUrl: getPublicChatUri(options, video)
|
||||
}
|
||||
}
|
||||
|
||||
// In order to connect to the chat using standard xmpp, it requires these settings:
|
||||
// - prosody-room-allow-s2s
|
||||
// - prosody-s2s-port
|
||||
if (settings['prosody-room-allow-s2s'] && settings['prosody-s2s-port']) {
|
||||
let roomJID: string
|
||||
if (settings['prosody-room-type'] === 'channel') {
|
||||
roomJID = `channel.${video.channel.id}@room.${prosodyDomain}`
|
||||
} else {
|
||||
roomJID = `${video.uuid}@room.${prosodyDomain}`
|
||||
}
|
||||
podcastChat.attributes.space = roomJID
|
||||
}
|
||||
|
||||
return result.concat([podcastChat])
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
export {
|
||||
initRSS
|
||||
}
|
@ -1,5 +1,4 @@
|
||||
|
||||
import type { RegisterServerOptions, VideoObject } from '@peertube/peertube-types'
|
||||
import type { RegisterServerOptions, VideoObject, Video } from '@peertube/peertube-types'
|
||||
import { getBaseRouterRoute, getBaseWebSocketRoute } from '../helpers'
|
||||
import { canonicalizePluginUri } from './canonicalize'
|
||||
|
||||
@ -19,7 +18,7 @@ export function getWSS2SUri (options: RegisterServerOptions): string | undefined
|
||||
return base + 'xmpp-websocket-s2s'
|
||||
}
|
||||
|
||||
export function getPublicChatUri (options: RegisterServerOptions, video: VideoObject): string {
|
||||
export function getPublicChatUri (options: RegisterServerOptions, video: VideoObject | Video): string {
|
||||
const url = getBaseRouterRoute(options) + 'webchat/room/' + encodeURIComponent(video.uuid)
|
||||
return canonicalizePluginUri(options, url, {
|
||||
removePluginVersion: true
|
||||
|
@ -1,15 +1,14 @@
|
||||
import type { RegisterServerOptions, Video } from '@peertube/peertube-types'
|
||||
import type { RegisterServerOptions } from '@peertube/peertube-types'
|
||||
import { migrateSettings } from './lib/migration/settings'
|
||||
import { initSettings } from './lib/settings'
|
||||
import { initCustomFields } from './lib/custom-fields'
|
||||
import { initRouters } from './lib/routers/index'
|
||||
import { initFederation } from './lib/federation/init'
|
||||
import { initRSS } from './lib/rss/init'
|
||||
import { prepareProsody, ensureProsodyRunning, ensureProsodyNotRunning } from './lib/prosody/ctl'
|
||||
import { unloadDebugMode } from './lib/debug'
|
||||
import { loadLoc } from './lib/loc'
|
||||
import decache from 'decache'
|
||||
import { CustomTag } from '@peertube/feed/lib/typings'
|
||||
import { URL } from 'url'
|
||||
|
||||
// FIXME: Peertube unregister don't have any parameter.
|
||||
// Using this global variable to fix this, so we can use helpers to unregister.
|
||||
@ -32,33 +31,7 @@ async function register (options: RegisterServerOptions): Promise<any> {
|
||||
await initCustomFields(options)
|
||||
await initRouters(options)
|
||||
await initFederation(options)
|
||||
|
||||
options.registerHook({
|
||||
// @ts-expect-error Type doesn't exist for peertube 5.1 yet
|
||||
target: 'filter:feed.podcast.video.create-custom-tags.result',
|
||||
handler: (result: CustomTag[], { video, liveItem }: { video: Video, liveItem: boolean }) => {
|
||||
if (!liveItem) {
|
||||
return result
|
||||
}
|
||||
|
||||
const webserverUrl = options.peertubeHelpers.config.getWebserverUrl()
|
||||
const hostname = (new URL(webserverUrl)).hostname
|
||||
const embedUrl = `${webserverUrl}/plugins/livechat/router/webchat/room/${encodeURIComponent(video.uuid)}`
|
||||
const xmppRoom = `room.${hostname}`
|
||||
|
||||
return result.concat([
|
||||
{
|
||||
name: 'podcast:chat',
|
||||
attributes: {
|
||||
server: hostname,
|
||||
protocol: 'xmpp',
|
||||
space: `${video.uuid}@${xmppRoom}`,
|
||||
embedUrl: embedUrl
|
||||
}
|
||||
}
|
||||
])
|
||||
}
|
||||
})
|
||||
await initRSS(options)
|
||||
|
||||
try {
|
||||
await prepareProsody(options)
|
||||
|
@ -159,7 +159,7 @@ In the ActivityPub object, there is also a `peertubeLiveChat` entry.
|
||||
Don't use the content of this entry. This is specific to the livechat plugin, and can be changed or removed in a near future.
|
||||
It is currently required for some endpoint discovery.
|
||||
|
||||
### Using RSS
|
||||
### Using Podcast RSS feed
|
||||
|
||||
{{% notice warning %}}
|
||||
This part is not implemented yet, but should be available for v7.2.0 release.
|
||||
|
Loading…
x
Reference in New Issue
Block a user