Skip to content

Commit 2af033c

Browse files
authored
Merge pull request #264 from jeremykendall/feature/improve-rules-public-api
Adding methods to improve Rules public API
2 parents 119ed8f + c6d6624 commit 2af033c

File tree

5 files changed

+150
-10
lines changed

5 files changed

+150
-10
lines changed

CHANGELOG.md

Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,28 @@
22

33
All Notable changes to `PHP Domain Parser` **5.x** series will be documented in this file
44

5+
## Next - TBD
6+
7+
### Added
8+
9+
- `Rules::resolveCookieDomain`
10+
- `Rules::resolveICANNDomain`
11+
- `Rules::resolvePrivateDomain`
12+
- `CouldNotResolvePublicSuffix::dueToUnresolvableDomain`
13+
14+
### Fixed
15+
16+
- Improve type hinting and return type by dropping EOL PHP versions support.
17+
- Improve development environment by dropping EOL PHP versions support.
18+
19+
### Deprecated
20+
21+
- None
22+
23+
### Removed
24+
25+
- Support for PHP7.0 and PHP7.1
26+
527
## 5.6.0 - 2019-12-29
628

729
### Added

src/Domain.php

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -156,7 +156,7 @@ private function setPublicSuffix(PublicSuffix $publicSuffix): PublicSuffix
156156
}
157157

158158
if (null === $this->domain || !$this->isResolvable()) {
159-
throw new CouldNotResolvePublicSuffix(sprintf('The domain `%s` can not contain a public suffix', $this->domain));
159+
throw CouldNotResolvePublicSuffix::dueToUnresolvableDomain($this);
160160
}
161161

162162
$publicSuffix = $this->normalize($publicSuffix);

src/Exception/CouldNotResolvePublicSuffix.php

Lines changed: 34 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -15,8 +15,42 @@
1515

1616
namespace Pdp\Exception;
1717

18+
use Pdp\Domain;
1819
use Pdp\Exception as BaseException;
20+
use function sprintf;
1921

2022
class CouldNotResolvePublicSuffix extends BaseException
2123
{
24+
/**
25+
* @var Domain|null
26+
*/
27+
private $domain;
28+
29+
public static function dueToUnresolvableDomain(?Domain $domain): self
30+
{
31+
$content = $domain;
32+
if (null !== $domain) {
33+
$content = $domain->getContent();
34+
}
35+
36+
$exception = new self(sprintf('The domain `%s` can not contain a public suffix.', $content));
37+
$exception->domain = $domain;
38+
39+
return $exception;
40+
}
41+
42+
public static function dueToUnSupportedSection(string $section): self
43+
{
44+
return new self('`'.$section.'` is an unknown Public Suffix List section.');
45+
}
46+
47+
public function hasDomain(): bool
48+
{
49+
return null !== $this->domain;
50+
}
51+
52+
public function getDomain(): ?Domain
53+
{
54+
return $this->domain;
55+
}
2256
}

src/Rules.php

Lines changed: 75 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,7 @@
1717

1818
use Pdp\Exception\CouldNotLoadRules;
1919
use Pdp\Exception\CouldNotResolvePublicSuffix;
20+
use Pdp\Exception\InvalidDomain;
2021
use function array_reverse;
2122
use function count;
2223
use function fclose;
@@ -104,7 +105,7 @@ public static function createFromPath(
104105

105106
$resource = @fopen(...$args);
106107
if (false === $resource) {
107-
throw new CouldNotLoadRules(sprintf('`%s`: failed to open stream: No such file or directory', $path));
108+
throw new CouldNotLoadRules(sprintf('`%s`: failed to open stream: No such file or directory.', $path));
108109
}
109110

110111
/** @var string $content */
@@ -193,7 +194,7 @@ public function getPublicSuffix($domain, string $section = self::ALL_DOMAINS): P
193194
}
194195

195196
if (!$domain->isResolvable()) {
196-
throw new CouldNotResolvePublicSuffix(sprintf('The domain `%s` can not contain a public suffix', $domain->getContent()));
197+
throw CouldNotResolvePublicSuffix::dueToUnresolvableDomain($domain);
197198
}
198199

