summaryrefslogtreecommitdiff
path: root/lib
diff options
context:
space:
mode:
Diffstat (limited to 'lib')
-rw-r--r--lib/Favicon/DataAccess.php3
-rw-r--r--lib/Favicon/Favicon.php2
-rw-r--r--lib/Minz/Request.php22
-rw-r--r--lib/Minz/Session.php19
-rw-r--r--lib/Minz/Url.php10
-rw-r--r--lib/SimplePie/SimplePie.php15
-rw-r--r--lib/SimplePie/SimplePie/Item.php1
-rw-r--r--lib/SimplePie/SimplePie/Misc.php4
-rw-r--r--lib/SimplePie/SimplePie/Sanitize.php77
-rw-r--r--lib/lib_opml.php4
-rw-r--r--lib/lib_rss.php53
11 files changed, 182 insertions, 28 deletions
diff --git a/lib/Favicon/DataAccess.php b/lib/Favicon/DataAccess.php
index 2bfdf640e..17f26b333 100644
--- a/lib/Favicon/DataAccess.php
+++ b/lib/Favicon/DataAccess.php
@@ -15,7 +15,8 @@ class DataAccess {
public function retrieveHeader($url) {
$this->set_context();
- return @get_headers($url, TRUE);
+ $headers = @get_headers($url, 1);
+ return array_change_key_case($headers);
}
public function saveCache($file, $data) {
diff --git a/lib/Favicon/Favicon.php b/lib/Favicon/Favicon.php
index 7ea6ccf16..1912050d6 100644
--- a/lib/Favicon/Favicon.php
+++ b/lib/Favicon/Favicon.php
@@ -99,7 +99,7 @@ class Favicon
switch ($status) {
case '301':
case '302':
- $url = $headers['Location'];
+ $url = isset($headers['location']) ? $headers['location'] : '';
break;
default:
$loop = FALSE;
diff --git a/lib/Minz/Request.php b/lib/Minz/Request.php
index effb9943c..f80b707d6 100644
--- a/lib/Minz/Request.php
+++ b/lib/Minz/Request.php
@@ -85,6 +85,17 @@ class Minz_Request {
}
/**
+ * Return true if the request is over HTTPS, false otherwise (HTTP)
+ */
+ public static function isHttps() {
+ if (isset($_SERVER['HTTP_X_FORWARDED_PROTO'])) {
+ return strtolower($_SERVER['HTTP_X_FORWARDED_PROTO']) === 'https';
+ } else {
+ return isset($_SERVER['HTTPS']) && $_SERVER['HTTPS'] === 'on';
+ }
+ }
+
+ /**
* Try to guess the base URL from $_SERVER information
*
* @return the base url (e.g. http://example.com/)
@@ -92,11 +103,7 @@ class Minz_Request {
public static function guessBaseUrl() {
$url = 'http';
- if (isset($_SERVER['HTTP_X_FORWARDED_PROTO'])) {
- $https = strtolower($_SERVER['HTTP_X_FORWARDED_PROTO']) === 'https';
- } else {
- $https = isset($_SERVER['HTTPS']) && $_SERVER['HTTPS'] === 'on';
- }
+ $https = self::isHttps();
if (!empty($_SERVER['HTTP_HOST'])) {
$host = $_SERVER['HTTP_HOST'];
@@ -130,12 +137,11 @@ class Minz_Request {
/**
* Return the base_url from configuration and add a suffix if given.
*
- * @param $base_url_suffix a string to add at base_url (default: empty string)
* @return the base_url with a suffix.
*/
- public static function getBaseUrl($base_url_suffix = '') {
+ public static function getBaseUrl() {
$conf = Minz_Configuration::get('system');
- $url = rtrim($conf->base_url, '/\\') . $base_url_suffix;
+ $url = rtrim($conf->base_url, '/\\');
return filter_var($url, FILTER_SANITIZE_URL);
}
diff --git a/lib/Minz/Session.php b/lib/Minz/Session.php
index 057e7746a..c94f2b646 100644
--- a/lib/Minz/Session.php
+++ b/lib/Minz/Session.php
@@ -59,18 +59,21 @@ class Minz_Session {
}
}
+ public static function getCookieDir() {
+ // Get the script_name (e.g. /p/i/index.php) and keep only the path.
+ $cookie_dir = empty($_SERVER['REQUEST_URI']) ? '/' : $_SERVER['REQUEST_URI'];
+ if (substr($cookie_dir, -1) !== '/') {
+ $cookie_dir = dirname($cookie_dir) . '/';
+ }
+ return $cookie_dir;
+ }
/**
* Spécifie la durée de vie des cookies
* @param $l la durée de vie
*/
public static function keepCookie($l) {
- // Get the script_name (e.g. /p/i/index.php) and keep only the path.
- $cookie_dir = empty($_SERVER['REQUEST_URI']) ? '/' : $_SERVER['REQUEST_URI'];
- if (substr($cookie_dir, -1) !== '/') {
- $cookie_dir = dirname($cookie_dir) . '/';
- }
- session_set_cookie_params($l, $cookie_dir, '', false, true);
+ session_set_cookie_params($l, self::getCookieDir(), '', Minz_Request::isHttps(), true);
}
@@ -83,11 +86,11 @@ class Minz_Session {
}
public static function deleteLongTermCookie($name) {
- setcookie($name, '', 1, '', '', false, true);
+ setcookie($name, '', 1, '', '', Minz_Request::isHttps(), true);
}
public static function setLongTermCookie($name, $value, $expire) {
- setcookie($name, $value, $expire, '', '', false, true);
+ setcookie($name, $value, $expire, '', '', Minz_Request::isHttps(), true);
}
public static function getLongTermCookie($name) {
diff --git a/lib/Minz/Url.php b/lib/Minz/Url.php
index 4279b045b..c7c67123e 100644
--- a/lib/Minz/Url.php
+++ b/lib/Minz/Url.php
@@ -24,10 +24,16 @@ class Minz_Url {
$url_string = '';
if ($absolute) {
- $url_string = Minz_Request::getBaseUrl(PUBLIC_TO_INDEX_PATH);
- if ($url_string === PUBLIC_TO_INDEX_PATH) {
+ $url_string = Minz_Request::getBaseUrl();
+ if ($url_string == '') {
$url_string = Minz_Request::guessBaseUrl();
}
+ if ($isArray) {
+ $url_string .= PUBLIC_TO_INDEX_PATH;
+ }
+ if ($absolute === 'root') {
+ $url_string = parse_url($url_string, PHP_URL_PATH);
+ }
} else {
$url_string = $isArray ? '.' : PUBLIC_RELATIVE;
}
diff --git a/lib/SimplePie/SimplePie.php b/lib/SimplePie/SimplePie.php
index 6c0962a9f..8af55c9fd 100644
--- a/lib/SimplePie/SimplePie.php
+++ b/lib/SimplePie/SimplePie.php
@@ -1123,6 +1123,7 @@ class SimplePie
$this->strip_attributes(false);
$this->add_attributes(false);
$this->set_image_handler(false);
+ $this->set_https_domains(array());
}
}
@@ -1234,6 +1235,19 @@ class SimplePie
}
/**
+ * Set the list of domains for which force HTTPS.
+ * @see SimplePie_Sanitize::set_https_domains()
+ * FreshRSS
+ */
+ public function set_https_domains($domains = array())
+ {
+ if (is_array($domains))
+ {
+ $this->sanitize->set_https_domains($domains);
+ }
+ }
+
+ /**
* Set the handler to enable the display of cached images.
*
* @param str $page Web-accessible path to the handler_image.php file.
@@ -1654,6 +1668,7 @@ class SimplePie
$locate = null;
}
+ $file->body = trim($file->body);
$this->raw_data = $file->body;
$this->permanent_url = $file->permanent_url;
$headers = $file->headers;
diff --git a/lib/SimplePie/SimplePie/Item.php b/lib/SimplePie/SimplePie/Item.php
index 27e93456e..19ba7c8f4 100644
--- a/lib/SimplePie/SimplePie/Item.php
+++ b/lib/SimplePie/SimplePie/Item.php
@@ -2877,6 +2877,7 @@ class SimplePie_Item
$width = null;
$url = $this->sanitize($enclosure[0]['attribs']['']['url'], SIMPLEPIE_CONSTRUCT_IRI, $this->get_base($enclosure[0]));
+ $url = $this->feed->sanitize->https_url($url); //FreshRSS
if (isset($enclosure[0]['attribs']['']['type']))
{
$type = $this->sanitize($enclosure[0]['attribs']['']['type'], SIMPLEPIE_CONSTRUCT_TEXT);
diff --git a/lib/SimplePie/SimplePie/Misc.php b/lib/SimplePie/SimplePie/Misc.php
index 9e7ac4fa8..2d154cbcb 100644
--- a/lib/SimplePie/SimplePie/Misc.php
+++ b/lib/SimplePie/SimplePie/Misc.php
@@ -80,8 +80,8 @@ class SimplePie_Misc
public static function absolutize_url($relative, $base)
{
if (substr($relative, 0, 2) === '//')
- {//Allow protocol-relative URLs "//www.example.net" which will pick HTTP or HTTPS automatically
- return $relative;
+ {//Protocol-relative URLs "//www.example.net"
+ return 'https:' . $relative;
}
$iri = SimplePie_IRI::absolutize(new SimplePie_IRI($base), $relative);
if ($iri === false)
diff --git a/lib/SimplePie/SimplePie/Sanitize.php b/lib/SimplePie/SimplePie/Sanitize.php
index a6863ec03..bdc601100 100644
--- a/lib/SimplePie/SimplePie/Sanitize.php
+++ b/lib/SimplePie/SimplePie/Sanitize.php
@@ -73,6 +73,15 @@ class SimplePie_Sanitize
var $force_fsockopen = false;
var $replace_url_attributes = null;
+ /**
+ * List of domains for which force HTTPS.
+ * @see SimplePie_Sanitize::set_https_domains()
+ * Array is tree split at DNS levels. Example:
+ * array('biz' => true, 'com' => array('example' => true), 'net' => array('example') => array('www' => true))
+ * FreshRSS
+ */
+ var $https_domains = array('com' => array('dailymotion' => true, 'youtube' => true));
+
public function __construct()
{
// Set defaults
@@ -242,6 +251,71 @@ class SimplePie_Sanitize
$this->replace_url_attributes = (array) $element_attribute;
}
+ /**
+ * Set the list of domains for which force HTTPS.
+ * @see SimplePie_Misc::https_url()
+ * Example array('biz', 'example.com', 'example.org', 'www.example.net');
+ * FreshRSS
+ */
+ public function set_https_domains($domains)
+ {
+ $this->https_domains = array();
+ foreach ($domains as $domain)
+ {
+ $domain = trim($domain, ". \t\n\r\0\x0B");
+ $segments = array_reverse(explode('.', $domain));
+ $node =& $this->https_domains;
+ foreach ($segments as $segment)
+ {//Build a tree
+ if ($node === true)
+ {
+ break;
+ }
+ if (!isset($node[$segment]))
+ {
+ $node[$segment] = array();
+ }
+ $node =& $node[$segment];
+ }
+ $node = true;
+ }
+ }
+
+ /**
+ * Check if the domain is in the list of forced HTTPS
+ * FreshRSS
+ */
+ protected function is_https_domain($domain)
+ {
+ $domain = trim($domain, '. ');
+ $segments = array_reverse(explode('.', $domain));
+ $node =& $this->https_domains;
+ foreach ($segments as $segment)
+ {//Explore the tree
+ if (isset($node[$segment]))
+ {
+ $node =& $node[$segment];
+ }
+ else
+ {
+ break;
+ }
+ }
+ return $node === true;
+ }
+
+ /**
+ * Force HTTPS for selected Web sites
+ * FreshRSS
+ */
+ public function https_url($url)
+ {
+ return (strtolower(substr($url, 0, 7)) === 'http://') &&
+ $this->is_https_domain(parse_url($url, PHP_URL_HOST)) ?
+ substr_replace($url, 's', 4, 0) : //Add the 's' to HTTPS
+ $url;
+ }
+
public function sanitize($data, $type, $base = '')
{
$data = trim($data);
@@ -451,7 +525,8 @@ class SimplePie_Sanitize
if ($element->hasAttribute($attribute))
{
$value = $this->registry->call('Misc', 'absolutize_url', array($element->getAttribute($attribute), $this->base));
- if ($value !== false)
+ $value = $this->https_url($value); //FreshRSS
+ if ($value)
{
$element->setAttribute($attribute, $value);
}
diff --git a/lib/lib_opml.php b/lib/lib_opml.php
index 02ae5f55c..66b854313 100644
--- a/lib/lib_opml.php
+++ b/lib/lib_opml.php
@@ -105,6 +105,10 @@ function libopml_parse_outline($outline_xml, $strict = true) {
);
}
+ if (empty($outline['text']) && isset($outline['title'])) {
+ $outline['text'] = $outline['title'];
+ }
+
foreach ($outline_xml->children() as $key => $value) {
// An outline may contain any number of outline children
if ($key === 'outline') {
diff --git a/lib/lib_rss.php b/lib/lib_rss.php
index 2a23fca45..f89baf9b1 100644
--- a/lib/lib_rss.php
+++ b/lib/lib_rss.php
@@ -1,20 +1,49 @@
<?php
if (!function_exists('json_decode')) {
require_once('JSON.php');
- function json_decode($var) {
- $JSON = new Services_JSON;
- return (array)($JSON->decode($var));
+ function json_decode($var, $assoc = false) {
+ $JSON = new Services_JSON($assoc ? SERVICES_JSON_LOOSE_TYPE : 0);
+ return $JSON->decode($var);
}
}
if (!function_exists('json_encode')) {
require_once('JSON.php');
function json_encode($var) {
- $JSON = new Services_JSON;
+ $JSON = new Services_JSON();
return $JSON->encodeUnsafe($var);
}
}
+if (!function_exists('array_replace_recursive')) { //PHP 5.2
+ function arr_recurse($array, $array1) {
+ foreach ($array1 as $key => $value) {
+ if (!isset($array[$key]) || (isset($array[$key]) && !is_array($array[$key]))) {
+ $array[$key] = array(); //create new key in $array, if it is empty or not an array
+ }
+ if (is_array($value)) {
+ $value = arr_recurse($array[$key], $value); // overwrite the value in the base array
+ }
+ $array[$key] = $value;
+ }
+ return $array;
+ }
+ function array_replace_recursive($array, $array1) { //http://php.net/manual/function.array-replace-recursive.php#92574
+ // handle the arguments, merge one by one
+ $args = func_get_args();
+ $array = $args[0];
+ if (!is_array($array)) {
+ return $array;
+ }
+ for ($i = 1; $i < count($args); $i++) {
+ if (is_array($args[$i])) {
+ $array = arr_recurse($array, $args[$i]);
+ }
+ }
+ return $array;
+ }
+}
+
/**
* Build a directory path by concatenating a list of directory names.
*
@@ -180,7 +209,7 @@ function customSimplePie() {
$simplePie->strip_attributes(array_merge($simplePie->strip_attributes, array(
'autoplay', 'onload', 'onunload', 'onclick', 'ondblclick', 'onmousedown', 'onmouseup',
'onmouseover', 'onmousemove', 'onmouseout', 'onfocus', 'onblur',
- 'onkeypress', 'onkeydown', 'onkeyup', 'onselect', 'onchange', 'seamless')));
+ 'onkeypress', 'onkeydown', 'onkeyup', 'onselect', 'onchange', 'seamless', 'sizes', 'srcset')));
$simplePie->add_attributes(array(
'img' => array('lazyload' => '', 'postpone' => ''), //http://www.w3.org/TR/resource-priorities/
'audio' => array('lazyload' => '', 'postpone' => '', 'preload' => 'none'),
@@ -209,6 +238,16 @@ function customSimplePie() {
'src',
),
));
+ $https_domains = array();
+ $force = @file(DATA_PATH . '/force-https.default.txt', FILE_IGNORE_NEW_LINES | FILE_SKIP_EMPTY_LINES);
+ if (is_array($force)) {
+ $https_domains = array_merge($https_domains, $force);
+ }
+ $force = @file(DATA_PATH . '/force-https.txt', FILE_IGNORE_NEW_LINES | FILE_SKIP_EMPTY_LINES);
+ if (is_array($force)) {
+ $https_domains = array_merge($https_domains, $force);
+ }
+ $simplePie->set_https_domains($https_domains);
return $simplePie;
}
@@ -509,3 +548,7 @@ function base64url_encode($data) {
function base64url_decode($data) {
return base64_decode(strtr($data, '-_', '+/'));
}
+
+function _i($icon, $url_only = false) {
+ return FreshRSS_Themes::icon($icon, $url_only);
+}