diff options
Diffstat (limited to 'shared/extra-utils/server')
-rw-r--r-- | shared/extra-utils/server/index.ts | 2 | ||||
-rw-r--r-- | shared/extra-utils/server/plugins-command.ts | 245 | ||||
-rw-r--r-- | shared/extra-utils/server/plugins.ts | 297 | ||||
-rw-r--r-- | shared/extra-utils/server/servers.ts | 3 |
4 files changed, 254 insertions, 293 deletions
diff --git a/shared/extra-utils/server/index.ts b/shared/extra-utils/server/index.ts index b5b6b2116..e602fec7e 100644 --- a/shared/extra-utils/server/index.ts +++ b/shared/extra-utils/server/index.ts | |||
@@ -4,3 +4,5 @@ export * from './follows-command' | |||
4 | export * from './follows' | 4 | export * from './follows' |
5 | export * from './jobs' | 5 | export * from './jobs' |
6 | export * from './jobs-command' | 6 | export * from './jobs-command' |
7 | export * from './plugins-command' | ||
8 | export * from './plugins' | ||
diff --git a/shared/extra-utils/server/plugins-command.ts b/shared/extra-utils/server/plugins-command.ts new file mode 100644 index 000000000..f06e58a22 --- /dev/null +++ b/shared/extra-utils/server/plugins-command.ts | |||
@@ -0,0 +1,245 @@ | |||
1 | /* eslint-disable @typescript-eslint/no-unused-expressions,@typescript-eslint/require-await */ | ||
2 | |||
3 | import { readJSON, writeJSON } from 'fs-extra' | ||
4 | import { join } from 'path' | ||
5 | import { root } from '@server/helpers/core-utils' | ||
6 | import { HttpStatusCode } from '@shared/core-utils' | ||
7 | import { | ||
8 | PeerTubePlugin, | ||
9 | PeerTubePluginIndex, | ||
10 | PeertubePluginIndexList, | ||
11 | PluginPackageJson, | ||
12 | PluginTranslation, | ||
13 | PluginType, | ||
14 | PublicServerSetting, | ||
15 | RegisteredServerSettings, | ||
16 | ResultList | ||
17 | } from '@shared/models' | ||
18 | import { buildServerDirectory } from '../miscs' | ||
19 | import { AbstractCommand, OverrideCommandOptions } from '../shared' | ||
20 | |||
21 | export class PluginsCommand extends AbstractCommand { | ||
22 | |||
23 | static getPluginTestPath (suffix = '') { | ||
24 | return join(root(), 'server', 'tests', 'fixtures', 'peertube-plugin-test' + suffix) | ||
25 | } | ||
26 | |||
27 | list (options: OverrideCommandOptions & { | ||
28 | start?: number | ||
29 | count?: number | ||
30 | sort?: string | ||
31 | pluginType?: PluginType | ||
32 | uninstalled?: boolean | ||
33 | }) { | ||
34 | const { start, count, sort, pluginType, uninstalled } = options | ||
35 | const path = '/api/v1/plugins' | ||
36 | |||
37 | return this.getRequestBody<ResultList<PeerTubePlugin>>({ | ||
38 | ...options, | ||
39 | |||
40 | path, | ||
41 | query: { | ||
42 | start, | ||
43 | count, | ||
44 | sort, | ||
45 | pluginType, | ||
46 | uninstalled | ||
47 | }, | ||
48 | defaultExpectedStatus: HttpStatusCode.OK_200 | ||
49 | }) | ||
50 | } | ||
51 | |||
52 | listAvailable (options: OverrideCommandOptions & { | ||
53 | start?: number | ||
54 | count?: number | ||
55 | sort?: string | ||
56 | pluginType?: PluginType | ||
57 | currentPeerTubeEngine?: string | ||
58 | search?: string | ||
59 | expectedStatus?: HttpStatusCode | ||
60 | }) { | ||
61 | const { start, count, sort, pluginType, search, currentPeerTubeEngine } = options | ||
62 | const path = '/api/v1/plugins/available' | ||
63 | |||
64 | const query: PeertubePluginIndexList = { | ||
65 | start, | ||
66 | count, | ||
67 | sort, | ||
68 | pluginType, | ||
69 | currentPeerTubeEngine, | ||
70 | search | ||
71 | } | ||
72 | |||
73 | return this.getRequestBody<ResultList<PeerTubePluginIndex>>({ | ||
74 | ...options, | ||
75 | |||
76 | path, | ||
77 | query, | ||
78 | defaultExpectedStatus: HttpStatusCode.OK_200 | ||
79 | }) | ||
80 | } | ||
81 | |||
82 | get (options: OverrideCommandOptions & { | ||
83 | npmName: string | ||
84 | }) { | ||
85 | const path = '/api/v1/plugins/' + options.npmName | ||
86 | |||
87 | return this.getRequestBody<PeerTubePlugin>({ | ||
88 | ...options, | ||
89 | |||
90 | path, | ||
91 | defaultExpectedStatus: HttpStatusCode.OK_200 | ||
92 | }) | ||
93 | } | ||
94 | |||
95 | updateSettings (options: OverrideCommandOptions & { | ||
96 | npmName: string | ||
97 | settings: any | ||
98 | }) { | ||
99 | const { npmName, settings } = options | ||
100 | const path = '/api/v1/plugins/' + npmName + '/settings' | ||
101 | |||
102 | return this.putBodyRequest({ | ||
103 | ...options, | ||
104 | |||
105 | path, | ||
106 | fields: { settings }, | ||
107 | defaultExpectedStatus: HttpStatusCode.NO_CONTENT_204 | ||
108 | }) | ||
109 | } | ||
110 | |||
111 | getRegisteredSettings (options: OverrideCommandOptions & { | ||
112 | npmName: string | ||
113 | }) { | ||
114 | const path = '/api/v1/plugins/' + options.npmName + '/registered-settings' | ||
115 | |||
116 | return this.getRequestBody<RegisteredServerSettings>({ | ||
117 | ...options, | ||
118 | |||
119 | path, | ||
120 | defaultExpectedStatus: HttpStatusCode.OK_200 | ||
121 | }) | ||
122 | } | ||
123 | |||
124 | getPublicSettings (options: OverrideCommandOptions & { | ||
125 | npmName: string | ||
126 | }) { | ||
127 | const { npmName } = options | ||
128 | const path = '/api/v1/plugins/' + npmName + '/public-settings' | ||
129 | |||
130 | return this.getRequestBody<PublicServerSetting>({ | ||
131 | ...options, | ||
132 | |||
133 | path, | ||
134 | defaultExpectedStatus: HttpStatusCode.OK_200 | ||
135 | }) | ||
136 | } | ||
137 | |||
138 | getTranslations (options: OverrideCommandOptions & { | ||
139 | locale: string | ||
140 | }) { | ||
141 | const { locale } = options | ||
142 | const path = '/plugins/translations/' + locale + '.json' | ||
143 | |||
144 | return this.getRequestBody<PluginTranslation>({ | ||
145 | ...options, | ||
146 | |||
147 | path, | ||
148 | defaultExpectedStatus: HttpStatusCode.OK_200 | ||
149 | }) | ||
150 | } | ||
151 | |||
152 | install (options: OverrideCommandOptions & { | ||
153 | path?: string | ||
154 | npmName?: string | ||
155 | }) { | ||
156 | const { npmName, path } = options | ||
157 | const apiPath = '/api/v1/plugins/install' | ||
158 | |||
159 | return this.postBodyRequest({ | ||
160 | ...options, | ||
161 | |||
162 | path: apiPath, | ||
163 | fields: { npmName, path }, | ||
164 | defaultExpectedStatus: HttpStatusCode.OK_200 | ||
165 | }) | ||
166 | } | ||
167 | |||
168 | update (options: OverrideCommandOptions & { | ||
169 | path?: string | ||
170 | npmName?: string | ||
171 | }) { | ||
172 | const { npmName, path } = options | ||
173 | const apiPath = '/api/v1/plugins/update' | ||
174 | |||
175 | return this.postBodyRequest({ | ||
176 | ...options, | ||
177 | |||
178 | path: apiPath, | ||
179 | fields: { npmName, path }, | ||
180 | defaultExpectedStatus: HttpStatusCode.OK_200 | ||
181 | }) | ||
182 | } | ||
183 | |||
184 | uninstall (options: OverrideCommandOptions & { | ||
185 | npmName: string | ||
186 | }) { | ||
187 | const { npmName } = options | ||
188 | const apiPath = '/api/v1/plugins/uninstall' | ||
189 | |||
190 | return this.postBodyRequest({ | ||
191 | ...options, | ||
192 | |||
193 | path: apiPath, | ||
194 | fields: { npmName }, | ||
195 | defaultExpectedStatus: HttpStatusCode.NO_CONTENT_204 | ||
196 | }) | ||
197 | } | ||
198 | |||
199 | getCSS (options: OverrideCommandOptions = {}) { | ||
200 | const path = '/plugins/global.css' | ||
201 | |||
202 | return this.getRequestText({ | ||
203 | ...options, | ||
204 | |||
205 | path, | ||
206 | defaultExpectedStatus: HttpStatusCode.OK_200 | ||
207 | }) | ||
208 | } | ||
209 | |||
210 | getExternalAuth (options: OverrideCommandOptions & { | ||
211 | npmName: string | ||
212 | npmVersion: string | ||
213 | authName: string | ||
214 | query?: any | ||
215 | }) { | ||
216 | const { npmName, npmVersion, authName, query } = options | ||
217 | |||
218 | const path = '/plugins/' + npmName + '/' + npmVersion + '/auth/' + authName | ||
219 | |||
220 | return this.getRequest({ | ||
221 | ...options, | ||
222 | |||
223 | path, | ||
224 | query, | ||
225 | defaultExpectedStatus: HttpStatusCode.OK_200, | ||
226 | redirects: 0 | ||
227 | }) | ||
228 | } | ||
229 | |||
230 | updatePackageJSON (npmName: string, json: any) { | ||
231 | const path = this.getPackageJSONPath(npmName) | ||
232 | |||
233 | return writeJSON(path, json) | ||
234 | } | ||
235 | |||
236 | getPackageJSON (npmName: string): Promise<PluginPackageJson> { | ||
237 | const path = this.getPackageJSONPath(npmName) | ||
238 | |||
239 | return readJSON(path) | ||
240 | } | ||
241 | |||
242 | private getPackageJSONPath (npmName: string) { | ||
243 | return buildServerDirectory(this.server, join('plugins', 'node_modules', npmName, 'package.json')) | ||
244 | } | ||
245 | } | ||
diff --git a/shared/extra-utils/server/plugins.ts b/shared/extra-utils/server/plugins.ts index d53e5b382..1084ea4f4 100644 --- a/shared/extra-utils/server/plugins.ts +++ b/shared/extra-utils/server/plugins.ts | |||
@@ -1,307 +1,18 @@ | |||
1 | /* eslint-disable @typescript-eslint/no-unused-expressions,@typescript-eslint/require-await */ | 1 | /* eslint-disable @typescript-eslint/no-unused-expressions,@typescript-eslint/require-await */ |
2 | 2 | ||
3 | import { expect } from 'chai' | 3 | import { expect } from 'chai' |
4 | import { readJSON, writeJSON } from 'fs-extra' | 4 | import { ServerInfo } from '../server/servers' |
5 | import { join } from 'path' | ||
6 | import { RegisteredServerSettings } from '@shared/models' | ||
7 | import { HttpStatusCode } from '../../../shared/core-utils/miscs/http-error-codes' | ||
8 | import { PeertubePluginIndexList } from '../../models/plugins/plugin-index/peertube-plugin-index-list.model' | ||
9 | import { PluginType } from '../../models/plugins/plugin.type' | ||
10 | import { buildServerDirectory, root } from '../miscs/miscs' | ||
11 | import { makeGetRequest, makePostBodyRequest, makePutBodyRequest } from '../requests/requests' | ||
12 | import { ServerInfo } from './servers' | ||
13 | |||
14 | function listPlugins (parameters: { | ||
15 | url: string | ||
16 | accessToken: string | ||
17 | start?: number | ||
18 | count?: number | ||
19 | sort?: string | ||
20 | pluginType?: PluginType | ||
21 | uninstalled?: boolean | ||
22 | expectedStatus?: HttpStatusCode | ||
23 | }) { | ||
24 | const { url, accessToken, start, count, sort, pluginType, uninstalled, expectedStatus = HttpStatusCode.OK_200 } = parameters | ||
25 | const path = '/api/v1/plugins' | ||
26 | |||
27 | return makeGetRequest({ | ||
28 | url, | ||
29 | path, | ||
30 | token: accessToken, | ||
31 | query: { | ||
32 | start, | ||
33 | count, | ||
34 | sort, | ||
35 | pluginType, | ||
36 | uninstalled | ||
37 | }, | ||
38 | statusCodeExpected: expectedStatus | ||
39 | }) | ||
40 | } | ||
41 | |||
42 | function listAvailablePlugins (parameters: { | ||
43 | url: string | ||
44 | accessToken: string | ||
45 | start?: number | ||
46 | count?: number | ||
47 | sort?: string | ||
48 | pluginType?: PluginType | ||
49 | currentPeerTubeEngine?: string | ||
50 | search?: string | ||
51 | expectedStatus?: HttpStatusCode | ||
52 | }) { | ||
53 | const { | ||
54 | url, | ||
55 | accessToken, | ||
56 | start, | ||
57 | count, | ||
58 | sort, | ||
59 | pluginType, | ||
60 | search, | ||
61 | currentPeerTubeEngine, | ||
62 | expectedStatus = HttpStatusCode.OK_200 | ||
63 | } = parameters | ||
64 | const path = '/api/v1/plugins/available' | ||
65 | |||
66 | const query: PeertubePluginIndexList = { | ||
67 | start, | ||
68 | count, | ||
69 | sort, | ||
70 | pluginType, | ||
71 | currentPeerTubeEngine, | ||
72 | search | ||
73 | } | ||
74 | |||
75 | return makeGetRequest({ | ||
76 | url, | ||
77 | path, | ||
78 | token: accessToken, | ||
79 | query, | ||
80 | statusCodeExpected: expectedStatus | ||
81 | }) | ||
82 | } | ||
83 | |||
84 | function getPlugin (parameters: { | ||
85 | url: string | ||
86 | accessToken: string | ||
87 | npmName: string | ||
88 | expectedStatus?: HttpStatusCode | ||
89 | }) { | ||
90 | const { url, accessToken, npmName, expectedStatus = HttpStatusCode.OK_200 } = parameters | ||
91 | const path = '/api/v1/plugins/' + npmName | ||
92 | |||
93 | return makeGetRequest({ | ||
94 | url, | ||
95 | path, | ||
96 | token: accessToken, | ||
97 | statusCodeExpected: expectedStatus | ||
98 | }) | ||
99 | } | ||
100 | |||
101 | function updatePluginSettings (parameters: { | ||
102 | url: string | ||
103 | accessToken: string | ||
104 | npmName: string | ||
105 | settings: any | ||
106 | expectedStatus?: HttpStatusCode | ||
107 | }) { | ||
108 | const { url, accessToken, npmName, settings, expectedStatus = HttpStatusCode.NO_CONTENT_204 } = parameters | ||
109 | const path = '/api/v1/plugins/' + npmName + '/settings' | ||
110 | |||
111 | return makePutBodyRequest({ | ||
112 | url, | ||
113 | path, | ||
114 | token: accessToken, | ||
115 | fields: { settings }, | ||
116 | statusCodeExpected: expectedStatus | ||
117 | }) | ||
118 | } | ||
119 | |||
120 | function getPluginRegisteredSettings (parameters: { | ||
121 | url: string | ||
122 | accessToken: string | ||
123 | npmName: string | ||
124 | expectedStatus?: HttpStatusCode | ||
125 | }) { | ||
126 | const { url, accessToken, npmName, expectedStatus = HttpStatusCode.OK_200 } = parameters | ||
127 | const path = '/api/v1/plugins/' + npmName + '/registered-settings' | ||
128 | |||
129 | return makeGetRequest({ | ||
130 | url, | ||
131 | path, | ||
132 | token: accessToken, | ||
133 | statusCodeExpected: expectedStatus | ||
134 | }) | ||
135 | } | ||
136 | 5 | ||
137 | async function testHelloWorldRegisteredSettings (server: ServerInfo) { | 6 | async function testHelloWorldRegisteredSettings (server: ServerInfo) { |
138 | const res = await getPluginRegisteredSettings({ | 7 | const body = await server.pluginsCommand.getRegisteredSettings({ npmName: 'peertube-plugin-hello-world' }) |
139 | url: server.url, | ||
140 | accessToken: server.accessToken, | ||
141 | npmName: 'peertube-plugin-hello-world' | ||
142 | }) | ||
143 | |||
144 | const registeredSettings = (res.body as RegisteredServerSettings).registeredSettings | ||
145 | 8 | ||
9 | const registeredSettings = body.registeredSettings | ||
146 | expect(registeredSettings).to.have.length.at.least(1) | 10 | expect(registeredSettings).to.have.length.at.least(1) |
147 | 11 | ||
148 | const adminNameSettings = registeredSettings.find(s => s.name === 'admin-name') | 12 | const adminNameSettings = registeredSettings.find(s => s.name === 'admin-name') |
149 | expect(adminNameSettings).to.not.be.undefined | 13 | expect(adminNameSettings).to.not.be.undefined |
150 | } | 14 | } |
151 | 15 | ||
152 | function getPublicSettings (parameters: { | ||
153 | url: string | ||
154 | npmName: string | ||
155 | expectedStatus?: HttpStatusCode | ||
156 | }) { | ||
157 | const { url, npmName, expectedStatus = HttpStatusCode.OK_200 } = parameters | ||
158 | const path = '/api/v1/plugins/' + npmName + '/public-settings' | ||
159 | |||
160 | return makeGetRequest({ | ||
161 | url, | ||
162 | path, | ||
163 | statusCodeExpected: expectedStatus | ||
164 | }) | ||
165 | } | ||
166 | |||
167 | function getPluginTranslations (parameters: { | ||
168 | url: string | ||
169 | locale: string | ||
170 | expectedStatus?: HttpStatusCode | ||
171 | }) { | ||
172 | const { url, locale, expectedStatus = HttpStatusCode.OK_200 } = parameters | ||
173 | const path = '/plugins/translations/' + locale + '.json' | ||
174 | |||
175 | return makeGetRequest({ | ||
176 | url, | ||
177 | path, | ||
178 | statusCodeExpected: expectedStatus | ||
179 | }) | ||
180 | } | ||
181 | |||
182 | function installPlugin (parameters: { | ||
183 | url: string | ||
184 | accessToken: string | ||
185 | path?: string | ||
186 | npmName?: string | ||
187 | expectedStatus?: HttpStatusCode | ||
188 | }) { | ||
189 | const { url, accessToken, npmName, path, expectedStatus = HttpStatusCode.OK_200 } = parameters | ||
190 | const apiPath = '/api/v1/plugins/install' | ||
191 | |||
192 | return makePostBodyRequest({ | ||
193 | url, | ||
194 | path: apiPath, | ||
195 | token: accessToken, | ||
196 | fields: { npmName, path }, | ||
197 | statusCodeExpected: expectedStatus | ||
198 | }) | ||
199 | } | ||
200 | |||
201 | function updatePlugin (parameters: { | ||
202 | url: string | ||
203 | accessToken: string | ||
204 | path?: string | ||
205 | npmName?: string | ||
206 | expectedStatus?: HttpStatusCode | ||
207 | }) { | ||
208 | const { url, accessToken, npmName, path, expectedStatus = HttpStatusCode.OK_200 } = parameters | ||
209 | const apiPath = '/api/v1/plugins/update' | ||
210 | |||
211 | return makePostBodyRequest({ | ||
212 | url, | ||
213 | path: apiPath, | ||
214 | token: accessToken, | ||
215 | fields: { npmName, path }, | ||
216 | statusCodeExpected: expectedStatus | ||
217 | }) | ||
218 | } | ||
219 | |||
220 | function uninstallPlugin (parameters: { | ||
221 | url: string | ||
222 | accessToken: string | ||
223 | npmName: string | ||
224 | expectedStatus?: HttpStatusCode | ||
225 | }) { | ||
226 | const { url, accessToken, npmName, expectedStatus = HttpStatusCode.NO_CONTENT_204 } = parameters | ||
227 | const apiPath = '/api/v1/plugins/uninstall' | ||
228 | |||
229 | return makePostBodyRequest({ | ||
230 | url, | ||
231 | path: apiPath, | ||
232 | token: accessToken, | ||
233 | fields: { npmName }, | ||
234 | statusCodeExpected: expectedStatus | ||
235 | }) | ||
236 | } | ||
237 | |||
238 | function getPluginsCSS (url: string) { | ||
239 | const path = '/plugins/global.css' | ||
240 | |||
241 | return makeGetRequest({ | ||
242 | url, | ||
243 | path, | ||
244 | statusCodeExpected: HttpStatusCode.OK_200 | ||
245 | }) | ||
246 | } | ||
247 | |||
248 | function getPackageJSONPath (server: ServerInfo, npmName: string) { | ||
249 | return buildServerDirectory(server, join('plugins', 'node_modules', npmName, 'package.json')) | ||
250 | } | ||
251 | |||
252 | function updatePluginPackageJSON (server: ServerInfo, npmName: string, json: any) { | ||
253 | const path = getPackageJSONPath(server, npmName) | ||
254 | |||
255 | return writeJSON(path, json) | ||
256 | } | ||
257 | |||
258 | function getPluginPackageJSON (server: ServerInfo, npmName: string) { | ||
259 | const path = getPackageJSONPath(server, npmName) | ||
260 | |||
261 | return readJSON(path) | ||
262 | } | ||
263 | |||
264 | function getPluginTestPath (suffix = '') { | ||
265 | return join(root(), 'server', 'tests', 'fixtures', 'peertube-plugin-test' + suffix) | ||
266 | } | ||
267 | |||
268 | function getExternalAuth (options: { | ||
269 | url: string | ||
270 | npmName: string | ||
271 | npmVersion: string | ||
272 | authName: string | ||
273 | query?: any | ||
274 | statusCodeExpected?: HttpStatusCode | ||
275 | }) { | ||
276 | const { url, npmName, npmVersion, authName, statusCodeExpected, query } = options | ||
277 | |||
278 | const path = '/plugins/' + npmName + '/' + npmVersion + '/auth/' + authName | ||
279 | |||
280 | return makeGetRequest({ | ||
281 | url, | ||
282 | path, | ||
283 | query, | ||
284 | statusCodeExpected: statusCodeExpected || HttpStatusCode.OK_200, | ||
285 | redirects: 0 | ||
286 | }) | ||
287 | } | ||
288 | |||
289 | export { | 16 | export { |
290 | listPlugins, | 17 | testHelloWorldRegisteredSettings |
291 | listAvailablePlugins, | ||
292 | installPlugin, | ||
293 | getPluginTranslations, | ||
294 | getPluginsCSS, | ||
295 | updatePlugin, | ||
296 | getPlugin, | ||
297 | uninstallPlugin, | ||
298 | testHelloWorldRegisteredSettings, | ||
299 | updatePluginSettings, | ||
300 | getPluginRegisteredSettings, | ||
301 | getPackageJSONPath, | ||
302 | updatePluginPackageJSON, | ||
303 | getPluginPackageJSON, | ||
304 | getPluginTestPath, | ||
305 | getPublicSettings, | ||
306 | getExternalAuth | ||
307 | } | 18 | } |
diff --git a/shared/extra-utils/server/servers.ts b/shared/extra-utils/server/servers.ts index 5511ce0b0..79d6b7b1a 100644 --- a/shared/extra-utils/server/servers.ts +++ b/shared/extra-utils/server/servers.ts | |||
@@ -20,6 +20,7 @@ import { ContactFormCommand } from './contact-form-command' | |||
20 | import { DebugCommand } from './debug-command' | 20 | import { DebugCommand } from './debug-command' |
21 | import { FollowsCommand } from './follows-command' | 21 | import { FollowsCommand } from './follows-command' |
22 | import { JobsCommand } from './jobs-command' | 22 | import { JobsCommand } from './jobs-command' |
23 | import { PluginsCommand } from './plugins-command' | ||
23 | 24 | ||
24 | interface ServerInfo { | 25 | interface ServerInfo { |
25 | app: ChildProcess | 26 | app: ChildProcess |
@@ -85,6 +86,7 @@ interface ServerInfo { | |||
85 | debugCommand?: DebugCommand | 86 | debugCommand?: DebugCommand |
86 | followsCommand?: FollowsCommand | 87 | followsCommand?: FollowsCommand |
87 | jobsCommand?: JobsCommand | 88 | jobsCommand?: JobsCommand |
89 | pluginsCommand?: PluginsCommand | ||
88 | } | 90 | } |
89 | 91 | ||
90 | function parallelTests () { | 92 | function parallelTests () { |
@@ -302,6 +304,7 @@ async function runServer (server: ServerInfo, configOverrideArg?: any, args = [] | |||
302 | server.debugCommand = new DebugCommand(server) | 304 | server.debugCommand = new DebugCommand(server) |
303 | server.followsCommand = new FollowsCommand(server) | 305 | server.followsCommand = new FollowsCommand(server) |
304 | server.jobsCommand = new JobsCommand(server) | 306 | server.jobsCommand = new JobsCommand(server) |
307 | server.pluginsCommand = new PluginsCommand(server) | ||
305 | 308 | ||
306 | res(server) | 309 | res(server) |
307 | }) | 310 | }) |