From 4c8fc24c1f6c4394bf3c55f4194c5c93e1f3a04f Mon Sep 17 00:00:00 2001 From: swentel Date: Tue, 21 Apr 2020 21:57:36 +0200 Subject: [PATCH] Allow iframe from YouTube and Vimeo --- controllers/Parse.php | 4 ++++ lib/XRay/Formats/Format.php | 10 ++++++++++ lib/XRay/Parser.php | 2 ++ lib/helpers.php | 9 +++++++++ tests/SanitizeTest.php | 18 ++++++++++++++++++ .../sanitize.example/entry-with-iframe-video | 19 +++++++++++++++++++ 6 files changed, 62 insertions(+) create mode 100644 tests/data/sanitize.example/entry-with-iframe-video diff --git a/controllers/Parse.php b/controllers/Parse.php index 49f00af..c5ecfff 100644 --- a/controllers/Parse.php +++ b/controllers/Parse.php @@ -71,6 +71,10 @@ class Parse { $opts['include-mf1'] = $request->get('include-mf1') == 'false' ? false : true; } + if($request->get('allow-iframe-video')) { + $opts['allowIframeVideo'] = $request->get('allow-iframe-video') == 'true'; + } + $url = $request->get('url'); $html = $request->get('html') ?: $request->get('body'); diff --git a/lib/XRay/Formats/Format.php b/lib/XRay/Formats/Format.php index 0042f40..a741552 100644 --- a/lib/XRay/Formats/Format.php +++ b/lib/XRay/Formats/Format.php @@ -67,6 +67,16 @@ abstract class Format implements iFormat { $config = HTMLPurifier_Config::createDefault(); $config->set('Cache.DefinitionImpl', null); + + if (\p3k\XRay\allow_iframe_video()) { + $allowed[] = 'iframe'; + $config->set('HTML.SafeIframe', true); + $config->set('URI.SafeIframeRegexp', '%^(https?:)?//(www\.youtube(?:-nocookie)?\.com/embed/|player\.vimeo\.com/video/)%'); + $config->set('AutoFormat.RemoveEmpty', true); + // Removes iframe in case it has no src. This strips the non-allowed domains. + $config->set('AutoFormat.RemoveEmpty.Predicate', array('iframe' => array(0 => 'src'))); + } + $config->set('HTML.AllowedElements', $allowed); if($baseURL) { diff --git a/lib/XRay/Parser.php b/lib/XRay/Parser.php index 28886b8..f34f0aa 100644 --- a/lib/XRay/Parser.php +++ b/lib/XRay/Parser.php @@ -12,6 +12,8 @@ class Parser { } public function parse($http_response, $opts=[]) { + $allowIframeVideo = isset($opts['allowIframeVideo']) ? $opts['allowIframeVideo'] : false; + allow_iframe_video($allowIframeVideo); $document = $this->parse_document($http_response, $opts); // If a target parameter was provided, make sure a link to it exists in the parsed document diff --git a/lib/helpers.php b/lib/helpers.php index 8a90a9c..b96f324 100644 --- a/lib/helpers.php +++ b/lib/helpers.php @@ -58,3 +58,12 @@ function phpmf2_version() { } return $version; } + +function allow_iframe_video($value = NULL) { + static $allow_iframe_video = false; + + if (isset($value)) + $allow_iframe_video = $value; + + return $allow_iframe_video; +} \ No newline at end of file diff --git a/tests/SanitizeTest.php b/tests/SanitizeTest.php index 318f7fd..a6dae85 100644 --- a/tests/SanitizeTest.php +++ b/tests/SanitizeTest.php @@ -115,6 +115,24 @@ class SanitizeTest extends PHPUnit_Framework_TestCase { $this->assertEquals('This content has some HTML escaped entities such as & ampersand, " quote, escaped <code> HTML tags, an ümlaut, an @at sign.', $data['data']['content']['html']); } + public function testAllowIframeVideo() { + $url = 'http://sanitize.example/entry-with-iframe-video'; + $response = $this->parse(['url' => $url]); + $body = $response->getContent(); + $data = json_decode($body, true); + $html = $data['data']['content']['html']; + $this->assertNotContains(' +

This is a not a nice video!

+ + + +