Added support for IDN

This commit is contained in:
Alejandro Celaya
2019-11-16 10:06:55 +01:00
parent ec33b95f97
commit 264b8c2a9e
5 changed files with 93 additions and 22 deletions

View File

@@ -0,0 +1,53 @@
<?php
declare(strict_types=1);
namespace Shlinkio\Shlink\Core\Util;
use Fig\Http\Message\RequestMethodInterface;
use GuzzleHttp\ClientInterface;
use GuzzleHttp\Exception\GuzzleException;
use GuzzleHttp\RequestOptions;
use Shlinkio\Shlink\Core\Exception\InvalidUrlException;
use Zend\Diactoros\Uri;
use function idn_to_ascii;
use const IDNA_DEFAULT;
use const INTL_IDNA_VARIANT_UTS46;
class UrlValidator implements UrlValidatorInterface
{
private const MAX_REDIRECTS = 15;
/** @var ClientInterface */
private $httpClient;
public function __construct(ClientInterface $httpClient)
{
$this->httpClient = $httpClient;
}
/**
* @throws InvalidUrlException
*/
public function validateUrl(string $url): void
{
// FIXME Guzzle is about to add support for this https://github.com/guzzle/guzzle/pull/2286
// Remove custom implementation when Guzzle's PR is merged
$uri = new Uri($url);
$originalHost = $uri->getHost();
$normalizedHost = idn_to_ascii($originalHost, IDNA_DEFAULT, INTL_IDNA_VARIANT_UTS46);
if ($originalHost !== $normalizedHost) {
$uri = $uri->withHost($normalizedHost);
}
try {
$this->httpClient->request(RequestMethodInterface::METHOD_GET, (string) $uri, [
RequestOptions::ALLOW_REDIRECTS => ['max' => self::MAX_REDIRECTS],
]);
} catch (GuzzleException $e) {
throw InvalidUrlException::fromUrl($url, $e);
}
}
}

View File

@@ -0,0 +1,15 @@
<?php
declare(strict_types=1);
namespace Shlinkio\Shlink\Core\Util;
use Shlinkio\Shlink\Core\Exception\InvalidUrlException;
interface UrlValidatorInterface
{
/**
* @throws InvalidUrlException
*/
public function validateUrl(string $url): void;
}