Skip to content

Commit f707d55

Browse files
committed
Added support for twitch
1 parent 24e8e01 commit f707d55

13 files changed

+433
-10
lines changed

CHANGELOG.md

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,7 @@ and this project adheres to [Semantic Versioning](http://semver.org/).
88
## [4.1.2] - Unreleased
99
### Added
1010
- Added the `ignored_errors` settings to ignore some curls errors instead throw an exception [#355]
11+
- Support for Twitch embeds [#332]
1112

1213
### Fixed
1314
- Ignored linkedData errors [#356]
@@ -49,6 +50,7 @@ Full library refactoring.
4950
- `providerImage` (use `favicon` or `icon` instead)
5051
- Support for files (pdf, jpg, video, etc).
5152

53+
[#332]: https://github.com/oscarotero/Embed/issues/332
5254
[#345]: https://github.com/oscarotero/Embed/issues/345
5355
[#346]: https://github.com/oscarotero/Embed/issues/346
5456
[#355]: https://github.com/oscarotero/Embed/issues/355
Lines changed: 66 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,66 @@
1+
<?php
2+
declare(strict_types = 1);
3+
4+
namespace Embed\Adapters\Twitch\Detectors;
5+
6+
use Embed\Detectors\Code as Detector;
7+
use Embed\EmbedCode;
8+
use function Embed\html;
9+
10+
class Code extends Detector
11+
{
12+
public function detect(): ?EmbedCode
13+
{
14+
return parent::detect()
15+
?: $this->fallback();
16+
}
17+
18+
private function fallback(): ?EmbedCode
19+
{
20+
$path = $this->extractor->getUri()->getPath();
21+
22+
if ($id = self::getVideoId($path)) {
23+
$code = self::generateCode(['video' => "v{$id}"]);
24+
return new EmbedCode($code, 620, 378);
25+
}
26+
27+
if ($id = self::getChannelId($path)) {
28+
$code = self::generateCode(['channel' => $id]);
29+
return new EmbedCode($code, 620, 378);
30+
}
31+
32+
return null;
33+
}
34+
35+
private static function getVideoId(string $path): ?string
36+
{
37+
if (preg_match('#^/videos/(\d+)$#', $path, $matches)) {
38+
return $matches[1];
39+
}
40+
41+
return null;
42+
}
43+
44+
private static function getChannelId(string $path): ?string
45+
{
46+
if (preg_match('#^/(\w+)$#', $path, $matches)) {
47+
return $matches[1];
48+
}
49+
50+
return null;
51+
}
52+
53+
private static function generateCode(array $params): string
54+
{
55+
$query = http_build_query(['autoplay' => 'false'] + $params);
56+
57+
return html('iframe', [
58+
'src' => "https://player.twitch.tv/?{$query}",
59+
'frameborder' => 0,
60+
'allowfullscreen' => 'true',
61+
'scrolling' => 'no',
62+
'height' => 378,
63+
'width' => 620,
64+
]);
65+
}
66+
}

src/Adapters/Twitch/Extractor.php

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,20 @@
1+
<?php
2+
declare(strict_types = 1);
3+
4+
namespace Embed\Adapters\Twitch;
5+
6+
use Embed\Extractor as Base;
7+
use Embed\Http\Crawler;
8+
use Psr\Http\Message\RequestInterface;
9+
use Psr\Http\Message\ResponseInterface;
10+
use Psr\Http\Message\UriInterface;
11+
12+
class Extractor extends Base
13+
{
14+
public function __construct(UriInterface $uri, RequestInterface $request, ResponseInterface $response, Crawler $crawler)
15+
{
16+
parent::__construct($uri, $request, $response, $crawler);
17+
18+
$this->code = new Detectors\Code($this);
19+
}
20+
}

src/ExtractorFactory.php

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -29,6 +29,7 @@ class ExtractorFactory
2929
'imageshack.com' => Adapters\ImageShack\Extractor::class,
3030
'imagizer.imageshack.com' => Adapters\ImageShack\Extractor::class,
3131
'youtube.com' => Adapters\Youtube\Extractor::class,
32+
'twitch.tv' => Adapters\Twitch\Extractor::class,
3233
];
3334
private array $customDetectors = [];
3435

tests/PagesTest.php

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -161,6 +161,8 @@ public function testSpotify()
161161
public function testTwitch()
162162
{
163163
$this->assertEmbed('https://www.twitch.tv/videos/72749628');
164+
$this->assertEmbed('https://www.twitch.tv/videos/106400740');
165+
$this->assertEmbed('https://www.twitch.tv/twit');
164166
}
165167

166168
public function testTwitter()
Lines changed: 52 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,52 @@
1+
<?php
2+
declare(strict_types = 1);
3+
4+
return [
5+
'headers' => [
6+
'access-control-allow-origin' => [
7+
'*'
8+
],
9+
'cache-control' => [
10+
'no-cache, no-store, must-revalidate, private'
11+
],
12+
'expires' => [
13+
'0'
14+
],
15+
'pragma' => [
16+
'no-cache'
17+
],
18+
'timing-allow-origin' => [
19+
'https://www.twitch.tv'
20+
],
21+
'date' => [
22+
'Sat, 23 May 2020 23:02:25 GMT'
23+
],
24+
'x-served-by' => [
25+
'cache-sea4472-SEA, cache-mad22046-MAD'
26+
],
27+
'x-cache' => [
28+
'MISS, MISS'
29+
],
30+
'x-cache-hits' => [
31+
'0, 0'
32+
],
33+
'x-timer' => [
34+
'S1590274945.952174,VS0,VS0,VE158'
35+
],
36+
'vary' => [
37+
'Accept-Encoding'
38+
],
39+
'strict-transport-security' => [
40+
'max-age=300'
41+
],
42+
'Content-Location' => [
43+
'https://api.twitch.tv/v5/oembed?url=https%3A%2F%2Fwww.twitch.tv%2Ftwit&format=json'
44+
],
45+
'X-Request-Time' => [
46+
'0.252 ms'
47+
]
48+
],
49+
'statusCode' => 204,
50+
'reasonPhrase' => 'No Content',
51+
'body' => ''
52+
];
Lines changed: 52 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,52 @@
1+
<?php
2+
declare(strict_types = 1);
3+
4+
return [
5+
'headers' => [
6+
'access-control-allow-origin' => [
7+
'*'
8+
],
9+
'cache-control' => [
10+
'no-cache, no-store, must-revalidate, private'
11+
],
12+
'expires' => [
13+
'0'
14+
],
15+
'pragma' => [
16+
'no-cache'
17+
],
18+
'timing-allow-origin' => [
19+
'https://www.twitch.tv'
20+
],
21+
'date' => [
22+
'Sat, 23 May 2020 23:02:24 GMT'
23+
],
24+
'x-served-by' => [
25+
'cache-sea4482-SEA, cache-mad22027-MAD'
26+
],
27+
'x-cache' => [
28+
'MISS, MISS'
29+
],
30+
'x-cache-hits' => [
31+
'0, 0'
32+
],
33+
'x-timer' => [
34+
'S1590274945.528781,VS0,VS0,VE159'
35+
],
36+
'vary' => [
37+
'Accept-Encoding'
38+
],
39+
'strict-transport-security' => [
40+
'max-age=300'
41+
],
42+
'Content-Location' => [
43+
'https://api.twitch.tv/v5/oembed?url=https%3A%2F%2Fwww.twitch.tv%2Fvideos%2F106400740&format=json'
44+
],
45+
'X-Request-Time' => [
46+
'0.261 ms'
47+
]
48+
],
49+
'statusCode' => 204,
50+
'reasonPhrase' => 'No Content',
51+
'body' => ''
52+
];

tests/cache/www.twitch.tv.twit.php

Lines changed: 82 additions & 0 deletions
Large diffs are not rendered by default.

tests/cache/www.twitch.tv.videos-106400740.php

Lines changed: 82 additions & 0 deletions
Large diffs are not rendered by default.
Lines changed: 30 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,30 @@
1+
<?php
2+
declare(strict_types = 1);
3+
4+
return [
5+
'authorName' => null,
6+
'authorUrl' => null,
7+
'cms' => null,
8+
'code' => [
9+
'html' => '<iframe src="https://player.twitch.tv/?autoplay=false&amp;channel=twit" frameborder="0" allowfullscreen="true" scrolling="no" height="378" width="620"></iframe>',
10+
'width' => 620,
11+
'height' => 378
12+
],
13+
'description' => 'Twitch is the world\'s leading video platform and community for gamers.',
14+
'favicon' => 'https://static.twitchcdn.net/assets/favicon-32-d6025c14e900565d6177.png',
15+
'feeds' => [],
16+
'icon' => null,
17+
'image' => 'https://static-cdn.jtvnw.net/ttv-static-metadata/twitch_logo3.jpg',
18+
'keywords' => [],
19+
'language' => null,
20+
'languages' => [],
21+
'license' => null,
22+
'providerName' => 'Twitch',
23+
'providerUrl' => 'https://www.twitch.tv',
24+
'publishedTime' => null,
25+
'redirect' => null,
26+
'title' => 'Twitch',
27+
'url' => 'https://www.twitch.tv/twit',
28+
'linkedData' => [],
29+
'oEmbed' => []
30+
];

0 commit comments

Comments
 (0)