mirror of
https://github.com/Chocobozzz/PeerTube.git
synced 2025-02-16 18:25:09 -06:00
Generate 600x600 and 1500x1500 avatars
This commit is contained in:
parent
fb2dc40858
commit
109e93c139
@ -21,7 +21,7 @@ export class ActorAvatarComponent implements OnInit, OnChanges {
|
||||
|
||||
@Input() previewImage: string
|
||||
|
||||
@Input({ transform: numberAttribute }) size: number
|
||||
@Input({ transform: numberAttribute }) size = 120
|
||||
|
||||
// Use an external link
|
||||
@Input() href: string
|
||||
|
@ -30,6 +30,16 @@ export class ConfigCommand extends AbstractCommand {
|
||||
}
|
||||
}
|
||||
|
||||
static getDisableRatesLimitOverrideConfig () {
|
||||
return {
|
||||
rates_limit: {
|
||||
api: {
|
||||
max: 5000
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// ---------------------------------------------------------------------------
|
||||
|
||||
enableSignup (requiresApproval: boolean, limit = -1) {
|
||||
|
BIN
packages/tests/fixtures/avatar-resized-1500x1500.png
vendored
Normal file
BIN
packages/tests/fixtures/avatar-resized-1500x1500.png
vendored
Normal file
Binary file not shown.
After Width: | Height: | Size: 75 KiB |
BIN
packages/tests/fixtures/avatar-resized-600x600.png
vendored
Normal file
BIN
packages/tests/fixtures/avatar-resized-600x600.png
vendored
Normal file
Binary file not shown.
After Width: | Height: | Size: 20 KiB |
BIN
packages/tests/fixtures/avatar2-resized-1500x1500.png
vendored
Normal file
BIN
packages/tests/fixtures/avatar2-resized-1500x1500.png
vendored
Normal file
Binary file not shown.
After Width: | Height: | Size: 80 KiB |
BIN
packages/tests/fixtures/avatar2-resized-600x600.png
vendored
Normal file
BIN
packages/tests/fixtures/avatar2-resized-600x600.png
vendored
Normal file
Binary file not shown.
After Width: | Height: | Size: 22 KiB |
@ -11,7 +11,7 @@ import {
|
||||
PeerTubeServer,
|
||||
setAccessTokensToServers
|
||||
} from '@peertube/peertube-server-commands'
|
||||
import { testFileExistsOrNot, testImage, testImageSize } from '@tests/shared/checks.js'
|
||||
import { testFileExistsOrNot, testImage, testAvatarSize } from '@tests/shared/checks.js'
|
||||
import { basename } from 'path'
|
||||
|
||||
function checkInitialConfig (server: PeerTubeServer, data: CustomConfig) {
|
||||
@ -739,7 +739,7 @@ describe('Test config', function () {
|
||||
const { avatars } = await checkAndGetServerImages()
|
||||
|
||||
for (const avatar of avatars) {
|
||||
await testImageSize(server.url, `avatar-resized-${avatar.width}x${avatar.width}`, avatar.path, extension)
|
||||
await testAvatarSize({ url: server.url, avatar, imageName: `avatar-resized-${avatar.width}x${avatar.width}` })
|
||||
}
|
||||
|
||||
avatarPath = avatars[0].path
|
||||
|
@ -1,5 +1,5 @@
|
||||
import './oauth.js'
|
||||
import './registrations`.js'
|
||||
import './registrations.js'
|
||||
import './two-factor.js'
|
||||
import './user-export.js'
|
||||
import './user-import.js'
|
||||
|
@ -435,7 +435,7 @@ function runTest (withObjectStorage: boolean) {
|
||||
expect(secondaryChannel.description).to.equal('noah description')
|
||||
expect(secondaryChannel.support).to.equal('noah support')
|
||||
|
||||
expect(secondaryChannel.avatars).to.have.lengthOf(2)
|
||||
expect(secondaryChannel.avatars).to.have.lengthOf(4)
|
||||
expect(secondaryChannel.banners).to.have.lengthOf(1)
|
||||
|
||||
const urls = [ ...secondaryChannel.avatars, ...secondaryChannel.banners ].map(a => a.url)
|
||||
@ -627,7 +627,7 @@ function runTest (withObjectStorage: boolean) {
|
||||
// PeerTube format
|
||||
{
|
||||
const json = await parseZIPJSONFile<AccountExportJSON>(zip, 'peertube/account.json')
|
||||
expect(json.avatars).to.have.lengthOf(2)
|
||||
expect(json.avatars).to.have.lengthOf(4)
|
||||
|
||||
for (const avatar of json.avatars) {
|
||||
await makeRawRequest({ url: avatar.url, expectedStatus: HttpStatusCode.OK_200 })
|
||||
|
@ -21,7 +21,7 @@ import { areMockObjectStorageTestsDisabled } from '@peertube/peertube-node-utils
|
||||
import { writeFile } from 'fs/promises'
|
||||
import { join } from 'path'
|
||||
import { expect } from 'chai'
|
||||
import { testImage, testImageSize } from '@tests/shared/checks.js'
|
||||
import { testImage, testAvatarSize } from '@tests/shared/checks.js'
|
||||
import { completeVideoCheck } from '@tests/shared/videos.js'
|
||||
import { completeCheckHlsPlaylist } from '@tests/shared/streaming-playlists.js'
|
||||
|
||||
@ -84,7 +84,7 @@ function runTest (withObjectStorage: boolean) {
|
||||
}
|
||||
|
||||
// Add avatars
|
||||
await server.users.updateMyAvatar({ token: noahToken, fixture: 'avatar.gif' })
|
||||
await server.users.updateMyAvatar({ token: noahToken, fixture: 'avatar.png' })
|
||||
|
||||
// Add password protected video
|
||||
await server.videos.upload({
|
||||
@ -168,9 +168,10 @@ function runTest (withObjectStorage: boolean) {
|
||||
expect(me.account.displayName).to.equal('noah')
|
||||
expect(me.username).to.equal('noah_remote')
|
||||
expect(me.account.description).to.equal('super noah description')
|
||||
expect(me.account.avatars).to.have.lengthOf(4)
|
||||
|
||||
for (const avatar of me.account.avatars) {
|
||||
await testImageSize(remoteServer.url, `avatar-resized-${avatar.width}x${avatar.width}`, avatar.path, '.gif')
|
||||
await testAvatarSize({ url: remoteServer.url, avatar, imageName: `avatar-resized-${avatar.width}x${avatar.width}` })
|
||||
}
|
||||
})
|
||||
|
||||
@ -482,7 +483,7 @@ function runTest (withObjectStorage: boolean) {
|
||||
// My avatars
|
||||
{
|
||||
const me = await remoteServer.users.getMyInfo({ token: remoteNoahToken })
|
||||
expect(me.account.avatars).to.have.lengthOf(2)
|
||||
expect(me.account.avatars).to.have.lengthOf(4)
|
||||
}
|
||||
|
||||
// Channels
|
||||
|
@ -1,9 +1,13 @@
|
||||
/* eslint-disable @typescript-eslint/no-unused-expressions,@typescript-eslint/require-await */
|
||||
|
||||
import { expect } from 'chai'
|
||||
import { testImageSize } from '@tests/shared/checks.js'
|
||||
import { testAvatarSize } from '@tests/shared/checks.js'
|
||||
import { AbuseState, HttpStatusCode, UserAdminFlag, UserRole, VideoPlaylistType } from '@peertube/peertube-models'
|
||||
import { cleanupTests, createSingleServer, PeerTubeServer, setAccessTokensToServers } from '@peertube/peertube-server-commands'
|
||||
import {
|
||||
cleanupTests,
|
||||
createSingleServer, PeerTubeServer,
|
||||
setAccessTokensToServers
|
||||
} from '@peertube/peertube-server-commands'
|
||||
|
||||
describe('Test users', function () {
|
||||
let server: PeerTubeServer
|
||||
@ -264,7 +268,7 @@ describe('Test users', function () {
|
||||
|
||||
const user = await server.users.getMyInfo({ token: userToken })
|
||||
for (const avatar of user.account.avatars) {
|
||||
await testImageSize(server.url, `avatar-resized-${avatar.width}x${avatar.width}`, avatar.path, '.gif')
|
||||
await testAvatarSize({ url: server.url, avatar, imageName: `avatar-resized-${avatar.width}x${avatar.width}` })
|
||||
}
|
||||
})
|
||||
|
||||
@ -276,7 +280,7 @@ describe('Test users', function () {
|
||||
|
||||
const user = await server.users.getMyInfo({ token: userToken })
|
||||
for (const avatar of user.account.avatars) {
|
||||
await testImageSize(server.url, `avatar-resized-${avatar.width}x${avatar.width}`, avatar.path, extension)
|
||||
await testAvatarSize({ url: server.url, avatar, imageName: `avatar-resized-${avatar.width}x${avatar.width}` })
|
||||
}
|
||||
}
|
||||
})
|
||||
|
@ -131,13 +131,13 @@ describe('Test multiple servers', function () {
|
||||
await completeVideoCheck({ server, originServer: servers[0], videoUUID: video.uuid, attributes: checkAttributes })
|
||||
publishedAt = video.publishedAt as string
|
||||
|
||||
expect(video.channel.avatars).to.have.lengthOf(2)
|
||||
expect(video.account.avatars).to.have.lengthOf(2)
|
||||
expect(video.channel.avatars).to.have.lengthOf(4)
|
||||
expect(video.account.avatars).to.have.lengthOf(4)
|
||||
|
||||
for (const image of [ ...video.channel.avatars, ...video.account.avatars ]) {
|
||||
expect(image.createdAt).to.exist
|
||||
expect(image.updatedAt).to.exist
|
||||
expect(image.width).to.be.above(20).and.below(1000)
|
||||
expect(image.width).to.be.above(20).and.below(2000)
|
||||
expect(image.path).to.exist
|
||||
|
||||
await makeGetRequest({
|
||||
|
@ -257,7 +257,7 @@ describe('Test video comments', function () {
|
||||
expect(data[0].text).to.equal('my second answer to thread 4')
|
||||
expect(data[0].account.name).to.equal('root')
|
||||
expect(data[0].account.displayName).to.equal('root')
|
||||
expect(data[0].account.avatars).to.have.lengthOf(2)
|
||||
expect(data[0].account.avatars).to.have.lengthOf(4)
|
||||
}
|
||||
|
||||
{
|
||||
@ -266,8 +266,8 @@ describe('Test video comments', function () {
|
||||
expect(total).to.equal(7)
|
||||
expect(data).to.have.lengthOf(2)
|
||||
|
||||
expect(data[0].account.avatars).to.have.lengthOf(2)
|
||||
expect(data[1].account.avatars).to.have.lengthOf(2)
|
||||
expect(data[0].account.avatars).to.have.lengthOf(4)
|
||||
expect(data[1].account.avatars).to.have.lengthOf(4)
|
||||
}
|
||||
})
|
||||
|
||||
|
@ -46,7 +46,7 @@ async function assertCountAreOkay (servers: PeerTubeServer[]) {
|
||||
expect(thumbnailsCount).to.equal(5) // 3 local videos, 1 local playlist, 2 remotes videos (lazy downloaded) and 1 remote playlist
|
||||
|
||||
const avatarsCount = await server.servers.countFiles('avatars')
|
||||
expect(avatarsCount).to.equal(4)
|
||||
expect(avatarsCount).to.equal(8)
|
||||
|
||||
const hlsRootCount = await server.servers.countFiles(join('streaming-playlists', 'hls'))
|
||||
expect(hlsRootCount).to.equal(3) // 2 videos + private directory
|
||||
|
@ -3,7 +3,7 @@
|
||||
import { expect } from 'chai'
|
||||
import { pathExists } from 'fs-extra/esm'
|
||||
import { readFile } from 'fs/promises'
|
||||
import { join } from 'path'
|
||||
import { join, parse } from 'path'
|
||||
import { HttpStatusCode } from '@peertube/peertube-models'
|
||||
import { buildAbsoluteFixturePath } from '@peertube/peertube-node-utils'
|
||||
import { makeGetRequest, PeerTubeServer } from '@peertube/peertube-server-commands'
|
||||
@ -42,14 +42,25 @@ async function expectLogContain (server: PeerTubeServer, str: string) {
|
||||
expect(content.toString()).to.contain(str)
|
||||
}
|
||||
|
||||
async function testImageSize (url: string, imageName: string, imageHTTPPath: string, extension = '.jpg') {
|
||||
const res = await makeGetRequest({
|
||||
async function testAvatarSize (options: {
|
||||
url: string
|
||||
imageName: string
|
||||
avatar: {
|
||||
width: number
|
||||
path: string
|
||||
}
|
||||
}) {
|
||||
const { url, imageName, avatar } = options
|
||||
|
||||
const { body } = await makeGetRequest({
|
||||
url,
|
||||
path: imageHTTPPath,
|
||||
path: avatar.path,
|
||||
expectedStatus: HttpStatusCode.OK_200
|
||||
})
|
||||
|
||||
const body = res.body
|
||||
const extension = parse(avatar.path).ext
|
||||
// We don't test big GIF avatars
|
||||
if (extension === '.gif' && avatar.width > 150) return
|
||||
|
||||
const data = await readFile(buildAbsoluteFixturePath(imageName + extension))
|
||||
const minLength = data.length - ((40 * data.length) / 100)
|
||||
@ -162,7 +173,7 @@ async function checkVideoDuration (server: PeerTubeServer, videoUUID: string, du
|
||||
export {
|
||||
dateIsValid,
|
||||
testImageGeneratedByFFmpeg,
|
||||
testImageSize,
|
||||
testAvatarSize,
|
||||
testImage,
|
||||
expectLogDoesNotContain,
|
||||
testFileExistsOrNot,
|
||||
|
@ -127,9 +127,15 @@ export async function prepareImportExportTests (options: {
|
||||
|
||||
const emailPort = await MockSmtpServer.Instance.collectEmails(emails)
|
||||
|
||||
const overrideConfig = {
|
||||
...objectStorageConfig,
|
||||
...ConfigCommand.getEmailOverrideConfig(emailPort),
|
||||
...ConfigCommand.getDisableRatesLimitOverrideConfig()
|
||||
}
|
||||
|
||||
const [ server, remoteServer, blockedServer ] = await Promise.all([
|
||||
createSingleServer(1, { ...objectStorageConfig, ...ConfigCommand.getEmailOverrideConfig(emailPort) }),
|
||||
createSingleServer(2, { ...objectStorageConfig, ...ConfigCommand.getEmailOverrideConfig(emailPort) }),
|
||||
createSingleServer(1, overrideConfig),
|
||||
createSingleServer(2, overrideConfig),
|
||||
|
||||
withBlockedServer
|
||||
? createSingleServer(3)
|
||||
|
@ -933,7 +933,7 @@ function checkActor (actor: any, options: { withAvatar?: boolean } = {}) {
|
||||
|
||||
if (withAvatar) {
|
||||
expect(actor.avatars).to.be.an('array')
|
||||
expect(actor.avatars).to.have.lengthOf(2)
|
||||
expect(actor.avatars).to.have.lengthOf(4)
|
||||
expect(actor.avatars[0].path).to.exist.and.not.empty
|
||||
}
|
||||
}
|
||||
|
@ -31,7 +31,7 @@ export async function processImage (options: {
|
||||
if (extension === '.gif') {
|
||||
await processGIF({ path, destination, newSize })
|
||||
} else {
|
||||
await jimpProcessor(path, destination, newSize, extension)
|
||||
await jimpProcessor({ path, destination, newSize, inputExt: extension })
|
||||
}
|
||||
|
||||
if (keepOriginal !== true) await remove(path)
|
||||
@ -56,7 +56,17 @@ export async function getImageSize (path: string) {
|
||||
// Private
|
||||
// ---------------------------------------------------------------------------
|
||||
|
||||
async function jimpProcessor (path: string, destination: string, newSize: { width: number, height: number }, inputExt: string) {
|
||||
async function jimpProcessor (options: {
|
||||
path: string
|
||||
destination: string
|
||||
newSize: {
|
||||
width: number
|
||||
height: number
|
||||
}
|
||||
inputExt: string
|
||||
}) {
|
||||
const { path, destination, newSize, inputExt } = options
|
||||
|
||||
let sourceImage: Jimp
|
||||
const inputBuffer = await readFile(path)
|
||||
|
||||
@ -125,7 +135,7 @@ function skipProcessing (options: {
|
||||
const { width, height } = newSize
|
||||
|
||||
if (hasExif(sourceImage)) return false
|
||||
if (sourceImage.getWidth() > width || sourceImage.getHeight() > height) return false
|
||||
if (sourceImage.getWidth() !== width || sourceImage.getHeight() !== height) return false
|
||||
if (inputExt !== outputExt) return false
|
||||
|
||||
const kB = 1000
|
||||
|
@ -882,6 +882,14 @@ const PREVIEWS_SIZE = {
|
||||
}
|
||||
const ACTOR_IMAGES_SIZE: { [key in ActorImageType_Type]: { width: number, height: number }[] } = {
|
||||
[ActorImageType.AVATAR]: [
|
||||
{
|
||||
width: 1500,
|
||||
height: 1500
|
||||
},
|
||||
{
|
||||
width: 600,
|
||||
height: 600
|
||||
},
|
||||
{
|
||||
width: 120,
|
||||
height: 120
|
||||
|
Loading…
Reference in New Issue
Block a user