diff --git a/application/Html2Text.php b/application/Html2Text.php
deleted file mode 100644
index 6b3c898a6..000000000
--- a/application/Html2Text.php
+++ /dev/null
@@ -1,331 +0,0 @@
-
- * @copyright Copyright 2012 Sean Murphy. All rights reserved.
- * @license http://creativecommons.org/publicdomain/zero/1.0/
- * @link http://php.net/manual/function.str-replace.php
- *
- * @param mixed $search
- * @param mixed $replace
- * @param mixed $subject
- * @param int $count
- * @return mixed
- */
-function mb_str_replace($search, $replace, $subject, &$count = 0) {
- if (!is_array($subject)) {
- // Normalize $search and $replace so they are both arrays of the same length
- $searches = is_array($search) ? array_values($search) : array($search);
- $replacements = is_array($replace) ? array_values($replace) : array($replace);
- $replacements = array_pad($replacements, count($searches), '');
- foreach ($searches as $key => $search) {
- $parts = mb_split(preg_quote($search), $subject);
- if (is_array($parts))
- {
- $count += count($parts) - 1;
- $subject = implode($replacements[$key], $parts);
- }
- }
- } else {
- // Call mb_str_replace for each subject in array, recursively
- foreach ($subject as $key => $value) {
- $subject[$key] = mb_str_replace($search, $replace, $value, $count);
- }
- }
- return $subject;
-}
-
-/******************************************************************************
- * Copyright (c) 2010 Jevon Wright and others.
- * All rights reserved. This program and the accompanying materials
- * are made available under the terms of the Eclipse Public License v1.0
- * which accompanies this distribution, and is available at
- * http://www.eclipse.org/legal/epl-v10.html
- *
- * or
- *
- * LGPL which is available at http://www.gnu.org/licenses/lgpl.html
- *
- *
- * Contributors:
- * Jevon Wright - initial API and implementation
- * Denis Flaven - some fixes for properly handling UTF-8 characters
- ****************************************************************************/
-
-class Html2Text {
-
- /**
- * Tries to convert the given HTML into a plain text format - best suited for
- * e-mail display, etc.
- *
- *
In particular, it tries to maintain the following features:
- *
- * - Links are maintained, with the 'href' copied over
- *
- Information in the <head> is lost
- *
- *
- * @param string html the input HTML
- * @return string the HTML converted, as best as possible, to text
- * @throws Html2TextException if the HTML could not be loaded as a {@link DOMDocument}
- */
- static function convert($html) {
- // replace with spaces
-
- $html = str_replace(" ", " ", $html);
- $html = mb_str_replace("\xc2\xa0", " ", $html); // DO NOT USE str_replace since it breaks the "à" character which is \xc3 \xa0 in UTF-8
-
- $html = static::fixNewlines($html);
-
- $doc = new \DOMDocument();
- if (!@$doc->loadHTML(''.$html)) // Forces the UTF-8 character set for HTML fragments
- {
- throw new Html2TextException("Could not load HTML - badly formed?", $html);
- }
-
- $output = static::iterateOverNode($doc);
-
- // remove leading and trailing spaces on each line
- $output = preg_replace("/[ \t]*\n[ \t]*/im", "\n", $output);
- $output = preg_replace("/ *\t */im", "\t", $output);
-
- // remove unnecessary empty lines
- $output = preg_replace("/\n\n\n*/im", "\n\n", $output);
-
- // remove leading and trailing whitespace
- $output = trim($output);
-
- return $output;
- }
-
- /**
- * Unify newlines; in particular, \r\n becomes \n, and
- * then \r becomes \n. This means that all newlines (Unix, Windows, Mac)
- * all become \ns.
- *
- * @param string text text with any number of \r, \r\n and \n combinations
- * @return string the fixed text
- */
- static function fixNewlines($text) {
- // replace \r\n to \n
- $text = str_replace("\r\n", "\n", $text);
- // remove \rs
- $text = str_replace("\r", "\n", $text);
-
- return $text;
- }
-
- static function nextChildName($node) {
- // get the next child
- $nextNode = $node->nextSibling;
- while ($nextNode != null) {
- if ($nextNode instanceof \DOMElement) {
- break;
- }
- $nextNode = $nextNode->nextSibling;
- }
- $nextName = null;
- if ($nextNode instanceof \DOMElement && $nextNode != null) {
- $nextName = strtolower($nextNode->nodeName);
- }
-
- return $nextName;
- }
-
- static function prevChildName($node) {
- // get the previous child
- $nextNode = $node->previousSibling;
- while ($nextNode != null) {
- if ($nextNode instanceof \DOMElement) {
- break;
- }
- $nextNode = $nextNode->previousSibling;
- }
- $nextName = null;
- if ($nextNode instanceof \DOMElement && $nextNode != null) {
- $nextName = strtolower($nextNode->nodeName);
- }
-
- return $nextName;
- }
-
- static function iterateOverNode($node) {
- if ($node instanceof \DOMText) {
- // Replace whitespace characters with a space (equivilant to \s)
- return preg_replace("/[\\t\\n\\f\\r ]+/im", " ", $node->wholeText);
- }
- if ($node instanceof \DOMDocumentType) {
- // ignore
- return "";
- }
-
- $nextName = static::nextChildName($node);
- $prevName = static::prevChildName($node);
-
- $name = strtolower($node->nodeName);
-
- // start whitespace
- switch ($name) {
- case "hr":
- return "---------------------------------------------------------------\n";
-
- case "style":
- case "head":
- case "title":
- case "meta":
- case "script":
- // ignore these tags
- return "";
-
- case "h1":
- case "h2":
- case "h3":
- case "h4":
- case "h5":
- case "h6":
- case "ol":
- case "ul":
- // add two newlines, second line is added below
- $output = "\n";
- break;
-
- case "td":
- case "th":
- // add tab char to separate table fields
- $output = "\t";
- break;
-
- case "tr":
- case "p":
- case "div":
- // add one line
- $output = "\n";
- break;
-
- case "li":
- $output = "- ";
- break;
-
- default:
- // print out contents of unknown tags
- $output = "";
- break;
- }
-
- // debug
- //$output .= "[$name,$nextName]";
-
- if (isset($node->childNodes)) {
- for ($i = 0; $i < $node->childNodes->length; $i++) {
- $n = $node->childNodes->item($i);
-
- $text = static::iterateOverNode($n);
-
- $output .= $text;
- }
- }
-
- // end whitespace
- switch ($name) {
- case "h1":
- case "h2":
- case "h3":
- case "h4":
- case "h5":
- case "h6":
- $output .= "\n";
- break;
-
- case "p":
- case "br":
- // add one line
- if ($nextName != "div")
- $output .= "\n";
- break;
-
- case "div":
- // add one line only if the next child isn't a div
- if ($nextName != "div" && $nextName != null)
- $output .= "\n";
- break;
-
- case "a":
- // links are returned in [text](link) format
- $href = $node->getAttribute("href");
-
- $output = trim($output);
-
- // remove double [[ ]] s from linking images
- if (substr($output, 0, 1) == "[" && substr($output, -1) == "]") {
- $output = substr($output, 1, strlen($output) - 2);
-
- // for linking images, the title of the overrides the title of the
- if ($node->getAttribute("title")) {
- $output = $node->getAttribute("title");
- }
- }
-
- // if there is no link text, but a title attr
- if (!$output && $node->getAttribute("title")) {
- $output = $node->getAttribute("title");
- }
-
- if ($href == null) {
- // it doesn't link anywhere
- if ($node->getAttribute("name") != null) {
- $output = "[$output]";
- }
- } else {
- if ($href == $output || $href == "mailto:$output" || $href == "http://$output" || $href == "https://$output") {
- // link to the same address: just use link
- $output;
- } else {
- // replace it
- if ($output) {
- $output = "[$output]($href)";
- } else {
- // empty string
- $output = $href;
- }
- }
- }
-
- // does the next node require additional whitespace?
- switch ($nextName) {
- case "h1": case "h2": case "h3": case "h4": case "h5": case "h6":
- $output .= "\n";
- break;
- }
- break;
-
- case "img":
- if ($node->getAttribute("title")) {
- $output = "[" . $node->getAttribute("title") . "]";
- } elseif ($node->getAttribute("alt")) {
- $output = "[" . $node->getAttribute("alt") . "]";
- } else {
- $output = "";
- }
- break;
-
- case "li":
- $output .= "\n";
- break;
-
- default:
- // do nothing
- }
-
- return $output;
- }
-
-}
diff --git a/application/Html2TextException.php b/application/Html2TextException.php
deleted file mode 100644
index ddfa86586..000000000
--- a/application/Html2TextException.php
+++ /dev/null
@@ -1,28 +0,0 @@
-more_info = $more_info;
- }
-}
diff --git a/application/utils.inc.php b/application/utils.inc.php
index 48e53f4bd..887df1ab2 100644
--- a/application/utils.inc.php
+++ b/application/utils.inc.php
@@ -26,6 +26,7 @@ use Combodo\iTop\Service\Module\ModuleService;
use ScssPhp\ScssPhp\Compiler;
use ScssPhp\ScssPhp\OutputStyle;
use ScssPhp\ScssPhp\ValueConverter;
+use Soundasleep\Html2Text;
/**
@@ -2067,7 +2068,7 @@ SQL;
{
try {
//return ''.$sHtml;
- return \Html2Text\Html2Text::convert(''.$sHtml);
+ return Html2Text::convert(''.$sHtml);
}
catch (Exception $e) {
return $e->getMessage();
diff --git a/composer.json b/composer.json
index 8adc82473..82774ff05 100644
--- a/composer.json
+++ b/composer.json
@@ -34,7 +34,8 @@
"symfony/yaml": "~6.4.0",
"tecnickcom/tcpdf": "^6.6.0",
"thenetworg/oauth2-azure": "^2.0",
- "masterminds/html5": "^2.8.0"
+ "masterminds/html5": "^2.8.0",
+ "soundasleep/html2text": "~1.1"
},
"require-dev": {
"symfony/debug-bundle": "~6.4.0",
diff --git a/composer.lock b/composer.lock
index b093c2cd5..2541265fa 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": "c8ab1de6659dd4fa2ded6043615b86e6",
+ "content-hash": "da75a60a57f3c216e40d472f4d98d026",
"packages": [
{
"name": "apereo/phpcas",
@@ -2041,6 +2041,61 @@
},
"time": "2024-01-13T12:36:40+00:00"
},
+ {
+ "name": "soundasleep/html2text",
+ "version": "1.1.0",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/soundasleep/html2text.git",
+ "reference": "3243a7107878a61685d2eccf99918d6479e039fc"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/soundasleep/html2text/zipball/3243a7107878a61685d2eccf99918d6479e039fc",
+ "reference": "3243a7107878a61685d2eccf99918d6479e039fc",
+ "shasum": ""
+ },
+ "require": {
+ "ext-dom": "*",
+ "ext-libxml": "*",
+ "php": ">=7.0"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "~7.0",
+ "soundasleep/component-tests": "~0.2"
+ },
+ "type": "library",
+ "autoload": {
+ "psr-4": {
+ "Soundasleep\\": "src"
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Jevon Wright",
+ "homepage": "https://jevon.org",
+ "role": "Developer"
+ }
+ ],
+ "description": "A PHP script to convert HTML into a plain text format",
+ "homepage": "https://github.com/soundasleep/html2text",
+ "keywords": [
+ "email",
+ "html",
+ "php",
+ "text"
+ ],
+ "support": {
+ "email": "support@jevon.org",
+ "issues": "https://github.com/soundasleep/html2text/issues",
+ "source": "https://github.com/soundasleep/html2text/tree/master"
+ },
+ "time": "2019-02-15T01:44:54+00:00"
+ },
{
"name": "symfony/cache",
"version": "v6.4.2",
diff --git a/lib/composer/autoload_classmap.php b/lib/composer/autoload_classmap.php
index f16c24d02..d08b22f6f 100644
--- a/lib/composer/autoload_classmap.php
+++ b/lib/composer/autoload_classmap.php
@@ -746,8 +746,6 @@ return array(
'HTMLDOMSanitizer' => $baseDir . '/core/htmlsanitizer.class.inc.php',
'HTMLNullSanitizer' => $baseDir . '/core/htmlsanitizer.class.inc.php',
'HTMLSanitizer' => $baseDir . '/core/htmlsanitizer.class.inc.php',
- 'Html2Text\\Html2Text' => $baseDir . '/application/Html2Text.php',
- 'Html2Text\\Html2TextException' => $baseDir . '/application/Html2TextException.php',
'ITopArchiveTar' => $baseDir . '/core/tar-itop.class.inc.php',
'InlineImage' => $baseDir . '/core/inlineimage.class.inc.php',
'InlineImageGC' => $baseDir . '/core/inlineimage.class.inc.php',
@@ -1152,11 +1150,11 @@ return array(
'ModuleHandlerApiInterface' => $baseDir . '/core/modulehandler.class.inc.php',
'MonthlyRotatingLogFileNameBuilder' => $baseDir . '/core/log.class.inc.php',
'MyHelpers' => $baseDir . '/core/MyHelpers.class.inc.php',
- 'MySQLException' => $baseDir . '/application/exceptions/mysql/MySQLException.php',
- 'MySQLHasGoneAwayException' => $baseDir . '/application/exceptions/mysql/MySQLHasGoneAwayException.php',
- 'MySQLNoTransactionException' => $baseDir . '/application/exceptions/mysql/MySQLNoTransactionException.php',
- 'MySQLQueryHasNoResultException' => $baseDir . '/application/exceptions/mysql/MySQLQueryHasNoResultException.php',
- 'MySQLTransactionNotClosedException' => $baseDir . '/application/exceptions/mysql/MySQLTransactionNotClosedException.php',
+ 'MySQLException' => $baseDir . '/core/cmdbsource.class.inc.php',
+ 'MySQLHasGoneAwayException' => $baseDir . '/core/cmdbsource.class.inc.php',
+ 'MySQLNoTransactionException' => $baseDir . '/core/cmdbsource.class.inc.php',
+ 'MySQLQueryHasNoResultException' => $baseDir . '/core/cmdbsource.class.inc.php',
+ 'MySQLTransactionNotClosedException' => $baseDir . '/core/cmdbsource.class.inc.php',
'NestedQueryExpression' => $baseDir . '/core/oql/expression.class.inc.php',
'NestedQueryOqlExpression' => $baseDir . '/core/oql/oqlquery.class.inc.php',
'NewObjectMenuNode' => $baseDir . '/application/menunode.class.inc.php',
@@ -1646,6 +1644,8 @@ return array(
'SimpleCryptSodiumEngine' => $baseDir . '/core/simplecrypt.class.inc.php',
'SimpleGraph' => $baseDir . '/core/simplegraph.class.inc.php',
'SimpleGraphException' => $baseDir . '/core/simplegraph.class.inc.php',
+ 'Soundasleep\\Html2Text' => $vendorDir . '/soundasleep/html2text/src/Html2Text.php',
+ 'Soundasleep\\Html2TextException' => $vendorDir . '/soundasleep/html2text/src/Html2TextException.php',
'SpreadsheetBulkExport' => $baseDir . '/core/spreadsheetbulkexport.class.inc.php',
'StimulusChecker' => $baseDir . '/core/userrights.class.inc.php',
'StimulusInternal' => $baseDir . '/core/stimulus.class.inc.php',
diff --git a/lib/composer/autoload_psr4.php b/lib/composer/autoload_psr4.php
index 632d6d2df..594907f1a 100644
--- a/lib/composer/autoload_psr4.php
+++ b/lib/composer/autoload_psr4.php
@@ -46,6 +46,7 @@ return array(
'Symfony\\Bundle\\FrameworkBundle\\' => array($vendorDir . '/symfony/framework-bundle'),
'Symfony\\Bundle\\DebugBundle\\' => array($vendorDir . '/symfony/debug-bundle'),
'Symfony\\Bridge\\Twig\\' => array($vendorDir . '/symfony/twig-bridge'),
+ 'Soundasleep\\' => array($vendorDir . '/soundasleep/html2text/src'),
'ScssPhp\\ScssPhp\\' => array($vendorDir . '/scssphp/scssphp/src'),
'Sabberworm\\CSS\\' => array($vendorDir . '/sabberworm/php-css-parser/src'),
'Psr\\Log\\' => array($vendorDir . '/psr/log/src'),
diff --git a/lib/composer/autoload_static.php b/lib/composer/autoload_static.php
index 8f1e52d1c..b1d9534ea 100644
--- a/lib/composer/autoload_static.php
+++ b/lib/composer/autoload_static.php
@@ -74,6 +74,7 @@ class ComposerStaticInit7f81b4a2a468a061c306af5e447a9a9f
'Symfony\\Bundle\\FrameworkBundle\\' => 31,
'Symfony\\Bundle\\DebugBundle\\' => 27,
'Symfony\\Bridge\\Twig\\' => 20,
+ 'Soundasleep\\' => 12,
'ScssPhp\\ScssPhp\\' => 16,
'Sabberworm\\CSS\\' => 15,
),
@@ -275,6 +276,10 @@ class ComposerStaticInit7f81b4a2a468a061c306af5e447a9a9f
array (
0 => __DIR__ . '/..' . '/symfony/twig-bridge',
),
+ 'Soundasleep\\' =>
+ array (
+ 0 => __DIR__ . '/..' . '/soundasleep/html2text/src',
+ ),
'ScssPhp\\ScssPhp\\' =>
array (
0 => __DIR__ . '/..' . '/scssphp/scssphp/src',
@@ -1129,8 +1134,6 @@ class ComposerStaticInit7f81b4a2a468a061c306af5e447a9a9f
'HTMLDOMSanitizer' => __DIR__ . '/../..' . '/core/htmlsanitizer.class.inc.php',
'HTMLNullSanitizer' => __DIR__ . '/../..' . '/core/htmlsanitizer.class.inc.php',
'HTMLSanitizer' => __DIR__ . '/../..' . '/core/htmlsanitizer.class.inc.php',
- 'Html2Text\\Html2Text' => __DIR__ . '/../..' . '/application/Html2Text.php',
- 'Html2Text\\Html2TextException' => __DIR__ . '/../..' . '/application/Html2TextException.php',
'ITopArchiveTar' => __DIR__ . '/../..' . '/core/tar-itop.class.inc.php',
'InlineImage' => __DIR__ . '/../..' . '/core/inlineimage.class.inc.php',
'InlineImageGC' => __DIR__ . '/../..' . '/core/inlineimage.class.inc.php',
@@ -1535,11 +1538,11 @@ class ComposerStaticInit7f81b4a2a468a061c306af5e447a9a9f
'ModuleHandlerApiInterface' => __DIR__ . '/../..' . '/core/modulehandler.class.inc.php',
'MonthlyRotatingLogFileNameBuilder' => __DIR__ . '/../..' . '/core/log.class.inc.php',
'MyHelpers' => __DIR__ . '/../..' . '/core/MyHelpers.class.inc.php',
- 'MySQLException' => __DIR__ . '/../..' . '/application/exceptions/mysql/MySQLException.php',
- 'MySQLHasGoneAwayException' => __DIR__ . '/../..' . '/application/exceptions/mysql/MySQLHasGoneAwayException.php',
- 'MySQLNoTransactionException' => __DIR__ . '/../..' . '/application/exceptions/mysql/MySQLNoTransactionException.php',
- 'MySQLQueryHasNoResultException' => __DIR__ . '/../..' . '/application/exceptions/mysql/MySQLQueryHasNoResultException.php',
- 'MySQLTransactionNotClosedException' => __DIR__ . '/../..' . '/application/exceptions/mysql/MySQLTransactionNotClosedException.php',
+ 'MySQLException' => __DIR__ . '/../..' . '/core/cmdbsource.class.inc.php',
+ 'MySQLHasGoneAwayException' => __DIR__ . '/../..' . '/core/cmdbsource.class.inc.php',
+ 'MySQLNoTransactionException' => __DIR__ . '/../..' . '/core/cmdbsource.class.inc.php',
+ 'MySQLQueryHasNoResultException' => __DIR__ . '/../..' . '/core/cmdbsource.class.inc.php',
+ 'MySQLTransactionNotClosedException' => __DIR__ . '/../..' . '/core/cmdbsource.class.inc.php',
'NestedQueryExpression' => __DIR__ . '/../..' . '/core/oql/expression.class.inc.php',
'NestedQueryOqlExpression' => __DIR__ . '/../..' . '/core/oql/oqlquery.class.inc.php',
'NewObjectMenuNode' => __DIR__ . '/../..' . '/application/menunode.class.inc.php',
@@ -2029,6 +2032,8 @@ class ComposerStaticInit7f81b4a2a468a061c306af5e447a9a9f
'SimpleCryptSodiumEngine' => __DIR__ . '/../..' . '/core/simplecrypt.class.inc.php',
'SimpleGraph' => __DIR__ . '/../..' . '/core/simplegraph.class.inc.php',
'SimpleGraphException' => __DIR__ . '/../..' . '/core/simplegraph.class.inc.php',
+ 'Soundasleep\\Html2Text' => __DIR__ . '/..' . '/soundasleep/html2text/src/Html2Text.php',
+ 'Soundasleep\\Html2TextException' => __DIR__ . '/..' . '/soundasleep/html2text/src/Html2TextException.php',
'SpreadsheetBulkExport' => __DIR__ . '/../..' . '/core/spreadsheetbulkexport.class.inc.php',
'StimulusChecker' => __DIR__ . '/../..' . '/core/userrights.class.inc.php',
'StimulusInternal' => __DIR__ . '/../..' . '/core/stimulus.class.inc.php',
diff --git a/lib/composer/installed.json b/lib/composer/installed.json
index 44d865ac7..9f278848e 100644
--- a/lib/composer/installed.json
+++ b/lib/composer/installed.json
@@ -2128,6 +2128,64 @@
},
"install-path": "../scssphp/scssphp"
},
+ {
+ "name": "soundasleep/html2text",
+ "version": "1.1.0",
+ "version_normalized": "1.1.0.0",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/soundasleep/html2text.git",
+ "reference": "3243a7107878a61685d2eccf99918d6479e039fc"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/soundasleep/html2text/zipball/3243a7107878a61685d2eccf99918d6479e039fc",
+ "reference": "3243a7107878a61685d2eccf99918d6479e039fc",
+ "shasum": ""
+ },
+ "require": {
+ "ext-dom": "*",
+ "ext-libxml": "*",
+ "php": ">=7.0"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "~7.0",
+ "soundasleep/component-tests": "~0.2"
+ },
+ "time": "2019-02-15T01:44:54+00:00",
+ "type": "library",
+ "installation-source": "dist",
+ "autoload": {
+ "psr-4": {
+ "Soundasleep\\": "src"
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Jevon Wright",
+ "homepage": "https://jevon.org",
+ "role": "Developer"
+ }
+ ],
+ "description": "A PHP script to convert HTML into a plain text format",
+ "homepage": "https://github.com/soundasleep/html2text",
+ "keywords": [
+ "email",
+ "html",
+ "php",
+ "text"
+ ],
+ "support": {
+ "email": "support@jevon.org",
+ "issues": "https://github.com/soundasleep/html2text/issues",
+ "source": "https://github.com/soundasleep/html2text/tree/master"
+ },
+ "install-path": "../soundasleep/html2text"
+ },
{
"name": "symfony/cache",
"version": "v6.4.2",
diff --git a/lib/composer/installed.php b/lib/composer/installed.php
index 16887e28c..3b63bb7b3 100644
--- a/lib/composer/installed.php
+++ b/lib/composer/installed.php
@@ -3,7 +3,7 @@
'name' => 'combodo/itop',
'pretty_version' => 'dev-develop',
'version' => 'dev-develop',
- 'reference' => '0036c70fbd34e0bfbdfdbaf26d497d8e1ed7bd04',
+ 'reference' => 'bfbb046b10aa2fc864d5fbc794df31e488542df4',
'type' => 'project',
'install_path' => __DIR__ . '/../../',
'aliases' => array(),
@@ -22,7 +22,7 @@
'combodo/itop' => array(
'pretty_version' => 'dev-develop',
'version' => 'dev-develop',
- 'reference' => '0036c70fbd34e0bfbdfdbaf26d497d8e1ed7bd04',
+ 'reference' => 'bfbb046b10aa2fc864d5fbc794df31e488542df4',
'type' => 'project',
'install_path' => __DIR__ . '/../../',
'aliases' => array(),
@@ -359,6 +359,15 @@
'aliases' => array(),
'dev_requirement' => false,
),
+ 'soundasleep/html2text' => array(
+ 'pretty_version' => '1.1.0',
+ 'version' => '1.1.0.0',
+ 'reference' => '3243a7107878a61685d2eccf99918d6479e039fc',
+ 'type' => 'library',
+ 'install_path' => __DIR__ . '/../soundasleep/html2text',
+ 'aliases' => array(),
+ 'dev_requirement' => false,
+ ),
'symfony/cache' => array(
'pretty_version' => 'v6.4.2',
'version' => '6.4.2.0',
diff --git a/lib/soundasleep/html2text/.editorconfig b/lib/soundasleep/html2text/.editorconfig
new file mode 100644
index 000000000..7974b6a8a
--- /dev/null
+++ b/lib/soundasleep/html2text/.editorconfig
@@ -0,0 +1,23 @@
+# EditorConfig is awesome: http://EditorConfig.org
+
+# top-most EditorConfig file
+root = true
+
+# Unix-style newlines with a newline ending every file
+[*]
+end_of_line = lf
+charset = utf-8
+insert_final_newline = true
+trim_trailing_whitespace = true
+indent_style = tab
+indent_size = 4
+
+[*.md]
+indent_style = space
+indent_size = 2
+
+# don't add newlines to test files
+[tests/*]
+indent_style = tabs
+trim_trailing_whitespace = false
+insert_final_newline = false
diff --git a/lib/soundasleep/html2text/.gitignore b/lib/soundasleep/html2text/.gitignore
new file mode 100644
index 000000000..255c0b0a9
--- /dev/null
+++ b/lib/soundasleep/html2text/.gitignore
@@ -0,0 +1,5 @@
+tests/*.output
+*.sublime-project
+*.sublime-workspace
+vendor/
+**/*.DS_Store
diff --git a/lib/soundasleep/html2text/.travis.yml b/lib/soundasleep/html2text/.travis.yml
new file mode 100644
index 000000000..3f03a9eee
--- /dev/null
+++ b/lib/soundasleep/html2text/.travis.yml
@@ -0,0 +1,10 @@
+language: php
+php:
+ - 7.3
+group: stable
+before_install:
+ - composer self-update
+install:
+ - composer install
+script:
+ - ./vendor/bin/phpunit
diff --git a/lib/soundasleep/html2text/CHANGELOG.md b/lib/soundasleep/html2text/CHANGELOG.md
new file mode 100644
index 000000000..a1bda0954
--- /dev/null
+++ b/lib/soundasleep/html2text/CHANGELOG.md
@@ -0,0 +1,37 @@
+# Changelog
+All notable changes to this project will be documented in this file.
+
+The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
+and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
+
+## [Unreleased]
+
+## [1.1.0] - 2019-02-15
+### Added
+- Zero-width non-joiners are now stripped to prevent output issues, similar to non-breaking whitespace
+
+### Fixed
+- Fix namespace in composer [#67](https://github.com/soundasleep/html2text/pull/67)
+
+## [1.0.0] - 2019-02-14
+### Added
+- Added `drop_links` option to render links without the target href [#65](https://github.com/soundasleep/html2text/pull/65)
+
+### Changed
+- **Important:** Changed namespace from `\Html2Text\Html2Text` to `\Soundasleep\Html2text` [#45](https://github.com/soundasleep/html2text/issues/45)
+- Treat non-breaking spaces consistently: never include them in output text [#64](https://github.com/soundasleep/html2text/pull/64)
+- Second argument to `convert()` is now an array, rather than boolean [#65](https://github.com/soundasleep/html2text/pull/65)
+- Optimise/improve newline & whitespace handling [#47](https://github.com/soundasleep/html2text/pull/47)
+- Upgrade PHP support to PHP 7.3+
+- Upgrade PHPUnit to 7.x
+- Re-release project under MIT license [#58](https://github.com/soundasleep/html2text/issues/58)
+
+## [0.5.0] - 2017-04-20
+### Added
+- Add ignore_error optional argument [#63](https://github.com/soundasleep/html2text/pull/63)
+- Blockquote support [#50](https://github.com/soundasleep/html2text/pull/50)
+
+[Unreleased]: https://github.com/soundasleep/html2text/compare/1.1.0...HEAD
+[1.1.0]: https://github.com/soundasleep/html2text/compare/1.0.0...1.1.0
+[1.0.0]: https://github.com/soundasleep/html2text/compare/0.5.0...1.0.0
+[0.5.0]: https://github.com/soundasleep/html2text/compare/0.5.0...0.3.4
diff --git a/lib/soundasleep/html2text/LICENSE.md b/lib/soundasleep/html2text/LICENSE.md
new file mode 100644
index 000000000..d8613be25
--- /dev/null
+++ b/lib/soundasleep/html2text/LICENSE.md
@@ -0,0 +1,21 @@
+MIT License
+
+Copyright (c) 2019 Jevon Wright
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in all
+copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
+SOFTWARE.
diff --git a/lib/soundasleep/html2text/README.md b/lib/soundasleep/html2text/README.md
new file mode 100644
index 000000000..c28034c12
--- /dev/null
+++ b/lib/soundasleep/html2text/README.md
@@ -0,0 +1,101 @@
+html2text [](https://travis-ci.org/soundasleep/html2text) [](https://packagist.org/packages/soundasleep/html2text)
+=========
+
+html2text is a very simple script that uses DOM methods to convert HTML into a format similar to what would be
+rendered by a browser - perfect for places where you need a quick text representation. For example:
+
+```html
+
+Ignored Title
+
+ Hello, World!
+
+ This is some e-mail content.
+ Even though it has whitespace and newlines, the e-mail converter
+ will handle it correctly.
+
+
Even mismatched tags.
+
+ A div
+ Another div
+
+
+ A link
+
+
+
+```
+
+Will be converted into:
+
+```text
+Hello, World!
+
+This is some e-mail content. Even though it has whitespace and newlines, the e-mail converter will handle it correctly.
+
+Even mismatched tags.
+
+A div
+Another div
+A div
+within a div
+
+[A link](http://foo.com)
+```
+
+See the [original blog post](http://journals.jevon.org/users/jevon-phd/entry/19818) or the related [StackOverflow answer](http://stackoverflow.com/a/2564472/39531).
+
+## Installing
+
+You can use [Composer](http://getcomposer.org/) to add the [package](https://packagist.org/packages/soundasleep/html2text) to your project:
+
+```json
+{
+ "require": {
+ "soundasleep/html2text": "~1.1"
+ }
+}
+```
+
+And then use it quite simply:
+
+```php
+$text = \Soundasleep\Html2Text::convert($html);
+```
+
+You can also include the supplied `html2text.php` and use `$text = convert_html_to_text($html);` instead.
+
+### Options
+
+| Option | Default | Description |
+|--------|---------|-------------|
+| **ignore_errors** | `false` | Set to `true` to ignore any XML parsing errors. |
+| **drop_links** | `false` | Set to `true` to not render links as `[http://foo.com](My Link)`, but rather just `My Link`. |
+
+Pass along options as a second argument to `convert`, for example:
+
+```php
+$options = array(
+ 'ignore_errors' => true,
+ // other options go here
+);
+$text = \Soundasleep\Html2Text::convert($html, $options);
+```
+
+## Tests
+
+Some very basic tests are provided in the `tests/` directory. Run them with `composer install && vendor/bin/phpunit`.
+
+## Troubleshooting
+
+### Class 'DOMDocument' not found
+
+You need to [install the PHP XML extension](https://github.com/soundasleep/html2text/issues/55) for your PHP version. e.g. `apt-get install php7.1-xml`
+
+## License
+
+`html2text` is [licensed under MIT](LICENSE.md), making it suitable for both Eclipse and GPL projects.
+
+## Other versions
+
+Also see [html2text_ruby](https://github.com/soundasleep/html2text_ruby), a Ruby implementation.
diff --git a/lib/soundasleep/html2text/composer.json b/lib/soundasleep/html2text/composer.json
new file mode 100644
index 000000000..409bb9d0d
--- /dev/null
+++ b/lib/soundasleep/html2text/composer.json
@@ -0,0 +1,32 @@
+{
+ "name": "soundasleep/html2text",
+ "description": "A PHP script to convert HTML into a plain text format",
+ "type": "library",
+ "keywords": [ "php", "html", "text", "email" ],
+ "homepage": "https://github.com/soundasleep/html2text",
+ "license": "MIT",
+ "authors": [
+ {
+ "name": "Jevon Wright",
+ "homepage": "https://jevon.org",
+ "role": "Developer"
+ }
+ ],
+ "autoload": {
+ "psr-4": {
+ "Soundasleep\\": "src"
+ }
+ },
+ "support": {
+ "email": "support@jevon.org"
+ },
+ "require": {
+ "php": ">=7.0",
+ "ext-dom": "*",
+ "ext-libxml": "*"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "~7.0",
+ "soundasleep/component-tests": "~0.2"
+ }
+}
diff --git a/lib/soundasleep/html2text/composer.lock b/lib/soundasleep/html2text/composer.lock
new file mode 100644
index 000000000..0e084dc91
--- /dev/null
+++ b/lib/soundasleep/html2text/composer.lock
@@ -0,0 +1,1586 @@
+{
+ "_readme": [
+ "This file locks the dependencies of your project to a known state",
+ "Read more about it at https://getcomposer.org/doc/01-basic-usage.md#installing-dependencies",
+ "This file is @generated automatically"
+ ],
+ "content-hash": "4eb1764bda1a63f84b468db3da77e779",
+ "packages": [],
+ "packages-dev": [
+ {
+ "name": "doctrine/instantiator",
+ "version": "1.1.0",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/doctrine/instantiator.git",
+ "reference": "185b8868aa9bf7159f5f953ed5afb2d7fcdc3bda"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/doctrine/instantiator/zipball/185b8868aa9bf7159f5f953ed5afb2d7fcdc3bda",
+ "reference": "185b8868aa9bf7159f5f953ed5afb2d7fcdc3bda",
+ "shasum": ""
+ },
+ "require": {
+ "php": "^7.1"
+ },
+ "require-dev": {
+ "athletic/athletic": "~0.1.8",
+ "ext-pdo": "*",
+ "ext-phar": "*",
+ "phpunit/phpunit": "^6.2.3",
+ "squizlabs/php_codesniffer": "^3.0.2"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "1.2.x-dev"
+ }
+ },
+ "autoload": {
+ "psr-4": {
+ "Doctrine\\Instantiator\\": "src/Doctrine/Instantiator/"
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Marco Pivetta",
+ "email": "ocramius@gmail.com",
+ "homepage": "http://ocramius.github.com/"
+ }
+ ],
+ "description": "A small, lightweight utility to instantiate objects in PHP without invoking their constructors",
+ "homepage": "https://github.com/doctrine/instantiator",
+ "keywords": [
+ "constructor",
+ "instantiate"
+ ],
+ "time": "2017-07-22T11:58:36+00:00"
+ },
+ {
+ "name": "justinrainbow/json-schema",
+ "version": "5.2.8",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/justinrainbow/json-schema.git",
+ "reference": "dcb6e1006bb5fd1e392b4daa68932880f37550d4"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/justinrainbow/json-schema/zipball/dcb6e1006bb5fd1e392b4daa68932880f37550d4",
+ "reference": "dcb6e1006bb5fd1e392b4daa68932880f37550d4",
+ "shasum": ""
+ },
+ "require": {
+ "php": ">=5.3.3"
+ },
+ "require-dev": {
+ "friendsofphp/php-cs-fixer": "~2.2.20",
+ "json-schema/json-schema-test-suite": "1.2.0",
+ "phpunit/phpunit": "^4.8.35"
+ },
+ "bin": [
+ "bin/validate-json"
+ ],
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "5.0.x-dev"
+ }
+ },
+ "autoload": {
+ "psr-4": {
+ "JsonSchema\\": "src/JsonSchema/"
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Bruno Prieto Reis",
+ "email": "bruno.p.reis@gmail.com"
+ },
+ {
+ "name": "Justin Rainbow",
+ "email": "justin.rainbow@gmail.com"
+ },
+ {
+ "name": "Igor Wiedler",
+ "email": "igor@wiedler.ch"
+ },
+ {
+ "name": "Robert Schönthal",
+ "email": "seroscho@googlemail.com"
+ }
+ ],
+ "description": "A library to validate a json schema.",
+ "homepage": "https://github.com/justinrainbow/json-schema",
+ "keywords": [
+ "json",
+ "schema"
+ ],
+ "time": "2019-01-14T23:55:14+00:00"
+ },
+ {
+ "name": "myclabs/deep-copy",
+ "version": "1.8.1",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/myclabs/DeepCopy.git",
+ "reference": "3e01bdad3e18354c3dce54466b7fbe33a9f9f7f8"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/myclabs/DeepCopy/zipball/3e01bdad3e18354c3dce54466b7fbe33a9f9f7f8",
+ "reference": "3e01bdad3e18354c3dce54466b7fbe33a9f9f7f8",
+ "shasum": ""
+ },
+ "require": {
+ "php": "^7.1"
+ },
+ "replace": {
+ "myclabs/deep-copy": "self.version"
+ },
+ "require-dev": {
+ "doctrine/collections": "^1.0",
+ "doctrine/common": "^2.6",
+ "phpunit/phpunit": "^7.1"
+ },
+ "type": "library",
+ "autoload": {
+ "psr-4": {
+ "DeepCopy\\": "src/DeepCopy/"
+ },
+ "files": [
+ "src/DeepCopy/deep_copy.php"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "description": "Create deep copies (clones) of your objects",
+ "keywords": [
+ "clone",
+ "copy",
+ "duplicate",
+ "object",
+ "object graph"
+ ],
+ "time": "2018-06-11T23:09:50+00:00"
+ },
+ {
+ "name": "phar-io/manifest",
+ "version": "1.0.3",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/phar-io/manifest.git",
+ "reference": "7761fcacf03b4d4f16e7ccb606d4879ca431fcf4"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/phar-io/manifest/zipball/7761fcacf03b4d4f16e7ccb606d4879ca431fcf4",
+ "reference": "7761fcacf03b4d4f16e7ccb606d4879ca431fcf4",
+ "shasum": ""
+ },
+ "require": {
+ "ext-dom": "*",
+ "ext-phar": "*",
+ "phar-io/version": "^2.0",
+ "php": "^5.6 || ^7.0"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "1.0.x-dev"
+ }
+ },
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Arne Blankerts",
+ "email": "arne@blankerts.de",
+ "role": "Developer"
+ },
+ {
+ "name": "Sebastian Heuer",
+ "email": "sebastian@phpeople.de",
+ "role": "Developer"
+ },
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sebastian@phpunit.de",
+ "role": "Developer"
+ }
+ ],
+ "description": "Component for reading phar.io manifest information from a PHP Archive (PHAR)",
+ "time": "2018-07-08T19:23:20+00:00"
+ },
+ {
+ "name": "phar-io/version",
+ "version": "2.0.1",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/phar-io/version.git",
+ "reference": "45a2ec53a73c70ce41d55cedef9063630abaf1b6"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/phar-io/version/zipball/45a2ec53a73c70ce41d55cedef9063630abaf1b6",
+ "reference": "45a2ec53a73c70ce41d55cedef9063630abaf1b6",
+ "shasum": ""
+ },
+ "require": {
+ "php": "^5.6 || ^7.0"
+ },
+ "type": "library",
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Arne Blankerts",
+ "email": "arne@blankerts.de",
+ "role": "Developer"
+ },
+ {
+ "name": "Sebastian Heuer",
+ "email": "sebastian@phpeople.de",
+ "role": "Developer"
+ },
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sebastian@phpunit.de",
+ "role": "Developer"
+ }
+ ],
+ "description": "Library for handling version information and constraints",
+ "time": "2018-07-08T19:19:57+00:00"
+ },
+ {
+ "name": "phpdocumentor/reflection-common",
+ "version": "1.0.1",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/phpDocumentor/ReflectionCommon.git",
+ "reference": "21bdeb5f65d7ebf9f43b1b25d404f87deab5bfb6"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/phpDocumentor/ReflectionCommon/zipball/21bdeb5f65d7ebf9f43b1b25d404f87deab5bfb6",
+ "reference": "21bdeb5f65d7ebf9f43b1b25d404f87deab5bfb6",
+ "shasum": ""
+ },
+ "require": {
+ "php": ">=5.5"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "^4.6"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "1.0.x-dev"
+ }
+ },
+ "autoload": {
+ "psr-4": {
+ "phpDocumentor\\Reflection\\": [
+ "src"
+ ]
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Jaap van Otterdijk",
+ "email": "opensource@ijaap.nl"
+ }
+ ],
+ "description": "Common reflection classes used by phpdocumentor to reflect the code structure",
+ "homepage": "http://www.phpdoc.org",
+ "keywords": [
+ "FQSEN",
+ "phpDocumentor",
+ "phpdoc",
+ "reflection",
+ "static analysis"
+ ],
+ "time": "2017-09-11T18:02:19+00:00"
+ },
+ {
+ "name": "phpdocumentor/reflection-docblock",
+ "version": "4.3.0",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/phpDocumentor/ReflectionDocBlock.git",
+ "reference": "94fd0001232e47129dd3504189fa1c7225010d08"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/phpDocumentor/ReflectionDocBlock/zipball/94fd0001232e47129dd3504189fa1c7225010d08",
+ "reference": "94fd0001232e47129dd3504189fa1c7225010d08",
+ "shasum": ""
+ },
+ "require": {
+ "php": "^7.0",
+ "phpdocumentor/reflection-common": "^1.0.0",
+ "phpdocumentor/type-resolver": "^0.4.0",
+ "webmozart/assert": "^1.0"
+ },
+ "require-dev": {
+ "doctrine/instantiator": "~1.0.5",
+ "mockery/mockery": "^1.0",
+ "phpunit/phpunit": "^6.4"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "4.x-dev"
+ }
+ },
+ "autoload": {
+ "psr-4": {
+ "phpDocumentor\\Reflection\\": [
+ "src/"
+ ]
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Mike van Riel",
+ "email": "me@mikevanriel.com"
+ }
+ ],
+ "description": "With this component, a library can provide support for annotations via DocBlocks or otherwise retrieve information that is embedded in a DocBlock.",
+ "time": "2017-11-30T07:14:17+00:00"
+ },
+ {
+ "name": "phpdocumentor/type-resolver",
+ "version": "0.4.0",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/phpDocumentor/TypeResolver.git",
+ "reference": "9c977708995954784726e25d0cd1dddf4e65b0f7"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/phpDocumentor/TypeResolver/zipball/9c977708995954784726e25d0cd1dddf4e65b0f7",
+ "reference": "9c977708995954784726e25d0cd1dddf4e65b0f7",
+ "shasum": ""
+ },
+ "require": {
+ "php": "^5.5 || ^7.0",
+ "phpdocumentor/reflection-common": "^1.0"
+ },
+ "require-dev": {
+ "mockery/mockery": "^0.9.4",
+ "phpunit/phpunit": "^5.2||^4.8.24"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "1.0.x-dev"
+ }
+ },
+ "autoload": {
+ "psr-4": {
+ "phpDocumentor\\Reflection\\": [
+ "src/"
+ ]
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Mike van Riel",
+ "email": "me@mikevanriel.com"
+ }
+ ],
+ "time": "2017-07-14T14:27:02+00:00"
+ },
+ {
+ "name": "phpspec/prophecy",
+ "version": "1.8.0",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/phpspec/prophecy.git",
+ "reference": "4ba436b55987b4bf311cb7c6ba82aa528aac0a06"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/phpspec/prophecy/zipball/4ba436b55987b4bf311cb7c6ba82aa528aac0a06",
+ "reference": "4ba436b55987b4bf311cb7c6ba82aa528aac0a06",
+ "shasum": ""
+ },
+ "require": {
+ "doctrine/instantiator": "^1.0.2",
+ "php": "^5.3|^7.0",
+ "phpdocumentor/reflection-docblock": "^2.0|^3.0.2|^4.0",
+ "sebastian/comparator": "^1.1|^2.0|^3.0",
+ "sebastian/recursion-context": "^1.0|^2.0|^3.0"
+ },
+ "require-dev": {
+ "phpspec/phpspec": "^2.5|^3.2",
+ "phpunit/phpunit": "^4.8.35 || ^5.7 || ^6.5 || ^7.1"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "1.8.x-dev"
+ }
+ },
+ "autoload": {
+ "psr-0": {
+ "Prophecy\\": "src/"
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Konstantin Kudryashov",
+ "email": "ever.zet@gmail.com",
+ "homepage": "http://everzet.com"
+ },
+ {
+ "name": "Marcello Duarte",
+ "email": "marcello.duarte@gmail.com"
+ }
+ ],
+ "description": "Highly opinionated mocking framework for PHP 5.3+",
+ "homepage": "https://github.com/phpspec/prophecy",
+ "keywords": [
+ "Double",
+ "Dummy",
+ "fake",
+ "mock",
+ "spy",
+ "stub"
+ ],
+ "time": "2018-08-05T17:53:17+00:00"
+ },
+ {
+ "name": "phpunit/php-code-coverage",
+ "version": "6.1.4",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/sebastianbergmann/php-code-coverage.git",
+ "reference": "807e6013b00af69b6c5d9ceb4282d0393dbb9d8d"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/sebastianbergmann/php-code-coverage/zipball/807e6013b00af69b6c5d9ceb4282d0393dbb9d8d",
+ "reference": "807e6013b00af69b6c5d9ceb4282d0393dbb9d8d",
+ "shasum": ""
+ },
+ "require": {
+ "ext-dom": "*",
+ "ext-xmlwriter": "*",
+ "php": "^7.1",
+ "phpunit/php-file-iterator": "^2.0",
+ "phpunit/php-text-template": "^1.2.1",
+ "phpunit/php-token-stream": "^3.0",
+ "sebastian/code-unit-reverse-lookup": "^1.0.1",
+ "sebastian/environment": "^3.1 || ^4.0",
+ "sebastian/version": "^2.0.1",
+ "theseer/tokenizer": "^1.1"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "^7.0"
+ },
+ "suggest": {
+ "ext-xdebug": "^2.6.0"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "6.1-dev"
+ }
+ },
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sebastian@phpunit.de",
+ "role": "lead"
+ }
+ ],
+ "description": "Library that provides collection, processing, and rendering functionality for PHP code coverage information.",
+ "homepage": "https://github.com/sebastianbergmann/php-code-coverage",
+ "keywords": [
+ "coverage",
+ "testing",
+ "xunit"
+ ],
+ "time": "2018-10-31T16:06:48+00:00"
+ },
+ {
+ "name": "phpunit/php-file-iterator",
+ "version": "2.0.2",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/sebastianbergmann/php-file-iterator.git",
+ "reference": "050bedf145a257b1ff02746c31894800e5122946"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/sebastianbergmann/php-file-iterator/zipball/050bedf145a257b1ff02746c31894800e5122946",
+ "reference": "050bedf145a257b1ff02746c31894800e5122946",
+ "shasum": ""
+ },
+ "require": {
+ "php": "^7.1"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "^7.1"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "2.0.x-dev"
+ }
+ },
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sebastian@phpunit.de",
+ "role": "lead"
+ }
+ ],
+ "description": "FilterIterator implementation that filters files based on a list of suffixes.",
+ "homepage": "https://github.com/sebastianbergmann/php-file-iterator/",
+ "keywords": [
+ "filesystem",
+ "iterator"
+ ],
+ "time": "2018-09-13T20:33:42+00:00"
+ },
+ {
+ "name": "phpunit/php-text-template",
+ "version": "1.2.1",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/sebastianbergmann/php-text-template.git",
+ "reference": "31f8b717e51d9a2afca6c9f046f5d69fc27c8686"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/sebastianbergmann/php-text-template/zipball/31f8b717e51d9a2afca6c9f046f5d69fc27c8686",
+ "reference": "31f8b717e51d9a2afca6c9f046f5d69fc27c8686",
+ "shasum": ""
+ },
+ "require": {
+ "php": ">=5.3.3"
+ },
+ "type": "library",
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sebastian@phpunit.de",
+ "role": "lead"
+ }
+ ],
+ "description": "Simple template engine.",
+ "homepage": "https://github.com/sebastianbergmann/php-text-template/",
+ "keywords": [
+ "template"
+ ],
+ "time": "2015-06-21T13:50:34+00:00"
+ },
+ {
+ "name": "phpunit/php-timer",
+ "version": "2.0.0",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/sebastianbergmann/php-timer.git",
+ "reference": "8b8454ea6958c3dee38453d3bd571e023108c91f"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/sebastianbergmann/php-timer/zipball/8b8454ea6958c3dee38453d3bd571e023108c91f",
+ "reference": "8b8454ea6958c3dee38453d3bd571e023108c91f",
+ "shasum": ""
+ },
+ "require": {
+ "php": "^7.1"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "^7.0"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "2.0-dev"
+ }
+ },
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sebastian@phpunit.de",
+ "role": "lead"
+ }
+ ],
+ "description": "Utility class for timing",
+ "homepage": "https://github.com/sebastianbergmann/php-timer/",
+ "keywords": [
+ "timer"
+ ],
+ "time": "2018-02-01T13:07:23+00:00"
+ },
+ {
+ "name": "phpunit/php-token-stream",
+ "version": "3.0.1",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/sebastianbergmann/php-token-stream.git",
+ "reference": "c99e3be9d3e85f60646f152f9002d46ed7770d18"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/sebastianbergmann/php-token-stream/zipball/c99e3be9d3e85f60646f152f9002d46ed7770d18",
+ "reference": "c99e3be9d3e85f60646f152f9002d46ed7770d18",
+ "shasum": ""
+ },
+ "require": {
+ "ext-tokenizer": "*",
+ "php": "^7.1"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "^7.0"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "3.0-dev"
+ }
+ },
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sebastian@phpunit.de"
+ }
+ ],
+ "description": "Wrapper around PHP's tokenizer extension.",
+ "homepage": "https://github.com/sebastianbergmann/php-token-stream/",
+ "keywords": [
+ "tokenizer"
+ ],
+ "time": "2018-10-30T05:52:18+00:00"
+ },
+ {
+ "name": "phpunit/phpunit",
+ "version": "7.5.4",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/sebastianbergmann/phpunit.git",
+ "reference": "2896657da5fb237bc316bdfc18c2650efeee0dc0"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/sebastianbergmann/phpunit/zipball/2896657da5fb237bc316bdfc18c2650efeee0dc0",
+ "reference": "2896657da5fb237bc316bdfc18c2650efeee0dc0",
+ "shasum": ""
+ },
+ "require": {
+ "doctrine/instantiator": "^1.1",
+ "ext-dom": "*",
+ "ext-json": "*",
+ "ext-libxml": "*",
+ "ext-mbstring": "*",
+ "ext-xml": "*",
+ "myclabs/deep-copy": "^1.7",
+ "phar-io/manifest": "^1.0.2",
+ "phar-io/version": "^2.0",
+ "php": "^7.1",
+ "phpspec/prophecy": "^1.7",
+ "phpunit/php-code-coverage": "^6.0.7",
+ "phpunit/php-file-iterator": "^2.0.1",
+ "phpunit/php-text-template": "^1.2.1",
+ "phpunit/php-timer": "^2.0",
+ "sebastian/comparator": "^3.0",
+ "sebastian/diff": "^3.0",
+ "sebastian/environment": "^4.0",
+ "sebastian/exporter": "^3.1",
+ "sebastian/global-state": "^2.0",
+ "sebastian/object-enumerator": "^3.0.3",
+ "sebastian/resource-operations": "^2.0",
+ "sebastian/version": "^2.0.1"
+ },
+ "conflict": {
+ "phpunit/phpunit-mock-objects": "*"
+ },
+ "require-dev": {
+ "ext-pdo": "*"
+ },
+ "suggest": {
+ "ext-soap": "*",
+ "ext-xdebug": "*",
+ "phpunit/php-invoker": "^2.0"
+ },
+ "bin": [
+ "phpunit"
+ ],
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "7.5-dev"
+ }
+ },
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sebastian@phpunit.de",
+ "role": "lead"
+ }
+ ],
+ "description": "The PHP Unit Testing framework.",
+ "homepage": "https://phpunit.de/",
+ "keywords": [
+ "phpunit",
+ "testing",
+ "xunit"
+ ],
+ "time": "2019-02-07T14:15:04+00:00"
+ },
+ {
+ "name": "sebastian/code-unit-reverse-lookup",
+ "version": "1.0.1",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/sebastianbergmann/code-unit-reverse-lookup.git",
+ "reference": "4419fcdb5eabb9caa61a27c7a1db532a6b55dd18"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/sebastianbergmann/code-unit-reverse-lookup/zipball/4419fcdb5eabb9caa61a27c7a1db532a6b55dd18",
+ "reference": "4419fcdb5eabb9caa61a27c7a1db532a6b55dd18",
+ "shasum": ""
+ },
+ "require": {
+ "php": "^5.6 || ^7.0"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "^5.7 || ^6.0"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "1.0.x-dev"
+ }
+ },
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sebastian@phpunit.de"
+ }
+ ],
+ "description": "Looks up which function or method a line of code belongs to",
+ "homepage": "https://github.com/sebastianbergmann/code-unit-reverse-lookup/",
+ "time": "2017-03-04T06:30:41+00:00"
+ },
+ {
+ "name": "sebastian/comparator",
+ "version": "3.0.2",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/sebastianbergmann/comparator.git",
+ "reference": "5de4fc177adf9bce8df98d8d141a7559d7ccf6da"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/sebastianbergmann/comparator/zipball/5de4fc177adf9bce8df98d8d141a7559d7ccf6da",
+ "reference": "5de4fc177adf9bce8df98d8d141a7559d7ccf6da",
+ "shasum": ""
+ },
+ "require": {
+ "php": "^7.1",
+ "sebastian/diff": "^3.0",
+ "sebastian/exporter": "^3.1"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "^7.1"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "3.0-dev"
+ }
+ },
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Jeff Welch",
+ "email": "whatthejeff@gmail.com"
+ },
+ {
+ "name": "Volker Dusch",
+ "email": "github@wallbash.com"
+ },
+ {
+ "name": "Bernhard Schussek",
+ "email": "bschussek@2bepublished.at"
+ },
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sebastian@phpunit.de"
+ }
+ ],
+ "description": "Provides the functionality to compare PHP values for equality",
+ "homepage": "https://github.com/sebastianbergmann/comparator",
+ "keywords": [
+ "comparator",
+ "compare",
+ "equality"
+ ],
+ "time": "2018-07-12T15:12:46+00:00"
+ },
+ {
+ "name": "sebastian/diff",
+ "version": "3.0.2",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/sebastianbergmann/diff.git",
+ "reference": "720fcc7e9b5cf384ea68d9d930d480907a0c1a29"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/sebastianbergmann/diff/zipball/720fcc7e9b5cf384ea68d9d930d480907a0c1a29",
+ "reference": "720fcc7e9b5cf384ea68d9d930d480907a0c1a29",
+ "shasum": ""
+ },
+ "require": {
+ "php": "^7.1"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "^7.5 || ^8.0",
+ "symfony/process": "^2 || ^3.3 || ^4"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "3.0-dev"
+ }
+ },
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Kore Nordmann",
+ "email": "mail@kore-nordmann.de"
+ },
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sebastian@phpunit.de"
+ }
+ ],
+ "description": "Diff implementation",
+ "homepage": "https://github.com/sebastianbergmann/diff",
+ "keywords": [
+ "diff",
+ "udiff",
+ "unidiff",
+ "unified diff"
+ ],
+ "time": "2019-02-04T06:01:07+00:00"
+ },
+ {
+ "name": "sebastian/environment",
+ "version": "4.1.0",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/sebastianbergmann/environment.git",
+ "reference": "6fda8ce1974b62b14935adc02a9ed38252eca656"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/sebastianbergmann/environment/zipball/6fda8ce1974b62b14935adc02a9ed38252eca656",
+ "reference": "6fda8ce1974b62b14935adc02a9ed38252eca656",
+ "shasum": ""
+ },
+ "require": {
+ "php": "^7.1"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "^7.5"
+ },
+ "suggest": {
+ "ext-posix": "*"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "4.1-dev"
+ }
+ },
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sebastian@phpunit.de"
+ }
+ ],
+ "description": "Provides functionality to handle HHVM/PHP environments",
+ "homepage": "http://www.github.com/sebastianbergmann/environment",
+ "keywords": [
+ "Xdebug",
+ "environment",
+ "hhvm"
+ ],
+ "time": "2019-02-01T05:27:49+00:00"
+ },
+ {
+ "name": "sebastian/exporter",
+ "version": "3.1.0",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/sebastianbergmann/exporter.git",
+ "reference": "234199f4528de6d12aaa58b612e98f7d36adb937"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/sebastianbergmann/exporter/zipball/234199f4528de6d12aaa58b612e98f7d36adb937",
+ "reference": "234199f4528de6d12aaa58b612e98f7d36adb937",
+ "shasum": ""
+ },
+ "require": {
+ "php": "^7.0",
+ "sebastian/recursion-context": "^3.0"
+ },
+ "require-dev": {
+ "ext-mbstring": "*",
+ "phpunit/phpunit": "^6.0"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "3.1.x-dev"
+ }
+ },
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Jeff Welch",
+ "email": "whatthejeff@gmail.com"
+ },
+ {
+ "name": "Volker Dusch",
+ "email": "github@wallbash.com"
+ },
+ {
+ "name": "Bernhard Schussek",
+ "email": "bschussek@2bepublished.at"
+ },
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sebastian@phpunit.de"
+ },
+ {
+ "name": "Adam Harvey",
+ "email": "aharvey@php.net"
+ }
+ ],
+ "description": "Provides the functionality to export PHP variables for visualization",
+ "homepage": "http://www.github.com/sebastianbergmann/exporter",
+ "keywords": [
+ "export",
+ "exporter"
+ ],
+ "time": "2017-04-03T13:19:02+00:00"
+ },
+ {
+ "name": "sebastian/global-state",
+ "version": "2.0.0",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/sebastianbergmann/global-state.git",
+ "reference": "e8ba02eed7bbbb9e59e43dedd3dddeff4a56b0c4"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/sebastianbergmann/global-state/zipball/e8ba02eed7bbbb9e59e43dedd3dddeff4a56b0c4",
+ "reference": "e8ba02eed7bbbb9e59e43dedd3dddeff4a56b0c4",
+ "shasum": ""
+ },
+ "require": {
+ "php": "^7.0"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "^6.0"
+ },
+ "suggest": {
+ "ext-uopz": "*"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "2.0-dev"
+ }
+ },
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sebastian@phpunit.de"
+ }
+ ],
+ "description": "Snapshotting of global state",
+ "homepage": "http://www.github.com/sebastianbergmann/global-state",
+ "keywords": [
+ "global state"
+ ],
+ "time": "2017-04-27T15:39:26+00:00"
+ },
+ {
+ "name": "sebastian/object-enumerator",
+ "version": "3.0.3",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/sebastianbergmann/object-enumerator.git",
+ "reference": "7cfd9e65d11ffb5af41198476395774d4c8a84c5"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/sebastianbergmann/object-enumerator/zipball/7cfd9e65d11ffb5af41198476395774d4c8a84c5",
+ "reference": "7cfd9e65d11ffb5af41198476395774d4c8a84c5",
+ "shasum": ""
+ },
+ "require": {
+ "php": "^7.0",
+ "sebastian/object-reflector": "^1.1.1",
+ "sebastian/recursion-context": "^3.0"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "^6.0"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "3.0.x-dev"
+ }
+ },
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sebastian@phpunit.de"
+ }
+ ],
+ "description": "Traverses array structures and object graphs to enumerate all referenced objects",
+ "homepage": "https://github.com/sebastianbergmann/object-enumerator/",
+ "time": "2017-08-03T12:35:26+00:00"
+ },
+ {
+ "name": "sebastian/object-reflector",
+ "version": "1.1.1",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/sebastianbergmann/object-reflector.git",
+ "reference": "773f97c67f28de00d397be301821b06708fca0be"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/sebastianbergmann/object-reflector/zipball/773f97c67f28de00d397be301821b06708fca0be",
+ "reference": "773f97c67f28de00d397be301821b06708fca0be",
+ "shasum": ""
+ },
+ "require": {
+ "php": "^7.0"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "^6.0"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "1.1-dev"
+ }
+ },
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sebastian@phpunit.de"
+ }
+ ],
+ "description": "Allows reflection of object attributes, including inherited and non-public ones",
+ "homepage": "https://github.com/sebastianbergmann/object-reflector/",
+ "time": "2017-03-29T09:07:27+00:00"
+ },
+ {
+ "name": "sebastian/recursion-context",
+ "version": "3.0.0",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/sebastianbergmann/recursion-context.git",
+ "reference": "5b0cd723502bac3b006cbf3dbf7a1e3fcefe4fa8"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/sebastianbergmann/recursion-context/zipball/5b0cd723502bac3b006cbf3dbf7a1e3fcefe4fa8",
+ "reference": "5b0cd723502bac3b006cbf3dbf7a1e3fcefe4fa8",
+ "shasum": ""
+ },
+ "require": {
+ "php": "^7.0"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "^6.0"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "3.0.x-dev"
+ }
+ },
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Jeff Welch",
+ "email": "whatthejeff@gmail.com"
+ },
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sebastian@phpunit.de"
+ },
+ {
+ "name": "Adam Harvey",
+ "email": "aharvey@php.net"
+ }
+ ],
+ "description": "Provides functionality to recursively process PHP variables",
+ "homepage": "http://www.github.com/sebastianbergmann/recursion-context",
+ "time": "2017-03-03T06:23:57+00:00"
+ },
+ {
+ "name": "sebastian/resource-operations",
+ "version": "2.0.1",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/sebastianbergmann/resource-operations.git",
+ "reference": "4d7a795d35b889bf80a0cc04e08d77cedfa917a9"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/sebastianbergmann/resource-operations/zipball/4d7a795d35b889bf80a0cc04e08d77cedfa917a9",
+ "reference": "4d7a795d35b889bf80a0cc04e08d77cedfa917a9",
+ "shasum": ""
+ },
+ "require": {
+ "php": "^7.1"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "2.0-dev"
+ }
+ },
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sebastian@phpunit.de"
+ }
+ ],
+ "description": "Provides a list of PHP built-in functions that operate on resources",
+ "homepage": "https://www.github.com/sebastianbergmann/resource-operations",
+ "time": "2018-10-04T04:07:39+00:00"
+ },
+ {
+ "name": "sebastian/version",
+ "version": "2.0.1",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/sebastianbergmann/version.git",
+ "reference": "99732be0ddb3361e16ad77b68ba41efc8e979019"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/sebastianbergmann/version/zipball/99732be0ddb3361e16ad77b68ba41efc8e979019",
+ "reference": "99732be0ddb3361e16ad77b68ba41efc8e979019",
+ "shasum": ""
+ },
+ "require": {
+ "php": ">=5.6"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "2.0.x-dev"
+ }
+ },
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sebastian@phpunit.de",
+ "role": "lead"
+ }
+ ],
+ "description": "Library that helps with managing the version number of Git-hosted PHP projects",
+ "homepage": "https://github.com/sebastianbergmann/version",
+ "time": "2016-10-03T07:35:21+00:00"
+ },
+ {
+ "name": "soundasleep/component-tests",
+ "version": "0.2.0",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/soundasleep/component-tests.git",
+ "reference": "7525ffd30ad2406f745ff94729717fe7bbfa2466"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/soundasleep/component-tests/zipball/7525ffd30ad2406f745ff94729717fe7bbfa2466",
+ "reference": "7525ffd30ad2406f745ff94729717fe7bbfa2466",
+ "shasum": ""
+ },
+ "require": {
+ "justinrainbow/json-schema": "~5.2",
+ "phpunit/phpunit": "~7.0"
+ },
+ "type": "library",
+ "autoload": {
+ "psr-4": {
+ "ComponentTests\\": "src"
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "description": "Common Composer and PHP component lint and validation tests",
+ "time": "2019-02-13T21:21:24+00:00"
+ },
+ {
+ "name": "symfony/polyfill-ctype",
+ "version": "v1.10.0",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/symfony/polyfill-ctype.git",
+ "reference": "e3d826245268269cd66f8326bd8bc066687b4a19"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/symfony/polyfill-ctype/zipball/e3d826245268269cd66f8326bd8bc066687b4a19",
+ "reference": "e3d826245268269cd66f8326bd8bc066687b4a19",
+ "shasum": ""
+ },
+ "require": {
+ "php": ">=5.3.3"
+ },
+ "suggest": {
+ "ext-ctype": "For best performance"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "1.9-dev"
+ }
+ },
+ "autoload": {
+ "psr-4": {
+ "Symfony\\Polyfill\\Ctype\\": ""
+ },
+ "files": [
+ "bootstrap.php"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Symfony Community",
+ "homepage": "https://symfony.com/contributors"
+ },
+ {
+ "name": "Gert de Pagter",
+ "email": "BackEndTea@gmail.com"
+ }
+ ],
+ "description": "Symfony polyfill for ctype functions",
+ "homepage": "https://symfony.com",
+ "keywords": [
+ "compatibility",
+ "ctype",
+ "polyfill",
+ "portable"
+ ],
+ "time": "2018-08-06T14:22:27+00:00"
+ },
+ {
+ "name": "theseer/tokenizer",
+ "version": "1.1.0",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/theseer/tokenizer.git",
+ "reference": "cb2f008f3f05af2893a87208fe6a6c4985483f8b"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/theseer/tokenizer/zipball/cb2f008f3f05af2893a87208fe6a6c4985483f8b",
+ "reference": "cb2f008f3f05af2893a87208fe6a6c4985483f8b",
+ "shasum": ""
+ },
+ "require": {
+ "ext-dom": "*",
+ "ext-tokenizer": "*",
+ "ext-xmlwriter": "*",
+ "php": "^7.0"
+ },
+ "type": "library",
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Arne Blankerts",
+ "email": "arne@blankerts.de",
+ "role": "Developer"
+ }
+ ],
+ "description": "A small library for converting tokenized PHP source code into XML and potentially other formats",
+ "time": "2017-04-07T12:08:54+00:00"
+ },
+ {
+ "name": "webmozart/assert",
+ "version": "1.4.0",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/webmozart/assert.git",
+ "reference": "83e253c8e0be5b0257b881e1827274667c5c17a9"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/webmozart/assert/zipball/83e253c8e0be5b0257b881e1827274667c5c17a9",
+ "reference": "83e253c8e0be5b0257b881e1827274667c5c17a9",
+ "shasum": ""
+ },
+ "require": {
+ "php": "^5.3.3 || ^7.0",
+ "symfony/polyfill-ctype": "^1.8"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "^4.6",
+ "sebastian/version": "^1.0.1"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "1.3-dev"
+ }
+ },
+ "autoload": {
+ "psr-4": {
+ "Webmozart\\Assert\\": "src/"
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Bernhard Schussek",
+ "email": "bschussek@gmail.com"
+ }
+ ],
+ "description": "Assertions to validate method input/output with nice error messages.",
+ "keywords": [
+ "assert",
+ "check",
+ "validate"
+ ],
+ "time": "2018-12-25T11:19:39+00:00"
+ }
+ ],
+ "aliases": [],
+ "minimum-stability": "stable",
+ "stability-flags": [],
+ "prefer-stable": false,
+ "prefer-lowest": false,
+ "platform": {
+ "php": ">=7.0",
+ "ext-dom": "*",
+ "ext-libxml": "*"
+ },
+ "platform-dev": []
+}
diff --git a/lib/soundasleep/html2text/convert.php b/lib/soundasleep/html2text/convert.php
new file mode 100644
index 000000000..48094eb21
--- /dev/null
+++ b/lib/soundasleep/html2text/convert.php
@@ -0,0 +1,21 @@
+
+
+
+
+ tests
+
+
+
diff --git a/lib/soundasleep/html2text/src/Html2Text.php b/lib/soundasleep/html2text/src/Html2Text.php
new file mode 100644
index 000000000..5153cefcf
--- /dev/null
+++ b/lib/soundasleep/html2text/src/Html2Text.php
@@ -0,0 +1,505 @@
+ false,
+ 'drop_links' => false,
+ );
+ }
+
+ /**
+ * Tries to convert the given HTML into a plain text format - best suited for
+ * e-mail display, etc.
+ *
+ * In particular, it tries to maintain the following features:
+ *
+ * - Links are maintained, with the 'href' copied over
+ *
- Information in the <head> is lost
+ *
+ *
+ * @param string $html the input HTML
+ * @param boolean $ignore_error Ignore xml parsing errors
+ * @return string the HTML converted, as best as possible, to text
+ * @throws Html2TextException if the HTML could not be loaded as a {@link \DOMDocument}
+ */
+ public static function convert($html, $options = array()) {
+
+ if ($options === false || $options === true) {
+ // Using old style (< 1.0) of passing in options
+ $options = array('ignore_errors' => $options);
+ }
+
+ $options = array_merge(static::defaultOptions(), $options);
+
+ // check all options are valid
+ foreach ($options as $key => $value) {
+ if (!in_array($key, array_keys(static::defaultOptions()))) {
+ throw new \InvalidArgumentException("Unknown html2text option '$key'");
+ }
+ }
+
+ $is_office_document = static::isOfficeDocument($html);
+
+ if ($is_office_document) {
+ // remove office namespace
+ $html = str_replace(array("", ""), "", $html);
+ }
+
+ $html = static::fixNewlines($html);
+ if (mb_detect_encoding($html, "UTF-8", true)) {
+ $html = mb_convert_encoding($html, "HTML-ENTITIES", "UTF-8");
+ }
+
+ $doc = static::getDocument($html, $options['ignore_errors']);
+
+ $output = static::iterateOverNode($doc, null, false, $is_office_document, $options);
+
+ // process output for whitespace/newlines
+ $output = static::processWhitespaceNewlines($output);
+
+ return $output;
+ }
+
+ /**
+ * Unify newlines; in particular, \r\n becomes \n, and
+ * then \r becomes \n. This means that all newlines (Unix, Windows, Mac)
+ * all become \ns.
+ *
+ * @param string $text text with any number of \r, \r\n and \n combinations
+ * @return string the fixed text
+ */
+ static function fixNewlines($text) {
+ // replace \r\n to \n
+ $text = str_replace("\r\n", "\n", $text);
+ // remove \rs
+ $text = str_replace("\r", "\n", $text);
+
+ return $text;
+ }
+
+ static function nbspCodes() {
+ return array(
+ "\xc2\xa0",
+ "\u00a0",
+ );
+ }
+
+ static function zwnjCodes() {
+ return array(
+ "\xe2\x80\x8c",
+ "\u200c",
+ );
+ }
+
+ /**
+ * Remove leading or trailing spaces and excess empty lines from provided multiline text
+ *
+ * @param string $text multiline text any number of leading or trailing spaces or excess lines
+ * @return string the fixed text
+ */
+ static function processWhitespaceNewlines($text) {
+
+ // remove excess spaces around tabs
+ $text = preg_replace("/ *\t */im", "\t", $text);
+
+ // remove leading whitespace
+ $text = ltrim($text);
+
+ // remove leading spaces on each line
+ $text = preg_replace("/\n[ \t]*/im", "\n", $text);
+
+ // convert non-breaking spaces to regular spaces to prevent output issues,
+ // do it here so they do NOT get removed with other leading spaces, as they
+ // are sometimes used for indentation
+ $text = static::renderText($text);
+
+ // remove trailing whitespace
+ $text = rtrim($text);
+
+ // remove trailing spaces on each line
+ $text = preg_replace("/[ \t]*\n/im", "\n", $text);
+
+ // unarmor pre blocks
+ $text = static::fixNewLines($text);
+
+ // remove unnecessary empty lines
+ $text = preg_replace("/\n\n\n*/im", "\n\n", $text);
+
+ return $text;
+ }
+
+ /**
+ * Parse HTML into a DOMDocument
+ *
+ * @param string $html the input HTML
+ * @param boolean $ignore_error Ignore xml parsing errors
+ * @return \DOMDocument the parsed document tree
+ */
+ static function getDocument($html, $ignore_error = false) {
+
+ $doc = new \DOMDocument();
+
+ $html = trim($html);
+
+ if (!$html) {
+ // DOMDocument doesn't support empty value and throws an error
+ // Return empty document instead
+ return $doc;
+ }
+
+ if ($html[0] !== '<') {
+ // If HTML does not begin with a tag, we put a body tag around it.
+ // If we do not do this, PHP will insert a paragraph tag around
+ // the first block of text for some reason which can mess up
+ // the newlines. See pre.html test for an example.
+ $html = '' . $html . '';
+ }
+
+ if ($ignore_error) {
+ $doc->strictErrorChecking = false;
+ $doc->recover = true;
+ $doc->xmlStandalone = true;
+ $old_internal_errors = libxml_use_internal_errors(true);
+ $load_result = $doc->loadHTML($html, LIBXML_NOWARNING | LIBXML_NOERROR | LIBXML_NONET | LIBXML_PARSEHUGE);
+ libxml_use_internal_errors($old_internal_errors);
+ }
+ else {
+ $load_result = $doc->loadHTML($html);
+ }
+
+ if (!$load_result) {
+ throw new Html2TextException("Could not load HTML - badly formed?", $html);
+ }
+
+ return $doc;
+ }
+
+ /**
+ * Can we guess that this HTML is generated by Microsoft Office?
+ */
+ static function isOfficeDocument($html) {
+ return strpos($html, "urn:schemas-microsoft-com:office") !== false;
+ }
+
+ /**
+ * Replace any special characters with simple text versions, to prevent output issues:
+ * - Convert non-breaking spaces to regular spaces; and
+ * - Convert zero-width non-joiners to '' (nothing).
+ *
+ * This is to match our goal of rendering documents as they would be rendered
+ * by a browser.
+ */
+ static function renderText($text) {
+ $text = str_replace(static::nbspCodes(), " ", $text);
+ $text = str_replace(static::zwnjCodes(), "", $text);
+ return $text;
+ }
+
+ static function isWhitespace($text) {
+ return strlen(trim(static::renderText($text), "\n\r\t ")) === 0;
+ }
+
+ static function nextChildName($node) {
+ // get the next child
+ $nextNode = $node->nextSibling;
+ while ($nextNode != null) {
+ if ($nextNode instanceof \DOMText) {
+ if (!static::isWhitespace($nextNode->wholeText)) {
+ break;
+ }
+ }
+
+ if ($nextNode instanceof \DOMElement) {
+ break;
+ }
+
+ $nextNode = $nextNode->nextSibling;
+ }
+
+ $nextName = null;
+ if (($nextNode instanceof \DOMElement || $nextNode instanceof \DOMText) && $nextNode != null) {
+ $nextName = strtolower($nextNode->nodeName);
+ }
+
+ return $nextName;
+ }
+
+ static function iterateOverNode($node, $prevName = null, $in_pre = false, $is_office_document = false, $options) {
+ if ($node instanceof \DOMText) {
+ // Replace whitespace characters with a space (equivilant to \s)
+ if ($in_pre) {
+ $text = "\n" . trim(static::renderText($node->wholeText), "\n\r\t ") . "\n";
+
+ // Remove trailing whitespace only
+ $text = preg_replace("/[ \t]*\n/im", "\n", $text);
+
+ // armor newlines with \r.
+ return str_replace("\n", "\r", $text);
+
+ } else {
+ $text = static::renderText($node->wholeText);
+ $text = preg_replace("/[\\t\\n\\f\\r ]+/im", " ", $text);
+
+ if (!static::isWhitespace($text) && ($prevName == 'p' || $prevName == 'div')) {
+ return "\n" . $text;
+ }
+ return $text;
+ }
+ }
+
+ if ($node instanceof \DOMDocumentType || $node instanceof \DOMProcessingInstruction) {
+ // ignore
+ return "";
+ }
+
+ $name = strtolower($node->nodeName);
+ $nextName = static::nextChildName($node);
+
+ // start whitespace
+ switch ($name) {
+ case "hr":
+ $prefix = '';
+ if ($prevName != null) {
+ $prefix = "\n";
+ }
+ return $prefix . "---------------------------------------------------------------\n";
+
+ case "style":
+ case "head":
+ case "title":
+ case "meta":
+ case "script":
+ // ignore these tags
+ return "";
+
+ case "h1":
+ case "h2":
+ case "h3":
+ case "h4":
+ case "h5":
+ case "h6":
+ case "ol":
+ case "ul":
+ case "pre":
+ // add two newlines
+ $output = "\n\n";
+ break;
+
+ case "td":
+ case "th":
+ // add tab char to separate table fields
+ $output = "\t";
+ break;
+
+ case "p":
+ // Microsoft exchange emails often include HTML which, when passed through
+ // html2text, results in lots of double line returns everywhere.
+ //
+ // To fix this, for any p element with a className of `MsoNormal` (the standard
+ // classname in any Microsoft export or outlook for a paragraph that behaves
+ // like a line return) we skip the first line returns and set the name to br.
+ if ($is_office_document && $node->getAttribute('class') == 'MsoNormal') {
+ $output = "";
+ $name = 'br';
+ break;
+ }
+
+ // add two lines
+ $output = "\n\n";
+ break;
+
+ case "tr":
+ // add one line
+ $output = "\n";
+ break;
+
+ case "div":
+ $output = "";
+ if ($prevName !== null) {
+ // add one line
+ $output .= "\n";
+ }
+ break;
+
+ case "li":
+ $output = "- ";
+ break;
+
+ default:
+ // print out contents of unknown tags
+ $output = "";
+ break;
+ }
+
+ // debug
+ //$output .= "[$name,$nextName]";
+
+ if (isset($node->childNodes)) {
+
+ $n = $node->childNodes->item(0);
+ $previousSiblingNames = array();
+ $previousSiblingName = null;
+
+ $parts = array();
+ $trailing_whitespace = 0;
+
+ while ($n != null) {
+
+ $text = static::iterateOverNode($n, $previousSiblingName, $in_pre || $name == 'pre', $is_office_document, $options);
+
+ // Pass current node name to next child, as previousSibling does not appear to get populated
+ if ($n instanceof \DOMDocumentType
+ || $n instanceof \DOMProcessingInstruction
+ || ($n instanceof \DOMText && static::isWhitespace($text))) {
+ // Keep current previousSiblingName, these are invisible
+ $trailing_whitespace++;
+ }
+ else {
+ $previousSiblingName = strtolower($n->nodeName);
+ $previousSiblingNames[] = $previousSiblingName;
+ $trailing_whitespace = 0;
+ }
+
+ $node->removeChild($n);
+ $n = $node->childNodes->item(0);
+
+ $parts[] = $text;
+ }
+
+ // Remove trailing whitespace, important for the br check below
+ while ($trailing_whitespace-- > 0) {
+ array_pop($parts);
+ }
+
+ // suppress last br tag inside a node list if follows text
+ $last_name = array_pop($previousSiblingNames);
+ if ($last_name === 'br') {
+ $last_name = array_pop($previousSiblingNames);
+ if ($last_name === '#text') {
+ array_pop($parts);
+ }
+ }
+
+ $output .= implode('', $parts);
+ }
+
+ // end whitespace
+ switch ($name) {
+ case "h1":
+ case "h2":
+ case "h3":
+ case "h4":
+ case "h5":
+ case "h6":
+ case "pre":
+ case "p":
+ // add two lines
+ $output .= "\n\n";
+ break;
+
+ case "br":
+ // add one line
+ $output .= "\n";
+ break;
+
+ case "div":
+ break;
+
+ case "a":
+ // links are returned in [text](link) format
+ $href = $node->getAttribute("href");
+
+ $output = trim($output);
+
+ // remove double [[ ]] s from linking images
+ if (substr($output, 0, 1) == "[" && substr($output, -1) == "]") {
+ $output = substr($output, 1, strlen($output) - 2);
+
+ // for linking images, the title of the overrides the title of the
+ if ($node->getAttribute("title")) {
+ $output = $node->getAttribute("title");
+ }
+ }
+
+ // if there is no link text, but a title attr
+ if (!$output && $node->getAttribute("title")) {
+ $output = $node->getAttribute("title");
+ }
+
+ if ($href == null) {
+ // it doesn't link anywhere
+ if ($node->getAttribute("name") != null) {
+ if ($options['drop_links']) {
+ $output = "$output";
+ } else {
+ $output = "[$output]";
+ }
+ }
+ } else {
+ if ($href == $output || $href == "mailto:$output" || $href == "http://$output" || $href == "https://$output") {
+ // link to the same address: just use link
+ $output = "$output";
+ } else {
+ // replace it
+ if ($output) {
+ if ($options['drop_links']) {
+ $output = "$output";
+ } else {
+ $output = "[$output]($href)";
+ }
+ } else {
+ // empty string
+ $output = "$href";
+ }
+ }
+ }
+
+ // does the next node require additional whitespace?
+ switch ($nextName) {
+ case "h1": case "h2": case "h3": case "h4": case "h5": case "h6":
+ $output .= "\n";
+ break;
+ }
+ break;
+
+ case "img":
+ if ($node->getAttribute("title")) {
+ $output = "[" . $node->getAttribute("title") . "]";
+ } elseif ($node->getAttribute("alt")) {
+ $output = "[" . $node->getAttribute("alt") . "]";
+ } else {
+ $output = "";
+ }
+ break;
+
+ case "li":
+ $output .= "\n";
+ break;
+
+ case "blockquote":
+ // process quoted text for whitespace/newlines
+ $output = static::processWhitespaceNewlines($output);
+
+ // add leading newline
+ $output = "\n" . $output;
+
+ // prepend '> ' at the beginning of all lines
+ $output = preg_replace("/\n/im", "\n> ", $output);
+
+ // replace leading '> >' with '>>'
+ $output = preg_replace("/\n> >/im", "\n>>", $output);
+
+ // add another leading newline and trailing newlines
+ $output = "\n" . $output . "\n\n";
+ break;
+ default:
+ // do nothing
+ }
+
+ return $output;
+ }
+}
diff --git a/lib/soundasleep/html2text/src/Html2TextException.php b/lib/soundasleep/html2text/src/Html2TextException.php
new file mode 100644
index 000000000..9171d86ea
--- /dev/null
+++ b/lib/soundasleep/html2text/src/Html2TextException.php
@@ -0,0 +1,14 @@
+more_info = $more_info;
+ }
+
+}
diff --git a/tests/php-unit-tests/unitary-tests/core/ActionEmailTest.php b/tests/php-unit-tests/unitary-tests/core/ActionEmailTest.php
index 41901e46e..afca36584 100644
--- a/tests/php-unit-tests/unitary-tests/core/ActionEmailTest.php
+++ b/tests/php-unit-tests/unitary-tests/core/ActionEmailTest.php
@@ -4,10 +4,10 @@ namespace Combodo\iTop\Test\UnitTest\Core;
use ActionEmail;
use Combodo\iTop\Test\UnitTest\ItopDataTestCase;
+use Dict;
use Exception;
use MetaModel;
use utils;
-use Dict;
/**
* @covers \ActionEmail
@@ -35,8 +35,6 @@ class ActionEmailTest extends ItopDataTestCase
{
parent::setUp();
- $this->RequireOnceItopFile('application/Html2Text.php');
-
static::$oActionEmail = MetaModel::NewObject('ActionEmail', [
'name' => 'Test action',
'status' => 'disabled',