diff options
author | Chocobozzz <me@florianbigard.com> | 2019-02-11 11:52:34 +0100 |
---|---|---|
committer | Chocobozzz <me@florianbigard.com> | 2019-02-11 11:52:34 +0100 |
commit | 88108880bbdba473cfe36ecbebc1c3c4f972e102 (patch) | |
tree | b242efb3b4f0d7e49d88f2d1f2063b5b3b0489c0 /server/tests/api/server | |
parent | 53a94c7cfa8368da4cd248d65df8346905938f0c (diff) | |
parent | 9b712a2017e4ab3cf12cd6bd58278905520159d0 (diff) | |
download | PeerTube-88108880bbdba473cfe36ecbebc1c3c4f972e102.tar.gz PeerTube-88108880bbdba473cfe36ecbebc1c3c4f972e102.tar.zst PeerTube-88108880bbdba473cfe36ecbebc1c3c4f972e102.zip |
Merge branch 'develop' into pr/1217
Diffstat (limited to 'server/tests/api/server')
-rw-r--r-- | server/tests/api/server/config.ts | 62 | ||||
-rw-r--r-- | server/tests/api/server/contact-form.ts | 86 | ||||
-rw-r--r-- | server/tests/api/server/email.ts | 16 | ||||
-rw-r--r-- | server/tests/api/server/follow-constraints.ts | 225 | ||||
-rw-r--r-- | server/tests/api/server/follows.ts | 67 | ||||
-rw-r--r-- | server/tests/api/server/handle-down.ts | 22 | ||||
-rw-r--r-- | server/tests/api/server/index.ts | 4 | ||||
-rw-r--r-- | server/tests/api/server/jobs.ts | 12 | ||||
-rw-r--r-- | server/tests/api/server/no-client.ts | 36 | ||||
-rw-r--r-- | server/tests/api/server/redundancy.ts | 483 | ||||
-rw-r--r-- | server/tests/api/server/reverse-proxy.ts | 6 | ||||
-rw-r--r-- | server/tests/api/server/stats.ts | 14 | ||||
-rw-r--r-- | server/tests/api/server/tracker.ts | 4 |
13 files changed, 506 insertions, 531 deletions
diff --git a/server/tests/api/server/config.ts b/server/tests/api/server/config.ts index facd1688d..0dfe6e4fe 100644 --- a/server/tests/api/server/config.ts +++ b/server/tests/api/server/config.ts | |||
@@ -4,8 +4,11 @@ import 'mocha' | |||
4 | import * as chai from 'chai' | 4 | import * as chai from 'chai' |
5 | import { About } from '../../../../shared/models/server/about.model' | 5 | import { About } from '../../../../shared/models/server/about.model' |
6 | import { CustomConfig } from '../../../../shared/models/server/custom-config.model' | 6 | import { CustomConfig } from '../../../../shared/models/server/custom-config.model' |
7 | import { deleteCustomConfig, getAbout, killallServers, reRunServer } from '../../utils' | ||
8 | import { | 7 | import { |
8 | deleteCustomConfig, | ||
9 | getAbout, | ||
10 | killallServers, | ||
11 | reRunServer, | ||
9 | flushTests, | 12 | flushTests, |
10 | getConfig, | 13 | getConfig, |
11 | getCustomConfig, | 14 | getCustomConfig, |
@@ -13,7 +16,8 @@ import { | |||
13 | runServer, | 16 | runServer, |
14 | setAccessTokensToServers, | 17 | setAccessTokensToServers, |
15 | updateCustomConfig | 18 | updateCustomConfig |
16 | } from '../../utils/index' | 19 | } from '../../../../shared/utils' |
20 | import { ServerConfig } from '../../../../shared/models' | ||
17 | 21 | ||
18 | const expect = chai.expect | 22 | const expect = chai.expect |
19 | 23 | ||
@@ -29,23 +33,32 @@ function checkInitialConfig (data: CustomConfig) { | |||
29 | expect(data.instance.defaultNSFWPolicy).to.equal('display') | 33 | expect(data.instance.defaultNSFWPolicy).to.equal('display') |
30 | expect(data.instance.customizations.css).to.be.empty | 34 | expect(data.instance.customizations.css).to.be.empty |
31 | expect(data.instance.customizations.javascript).to.be.empty | 35 | expect(data.instance.customizations.javascript).to.be.empty |
36 | |||
32 | expect(data.services.twitter.username).to.equal('@Chocobozzz') | 37 | expect(data.services.twitter.username).to.equal('@Chocobozzz') |
33 | expect(data.services.twitter.whitelisted).to.be.false | 38 | expect(data.services.twitter.whitelisted).to.be.false |
39 | |||
34 | expect(data.cache.previews.size).to.equal(1) | 40 | expect(data.cache.previews.size).to.equal(1) |
35 | expect(data.cache.captions.size).to.equal(1) | 41 | expect(data.cache.captions.size).to.equal(1) |
42 | |||
36 | expect(data.signup.enabled).to.be.true | 43 | expect(data.signup.enabled).to.be.true |
37 | expect(data.signup.limit).to.equal(4) | 44 | expect(data.signup.limit).to.equal(4) |
38 | expect(data.signup.requiresEmailVerification).to.be.false | 45 | expect(data.signup.requiresEmailVerification).to.be.false |
46 | |||
39 | expect(data.admin.email).to.equal('admin1@example.com') | 47 | expect(data.admin.email).to.equal('admin1@example.com') |
48 | expect(data.contactForm.enabled).to.be.true | ||
49 | |||
40 | expect(data.user.videoQuota).to.equal(5242880) | 50 | expect(data.user.videoQuota).to.equal(5242880) |
41 | expect(data.user.videoQuotaDaily).to.equal(-1) | 51 | expect(data.user.videoQuotaDaily).to.equal(-1) |
42 | expect(data.transcoding.enabled).to.be.false | 52 | expect(data.transcoding.enabled).to.be.false |
53 | expect(data.transcoding.allowAdditionalExtensions).to.be.false | ||
43 | expect(data.transcoding.threads).to.equal(2) | 54 | expect(data.transcoding.threads).to.equal(2) |
44 | expect(data.transcoding.resolutions['240p']).to.be.true | 55 | expect(data.transcoding.resolutions['240p']).to.be.true |
45 | expect(data.transcoding.resolutions['360p']).to.be.true | 56 | expect(data.transcoding.resolutions['360p']).to.be.true |
46 | expect(data.transcoding.resolutions['480p']).to.be.true | 57 | expect(data.transcoding.resolutions['480p']).to.be.true |
47 | expect(data.transcoding.resolutions['720p']).to.be.true | 58 | expect(data.transcoding.resolutions['720p']).to.be.true |
48 | expect(data.transcoding.resolutions['1080p']).to.be.true | 59 | expect(data.transcoding.resolutions['1080p']).to.be.true |
60 | expect(data.transcoding.hls.enabled).to.be.true | ||
61 | |||
49 | expect(data.import.videos.http.enabled).to.be.true | 62 | expect(data.import.videos.http.enabled).to.be.true |
50 | expect(data.import.videos.torrent.enabled).to.be.true | 63 | expect(data.import.videos.torrent.enabled).to.be.true |
51 | } | 64 | } |
@@ -59,23 +72,33 @@ function checkUpdatedConfig (data: CustomConfig) { | |||
59 | expect(data.instance.defaultNSFWPolicy).to.equal('blur') | 72 | expect(data.instance.defaultNSFWPolicy).to.equal('blur') |
60 | expect(data.instance.customizations.javascript).to.equal('alert("coucou")') | 73 | expect(data.instance.customizations.javascript).to.equal('alert("coucou")') |
61 | expect(data.instance.customizations.css).to.equal('body { background-color: red; }') | 74 | expect(data.instance.customizations.css).to.equal('body { background-color: red; }') |
75 | |||
62 | expect(data.services.twitter.username).to.equal('@Kuja') | 76 | expect(data.services.twitter.username).to.equal('@Kuja') |
63 | expect(data.services.twitter.whitelisted).to.be.true | 77 | expect(data.services.twitter.whitelisted).to.be.true |
78 | |||
64 | expect(data.cache.previews.size).to.equal(2) | 79 | expect(data.cache.previews.size).to.equal(2) |
65 | expect(data.cache.captions.size).to.equal(3) | 80 | expect(data.cache.captions.size).to.equal(3) |
81 | |||
66 | expect(data.signup.enabled).to.be.false | 82 | expect(data.signup.enabled).to.be.false |
67 | expect(data.signup.limit).to.equal(5) | 83 | expect(data.signup.limit).to.equal(5) |
68 | expect(data.signup.requiresEmailVerification).to.be.true | 84 | expect(data.signup.requiresEmailVerification).to.be.true |
85 | |||
69 | expect(data.admin.email).to.equal('superadmin1@example.com') | 86 | expect(data.admin.email).to.equal('superadmin1@example.com') |
87 | expect(data.contactForm.enabled).to.be.false | ||
88 | |||
70 | expect(data.user.videoQuota).to.equal(5242881) | 89 | expect(data.user.videoQuota).to.equal(5242881) |
71 | expect(data.user.videoQuotaDaily).to.equal(318742) | 90 | expect(data.user.videoQuotaDaily).to.equal(318742) |
91 | |||
72 | expect(data.transcoding.enabled).to.be.true | 92 | expect(data.transcoding.enabled).to.be.true |
73 | expect(data.transcoding.threads).to.equal(1) | 93 | expect(data.transcoding.threads).to.equal(1) |
94 | expect(data.transcoding.allowAdditionalExtensions).to.be.true | ||
74 | expect(data.transcoding.resolutions['240p']).to.be.false | 95 | expect(data.transcoding.resolutions['240p']).to.be.false |
75 | expect(data.transcoding.resolutions['360p']).to.be.true | 96 | expect(data.transcoding.resolutions['360p']).to.be.true |
76 | expect(data.transcoding.resolutions['480p']).to.be.true | 97 | expect(data.transcoding.resolutions['480p']).to.be.true |
77 | expect(data.transcoding.resolutions['720p']).to.be.false | 98 | expect(data.transcoding.resolutions['720p']).to.be.false |
78 | expect(data.transcoding.resolutions['1080p']).to.be.false | 99 | expect(data.transcoding.resolutions['1080p']).to.be.false |
100 | expect(data.transcoding.hls.enabled).to.be.false | ||
101 | |||
79 | expect(data.import.videos.http.enabled).to.be.false | 102 | expect(data.import.videos.http.enabled).to.be.false |
80 | expect(data.import.videos.torrent.enabled).to.be.false | 103 | expect(data.import.videos.torrent.enabled).to.be.false |
81 | } | 104 | } |
@@ -93,7 +116,7 @@ describe('Test config', function () { | |||
93 | 116 | ||
94 | it('Should have a correct config on a server with registration enabled', async function () { | 117 | it('Should have a correct config on a server with registration enabled', async function () { |
95 | const res = await getConfig(server.url) | 118 | const res = await getConfig(server.url) |
96 | const data = res.body | 119 | const data: ServerConfig = res.body |
97 | 120 | ||
98 | expect(data.signup.allowed).to.be.true | 121 | expect(data.signup.allowed).to.be.true |
99 | }) | 122 | }) |
@@ -108,11 +131,23 @@ describe('Test config', function () { | |||
108 | ]) | 131 | ]) |
109 | 132 | ||
110 | const res = await getConfig(server.url) | 133 | const res = await getConfig(server.url) |
111 | const data = res.body | 134 | const data: ServerConfig = res.body |
112 | 135 | ||
113 | expect(data.signup.allowed).to.be.false | 136 | expect(data.signup.allowed).to.be.false |
114 | }) | 137 | }) |
115 | 138 | ||
139 | it('Should have the correct video allowed extensions', async function () { | ||
140 | const res = await getConfig(server.url) | ||
141 | const data: ServerConfig = res.body | ||
142 | |||
143 | expect(data.video.file.extensions).to.have.lengthOf(3) | ||
144 | expect(data.video.file.extensions).to.contain('.mp4') | ||
145 | expect(data.video.file.extensions).to.contain('.webm') | ||
146 | expect(data.video.file.extensions).to.contain('.ogv') | ||
147 | |||
148 | expect(data.contactForm.enabled).to.be.true | ||
149 | }) | ||
150 | |||
116 | it('Should get the customized configuration', async function () { | 151 | it('Should get the customized configuration', async function () { |
117 | const res = await getCustomConfig(server.url, server.accessToken) | 152 | const res = await getCustomConfig(server.url, server.accessToken) |
118 | const data = res.body as CustomConfig | 153 | const data = res.body as CustomConfig |
@@ -156,12 +191,16 @@ describe('Test config', function () { | |||
156 | admin: { | 191 | admin: { |
157 | email: 'superadmin1@example.com' | 192 | email: 'superadmin1@example.com' |
158 | }, | 193 | }, |
194 | contactForm: { | ||
195 | enabled: false | ||
196 | }, | ||
159 | user: { | 197 | user: { |
160 | videoQuota: 5242881, | 198 | videoQuota: 5242881, |
161 | videoQuotaDaily: 318742 | 199 | videoQuotaDaily: 318742 |
162 | }, | 200 | }, |
163 | transcoding: { | 201 | transcoding: { |
164 | enabled: true, | 202 | enabled: true, |
203 | allowAdditionalExtensions: true, | ||
165 | threads: 1, | 204 | threads: 1, |
166 | resolutions: { | 205 | resolutions: { |
167 | '240p': false, | 206 | '240p': false, |
@@ -169,6 +208,9 @@ describe('Test config', function () { | |||
169 | '480p': true, | 208 | '480p': true, |
170 | '720p': false, | 209 | '720p': false, |
171 | '1080p': false | 210 | '1080p': false |
211 | }, | ||
212 | hls: { | ||
213 | enabled: false | ||
172 | } | 214 | } |
173 | }, | 215 | }, |
174 | import: { | 216 | import: { |
@@ -190,6 +232,18 @@ describe('Test config', function () { | |||
190 | checkUpdatedConfig(data) | 232 | checkUpdatedConfig(data) |
191 | }) | 233 | }) |
192 | 234 | ||
235 | it('Should have the correct updated video allowed extensions', async function () { | ||
236 | const res = await getConfig(server.url) | ||
237 | const data: ServerConfig = res.body | ||
238 | |||
239 | expect(data.video.file.extensions).to.have.length.above(3) | ||
240 | expect(data.video.file.extensions).to.contain('.mp4') | ||
241 | expect(data.video.file.extensions).to.contain('.webm') | ||
242 | expect(data.video.file.extensions).to.contain('.ogv') | ||
243 | expect(data.video.file.extensions).to.contain('.flv') | ||
244 | expect(data.video.file.extensions).to.contain('.mkv') | ||
245 | }) | ||
246 | |||
193 | it('Should have the configuration updated after a restart', async function () { | 247 | it('Should have the configuration updated after a restart', async function () { |
194 | this.timeout(10000) | 248 | this.timeout(10000) |
195 | 249 | ||
diff --git a/server/tests/api/server/contact-form.ts b/server/tests/api/server/contact-form.ts new file mode 100644 index 000000000..93221d0a3 --- /dev/null +++ b/server/tests/api/server/contact-form.ts | |||
@@ -0,0 +1,86 @@ | |||
1 | /* tslint:disable:no-unused-expression */ | ||
2 | |||
3 | import * as chai from 'chai' | ||
4 | import 'mocha' | ||
5 | import { flushTests, killallServers, runServer, ServerInfo, setAccessTokensToServers, wait } from '../../../../shared/utils' | ||
6 | import { MockSmtpServer } from '../../../../shared/utils/miscs/email' | ||
7 | import { waitJobs } from '../../../../shared/utils/server/jobs' | ||
8 | import { sendContactForm } from '../../../../shared/utils/server/contact-form' | ||
9 | |||
10 | const expect = chai.expect | ||
11 | |||
12 | describe('Test contact form', function () { | ||
13 | let server: ServerInfo | ||
14 | const emails: object[] = [] | ||
15 | |||
16 | before(async function () { | ||
17 | this.timeout(30000) | ||
18 | |||
19 | await MockSmtpServer.Instance.collectEmails(emails) | ||
20 | |||
21 | await flushTests() | ||
22 | |||
23 | const overrideConfig = { | ||
24 | smtp: { | ||
25 | hostname: 'localhost' | ||
26 | } | ||
27 | } | ||
28 | server = await runServer(1, overrideConfig) | ||
29 | await setAccessTokensToServers([ server ]) | ||
30 | }) | ||
31 | |||
32 | it('Should send a contact form', async function () { | ||
33 | this.timeout(10000) | ||
34 | |||
35 | await sendContactForm({ | ||
36 | url: server.url, | ||
37 | fromEmail: 'toto@example.com', | ||
38 | body: 'my super message', | ||
39 | fromName: 'Super toto' | ||
40 | }) | ||
41 | |||
42 | await waitJobs(server) | ||
43 | |||
44 | expect(emails).to.have.lengthOf(1) | ||
45 | |||
46 | const email = emails[0] | ||
47 | |||
48 | expect(email['from'][0]['address']).equal('toto@example.com') | ||
49 | expect(email['to'][0]['address']).equal('admin1@example.com') | ||
50 | expect(email['subject']).contains('Contact form') | ||
51 | expect(email['text']).contains('my super message') | ||
52 | }) | ||
53 | |||
54 | it('Should not be able to send another contact form because of the anti spam checker', async function () { | ||
55 | await sendContactForm({ | ||
56 | url: server.url, | ||
57 | fromEmail: 'toto@example.com', | ||
58 | body: 'my super message', | ||
59 | fromName: 'Super toto' | ||
60 | }) | ||
61 | |||
62 | await sendContactForm({ | ||
63 | url: server.url, | ||
64 | fromEmail: 'toto@example.com', | ||
65 | body: 'my super message', | ||
66 | fromName: 'Super toto', | ||
67 | expectedStatus: 403 | ||
68 | }) | ||
69 | }) | ||
70 | |||
71 | it('Should be able to send another contact form after a while', async function () { | ||
72 | await wait(1000) | ||
73 | |||
74 | await sendContactForm({ | ||
75 | url: server.url, | ||
76 | fromEmail: 'toto@example.com', | ||
77 | body: 'my super message', | ||
78 | fromName: 'Super toto' | ||
79 | }) | ||
80 | }) | ||
81 | |||
82 | after(async function () { | ||
83 | MockSmtpServer.Instance.kill() | ||
84 | killallServers([ server ]) | ||
85 | }) | ||
86 | }) | ||
diff --git a/server/tests/api/server/email.ts b/server/tests/api/server/email.ts index 713a27143..f96c57b66 100644 --- a/server/tests/api/server/email.ts +++ b/server/tests/api/server/email.ts | |||
@@ -14,11 +14,14 @@ import { | |||
14 | unblockUser, | 14 | unblockUser, |
15 | uploadVideo, | 15 | uploadVideo, |
16 | userLogin, | 16 | userLogin, |
17 | verifyEmail | 17 | verifyEmail, |
18 | } from '../../utils' | 18 | flushTests, |
19 | import { flushTests, killallServers, ServerInfo, setAccessTokensToServers } from '../../utils/index' | 19 | killallServers, |
20 | import { mockSmtpServer } from '../../utils/miscs/email' | 20 | ServerInfo, |
21 | import { waitJobs } from '../../utils/server/jobs' | 21 | setAccessTokensToServers |
22 | } from '../../../../shared/utils' | ||
23 | import { MockSmtpServer } from '../../../../shared/utils/miscs/email' | ||
24 | import { waitJobs } from '../../../../shared/utils/server/jobs' | ||
22 | 25 | ||
23 | const expect = chai.expect | 26 | const expect = chai.expect |
24 | 27 | ||
@@ -38,7 +41,7 @@ describe('Test emails', function () { | |||
38 | before(async function () { | 41 | before(async function () { |
39 | this.timeout(30000) | 42 | this.timeout(30000) |
40 | 43 | ||
41 | await mockSmtpServer(emails) | 44 | await MockSmtpServer.Instance.collectEmails(emails) |
42 | 45 | ||
43 | await flushTests() | 46 | await flushTests() |
44 | 47 | ||
@@ -248,6 +251,7 @@ describe('Test emails', function () { | |||
248 | }) | 251 | }) |
249 | 252 | ||
250 | after(async function () { | 253 | after(async function () { |
254 | MockSmtpServer.Instance.kill() | ||
251 | killallServers([ server ]) | 255 | killallServers([ server ]) |
252 | }) | 256 | }) |
253 | }) | 257 | }) |
diff --git a/server/tests/api/server/follow-constraints.ts b/server/tests/api/server/follow-constraints.ts new file mode 100644 index 000000000..8bb073c41 --- /dev/null +++ b/server/tests/api/server/follow-constraints.ts | |||
@@ -0,0 +1,225 @@ | |||
1 | /* tslint:disable:no-unused-expression */ | ||
2 | |||
3 | import * as chai from 'chai' | ||
4 | import 'mocha' | ||
5 | import { | ||
6 | doubleFollow, | ||
7 | getAccountVideos, | ||
8 | getVideo, | ||
9 | getVideoChannelVideos, | ||
10 | getVideoWithToken, | ||
11 | flushAndRunMultipleServers, | ||
12 | killallServers, | ||
13 | ServerInfo, | ||
14 | setAccessTokensToServers, | ||
15 | uploadVideo | ||
16 | } from '../../../../shared/utils' | ||
17 | import { unfollow } from '../../../../shared/utils/server/follows' | ||
18 | import { userLogin } from '../../../../shared/utils/users/login' | ||
19 | import { createUser } from '../../../../shared/utils/users/users' | ||
20 | |||
21 | const expect = chai.expect | ||
22 | |||
23 | describe('Test follow constraints', function () { | ||
24 | let servers: ServerInfo[] = [] | ||
25 | let video1UUID: string | ||
26 | let video2UUID: string | ||
27 | let userAccessToken: string | ||
28 | |||
29 | before(async function () { | ||
30 | this.timeout(30000) | ||
31 | |||
32 | servers = await flushAndRunMultipleServers(2) | ||
33 | |||
34 | // Get the access tokens | ||
35 | await setAccessTokensToServers(servers) | ||
36 | |||
37 | { | ||
38 | const res = await uploadVideo(servers[ 0 ].url, servers[ 0 ].accessToken, { name: 'video server 1' }) | ||
39 | video1UUID = res.body.video.uuid | ||
40 | } | ||
41 | { | ||
42 | const res = await uploadVideo(servers[ 1 ].url, servers[ 1 ].accessToken, { name: 'video server 2' }) | ||
43 | video2UUID = res.body.video.uuid | ||
44 | } | ||
45 | |||
46 | const user = { | ||
47 | username: 'user1', | ||
48 | password: 'super_password' | ||
49 | } | ||
50 | await createUser(servers[0].url, servers[0].accessToken, user.username, user.password) | ||
51 | userAccessToken = await userLogin(servers[0], user) | ||
52 | |||
53 | await doubleFollow(servers[0], servers[1]) | ||
54 | }) | ||
55 | |||
56 | describe('With a followed instance', function () { | ||
57 | |||
58 | describe('With an unlogged user', function () { | ||
59 | |||
60 | it('Should get the local video', async function () { | ||
61 | await getVideo(servers[0].url, video1UUID, 200) | ||
62 | }) | ||
63 | |||
64 | it('Should get the remote video', async function () { | ||
65 | await getVideo(servers[0].url, video2UUID, 200) | ||
66 | }) | ||
67 | |||
68 | it('Should list local account videos', async function () { | ||
69 | const res = await getAccountVideos(servers[0].url, undefined, 'root@localhost:9001', 0, 5) | ||
70 | |||
71 | expect(res.body.total).to.equal(1) | ||
72 | expect(res.body.data).to.have.lengthOf(1) | ||
73 | }) | ||
74 | |||
75 | it('Should list remote account videos', async function () { | ||
76 | const res = await getAccountVideos(servers[0].url, undefined, 'root@localhost:9002', 0, 5) | ||
77 | |||
78 | expect(res.body.total).to.equal(1) | ||
79 | expect(res.body.data).to.have.lengthOf(1) | ||
80 | }) | ||
81 | |||
82 | it('Should list local channel videos', async function () { | ||
83 | const res = await getVideoChannelVideos(servers[0].url, undefined, 'root_channel@localhost:9001', 0, 5) | ||
84 | |||
85 | expect(res.body.total).to.equal(1) | ||
86 | expect(res.body.data).to.have.lengthOf(1) | ||
87 | }) | ||
88 | |||
89 | it('Should list remote channel videos', async function () { | ||
90 | const res = await getVideoChannelVideos(servers[0].url, undefined, 'root_channel@localhost:9002', 0, 5) | ||
91 | |||
92 | expect(res.body.total).to.equal(1) | ||
93 | expect(res.body.data).to.have.lengthOf(1) | ||
94 | }) | ||
95 | }) | ||
96 | |||
97 | describe('With a logged user', function () { | ||
98 | it('Should get the local video', async function () { | ||
99 | await getVideoWithToken(servers[0].url, userAccessToken, video1UUID, 200) | ||
100 | }) | ||
101 | |||
102 | it('Should get the remote video', async function () { | ||
103 | await getVideoWithToken(servers[0].url, userAccessToken, video2UUID, 200) | ||
104 | }) | ||
105 | |||
106 | it('Should list local account videos', async function () { | ||
107 | const res = await getAccountVideos(servers[0].url, userAccessToken, 'root@localhost:9001', 0, 5) | ||
108 | |||
109 | expect(res.body.total).to.equal(1) | ||
110 | expect(res.body.data).to.have.lengthOf(1) | ||
111 | }) | ||
112 | |||
113 | it('Should list remote account videos', async function () { | ||
114 | const res = await getAccountVideos(servers[0].url, userAccessToken, 'root@localhost:9002', 0, 5) | ||
115 | |||
116 | expect(res.body.total).to.equal(1) | ||
117 | expect(res.body.data).to.have.lengthOf(1) | ||
118 | }) | ||
119 | |||
120 | it('Should list local channel videos', async function () { | ||
121 | const res = await getVideoChannelVideos(servers[0].url, userAccessToken, 'root_channel@localhost:9001', 0, 5) | ||
122 | |||
123 | expect(res.body.total).to.equal(1) | ||
124 | expect(res.body.data).to.have.lengthOf(1) | ||
125 | }) | ||
126 | |||
127 | it('Should list remote channel videos', async function () { | ||
128 | const res = await getVideoChannelVideos(servers[0].url, userAccessToken, 'root_channel@localhost:9002', 0, 5) | ||
129 | |||
130 | expect(res.body.total).to.equal(1) | ||
131 | expect(res.body.data).to.have.lengthOf(1) | ||
132 | }) | ||
133 | }) | ||
134 | }) | ||
135 | |||
136 | describe('With a non followed instance', function () { | ||
137 | |||
138 | before(async function () { | ||
139 | this.timeout(30000) | ||
140 | |||
141 | await unfollow(servers[0].url, servers[0].accessToken, servers[1]) | ||
142 | }) | ||
143 | |||
144 | describe('With an unlogged user', function () { | ||
145 | |||
146 | it('Should get the local video', async function () { | ||
147 | await getVideo(servers[0].url, video1UUID, 200) | ||
148 | }) | ||
149 | |||
150 | it('Should not get the remote video', async function () { | ||
151 | await getVideo(servers[0].url, video2UUID, 403) | ||
152 | }) | ||
153 | |||
154 | it('Should list local account videos', async function () { | ||
155 | const res = await getAccountVideos(servers[0].url, undefined, 'root@localhost:9001', 0, 5) | ||
156 | |||
157 | expect(res.body.total).to.equal(1) | ||
158 | expect(res.body.data).to.have.lengthOf(1) | ||
159 | }) | ||
160 | |||
161 | it('Should not list remote account videos', async function () { | ||
162 | const res = await getAccountVideos(servers[0].url, undefined, 'root@localhost:9002', 0, 5) | ||
163 | |||
164 | expect(res.body.total).to.equal(0) | ||
165 | expect(res.body.data).to.have.lengthOf(0) | ||
166 | }) | ||
167 | |||
168 | it('Should list local channel videos', async function () { | ||
169 | const res = await getVideoChannelVideos(servers[0].url, undefined, 'root_channel@localhost:9001', 0, 5) | ||
170 | |||
171 | expect(res.body.total).to.equal(1) | ||
172 | expect(res.body.data).to.have.lengthOf(1) | ||
173 | }) | ||
174 | |||
175 | it('Should not list remote channel videos', async function () { | ||
176 | const res = await getVideoChannelVideos(servers[0].url, undefined, 'root_channel@localhost:9002', 0, 5) | ||
177 | |||
178 | expect(res.body.total).to.equal(0) | ||
179 | expect(res.body.data).to.have.lengthOf(0) | ||
180 | }) | ||
181 | }) | ||
182 | |||
183 | describe('With a logged user', function () { | ||
184 | it('Should get the local video', async function () { | ||
185 | await getVideoWithToken(servers[0].url, userAccessToken, video1UUID, 200) | ||
186 | }) | ||
187 | |||
188 | it('Should get the remote video', async function () { | ||
189 | await getVideoWithToken(servers[0].url, userAccessToken, video2UUID, 200) | ||
190 | }) | ||
191 | |||
192 | it('Should list local account videos', async function () { | ||
193 | const res = await getAccountVideos(servers[0].url, userAccessToken, 'root@localhost:9001', 0, 5) | ||
194 | |||
195 | expect(res.body.total).to.equal(1) | ||
196 | expect(res.body.data).to.have.lengthOf(1) | ||
197 | }) | ||
198 | |||
199 | it('Should list remote account videos', async function () { | ||
200 | const res = await getAccountVideos(servers[0].url, userAccessToken, 'root@localhost:9002', 0, 5) | ||
201 | |||
202 | expect(res.body.total).to.equal(1) | ||
203 | expect(res.body.data).to.have.lengthOf(1) | ||
204 | }) | ||
205 | |||
206 | it('Should list local channel videos', async function () { | ||
207 | const res = await getVideoChannelVideos(servers[0].url, userAccessToken, 'root_channel@localhost:9001', 0, 5) | ||
208 | |||
209 | expect(res.body.total).to.equal(1) | ||
210 | expect(res.body.data).to.have.lengthOf(1) | ||
211 | }) | ||
212 | |||
213 | it('Should list remote channel videos', async function () { | ||
214 | const res = await getVideoChannelVideos(servers[0].url, userAccessToken, 'root_channel@localhost:9002', 0, 5) | ||
215 | |||
216 | expect(res.body.total).to.equal(1) | ||
217 | expect(res.body.data).to.have.lengthOf(1) | ||
218 | }) | ||
219 | }) | ||
220 | }) | ||
221 | |||
222 | after(async function () { | ||
223 | killallServers(servers) | ||
224 | }) | ||
225 | }) | ||
diff --git a/server/tests/api/server/follows.ts b/server/tests/api/server/follows.ts index e8914a9d4..ad4c87c73 100644 --- a/server/tests/api/server/follows.ts +++ b/server/tests/api/server/follows.ts | |||
@@ -4,7 +4,7 @@ import * as chai from 'chai' | |||
4 | import 'mocha' | 4 | import 'mocha' |
5 | import { Video, VideoPrivacy } from '../../../../shared/models/videos' | 5 | import { Video, VideoPrivacy } from '../../../../shared/models/videos' |
6 | import { VideoComment, VideoCommentThreadTree } from '../../../../shared/models/videos/video-comment.model' | 6 | import { VideoComment, VideoCommentThreadTree } from '../../../../shared/models/videos/video-comment.model' |
7 | import { completeVideoCheck } from '../../utils' | 7 | import { completeVideoCheck } from '../../../../shared/utils' |
8 | import { | 8 | import { |
9 | flushAndRunMultipleServers, | 9 | flushAndRunMultipleServers, |
10 | getVideosList, | 10 | getVideosList, |
@@ -12,21 +12,26 @@ import { | |||
12 | ServerInfo, | 12 | ServerInfo, |
13 | setAccessTokensToServers, | 13 | setAccessTokensToServers, |
14 | uploadVideo | 14 | uploadVideo |
15 | } from '../../utils/index' | 15 | } from '../../../../shared/utils/index' |
16 | import { dateIsValid } from '../../utils/miscs/miscs' | 16 | import { dateIsValid } from '../../../../shared/utils/miscs/miscs' |
17 | import { follow, getFollowersListPaginationAndSort, getFollowingListPaginationAndSort, unfollow } from '../../utils/server/follows' | 17 | import { |
18 | import { expectAccountFollows } from '../../utils/users/accounts' | 18 | follow, |
19 | import { userLogin } from '../../utils/users/login' | 19 | getFollowersListPaginationAndSort, |
20 | import { createUser } from '../../utils/users/users' | 20 | getFollowingListPaginationAndSort, |
21 | unfollow | ||
22 | } from '../../../../shared/utils/server/follows' | ||
23 | import { expectAccountFollows } from '../../../../shared/utils/users/accounts' | ||
24 | import { userLogin } from '../../../../shared/utils/users/login' | ||
25 | import { createUser } from '../../../../shared/utils/users/users' | ||
21 | import { | 26 | import { |
22 | addVideoCommentReply, | 27 | addVideoCommentReply, |
23 | addVideoCommentThread, | 28 | addVideoCommentThread, |
24 | getVideoCommentThreads, | 29 | getVideoCommentThreads, |
25 | getVideoThreadComments | 30 | getVideoThreadComments |
26 | } from '../../utils/videos/video-comments' | 31 | } from '../../../../shared/utils/videos/video-comments' |
27 | import { rateVideo } from '../../utils/videos/videos' | 32 | import { rateVideo } from '../../../../shared/utils/videos/videos' |
28 | import { waitJobs } from '../../utils/server/jobs' | 33 | import { waitJobs } from '../../../../shared/utils/server/jobs' |
29 | import { createVideoCaption, listVideoCaptions, testCaptionFile } from '../../utils/videos/video-captions' | 34 | import { createVideoCaption, listVideoCaptions, testCaptionFile } from '../../../../shared/utils/videos/video-captions' |
30 | import { VideoCaption } from '../../../../shared/models/videos/caption/video-caption.model' | 35 | import { VideoCaption } from '../../../../shared/models/videos/caption/video-caption.model' |
31 | 36 | ||
32 | const expect = chai.expect | 37 | const expect = chai.expect |
@@ -93,7 +98,26 @@ describe('Test follows', function () { | |||
93 | expect(server3Follow.state).to.equal('accepted') | 98 | expect(server3Follow.state).to.equal('accepted') |
94 | }) | 99 | }) |
95 | 100 | ||
96 | it('Should have 0 followings on server 1 and 2', async function () { | 101 | it('Should search followings on server 1', async function () { |
102 | { | ||
103 | const res = await getFollowingListPaginationAndSort(servers[ 0 ].url, 0, 1, 'createdAt', ':9002') | ||
104 | const follows = res.body.data | ||
105 | |||
106 | expect(res.body.total).to.equal(1) | ||
107 | expect(follows.length).to.equal(1) | ||
108 | expect(follows[ 0 ].following.host).to.equal('localhost:9002') | ||
109 | } | ||
110 | |||
111 | { | ||
112 | const res = await getFollowingListPaginationAndSort(servers[ 0 ].url, 0, 1, 'createdAt', 'bla') | ||
113 | const follows = res.body.data | ||
114 | |||
115 | expect(res.body.total).to.equal(0) | ||
116 | expect(follows.length).to.equal(0) | ||
117 | } | ||
118 | }) | ||
119 | |||
120 | it('Should have 0 followings on server 2 and 3', async function () { | ||
97 | for (const server of [ servers[1], servers[2] ]) { | 121 | for (const server of [ servers[1], servers[2] ]) { |
98 | const res = await getFollowingListPaginationAndSort(server.url, 0, 5, 'createdAt') | 122 | const res = await getFollowingListPaginationAndSort(server.url, 0, 5, 'createdAt') |
99 | const follows = res.body.data | 123 | const follows = res.body.data |
@@ -116,6 +140,25 @@ describe('Test follows', function () { | |||
116 | } | 140 | } |
117 | }) | 141 | }) |
118 | 142 | ||
143 | it('Should search followers on server 2', async function () { | ||
144 | { | ||
145 | const res = await getFollowersListPaginationAndSort(servers[ 2 ].url, 0, 5, 'createdAt', '9001') | ||
146 | const follows = res.body.data | ||
147 | |||
148 | expect(res.body.total).to.equal(1) | ||
149 | expect(follows.length).to.equal(1) | ||
150 | expect(follows[ 0 ].following.host).to.equal('localhost:9003') | ||
151 | } | ||
152 | |||
153 | { | ||
154 | const res = await getFollowersListPaginationAndSort(servers[ 2 ].url, 0, 5, 'createdAt', 'bla') | ||
155 | const follows = res.body.data | ||
156 | |||
157 | expect(res.body.total).to.equal(0) | ||
158 | expect(follows.length).to.equal(0) | ||
159 | } | ||
160 | }) | ||
161 | |||
119 | it('Should have 0 followers on server 1', async function () { | 162 | it('Should have 0 followers on server 1', async function () { |
120 | const res = await getFollowersListPaginationAndSort(servers[0].url, 0, 5, 'createdAt') | 163 | const res = await getFollowersListPaginationAndSort(servers[0].url, 0, 5, 'createdAt') |
121 | const follows = res.body.data | 164 | const follows = res.body.data |
diff --git a/server/tests/api/server/handle-down.ts b/server/tests/api/server/handle-down.ts index b0a3d029a..cd5acbe16 100644 --- a/server/tests/api/server/handle-down.ts +++ b/server/tests/api/server/handle-down.ts | |||
@@ -5,24 +5,30 @@ import 'mocha' | |||
5 | import { JobState, Video } from '../../../../shared/models' | 5 | import { JobState, Video } from '../../../../shared/models' |
6 | import { VideoPrivacy } from '../../../../shared/models/videos' | 6 | import { VideoPrivacy } from '../../../../shared/models/videos' |
7 | import { VideoCommentThreadTree } from '../../../../shared/models/videos/video-comment.model' | 7 | import { VideoCommentThreadTree } from '../../../../shared/models/videos/video-comment.model' |
8 | import { completeVideoCheck, getVideo, immutableAssign, reRunServer, unfollow, viewVideo } from '../../utils' | 8 | |
9 | import { | 9 | import { |
10 | completeVideoCheck, | ||
10 | flushAndRunMultipleServers, | 11 | flushAndRunMultipleServers, |
12 | getVideo, | ||
11 | getVideosList, | 13 | getVideosList, |
14 | immutableAssign, | ||
12 | killallServers, | 15 | killallServers, |
16 | reRunServer, | ||
13 | ServerInfo, | 17 | ServerInfo, |
14 | setAccessTokensToServers, | 18 | setAccessTokensToServers, |
19 | unfollow, | ||
20 | updateVideo, | ||
15 | uploadVideo, | 21 | uploadVideo, |
16 | wait | 22 | wait |
17 | } from '../../utils/index' | 23 | } from '../../../../shared/utils' |
18 | import { follow, getFollowersListPaginationAndSort } from '../../utils/server/follows' | 24 | import { follow, getFollowersListPaginationAndSort } from '../../../../shared/utils/server/follows' |
19 | import { getJobsListPaginationAndSort, waitJobs } from '../../utils/server/jobs' | 25 | import { getJobsListPaginationAndSort, waitJobs } from '../../../../shared/utils/server/jobs' |
20 | import { | 26 | import { |
21 | addVideoCommentReply, | 27 | addVideoCommentReply, |
22 | addVideoCommentThread, | 28 | addVideoCommentThread, |
23 | getVideoCommentThreads, | 29 | getVideoCommentThreads, |
24 | getVideoThreadComments | 30 | getVideoThreadComments |
25 | } from '../../utils/videos/video-comments' | 31 | } from '../../../../shared/utils/videos/video-comments' |
26 | 32 | ||
27 | const expect = chai.expect | 33 | const expect = chai.expect |
28 | 34 | ||
@@ -195,15 +201,15 @@ describe('Test handle downs', function () { | |||
195 | expect(res.body.data).to.have.lengthOf(2) | 201 | expect(res.body.data).to.have.lengthOf(2) |
196 | }) | 202 | }) |
197 | 203 | ||
198 | it('Should send a view to server 3, and automatically fetch the video', async function () { | 204 | it('Should send an update to server 3, and automatically fetch the video', async function () { |
199 | this.timeout(15000) | 205 | this.timeout(15000) |
200 | 206 | ||
201 | const res1 = await getVideosList(servers[2].url) | 207 | const res1 = await getVideosList(servers[2].url) |
202 | expect(res1.body.data).to.be.an('array') | 208 | expect(res1.body.data).to.be.an('array') |
203 | expect(res1.body.data).to.have.lengthOf(11) | 209 | expect(res1.body.data).to.have.lengthOf(11) |
204 | 210 | ||
205 | await viewVideo(servers[0].url, missedVideo1.uuid) | 211 | await updateVideo(servers[0].url, servers[0].accessToken, missedVideo1.uuid, { }) |
206 | await viewVideo(servers[0].url, unlistedVideo.uuid) | 212 | await updateVideo(servers[0].url, servers[0].accessToken, unlistedVideo.uuid, { }) |
207 | 213 | ||
208 | await waitJobs(servers) | 214 | await waitJobs(servers) |
209 | 215 | ||
diff --git a/server/tests/api/server/index.ts b/server/tests/api/server/index.ts index c74c68a33..1f80cc6cf 100644 --- a/server/tests/api/server/index.ts +++ b/server/tests/api/server/index.ts | |||
@@ -1,9 +1,11 @@ | |||
1 | import './config' | 1 | import './config' |
2 | import './contact-form' | ||
2 | import './email' | 3 | import './email' |
4 | import './follow-constraints' | ||
3 | import './follows' | 5 | import './follows' |
4 | import './handle-down' | 6 | import './handle-down' |
5 | import './jobs' | 7 | import './jobs' |
6 | import './redundancy' | ||
7 | import './reverse-proxy' | 8 | import './reverse-proxy' |
8 | import './stats' | 9 | import './stats' |
9 | import './tracker' | 10 | import './tracker' |
11 | import './no-client' | ||
diff --git a/server/tests/api/server/jobs.ts b/server/tests/api/server/jobs.ts index cd59d9a1b..52948b1d6 100644 --- a/server/tests/api/server/jobs.ts +++ b/server/tests/api/server/jobs.ts | |||
@@ -2,12 +2,12 @@ | |||
2 | 2 | ||
3 | import * as chai from 'chai' | 3 | import * as chai from 'chai' |
4 | import 'mocha' | 4 | import 'mocha' |
5 | import { killallServers, ServerInfo, setAccessTokensToServers } from '../../utils/index' | 5 | import { killallServers, ServerInfo, setAccessTokensToServers } from '../../../../shared/utils/index' |
6 | import { doubleFollow } from '../../utils/server/follows' | 6 | import { doubleFollow } from '../../../../shared/utils/server/follows' |
7 | import { getJobsList, getJobsListPaginationAndSort, waitJobs } from '../../utils/server/jobs' | 7 | import { getJobsList, getJobsListPaginationAndSort, waitJobs } from '../../../../shared/utils/server/jobs' |
8 | import { flushAndRunMultipleServers } from '../../utils/server/servers' | 8 | import { flushAndRunMultipleServers } from '../../../../shared/utils/server/servers' |
9 | import { uploadVideo } from '../../utils/videos/videos' | 9 | import { uploadVideo } from '../../../../shared/utils/videos/videos' |
10 | import { dateIsValid } from '../../utils/miscs/miscs' | 10 | import { dateIsValid } from '../../../../shared/utils/miscs/miscs' |
11 | 11 | ||
12 | const expect = chai.expect | 12 | const expect = chai.expect |
13 | 13 | ||
diff --git a/server/tests/api/server/no-client.ts b/server/tests/api/server/no-client.ts new file mode 100644 index 000000000..3b95ce945 --- /dev/null +++ b/server/tests/api/server/no-client.ts | |||
@@ -0,0 +1,36 @@ | |||
1 | import 'mocha' | ||
2 | import * as request from 'supertest' | ||
3 | import { | ||
4 | flushTests, | ||
5 | killallServers, | ||
6 | ServerInfo | ||
7 | } from '../../../../shared/utils' | ||
8 | import { runServer } from '../../../../shared/utils/server/servers' | ||
9 | |||
10 | describe('Start and stop server without web client routes', function () { | ||
11 | let server: ServerInfo | ||
12 | |||
13 | before(async function () { | ||
14 | this.timeout(30000) | ||
15 | |||
16 | await flushTests() | ||
17 | |||
18 | server = await runServer(1, {}, ['--no-client']) | ||
19 | }) | ||
20 | |||
21 | it('Should fail getting the client', function () { | ||
22 | const req = request(server.url) | ||
23 | .get('/') | ||
24 | |||
25 | return req.expect(404) | ||
26 | }) | ||
27 | |||
28 | after(async function () { | ||
29 | killallServers([ server ]) | ||
30 | |||
31 | // Keep the logs if the test failed | ||
32 | if (this['ok']) { | ||
33 | await flushTests() | ||
34 | } | ||
35 | }) | ||
36 | }) | ||
diff --git a/server/tests/api/server/redundancy.ts b/server/tests/api/server/redundancy.ts deleted file mode 100644 index 1960854b6..000000000 --- a/server/tests/api/server/redundancy.ts +++ /dev/null | |||
@@ -1,483 +0,0 @@ | |||
1 | /* tslint:disable:no-unused-expression */ | ||
2 | |||
3 | import * as chai from 'chai' | ||
4 | import 'mocha' | ||
5 | import { VideoDetails } from '../../../../shared/models/videos' | ||
6 | import { | ||
7 | doubleFollow, | ||
8 | flushAndRunMultipleServers, | ||
9 | getFollowingListPaginationAndSort, | ||
10 | getVideo, | ||
11 | immutableAssign, | ||
12 | killallServers, makeGetRequest, | ||
13 | root, | ||
14 | ServerInfo, | ||
15 | setAccessTokensToServers, unfollow, | ||
16 | uploadVideo, | ||
17 | viewVideo, | ||
18 | wait, | ||
19 | waitUntilLog, | ||
20 | checkVideoFilesWereRemoved, removeVideo | ||
21 | } from '../../utils' | ||
22 | import { waitJobs } from '../../utils/server/jobs' | ||
23 | import * as magnetUtil from 'magnet-uri' | ||
24 | import { updateRedundancy } from '../../utils/server/redundancy' | ||
25 | import { ActorFollow } from '../../../../shared/models/actors' | ||
26 | import { readdir } from 'fs-extra' | ||
27 | import { join } from 'path' | ||
28 | import { VideoRedundancyStrategy } from '../../../../shared/models/redundancy' | ||
29 | import { getStats } from '../../utils/server/stats' | ||
30 | import { ServerStats } from '../../../../shared/models/server/server-stats.model' | ||
31 | |||
32 | const expect = chai.expect | ||
33 | |||
34 | let servers: ServerInfo[] = [] | ||
35 | let video1Server2UUID: string | ||
36 | |||
37 | function checkMagnetWebseeds (file: { magnetUri: string, resolution: { id: number } }, baseWebseeds: string[], server: ServerInfo) { | ||
38 | const parsed = magnetUtil.decode(file.magnetUri) | ||
39 | |||
40 | for (const ws of baseWebseeds) { | ||
41 | const found = parsed.urlList.find(url => url === `${ws}-${file.resolution.id}.mp4`) | ||
42 | expect(found, `Webseed ${ws} not found in ${file.magnetUri} on server ${server.url}`).to.not.be.undefined | ||
43 | } | ||
44 | |||
45 | expect(parsed.urlList).to.have.lengthOf(baseWebseeds.length) | ||
46 | } | ||
47 | |||
48 | async function runServers (strategy: VideoRedundancyStrategy, additionalParams: any = {}) { | ||
49 | const config = { | ||
50 | redundancy: { | ||
51 | videos: { | ||
52 | check_interval: '5 seconds', | ||
53 | strategies: [ | ||
54 | immutableAssign({ | ||
55 | min_lifetime: '1 hour', | ||
56 | strategy: strategy, | ||
57 | size: '100KB' | ||
58 | }, additionalParams) | ||
59 | ] | ||
60 | } | ||
61 | } | ||
62 | } | ||
63 | servers = await flushAndRunMultipleServers(3, config) | ||
64 | |||
65 | // Get the access tokens | ||
66 | await setAccessTokensToServers(servers) | ||
67 | |||
68 | { | ||
69 | const res = await uploadVideo(servers[ 1 ].url, servers[ 1 ].accessToken, { name: 'video 1 server 2' }) | ||
70 | video1Server2UUID = res.body.video.uuid | ||
71 | |||
72 | await viewVideo(servers[ 1 ].url, video1Server2UUID) | ||
73 | } | ||
74 | |||
75 | await waitJobs(servers) | ||
76 | |||
77 | // Server 1 and server 2 follow each other | ||
78 | await doubleFollow(servers[ 0 ], servers[ 1 ]) | ||
79 | // Server 1 and server 3 follow each other | ||
80 | await doubleFollow(servers[ 0 ], servers[ 2 ]) | ||
81 | // Server 2 and server 3 follow each other | ||
82 | await doubleFollow(servers[ 1 ], servers[ 2 ]) | ||
83 | |||
84 | await waitJobs(servers) | ||
85 | } | ||
86 | |||
87 | async function check1WebSeed (strategy: VideoRedundancyStrategy, videoUUID?: string) { | ||
88 | if (!videoUUID) videoUUID = video1Server2UUID | ||
89 | |||
90 | const webseeds = [ | ||
91 | 'http://localhost:9002/static/webseed/' + videoUUID | ||
92 | ] | ||
93 | |||
94 | for (const server of servers) { | ||
95 | { | ||
96 | const res = await getVideo(server.url, videoUUID) | ||
97 | |||
98 | const video: VideoDetails = res.body | ||
99 | for (const f of video.files) { | ||
100 | checkMagnetWebseeds(f, webseeds, server) | ||
101 | } | ||
102 | } | ||
103 | } | ||
104 | } | ||
105 | |||
106 | async function checkStatsWith2Webseed (strategy: VideoRedundancyStrategy) { | ||
107 | const res = await getStats(servers[0].url) | ||
108 | const data: ServerStats = res.body | ||
109 | |||
110 | expect(data.videosRedundancy).to.have.lengthOf(1) | ||
111 | const stat = data.videosRedundancy[0] | ||
112 | |||
113 | expect(stat.strategy).to.equal(strategy) | ||
114 | expect(stat.totalSize).to.equal(102400) | ||
115 | expect(stat.totalUsed).to.be.at.least(1).and.below(102401) | ||
116 | expect(stat.totalVideoFiles).to.equal(4) | ||
117 | expect(stat.totalVideos).to.equal(1) | ||
118 | } | ||
119 | |||
120 | async function checkStatsWith1Webseed (strategy: VideoRedundancyStrategy) { | ||
121 | const res = await getStats(servers[0].url) | ||
122 | const data: ServerStats = res.body | ||
123 | |||
124 | expect(data.videosRedundancy).to.have.lengthOf(1) | ||
125 | |||
126 | const stat = data.videosRedundancy[0] | ||
127 | expect(stat.strategy).to.equal(strategy) | ||
128 | expect(stat.totalSize).to.equal(102400) | ||
129 | expect(stat.totalUsed).to.equal(0) | ||
130 | expect(stat.totalVideoFiles).to.equal(0) | ||
131 | expect(stat.totalVideos).to.equal(0) | ||
132 | } | ||
133 | |||
134 | async function check2Webseeds (strategy: VideoRedundancyStrategy, videoUUID?: string) { | ||
135 | if (!videoUUID) videoUUID = video1Server2UUID | ||
136 | |||
137 | const webseeds = [ | ||
138 | 'http://localhost:9001/static/webseed/' + videoUUID, | ||
139 | 'http://localhost:9002/static/webseed/' + videoUUID | ||
140 | ] | ||
141 | |||
142 | for (const server of servers) { | ||
143 | const res = await getVideo(server.url, videoUUID) | ||
144 | |||
145 | const video: VideoDetails = res.body | ||
146 | |||
147 | for (const file of video.files) { | ||
148 | checkMagnetWebseeds(file, webseeds, server) | ||
149 | |||
150 | // Only servers 1 and 2 have the video | ||
151 | if (server.serverNumber !== 3) { | ||
152 | await makeGetRequest({ | ||
153 | url: server.url, | ||
154 | statusCodeExpected: 200, | ||
155 | path: '/static/webseed/' + `${videoUUID}-${file.resolution.id}.mp4`, | ||
156 | contentType: null | ||
157 | }) | ||
158 | } | ||
159 | } | ||
160 | } | ||
161 | |||
162 | for (const directory of [ 'test1', 'test2' ]) { | ||
163 | const files = await readdir(join(root(), directory, 'videos')) | ||
164 | expect(files).to.have.length.at.least(4) | ||
165 | |||
166 | for (const resolution of [ 240, 360, 480, 720 ]) { | ||
167 | expect(files.find(f => f === `${videoUUID}-${resolution}.mp4`)).to.not.be.undefined | ||
168 | } | ||
169 | } | ||
170 | } | ||
171 | |||
172 | async function enableRedundancyOnServer1 () { | ||
173 | await updateRedundancy(servers[ 0 ].url, servers[ 0 ].accessToken, servers[ 1 ].host, true) | ||
174 | |||
175 | const res = await getFollowingListPaginationAndSort(servers[ 0 ].url, 0, 5, '-createdAt') | ||
176 | const follows: ActorFollow[] = res.body.data | ||
177 | const server2 = follows.find(f => f.following.host === 'localhost:9002') | ||
178 | const server3 = follows.find(f => f.following.host === 'localhost:9003') | ||
179 | |||
180 | expect(server3).to.not.be.undefined | ||
181 | expect(server3.following.hostRedundancyAllowed).to.be.false | ||
182 | |||
183 | expect(server2).to.not.be.undefined | ||
184 | expect(server2.following.hostRedundancyAllowed).to.be.true | ||
185 | } | ||
186 | |||
187 | async function disableRedundancyOnServer1 () { | ||
188 | await updateRedundancy(servers[ 0 ].url, servers[ 0 ].accessToken, servers[ 1 ].host, false) | ||
189 | |||
190 | const res = await getFollowingListPaginationAndSort(servers[ 0 ].url, 0, 5, '-createdAt') | ||
191 | const follows: ActorFollow[] = res.body.data | ||
192 | const server2 = follows.find(f => f.following.host === 'localhost:9002') | ||
193 | const server3 = follows.find(f => f.following.host === 'localhost:9003') | ||
194 | |||
195 | expect(server3).to.not.be.undefined | ||
196 | expect(server3.following.hostRedundancyAllowed).to.be.false | ||
197 | |||
198 | expect(server2).to.not.be.undefined | ||
199 | expect(server2.following.hostRedundancyAllowed).to.be.false | ||
200 | } | ||
201 | |||
202 | async function cleanServers () { | ||
203 | killallServers(servers) | ||
204 | } | ||
205 | |||
206 | describe('Test videos redundancy', function () { | ||
207 | |||
208 | describe('With most-views strategy', function () { | ||
209 | const strategy = 'most-views' | ||
210 | |||
211 | before(function () { | ||
212 | this.timeout(120000) | ||
213 | |||
214 | return runServers(strategy) | ||
215 | }) | ||
216 | |||
217 | it('Should have 1 webseed on the first video', async function () { | ||
218 | await check1WebSeed(strategy) | ||
219 | await checkStatsWith1Webseed(strategy) | ||
220 | }) | ||
221 | |||
222 | it('Should enable redundancy on server 1', function () { | ||
223 | return enableRedundancyOnServer1() | ||
224 | }) | ||
225 | |||
226 | it('Should have 2 webseed on the first video', async function () { | ||
227 | this.timeout(40000) | ||
228 | |||
229 | await waitJobs(servers) | ||
230 | await waitUntilLog(servers[0], 'Duplicated ', 4) | ||
231 | await waitJobs(servers) | ||
232 | |||
233 | await check2Webseeds(strategy) | ||
234 | await checkStatsWith2Webseed(strategy) | ||
235 | }) | ||
236 | |||
237 | it('Should undo redundancy on server 1 and remove duplicated videos', async function () { | ||
238 | this.timeout(40000) | ||
239 | |||
240 | await disableRedundancyOnServer1() | ||
241 | |||
242 | await waitJobs(servers) | ||
243 | await wait(5000) | ||
244 | |||
245 | await check1WebSeed(strategy) | ||
246 | |||
247 | await checkVideoFilesWereRemoved(video1Server2UUID, servers[0].serverNumber, [ 'videos' ]) | ||
248 | }) | ||
249 | |||
250 | after(function () { | ||
251 | return cleanServers() | ||
252 | }) | ||
253 | }) | ||
254 | |||
255 | describe('With trending strategy', function () { | ||
256 | const strategy = 'trending' | ||
257 | |||
258 | before(function () { | ||
259 | this.timeout(120000) | ||
260 | |||
261 | return runServers(strategy) | ||
262 | }) | ||
263 | |||
264 | it('Should have 1 webseed on the first video', async function () { | ||
265 | await check1WebSeed(strategy) | ||
266 | await checkStatsWith1Webseed(strategy) | ||
267 | }) | ||
268 | |||
269 | it('Should enable redundancy on server 1', function () { | ||
270 | return enableRedundancyOnServer1() | ||
271 | }) | ||
272 | |||
273 | it('Should have 2 webseed on the first video', async function () { | ||
274 | this.timeout(40000) | ||
275 | |||
276 | await waitJobs(servers) | ||
277 | await waitUntilLog(servers[0], 'Duplicated ', 4) | ||
278 | await waitJobs(servers) | ||
279 | |||
280 | await check2Webseeds(strategy) | ||
281 | await checkStatsWith2Webseed(strategy) | ||
282 | }) | ||
283 | |||
284 | it('Should unfollow on server 1 and remove duplicated videos', async function () { | ||
285 | this.timeout(40000) | ||
286 | |||
287 | await unfollow(servers[0].url, servers[0].accessToken, servers[1]) | ||
288 | |||
289 | await waitJobs(servers) | ||
290 | await wait(5000) | ||
291 | |||
292 | await check1WebSeed(strategy) | ||
293 | |||
294 | await checkVideoFilesWereRemoved(video1Server2UUID, servers[0].serverNumber, [ 'videos' ]) | ||
295 | }) | ||
296 | |||
297 | after(function () { | ||
298 | return cleanServers() | ||
299 | }) | ||
300 | }) | ||
301 | |||
302 | describe('With recently added strategy', function () { | ||
303 | const strategy = 'recently-added' | ||
304 | |||
305 | before(function () { | ||
306 | this.timeout(120000) | ||
307 | |||
308 | return runServers(strategy, { min_views: 3 }) | ||
309 | }) | ||
310 | |||
311 | it('Should have 1 webseed on the first video', async function () { | ||
312 | await check1WebSeed(strategy) | ||
313 | await checkStatsWith1Webseed(strategy) | ||
314 | }) | ||
315 | |||
316 | it('Should enable redundancy on server 1', function () { | ||
317 | return enableRedundancyOnServer1() | ||
318 | }) | ||
319 | |||
320 | it('Should still have 1 webseed on the first video', async function () { | ||
321 | this.timeout(40000) | ||
322 | |||
323 | await waitJobs(servers) | ||
324 | await wait(15000) | ||
325 | await waitJobs(servers) | ||
326 | |||
327 | await check1WebSeed(strategy) | ||
328 | await checkStatsWith1Webseed(strategy) | ||
329 | }) | ||
330 | |||
331 | it('Should view 2 times the first video to have > min_views config', async function () { | ||
332 | this.timeout(40000) | ||
333 | |||
334 | await viewVideo(servers[ 0 ].url, video1Server2UUID) | ||
335 | await viewVideo(servers[ 2 ].url, video1Server2UUID) | ||
336 | |||
337 | await wait(10000) | ||
338 | await waitJobs(servers) | ||
339 | }) | ||
340 | |||
341 | it('Should have 2 webseed on the first video', async function () { | ||
342 | this.timeout(40000) | ||
343 | |||
344 | await waitJobs(servers) | ||
345 | await waitUntilLog(servers[0], 'Duplicated ', 4) | ||
346 | await waitJobs(servers) | ||
347 | |||
348 | await check2Webseeds(strategy) | ||
349 | await checkStatsWith2Webseed(strategy) | ||
350 | }) | ||
351 | |||
352 | it('Should remove the video and the redundancy files', async function () { | ||
353 | this.timeout(20000) | ||
354 | |||
355 | await removeVideo(servers[1].url, servers[1].accessToken, video1Server2UUID) | ||
356 | |||
357 | await waitJobs(servers) | ||
358 | |||
359 | for (const server of servers) { | ||
360 | await checkVideoFilesWereRemoved(video1Server2UUID, server.serverNumber) | ||
361 | } | ||
362 | }) | ||
363 | |||
364 | after(function () { | ||
365 | return cleanServers() | ||
366 | }) | ||
367 | }) | ||
368 | |||
369 | describe('Test expiration', function () { | ||
370 | const strategy = 'recently-added' | ||
371 | |||
372 | async function checkContains (servers: ServerInfo[], str: string) { | ||
373 | for (const server of servers) { | ||
374 | const res = await getVideo(server.url, video1Server2UUID) | ||
375 | const video: VideoDetails = res.body | ||
376 | |||
377 | for (const f of video.files) { | ||
378 | expect(f.magnetUri).to.contain(str) | ||
379 | } | ||
380 | } | ||
381 | } | ||
382 | |||
383 | async function checkNotContains (servers: ServerInfo[], str: string) { | ||
384 | for (const server of servers) { | ||
385 | const res = await getVideo(server.url, video1Server2UUID) | ||
386 | const video: VideoDetails = res.body | ||
387 | |||
388 | for (const f of video.files) { | ||
389 | expect(f.magnetUri).to.not.contain(str) | ||
390 | } | ||
391 | } | ||
392 | } | ||
393 | |||
394 | before(async function () { | ||
395 | this.timeout(120000) | ||
396 | |||
397 | await runServers(strategy, { min_lifetime: '7 seconds', min_views: 0 }) | ||
398 | |||
399 | await enableRedundancyOnServer1() | ||
400 | }) | ||
401 | |||
402 | it('Should still have 2 webseeds after 10 seconds', async function () { | ||
403 | this.timeout(40000) | ||
404 | |||
405 | await wait(10000) | ||
406 | |||
407 | try { | ||
408 | await checkContains(servers, 'http%3A%2F%2Flocalhost%3A9001') | ||
409 | } catch { | ||
410 | // Maybe a server deleted a redundancy in the scheduler | ||
411 | await wait(2000) | ||
412 | |||
413 | await checkContains(servers, 'http%3A%2F%2Flocalhost%3A9001') | ||
414 | } | ||
415 | }) | ||
416 | |||
417 | it('Should stop server 1 and expire video redundancy', async function () { | ||
418 | this.timeout(40000) | ||
419 | |||
420 | killallServers([ servers[0] ]) | ||
421 | |||
422 | await wait(10000) | ||
423 | |||
424 | await checkNotContains([ servers[1], servers[2] ], 'http%3A%2F%2Flocalhost%3A9001') | ||
425 | }) | ||
426 | |||
427 | after(function () { | ||
428 | return killallServers([ servers[1], servers[2] ]) | ||
429 | }) | ||
430 | }) | ||
431 | |||
432 | describe('Test file replacement', function () { | ||
433 | let video2Server2UUID: string | ||
434 | const strategy = 'recently-added' | ||
435 | |||
436 | before(async function () { | ||
437 | this.timeout(120000) | ||
438 | |||
439 | await runServers(strategy, { min_lifetime: '7 seconds', min_views: 0 }) | ||
440 | |||
441 | await enableRedundancyOnServer1() | ||
442 | |||
443 | await waitJobs(servers) | ||
444 | await waitUntilLog(servers[0], 'Duplicated ', 4) | ||
445 | await waitJobs(servers) | ||
446 | |||
447 | await check2Webseeds(strategy) | ||
448 | await checkStatsWith2Webseed(strategy) | ||
449 | |||
450 | const res = await uploadVideo(servers[ 1 ].url, servers[ 1 ].accessToken, { name: 'video 2 server 2' }) | ||
451 | video2Server2UUID = res.body.video.uuid | ||
452 | }) | ||
453 | |||
454 | it('Should cache video 2 webseed on the first video', async function () { | ||
455 | this.timeout(50000) | ||
456 | |||
457 | await waitJobs(servers) | ||
458 | |||
459 | await wait(7000) | ||
460 | |||
461 | try { | ||
462 | await check1WebSeed(strategy, video1Server2UUID) | ||
463 | await check2Webseeds(strategy, video2Server2UUID) | ||
464 | } catch { | ||
465 | await wait(3000) | ||
466 | |||
467 | try { | ||
468 | await check1WebSeed(strategy, video1Server2UUID) | ||
469 | await check2Webseeds(strategy, video2Server2UUID) | ||
470 | } catch { | ||
471 | await wait(5000) | ||
472 | |||
473 | await check1WebSeed(strategy, video1Server2UUID) | ||
474 | await check2Webseeds(strategy, video2Server2UUID) | ||
475 | } | ||
476 | } | ||
477 | }) | ||
478 | |||
479 | after(function () { | ||
480 | return cleanServers() | ||
481 | }) | ||
482 | }) | ||
483 | }) | ||
diff --git a/server/tests/api/server/reverse-proxy.ts b/server/tests/api/server/reverse-proxy.ts index e2c2a293e..ee0fffd5a 100644 --- a/server/tests/api/server/reverse-proxy.ts +++ b/server/tests/api/server/reverse-proxy.ts | |||
@@ -15,7 +15,7 @@ import { | |||
15 | userLogin, | 15 | userLogin, |
16 | viewVideo, | 16 | viewVideo, |
17 | wait | 17 | wait |
18 | } from '../../utils' | 18 | } from '../../../../shared/utils' |
19 | const expect = chai.expect | 19 | const expect = chai.expect |
20 | 20 | ||
21 | import { | 21 | import { |
@@ -23,7 +23,7 @@ import { | |||
23 | flushTests, | 23 | flushTests, |
24 | runServer, | 24 | runServer, |
25 | registerUser, getCustomConfig, setAccessTokensToServers, updateCustomConfig | 25 | registerUser, getCustomConfig, setAccessTokensToServers, updateCustomConfig |
26 | } from '../../utils/index' | 26 | } from '../../../../shared/utils/index' |
27 | 27 | ||
28 | describe('Test application behind a reverse proxy', function () { | 28 | describe('Test application behind a reverse proxy', function () { |
29 | let server = null | 29 | let server = null |
@@ -95,7 +95,7 @@ describe('Test application behind a reverse proxy', function () { | |||
95 | it('Should rate limit logins', async function () { | 95 | it('Should rate limit logins', async function () { |
96 | const user = { username: 'root', password: 'fail' } | 96 | const user = { username: 'root', password: 'fail' } |
97 | 97 | ||
98 | for (let i = 0; i < 14; i++) { | 98 | for (let i = 0; i < 19; i++) { |
99 | await userLogin(server, user, 400) | 99 | await userLogin(server, user, 400) |
100 | } | 100 | } |
101 | 101 | ||
diff --git a/server/tests/api/server/stats.ts b/server/tests/api/server/stats.ts index cb229e876..aaa6c62f7 100644 --- a/server/tests/api/server/stats.ts +++ b/server/tests/api/server/stats.ts | |||
@@ -13,11 +13,11 @@ import { | |||
13 | uploadVideo, | 13 | uploadVideo, |
14 | viewVideo, | 14 | viewVideo, |
15 | wait | 15 | wait |
16 | } from '../../utils' | 16 | } from '../../../../shared/utils' |
17 | import { flushTests, setAccessTokensToServers } from '../../utils/index' | 17 | import { flushTests, setAccessTokensToServers } from '../../../../shared/utils/index' |
18 | import { getStats } from '../../utils/server/stats' | 18 | import { getStats } from '../../../../shared/utils/server/stats' |
19 | import { addVideoCommentThread } from '../../utils/videos/video-comments' | 19 | import { addVideoCommentThread } from '../../../../shared/utils/videos/video-comments' |
20 | import { waitJobs } from '../../utils/server/jobs' | 20 | import { waitJobs } from '../../../../shared/utils/server/jobs' |
21 | 21 | ||
22 | const expect = chai.expect | 22 | const expect = chai.expect |
23 | 23 | ||
@@ -39,7 +39,7 @@ describe('Test stats (excluding redundancy)', function () { | |||
39 | } | 39 | } |
40 | await createUser(servers[0].url, servers[0].accessToken, user.username, user.password) | 40 | await createUser(servers[0].url, servers[0].accessToken, user.username, user.password) |
41 | 41 | ||
42 | const resVideo = await uploadVideo(servers[0].url, servers[0].accessToken, {}) | 42 | const resVideo = await uploadVideo(servers[0].url, servers[0].accessToken, { fixture: 'video_short.webm' }) |
43 | const videoUUID = resVideo.body.video.uuid | 43 | const videoUUID = resVideo.body.video.uuid |
44 | 44 | ||
45 | await addVideoCommentThread(servers[0].url, servers[0].accessToken, videoUUID, 'comment') | 45 | await addVideoCommentThread(servers[0].url, servers[0].accessToken, videoUUID, 'comment') |
@@ -60,6 +60,7 @@ describe('Test stats (excluding redundancy)', function () { | |||
60 | expect(data.totalLocalVideoComments).to.equal(1) | 60 | expect(data.totalLocalVideoComments).to.equal(1) |
61 | expect(data.totalLocalVideos).to.equal(1) | 61 | expect(data.totalLocalVideos).to.equal(1) |
62 | expect(data.totalLocalVideoViews).to.equal(1) | 62 | expect(data.totalLocalVideoViews).to.equal(1) |
63 | expect(data.totalLocalVideoFilesSize).to.equal(218910) | ||
63 | expect(data.totalUsers).to.equal(2) | 64 | expect(data.totalUsers).to.equal(2) |
64 | expect(data.totalVideoComments).to.equal(1) | 65 | expect(data.totalVideoComments).to.equal(1) |
65 | expect(data.totalVideos).to.equal(1) | 66 | expect(data.totalVideos).to.equal(1) |
@@ -74,6 +75,7 @@ describe('Test stats (excluding redundancy)', function () { | |||
74 | expect(data.totalLocalVideoComments).to.equal(0) | 75 | expect(data.totalLocalVideoComments).to.equal(0) |
75 | expect(data.totalLocalVideos).to.equal(0) | 76 | expect(data.totalLocalVideos).to.equal(0) |
76 | expect(data.totalLocalVideoViews).to.equal(0) | 77 | expect(data.totalLocalVideoViews).to.equal(0) |
78 | expect(data.totalLocalVideoFilesSize).to.equal(0) | ||
77 | expect(data.totalUsers).to.equal(1) | 79 | expect(data.totalUsers).to.equal(1) |
78 | expect(data.totalVideoComments).to.equal(1) | 80 | expect(data.totalVideoComments).to.equal(1) |
79 | expect(data.totalVideos).to.equal(1) | 81 | expect(data.totalVideos).to.equal(1) |
diff --git a/server/tests/api/server/tracker.ts b/server/tests/api/server/tracker.ts index 856f2f4d1..25ca00029 100644 --- a/server/tests/api/server/tracker.ts +++ b/server/tests/api/server/tracker.ts | |||
@@ -2,8 +2,8 @@ | |||
2 | 2 | ||
3 | import * as magnetUtil from 'magnet-uri' | 3 | import * as magnetUtil from 'magnet-uri' |
4 | import 'mocha' | 4 | import 'mocha' |
5 | import { getVideo, killallServers, runServer, ServerInfo, uploadVideo } from '../../utils' | 5 | import { getVideo, killallServers, runServer, ServerInfo, uploadVideo } from '../../../../shared/utils' |
6 | import { flushTests, setAccessTokensToServers } from '../../utils/index' | 6 | import { flushTests, setAccessTokensToServers } from '../../../../shared/utils/index' |
7 | import { VideoDetails } from '../../../../shared/models/videos' | 7 | import { VideoDetails } from '../../../../shared/models/videos' |
8 | import * as WebTorrent from 'webtorrent' | 8 | import * as WebTorrent from 'webtorrent' |
9 | 9 | ||