]>
Commit | Line | Data |
---|---|---|
41fb13c3 | 1 | import express from 'express' |
5e2b2e27 | 2 | import { body, param, query, ValidationChain } from 'express-validator' |
c0e8b12e | 3 | import { HttpStatusCode } from '../../../shared/models/http/http-error-codes' |
428ccb8b C |
4 | import { PluginType } from '../../../shared/models/plugins/plugin.type' |
5 | import { InstallOrUpdatePlugin } from '../../../shared/models/plugins/server/api/install-plugin.model' | |
6 | import { exists, isBooleanValid, isSafePath, toBooleanOrNull, toIntOrNull } from '../../helpers/custom-validators/misc' | |
b5f919ac | 7 | import { isNpmPluginNameValid, isPluginNameValid, isPluginTypeValid, isPluginVersionValid } from '../../helpers/custom-validators/plugins' |
428ccb8b C |
8 | import { logger } from '../../helpers/logger' |
9 | import { CONFIG } from '../../initializers/config' | |
345da516 | 10 | import { PluginManager } from '../../lib/plugins/plugin-manager' |
ad91e700 | 11 | import { PluginModel } from '../../models/server/plugin' |
10363c74 | 12 | import { areValidationErrors } from './shared' |
345da516 | 13 | |
5e2b2e27 C |
14 | const getPluginValidator = (pluginType: PluginType, withVersion = true) => { |
15 | const validators: (ValidationChain | express.Handler)[] = [ | |
16 | param('pluginName').custom(isPluginNameValid).withMessage('Should have a valid plugin name') | |
17 | ] | |
345da516 | 18 | |
5e2b2e27 C |
19 | if (withVersion) { |
20 | validators.push( | |
21 | param('pluginVersion').custom(isPluginVersionValid).withMessage('Should have a valid plugin version') | |
22 | ) | |
23 | } | |
345da516 | 24 | |
5e2b2e27 C |
25 | return validators.concat([ |
26 | (req: express.Request, res: express.Response, next: express.NextFunction) => { | |
27 | logger.debug('Checking getPluginValidator parameters', { parameters: req.params }) | |
28 | ||
29 | if (areValidationErrors(req, res)) return | |
30 | ||
31 | const npmName = PluginModel.buildNpmName(req.params.pluginName, pluginType) | |
32 | const plugin = PluginManager.Instance.getRegisteredPluginOrTheme(npmName) | |
33 | ||
76148b27 RK |
34 | if (!plugin) { |
35 | return res.fail({ | |
36 | status: HttpStatusCode.NOT_FOUND_404, | |
37 | message: 'No plugin found named ' + npmName | |
38 | }) | |
39 | } | |
40 | if (withVersion && plugin.version !== req.params.pluginVersion) { | |
41 | return res.fail({ | |
42 | status: HttpStatusCode.NOT_FOUND_404, | |
43 | message: 'No plugin found named ' + npmName + ' with version ' + req.params.pluginVersion | |
44 | }) | |
45 | } | |
345da516 | 46 | |
5e2b2e27 | 47 | res.locals.registeredPlugin = plugin |
345da516 | 48 | |
5e2b2e27 | 49 | return next() |
345da516 | 50 | } |
5e2b2e27 C |
51 | ]) |
52 | } | |
53 | ||
4a8d113b C |
54 | const getExternalAuthValidator = [ |
55 | param('authName').custom(exists).withMessage('Should have a valid auth name'), | |
56 | ||
57 | (req: express.Request, res: express.Response, next: express.NextFunction) => { | |
58 | logger.debug('Checking getExternalAuthValidator parameters', { parameters: req.params }) | |
59 | ||
60 | if (areValidationErrors(req, res)) return | |
61 | ||
62 | const plugin = res.locals.registeredPlugin | |
76148b27 RK |
63 | if (!plugin.registerHelpers) { |
64 | return res.fail({ | |
65 | status: HttpStatusCode.NOT_FOUND_404, | |
66 | message: 'No registered helpers were found for this plugin' | |
67 | }) | |
68 | } | |
4a8d113b | 69 | |
1896bca0 | 70 | const externalAuth = plugin.registerHelpers.getExternalAuths().find(a => a.authName === req.params.authName) |
76148b27 RK |
71 | if (!externalAuth) { |
72 | return res.fail({ | |
73 | status: HttpStatusCode.NOT_FOUND_404, | |
74 | message: 'No external auths were found for this plugin' | |
75 | }) | |
76 | } | |
4a8d113b C |
77 | |
78 | res.locals.externalAuth = externalAuth | |
79 | ||
80 | return next() | |
81 | } | |
82 | ] | |
83 | ||
5e2b2e27 C |
84 | const pluginStaticDirectoryValidator = [ |
85 | param('staticEndpoint').custom(isSafePath).withMessage('Should have a valid static endpoint'), | |
345da516 | 86 | |
5e2b2e27 C |
87 | (req: express.Request, res: express.Response, next: express.NextFunction) => { |
88 | logger.debug('Checking pluginStaticDirectoryValidator parameters', { parameters: req.params }) | |
89 | ||
90 | if (areValidationErrors(req, res)) return | |
345da516 C |
91 | |
92 | return next() | |
93 | } | |
94 | ] | |
95 | ||
ad91e700 | 96 | const listPluginsValidator = [ |
6702a1b2 | 97 | query('pluginType') |
ad91e700 | 98 | .optional() |
a02b93ce | 99 | .customSanitizer(toIntOrNull) |
ad91e700 C |
100 | .custom(isPluginTypeValid).withMessage('Should have a valid plugin type'), |
101 | query('uninstalled') | |
102 | .optional() | |
c8861d5d | 103 | .customSanitizer(toBooleanOrNull) |
ad91e700 C |
104 | .custom(isBooleanValid).withMessage('Should have a valid uninstalled attribute'), |
105 | ||
106 | (req: express.Request, res: express.Response, next: express.NextFunction) => { | |
107 | logger.debug('Checking listPluginsValidator parameters', { parameters: req.query }) | |
108 | ||
109 | if (areValidationErrors(req, res)) return | |
110 | ||
111 | return next() | |
112 | } | |
113 | ] | |
114 | ||
b5f919ac | 115 | const installOrUpdatePluginValidator = [ |
8d2be0ed C |
116 | body('npmName') |
117 | .optional() | |
118 | .custom(isNpmPluginNameValid).withMessage('Should have a valid npm name'), | |
3a1157a6 JL |
119 | body('pluginVersion') |
120 | .optional() | |
121 | .custom(isPluginVersionValid).withMessage('Should have a valid plugin version'), | |
8d2be0ed C |
122 | body('path') |
123 | .optional() | |
124 | .custom(isSafePath).withMessage('Should have a valid safe path'), | |
ad91e700 C |
125 | |
126 | (req: express.Request, res: express.Response, next: express.NextFunction) => { | |
b5f919ac | 127 | logger.debug('Checking installOrUpdatePluginValidator parameters', { parameters: req.body }) |
ad91e700 C |
128 | |
129 | if (areValidationErrors(req, res)) return | |
130 | ||
b5f919ac | 131 | const body: InstallOrUpdatePlugin = req.body |
8d2be0ed | 132 | if (!body.path && !body.npmName) { |
76148b27 | 133 | return res.fail({ message: 'Should have either a npmName or a path' }) |
8d2be0ed | 134 | } |
3a1157a6 JL |
135 | if (body.pluginVersion && !body.npmName) { |
136 | return res.fail({ message: 'Should have a npmName when specifying a pluginVersion' }) | |
137 | } | |
8d2be0ed | 138 | |
ad91e700 C |
139 | return next() |
140 | } | |
141 | ] | |
142 | ||
143 | const uninstallPluginValidator = [ | |
144 | body('npmName').custom(isNpmPluginNameValid).withMessage('Should have a valid npm name'), | |
145 | ||
146 | (req: express.Request, res: express.Response, next: express.NextFunction) => { | |
dba85a1e | 147 | logger.debug('Checking uninstallPluginValidator parameters', { parameters: req.body }) |
ad91e700 C |
148 | |
149 | if (areValidationErrors(req, res)) return | |
150 | ||
151 | return next() | |
152 | } | |
153 | ] | |
154 | ||
dba85a1e | 155 | const existingPluginValidator = [ |
60cfd4cb | 156 | param('npmName').custom(isNpmPluginNameValid).withMessage('Should have a valid plugin name'), |
ad91e700 C |
157 | |
158 | async (req: express.Request, res: express.Response, next: express.NextFunction) => { | |
dba85a1e | 159 | logger.debug('Checking enabledPluginValidator parameters', { parameters: req.params }) |
ad91e700 C |
160 | |
161 | if (areValidationErrors(req, res)) return | |
162 | ||
dba85a1e | 163 | const plugin = await PluginModel.loadByNpmName(req.params.npmName) |
ad91e700 | 164 | if (!plugin) { |
76148b27 RK |
165 | return res.fail({ |
166 | status: HttpStatusCode.NOT_FOUND_404, | |
167 | message: 'Plugin not found' | |
168 | }) | |
ad91e700 C |
169 | } |
170 | ||
171 | res.locals.plugin = plugin | |
ad91e700 C |
172 | return next() |
173 | } | |
174 | ] | |
175 | ||
176 | const updatePluginSettingsValidator = [ | |
177 | body('settings').exists().withMessage('Should have settings'), | |
178 | ||
179 | (req: express.Request, res: express.Response, next: express.NextFunction) => { | |
180 | logger.debug('Checking enabledPluginValidator parameters', { parameters: req.body }) | |
181 | ||
182 | if (areValidationErrors(req, res)) return | |
183 | ||
184 | return next() | |
185 | } | |
186 | ] | |
187 | ||
6702a1b2 | 188 | const listAvailablePluginsValidator = [ |
6702a1b2 C |
189 | query('search') |
190 | .optional() | |
191 | .exists().withMessage('Should have a valid search'), | |
192 | query('pluginType') | |
193 | .optional() | |
a02b93ce | 194 | .customSanitizer(toIntOrNull) |
6702a1b2 | 195 | .custom(isPluginTypeValid).withMessage('Should have a valid plugin type'), |
09071200 C |
196 | query('currentPeerTubeEngine') |
197 | .optional() | |
198 | .custom(isPluginVersionValid).withMessage('Should have a valid current peertube engine'), | |
6702a1b2 C |
199 | |
200 | (req: express.Request, res: express.Response, next: express.NextFunction) => { | |
201 | logger.debug('Checking enabledPluginValidator parameters', { parameters: req.query }) | |
202 | ||
203 | if (areValidationErrors(req, res)) return | |
204 | ||
205 | if (CONFIG.PLUGINS.INDEX.ENABLED === false) { | |
76148b27 | 206 | return res.fail({ message: 'Plugin index is not enabled' }) |
6702a1b2 C |
207 | } |
208 | ||
209 | return next() | |
210 | } | |
211 | ] | |
212 | ||
345da516 C |
213 | // --------------------------------------------------------------------------- |
214 | ||
215 | export { | |
5e2b2e27 C |
216 | pluginStaticDirectoryValidator, |
217 | getPluginValidator, | |
ad91e700 C |
218 | updatePluginSettingsValidator, |
219 | uninstallPluginValidator, | |
6702a1b2 | 220 | listAvailablePluginsValidator, |
dba85a1e | 221 | existingPluginValidator, |
b5f919ac | 222 | installOrUpdatePluginValidator, |
4a8d113b C |
223 | listPluginsValidator, |
224 | getExternalAuthValidator | |
345da516 | 225 | } |