Improve image test comparison
|
@ -219,7 +219,10 @@
|
|||
"eslint-plugin-node": "^11.0.0",
|
||||
"eslint-plugin-promise": "^6.0.0",
|
||||
"fast-xml-parser": "^4.0.0-beta.8",
|
||||
"jpeg-js": "^0.4.4",
|
||||
"mocha": "^10.0.0",
|
||||
"pixelmatch": "^5.3.0",
|
||||
"pngjs": "^7.0.0",
|
||||
"proxy": "^1.0.2",
|
||||
"resolve-tspaths": "^0.8.8",
|
||||
"socket.io-client": "^4.5.4",
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
/* eslint-disable @typescript-eslint/no-unused-expressions,@typescript-eslint/require-await */
|
||||
|
||||
import { expect } from 'chai'
|
||||
import { testImage } from '@server/tests/shared'
|
||||
import { testImageSize } from '@server/tests/shared'
|
||||
import { AbuseState, HttpStatusCode, UserAdminFlag, UserRole, VideoPlaylistType } from '@shared/models'
|
||||
import { cleanupTests, createSingleServer, PeerTubeServer, setAccessTokensToServers } from '@shared/server-commands'
|
||||
|
||||
|
@ -274,7 +274,7 @@ describe('Test users', function () {
|
|||
|
||||
const user = await server.users.getMyInfo({ token: userToken })
|
||||
for (const avatar of user.account.avatars) {
|
||||
await testImage(server.url, `avatar-resized-${avatar.width}x${avatar.width}`, avatar.path, '.gif')
|
||||
await testImageSize(server.url, `avatar-resized-${avatar.width}x${avatar.width}`, avatar.path, '.gif')
|
||||
}
|
||||
})
|
||||
|
||||
|
@ -286,7 +286,7 @@ describe('Test users', function () {
|
|||
|
||||
const user = await server.users.getMyInfo({ token: userToken })
|
||||
for (const avatar of user.account.avatars) {
|
||||
await testImage(server.url, `avatar-resized-${avatar.width}x${avatar.width}`, avatar.path, extension)
|
||||
await testImageSize(server.url, `avatar-resized-${avatar.width}x${avatar.width}`, avatar.path, extension)
|
||||
}
|
||||
}
|
||||
})
|
||||
|
|
|
@ -68,6 +68,8 @@ async function checkVideoServer2 (server: PeerTubeServer, id: number | string) {
|
|||
expect(video.description).to.equal('my super description')
|
||||
expect(video.tags).to.deep.equal([ 'supertag1', 'supertag2' ])
|
||||
|
||||
await testImage(server.url, 'thumbnail', video.thumbnailPath)
|
||||
|
||||
expect(video.files).to.have.lengthOf(1)
|
||||
|
||||
const bodyCaptions = await server.captions.list({ videoId: id })
|
||||
|
@ -254,18 +256,20 @@ describe('Test video imports', function () {
|
|||
it('Should import a video on server 2 with some fields', async function () {
|
||||
this.timeout(60_000)
|
||||
|
||||
const attributes = {
|
||||
targetUrl: FIXTURE_URLS.youtube,
|
||||
channelId: servers[1].store.channel.id,
|
||||
privacy: VideoPrivacy.PUBLIC,
|
||||
category: 10,
|
||||
licence: 7,
|
||||
language: 'en',
|
||||
name: 'my super name',
|
||||
description: 'my super description',
|
||||
tags: [ 'supertag1', 'supertag2' ]
|
||||
}
|
||||
const { video } = await servers[1].imports.importVideo({ attributes })
|
||||
const { video } = await servers[1].imports.importVideo({
|
||||
attributes: {
|
||||
targetUrl: FIXTURE_URLS.youtube,
|
||||
channelId: servers[1].store.channel.id,
|
||||
privacy: VideoPrivacy.PUBLIC,
|
||||
category: 10,
|
||||
licence: 7,
|
||||
language: 'en',
|
||||
name: 'my super name',
|
||||
description: 'my super description',
|
||||
tags: [ 'supertag1', 'supertag2' ],
|
||||
thumbnailfile: 'thumbnail.jpg'
|
||||
}
|
||||
})
|
||||
expect(video.name).to.equal('my super name')
|
||||
})
|
||||
|
||||
|
|
Before Width: | Height: | Size: 4.9 KiB After Width: | Height: | Size: 4.9 KiB |
Before Width: | Height: | Size: 4.1 KiB After Width: | Height: | Size: 5.4 KiB |
Before Width: | Height: | Size: 9.9 KiB After Width: | Height: | Size: 10 KiB |
Before Width: | Height: | Size: 4.9 KiB After Width: | Height: | Size: 4.9 KiB |
Before Width: | Height: | Size: 4.9 KiB After Width: | Height: | Size: 4.9 KiB |
Before Width: | Height: | Size: 4.9 KiB After Width: | Height: | Size: 4.9 KiB |
Before Width: | Height: | Size: 31 KiB After Width: | Height: | Size: 31 KiB |
Before Width: | Height: | Size: 6.2 KiB After Width: | Height: | Size: 6.1 KiB |
Before Width: | Height: | Size: 5.4 KiB After Width: | Height: | Size: 5.4 KiB |
Before Width: | Height: | Size: 4.9 KiB After Width: | Height: | Size: 5.5 KiB |
|
@ -32,7 +32,7 @@ describe('Image helpers', function () {
|
|||
const imageDestJPG = join(imageDestDir, 'test.jpg')
|
||||
const imageDestPNG = join(imageDestDir, 'test.png')
|
||||
|
||||
const thumbnailSize = { width: 223, height: 122 }
|
||||
const thumbnailSize = { width: 280, height: 157 }
|
||||
|
||||
it('Should skip processing if the source image is okay', async function () {
|
||||
const input = buildAbsoluteFixturePath('thumbnail.jpg')
|
||||
|
|
|
@ -2,7 +2,10 @@
|
|||
|
||||
import { expect } from 'chai'
|
||||
import { pathExists, readFile } from 'fs-extra'
|
||||
import JPEG from 'jpeg-js'
|
||||
import { join } from 'path'
|
||||
import pixelmatch from 'pixelmatch'
|
||||
import { PNG } from 'pngjs'
|
||||
import { root } from '@shared/core-utils'
|
||||
import { HttpStatusCode } from '@shared/models'
|
||||
import { makeGetRequest, PeerTubeServer } from '@shared/server-commands'
|
||||
|
@ -41,7 +44,7 @@ async function expectLogContain (server: PeerTubeServer, str: string) {
|
|||
expect(content.toString()).to.contain(str)
|
||||
}
|
||||
|
||||
async function testImage (url: string, imageName: string, imageHTTPPath: string, extension = '.jpg') {
|
||||
async function testImageSize (url: string, imageName: string, imageHTTPPath: string, extension = '.jpg') {
|
||||
const res = await makeGetRequest({
|
||||
url,
|
||||
path: imageHTTPPath,
|
||||
|
@ -58,6 +61,29 @@ async function testImage (url: string, imageName: string, imageHTTPPath: string,
|
|||
expect(body.length).to.be.below(maxLength, 'the generated image is way larger than the recorded fixture')
|
||||
}
|
||||
|
||||
async function testImage (url: string, imageName: string, imageHTTPPath: string, extension = '.jpg') {
|
||||
const res = await makeGetRequest({
|
||||
url,
|
||||
path: imageHTTPPath,
|
||||
expectedStatus: HttpStatusCode.OK_200
|
||||
})
|
||||
|
||||
const body = res.body
|
||||
const data = await readFile(join(root(), 'server', 'tests', 'fixtures', imageName + extension))
|
||||
|
||||
const img1 = imageHTTPPath.endsWith('.png')
|
||||
? PNG.sync.read(body)
|
||||
: JPEG.decode(body)
|
||||
|
||||
const img2 = extension === '.png'
|
||||
? PNG.sync.read(data)
|
||||
: JPEG.decode(data)
|
||||
|
||||
const result = pixelmatch(img1.data, img2.data, null, img1.width, img1.height, { threshold: 0.1 })
|
||||
|
||||
expect(result).to.equal(0, `${imageHTTPPath} image is not the same as ${imageName}${extension}`)
|
||||
}
|
||||
|
||||
async function testFileExistsOrNot (server: PeerTubeServer, directory: string, filePath: string, exist: boolean) {
|
||||
const base = server.servers.buildDirectory(directory)
|
||||
|
||||
|
@ -104,6 +130,7 @@ function checkBadSortPagination (url: string, path: string, token?: string, quer
|
|||
|
||||
export {
|
||||
dateIsValid,
|
||||
testImageSize,
|
||||
testImage,
|
||||
expectLogDoesNotContain,
|
||||
testFileExistsOrNot,
|
||||
|
|
|
@ -7,13 +7,15 @@ import { AbstractCommand, OverrideCommandOptions } from '../shared'
|
|||
export class ImportsCommand extends AbstractCommand {
|
||||
|
||||
importVideo (options: OverrideCommandOptions & {
|
||||
attributes: VideoImportCreate & { torrentfile?: string }
|
||||
attributes: (VideoImportCreate | { torrentfile?: string, previewfile?: string, thumbnailfile?: string })
|
||||
}) {
|
||||
const { attributes } = options
|
||||
const path = '/api/v1/videos/imports'
|
||||
|
||||
let attaches: any = {}
|
||||
if (attributes.torrentfile) attaches = { torrentfile: attributes.torrentfile }
|
||||
if (attributes.thumbnailfile) attaches = { thumbnailfile: attributes.thumbnailfile }
|
||||
if (attributes.previewfile) attaches = { previewfile: attributes.previewfile }
|
||||
|
||||
return unwrapBody<VideoImport>(this.postUploadRequest({
|
||||
...options,
|
||||
|
|
12
yarn.lock
|
@ -7592,6 +7592,13 @@ pixelmatch@^4.0.2:
|
|||
dependencies:
|
||||
pngjs "^3.0.0"
|
||||
|
||||
pixelmatch@^5.3.0:
|
||||
version "5.3.0"
|
||||
resolved "https://registry.yarnpkg.com/pixelmatch/-/pixelmatch-5.3.0.tgz#5e5321a7abedfb7962d60dbf345deda87cb9560a"
|
||||
integrity sha512-o8mkY4E/+LNUf6LzX96ht6k6CEDi65k9G2rjMtBe9Oo+VPKSvl+0GKHuH/AlG+GA5LPG/i5hrekkxUc3s2HU+Q==
|
||||
dependencies:
|
||||
pngjs "^6.0.0"
|
||||
|
||||
please-upgrade-node@^3.2.0:
|
||||
version "3.2.0"
|
||||
resolved "https://registry.yarnpkg.com/please-upgrade-node/-/please-upgrade-node-3.2.0.tgz#aeddd3f994c933e4ad98b99d9a556efa0e2fe942"
|
||||
|
@ -7609,6 +7616,11 @@ pngjs@^6.0.0:
|
|||
resolved "https://registry.yarnpkg.com/pngjs/-/pngjs-6.0.0.tgz#ca9e5d2aa48db0228a52c419c3308e87720da821"
|
||||
integrity sha512-TRzzuFRRmEoSW/p1KVAmiOgPco2Irlah+bGFCeNfJXxxYGwSw7YwAOAcd7X28K/m5bjBWKsC29KyoMfHbypayg==
|
||||
|
||||
pngjs@^7.0.0:
|
||||
version "7.0.0"
|
||||
resolved "https://registry.yarnpkg.com/pngjs/-/pngjs-7.0.0.tgz#a8b7446020ebbc6ac739db6c5415a65d17090e26"
|
||||
integrity sha512-LKWqWJRhstyYo9pGvgor/ivk2w94eSjE3RGVuzLGlr3NmD8bf7RcYGze1mNdEHRP6TRP6rMuDHk5t44hnTRyow==
|
||||
|
||||
postcss@^8.1.10, postcss@^8.3.11:
|
||||
version "8.4.21"
|
||||
resolved "https://registry.yarnpkg.com/postcss/-/postcss-8.4.21.tgz#c639b719a57efc3187b13a1d765675485f4134f4"
|
||||
|
|