199200
return PublicSuffix::createFromDomain($domain->resolve($this->findPublicSuffix($domain, $section)));
@@ -211,19 +212,84 @@ public function resolve($domain, string $section = self::ALL_DOMAINS): Domain
211212
{
212213
$section = $this->validateSection($section);
213214
try {
214-
$domain = $domain instanceof Domain
215-
? $domain
216-
: new Domain($domain, null, $this->asciiIDNAOption, $this->unicodeIDNAOption);
217-
if (!$domain->isResolvable()) {
215+
if ('' === $section) {
216+
return $this->resolveCookieDomain($domain);
217+
} elseif (self::ICANN_DOMAINS === $section) {
218+
return $this->resolveICANNDomain($domain);
219+
}
220+
221+
return $this->resolvePrivateDomain($domain);
222+
} catch (CouldNotResolvePublicSuffix $exception) {
223+
if ($exception->hasDomain()) {
224+
/** @var Domain */
225+
$domain = $exception->getDomain();
226+
218227
return $domain;
219228
}
220229

221-
return $domain->resolve($this->findPublicSuffix($domain, $section));
222-
} catch (Exception $e) {
230+
return new Domain($domain, null, $this->asciiIDNAOption, $this->unicodeIDNAOption);
231+
} catch (Exception $exception) {
223232
return new Domain(null, null, $this->asciiIDNAOption, $this->unicodeIDNAOption);
224233
}
225234
}
226235

236+
/**
237+
* Returns PSL info for a given domain against the PSL rules for cookie domain detection.
238+
*
239+
* @param mixed $domain the domain value
240+
*/
241+
public function resolveCookieDomain($domain): Domain
242+
{
243+
$domain = $this->validateDomain($domain);
244+
245+
return $domain->resolve($this->findPublicSuffix($domain, ''));
246+
}
247+
248+
/**
249+
* Returns PSL info for a given domain against the PSL rules for ICANN domain detection.
250+
*
251+
* @param mixed $domain
252+
*/
253+
public function resolveICANNDomain($domain): Domain
254+
{
255+
$domain = $this->validateDomain($domain);
256+
257+
return $domain->resolve($this->findPublicSuffix($domain, self::ICANN_DOMAINS));
258+
}
259+
260+
/**
261+
* Returns PSL info for a given domain against the PSL rules for private domain detection.
262+
*
263+
* @param mixed $domain
264+
*/
265+
public function resolvePrivateDomain($domain): Domain
266+
{
267+
$domain = $this->validateDomain($domain);
268+
269+
return $domain->resolve($this->findPublicSuffix($domain, self::PRIVATE_DOMAINS));
270+
}
271+
272+
/**
273+
* Assert the domain is valid and is resolvable.
274+
*
275+
* @param mixed $domain
276+
*
277+
* @throws InvalidDomain if the domain is invalid
278+
* @throws CouldNotResolvePublicSuffix if the domain is not resolvable
279+
*/
280+
private function validateDomain($domain): Domain
281+
{
282+
if (!($domain instanceof Domain)) {
283+
$domain = new Domain($domain, null, $this->asciiIDNAOption, $this->unicodeIDNAOption);
284+
}
285+
286+
if (!$domain->isResolvable()) {
287+
throw CouldNotResolvePublicSuffix::dueToUnresolvableDomain($domain);
288+
}
289+
290+
return $domain;
291+
}
292+
227293
/**
228294
* Assert the section status.
229295
*
@@ -243,7 +309,7 @@ private function validateSection(string $section): string
243309
return $section;
244310
}
245311

246-
throw new CouldNotResolvePublicSuffix(sprintf('%s is an unknown Public Suffix List section', $section));
312+
throw CouldNotResolvePublicSuffix::dueToUnSupportedSection($section);
247313
}
248314

249315
/**

tests/RulesTest.php

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -114,6 +114,10 @@ public function testwithIDNAOptions(): void
114114

115115
/**
116116
* @covers ::resolve
117+
* @covers ::resolveCookieDomain
118+
* @covers ::resolveICANNDomain
119+
* @covers ::resolvePrivateDomain
120+
* @covers ::validateDomain
117121
* @covers ::validateSection
118122
* @covers \Pdp\Domain::isResolvable
119123
* @covers \Pdp\PublicSuffix::setSection
@@ -191,6 +195,8 @@ public function testIsSuffixValidTrue(): void
191195

192196
/**
193197
* @covers ::resolve
198+
* @covers ::resolveCookieDomain
199+
* @covers ::validateDomain
194200
* @covers ::validateSection
195201
* @covers \Pdp\Domain::isResolvable
196202
* @covers ::findPublicSuffix
@@ -215,6 +221,8 @@ public function testIsSuffixValidFalseWithPunycoded(): void
215221

216222
/**
217223
* @covers ::resolve
224+
* @covers ::resolveICANNDomain
225+
* @covers ::validateDomain
218226
* @covers ::validateSection
219227
* @covers \Pdp\Domain::isResolvable
220228
* @covers ::findPublicSuffix
@@ -239,6 +247,8 @@ public function testSubDomainIsNull(): void
239247

240248
/**
241249
* @covers ::resolve
250+
* @covers ::resolveCookieDomain
251+
* @covers ::validateDomain
242252
* @covers ::validateSection
243253
* @covers \Pdp\IDNAConverterTrait::parse
244254
*/
@@ -281,6 +291,8 @@ public function testWithAbsoluteHostInvalid(): void
281291

282292
/**
283293
* @covers ::resolve
294+
* @covers ::resolvePrivateDomain
295+
* @covers ::validateDomain
284296
* @covers ::validateSection
285297
* @covers ::findPublicSuffix
286298
* @covers ::findPublicSuffixFromSection
@@ -299,6 +311,8 @@ public function testWithPrivateDomainInvalid(): void
299311

300312
/**
301313
* @covers ::resolve
314+
* @covers ::resolvePrivateDomain
315+
* @covers ::validateDomain
302316
* @covers ::validateSection
303317
* @covers ::findPublicSuffix
304318
* @covers ::findPublicSuffixFromSection
@@ -367,6 +381,8 @@ public function testWithDomainInterfaceObject(): void
367381

368382
/**
369383
* @covers ::resolve
384+
* @covers ::resolveICANNDomain
385+
* @covers ::validateDomain
370386
* @covers \Pdp\Domain::setRegistrableDomain
371387
* @covers \Pdp\Domain::getRegistrableDomain
372388
* @dataProvider parseDataProvider
@@ -383,6 +399,8 @@ public function testGetRegistrableDomain($publicSuffix, $registrableDomain, $dom
383399

384400
/**
385401
* @covers ::resolve
402+
* @covers ::resolveICANNDomain
403+
* @covers ::validateDomain
386404
* @covers \Pdp\IDNAConverterTrait::parse
387405
* @covers \Pdp\Domain::setPublicSuffix
388406
* @covers \Pdp\Domain::getPublicSuffix

0 commit comments

Comments
 (0)