Skip to content

Commit

Permalink
Moved all remaining 'util' functions to functions.php. Fixes #49.
Browse files Browse the repository at this point in the history
  • Loading branch information
evert committed May 20, 2015
1 parent 6294b0d commit 66e7f72
Show file tree
Hide file tree
Showing 4 changed files with 265 additions and 190 deletions.
9 changes: 9 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,6 +1,15 @@
ChangeLog
=========

4.0.0 (2015-05-20)
------------------

* Deprecated: All static functions from `Sabre\HTTP\URLUtil` and
`Sabre\HTTP\Util` moved to a separate `functions.php`, which is also
autoloaded. The old functions are still there, but will be removed in a
future version. (#49)


4.0.0-alpha3 (2015-05-19)
-------------------------

Expand Down
40 changes: 11 additions & 29 deletions lib/URLUtil.php
Original file line number Diff line number Diff line change
Expand Up @@ -7,15 +7,10 @@
/**
* URL utility class
*
* This class provides methods to deal with encoding and decoding url (percent encoded) strings.
*
* It was not possible to use PHP's built-in methods for this, because some clients don't like
* encoding of certain characters.
*
* Specifically, it was found that GVFS (gnome's webdav client) does not like encoding of ( and
* ). Since these are reserved, but don't have a reserved meaning in url, these characters are
* kept as-is.
* Note: this class is deprecated. All its functionality moved to functions.php
* or sabre\uri.
*
* @deprectated
* @copyright Copyright (C) 2009-2015 fruux GmbH (https://fruux.com/).
* @author Evert Pot (http://evertpot.com/)
* @license http://sabre.io/license/ Modified BSD License
Expand All @@ -27,16 +22,13 @@ class URLUtil {
*
* slashes (/) are treated as path-separators.
*
* @deprecated use \Sabre\HTTP\encodePath()
* @param string $path
* @return string
*/
static function encodePath($path) {

return preg_replace_callback('/([^A-Za-z0-9_\-\.~\(\)\/:@])/', function($match) {

return '%' . sprintf('%02x', ord($match[0]));

}, $path);
return encodePath($path);

}

Expand All @@ -45,49 +37,39 @@ static function encodePath($path) {
*
* Slashes are considered part of the name, and are encoded as %2f
*
* @deprecated use \Sabre\HTTP\encodePathSegment()
* @param string $pathSegment
* @return string
*/
static function encodePathSegment($pathSegment) {

return preg_replace_callback('/([^A-Za-z0-9_\-\.~\(\):@])/', function($match) {

return '%' . sprintf('%02x', ord($match[0]));
return encodePathSegment($pathSegment);

}, $pathSegment);
}

/**
* Decodes a url-encoded path
*
* @deprecated use \Sabre\HTTP\decodePath
* @param string $path
* @return string
*/
static function decodePath($path) {

return self::decodePathSegment($path);
return decodePath($path);

}

/**
* Decodes a url-encoded path segment
*
* @deprecated use \Sabre\HTTP\decodePathSegment()
* @param string $path
* @return string
*/
static function decodePathSegment($path) {

$path = rawurldecode($path);
$encoding = mb_detect_encoding($path, ['UTF-8', 'ISO-8859-1']);

switch ($encoding) {

case 'ISO-8859-1' :
$path = utf8_encode($path);

}

return $path;
return decodePathSegment($path);

}

Expand Down
167 changes: 6 additions & 161 deletions lib/Util.php
Original file line number Diff line number Diff line change
Expand Up @@ -8,191 +8,36 @@
* @copyright Copyright (C) 2009-2015 fruux GmbH (https://fruux.com/).
* @author Evert Pot (http://evertpot.com/)
* @author Paul Voegler
* @deprecated All these functions moved to functions.php
* @license http://sabre.io/license/ Modified BSD License
*/
class Util {

/**
* This method can be used to aid with content negotiation.
*
* It takes 2 arguments, the $acceptHeaderValue, which usually comes from
* an Accept header, and $availableOptions, which contains an array of
* items that the server can support.
*
* The result of this function will be the 'best possible option'. If no
* best possible option could be found, null is returned.
*
* When it's null you can according to the spec either return a default, or
* you can choose to emit 406 Not Acceptable.
*
* The method also accepts sending 'null' for the $acceptHeaderValue,
* implying that no accept header was sent.
* Content negotiation
*
* @deprecated Use \Sabre\HTTP\negotiateContentType
* @param string|null $acceptHeaderValue
* @param array $availableOptions
* @return string|null
*/
static function negotiateContentType($acceptHeaderValue, array $availableOptions) {

if (!$acceptHeaderValue) {
// Grabbing the first in the list.
return reset($availableOptions);
}

$proposals = array_map(
['self', 'parseMimeType'],
explode(',', $acceptHeaderValue)
);

// Ensuring array keys are reset.
$availableOptions = array_values($availableOptions);

$options = array_map(
['self', 'parseMimeType'],
$availableOptions
);

$lastQuality = 0;
$lastSpecificity = 0;
$lastOptionIndex = 0;
$lastChoice = null;

foreach ($proposals as $proposal) {

// Ignoring broken values.
if (is_null($proposal)) continue;

// If the quality is lower we don't have to bother comparing.
if ($proposal['quality'] < $lastQuality) {
continue;
}

foreach ($options as $optionIndex => $option) {

if ($proposal['type'] !== '*' && $proposal['type'] !== $option['type']) {
// no match on type.
continue;
}
if ($proposal['subType'] !== '*' && $proposal['subType'] !== $option['subType']) {
// no match on subtype.
continue;
}

// Any parameters appearing on the options must appear on
// proposals.
foreach ($option['parameters'] as $paramName => $paramValue) {
if (!array_key_exists($paramName, $proposal['parameters'])) {
continue 2;
}
if ($paramValue !== $proposal['parameters'][$paramName]) {
continue 2;
}
}

// If we got here, we have a match on parameters, type and
// subtype. We need to calculate a score for how specific the
// match was.
$specificity =
($proposal['type'] !== '*' ? 20 : 0) +
($proposal['subType'] !== '*' ? 10 : 0) +
count($option['parameters']);


// Does this entry win?
if (
($proposal['quality'] > $lastQuality) ||
($proposal['quality'] === $lastQuality && $specificity > $lastSpecificity) ||
($proposal['quality'] === $lastQuality && $specificity === $lastSpecificity && $optionIndex < $lastOptionIndex)
) {

$lastQuality = $proposal['quality'];
$lastSpecificity = $specificity;
$lastOptionIndex = $optionIndex;
$lastChoice = $availableOptions[$optionIndex];

}

}

}

return $lastChoice;

}

/**
* Parses a mime-type and splits it into:
*
* 1. type
* 2. subtype
* 3. quality
* 4. parameters
*
* @param string $str
* @return array
*/
private static function parseMimeType($str) {

$parameters = [];
// If no q= parameter appears, then quality = 1.
$quality = 1;

$parts = explode(';', $str);

// The first part is the mime-type.
$mimeType = array_shift($parts);

$mimeType = explode('/', trim($mimeType));
if (count($mimeType) !== 2) {
// Illegal value
return null;
}
list($type, $subType) = $mimeType;

foreach ($parts as $part) {

$part = trim($part);
if (strpos($part, '=')) {
list($partName, $partValue) =
explode('=', $part, 2);
} else {
$partName = $part;
$partValue = null;
}

// The quality parameter, if it appears, also marks the end of
// the parameter list. Anything after the q= counts as an
// 'accept extension' and could introduce new semantics in
// content-negotation.
if ($partName !== 'q') {
$parameters[$partName] = $part;
} else {
$quality = (float)$partValue;
break; // Stop parsing parts
}

}

return [
'type' => $type,
'subType' => $subType,
'quality' => $quality,
'parameters' => $parameters,
];
return negotiateContentType($acceptHeaderValue, $availableOptions);

}

/**
* Deprecated! Use negotiateContentType.
*
* @deprecated
* @deprecated Use \Sabre\HTTP\NegotiateContentType
* @param string|null $acceptHeader
* @param array $availableOptions
* @return string|null
*/
static function negotiate($acceptHeaderValue, array $availableOptions) {

return self::negotiateContentType($acceptHeaderValue, $availableOptions);
return negotiateContentType($acceptHeaderValue, $availableOptions);

}

Expand Down
Loading

0 comments on commit 66e7f72

Please sign in to comment.