diff options
| author | 2024-09-22 11:05:06 +0200 | |
|---|---|---|
| committer | 2024-09-22 11:05:06 +0200 | |
| commit | 1c09408c6459eb8d719d94ba593edfa44883cb85 (patch) | |
| tree | 67e8e8e464c2f491aae2a5c16bb8ee46bcb2b41b | |
| parent | c599ff4e4b09274f23369706e92b5040aa182038 (diff) | |
Fix HTML encodings in e.g. cURL options (#6821)
* Fix HTML encodings in e.g. cURL options
* Trim headers whitespace
| -rwxr-xr-x | app/Controllers/feedController.php | 15 | ||||
| -rw-r--r-- | app/Controllers/subscriptionController.php | 15 | ||||
| -rw-r--r-- | app/layout/aside_configure.phtml | 2 | ||||
| -rw-r--r-- | app/views/helpers/feed/update.phtml | 15 | ||||
| -rw-r--r-- | lib/Minz/Request.php | 9 | ||||
| -rw-r--r-- | lib/core-extensions/UserCSS/extension.php | 4 | ||||
| -rw-r--r-- | lib/core-extensions/UserJS/extension.php | 4 |
7 files changed, 35 insertions, 29 deletions
diff --git a/app/Controllers/feedController.php b/app/Controllers/feedController.php index c2d25821d..105099966 100755 --- a/app/Controllers/feedController.php +++ b/app/Controllers/feedController.php @@ -170,15 +170,15 @@ class FreshRSS_feed_Controller extends FreshRSS_ActionController { $http_auth = $user . ':' . $pass; } - $cookie = Minz_Request::paramString('curl_params_cookie'); + $cookie = Minz_Request::paramString('curl_params_cookie', plaintext: true); $cookie_file = Minz_Request::paramBoolean('curl_params_cookiefile'); $max_redirs = Minz_Request::paramInt('curl_params_redirects'); - $useragent = Minz_Request::paramString('curl_params_useragent'); - $proxy_address = Minz_Request::paramString('curl_params'); - $proxy_type = Minz_Request::paramString('proxy_type'); - $request_method = Minz_Request::paramString('curl_method'); - $request_fields = Minz_Request::paramString('curl_fields', true); - $headers = Minz_Request::paramTextToArray('http_headers'); + $useragent = Minz_Request::paramString('curl_params_useragent', plaintext: true); + $proxy_address = Minz_Request::paramString('curl_params', plaintext: true); + $proxy_type = Minz_Request::paramString('proxy_type', plaintext: true); + $request_method = Minz_Request::paramString('curl_method', plaintext: true); + $request_fields = Minz_Request::paramString('curl_fields', plaintext: true); + $headers = Minz_Request::paramTextToArray('http_headers', plaintext: true); $opts = []; if ($proxy_type !== '') { @@ -210,6 +210,7 @@ class FreshRSS_feed_Controller extends FreshRSS_ActionController { } } if(!empty($headers)) { + $headers = array_filter(array_map('trim', $headers)); $opts[CURLOPT_HTTPHEADER] = array_merge($headers, $opts[CURLOPT_HTTPHEADER] ?? []); } diff --git a/app/Controllers/subscriptionController.php b/app/Controllers/subscriptionController.php index 225e93f95..e2e3bbf11 100644 --- a/app/Controllers/subscriptionController.php +++ b/app/Controllers/subscriptionController.php @@ -138,15 +138,15 @@ class FreshRSS_subscription_Controller extends FreshRSS_ActionController { } $feed->_attribute('read_when_same_title_in_feed', $read_when_same_title_in_feed); - $cookie = Minz_Request::paramString('curl_params_cookie'); + $cookie = Minz_Request::paramString('curl_params_cookie', plaintext: true); $cookie_file = Minz_Request::paramBoolean('curl_params_cookiefile'); $max_redirs = Minz_Request::paramInt('curl_params_redirects'); - $useragent = Minz_Request::paramString('curl_params_useragent'); - $proxy_address = Minz_Request::paramString('curl_params'); - $proxy_type = Minz_Request::paramString('proxy_type'); - $request_method = Minz_Request::paramString('curl_method'); - $request_fields = Minz_Request::paramString('curl_fields', true); - $headers = Minz_Request::paramTextToArray('http_headers'); + $useragent = Minz_Request::paramString('curl_params_useragent', plaintext: true); + $proxy_address = Minz_Request::paramString('curl_params', plaintext: true); + $proxy_type = Minz_Request::paramString('proxy_type', plaintext: true); + $request_method = Minz_Request::paramString('curl_method', plaintext: true); + $request_fields = Minz_Request::paramString('curl_fields', plaintext: true); + $headers = Minz_Request::paramTextToArray('http_headers', plaintext: true); $opts = []; if ($proxy_type !== '') { $opts[CURLOPT_PROXY] = $proxy_address; @@ -179,6 +179,7 @@ class FreshRSS_subscription_Controller extends FreshRSS_ActionController { } if(!empty($headers)) { + $headers = array_filter(array_map('trim', $headers)); $opts[CURLOPT_HTTPHEADER] = array_merge($headers, $opts[CURLOPT_HTTPHEADER] ?? []); } diff --git a/app/layout/aside_configure.phtml b/app/layout/aside_configure.phtml index 4d4571c4e..06c5efa83 100644 --- a/app/layout/aside_configure.phtml +++ b/app/layout/aside_configure.phtml @@ -6,7 +6,7 @@ <ul> <li class="item nav-section"> - <div class="item nav-header"><?= _t('gen.menu.account') ?>: <?= htmlspecialchars(Minz_User::name() ?? '', ENT_NOQUOTES, 'UTF-8')?></div> + <div class="item nav-header"><?= _t('gen.menu.account') ?>: <?= htmlspecialchars(Minz_User::name() ?? '', ENT_NOQUOTES, 'UTF-8') ?></div> <ul> <li class="item<?= Minz_Request::controllerName() === 'user' && Minz_Request::actionName() === 'profile' ? ' active' : '' ?>"> <a href="<?= _url('user', 'profile') ?>"><?= _t('gen.menu.user_profile') ?></a> diff --git a/app/views/helpers/feed/update.phtml b/app/views/helpers/feed/update.phtml index 5a08d1a3e..5a14eff0f 100644 --- a/app/views/helpers/feed/update.phtml +++ b/app/views/helpers/feed/update.phtml @@ -646,7 +646,7 @@ <label class="group-name" for="curl_params_cookie"><?= _t('sub.feed.css_cookie') ?></label> <div class="group-controls"> <input type="text" name="curl_params_cookie" id="curl_params_cookie" class="w100" value="<?= - !empty($curlParams[CURLOPT_COOKIE]) ? $curlParams[CURLOPT_COOKIE] : '' + htmlspecialchars((string)($curlParams[CURLOPT_COOKIE] ?? ''), ENT_COMPAT, 'UTF-8') ?>" placeholder="<?= _t('gen.short.blank_to_disable') ?>" /> <p class="help"><?= _i('help') ?> <?= _t('sub.feed.css_cookie_help') ?></p> <label for="curl_params_cookiefile"> @@ -684,7 +684,7 @@ <label class="group-name" for="curl_params_useragent"><?= _t('sub.feed.useragent') ?></label> <div class="group-controls"> <input type="text" name="curl_params_useragent" id="curl_params_useragent" class="w100" value="<?= - !empty($curlParams[CURLOPT_USERAGENT]) ? $curlParams[CURLOPT_USERAGENT] : '' + htmlspecialchars((string)($curlParams[CURLOPT_USERAGENT] ?? ''), ENT_COMPAT, 'UTF-8') ?>" placeholder="<?= _t('gen.short.blank_to_disable') ?>" /> <p class="help"><?= _i('help') ?> <?= _t('sub.feed.useragent_help') ?></p> </div> @@ -701,7 +701,7 @@ ?> </select> <input type="text" name="curl_params" id="curl_params" value="<?= - !empty($curlParams[CURLOPT_PROXY]) ? $curlParams[CURLOPT_PROXY] : '' + htmlspecialchars((string)($curlParams[CURLOPT_PROXY] ?? ''), ENT_COMPAT, 'UTF-8') ?>" placeholder="<?= _t('gen.short.blank_to_disable') ?>" /> <p class="help"><?= _i('help') ?> <?= _t('sub.feed.proxy_help') ?></p> </div> @@ -722,8 +722,7 @@ </select> <div class="stick"> <input type="text" name="curl_fields" id="curl_fields" value="<?= - $this->feed->attributeArray('curl_params') !== null && !empty($this->feed->attributeArray('curl_params')[CURLOPT_POSTFIELDS]) ? - htmlentities($this->feed->attributeArray('curl_params')[CURLOPT_POSTFIELDS], ENT_COMPAT) : '' + htmlspecialchars($this->feed->attributeArray('curl_params')[CURLOPT_POSTFIELDS] ?? '', ENT_COMPAT, 'UTF-8') ?>" placeholder="<?= _t('sub.feed.method_postparams') ?>" /> </div> <p class="help"><?= _i('help') ?> <?= _t('sub.feed.method_help') ?></p> @@ -751,7 +750,11 @@ <div class="form-group"> <label class="group-name" for="http_headers"><?= _t('sub.feed.http_headers') ?></label> <div class="group-controls"> - <textarea class="valid-json" id="http_headers" name="http_headers" rows="3" cols="64" spellcheck="false"><?= !empty($this->feed->attributeArray('curl_params')) ? implode(PHP_EOL, $this->feed->attributeArray('curl_params')[CURLOPT_HTTPHEADER]) : '' ?></textarea> + <textarea class="valid-json" id="http_headers" name="http_headers" rows="3" cols="64" spellcheck="false"><?php + foreach ($this->feed->attributeArray('curl_params')[CURLOPT_HTTPHEADER] ?? [] as $header) { + echo htmlspecialchars($header, ENT_NOQUOTES, 'UTF-8'), PHP_EOL; + } + ?></textarea> <p class="help"><?= _i('help') ?> <?= _t('sub.feed.http_headers_help') ?></p> </div> </div> diff --git a/lib/Minz/Request.php b/lib/Minz/Request.php index 13a4f6841..b4d4549a9 100644 --- a/lib/Minz/Request.php +++ b/lib/Minz/Request.php @@ -142,14 +142,15 @@ class Minz_Request { * It will return an array where each cell contains one line of a text. The new line * character is used to break the text into lines. This method is well suited to use * to split textarea content. - * @param array<string> $default + * @param bool $plaintext `true` to return special characters without any escaping (unsafe), `false` (default) to XML-encode them * @return array<string> */ - public static function paramTextToArray(string $key, array $default = []): array { + public static function paramTextToArray(string $key, bool $plaintext = false): array { if (isset(self::$params[$key]) && is_string(self::$params[$key])) { - return preg_split('/\R/u', self::$params[$key]) ?: []; + $result = preg_split('/\R/u', self::$params[$key]) ?: []; + return $plaintext ? $result : Minz_Helper::htmlspecialchars_utf8($result); } - return $default; + return []; } public static function defaultControllerName(): string { diff --git a/lib/core-extensions/UserCSS/extension.php b/lib/core-extensions/UserCSS/extension.php index 5343fd39a..c0622b145 100644 --- a/lib/core-extensions/UserCSS/extension.php +++ b/lib/core-extensions/UserCSS/extension.php @@ -22,13 +22,13 @@ final class UserCSSExtension extends Minz_Extension { $this->registerTranslates(); if (Minz_Request::isPost()) { - $css_rules = html_entity_decode(Minz_Request::paramString('css-rules')); + $css_rules = Minz_Request::paramString('css-rules', plaintext: true); $this->saveFile(self::FILENAME, $css_rules); } $this->css_rules = ''; if ($this->hasFile(self::FILENAME)) { - $this->css_rules = htmlentities($this->getFile(self::FILENAME) ?? ''); + $this->css_rules = htmlspecialchars($this->getFile(self::FILENAME) ?? '', ENT_NOQUOTES, 'UTF-8'); } } } diff --git a/lib/core-extensions/UserJS/extension.php b/lib/core-extensions/UserJS/extension.php index a33114ec5..3b860029a 100644 --- a/lib/core-extensions/UserJS/extension.php +++ b/lib/core-extensions/UserJS/extension.php @@ -22,13 +22,13 @@ final class UserJSExtension extends Minz_Extension { $this->registerTranslates(); if (Minz_Request::isPost()) { - $js_rules = html_entity_decode(Minz_Request::paramString('js-rules')); + $js_rules = Minz_Request::paramString('js-rules', plaintext: true); $this->saveFile(self::FILENAME, $js_rules); } $this->js_rules = ''; if ($this->hasFile(self::FILENAME)) { - $this->js_rules = htmlentities($this->getFile(self::FILENAME) ?? ''); + $this->js_rules = htmlspecialchars($this->getFile(self::FILENAME) ?? '', ENT_NOQUOTES, 'UTF-8'); } } } |
