diff --git a/app/MetadataResolver/HentaiFoundryResolver.php b/app/MetadataResolver/HentaiFoundryResolver.php
new file mode 100644
index 0000000..87131a5
--- /dev/null
+++ b/app/MetadataResolver/HentaiFoundryResolver.php
@@ -0,0 +1,56 @@
+client = $client;
+ $this->ogpResolver = $ogpResolver;
+ }
+
+ private function nbsp2space(string $string): string
+ {
+ return str_replace("\xc2\xa0", ' ', $string);
+ }
+
+ private function br2nl(string $string): string
+ {
+ return str_replace(' ', PHP_EOL, $string);
+ }
+
+ public function resolve(string $url): Metadata
+ {
+ $res = $this->client->get(
+ http_build_url($url, ['query' => 'enterAgree=1']),
+ ['cookies' => new CookieJar()]
+ );
+
+ $metadata = new Metadata();
+ $crawler = new Crawler((string) $res->getBody());
+
+ $author = $crawler->filter('#picBox .boxtitle a')->text();
+ $description = trim(strip_tags($this->nbsp2space($this->br2nl($crawler->filter('.picDescript')->html()))));
+
+ $metadata->title = $crawler->filter('#picBox .boxtitle .imageTitle')->text();
+ $metadata->description = 'by ' . $author . PHP_EOL . $description;
+ $metadata->image = 'https:' . $crawler->filter('img[src^="//picture"]')->attr('src');
+ $metadata->tags = $crawler->filter('a[rel="tag"]')->extract('_text');
+
+ return $metadata;
+ }
+}
diff --git a/app/MetadataResolver/MetadataResolver.php b/app/MetadataResolver/MetadataResolver.php
index bb2ec08..e12f662 100644
--- a/app/MetadataResolver/MetadataResolver.php
+++ b/app/MetadataResolver/MetadataResolver.php
@@ -33,6 +33,7 @@ class MetadataResolver implements Resolver
'~store\.steampowered\.com/app/\d+~' => SteamResolver::class,
'~www\.xtube\.com/video-watch/.*-\d+$~'=> XtubeResolver::class,
'~ss\.kb10uy\.org/posts/\d+$~' => Kb10uyShortStoryServerResolver::class,
+ '~www\.hentai-foundry\.com/pictures/user/.+/\d+/.+~'=> HentaiFoundryResolver::class,
];
public $mimeTypes = [
diff --git a/composer.json b/composer.json
index 2c46aed..3b89d39 100644
--- a/composer.json
+++ b/composer.json
@@ -10,6 +10,7 @@
"doctrine/dbal": "^2.9",
"fideloper/proxy": "~3.3",
"guzzlehttp/guzzle": "^6.3",
+ "jakeasmith/http_build_url": "^1.0",
"laravel/framework": "5.5.*",
"laravel/tinker": "~1.0",
"misd/linkify": "^1.1",
diff --git a/composer.lock b/composer.lock
index eaf81d3..fb352b4 100644
--- a/composer.lock
+++ b/composer.lock
@@ -4,7 +4,7 @@
"Read more about it at https://getcomposer.org/doc/01-basic-usage.md#installing-dependencies",
"This file is @generated automatically"
],
- "content-hash": "28abd730d4572663d10ae815393c73cd",
+ "content-hash": "b6dfb80c350a7276bb2513a1aeb3d602",
"packages": [
{
"name": "anhskohbo/no-captcha",
@@ -806,6 +806,39 @@
],
"time": "2019-07-01T23:21:34+00:00"
},
+ {
+ "name": "jakeasmith/http_build_url",
+ "version": "1.0.1",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/jakeasmith/http_build_url.git",
+ "reference": "93c273e77cb1edead0cf8bcf8cd2003428e74e37"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/jakeasmith/http_build_url/zipball/93c273e77cb1edead0cf8bcf8cd2003428e74e37",
+ "reference": "93c273e77cb1edead0cf8bcf8cd2003428e74e37",
+ "shasum": ""
+ },
+ "type": "library",
+ "autoload": {
+ "files": [
+ "src/http_build_url.php"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Jake A. Smith",
+ "email": "theman@jakeasmith.com"
+ }
+ ],
+ "description": "Provides functionality for http_build_url() to environments without pecl_http.",
+ "time": "2017-05-01T15:36:40+00:00"
+ },
{
"name": "jakub-onderka/php-console-color",
"version": "v0.2",
diff --git a/tests/Unit/MetadataResolver/HentaiFoundryResolverTest.php b/tests/Unit/MetadataResolver/HentaiFoundryResolverTest.php
new file mode 100644
index 0000000..f781bb1
--- /dev/null
+++ b/tests/Unit/MetadataResolver/HentaiFoundryResolverTest.php
@@ -0,0 +1,36 @@
+shouldUseMock()) {
+ sleep(1);
+ }
+ }
+
+ public function test()
+ {
+ $responseText = file_get_contents(__DIR__ . '/../../fixture/HentaiFoundry/illust.html');
+
+ $this->createResolver(HentaiFoundryResolver::class, $responseText);
+
+ $metadata = $this->resolver->resolve('https://www.hentai-foundry.com/pictures/user/DevilHS/723498/Witchcraft');
+ $this->assertSame('Witchcraft', $metadata->title);
+ $this->assertSame('by DevilHS' . PHP_EOL . 'gift for Liru', $metadata->description);
+ $this->assertEquals(['witch', 'futa'], $metadata->tags);
+ $this->assertSame('https://pictures.hentai-foundry.com/d/DevilHS/723498/DevilHS-723498-Witchcraft.png', $metadata->image);
+ if ($this->shouldUseMock()) {
+ $this->assertSame('https://www.hentai-foundry.com/pictures/user/DevilHS/723498/Witchcraft?enterAgree=1', (string) $this->handler->getLastRequest()->getUri());
+ }
+ }
+}
diff --git a/tests/fixture/HentaiFoundry/illust.html b/tests/fixture/HentaiFoundry/illust.html
new file mode 100644
index 0000000..fc5b11c
--- /dev/null
+++ b/tests/fixture/HentaiFoundry/illust.html
@@ -0,0 +1,350 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+Witchcraft by DevilHS - Hentai Foundry
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+Witchcraft
+
+
+
+
+
+
+
+
+Witchcraft
+
+
+
+
+Description
+
+
gift for Liru
+
+General Info
+
+
+
+ Ratings N Sx ♀ Tg
Comments 11
+ Category
+Original » Futanari (Dickgirls) Media Digital drawing or painting
+ Date Submitted July 25, 2019, 7:29:48 PM Time Taken
+ Views 20597 Reference
+ Favorites... 876 Keywords witch , futa
+
+ Vote Score 649 License Berne Convention
+
+
+
+
+
+
+
+
+
+
\ No newline at end of file