Augmentation vers version 3.3.0
This commit is contained in:
22
vendor/s9e/text-formatter/src/Utils/Http.php
vendored
22
vendor/s9e/text-formatter/src/Utils/Http.php
vendored
@@ -1,24 +1,38 @@
|
||||
<?php
|
||||
|
||||
/*
|
||||
/**
|
||||
* @package s9e\TextFormatter
|
||||
* @copyright Copyright (c) 2010-2019 The s9e Authors
|
||||
* @license http://www.opensource.org/licenses/mit-license.php The MIT License
|
||||
*/
|
||||
namespace s9e\TextFormatter\Utils;
|
||||
|
||||
use s9e\TextFormatter\Utils\Http\Clients\Cached;
|
||||
use s9e\TextFormatter\Utils\Http\Clients\Curl;
|
||||
use s9e\TextFormatter\Utils\Http\Clients\Native;
|
||||
|
||||
abstract class Http
|
||||
{
|
||||
/**
|
||||
* Instantiate and return an HTTP client
|
||||
*
|
||||
* @return Http\Client
|
||||
*/
|
||||
public static function getClient()
|
||||
{
|
||||
return (\extension_loaded('curl')) ? new Curl : new Native;
|
||||
return (extension_loaded('curl')) ? new Curl : new Native;
|
||||
}
|
||||
public static function getCachingClient($cacheDir = \null)
|
||||
/**
|
||||
* Instantiate and return a caching HTTP client
|
||||
*
|
||||
* @param string $cacheDir
|
||||
* @return Cached
|
||||
*/
|
||||
public static function getCachingClient($cacheDir = null)
|
||||
{
|
||||
$client = new Cached(self::getClient());
|
||||
$client->cacheDir = (isset($cacheDir)) ? $cacheDir : \sys_get_temp_dir();
|
||||
$client->cacheDir = (isset($cacheDir)) ? $cacheDir : sys_get_temp_dir();
|
||||
|
||||
return $client;
|
||||
}
|
||||
}
|
||||
@@ -1,15 +1,40 @@
|
||||
<?php
|
||||
|
||||
/*
|
||||
/**
|
||||
* @package s9e\TextFormatter
|
||||
* @copyright Copyright (c) 2010-2019 The s9e Authors
|
||||
* @license http://www.opensource.org/licenses/mit-license.php The MIT License
|
||||
*/
|
||||
namespace s9e\TextFormatter\Utils\Http;
|
||||
|
||||
abstract class Client
|
||||
{
|
||||
public $sslVerifyPeer = \false;
|
||||
/**
|
||||
* @var bool Whether to verify the peer's SSL certificate
|
||||
*/
|
||||
public $sslVerifyPeer = false;
|
||||
|
||||
/**
|
||||
* @var integer Request timeout
|
||||
*/
|
||||
public $timeout = 10;
|
||||
abstract public function get($url, $headers = []);
|
||||
abstract public function post($url, $headers = [], $body = '');
|
||||
|
||||
/**
|
||||
* Execute a GET request and return the response's body
|
||||
*
|
||||
* @param string $url Request URL
|
||||
* @param array $options Request options
|
||||
* @return string|bool Response content or FALSE
|
||||
*/
|
||||
abstract public function get($url, array $options = []);
|
||||
|
||||
/**
|
||||
* Execute a POST request and return the response's body
|
||||
*
|
||||
* @param string $url Request URL
|
||||
* @param array $options Request options
|
||||
* @param string $body Request body
|
||||
* @return string|bool Response content or FALSE
|
||||
*/
|
||||
abstract public function post($url, array $options = [], $body = '');
|
||||
}
|
||||
@@ -1,54 +1,108 @@
|
||||
<?php
|
||||
|
||||
/*
|
||||
/**
|
||||
* @package s9e\TextFormatter
|
||||
* @copyright Copyright (c) 2010-2019 The s9e Authors
|
||||
* @license http://www.opensource.org/licenses/mit-license.php The MIT License
|
||||
*/
|
||||
namespace s9e\TextFormatter\Utils\Http\Clients;
|
||||
|
||||
use s9e\TextFormatter\Utils\Http\Client;
|
||||
|
||||
class Cached extends Client
|
||||
{
|
||||
/**
|
||||
* @var Client
|
||||
*/
|
||||
public $client;
|
||||
|
||||
/**
|
||||
* @var string
|
||||
*/
|
||||
public $cacheDir;
|
||||
|
||||
/**
|
||||
* @param Client $client
|
||||
*/
|
||||
public function __construct(Client $client)
|
||||
{
|
||||
$this->client = $client;
|
||||
$this->timeout = $client->timeout;
|
||||
$this->sslVerifyPeer = $client->sslVerifyPeer;
|
||||
}
|
||||
public function get($url, $headers = [])
|
||||
|
||||
/**
|
||||
* {@inheritdoc}
|
||||
*/
|
||||
public function get($url, array $options = [])
|
||||
{
|
||||
$filepath = $this->getCachedFilepath([$url, $headers]);
|
||||
if (isset($filepath) && \file_exists(\preg_replace('(^compress\\.zlib://)', '', $filepath)))
|
||||
return \file_get_contents($filepath);
|
||||
$content = $this->getClient()->get($url, $headers);
|
||||
if (isset($filepath) && $content !== \false)
|
||||
\file_put_contents($filepath, $content);
|
||||
$filepath = $this->getCachedFilepath([$url, $options]);
|
||||
if (isset($filepath) && file_exists(preg_replace('(^compress\\.zlib://)', '', $filepath)))
|
||||
{
|
||||
return file_get_contents($filepath);
|
||||
}
|
||||
|
||||
$content = $this->getClient()->get($url, $options);
|
||||
if (isset($filepath) && $content !== false)
|
||||
{
|
||||
file_put_contents($filepath, $content);
|
||||
}
|
||||
|
||||
return $content;
|
||||
}
|
||||
public function post($url, $headers = [], $body = '')
|
||||
|
||||
/**
|
||||
* {@inheritdoc}
|
||||
*/
|
||||
public function post($url, array $options = [], $body = '')
|
||||
{
|
||||
return $this->getClient()->post($url, $headers, $body);
|
||||
return $this->getClient()->post($url, $options, $body);
|
||||
}
|
||||
|
||||
/**
|
||||
* Generate and return a filepath that matches given vars
|
||||
*
|
||||
* @param array $vars
|
||||
* @return string
|
||||
*/
|
||||
protected function getCachedFilepath(array $vars)
|
||||
{
|
||||
if (!isset($this->cacheDir))
|
||||
return \null;
|
||||
{
|
||||
return null;
|
||||
}
|
||||
|
||||
$filepath = $this->cacheDir . '/http.' . $this->getCacheKey($vars);
|
||||
if (\extension_loaded('zlib'))
|
||||
if (extension_loaded('zlib'))
|
||||
{
|
||||
$filepath = 'compress.zlib://' . $filepath . '.gz';
|
||||
}
|
||||
|
||||
return $filepath;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Generate a key for a given set of values
|
||||
*
|
||||
* @param string[] $vars
|
||||
* @return string
|
||||
*/
|
||||
protected function getCacheKey(array $vars)
|
||||
{
|
||||
return \strtr(\base64_encode(\sha1(\serialize($vars), \true)), '/', '_');
|
||||
return strtr(base64_encode(sha1(serialize($vars), true)), '/', '_');
|
||||
}
|
||||
|
||||
/**
|
||||
* Return cached client configured with this client's options
|
||||
*
|
||||
* @return Client
|
||||
*/
|
||||
protected function getClient()
|
||||
{
|
||||
$this->client->timeout = $this->timeout;
|
||||
$this->client->sslVerifyPeer = $this->sslVerifyPeer;
|
||||
|
||||
return $this->client;
|
||||
}
|
||||
}
|
||||
@@ -1,48 +1,86 @@
|
||||
<?php
|
||||
|
||||
/*
|
||||
/**
|
||||
* @package s9e\TextFormatter
|
||||
* @copyright Copyright (c) 2010-2019 The s9e Authors
|
||||
* @license http://www.opensource.org/licenses/mit-license.php The MIT License
|
||||
*/
|
||||
namespace s9e\TextFormatter\Utils\Http\Clients;
|
||||
|
||||
use s9e\TextFormatter\Utils\Http\Client;
|
||||
|
||||
class Curl extends Client
|
||||
{
|
||||
/**
|
||||
* @var resource cURL handle, shared across instances
|
||||
*/
|
||||
protected static $handle;
|
||||
public function get($url, $headers = [])
|
||||
|
||||
/**
|
||||
* {@inheritdoc}
|
||||
*/
|
||||
public function get($url, array $options = [])
|
||||
{
|
||||
$options += ['headers' => []];
|
||||
|
||||
$handle = $this->getHandle();
|
||||
\curl_setopt($handle, \CURLOPT_HTTPGET, \true);
|
||||
\curl_setopt($handle, \CURLOPT_HTTPHEADER, $headers);
|
||||
\curl_setopt($handle, \CURLOPT_URL, $url);
|
||||
return \curl_exec($handle);
|
||||
curl_setopt($handle, CURLOPT_HEADER, !empty($options['returnHeaders']));
|
||||
curl_setopt($handle, CURLOPT_HTTPGET, true);
|
||||
curl_setopt($handle, CURLOPT_HTTPHEADER, $options['headers']);
|
||||
curl_setopt($handle, CURLOPT_URL, $url);
|
||||
|
||||
return curl_exec($handle);
|
||||
}
|
||||
public function post($url, $headers = [], $body = '')
|
||||
|
||||
/**
|
||||
* {@inheritdoc}
|
||||
*/
|
||||
public function post($url, array $options = [], $body = '')
|
||||
{
|
||||
$headers[] = 'Content-Length: ' . \strlen($body);
|
||||
$options += ['headers' => []];
|
||||
$options['headers'][] = 'Content-Length: ' . strlen($body);
|
||||
|
||||
$handle = $this->getHandle();
|
||||
\curl_setopt($handle, \CURLOPT_HTTPHEADER, $headers);
|
||||
\curl_setopt($handle, \CURLOPT_POST, \true);
|
||||
\curl_setopt($handle, \CURLOPT_POSTFIELDS, $body);
|
||||
\curl_setopt($handle, \CURLOPT_URL, $url);
|
||||
return \curl_exec($handle);
|
||||
curl_setopt($handle, CURLOPT_HEADER, !empty($options['returnHeaders']));
|
||||
curl_setopt($handle, CURLOPT_HTTPHEADER, $options['headers']);
|
||||
curl_setopt($handle, CURLOPT_POST, true);
|
||||
curl_setopt($handle, CURLOPT_POSTFIELDS, $body);
|
||||
curl_setopt($handle, CURLOPT_URL, $url);
|
||||
|
||||
return curl_exec($handle);
|
||||
}
|
||||
|
||||
/**
|
||||
* Return a globally cached cURL handle, configured for current instance
|
||||
*
|
||||
* @return resource
|
||||
*/
|
||||
protected function getHandle()
|
||||
{
|
||||
if (!isset(self::$handle))
|
||||
{
|
||||
self::$handle = $this->getNewHandle();
|
||||
\curl_setopt(self::$handle, \CURLOPT_SSL_VERIFYPEER, $this->sslVerifyPeer);
|
||||
\curl_setopt(self::$handle, \CURLOPT_TIMEOUT, $this->timeout);
|
||||
}
|
||||
|
||||
curl_setopt(self::$handle, CURLOPT_SSL_VERIFYPEER, $this->sslVerifyPeer);
|
||||
curl_setopt(self::$handle, CURLOPT_TIMEOUT, $this->timeout);
|
||||
|
||||
return self::$handle;
|
||||
}
|
||||
|
||||
/**
|
||||
* Create and return a new cURL handle
|
||||
*
|
||||
* @return resource
|
||||
*/
|
||||
protected function getNewHandle()
|
||||
{
|
||||
$handle = \curl_init();
|
||||
\curl_setopt($handle, \CURLOPT_ENCODING, '');
|
||||
\curl_setopt($handle, \CURLOPT_FAILONERROR, \true);
|
||||
\curl_setopt($handle, \CURLOPT_FOLLOWLOCATION, \true);
|
||||
\curl_setopt($handle, \CURLOPT_RETURNTRANSFER, \true);
|
||||
$handle = curl_init();
|
||||
curl_setopt($handle, CURLOPT_ENCODING, '');
|
||||
curl_setopt($handle, CURLOPT_FAILONERROR, true);
|
||||
curl_setopt($handle, CURLOPT_FOLLOWLOCATION, true);
|
||||
curl_setopt($handle, CURLOPT_RETURNTRANSFER, true);
|
||||
|
||||
return $handle;
|
||||
}
|
||||
}
|
||||
@@ -1,56 +1,125 @@
|
||||
<?php
|
||||
|
||||
/*
|
||||
/**
|
||||
* @package s9e\TextFormatter
|
||||
* @copyright Copyright (c) 2010-2019 The s9e Authors
|
||||
* @license http://www.opensource.org/licenses/mit-license.php The MIT License
|
||||
*/
|
||||
namespace s9e\TextFormatter\Utils\Http\Clients;
|
||||
|
||||
use s9e\TextFormatter\Utils\Http\Client;
|
||||
|
||||
class Native extends Client
|
||||
{
|
||||
/**
|
||||
* @var bool Whether to use gzip encoding
|
||||
*/
|
||||
public $gzipEnabled;
|
||||
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public function __construct()
|
||||
{
|
||||
$this->gzipEnabled = \extension_loaded('zlib');
|
||||
$this->gzipEnabled = extension_loaded('zlib');
|
||||
}
|
||||
public function get($url, $headers = [])
|
||||
|
||||
/**
|
||||
* {@inheritdoc}
|
||||
*/
|
||||
public function get($url, array $options = [])
|
||||
{
|
||||
return $this->request('GET', $url, $headers);
|
||||
return $this->request('GET', $url, $options);
|
||||
}
|
||||
public function post($url, $headers = [], $body = '')
|
||||
|
||||
/**
|
||||
* {@inheritdoc}
|
||||
*/
|
||||
public function post($url, array $options = [], $body = '')
|
||||
{
|
||||
return $this->request('POST', $url, $headers, $body);
|
||||
return $this->request('POST', $url, $options, $body);
|
||||
}
|
||||
protected function createContext($method, array $headers, $body)
|
||||
|
||||
/**
|
||||
* Create a stream context for given request
|
||||
*
|
||||
* @param string $method Request method
|
||||
* @param array $options Request options
|
||||
* @param string $body Request body
|
||||
* @return resource
|
||||
*/
|
||||
protected function createContext($method, array $options, $body)
|
||||
{
|
||||
$contextOptions = [
|
||||
'ssl' => ['verify_peer' => $this->sslVerifyPeer],
|
||||
'http' => [
|
||||
'method' => $method,
|
||||
'timeout' => $this->timeout,
|
||||
'header' => $this->generateHeaders($headers, $body),
|
||||
'header' => $this->generateHeaders($options, $body),
|
||||
'content' => $body
|
||||
]
|
||||
];
|
||||
return \stream_context_create($contextOptions);
|
||||
|
||||
return stream_context_create($contextOptions);
|
||||
}
|
||||
|
||||
/**
|
||||
* Decompress given page if applicable
|
||||
*
|
||||
* @param string $content Response body, potentially compressed
|
||||
* @return string Response body, uncompressed
|
||||
*/
|
||||
protected function decompress($content)
|
||||
{
|
||||
if ($this->gzipEnabled && \substr($content, 0, 2) === "\x1f\x8b")
|
||||
return \gzdecode($content);
|
||||
if ($this->gzipEnabled && substr($content, 0, 2) === "\x1f\x8b")
|
||||
{
|
||||
return gzdecode($content);
|
||||
}
|
||||
|
||||
return $content;
|
||||
}
|
||||
protected function generateHeaders(array $headers, $body)
|
||||
|
||||
/**
|
||||
* Generate a list of headers for given request
|
||||
*
|
||||
* @param array $options Request options
|
||||
* @param string $body Request body
|
||||
* @return string[]
|
||||
*/
|
||||
protected function generateHeaders(array $options, $body)
|
||||
{
|
||||
$options += ['headers' => []];
|
||||
if ($this->gzipEnabled)
|
||||
$headers[] = 'Accept-Encoding: gzip';
|
||||
$headers[] = 'Content-Length: ' . \strlen($body);
|
||||
return $headers;
|
||||
{
|
||||
$options['headers'][] = 'Accept-Encoding: gzip';
|
||||
}
|
||||
$options['headers'][] = 'Content-Length: ' . strlen($body);
|
||||
|
||||
return $options['headers'];
|
||||
}
|
||||
protected function request($method, $url, $headers, $body = '')
|
||||
|
||||
/**
|
||||
* Execute an HTTP request
|
||||
*
|
||||
* @param string $method Request method
|
||||
* @param string $url Request URL
|
||||
* @param array $options Request options
|
||||
* @return string|bool Response body or FALSE
|
||||
*/
|
||||
protected function request($method, $url, array $options, $body = '')
|
||||
{
|
||||
$response = @\file_get_contents($url, \false, $this->createContext($method, $headers, $body));
|
||||
return (\is_string($response)) ? $this->decompress($response) : $response;
|
||||
$response = @file_get_contents($url, false, $this->createContext($method, $options, $body));
|
||||
if ($response === false)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
$response = $this->decompress($response);
|
||||
if (!empty($options['returnHeaders']))
|
||||
{
|
||||
$response = implode("\r\n", $http_response_header) . "\r\n\r\n" . $response;
|
||||
}
|
||||
|
||||
return $response;
|
||||
}
|
||||
}
|
||||
94
vendor/s9e/text-formatter/src/Utils/XPath.php
vendored
94
vendor/s9e/text-formatter/src/Utils/XPath.php
vendored
@@ -1,43 +1,109 @@
|
||||
<?php
|
||||
|
||||
/*
|
||||
/**
|
||||
* @package s9e\TextFormatter
|
||||
* @copyright Copyright (c) 2010-2019 The s9e Authors
|
||||
* @license http://www.opensource.org/licenses/mit-license.php The MIT License
|
||||
*/
|
||||
namespace s9e\TextFormatter\Utils;
|
||||
|
||||
use InvalidArgumentException;
|
||||
|
||||
abstract class XPath
|
||||
{
|
||||
/**
|
||||
* Export a literal as an XPath expression
|
||||
*
|
||||
* @param mixed $value Literal, e.g. "foo"
|
||||
* @return string XPath expression, e.g. "'foo'"
|
||||
*/
|
||||
public static function export($value)
|
||||
{
|
||||
if (!\is_scalar($value))
|
||||
$callback = get_called_class() . '::export' . ucfirst(gettype($value));
|
||||
if (!is_callable($callback))
|
||||
{
|
||||
throw new InvalidArgumentException(__METHOD__ . '() cannot export non-scalar values');
|
||||
if (\is_int($value))
|
||||
return (string) $value;
|
||||
if (\is_float($value))
|
||||
return \preg_replace('(\\.?0+$)', '', \sprintf('%F', $value));
|
||||
return self::exportString((string) $value);
|
||||
}
|
||||
|
||||
return $callback($value);
|
||||
}
|
||||
protected static function exportString($str)
|
||||
|
||||
/**
|
||||
* Export given boolean value
|
||||
*
|
||||
* @param bool $value
|
||||
* @return string
|
||||
*/
|
||||
protected static function exportBoolean(bool $value): string
|
||||
{
|
||||
if (\strpos($str, "'") === \false)
|
||||
return ($value) ? 'true()' : 'false()';
|
||||
}
|
||||
|
||||
/**
|
||||
* Export given float value
|
||||
*
|
||||
* @param float $value
|
||||
* @return string
|
||||
*/
|
||||
protected static function exportDouble(float $value): string
|
||||
{
|
||||
if (!is_finite($value))
|
||||
{
|
||||
throw new InvalidArgumentException(__METHOD__ . '() cannot export irrational numbers');
|
||||
}
|
||||
|
||||
// Avoid locale issues by using sprintf()
|
||||
return preg_replace('(\\.?0+$)', '', sprintf('%F', $value));
|
||||
}
|
||||
|
||||
/**
|
||||
* Export given integer value
|
||||
*
|
||||
* @param integer $value
|
||||
* @return string
|
||||
*/
|
||||
protected static function exportInteger(int $value): string
|
||||
{
|
||||
return (string) $value;
|
||||
}
|
||||
|
||||
/**
|
||||
* Export a string as an XPath expression
|
||||
*
|
||||
* @param string $str Literal, e.g. "foo"
|
||||
* @return string XPath expression, e.g. "'foo'"
|
||||
*/
|
||||
protected static function exportString(string $str): string
|
||||
{
|
||||
// foo becomes 'foo'
|
||||
if (strpos($str, "'") === false)
|
||||
{
|
||||
return "'" . $str . "'";
|
||||
if (\strpos($str, '"') === \false)
|
||||
}
|
||||
|
||||
// d'oh becomes "d'oh"
|
||||
if (strpos($str, '"') === false)
|
||||
{
|
||||
return '"' . $str . '"';
|
||||
}
|
||||
|
||||
// This string contains both ' and ". XPath 1.0 doesn't have a mechanism to escape quotes,
|
||||
// so we have to get creative and use concat() to join chunks in single quotes and chunks
|
||||
// in double quotes
|
||||
$toks = [];
|
||||
$c = '"';
|
||||
$pos = 0;
|
||||
while ($pos < \strlen($str))
|
||||
while ($pos < strlen($str))
|
||||
{
|
||||
$spn = \strcspn($str, $c, $pos);
|
||||
$spn = strcspn($str, $c, $pos);
|
||||
if ($spn)
|
||||
{
|
||||
$toks[] = $c . \substr($str, $pos, $spn) . $c;
|
||||
$toks[] = $c . substr($str, $pos, $spn) . $c;
|
||||
$pos += $spn;
|
||||
}
|
||||
$c = ($c === '"') ? "'" : '"';
|
||||
}
|
||||
return 'concat(' . \implode(',', $toks) . ')';
|
||||
|
||||
return 'concat(' . implode(',', $toks) . ')';
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user