X-Git-Url: https://git.immae.eu/?a=blobdiff_plain;f=application%2FUtils.php;h=ab463af9749cf3a597305fa37e1e91dbcf26046f;hb=105fb7a2a0f46598b7ea423c86a999ef96ace1ec;hp=a936b09fa87710ef86df5ffd9f28a8584b9ac09c;hpb=52b503105d389d1796698114573ff618b2ad34a2;p=github%2Fshaarli%2FShaarli.git diff --git a/application/Utils.php b/application/Utils.php index a936b09f..ab463af9 100644 --- a/application/Utils.php +++ b/application/Utils.php @@ -216,22 +216,30 @@ function is_session_id_valid($sessionId) function autoLocale($headerLocale) { // Default if browser does not send HTTP_ACCEPT_LANGUAGE - $attempts = array('en_US', 'en_US.utf8', 'en_US.UTF-8'); - if (isset($headerLocale)) { - // (It's a bit crude, but it works very well. Preferred language is always presented first.) - if (preg_match('/([a-z]{2,3})[-_]?([a-z]{2})?/i', $headerLocale, $matches)) { - $first = [strtolower($matches[1]), strtoupper($matches[1])]; - $separators = ['_', '-']; - $encodings = ['utf8', 'UTF-8']; - if (!empty($matches[2])) { - $second = [strtoupper($matches[2]), strtolower($matches[2])]; - $attempts = cartesian_product_generator([$first, $separators, $second, ['.'], $encodings]); - } else { - $attempts = cartesian_product_generator([$first, $separators, $first, ['.'], $encodings]); + $locales = array('en_US', 'en_US.utf8', 'en_US.UTF-8'); + if (! empty($headerLocale)) { + if (preg_match_all('/([a-z]{2,3})[-_]?([a-z]{2})?,?/i', $headerLocale, $matches, PREG_SET_ORDER)) { + $attempts = []; + foreach ($matches as $match) { + $first = [strtolower($match[1]), strtoupper($match[1])]; + $separators = ['_', '-']; + $encodings = ['utf8', 'UTF-8']; + if (!empty($match[2])) { + $second = [strtoupper($match[2]), strtolower($match[2])]; + $items = [$first, $separators, $second, ['.'], $encodings]; + } else { + $items = [$first, $separators, $first, ['.'], $encodings]; + } + $attempts = array_merge($attempts, iterator_to_array(cartesian_product_generator($items))); + } + + if (! empty($attempts)) { + $locales = array_merge(array_map('implode', $attempts), $locales); } } } - setlocale(LC_ALL, implode('implode', iterator_to_array($attempts))); + + setlocale(LC_ALL, $locales); } /** @@ -313,25 +321,117 @@ function normalize_spaces($string) * otherwise default format '%c' will be returned. * * @param DateTime $date to format. + * @param bool $time Displays time if true. * @param bool $intl Use international format if true. * * @return bool|string Formatted date, or false if the input is invalid. */ -function format_date($date, $intl = true) +function format_date($date, $time = true, $intl = true) { if (! $date instanceof DateTime) { return false; } if (! $intl || ! class_exists('IntlDateFormatter')) { - return strftime('%c', $date->getTimestamp()); + $format = $time ? '%c' : '%x'; + return strftime($format, $date->getTimestamp()); } $formatter = new IntlDateFormatter( setlocale(LC_TIME, 0), IntlDateFormatter::LONG, - IntlDateFormatter::LONG + $time ? IntlDateFormatter::LONG : IntlDateFormatter::NONE ); return $formatter->format($date); } + +/** + * Check if the input is an integer, no matter its real type. + * + * PHP is a bit messy regarding this: + * - is_int returns false if the input is a string + * - ctype_digit returns false if the input is an integer or negative + * + * @param mixed $input value + * + * @return bool true if the input is an integer, false otherwise + */ +function is_integer_mixed($input) +{ + if (is_array($input) || is_bool($input) || is_object($input)) { + return false; + } + $input = strval($input); + return ctype_digit($input) || (startsWith($input, '-') && ctype_digit(substr($input, 1))); +} + +/** + * Convert post_max_size/upload_max_filesize (e.g. '16M') parameters to bytes. + * + * @param string $val Size expressed in string. + * + * @return int Size expressed in bytes. + */ +function return_bytes($val) +{ + if (is_integer_mixed($val) || $val === '0' || empty($val)) { + return $val; + } + $val = trim($val); + $last = strtolower($val[strlen($val)-1]); + $val = intval(substr($val, 0, -1)); + switch($last) { + case 'g': $val *= 1024; + case 'm': $val *= 1024; + case 'k': $val *= 1024; + } + return $val; +} + +/** + * Return a human readable size from bytes. + * + * @param int $bytes value + * + * @return string Human readable size + */ +function human_bytes($bytes) +{ + if ($bytes === '') { + return t('Setting not set'); + } + if (! is_integer_mixed($bytes)) { + return $bytes; + } + $bytes = intval($bytes); + if ($bytes === 0) { + return t('Unlimited'); + } + + $units = [t('B'), t('kiB'), t('MiB'), t('GiB')]; + for ($i = 0; $i < count($units) && $bytes >= 1024; ++$i) { + $bytes /= 1024; + } + + return round($bytes) . $units[$i]; +} + +/** + * Try to determine max file size for uploads (POST). + * Returns an integer (in bytes) or formatted depending on $format. + * + * @param mixed $limitPost post_max_size PHP setting + * @param mixed $limitUpload upload_max_filesize PHP setting + * @param bool $format Format max upload size to human readable size + * + * @return int|string max upload file size + */ +function get_max_upload_size($limitPost, $limitUpload, $format = true) +{ + $size1 = return_bytes($limitPost); + $size2 = return_bytes($limitUpload); + // Return the smaller of two: + $maxsize = min($size1, $size2); + return $format ? human_bytes($maxsize) : $maxsize; +}