diff --git a/civicrm.php b/civicrm.php
index 78db7da479460fc16dda05e375ca4d440dc25cd3..ddda411b20fedefac72eb72a37a940f88226b928 100644
--- a/civicrm.php
+++ b/civicrm.php
@@ -2,7 +2,7 @@
 /*
 Plugin Name: CiviCRM
 Description: CiviCRM - Growing and Sustaining Relationships
-Version: 5.24.2
+Version: 5.24.3
 Author: CiviCRM LLC
 Author URI: https://civicrm.org/
 Plugin URI: https://docs.civicrm.org/sysadmin/en/latest/install/wordpress/
@@ -54,7 +54,7 @@ if ( ! defined( 'ABSPATH' ) ) exit;
 
 
 // Set version here: when it changes, will force JS to reload
-define( 'CIVICRM_PLUGIN_VERSION', '5.24.2' );
+define( 'CIVICRM_PLUGIN_VERSION', '5.24.3' );
 
 // Store reference to this file
 if (!defined('CIVICRM_PLUGIN_FILE')) {
@@ -121,17 +121,6 @@ if ( file_exists( CIVICRM_SETTINGS_PATH )  ) {
 // Prevent CiviCRM from rendering its own header
 define( 'CIVICRM_UF_HEAD', TRUE );
 
-/**
- * Setting this to 'true' will replace all mailing URLs calls to 'extern/url.php'
- * and 'extern/open.php' with their REST counterpart 'civicrm/v3/url' and 'civicrm/v3/open'.
- *
- * Use for test purposes, may affect mailing
- * performance, see Plugin->replace_tracking_urls() method.
- */
-if ( ! defined( 'CIVICRM_WP_REST_REPLACE_MAILING_TRACKING' ) ) {
-  define( 'CIVICRM_WP_REST_REPLACE_MAILING_TRACKING', false );
-}
-
 
 /**
  * Define CiviCRM_For_WordPress Class.
@@ -203,15 +192,6 @@ class CiviCRM_For_WordPress {
    */
   public $users;
 
-  /**
-   * Compatibility object.
-   *
-   * @since 5.24
-   * @access public
-   * @var object CiviCRM_For_WordPress_Compat The plugin compatibility object.
-   */
-  public $compat;
-
 
   // ---------------------------------------------------------------------------
   // Setup
@@ -532,15 +512,6 @@ class CiviCRM_For_WordPress {
     include_once CIVICRM_PLUGIN_DIR . 'includes/civicrm.basepage.php';
     $this->basepage = new CiviCRM_For_WordPress_Basepage;
 
-    // Include compatibility class
-    include_once CIVICRM_PLUGIN_DIR . 'includes/civicrm.compat.php';
-    $this->compat = new CiviCRM_For_WordPress_Compat;
-
-    if ( ! class_exists( 'CiviCRM_WP_REST\Autoloader' ) ) {
-      // Include REST API autoloader class
-      require_once( CIVICRM_PLUGIN_DIR . 'wp-rest/Autoloader.php' );
-    }
-
   }
 
 
@@ -665,16 +636,6 @@ class CiviCRM_For_WordPress {
     // Register hooks for clean URLs.
     $this->register_hooks_clean_urls();
 
-    if ( ! class_exists( 'CiviCRM_WP_REST\Plugin' ) ) {
-
-      // Set up REST API.
-      CiviCRM_WP_REST\Autoloader::add_source( $source_path = trailingslashit( CIVICRM_PLUGIN_DIR . 'wp-rest' ) );
-
-      // Init REST API.
-      new CiviCRM_WP_REST\Plugin;
-
-    }
-
   }
 
 
@@ -822,12 +783,10 @@ class CiviCRM_For_WordPress {
      * Broadcast the rewrite rules event.
      *
      * @since 5.7
-     * @since 5.24 Added $basepage parameter.
      *
      * @param bool $flush_rewrite_rules True if rules flushed, false otherwise.
-     * @param WP_Post $basepage The Basepage post object.
      */
-    do_action( 'civicrm_after_rewrite_rules', $flush_rewrite_rules, $basepage );
+    do_action( 'civicrm_after_rewrite_rules', $flush_rewrite_rules );
 
   }
 
diff --git a/civicrm/CRM/Activity/BAO/Activity.php b/civicrm/CRM/Activity/BAO/Activity.php
index 59b9d813667d7ac209731957077d9e9777567b5c..88a5216204dd949a5128be5e7b38572c18c5a0de 100644
--- a/civicrm/CRM/Activity/BAO/Activity.php
+++ b/civicrm/CRM/Activity/BAO/Activity.php
@@ -149,6 +149,7 @@ class CRM_Activity_BAO_Activity extends CRM_Activity_DAO_Activity {
     }
 
     $transaction = new CRM_Core_Transaction();
+    $sqlWhereParams = $where = [];
     if (is_array(CRM_Utils_Array::value('source_record_id', $params))) {
       $sourceRecordIds = implode(',', $params['source_record_id']);
     }
@@ -156,18 +157,19 @@ class CRM_Activity_BAO_Activity extends CRM_Activity_DAO_Activity {
       $sourceRecordIds = CRM_Utils_Array::value('source_record_id', $params);
     }
 
+    if ($sourceRecordIds) {
+      $where[] = 'source_record_id IN ( %1 )';
+      $sqlWhereParams[1] = [$sourceRecordIds, 'CommaSeparatedIntegers'];
+    }
     $result = NULL;
     if (!$moveToTrash) {
       if (!isset($params['id'])) {
-        if (is_array($params['activity_type_id'])) {
-          $activityTypes = implode(',', $params['activity_type_id']);
-        }
-        else {
-          $activityTypes = $params['activity_type_id'];
+        if (!empty($params['activity_type_id'])) {
+          $where[] = 'activity_type_id IN ( %2 )';
+          $sqlWhereParams[2] = [implode(',', (array) $params['activity_type_id']), 'CommaSeparatedIntegers'];
         }
-
-        $query = "DELETE FROM civicrm_activity WHERE source_record_id IN ({$sourceRecordIds}) AND activity_type_id IN ( {$activityTypes} )";
-        $dao = CRM_Core_DAO::executeQuery($query);
+        $query = "DELETE FROM civicrm_activity WHERE " . implode(' AND ', $where);
+        $dao = CRM_Core_DAO::executeQuery($query, $sqlWhereParams);
       }
       else {
         $activity = new CRM_Activity_DAO_Activity();
@@ -178,8 +180,8 @@ class CRM_Activity_BAO_Activity extends CRM_Activity_DAO_Activity {
         $activity->case_id = CRM_Case_BAO_Case::getCaseIdByActivityId($activity->id);
 
         // CRM-13994 delete activity entity_tag
-        $query = "DELETE FROM civicrm_entity_tag WHERE entity_table = 'civicrm_activity' AND entity_id = {$activity->id}";
-        $dao = CRM_Core_DAO::executeQuery($query);
+        $query = "DELETE FROM civicrm_entity_tag WHERE entity_table = 'civicrm_activity' AND entity_id = %1";
+        $dao = CRM_Core_DAO::executeQuery($query, [1 => [$activity->id, 'Positive']]);
       }
     }
     else {
diff --git a/civicrm/CRM/Admin/Form/Job.php b/civicrm/CRM/Admin/Form/Job.php
index 3009a5b73076ff7dad7bebab0afdd7235e2d7add..e304420e0cd232db2afe9a60e596163dda643b95 100644
--- a/civicrm/CRM/Admin/Form/Job.php
+++ b/civicrm/CRM/Admin/Form/Job.php
@@ -55,6 +55,23 @@ class CRM_Admin_Form_Job extends CRM_Admin_Form {
       return;
     }
 
+    if ($this->_action & CRM_Core_Action::VIEW) {
+      $this->assign('jobName', self::getJobName($this->_id)); 
+      $this->addButtons([
+        [
+          'type' => 'submit',
+          'name' => ts('Execute'),
+          'isDefault' => TRUE,
+        ],
+        [
+          'type' => 'cancel',
+          'name' => ts('Cancel'),
+        ],
+      ]);
+      return;
+    }
+        
+
     $attributes = CRM_Core_DAO::getAttribute('CRM_Core_DAO_Job');
 
     $this->add('text', 'name', ts('Name'),
@@ -172,6 +189,16 @@ class CRM_Admin_Form_Job extends CRM_Admin_Form {
       return;
     }
 
+    // using View action for Execute. Doh.
+    if ($this->_action & CRM_Core_Action::VIEW) {
+      $jm = new CRM_Core_JobManager();
+      $jm->executeJobById($this->_id);
+      $jobName = self::getJobName($this->_id);
+      CRM_Core_Session::setStatus(ts('%1 Scheduled Job has been executed. See the log for details.', [1 => $jobName]), ts("Executed"), "success");
+      CRM_Utils_System::redirect(CRM_Utils_System::url('civicrm/admin/job', 'reset=1'));
+      return;
+    }
+
     $values = $this->controller->exportValues($this->_name);
     $domainID = CRM_Core_Config::domainID();
 
@@ -223,4 +250,17 @@ class CRM_Admin_Form_Job extends CRM_Admin_Form {
 
   }
 
+  /**
+   * Get the API action aka Job Name for this scheduled job
+   * @param int $id - Id of the stored Job
+   *
+   * @return string
+   */
+  private static function getJobName($id) {
+    $entity = CRM_Core_DAO::getFieldValue('CRM_Core_DAO_Job', $id, 'api_entity');
+    $action = CRM_Core_DAO::getFieldValue('CRM_Core_DAO_Job', $id, 'api_action');
+    $name = CRM_Core_DAO::getFieldValue('CRM_Core_DAO_Job', $id, 'name');
+    return $name . ' (' . $entity . '.' . $action . ')';
+  }
+
 }
diff --git a/civicrm/CRM/Admin/Page/Job.php b/civicrm/CRM/Admin/Page/Job.php
index d2c1f0113c1d715c6a1f48a2b209f7fe48c867d0..9d785c876bfa69980a3a3a99ec74cc459af5f365 100644
--- a/civicrm/CRM/Admin/Page/Job.php
+++ b/civicrm/CRM/Admin/Page/Job.php
@@ -58,10 +58,10 @@ class CRM_Admin_Page_Job extends CRM_Core_Page_Basic {
           'qs' => 'action=update&id=%%id%%&reset=1',
           'title' => ts('Edit Scheduled Job'),
         ),
-        CRM_Core_Action::EXPORT => array(
+        CRM_Core_Action::VIEW => array(
           'name' => ts('Execute Now'),
           'url' => 'civicrm/admin/job',
-          'qs' => 'action=export&id=%%id%%&reset=1',
+          'qs' => 'action=view&id=%%id%%&reset=1',
           'title' => ts('Execute Scheduled Job Now'),
         ),
         CRM_Core_Action::DISABLE => array(
@@ -118,12 +118,6 @@ class CRM_Admin_Page_Job extends CRM_Core_Page_Basic {
       $this, FALSE, 0
     );
 
-    // FIXME: Why are we comparing an integer with a string here?
-    if ($this->_action == 'export') {
-      $session = CRM_Core_Session::singleton();
-      $session->pushUserContext(CRM_Utils_System::url('civicrm/admin/job', 'reset=1'));
-    }
-
     if (($this->_action & CRM_Core_Action::COPY) && (!empty($this->_id))) {
       try {
         $jobResult = civicrm_api3('Job', 'clone', array('id' => $this->_id));
@@ -151,14 +145,6 @@ class CRM_Admin_Page_Job extends CRM_Core_Page_Basic {
       CRM_Core_Session::setStatus(ts('Execution of scheduled jobs has been turned off by default since this is a non-production environment. You can override this for particular jobs by adding runInNonProductionEnvironment=TRUE as a parameter.'), ts("Non-production Environment"), "warning", array('expires' => 0));
     }
 
-    // using Export action for Execute. Doh.
-    if ($this->_action & CRM_Core_Action::EXPORT) {
-      $jm = new CRM_Core_JobManager();
-      $jm->executeJobById($this->_id);
-
-      CRM_Core_Session::setStatus(ts('Selected Scheduled Job has been executed. See the log for details.'), ts("Executed"), "success");
-    }
-
     $sj = new CRM_Core_JobManager();
     $rows = $temp = array();
     foreach ($sj->jobs as $job) {
diff --git a/civicrm/CRM/Campaign/BAO/Campaign.php b/civicrm/CRM/Campaign/BAO/Campaign.php
index 3446316570c23e85f97df51c819d80ce0953c855..50b63b0d7f59d81ecb81a09d1e731d776ec1aa9c 100644
--- a/civicrm/CRM/Campaign/BAO/Campaign.php
+++ b/civicrm/CRM/Campaign/BAO/Campaign.php
@@ -416,18 +416,12 @@ INNER JOIN civicrm_option_group grp ON ( campaign_type.option_group_id = grp.id
       $queryParams[6] = ['%' . trim($params['description']) . '%', 'String'];
     }
     if (!empty($params['campaign_type_id'])) {
-      $typeId = $params['campaign_type_id'];
-      if (is_array($params['campaign_type_id'])) {
-        $typeId = implode(' , ', $params['campaign_type_id']);
-      }
-      $where[] = "( campaign.campaign_type_id IN ( {$typeId} ) )";
+      $where[] = "( campaign.campaign_type_id IN ( %7 ) )";
+      $queryParams[7] = [implode(',', (array) $params['campaign_type_id']), 'CommaSeparatedIntegers'];
     }
     if (!empty($params['status_id'])) {
-      $statusId = $params['status_id'];
-      if (is_array($params['status_id'])) {
-        $statusId = implode(' , ', $params['status_id']);
-      }
-      $where[] = "( campaign.status_id IN ( {$statusId} ) )";
+      $where[] = "( campaign.status_id IN ( %8 ) )";
+      $queryParams[8] = [implode(',', (array) $params['status_id']), 'CommaSeparatedIntegers'];
     }
     if (array_key_exists('is_active', $params)) {
       $active = "( campaign.is_active = 1 )";
diff --git a/civicrm/CRM/Case/XMLProcessor/Report.php b/civicrm/CRM/Case/XMLProcessor/Report.php
index 453f39ecf96579af1447e7b832ed2f5f2ccdf930..720bbbabe70e4167966a1db6572606a284808d76 100644
--- a/civicrm/CRM/Case/XMLProcessor/Report.php
+++ b/civicrm/CRM/Case/XMLProcessor/Report.php
@@ -443,7 +443,7 @@ WHERE      a.id = %1
 
     $activity['fields'][] = array(
       'label' => ts('Details'),
-      'value' => $this->redact(CRM_Utils_String::stripAlternatives($activityDAO->details)),
+      'value' => $this->redact(CRM_Utils_String::purifyHTML(CRM_Utils_String::stripAlternatives($activityDAO->details))),
       'type' => 'Memo',
     );
 
diff --git a/civicrm/CRM/Contact/BAO/Query.php b/civicrm/CRM/Contact/BAO/Query.php
index 04e33776d16aba525dec7c8f6a6c4851d8def2cb..c95702217629f4927655e4f1835336fdca7936fd 100644
--- a/civicrm/CRM/Contact/BAO/Query.php
+++ b/civicrm/CRM/Contact/BAO/Query.php
@@ -3092,7 +3092,7 @@ class CRM_Contact_BAO_Query {
       $groupContactCacheClause = $this->addGroupContactCache($smartGroupIDs, $gccTableAlias, "contact_a", $op);
       if (!empty($groupContactCacheClause)) {
         if ($isNotOp) {
-          $groupIds = implode(',', (array) $smartGroupIDs);
+          $groupIds = CRM_Utils_Type::validate(implode(',', (array) $smartGroupIDs), 'CommaSeparatedIntegers');
           $gcTable = "civicrm_group_contact_{$this->_groupUniqueKey}";
           $joinClause = ["contact_a.id = {$gcTable}.contact_id"];
           $this->_tables[$gcTable] = $this->_whereTables[$gcTable] = " LEFT JOIN civicrm_group_contact {$gcTable} ON (" . implode(' AND ', $joinClause) . ")";
@@ -4049,15 +4049,14 @@ WHERE  $smartGroupClause
    */
   public function privacy(&$values) {
     list($name, $op, $value, $grouping) = $values;
-    //fixed for profile search listing CRM-4633
-    if (strpbrk($value, "[")) {
-      $value = "'{$value}'";
-      $op = "!{$op}";
-      $this->_where[$grouping][] = "contact_a.{$name} $op $value";
-    }
-    else {
-      $this->_where[$grouping][] = "contact_a.{$name} $op $value";
+    if (is_array($value)) {
+      if (in_array(key($value), CRM_Core_DAO::acceptedSQLOperators(), TRUE)) {
+        $op = key($value);
+        $value = $value[$op];
+      }
     }
+    CRM_Utils_Type::validate($value, 'Integer');
+    $this->_where[$grouping][] = "contact_a.{$name} $op $value";
     $field = CRM_Utils_Array::value($name, $this->_fields);
     $op = CRM_Utils_Array::value($op, CRM_Core_SelectValues::getSearchBuilderOperators(), $op);
     $title = $field ? $field['title'] : $name;
diff --git a/civicrm/CRM/Core/Invoke.php b/civicrm/CRM/Core/Invoke.php
index 1ea5fa8b162011856cc5949ededa65540003921c..2cd7117fa8a33c56f7fdc3e4f38fccc22aae2fa4 100644
--- a/civicrm/CRM/Core/Invoke.php
+++ b/civicrm/CRM/Core/Invoke.php
@@ -150,6 +150,47 @@ class CRM_Core_Invoke {
     return $item;
   }
 
+  /**
+   * Register an alternative phar:// stream wrapper to filter out insecure Phars
+   *
+   * PHP makes it possible to trigger Object Injection vulnerabilities by using
+   * a side-effect of the phar:// stream wrapper that unserializes Phar
+   * metadata. To mitigate this vulnerability, projects such as TYPO3 and Drupal
+   * have implemented an alternative Phar stream wrapper that disallows
+   * inclusion of phar files based on certain parameters.
+   *
+   * This code attempts to register the TYPO3 Phar stream wrapper using the
+   * interceptor defined in \Civi\Core\Security\PharExtensionInterceptor. In an
+   * environment where the stream wrapper was already registered via
+   * \TYPO3\PharStreamWrapper\Manager (i.e. Drupal), this code does not do
+   * anything. In other environments (e.g. WordPress, at the time of this
+   * writing), the TYPO3 library is used to register the interceptor to mitigate
+   * the vulnerability.
+   */
+  private static function registerPharHandler() {
+    try {
+      // try to get the existing stream wrapper, registered e.g. by Drupal
+      \TYPO3\PharStreamWrapper\Manager::instance();
+    }
+    catch (\LogicException $e) {
+      if ($e->getCode() === 1535189872) {
+        // no phar stream wrapper was registered by \TYPO3\PharStreamWrapper\Manager.
+        // This means we're probably not on Drupal and need to register our own.
+        \TYPO3\PharStreamWrapper\Manager::initialize(
+          (new \TYPO3\PharStreamWrapper\Behavior())
+            ->withAssertion(new \Civi\Core\Security\PharExtensionInterceptor())
+        );
+        if (in_array('phar', stream_get_wrappers())) {
+          stream_wrapper_unregister('phar');
+          stream_wrapper_register('phar', \TYPO3\PharStreamWrapper\PharStreamWrapper::class);
+        }
+      } else {
+        // this is not an exception we can handle
+        throw $e;
+      }
+    }
+  }
+
   /**
    * Given a menu item, call the appropriate controller and return the response
    *
@@ -161,6 +202,8 @@ class CRM_Core_Invoke {
     $ids = new CRM_Core_IDS();
     $ids->check($item);
 
+    self::registerPharHandler();
+
     $config = CRM_Core_Config::singleton();
     if ($config->userFramework == 'Joomla' && $item) {
       $config->userFrameworkURLVar = 'task';
diff --git a/civicrm/CRM/Core/Page/QUnit.php b/civicrm/CRM/Core/Page/QUnit.php
index ae1c90c3441adc8fb5ed1cd8a40a70b91efe373c..5fb8bc8b63da744e936a3f35b0fe08369eb96438 100644
--- a/civicrm/CRM/Core/Page/QUnit.php
+++ b/civicrm/CRM/Core/Page/QUnit.php
@@ -15,6 +15,13 @@ class CRM_Core_Page_QUnit extends CRM_Core_Page {
    * @throws \CRM_Core_Exception
    */
   public function run() {
+    $qunitJsFile = Civi::paths()->getPath('[civicrm.bower]/qunit/qunit/qunit.js');
+    $qunitJsUrl = Civi::paths()->getUrl('[civicrm.bower]/qunit/qunit/qunit.js');
+    $qunitCssUrl = Civi::paths()->getUrl('[civicrm.bower]/qunit/qunit/qunit.css');
+    if (!file_exists($qunitJsFile)) {
+      throw new \CRM_Core_Exception("QUnit is not available. Please install it in [civicrm.bower]/qunit.");
+    }
+
     list ($ext, $suite) = $this->getRequestExtAndSuite();
     if (empty($ext) || empty($suite)) {
       throw new CRM_Core_Exception("FIXME: Not implemented: QUnit browser");
@@ -45,8 +52,8 @@ class CRM_Core_Page_QUnit extends CRM_Core_Page {
 
     CRM_Utils_System::setTitle(ts('QUnit: %2 (%1)', [1 => $ext, 2 => $suite]));
     CRM_Core_Resources::singleton()
-      ->addScriptFile('civicrm', 'bower_components/qunit/qunit/qunit.js', 1, 'html-header')
-      ->addStyleFile('civicrm', 'bower_components/qunit/qunit/qunit.css', 1, 'html-header');
+      ->addScriptUrl($qunitJsUrl, 1, 'html-header')
+      ->addStyleUrl($qunitCssUrl, 1, 'html-header');
     parent::run();
   }
 
diff --git a/civicrm/CRM/Report/Form.php b/civicrm/CRM/Report/Form.php
index 56bfdd6f7e390e222ff466299f3671f99fcb51c5..47adf78eed1b64a28ccf515bca0fe5131f50c409 100644
--- a/civicrm/CRM/Report/Form.php
+++ b/civicrm/CRM/Report/Form.php
@@ -139,11 +139,6 @@ class CRM_Report_Form extends CRM_Core_Form {
    */
   protected $_groupFilter = FALSE;
 
-  /**
-   * Required for civiexportexcel.
-   */
-  public $supportsExportExcel = TRUE;
-
   /**
    * Has the report been optimised for group filtering.
    *
@@ -1423,7 +1418,7 @@ class CRM_Report_Form extends CRM_Core_Form {
     if (!CRM_Core_Permission::check('view report sql')) {
       return;
     }
-    $ignored_output_modes = ['pdf', 'csv', 'print', 'excel2007'];
+    $ignored_output_modes = ['pdf', 'csv', 'print'];
     if (in_array($this->_outputMode, $ignored_output_modes)) {
       return;
     }
@@ -2850,11 +2845,6 @@ WHERE cg.extends IN ('" . implode("','", $this->_customGroupExtends) . "') AND
       $this->_absoluteUrl = TRUE;
       $this->addPaging = FALSE;
     }
-    elseif ($this->_outputMode == 'excel2007') {
-      $printOnly = TRUE;
-      $this->_absoluteUrl = TRUE;
-      $this->addPaging = FALSE;
-    }
     elseif ($this->_outputMode == 'group') {
       $this->assign('outputMode', 'group');
     }
@@ -3497,9 +3487,6 @@ WHERE cg.extends IN ('" . implode("','", $this->_customGroupExtends) . "') AND
     elseif ($this->_outputMode == 'csv') {
       CRM_Report_Utils_Report::export2csv($this, $rows);
     }
-    elseif ($this->_outputMode == 'excel2007') {
-      CRM_CiviExportExcel_Utils_Report::export2excel2007($this, $rows);
-    }
     elseif ($this->_outputMode == 'group') {
       $group = $this->_params['groups'];
       $this->add2group($group);
diff --git a/civicrm/CRM/Upgrade/Incremental/sql/5.24.3.mysql.tpl b/civicrm/CRM/Upgrade/Incremental/sql/5.24.3.mysql.tpl
new file mode 100644
index 0000000000000000000000000000000000000000..63e37fb98336231872bfd3dcac012e36946056cd
--- /dev/null
+++ b/civicrm/CRM/Upgrade/Incremental/sql/5.24.3.mysql.tpl
@@ -0,0 +1 @@
+{* file to handle db changes in 5.24.3 during upgrade *}
diff --git a/civicrm/CRM/Utils/Check/Component/Security.php b/civicrm/CRM/Utils/Check/Component/Security.php
index 3a17c834fdcb41033163a986e1e32ce0538fa7cc..2c79192a25d96f40f64a935331a2457f59b8fc19 100644
--- a/civicrm/CRM/Utils/Check/Component/Security.php
+++ b/civicrm/CRM/Utils/Check/Component/Security.php
@@ -223,6 +223,16 @@ class CRM_Utils_Check_Component_Security extends CRM_Utils_Check_Component {
         "{$civicrm_root}/packages/html2text/class.html2text.inc",
         \Psr\Log\LogLevel::CRITICAL,
       ],
+      [
+        // MOSS CIV-01-002: The "demo.html" is problematic. Other unnecessary files should be deleted as a precaution. Consider deleting the folder and re-running 'composer install'.
+        Civi::paths()->getPath('[civicrm.bower]/google-code-prettify/styles/demo.html'),
+        \Psr\Log\LogLevel::CRITICAL,
+      ],
+      [
+        // MOSS CIV-01-002: Certain QUnit addons are problematic. Other unnecessary files should be deleted as a precaution. Consider deleting the folder and re-running 'composer install'.
+        Civi::paths()->getPath('[civicrm.bower]/qunit/addons'),
+        \Psr\Log\LogLevel::CRITICAL,
+      ],
     ];
     foreach ($files as $file) {
       if (file_exists($file[0])) {
diff --git a/civicrm/CRM/Utils/System/WordPress.php b/civicrm/CRM/Utils/System/WordPress.php
index 80cb3692af41d4b5ff8992308e9f26c01a46190e..6c215d2954f825fcb02c18f0f3adb580cf9d7a99 100644
--- a/civicrm/CRM/Utils/System/WordPress.php
+++ b/civicrm/CRM/Utils/System/WordPress.php
@@ -409,63 +409,22 @@ class CRM_Utils_System_WordPress extends CRM_Utils_System_Base {
    * @inheritDoc
    */
   public function getUFLocale() {
-    // Bail early if method is called when WordPress isn't bootstrapped.
-    // Additionally, the function checked here is located in pluggable.php
-    // and is required by wp_get_referer() - so this also bails early if it is
-    // called too early in the request lifecycle.
-    // @see https://core.trac.wordpress.org/ticket/25294
-    if (!function_exists('wp_validate_redirect')) {
-      return NULL;
+    // Polylang plugin
+    if (function_exists('pll_current_language')) {
+      $language = pll_current_language();
     }
-
-    // Default to WordPress User locale.
-    $locale = get_user_locale();
-
-    // Is this a "back-end" AJAX call?
-    $is_backend = FALSE;
-    if (wp_doing_ajax() && FALSE !== strpos(wp_get_referer(), admin_url())) {
-      $is_backend = TRUE;
+    // WPML plugin
+    elseif (defined('ICL_LANGUAGE_CODE')) {
+      $language = ICL_LANGUAGE_CODE;
     }
-
-    // Ignore when in WordPress admin or it's a "back-end" AJAX call.
-    if (!(is_admin() || $is_backend)) {
-
-      // Reaching here means it is very likely to be a front-end context.
-
-      // Default to WordPress locale.
-      $locale = get_locale();
-
-      // Maybe override with the locale that Polylang reports.
-      if (function_exists('pll_current_language')) {
-        $pll_locale = pll_current_language('locale');
-        if (!empty($pll_locale)) {
-          $locale = $pll_locale;
-        }
-      }
-
-      // Maybe override with the locale that WPML reports.
-      elseif (defined('ICL_LANGUAGE_CODE')) {
-        $languages = apply_filters('wpml_active_languages', NULL);
-        foreach ($languages as $language) {
-          if ($language['active']) {
-            $locale = $language['default_locale'];
-            break;
-          }
-        }
-      }
-
-      // TODO: Set locale for other WordPress plugins.
-      // @see https://wordpress.org/plugins/tags/multilingual/
-      // A hook would be nice here.
-
+    // Wordpress "standard" single language mode
+    // We still have to check if the function exists as it may not during bootstrap
+    elseif (function_exists('get_locale')) {
+      $language = get_locale();
     }
 
-    if (!empty($locale)) {
-      // If for some reason only we get a language code, convert it to a locale.
-      if (2 === strlen($locale)) {
-        $locale = CRM_Core_I18n_PseudoConstant::longForShort($locale);
-      }
-      return $locale;
+    if (!empty($language)) {
+      return CRM_Core_I18n_PseudoConstant::longForShort(substr($language, 0, 2));
     }
     else {
       return NULL;
diff --git a/civicrm/Civi/Core/Security/PharExtensionInterceptor.php b/civicrm/Civi/Core/Security/PharExtensionInterceptor.php
new file mode 100644
index 0000000000000000000000000000000000000000..d2773db119130a6220def09bf17b1e6812f4d52c
--- /dev/null
+++ b/civicrm/Civi/Core/Security/PharExtensionInterceptor.php
@@ -0,0 +1,82 @@
+<?php
+
+namespace Civi\Core\Security;
+
+use TYPO3\PharStreamWrapper\Assertable;
+use TYPO3\PharStreamWrapper\Helper;
+use TYPO3\PharStreamWrapper\Exception;
+
+/**
+ * An alternate PharExtensionInterceptor to support phar-based CLI tools.
+ *
+ * This is largely based on Drupal\Core\Security\PharExtensionInterceptor,
+ * originally licensed under GPL2+
+ *
+ * @see \TYPO3\PharStreamWrapper\Interceptor\PharExtensionInterceptor
+ */
+class PharExtensionInterceptor implements Assertable {
+
+  /**
+   * Determines whether phar file is allowed to execute.
+   *
+   * The phar file is allowed to execute if:
+   * - the base file name has a ".phar" suffix.
+   * - it is the CLI tool that has invoked the interceptor.
+   *
+   * @param string $path
+   *   The path of the phar file to check.
+   * @param string $command
+   *   The command being carried out.
+   *
+   * @return bool
+   *   TRUE if the phar file is allowed to execute.
+   *
+   * @throws Exception
+   *   Thrown when the file is not allowed to execute.
+   */
+  public function assert(string $path, string $command): bool {
+    if ($this->baseFileContainsPharExtension($path)) {
+      return TRUE;
+    }
+    throw new Exception(
+      sprintf(
+        'Unexpected file extension in "%s"',
+        $path
+      ),
+      1535198703
+    );
+  }
+
+  /**
+   * Determines if a path has a .phar extension or invoked execution.
+   *
+   * @param string $path
+   *   The path of the phar file to check.
+   *
+   * @return bool
+   *   TRUE if the file has a .phar extension or if the execution has been
+   *   invoked by the phar file.
+   */
+  private function baseFileContainsPharExtension($path) {
+    $baseFile = Helper::determineBaseFile($path);
+    if ($baseFile === NULL) {
+      return FALSE;
+    }
+    // If the stream wrapper is registered by invoking a phar file that does
+    // not not have .phar extension then this should be allowed. For
+    // example, some CLI tools recommend removing the extension.
+    $backtrace = debug_backtrace(DEBUG_BACKTRACE_IGNORE_ARGS);
+    // Find the last entry in the backtrace containing a 'file' key as
+    // sometimes the last caller is executed outside the scope of a file. For
+    // example, this occurs with shutdown functions.
+    do {
+      $caller = array_pop($backtrace);
+    } while (empty($caller['file']) && !empty($backtrace));
+    if (isset($caller['file']) && $baseFile === Helper::determineBaseFile($caller['file'])) {
+      return TRUE;
+    }
+    $fileExtension = pathinfo($baseFile, PATHINFO_EXTENSION);
+    return strtolower($fileExtension) === 'phar';
+  }
+
+}
diff --git a/civicrm/api/api.php b/civicrm/api/api.php
index 7cbc5d180dcb56f88b29b805d538a6e4bcaaf1fc..43902e227c016f9f6b879e90fdf390b63f72df2a 100644
--- a/civicrm/api/api.php
+++ b/civicrm/api/api.php
@@ -200,7 +200,7 @@ function civicrm_error($result) {
  * @return string|null
  */
 function _civicrm_api_get_camel_name($entity) {
-  return is_string($entity) ? CRM_Utils_String::convertStringToCamel($entity) : NULL;
+  return is_string($entity) ? \Civi\API\Request::normalizeEntityName($entity) : NULL;
 }
 
 /**
diff --git a/civicrm/api/v3/Contact.php b/civicrm/api/v3/Contact.php
index 00c0bebe1d53647f9a54134cbbdc100ae53d089c..1b7f9cade80cf47f9fca95962d3f8976a1a255d0 100644
--- a/civicrm/api/v3/Contact.php
+++ b/civicrm/api/v3/Contact.php
@@ -757,6 +757,10 @@ function civicrm_api3_contact_getquick($params) {
   // If we are doing quicksearch by a field other than name, make sure that field is added to results
   if (!empty($params['field_name'])) {
     $field_name = CRM_Utils_String::munge($params['field_name']);
+    // there is no good reason to request api_key via getquick
+    if ($field_name == 'api_key') {
+      throw new API_Exception('Illegal value "api_key" for parameter "field_name"');
+    }
     // Unique name contact_id = id
     if ($field_name == 'contact_id') {
       $field_name = 'id';
diff --git a/civicrm/bower_components/angular-bootstrap/.composer-downloads/angular-bootstrap-02435d2082ac71ec4f13fbdf2f4d3e1a.json b/civicrm/bower_components/angular-bootstrap/.composer-downloads/angular-bootstrap-02435d2082ac71ec4f13fbdf2f4d3e1a.json
index ae35559dc5b2a02e910fb9d1f49b71881b565b00..a5d0dfa9f6a8144fdf93064ebeb7845f97547ad4 100644
--- a/civicrm/bower_components/angular-bootstrap/.composer-downloads/angular-bootstrap-02435d2082ac71ec4f13fbdf2f4d3e1a.json
+++ b/civicrm/bower_components/angular-bootstrap/.composer-downloads/angular-bootstrap-02435d2082ac71ec4f13fbdf2f4d3e1a.json
@@ -1,4 +1,6 @@
 {
     "name": "civicrm/civicrm-core:angular-bootstrap",
-    "url": "https://github.com/angular-ui/bootstrap-bower/archive/2.5.0.zip"
+    "url": "https://github.com/angular-ui/bootstrap-bower/archive/2.5.0.zip",
+    "checksum": "57dea2ac376e455a052f9a2329be20b1bf72107862c7fa04fa993f4ce396572b",
+    "ignore": null
 }
\ No newline at end of file
diff --git a/civicrm/bower_components/angular-file-upload/.composer-downloads/angular-file-upload-e60440287b4df1cbc04045e77a8c05f5.json b/civicrm/bower_components/angular-file-upload/.composer-downloads/angular-file-upload-e60440287b4df1cbc04045e77a8c05f5.json
index c73357d95c901c90bc8ede8b78a6b6eaada15c58..8b2c667187ebd8de0bdfeb9fc64dbdeaba2a662a 100644
--- a/civicrm/bower_components/angular-file-upload/.composer-downloads/angular-file-upload-e60440287b4df1cbc04045e77a8c05f5.json
+++ b/civicrm/bower_components/angular-file-upload/.composer-downloads/angular-file-upload-e60440287b4df1cbc04045e77a8c05f5.json
@@ -1,4 +1,8 @@
 {
     "name": "civicrm/civicrm-core:angular-file-upload",
-    "url": "https://github.com/nervgh/angular-file-upload/archive/v1.1.6.zip"
+    "url": "https://github.com/nervgh/angular-file-upload/archive/v1.1.6.zip",
+    "checksum": "5270549e05fc3223f21c401c6ebd738f7ac1eff372ff78a4dd31aff974586951",
+    "ignore": [
+        "examples"
+    ]
 }
\ No newline at end of file
diff --git a/civicrm/bower_components/angular-jquery-dialog-service/.composer-downloads/angular-jquery-dialog-service-1e0a7077e80f08e2a94cb4baa0a72f72.json b/civicrm/bower_components/angular-jquery-dialog-service/.composer-downloads/angular-jquery-dialog-service-1e0a7077e80f08e2a94cb4baa0a72f72.json
index 3c1ca0c3e00615039aec00d7bd3d4ea29f6ae015..a93dc6f7fe1b0cb6e1aee4c081410c752e99a01d 100644
--- a/civicrm/bower_components/angular-jquery-dialog-service/.composer-downloads/angular-jquery-dialog-service-1e0a7077e80f08e2a94cb4baa0a72f72.json
+++ b/civicrm/bower_components/angular-jquery-dialog-service/.composer-downloads/angular-jquery-dialog-service-1e0a7077e80f08e2a94cb4baa0a72f72.json
@@ -1,4 +1,6 @@
 {
     "name": "civicrm/civicrm-core:angular-jquery-dialog-service",
-    "url": "https://github.com/totten/angular-jquery-dialog-service/archive/v0.8.0-civicrm-1.0.zip"
+    "url": "https://github.com/totten/angular-jquery-dialog-service/archive/v0.8.0-civicrm-1.0.zip",
+    "checksum": "16c600e9c7586b0b8482da7f2437e2c9f67c7783ed261de3f95aac24f288371f",
+    "ignore": null
 }
\ No newline at end of file
diff --git a/civicrm/bower_components/angular-mocks/.composer-downloads/angular-mocks-f6200e65f802695e672eba66b582c642.json b/civicrm/bower_components/angular-mocks/.composer-downloads/angular-mocks-f6200e65f802695e672eba66b582c642.json
index 3240c0443e581f96df745b66cc2d6382e8e74c7a..f3fa6e5a2087bc330f60ac9750f206595a5b8105 100644
--- a/civicrm/bower_components/angular-mocks/.composer-downloads/angular-mocks-f6200e65f802695e672eba66b582c642.json
+++ b/civicrm/bower_components/angular-mocks/.composer-downloads/angular-mocks-f6200e65f802695e672eba66b582c642.json
@@ -1,4 +1,6 @@
 {
     "name": "civicrm/civicrm-core:angular-mocks",
-    "url": "https://github.com/angular/bower-angular-mocks/archive/v1.5.11.zip"
+    "url": "https://github.com/angular/bower-angular-mocks/archive/v1.5.11.zip",
+    "checksum": "77f429f3cb5ac4ca022e69d7dddcd201f874abc08ad485281a8330fa9458f2ca",
+    "ignore": null
 }
\ No newline at end of file
diff --git a/civicrm/bower_components/angular-route/.composer-downloads/angular-route-e3ac2d15fca8a7bc6c303335035b7ec6.json b/civicrm/bower_components/angular-route/.composer-downloads/angular-route-e3ac2d15fca8a7bc6c303335035b7ec6.json
index 060e6e74e18399810bf0b795b5bc21ae5093dcd7..f509791f83b2b20048a9f642ed1d1c1ee5297f8a 100644
--- a/civicrm/bower_components/angular-route/.composer-downloads/angular-route-e3ac2d15fca8a7bc6c303335035b7ec6.json
+++ b/civicrm/bower_components/angular-route/.composer-downloads/angular-route-e3ac2d15fca8a7bc6c303335035b7ec6.json
@@ -1,4 +1,6 @@
 {
     "name": "civicrm/civicrm-core:angular-route",
-    "url": "https://github.com/angular/bower-angular-route/archive/v1.5.11.zip"
+    "url": "https://github.com/angular/bower-angular-route/archive/v1.5.11.zip",
+    "checksum": "b8e307b6a1a650f09b2c1856e7c39047f6a09c4ef22158f75e77f9874bf213c0",
+    "ignore": null
 }
\ No newline at end of file
diff --git a/civicrm/bower_components/angular-sanitize/.composer-downloads/angular-sanitize-2e0dffb0d66d69809f64b5824d8df7ec.json b/civicrm/bower_components/angular-sanitize/.composer-downloads/angular-sanitize-2e0dffb0d66d69809f64b5824d8df7ec.json
index 4811eb258d063bb8ef5a6e36595da05940d0881d..77d8b2b91be24c49344b4977ecd0e8e9c29a3724 100644
--- a/civicrm/bower_components/angular-sanitize/.composer-downloads/angular-sanitize-2e0dffb0d66d69809f64b5824d8df7ec.json
+++ b/civicrm/bower_components/angular-sanitize/.composer-downloads/angular-sanitize-2e0dffb0d66d69809f64b5824d8df7ec.json
@@ -1,4 +1,6 @@
 {
     "name": "civicrm/civicrm-core:angular-sanitize",
-    "url": "https://github.com/angular/bower-angular-sanitize/archive/v1.5.11.zip"
+    "url": "https://github.com/angular/bower-angular-sanitize/archive/v1.5.11.zip",
+    "checksum": "adc8684ea4bc8a11c51ab1c1ff3a92aa7a2b5f1eaf7f51a054fd1758b3a78df0",
+    "ignore": null
 }
\ No newline at end of file
diff --git a/civicrm/bower_components/angular-ui-sortable/.composer-downloads/angular-ui-sortable-c3c4e428641d501819195be170cbe824.json b/civicrm/bower_components/angular-ui-sortable/.composer-downloads/angular-ui-sortable-c3c4e428641d501819195be170cbe824.json
index 43c1d9f619362f07fbfb12b43574c4e73ec131a4..d53f82bb2cab621911e7b24587149baa98f0dae4 100644
--- a/civicrm/bower_components/angular-ui-sortable/.composer-downloads/angular-ui-sortable-c3c4e428641d501819195be170cbe824.json
+++ b/civicrm/bower_components/angular-ui-sortable/.composer-downloads/angular-ui-sortable-c3c4e428641d501819195be170cbe824.json
@@ -1,4 +1,6 @@
 {
     "name": "civicrm/civicrm-core:angular-ui-sortable",
-    "url": "https://github.com/angular-ui/ui-sortable/archive/v0.19.0.zip"
+    "url": "https://github.com/angular-ui/ui-sortable/archive/v0.19.0.zip",
+    "checksum": "d0ff44faaca9ea2c7b517563a786ed7758bdddc2ab7a1ea96b3673eb9d896407",
+    "ignore": null
 }
\ No newline at end of file
diff --git a/civicrm/bower_components/angular-ui-utils/.composer-downloads/angular-ui-utils-74b1ad1150f4c22741f9e1e45a4f92cd.json b/civicrm/bower_components/angular-ui-utils/.composer-downloads/angular-ui-utils-74b1ad1150f4c22741f9e1e45a4f92cd.json
index d127edaf5c1fe6b7f58770a3142737cdab2d70c5..dbf864a3afc6103f35409484036dcfb5b71e5eaa 100644
--- a/civicrm/bower_components/angular-ui-utils/.composer-downloads/angular-ui-utils-74b1ad1150f4c22741f9e1e45a4f92cd.json
+++ b/civicrm/bower_components/angular-ui-utils/.composer-downloads/angular-ui-utils-74b1ad1150f4c22741f9e1e45a4f92cd.json
@@ -1,4 +1,6 @@
 {
     "name": "civicrm/civicrm-core:angular-ui-utils",
-    "url": "https://github.com/angular-ui/ui-utils/archive/v0.1.1.zip"
+    "url": "https://github.com/angular-ui/ui-utils/archive/v0.1.1.zip",
+    "checksum": "b072c219c8caf6022dac9e35ba95b5e462630312bebb9ff9d420d7fb8e2a1cf2",
+    "ignore": null
 }
\ No newline at end of file
diff --git a/civicrm/bower_components/angular-unsavedChanges/.composer-downloads/angular-unsavedChanges-6731bbc27c37c58c64ec4701b2519568.json b/civicrm/bower_components/angular-unsavedChanges/.composer-downloads/angular-unsavedChanges-6731bbc27c37c58c64ec4701b2519568.json
index bb30325b4e3f02e101338463f91bdf97a536aa9f..a34d74743889e2b123034c626a77904bc92af2ac 100644
--- a/civicrm/bower_components/angular-unsavedChanges/.composer-downloads/angular-unsavedChanges-6731bbc27c37c58c64ec4701b2519568.json
+++ b/civicrm/bower_components/angular-unsavedChanges/.composer-downloads/angular-unsavedChanges-6731bbc27c37c58c64ec4701b2519568.json
@@ -1,4 +1,12 @@
 {
     "name": "civicrm/civicrm-core:angular-unsavedchanges",
-    "url": "https://github.com/facultymatt/angular-unsavedChanges/archive/v0.1.1.zip"
+    "url": "https://github.com/facultymatt/angular-unsavedChanges/archive/v0.1.1.zip",
+    "checksum": "0e5bb0d1d492215e6294992f2d39a0975aebf9ca641b5285ef26920ef496b414",
+    "ignore": [
+        ".*",
+        "node_modules",
+        "bower_components",
+        "test",
+        "tests"
+    ]
 }
\ No newline at end of file
diff --git a/civicrm/bower_components/angular-xeditable/.composer-downloads/angular-xeditable-9b1e32a8b3e1d76027b3a4167ab2ff58.json b/civicrm/bower_components/angular-xeditable/.composer-downloads/angular-xeditable-9b1e32a8b3e1d76027b3a4167ab2ff58.json
index 013d08f17a427c6a4b22fe17d854d8dda3138d75..d3b2b10e13d10f91171ac2588f7a7644cc4726ae 100644
--- a/civicrm/bower_components/angular-xeditable/.composer-downloads/angular-xeditable-9b1e32a8b3e1d76027b3a4167ab2ff58.json
+++ b/civicrm/bower_components/angular-xeditable/.composer-downloads/angular-xeditable-9b1e32a8b3e1d76027b3a4167ab2ff58.json
@@ -1,4 +1,21 @@
 {
     "name": "civicrm/civicrm-core:angular-xeditable",
-    "url": "https://github.com/vitalets/angular-xeditable/archive/0.9.0.zip"
+    "url": "https://github.com/vitalets/angular-xeditable/archive/0.9.0.zip",
+    "checksum": "30ee56284018f11bca7cd4d1c6c0ea0de39ca6a94164cc79cd00e2c7159fe37f",
+    "ignore": [
+        ".*",
+        "node_modules",
+        "bower_components",
+        "playground",
+        "test",
+        "libs",
+        "docs",
+        "zip",
+        "src",
+        "starter",
+        "Gruntfile.js",
+        "index.html",
+        "jsdoc.conf.json",
+        "package.json"
+    ]
 }
\ No newline at end of file
diff --git a/civicrm/bower_components/angular/.composer-downloads/angular-d18b8624a0f5f721da7b82365fc562dd.json b/civicrm/bower_components/angular/.composer-downloads/angular-d18b8624a0f5f721da7b82365fc562dd.json
index 3833c8233011c9445621e649ccc02910e6ee9b21..4fbd5d117d2b72466e6b03490217a5aea9ec00a0 100644
--- a/civicrm/bower_components/angular/.composer-downloads/angular-d18b8624a0f5f721da7b82365fc562dd.json
+++ b/civicrm/bower_components/angular/.composer-downloads/angular-d18b8624a0f5f721da7b82365fc562dd.json
@@ -1,4 +1,6 @@
 {
     "name": "civicrm/civicrm-core:angular",
-    "url": "https://github.com/angular/bower-angular/archive/v1.5.11.zip"
+    "url": "https://github.com/angular/bower-angular/archive/v1.5.11.zip",
+    "checksum": "ce8ecba711e2d10f58e8f969f96fb3d2a69a974c22a7ef6afa63bfb75b6bcece",
+    "ignore": null
 }
\ No newline at end of file
diff --git a/civicrm/bower_components/checklist-model/.composer-downloads/checklist-model-71a4c0cb1382f152af0850bd2adbb843.json b/civicrm/bower_components/checklist-model/.composer-downloads/checklist-model-71a4c0cb1382f152af0850bd2adbb843.json
index 8222a0d2633fd0efb23d1e6be37394a821e32a8a..3aed27e2cb766bd969b5e630a11c41d6678f2335 100644
--- a/civicrm/bower_components/checklist-model/.composer-downloads/checklist-model-71a4c0cb1382f152af0850bd2adbb843.json
+++ b/civicrm/bower_components/checklist-model/.composer-downloads/checklist-model-71a4c0cb1382f152af0850bd2adbb843.json
@@ -1,4 +1,14 @@
 {
     "name": "civicrm/civicrm-core:checklist-model",
-    "url": "https://github.com/vitalets/checklist-model/archive/1.0.0.zip"
+    "url": "https://github.com/vitalets/checklist-model/archive/1.0.0.zip",
+    "checksum": "137cdbefccb3eea1c62e526b67c147d05e68a362e24f6f3a92a865c1afaa75d1",
+    "ignore": [
+        ".*",
+        "node_modules",
+        "docs",
+        "Gruntfile.js",
+        "index.html",
+        "package.json",
+        "test"
+    ]
 }
\ No newline at end of file
diff --git a/civicrm/bower_components/ckeditor/.composer-downloads/ckeditor-55ec7732cc4d2d985134a433fa86a610.json b/civicrm/bower_components/ckeditor/.composer-downloads/ckeditor-55ec7732cc4d2d985134a433fa86a610.json
index 9e325615d86d9b9c683ddd6e11d692e1da9dc6e5..83023c5bb3c77900efe5ac4ce0002073484da40b 100644
--- a/civicrm/bower_components/ckeditor/.composer-downloads/ckeditor-55ec7732cc4d2d985134a433fa86a610.json
+++ b/civicrm/bower_components/ckeditor/.composer-downloads/ckeditor-55ec7732cc4d2d985134a433fa86a610.json
@@ -1,4 +1,6 @@
 {
     "name": "civicrm/civicrm-core:ckeditor",
-    "url": "https://github.com/ckeditor/ckeditor-releases/archive/4.14.0.zip"
+    "url": "https://github.com/ckeditor/ckeditor-releases/archive/4.14.0.zip",
+    "checksum": "97a5c24a1e123698cc8838ffff905189df8210f7a25cf4417db0c92faad6782a",
+    "ignore": null
 }
\ No newline at end of file
diff --git a/civicrm/bower_components/crossfilter-1.3.x/.composer-downloads/crossfilter-1.3.x-7acfcad9e23c80333653a6e5d55428e5.json b/civicrm/bower_components/crossfilter-1.3.x/.composer-downloads/crossfilter-1.3.x-7acfcad9e23c80333653a6e5d55428e5.json
index 590664e856fe767b35eebbfdb9f0377a90335b7e..0ef7b9ac3d04e1b0132d2e50fd54ff3e64a1ed2b 100644
--- a/civicrm/bower_components/crossfilter-1.3.x/.composer-downloads/crossfilter-1.3.x-7acfcad9e23c80333653a6e5d55428e5.json
+++ b/civicrm/bower_components/crossfilter-1.3.x/.composer-downloads/crossfilter-1.3.x-7acfcad9e23c80333653a6e5d55428e5.json
@@ -1,4 +1,17 @@
 {
     "name": "civicrm/civicrm-core:crossfilter-1.3.x",
-    "url": "https://github.com/crossfilter/crossfilter/archive/1.3.14.zip"
+    "url": "https://github.com/crossfilter/crossfilter/archive/1.3.14.zip",
+    "checksum": "0022d193efc89411ad7c0d2119cf9403ceea87db35341a357c310be6d2654625",
+    "ignore": [
+        ".*",
+        "node_modules",
+        "bower_components",
+        "src",
+        "lib",
+        "test",
+        "component.json",
+        "package.json",
+        "index.js",
+        "Makefile"
+    ]
 }
\ No newline at end of file
diff --git a/civicrm/bower_components/crossfilter2/.composer-downloads/crossfilter2-cfc7aab525b6a272826f0d7b1046426e.json b/civicrm/bower_components/crossfilter2/.composer-downloads/crossfilter2-cfc7aab525b6a272826f0d7b1046426e.json
index f5dd634474b558313fa1e9384dcb426fc2f8897a..425db5066146f659d79eedabbeedd2832252e8c4 100644
--- a/civicrm/bower_components/crossfilter2/.composer-downloads/crossfilter2-cfc7aab525b6a272826f0d7b1046426e.json
+++ b/civicrm/bower_components/crossfilter2/.composer-downloads/crossfilter2-cfc7aab525b6a272826f0d7b1046426e.json
@@ -1,4 +1,17 @@
 {
     "name": "civicrm/civicrm-core:crossfilter2",
-    "url": "https://github.com/crossfilter/crossfilter/archive/1.4.7.zip"
+    "url": "https://github.com/crossfilter/crossfilter/archive/1.4.7.zip",
+    "checksum": "a50af5c806340de7b202aeb88d52d69cb6ae4e8f9b1434e75a5c5d8623b3d99e",
+    "ignore": [
+        ".*",
+        "node_modules",
+        "bower_components",
+        "package.json",
+        "index.js",
+        "src",
+        "component.json",
+        "media",
+        "test",
+        "tests"
+    ]
 }
\ No newline at end of file
diff --git a/civicrm/bower_components/css-color-names/.composer-downloads/css-color-names-54216149e268d2a17ad72fce05bfdc93.json b/civicrm/bower_components/css-color-names/.composer-downloads/css-color-names-54216149e268d2a17ad72fce05bfdc93.json
index 48818eca5017d8eec2535f872198c352a7bb5b1e..0e7bed1fab4f31dda986a1a0e66f6f41dbc56996 100644
--- a/civicrm/bower_components/css-color-names/.composer-downloads/css-color-names-54216149e268d2a17ad72fce05bfdc93.json
+++ b/civicrm/bower_components/css-color-names/.composer-downloads/css-color-names-54216149e268d2a17ad72fce05bfdc93.json
@@ -1,4 +1,6 @@
 {
     "name": "civicrm/civicrm-core:css-color-names",
-    "url": "https://github.com/bahamas10/css-color-names/archive/v1.0.1.zip"
+    "url": "https://github.com/bahamas10/css-color-names/archive/v1.0.1.zip",
+    "checksum": "b1d0dfcf8d881be9f13ccaad804d700f23edb51dba6cdeefba6c7134e11ba12d",
+    "ignore": null
 }
\ No newline at end of file
diff --git a/civicrm/bower_components/d3-3.5.x/.composer-downloads/d3-3.5.x-3ba96c298dad99990feb13a2bc313897.json b/civicrm/bower_components/d3-3.5.x/.composer-downloads/d3-3.5.x-3ba96c298dad99990feb13a2bc313897.json
index f7a4dc38bb392ff461d205fdb97f4c77ebe3a6f9..5ae022ca1524e2840482c48df5cda13272b31dd1 100644
--- a/civicrm/bower_components/d3-3.5.x/.composer-downloads/d3-3.5.x-3ba96c298dad99990feb13a2bc313897.json
+++ b/civicrm/bower_components/d3-3.5.x/.composer-downloads/d3-3.5.x-3ba96c298dad99990feb13a2bc313897.json
@@ -1,4 +1,6 @@
 {
     "name": "civicrm/civicrm-core:d3-3.5.x",
-    "url": "https://github.com/mbostock-bower/d3-bower/archive/v3.5.17.zip"
+    "url": "https://github.com/mbostock-bower/d3-bower/archive/v3.5.17.zip",
+    "checksum": "d6836da86c261cc430dbf838751e5fa33173d26115e8a7032819f59f442589a9",
+    "ignore": null
 }
\ No newline at end of file
diff --git a/civicrm/bower_components/d3/.composer-downloads/d3-e53125275854402400f74fd6ab3f7659.json b/civicrm/bower_components/d3/.composer-downloads/d3-e53125275854402400f74fd6ab3f7659.json
index 3ac99310416fde4a44921ad3a2db3e472ef74eb2..568d992d1dd65f58bc208a1362f27ae7fdd9114a 100644
--- a/civicrm/bower_components/d3/.composer-downloads/d3-e53125275854402400f74fd6ab3f7659.json
+++ b/civicrm/bower_components/d3/.composer-downloads/d3-e53125275854402400f74fd6ab3f7659.json
@@ -1,4 +1,21 @@
 {
     "name": "civicrm/civicrm-core:d3",
-    "url": "https://github.com/mbostock-bower/d3-bower/archive/v3.4.11.zip"
+    "url": "https://github.com/mbostock-bower/d3-bower/archive/v3.4.11.zip",
+    "checksum": "7bcf5e3ea68dc255c1049e3fcf42e6a2b7e65dc53d49481d91e0984ef797877f",
+    "ignore": [
+        ".DS_Store",
+        ".git",
+        ".gitignore",
+        ".npmignore",
+        ".travis.yml",
+        "Makefile",
+        "bin",
+        "component.json",
+        "index.js",
+        "lib",
+        "node_modules",
+        "package.json",
+        "src",
+        "test"
+    ]
 }
\ No newline at end of file
diff --git a/civicrm/bower_components/datatables/.composer-downloads/datatables-06669348abd69fdff10f03f7c7ff1571.json b/civicrm/bower_components/datatables/.composer-downloads/datatables-06669348abd69fdff10f03f7c7ff1571.json
index 326f23e4563737dae7c102ac8a39a5688701f871..9e834db269e96dd7c5afc0b0ff68524f33f8eff4 100644
--- a/civicrm/bower_components/datatables/.composer-downloads/datatables-06669348abd69fdff10f03f7c7ff1571.json
+++ b/civicrm/bower_components/datatables/.composer-downloads/datatables-06669348abd69fdff10f03f7c7ff1571.json
@@ -1,4 +1,13 @@
 {
     "name": "civicrm/civicrm-core:datatables",
-    "url": "https://github.com/DataTables/DataTables/archive/1.10.19.zip"
+    "url": "https://github.com/DataTables/DataTables/archive/1.10.19.zip",
+    "checksum": "ec4dbe239d1959e1022b4f755dde98b3105b62a7c0728ebbcb738e2d9038b013",
+    "ignore": [
+        "/.*",
+        "examples",
+        "media/unit_testing",
+        "composer.json",
+        "dataTables.jquery.json",
+        "package.json"
+    ]
 }
\ No newline at end of file
diff --git a/civicrm/bower_components/dc-2.1.x/.composer-downloads/dc-2.1.x-ea78359606fb2b93565a6497513116e7.json b/civicrm/bower_components/dc-2.1.x/.composer-downloads/dc-2.1.x-ea78359606fb2b93565a6497513116e7.json
index 7ef3ee7dfbd55a9b7179c80826fb32cbe00ee6ef..a0c3e56fbec658b0384574158415cf2a4d97c1b3 100644
--- a/civicrm/bower_components/dc-2.1.x/.composer-downloads/dc-2.1.x-ea78359606fb2b93565a6497513116e7.json
+++ b/civicrm/bower_components/dc-2.1.x/.composer-downloads/dc-2.1.x-ea78359606fb2b93565a6497513116e7.json
@@ -1,4 +1,25 @@
 {
     "name": "civicrm/civicrm-core:dc-2.1.x",
-    "url": "https://github.com/NickQiZhu/dc.js/archive/2.1.10.zip"
+    "url": "https://github.com/NickQiZhu/dc.js/archive/2.1.10.zip",
+    "checksum": "8b35c4d5111c3098b82b91200140f56634b1ac8284993e9125263fd124148ed3",
+    "ignore": [
+        ".*",
+        "style",
+        "web",
+        "*.json",
+        "regression",
+        "scripts",
+        "spec",
+        "src",
+        "docs",
+        "grunt",
+        "Gruntfile.js",
+        "Changelog.md",
+        "welcome.md",
+        "class-hierarchy.dot",
+        "index.js",
+        "CONTRIBUTING.md",
+        "LICENSE_BANNER",
+        "AUTHORS"
+    ]
 }
\ No newline at end of file
diff --git a/civicrm/bower_components/es6-promise/.composer-downloads/es6-promise-60df2490a63990439db23398a56349b2.json b/civicrm/bower_components/es6-promise/.composer-downloads/es6-promise-60df2490a63990439db23398a56349b2.json
index ed3cc5662f1f2cae374e5e6d309da1869c84198a..9ae139f2faf0b4db26342db2152feaf905d3983d 100644
--- a/civicrm/bower_components/es6-promise/.composer-downloads/es6-promise-60df2490a63990439db23398a56349b2.json
+++ b/civicrm/bower_components/es6-promise/.composer-downloads/es6-promise-60df2490a63990439db23398a56349b2.json
@@ -1,4 +1,6 @@
 {
     "name": "civicrm/civicrm-core:es6-promise",
-    "url": "https://github.com/components/es6-promise/archive/v4.2.4.zip"
+    "url": "https://github.com/components/es6-promise/archive/v4.2.4.zip",
+    "checksum": "383cbddf53fc4153a2bae1ead8b25d03e86997d09e9f7e4622de6b8a85fe07fc",
+    "ignore": null
 }
\ No newline at end of file
diff --git a/civicrm/bower_components/font-awesome/.composer-downloads/font-awesome-32b121f1e564c015b458c30a6337ac1b.json b/civicrm/bower_components/font-awesome/.composer-downloads/font-awesome-32b121f1e564c015b458c30a6337ac1b.json
index a7cc944ae518e563d7f52fa2dbbfb1a2576d3345..d3474547a53d0bda314b968c4230258daed20e22 100644
--- a/civicrm/bower_components/font-awesome/.composer-downloads/font-awesome-32b121f1e564c015b458c30a6337ac1b.json
+++ b/civicrm/bower_components/font-awesome/.composer-downloads/font-awesome-32b121f1e564c015b458c30a6337ac1b.json
@@ -1,4 +1,14 @@
 {
     "name": "civicrm/civicrm-core:font-awesome",
-    "url": "https://github.com/FortAwesome/Font-Awesome/archive/v4.7.0.zip"
+    "url": "https://github.com/FortAwesome/Font-Awesome/archive/v4.7.0.zip",
+    "checksum": "e36b674d1b841bf063e56e04fa0f9bd79df1cc8d968f5b07e42d6aa54b7b4e01",
+    "ignore": [
+        "*/.*",
+        "*.json",
+        "src",
+        "*.yml",
+        "Gemfile",
+        "Gemfile.lock",
+        "*.md"
+    ]
 }
\ No newline at end of file
diff --git a/civicrm/bower_components/google-code-prettify/.composer-downloads/google-code-prettify-8b46b49e999a9774c040fd46f81a68a5.json b/civicrm/bower_components/google-code-prettify/.composer-downloads/google-code-prettify-8b46b49e999a9774c040fd46f81a68a5.json
index 5104588da1d9f8c5fad40bb9e19cc5f43c333a38..39173a30ce40b275cf1804864af80300b6c15d1a 100644
--- a/civicrm/bower_components/google-code-prettify/.composer-downloads/google-code-prettify-8b46b49e999a9774c040fd46f81a68a5.json
+++ b/civicrm/bower_components/google-code-prettify/.composer-downloads/google-code-prettify-8b46b49e999a9774c040fd46f81a68a5.json
@@ -1,4 +1,15 @@
 {
     "name": "civicrm/civicrm-core:google-code-prettify",
-    "url": "https://github.com/tcollard/google-code-prettify/archive/v1.0.5.zip"
+    "url": "https://github.com/tcollard/google-code-prettify/archive/v1.0.5.zip",
+    "checksum": "4ce1fad9f2051267ebea11dccb1ed6eb82c031eaf5ee0897bbe03f7e47200511",
+    "ignore": [
+        "closure-compiler",
+        "js-modules",
+        "tests",
+        "yui-compressor",
+        "Makefile",
+        "examples",
+        "*.html",
+        "run_prettify*js"
+    ]
 }
\ No newline at end of file
diff --git a/civicrm/bower_components/google-code-prettify/CHANGES.html b/civicrm/bower_components/google-code-prettify/CHANGES.html
deleted file mode 100644
index de9e2b79116af2515c42c59feafd36a6a3fd497c..0000000000000000000000000000000000000000
--- a/civicrm/bower_components/google-code-prettify/CHANGES.html
+++ /dev/null
@@ -1,172 +0,0 @@
-<html>
-  <head>
-    <meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
-    <title>Change Log</title>
-  </head>
-  <body bgcolor="white">
-    <a style="float:right" href="README.html">README</a>
-
-    <h1>Known Issues</h1>
-    <ul>
-      <li>Perl formatting is really crappy.  Partly because the author is lazy and
-      partly because Perl is
-      <a href="http://www.perlmonks.org/?node_id=663393">hard</a> to parse.
-      <li>On some browsers, <code>&lt;code&gt;</code> elements with newlines in the text
-      which use CSS to specify <code>white-space:pre</code> will have the newlines
-      improperly stripped if the element is not attached to the document at the time
-      the stripping is done.  Also, on IE 6, all newlines will be stripped from
-      <code>&lt;code&gt;</code> elements because of the way IE6 produces
-      <code>innerHTML</code>.  Workaround: use <code>&lt;pre&gt;</code> for code with
-      newlines.
-    </ul>
-
-    <h1>Change Log</h1>
-    <h2>29 March 2007</h2>
-    <ul>
-      <li>Added <a href="tests/prettify_test.html#PHP">tests</a> for PHP support
-        to address
-      <a href="http://code.google.com/p/google-code-prettify/issues/detail?id=3"
-       >issue 3</a>.
-      <li>Fixed
-      <a href="http://code.google.com/p/google-code-prettify/issues/detail?id=6"
-       >bug</a>: <code>prettyPrintOne</code> was not halting.  This was not
-        reachable through the normal entry point.
-      <li>Fixed
-      <a href="http://code.google.com/p/google-code-prettify/issues/detail?id=4"
-       >bug</a>: recursing into a script block or PHP tag that was not properly
-        closed would not silently drop the content.
-        (<a href="tests/prettify_test.html#issue4">test</a>)
-      <li>Fixed
-      <a href="http://code.google.com/p/google-code-prettify/issues/detail?id=8"
-       >bug</a>: was eating tabs
-        (<a href="tests/prettify_test.html#issue8">test</a>)
-      <li>Fixed entity handling so that the caveat
-        <blockquote>
-          <p>Caveats: please properly escape less-thans.  <tt>x&amp;lt;y</tt>
-          instead of <tt>x&lt;y</tt>, and use <tt>&quot;</tt> instead of
-          <tt>&amp;quot;</tt> for string delimiters.</p>
-        </blockquote>
-        is no longer applicable.
-      <li>Added noisefree's C#
-      <a href="http://code.google.com/p/google-code-prettify/issues/detail?id=4"
-       >patch</a>
-      <li>Added a <a href="http://google-code-prettify.googlecode.com/files/prettify-small.zip">distribution</a> that has comments and
-        whitespace removed to reduce download size from 45.5kB to 12.8kB.
-    </ul>
-    <h2>4 Jul 2008</h2>
-    <ul>
-      <li>Added <a href="http://code.google.com/p/google-code-prettify/issues/detail?id=17">language specific formatters</a> that are triggered by the presence
-      of a <code>lang-&lt;language-file-extension&gt;</code></li>
-      <li>Fixed <a href="http://code.google.com/p/google-code-prettify/issues/detail?id=29">bug</a>: python handling of <code>'''string'''</code>
-      <li>Fixed bug: <code>/</code> in regex <code>[charsets] should not end regex</code>
-    </ul>
-    <h2>5 Jul 2008</h2>
-    <ul>
-      <li>Defined language extensions for Lisp and Lua</code>
-    </ul>
-    <h2>14 Jul 2008</h2>
-    <ul>
-      <li>Language handlers for F#, OCAML, SQL</code>
-      <li>Support for <code>nocode</code> spans to allow embedding of line
-      numbers and code annotations which should not be styled or otherwise
-      affect the tokenization of prettified code.
-      See the issue 22
-      <a href="tests/prettify_test.html#issue22">testcase</a>.</code>
-    </ul>
-    <h2>6 Jan 2009</h2>
-    <ul>
-      <li>Language handlers for Visual Basic, Haskell, CSS, and WikiText</li>
-      <li>Added <tt>.mxml</tt> extension to the markup style handler for
-        Flex <a href="http://en.wikipedia.org/wiki/MXML">MXML files</a>.  See
-        <a
-        href="http://code.google.com/p/google-code-prettify/issues/detail?id=37"
-        >issue 37</a>.
-      <li>Added <tt>.m</tt> extension to the C style handler so that Objective
-        C source files properly highlight.  See
-        <a
-        href="http://code.google.com/p/google-code-prettify/issues/detail?id=58"
-       >issue 58</a>.
-      <li>Changed HTML lexer to use the same embedded source mechanism as the
-        wiki language handler, and changed to use the registered
-        CSS handler for STYLE element content.
-    </ul>
-    <h2>21 May 2009</h2>
-    <ul>
-      <li>Rewrote to improve performance on large files.
-        See <a href="http://mikesamuel.blogspot.com/2009/05/efficient-parsing-in-javascript.html">benchmarks</a>.</li>
-      <li>Fixed bugs with highlighting of Haskell line comments, Lisp
-        number literals, Lua strings, C preprocessor directives,
-        newlines in Wiki code on Windows, and newlines in IE6.</li>
-    </ul>
-    <h2>14 August 2009</h2>
-    <ul>
-      <li>Fixed prettifying of <code>&lt;code&gt;</code> blocks with embedded newlines.
-    </ul>
-    <h2>3 October 2009</h2>
-    <ul>
-      <li>Fixed prettifying of XML/HTML tags that contain uppercase letters.
-    </ul>
-    <h2>19 July 2010</h2>
-    <ul>
-      <li>Added support for line numbers.  Bug
-        <a href="http://code.google.com/p/google-code-prettify/issues/detail?id=22"
-         >22</a></li>
-      <li>Added YAML support.  Bug
-        <a href="http://code.google.com/p/google-code-prettify/issues/detail?id=123"
-         >123</a></li>
-      <li>Added VHDL support courtesy Le Poussin.</li>
-      <li>IE performance improvements.  Bug
-        <a href="http://code.google.com/p/google-code-prettify/issues/detail?id=102"
-         >102</a> courtesy jacobly.</li>
-      <li>A variety of markup formatting fixes courtesy smain and thezbyg.</li>
-      <li>Fixed copy and paste in IE[678].
-      <li>Changed output to use <code>&amp;#160;</code> instead of
-        <code>&amp;nbsp;</code> so that the output works when embedded in XML.
-        Bug
-        <a href="http://code.google.com/p/google-code-prettify/issues/detail?id=108"
-         >108</a>.</li>
-    </ul>
-    <h2>7 September 2010</h2>
-    <ul>
-      <li>Added support for coffeescript courtesy Cezary Bartoszuk.</li>
-    </ul>
-    <h2>4 March 2011</h2>
-    <ul>
-      <li>Added a <a href="http://google-code-prettify.googlecode.com/svn/trunk/styles/index.html">themes
-      gallery</a> to showcase contributed styles.</li>
-      <li>Added support for XQuery courtesy Patrick Wied, Nemerle
-      courtesy Zimin A.V., and Latex support courtesy Martin S.</li>
-    </ul>
-    <h2>29 March 2011</h2>
-    <ul>
-      <li>Fixed IE newline issues, and copying/pasting of prettified
-      source code from IE.  This required significant internal changes
-      but involves no API changes.
-      <b>Caveat:</b> <code>prettyPrintOne</code> injects the HTML
-      passed to it into a <code>&lt;pre&gt;</code> element.
-      If the HTML comes from a trusted source, this may allow XSS.
-      Do not do this.  This should not be a problem for existing apps
-      since the standard usage is to rewrite the HTML and then inject
-      it, so anyone doing that with untrusted HTML already has an XSS
-      vulnerability.  If you sanitize and prettify HTML from an
-      untrusted source, sanitize first.
-    </ul>
-    <h2>4 February 2013</h2>
-    <ul>
-      <li>Language handlers for Dart, Erlang, Mumps, TCL, R, S., and others</li>
-      <li>Bug fix: VB REM style comments.</li>
-      <li>Bug fix: CSS color literals / ID selector confusion.</li>
-      <li>Bug fix: IE8 line breaks.</li>
-    </ul>
-    <h2>24 February 2013</h2>
-    <ul>
-      <li>Added a one script autoload&amp;run mechanism and a way to
-          embed hints in processing instructions/comments.
-          See <a href="examples/quine.html">example</a>.
-    </ul>
-    <h2>4 March 2013</h2>
-    <ul>
-      <li>Matlab language handler courtesy Amro&#xb3;</li>
-    </ul>
-  </body>
-</html>
diff --git a/civicrm/bower_components/google-code-prettify/README-zh-Hans.html b/civicrm/bower_components/google-code-prettify/README-zh-Hans.html
deleted file mode 100644
index b92e3c0fb879ce940635e67dc0ca4e1e189e2502..0000000000000000000000000000000000000000
--- a/civicrm/bower_components/google-code-prettify/README-zh-Hans.html
+++ /dev/null
@@ -1,143 +0,0 @@
-<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
- "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
-
-<html>
-  <head>
-    <meta http-equiv="content-type" value="text/html; charset=UTF-8" />
-    <title>Javascript code prettifier</title>
-
-    <link href="src/prettify.css" type="text/css" rel="stylesheet" />
-
-    <script src="src/prettify.js" type="text/javascript"></script>
-
-    <style type="text/css">
-      body { margin-left: .5in }
-      h1, h2, h3, h4, .footer { margin-left: -.4in; }
-    </style>
-  </head>
-
-  <body onload="prettyPrint()" bgcolor="white">
-    <h1>Javascript code prettifier</h1>
-	<h1>Javascript 代码美容师</h1>
-    <h2>安装使用</h2>
-    <ol>
-      <li><a href="http://google-code-prettify.googlecode.com/files/prettify-small-5-Jul-2008.zip">下载</a> 文件
-      <li>在你的文件中包含这儿的脚本和样式表(你要保证这儿的 css 和 js 文件按在你的服务器上, 并且调整在 <tt>script</tt> 和 <tt>link</tt>标签中的路径)
-        <pre class="prettyprint">
-&lt;link href="prettify.css" type="text/css" rel="stylesheet" />
-&lt;script type="text/javascript" src="prettify.js">&lt;/script></pre>
-      <li>添加<code class="prettyprint">onload="prettyPrint()"</code> 到你的文件的 body 标签中.
-      <li>修改样式表,使用你自己喜欢的颜色.</li>
-    </ol>
-
-    <h2>使用方法<br></h2>
-    <p>在
-    <tt>&lt;pre class="prettyprint"&gt;...&lt;/pre&gt;</tt> 或 <tt>&lt;code class="prettyprint"&gt;...&lt;/code&gt;</tt>
-    中间放上代码片段,它就会自动被美化了.
-
-    <table summary="code examples">
-      <tr>
-        <th>The original
-        <th>Prettier
-      <tr>
-        <td><pre style="border: 1px solid #888;padding: 2px"
-             ><a name="voila1"></a>class Voila {
-public:
-  // Voila
-  static const string VOILA = "Voila";
-
-  // will not interfere with embedded <a href="#voila1">tags</a>.
-}</pre>
-
-        <td><pre class="prettyprint"><a name="voila2"></a>class Voila {
-public:
-  // Voila
-  static const string VOILA = "Voila";
-
-  // will not interfere with embedded <a href="#voila2">tags</a>.
-}</pre>
-    </table>
-
-    
-    <h2>常见问题</h2>
-    <h3 id="langs">它是为什么语言工作的?</h3>
-    <p><tt>prettify.js中的注释是权威的,但是它的语法分析程序可以在很多语言中使用</tt>,包括 C ,
-    Java, Python, Bash, SQL, HTML, XML, CSS, Javascript, 和 Makefiles.
-    它在 Ruby, PHP, VB, 和 Awk 中还算可以,而且也可以在 Perl 和 Ruby的合适子集中起作用,但是, 因为注释的约定,它对
-    Smalltalk, 或 CAML类似的语言起作用.<br></p>
-
-    
-    <p>LISP系列的语言可以使用一个拓展<a href="http://code.google.com/p/google-code-prettify/source/browse/trunk/src/lang-lisp.js"><code>lang-lisp.js</code></a>.</p><p>对于 <a href="http://code.google.com/p/google-code-prettify/source/browse/trunk/src/lang-css"><code>CSS</code></a>,
-    <a href="http://code.google.com/p/google-code-prettify/source/browse/trunk/src/lang-hs"><code>Haskell</code></a>,
-    <a href="http://code.google.com/p/google-code-prettify/source/browse/trunk/src/lang-lua.js"><code>Lua</code></a>,
-    <a href="http://code.google.com/p/google-code-prettify/source/browse/trunk/src/lang-ml.js"><code>OCAML, SML, F#</code></a>,
-    <a href="http://code.google.com/p/google-code-prettify/source/browse/trunk/src/lang-vb.js"><code>Visual Basic</code></a>,
-    <a href="http://code.google.com/p/google-code-prettify/source/browse/trunk/src/lang-sql.js"><code>SQL</code></a>,
-    <a href="http://code.google.com/p/google-code-prettify/source/browse/trunk/src/lang-proto.js"><code>Protocol Buffers</code></a>, 和
-    <a href="http://code.google.com/p/google-code-prettify/source/browse/trunk/src/lang-wiki.js"><code>WikiText</code></a>..也是类似的</p><p>如果你想给你喜欢的语言写个拓展版本, 请参阅<tt>src/lang-lisp.js</tt> ,并写一个包括你的语言的拓展的 <a href="http://code.google.com/p/google-code-prettify/issues/list"
-     >发布</a> 和一个测试用例.</p>
-
-    <h3>如何指定我的代码在哪种语言里?</h3>
-    <p>你不需要指定语言环境,因为 <code>prettyprint()</code>
-    会对此进行猜测.  你可以使用<code> prettyprint </code>这个类通过指定语言的拓展名来指定语言,就像这样:</p>
-    <pre class="prettyprint lang-html"
->&lt;pre class=&quot;prettyprint <b>lang-html</b>&quot;&gt;
-  The lang-* class specifies the language file extensions.
-  File extensions supported by default include
-    "bsh", "c", "cc", "cpp", "cs", "csh", "cyc", "cv", "htm", "html",
-    "java", "js", "m", "mxml", "perl", "pl", "pm", "py", "rb", "sh",
-    "xhtml", "xml", "xsl".
-&lt;/pre&gt;</pre>
-
-    <h3>它在混淆代码例子上不起作用吗?</h3>
-    <p>是的.  美化混淆代码就像给小猪涂口红,也就是不在这个工具的范围内. <br></p>
-
-    <h3>它可以在那些浏览器上工作?</h3>
-    <p>这个工具已经在 IE 6, Firefox 1.5 &amp; 2, 和 Safari 2.0.4 上测试通过. 打开 <a href="tests/prettify_test.html">测试页面</a> ,看看它能不能在你的浏览器上起作用.</p>
-
-    <h3>有什么改变?</h3>
-    <p>查看 <a href="CHANGES.html">变化日志</a></p>
-
-    <h3>&nbsp;为什么Prettyprinting 对WordPress中的字符串没用?</h3>
-    <p>很显然,wordpress 在 &quot;smart quoting&quot; 时会改变关闭符号.
-    这使得关闭符号跟开始符号不配套.
-    <p>这和复制粘贴代码一样,破坏了美化作用. 去
-    <a href="http://wordpress.org/support/topic/125038"
-    >WordPress's help center</a> 查看更多关于如何关闭插入代码段时的&quot;smart quoting&quot;的信息.</p>
-
-    <h3>如何在我的代码中加入行号?  (Out of date -- see <a href="README.html">English version</a>)</h3>
-    <p>你可以使用 <code>nocode</code> 类来标记 span 标记不是代码.
-<pre>&lt;pre class=prettyprint&gt;
-&lt;span class="<b>nocode</b>"&gt;1:&lt;/span&gt; /* This is line 1 of my code
-&lt;span class="<b>nocode</b>"&gt;2:&lt;/span&gt;  * and here's line 2 */
-&lt;span class="<b>nocode</b>"&gt;3:&lt;/span&gt; print("I'm line number 3");
-&lt;/pre&gt;</pre>得到
-<pre class=prettyprint>
-<span class="nocode">1:</span> /* This is line 1 of my code
-<span class="nocode">2:</span>  * and here's line 2 */
-<span class="nocode">3:</span> print("I'm line number 3");
-</pre>
-
-    <p>查看一个更完整的例子: issue22
-    <a href="tests/prettify_test.html#issue22">testcase</a>.</p>
-
-    <h3>我得到了这样一条错误信息 &quot;a is not a function&quot; 或 &quot;opt_whenDone is not a function&quot;</h3>
-    <p>如果你通过事件句柄条用 <code>prettyPrint</code> , 把它隐藏到一个函数中. <br></p><p>不要这么写
-    </p><blockquote>
-      <code class="prettyprint lang-js"
-       >addEventListener('load', prettyPrint, false);</code>
-    </blockquote>而要这么写
-    <blockquote>
-      <code class="prettyprint lang-js"
-       >addEventListener('load', function (event) { prettyPrint() }, false);</code>
-    </blockquote>这样的话,浏览器就不会把时间对象传递给 <code>prettyPrint</code> ,事件对象会让它困惑的.
-
-    <br><br><br>
-
-    <div class="footer">
-<!-- Created: Tue Oct  3 17:51:56 PDT 2006 -->
-<!-- hhmts start -->
-Last modified: Wed Jan  7 13:25:42 PST 2009<br><!-- hhmts end -->
-    </div>
-  </body>
-</html>
diff --git a/civicrm/bower_components/google-code-prettify/README.html b/civicrm/bower_components/google-code-prettify/README.html
deleted file mode 100644
index d1fd4a1f8dab6e1fb301d091ca76d5e13deec1ac..0000000000000000000000000000000000000000
--- a/civicrm/bower_components/google-code-prettify/README.html
+++ /dev/null
@@ -1,233 +0,0 @@
-<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
- "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
-
-<html>
-  <head>
-    <title>Javascript code prettifier</title>
-
-    <link href="src/prettify.css" type="text/css" rel="stylesheet" />
-
-    <script src="src/prettify.js" type="text/javascript"></script>
-
-    <style type="text/css">
-      body { margin-left: .5in }
-      h1, h2, h3, h4, .footer { margin-left: -.4in; }
-      a.Extension { display: inline-block; width: 5em; height:2.5em; border: 1px solid black; vertical-align: top; text-align: center }
-    </style>
-  </head>
-
-  <body onload="prettyPrint()" bgcolor="white">
-    <small style="float: right">Languages : <a href="README-zh-Hans.html">CH</a></small>
-    <h1>Javascript code prettifier</h1>
-
-    <h2>Setup</h2>
-    <ol>
-      <li><a href="http://code.google.com/p/google-code-prettify/downloads/list">Download</a> a distribution
-      <li>Include the script tag below in your document
-        <pre class="prettyprint">
-&gt;script src="https://google-code-prettify.googlecode.com/svn/loader/run_prettify.js&gt;&lt;/script&gt;</pre>
-      <li>See <a href="http://code.google.com/p/google-code-prettify/wiki/GettingStarted">Getting Started</a> to configure that URL with options you need.</a>
-      <li>Look at the <a href="http://google-code-prettify.googlecode.com/svn/trunk/styles/index.html">skin gallery</a> and pick styles that suit you.</li>
-    </ol>
-
-    <h2>Usage</h2>
-    <p>Put code snippets in
-    <tt>&lt;pre class="prettyprint"&gt;...&lt;/pre&gt;</tt>
-    or <tt>&lt;code class="prettyprint"&gt;...&lt;/code&gt;</tt>
-    and it will automatically be pretty printed.
-
-    <table summary="code examples">
-      <tr>
-        <th>The original
-        <th>Prettier
-      <tr>
-        <td><pre style="border: 1px solid #888;padding: 2px"
-             ><a name="voila1"></a>class Voila {
-public:
-  // Voila
-  static const string VOILA = "Voila";
-
-  // will not interfere with embedded <a href="#voila1">tags</a>.
-}</pre>
-
-        <td><pre class="prettyprint"><a name="voila2"></a>class Voila {
-public:
-  // Voila
-  static const string VOILA = "Voila";
-
-  // will not interfere with embedded <a href="#voila2">tags</a>.
-}</pre>
-    </table>
-
-    <h2>FAQ</h2>
-    <h3 id="langs">For which languages does it work?</h3>
-    <p>The comments in <tt>prettify.js</tt> are authoritative but the lexer
-    should work on a number of languages including C and friends,
-    Java, Python, Bash, SQL, HTML, XML, CSS, Javascript, Makefiles,
-    and Rust.
-    It works passably on Ruby, PHP, VB, and Awk and a decent subset of Perl
-    and Ruby, but, because of commenting conventions, but doesn't work on
-    Smalltalk.</p>
-
-    <p>Other languages are supported via extensions:
-    <div>
-      <a class="Extension" href="http://code.google.com/p/google-code-prettify/source/browse/trunk/src/lang-apollo.js">Apollo</a>
-      <a class="Extension" href="http://code.google.com/p/google-code-prettify/source/browse/trunk/src/lang-basic.js">Basic</a>
-      <a class="Extension" href="http://code.google.com/p/google-code-prettify/source/browse/trunk/src/lang-clj.js">Clojure</a>
-      <a class="Extension" href="http://code.google.com/p/google-code-prettify/source/browse/trunk/src/lang-css.js">CSS</a>
-      <a class="Extension" href="http://code.google.com/p/google-code-prettify/source/browse/trunk/src/lang-dart.js">Dart</a>
-      <a class="Extension" href="http://code.google.com/p/google-code-prettify/source/browse/trunk/src/lang-erlang.js">Erlang</a>
-      <a class="Extension" href="http://code.google.com/p/google-code-prettify/source/browse/trunk/src/lang-go.js">Go</a>
-      <a class="Extension" href="http://code.google.com/p/google-code-prettify/source/browse/trunk/src/lang-hs.js">Haskell</a>
-      <a class="Extension" href="http://code.google.com/p/google-code-prettify/source/browse/trunk/src/lang-lisp.js">Lisp, Scheme</a>
-      <a class="Extension" href="http://code.google.com/p/google-code-prettify/source/browse/trunk/src/lang-llvm.js">Llvm</a>
-      <a class="Extension" href="http://code.google.com/p/google-code-prettify/source/browse/trunk/src/lang-lua.js">Lua</a>
-      <a class="Extension" href="http://code.google.com/p/google-code-prettify/source/browse/trunk/src/lang-matlab.js">Matlab</a>
-      <a class="Extension" href="http://code.google.com/p/google-code-prettify/source/browse/trunk/src/lang-ml.js">MLs:F#, Ocaml,SML</a>
-      <a class="Extension" href="http://code.google.com/p/google-code-prettify/source/browse/trunk/src/lang-mumps.js">Mumps</a>
-      <a class="Extension" href="http://code.google.com/p/google-code-prettify/source/browse/trunk/src/lang-n.js">Nemerle</a>
-      <a class="Extension" href="http://code.google.com/p/google-code-prettify/source/browse/trunk/src/lang-pascal.js">Pascal</a>
-      <a class="Extension" href="http://code.google.com/p/google-code-prettify/source/browse/trunk/src/lang-proto.js">Protocol buffers</a>
-      <a class="Extension" href="http://code.google.com/p/google-code-prettify/source/browse/trunk/src/lang-r.js">R, S</a>
-      <a class="Extension" href="http://code.google.com/p/google-code-prettify/source/browse/trunk/src/lang-rd.js">RD</a>
-      <a class="Extension" href="http://code.google.com/p/google-code-prettify/source/browse/trunk/src/lang-scala.js">Scala</a>
-      <a class="Extension" href="http://code.google.com/p/google-code-prettify/source/browse/trunk/src/lang-sql.js">SQL</a>
-      <a class="Extension" href="http://code.google.com/p/google-code-prettify/source/browse/trunk/src/lang-tcl.js">TCL</a>
-      <a class="Extension" href="http://code.google.com/p/google-code-prettify/source/browse/trunk/src/lang-tex.js">Latek</a>
-      <a class="Extension" href="http://code.google.com/p/google-code-prettify/source/browse/trunk/src/lang-vb.js">Visual Basic</a>
-      <a class="Extension" href="http://code.google.com/p/google-code-prettify/source/browse/trunk/src/lang-vhdl.js">CHDL</a>
-      <a class="Extension" href="http://code.google.com/p/google-code-prettify/source/browse/trunk/src/lang-wiki.js">Wiki</a>
-      <a class="Extension" href="http://code.google.com/p/google-code-prettify/source/browse/trunk/src/lang-xq.js">XQ</a>
-      <a class="Extension" href="http://code.google.com/p/google-code-prettify/source/browse/trunk/src/lang-yaml.js">YAML</a>
-    </div>
-
-    <p>If you'd like to add an extension for your favorite language, please
-    look at <tt>src/lang-lisp.js</tt> and file an
-    <a href="http://code.google.com/p/google-code-prettify/issues/list"
-     >issue</a> including your language extension, and a testcase.</p>
-
-    <h3>How do I specify the language of my code?</h3>
-    <p>You don't need to specify the language since <code>prettyprint()</code>
-    will guess.  You can specify a language by specifying the language extension
-    along with the <code>prettyprint</code> class like so:</p>
-    <pre class="prettyprint lang-html"
->&lt;pre class=&quot;prettyprint <b>lang-html</b>&quot;&gt;
-  The lang-* class specifies the language file extensions.
-  File extensions supported by default include
-    "bsh", "c", "cc", "cpp", "cs", "csh", "cyc", "cv", "htm", "html",
-    "java", "js", "m", "mxml", "perl", "pl", "pm", "py", "rb", "sh",
-    "xhtml", "xml", "xsl".
-&lt;/pre&gt;</pre>
-
-    <p>You may also use the
-    <a href="http://dev.w3.org/html5/spec-author-view/the-code-element.html#the-code-element"
-     >HTML 5</a> convention of embedding a <tt>code</tt> element inside the
-    <code>PRE</code> and using <code>language-java</code> style classes.
-    E.g. <xmp class="prettyprint"><pre class="prettyprint"><code class="language-java">...</code></pre></xmp>
-
-    <h3>It doesn't work on <tt>&lt;obfuscated code sample&gt;</tt>?</h3>
-    <p>Yes.  Prettifying obfuscated code is like putting lipstick on a pig
-    &mdash; i.e. outside the scope of this tool.</p>
-
-    <h3>Which browsers does it work with?</h3>
-    <p>It's been tested with IE 6, Firefox 1.5 &amp; 2, and Safari 2.0.4.
-    Look at <a href="tests/prettify_test.html">the test page</a> to see if it
-    works in your browser.</p>
-
-    <h3>What's changed?</h3>
-    <p>See the <a href="CHANGES.html">change log</a></p>
-
-    <h3>Why doesn't Prettyprinting of strings work on WordPress?</h3>
-    <p>Apparently wordpress does "smart quoting" which changes close quotes.
-    This causes end quotes to not match up with open quotes.
-    <p>This breaks prettifying as well as copying and pasting of code samples.
-    See
-    <a href="http://wordpress.org/support/topic/125038"
-    >WordPress's help center</a> for info on how to stop smart quoting of code
-    snippets.</p>
-
-    <h3 id="linenums">How do I put line numbers in my code?</h3>
-    <p>You can use the <code>linenums</code> class to turn on line
-    numbering.  If your code doesn't start at line number 1, you can
-    add a colon and a line number to the end of that class as in
-    <code>linenums:52</code>.
-
-    <p>For example
-<pre class="prettyprint">&lt;pre class="prettyprint linenums:<b>4</b>"
-&gt;// This is line 4.
-foo();
-bar();
-baz();
-boo();
-far();
-faz();
-&lt;pre&gt;</pre>
-    produces
-<pre class="prettyprint linenums:4"
->// This is line 4.
-foo();
-bar();
-baz();
-boo();
-far();
-faz();
-</pre>
-
-    <h3>How do I prevent a portion of markup from being marked as code?</h3>
-    <p>You can use the <code>nocode</code> class to identify a span of markup
-    that is not code.
-<pre class="prettyprint">&lt;pre class=prettyprint&gt;
-int x = foo();  /* This is a comment  &lt;span class="nocode"&gt;This is not code&lt;/span&gt;
-  Continuation of comment */
-int y = bar();
-&lt;/pre&gt;</pre>
-produces
-<pre class="prettyprint">
-int x = foo();  /* This is a comment  <span class="nocode">This is not code</span>
-  Continuation of comment */
-int y = bar();
-</pre>
-
-    <p>For a more complete example see the issue22
-    <a href="tests/prettify_test.html#issue22">testcase</a>.</p>
-
-    <h3>I get an error message "a is not a function" or "opt_whenDone is not a function"</h3>
-    <p>If you are calling <code>prettyPrint</code> via an event handler, wrap it in a function.
-    Instead of doing
-    <blockquote>
-      <code class="prettyprint lang-js"
-       >addEventListener('load', prettyPrint, false);</code>
-    </blockquote>
-    wrap it in a closure like
-    <blockquote>
-      <code class="prettyprint lang-js"
-       >addEventListener('load', function (event) { prettyPrint() }, false);</code>
-    </blockquote>
-    so that the browser does not pass an event object to <code>prettyPrint</code> which
-    will confuse it.
-
-    <h3>How can I customize the colors and styles of my code?</h3>
-    <p>
-    Prettify adds <code>&lt;span&gt;</code> with <code>class</code>es describing
-    the kind of code.  You can create CSS styles to matches these
-    classes.
-    See the
-    <a href="http://google-code-prettify.googlecode.com/svn/trunk/styles/index.html">
-    theme gallery</a> for examples.
-    </p>
-
-    <h3>I can't add classes to my code (because it comes from Markdown, etc.)</h3>
-    <p>
-    Instead of <code class="prettyprint">&lt;pre class="prettyprint ..."&gt;</code> you can use a
-    comment or processing instructions that survives processing instructions :
-    <code>&lt;?prettify ...?&gt;</code> works as explained in 
-    <a href="http://code.google.com/p/google-code-prettify/wiki/GettingStarted">Getting Started</a></p>
-
-    <br><br><br>
-
-    <div class="footer">
-<!-- Created: Tue Oct  3 17:51:56 PDT 2006 -->
-<!-- hhmts start -->Last modified: Mon Mar  4 14:16:04 EST 2013 <!-- hhmts end -->
-    </div>
-  </body>
-</html>
diff --git a/civicrm/bower_components/google-code-prettify/bin/run_prettify.min.js b/civicrm/bower_components/google-code-prettify/bin/run_prettify.min.js
deleted file mode 100644
index 9eb3e166f59f0c2d5d55d774c27d7bbecb0dd8a2..0000000000000000000000000000000000000000
--- a/civicrm/bower_components/google-code-prettify/bin/run_prettify.min.js
+++ /dev/null
@@ -1,34 +0,0 @@
-!function(){var r=null;
-(function(){function X(e){function j(){try{J.doScroll("left")}catch(e){P(j,50);return}w("poll")}function w(j){if(!(j.type=="readystatechange"&&x.readyState!="complete")&&((j.type=="load"?n:x)[z](i+j.type,w,!1),!m&&(m=!0)))e.call(n,j.type||j)}var Y=x.addEventListener,m=!1,C=!0,t=Y?"addEventListener":"attachEvent",z=Y?"removeEventListener":"detachEvent",i=Y?"":"on";if(x.readyState=="complete")e.call(n,"lazy");else{if(x.createEventObject&&J.doScroll){try{C=!n.frameElement}catch(A){}C&&j()}x[t](i+"DOMContentLoaded",
-w,!1);x[t](i+"readystatechange",w,!1);n[t](i+"load",w,!1)}}function Q(){S&&X(function(){var e=K.length;$(e?function(){for(var j=0;j<e;++j)(function(e){P(function(){n.exports[K[e]].apply(n,arguments)},0)})(j)}:void 0)})}for(var n=window,P=n.setTimeout,x=document,J=x.documentElement,L=x.head||x.getElementsByTagName("head")[0]||J,z="",A=x.scripts,m=A.length;--m>=0;){var M=A[m],T=M.src.match(/^[^#?]*\/run_prettify\.js(\?[^#]*)?(?:#.*)?$/);if(T){z=T[1]||"";M.parentNode.removeChild(M);break}}var S=!0,D=
-[],N=[],K=[];z.replace(/[&?]([^&=]+)=([^&]+)/g,function(e,j,w){w=decodeURIComponent(w);j=decodeURIComponent(j);j=="autorun"?S=!/^[0fn]/i.test(w):j=="lang"?D.push(w):j=="skin"?N.push(w):j=="callback"&&K.push(w)});m=0;for(z=D.length;m<z;++m)(function(){var e=x.createElement("script");e.onload=e.onerror=e.onreadystatechange=function(){if(e&&(!e.readyState||/loaded|complete/.test(e.readyState)))e.onerror=e.onload=e.onreadystatechange=r,--R,R||P(Q,0),e.parentNode&&e.parentNode.removeChild(e),e=r};e.type=
-"text/javascript";e.src="https://google-code-prettify.googlecode.com/svn/loader/lang-"+encodeURIComponent(D[m])+".js";L.insertBefore(e,L.firstChild)})(D[m]);for(var R=D.length,A=[],m=0,z=N.length;m<z;++m)A.push("https://google-code-prettify.googlecode.com/svn/loader/skins/"+encodeURIComponent(N[m])+".css");A.push("https://google-code-prettify.googlecode.com/svn/loader/prettify.css");(function(e){function j(m){if(m!==w){var n=x.createElement("link");n.rel="stylesheet";n.type="text/css";if(m+1<w)n.error=
-n.onerror=function(){j(m+1)};n.href=e[m];L.appendChild(n)}}var w=e.length;j(0)})(A);var $=function(){window.PR_SHOULD_USE_CONTINUATION=!0;var e;(function(){function j(a){function d(f){var b=f.charCodeAt(0);if(b!==92)return b;var a=f.charAt(1);return(b=i[a])?b:"0"<=a&&a<="7"?parseInt(f.substring(1),8):a==="u"||a==="x"?parseInt(f.substring(2),16):f.charCodeAt(1)}function h(f){if(f<32)return(f<16?"\\x0":"\\x")+f.toString(16);f=String.fromCharCode(f);return f==="\\"||f==="-"||f==="]"||f==="^"?"\\"+f:
-f}function b(f){var b=f.substring(1,f.length-1).match(/\\u[\dA-Fa-f]{4}|\\x[\dA-Fa-f]{2}|\\[0-3][0-7]{0,2}|\\[0-7]{1,2}|\\[\S\s]|[^\\]/g),f=[],a=b[0]==="^",c=["["];a&&c.push("^");for(var a=a?1:0,g=b.length;a<g;++a){var k=b[a];if(/\\[bdsw]/i.test(k))c.push(k);else{var k=d(k),o;a+2<g&&"-"===b[a+1]?(o=d(b[a+2]),a+=2):o=k;f.push([k,o]);o<65||k>122||(o<65||k>90||f.push([Math.max(65,k)|32,Math.min(o,90)|32]),o<97||k>122||f.push([Math.max(97,k)&-33,Math.min(o,122)&-33]))}}f.sort(function(f,a){return f[0]-
-a[0]||a[1]-f[1]});b=[];g=[];for(a=0;a<f.length;++a)k=f[a],k[0]<=g[1]+1?g[1]=Math.max(g[1],k[1]):b.push(g=k);for(a=0;a<b.length;++a)k=b[a],c.push(h(k[0])),k[1]>k[0]&&(k[1]+1>k[0]&&c.push("-"),c.push(h(k[1])));c.push("]");return c.join("")}function e(f){for(var a=f.source.match(/\[(?:[^\\\]]|\\[\S\s])*]|\\u[\dA-Fa-f]{4}|\\x[\dA-Fa-f]{2}|\\\d+|\\[^\dux]|\(\?[!:=]|[()^]|[^()[\\^]+/g),c=a.length,d=[],g=0,k=0;g<c;++g){var o=a[g];o==="("?++k:"\\"===o.charAt(0)&&(o=+o.substring(1))&&(o<=k?d[o]=-1:a[g]=h(o))}for(g=
-1;g<d.length;++g)-1===d[g]&&(d[g]=++j);for(k=g=0;g<c;++g)o=a[g],o==="("?(++k,d[k]||(a[g]="(?:")):"\\"===o.charAt(0)&&(o=+o.substring(1))&&o<=k&&(a[g]="\\"+d[o]);for(g=0;g<c;++g)"^"===a[g]&&"^"!==a[g+1]&&(a[g]="");if(f.ignoreCase&&F)for(g=0;g<c;++g)o=a[g],f=o.charAt(0),o.length>=2&&f==="["?a[g]=b(o):f!=="\\"&&(a[g]=o.replace(/[A-Za-z]/g,function(a){a=a.charCodeAt(0);return"["+String.fromCharCode(a&-33,a|32)+"]"}));return a.join("")}for(var j=0,F=!1,l=!1,I=0,c=a.length;I<c;++I){var p=a[I];if(p.ignoreCase)l=
-!0;else if(/[a-z]/i.test(p.source.replace(/\\u[\da-f]{4}|\\x[\da-f]{2}|\\[^UXux]/gi,""))){F=!0;l=!1;break}}for(var i={b:8,t:9,n:10,v:11,f:12,r:13},q=[],I=0,c=a.length;I<c;++I){p=a[I];if(p.global||p.multiline)throw Error(""+p);q.push("(?:"+e(p)+")")}return RegExp(q.join("|"),l?"gi":"g")}function m(a,d){function h(a){var c=a.nodeType;if(c==1){if(!b.test(a.className)){for(c=a.firstChild;c;c=c.nextSibling)h(c);c=a.nodeName.toLowerCase();if("br"===c||"li"===c)e[l]="\n",F[l<<1]=j++,F[l++<<1|1]=a}}else if(c==
-3||c==4)c=a.nodeValue,c.length&&(c=d?c.replace(/\r\n?/g,"\n"):c.replace(/[\t\n\r ]+/g," "),e[l]=c,F[l<<1]=j,j+=c.length,F[l++<<1|1]=a)}var b=/(?:^|\s)nocode(?:\s|$)/,e=[],j=0,F=[],l=0;h(a);return{a:e.join("").replace(/\n$/,""),d:F}}function n(a,d,h,b){d&&(a={a:d,e:a},h(a),b.push.apply(b,a.g))}function x(a){for(var d=void 0,h=a.firstChild;h;h=h.nextSibling)var b=h.nodeType,d=b===1?d?a:h:b===3?S.test(h.nodeValue)?a:d:d;return d===a?void 0:d}function C(a,d){function h(a){for(var l=a.e,j=[l,"pln"],c=
-0,p=a.a.match(e)||[],m={},q=0,f=p.length;q<f;++q){var B=p[q],y=m[B],u=void 0,g;if(typeof y==="string")g=!1;else{var k=b[B.charAt(0)];if(k)u=B.match(k[1]),y=k[0];else{for(g=0;g<i;++g)if(k=d[g],u=B.match(k[1])){y=k[0];break}u||(y="pln")}if((g=y.length>=5&&"lang-"===y.substring(0,5))&&!(u&&typeof u[1]==="string"))g=!1,y="src";g||(m[B]=y)}k=c;c+=B.length;if(g){g=u[1];var o=B.indexOf(g),H=o+g.length;u[2]&&(H=B.length-u[2].length,o=H-g.length);y=y.substring(5);n(l+k,B.substring(0,o),h,j);n(l+k+o,g,A(y,
-g),j);n(l+k+H,B.substring(H),h,j)}else j.push(l+k,y)}a.g=j}var b={},e;(function(){for(var h=a.concat(d),l=[],i={},c=0,p=h.length;c<p;++c){var m=h[c],q=m[3];if(q)for(var f=q.length;--f>=0;)b[q.charAt(f)]=m;m=m[1];q=""+m;i.hasOwnProperty(q)||(l.push(m),i[q]=r)}l.push(/[\S\s]/);e=j(l)})();var i=d.length;return h}function t(a){var d=[],h=[];a.tripleQuotedStrings?d.push(["str",/^(?:'''(?:[^'\\]|\\[\S\s]|''?(?=[^']))*(?:'''|$)|"""(?:[^"\\]|\\[\S\s]|""?(?=[^"]))*(?:"""|$)|'(?:[^'\\]|\\[\S\s])*(?:'|$)|"(?:[^"\\]|\\[\S\s])*(?:"|$))/,
-r,"'\""]):a.multiLineStrings?d.push(["str",/^(?:'(?:[^'\\]|\\[\S\s])*(?:'|$)|"(?:[^"\\]|\\[\S\s])*(?:"|$)|`(?:[^\\`]|\\[\S\s])*(?:`|$))/,r,"'\"`"]):d.push(["str",/^(?:'(?:[^\n\r'\\]|\\.)*(?:'|$)|"(?:[^\n\r"\\]|\\.)*(?:"|$))/,r,"\"'"]);a.verbatimStrings&&h.push(["str",/^@"(?:[^"]|"")*(?:"|$)/,r]);var b=a.hashComments;b&&(a.cStyleComments?(b>1?d.push(["com",/^#(?:##(?:[^#]|#(?!##))*(?:###|$)|.*)/,r,"#"]):d.push(["com",/^#(?:(?:define|e(?:l|nd)if|else|error|ifn?def|include|line|pragma|undef|warning)\b|[^\n\r]*)/,
-r,"#"]),h.push(["str",/^<(?:(?:(?:\.\.\/)*|\/?)(?:[\w-]+(?:\/[\w-]+)+)?[\w-]+\.h(?:h|pp|\+\+)?|[a-z]\w*)>/,r])):d.push(["com",/^#[^\n\r]*/,r,"#"]));a.cStyleComments&&(h.push(["com",/^\/\/[^\n\r]*/,r]),h.push(["com",/^\/\*[\S\s]*?(?:\*\/|$)/,r]));if(b=a.regexLiterals){var e=(b=b>1?"":"\n\r")?".":"[\\S\\s]";h.push(["lang-regex",RegExp("^(?:^^\\.?|[+-]|[!=]=?=?|\\#|%=?|&&?=?|\\(|\\*=?|[+\\-]=|->|\\/=?|::?|<<?=?|>>?>?=?|,|;|\\?|@|\\[|~|{|\\^\\^?=?|\\|\\|?=?|break|case|continue|delete|do|else|finally|instanceof|return|throw|try|typeof)\\s*("+
-("/(?=[^/*"+b+"])(?:[^/\\x5B\\x5C"+b+"]|\\x5C"+e+"|\\x5B(?:[^\\x5C\\x5D"+b+"]|\\x5C"+e+")*(?:\\x5D|$))+/")+")")])}(b=a.types)&&h.push(["typ",b]);b=(""+a.keywords).replace(/^ | $/g,"");b.length&&h.push(["kwd",RegExp("^(?:"+b.replace(/[\s,]+/g,"|")+")\\b"),r]);d.push(["pln",/^\s+/,r," \r\n\t\u00a0"]);b="^.[^\\s\\w.$@'\"`/\\\\]*";a.regexLiterals&&(b+="(?!s*/)");h.push(["lit",/^@[$_a-z][\w$@]*/i,r],["typ",/^(?:[@_]?[A-Z]+[a-z][\w$@]*|\w+_t\b)/,r],["pln",/^[$_a-z][\w$@]*/i,r],["lit",/^(?:0x[\da-f]+|(?:\d(?:_\d+)*\d*(?:\.\d*)?|\.\d\+)(?:e[+-]?\d+)?)[a-z]*/i,
-r,"0123456789"],["pln",/^\\[\S\s]?/,r],["pun",RegExp(b),r]);return C(d,h)}function z(a,d,h){function b(a){var c=a.nodeType;if(c==1&&!j.test(a.className))if("br"===a.nodeName)e(a),a.parentNode&&a.parentNode.removeChild(a);else for(a=a.firstChild;a;a=a.nextSibling)b(a);else if((c==3||c==4)&&h){var d=a.nodeValue,i=d.match(m);if(i)c=d.substring(0,i.index),a.nodeValue=c,(d=d.substring(i.index+i[0].length))&&a.parentNode.insertBefore(l.createTextNode(d),a.nextSibling),e(a),c||a.parentNode.removeChild(a)}}
-function e(a){function b(a,c){var d=c?a.cloneNode(!1):a,f=a.parentNode;if(f){var f=b(f,1),h=a.nextSibling;f.appendChild(d);for(var e=h;e;e=h)h=e.nextSibling,f.appendChild(e)}return d}for(;!a.nextSibling;)if(a=a.parentNode,!a)return;for(var a=b(a.nextSibling,0),d;(d=a.parentNode)&&d.nodeType===1;)a=d;c.push(a)}for(var j=/(?:^|\s)nocode(?:\s|$)/,m=/\r\n?|\n/,l=a.ownerDocument,i=l.createElement("li");a.firstChild;)i.appendChild(a.firstChild);for(var c=[i],p=0;p<c.length;++p)b(c[p]);d===(d|0)&&c[0].setAttribute("value",
-d);var n=l.createElement("ol");n.className="linenums";for(var d=Math.max(0,d-1|0)||0,p=0,q=c.length;p<q;++p)i=c[p],i.className="L"+(p+d)%10,i.firstChild||i.appendChild(l.createTextNode("\u00a0")),n.appendChild(i);a.appendChild(n)}function i(a,d){for(var h=d.length;--h>=0;){var b=d[h];U.hasOwnProperty(b)?V.console&&console.warn("cannot override language handler %s",b):U[b]=a}}function A(a,d){if(!a||!U.hasOwnProperty(a))a=/^\s*</.test(d)?"default-markup":"default-code";return U[a]}function D(a){var d=
-a.h;try{var h=m(a.c,a.i),b=h.a;a.a=b;a.d=h.d;a.e=0;A(d,b)(a);var e=/\bMSIE\s(\d+)/.exec(navigator.userAgent),e=e&&+e[1]<=8,d=/\n/g,i=a.a,j=i.length,h=0,l=a.d,n=l.length,b=0,c=a.g,p=c.length,t=0;c[p]=j;var q,f;for(f=q=0;f<p;)c[f]!==c[f+2]?(c[q++]=c[f++],c[q++]=c[f++]):f+=2;p=q;for(f=q=0;f<p;){for(var x=c[f],y=c[f+1],u=f+2;u+2<=p&&c[u+1]===y;)u+=2;c[q++]=x;c[q++]=y;f=u}c.length=q;var g=a.c,k;if(g)k=g.style.display,g.style.display="none";try{for(;b<n;){var o=l[b+2]||j,H=c[t+2]||j,u=Math.min(o,H),E=l[b+
-1],W;if(E.nodeType!==1&&(W=i.substring(h,u))){e&&(W=W.replace(d,"\r"));E.nodeValue=W;var Z=E.ownerDocument,s=Z.createElement("span");s.className=c[t+1];var z=E.parentNode;z.replaceChild(s,E);s.appendChild(E);h<o&&(l[b+1]=E=Z.createTextNode(i.substring(u,o)),z.insertBefore(E,s.nextSibling))}h=u;h>=o&&(b+=2);h>=H&&(t+=2)}}finally{if(g)g.style.display=k}}catch(v){V.console&&console.log(v&&v.stack||v)}}var V=window,G=["break,continue,do,else,for,if,return,while"],O=[[G,"auto,case,char,const,default,double,enum,extern,float,goto,inline,int,long,register,short,signed,sizeof,static,struct,switch,typedef,union,unsigned,void,volatile"],
-"catch,class,delete,false,import,new,operator,private,protected,public,this,throw,true,try,typeof"],J=[O,"alignof,align_union,asm,axiom,bool,concept,concept_map,const_cast,constexpr,decltype,delegate,dynamic_cast,explicit,export,friend,generic,late_check,mutable,namespace,nullptr,property,reinterpret_cast,static_assert,static_cast,template,typeid,typename,using,virtual,where"],K=[O,"abstract,assert,boolean,byte,extends,final,finally,implements,import,instanceof,interface,null,native,package,strictfp,super,synchronized,throws,transient"],
-L=[K,"as,base,by,checked,decimal,delegate,descending,dynamic,event,fixed,foreach,from,group,implicit,in,internal,into,is,let,lock,object,out,override,orderby,params,partial,readonly,ref,sbyte,sealed,stackalloc,string,select,uint,ulong,unchecked,unsafe,ushort,var,virtual,where"],O=[O,"debugger,eval,export,function,get,null,set,undefined,var,with,Infinity,NaN"],M=[G,"and,as,assert,class,def,del,elif,except,exec,finally,from,global,import,in,is,lambda,nonlocal,not,or,pass,print,raise,try,with,yield,False,True,None"],
-N=[G,"alias,and,begin,case,class,def,defined,elsif,end,ensure,false,in,module,next,nil,not,or,redo,rescue,retry,self,super,then,true,undef,unless,until,when,yield,BEGIN,END"],R=[G,"as,assert,const,copy,drop,enum,extern,fail,false,fn,impl,let,log,loop,match,mod,move,mut,priv,pub,pure,ref,self,static,struct,true,trait,type,unsafe,use"],G=[G,"case,done,elif,esac,eval,fi,function,in,local,set,then,until"],Q=/^(DIR|FILE|vector|(de|priority_)?queue|list|stack|(const_)?iterator|(multi)?(set|map)|bitset|u?(int|float)\d*)\b/,
-S=/\S/,T=t({keywords:[J,L,O,"caller,delete,die,do,dump,elsif,eval,exit,foreach,for,goto,if,import,last,local,my,next,no,our,print,package,redo,require,sub,undef,unless,until,use,wantarray,while,BEGIN,END",M,N,G],hashComments:!0,cStyleComments:!0,multiLineStrings:!0,regexLiterals:!0}),U={};i(T,["default-code"]);i(C([],[["pln",/^[^<?]+/],["dec",/^<!\w[^>]*(?:>|$)/],["com",/^<\!--[\S\s]*?(?:--\>|$)/],["lang-",/^<\?([\S\s]+?)(?:\?>|$)/],["lang-",/^<%([\S\s]+?)(?:%>|$)/],["pun",/^(?:<[%?]|[%?]>)/],["lang-",
-/^<xmp\b[^>]*>([\S\s]+?)<\/xmp\b[^>]*>/i],["lang-js",/^<script\b[^>]*>([\S\s]*?)(<\/script\b[^>]*>)/i],["lang-css",/^<style\b[^>]*>([\S\s]*?)(<\/style\b[^>]*>)/i],["lang-in.tag",/^(<\/?[a-z][^<>]*>)/i]]),["default-markup","htm","html","mxml","xhtml","xml","xsl"]);i(C([["pln",/^\s+/,r," \t\r\n"],["atv",/^(?:"[^"]*"?|'[^']*'?)/,r,"\"'"]],[["tag",/^^<\/?[a-z](?:[\w-.:]*\w)?|\/?>$/i],["atn",/^(?!style[\s=]|on)[a-z](?:[\w:-]*\w)?/i],["lang-uq.val",/^=\s*([^\s"'>]*(?:[^\s"'/>]|\/(?=\s)))/],["pun",/^[/<->]+/],
-["lang-js",/^on\w+\s*=\s*"([^"]+)"/i],["lang-js",/^on\w+\s*=\s*'([^']+)'/i],["lang-js",/^on\w+\s*=\s*([^\s"'>]+)/i],["lang-css",/^style\s*=\s*"([^"]+)"/i],["lang-css",/^style\s*=\s*'([^']+)'/i],["lang-css",/^style\s*=\s*([^\s"'>]+)/i]]),["in.tag"]);i(C([],[["atv",/^[\S\s]+/]]),["uq.val"]);i(t({keywords:J,hashComments:!0,cStyleComments:!0,types:Q}),["c","cc","cpp","cxx","cyc","m"]);i(t({keywords:"null,true,false"}),["json"]);i(t({keywords:L,hashComments:!0,cStyleComments:!0,verbatimStrings:!0,types:Q}),
-["cs"]);i(t({keywords:K,cStyleComments:!0}),["java"]);i(t({keywords:G,hashComments:!0,multiLineStrings:!0}),["bash","bsh","csh","sh"]);i(t({keywords:M,hashComments:!0,multiLineStrings:!0,tripleQuotedStrings:!0}),["cv","py","python"]);i(t({keywords:"caller,delete,die,do,dump,elsif,eval,exit,foreach,for,goto,if,import,last,local,my,next,no,our,print,package,redo,require,sub,undef,unless,until,use,wantarray,while,BEGIN,END",hashComments:!0,multiLineStrings:!0,regexLiterals:2}),["perl","pl","pm"]);i(t({keywords:N,
-hashComments:!0,multiLineStrings:!0,regexLiterals:!0}),["rb","ruby"]);i(t({keywords:O,cStyleComments:!0,regexLiterals:!0}),["javascript","js"]);i(t({keywords:"all,and,by,catch,class,else,extends,false,finally,for,if,in,is,isnt,loop,new,no,not,null,of,off,on,or,return,super,then,throw,true,try,unless,until,when,while,yes",hashComments:3,cStyleComments:!0,multilineStrings:!0,tripleQuotedStrings:!0,regexLiterals:!0}),["coffee"]);i(t({keywords:R,cStyleComments:!0,multilineStrings:!0}),["rc","rs","rust"]);
-i(C([],[["str",/^[\S\s]+/]]),["regex"]);var X=V.PR={createSimpleLexer:C,registerLangHandler:i,sourceDecorator:t,PR_ATTRIB_NAME:"atn",PR_ATTRIB_VALUE:"atv",PR_COMMENT:"com",PR_DECLARATION:"dec",PR_KEYWORD:"kwd",PR_LITERAL:"lit",PR_NOCODE:"nocode",PR_PLAIN:"pln",PR_PUNCTUATION:"pun",PR_SOURCE:"src",PR_STRING:"str",PR_TAG:"tag",PR_TYPE:"typ",prettyPrintOne:function(a,d,e){var b=document.createElement("div");b.innerHTML="<pre>"+a+"</pre>";b=b.firstChild;e&&z(b,e,!0);D({h:d,j:e,c:b,i:1});return b.innerHTML},
-prettyPrint:e=e=function(a,d){function e(){for(var b=V.PR_SHOULD_USE_CONTINUATION?c.now()+250:Infinity;p<j.length&&c.now()<b;p++){for(var d=j[p],m=k,l=d;l=l.previousSibling;){var n=l.nodeType,s=(n===7||n===8)&&l.nodeValue;if(s?!/^\??prettify\b/.test(s):n!==3||/\S/.test(l.nodeValue))break;if(s){m={};s.replace(/\b(\w+)=([\w%+\-.:]+)/g,function(a,b,c){m[b]=c});break}}l=d.className;if((m!==k||f.test(l))&&!w.test(l)){n=!1;for(s=d.parentNode;s;s=s.parentNode)if(g.test(s.tagName)&&s.className&&f.test(s.className)){n=
-!0;break}if(!n){d.className+=" prettyprinted";n=m.lang;if(!n){var n=l.match(q),A;if(!n&&(A=x(d))&&u.test(A.tagName))n=A.className.match(q);n&&(n=n[1])}if(y.test(d.tagName))s=1;else var s=d.currentStyle,v=i.defaultView,s=(s=s?s.whiteSpace:v&&v.getComputedStyle?v.getComputedStyle(d,r).getPropertyValue("white-space"):0)&&"pre"===s.substring(0,3);v=m.linenums;if(!(v=v==="true"||+v))v=(v=l.match(/\blinenums\b(?::(\d+))?/))?v[1]&&v[1].length?+v[1]:!0:!1;v&&z(d,v,s);t={h:n,c:d,j:v,i:s};D(t)}}}p<j.length?
-P(e,250):"function"===typeof a&&a()}for(var b=d||document.body,i=b.ownerDocument||document,b=[b.getElementsByTagName("pre"),b.getElementsByTagName("code"),b.getElementsByTagName("xmp")],j=[],m=0;m<b.length;++m)for(var l=0,n=b[m].length;l<n;++l)j.push(b[m][l]);var b=r,c=Date;c.now||(c={now:function(){return+new Date}});var p=0,t,q=/\blang(?:uage)?-([\w.]+)(?!\S)/,f=/\bprettyprint\b/,w=/\bprettyprinted\b/,y=/pre|xmp/i,u=/^code$/i,g=/^(?:pre|code|xmp)$/i,k={};e()}};typeof define==="function"&&define.amd&&
-define("google-code-prettify",[],function(){return X})})();return e}();R||P(Q,0)})();}()
diff --git a/civicrm/bower_components/google-code-prettify/src/run_prettify.js b/civicrm/bower_components/google-code-prettify/src/run_prettify.js
deleted file mode 100644
index dd136b921c20b646d2a6d4986da49982522735a6..0000000000000000000000000000000000000000
--- a/civicrm/bower_components/google-code-prettify/src/run_prettify.js
+++ /dev/null
@@ -1,1905 +0,0 @@
-// Copyright (C) 2013 Google Inc.
-//
-// Licensed under the Apache License, Version 2.0 (the "License");
-// you may not use this file except in compliance with the License.
-// You may obtain a copy of the License at
-//
-//      http://www.apache.org/licenses/LICENSE-2.0
-//
-// Unless required by applicable law or agreed to in writing, software
-// distributed under the License is distributed on an "AS IS" BASIS,
-// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-// See the License for the specific language governing permissions and
-// limitations under the License.
-
-
-// Looks at query parameters to decide which language handlers and style-sheets
-// to load.
-
-// Query Parameter     Format           Effect                        Default
-// +------------------+---------------+------------------------------+--------+
-// | autorun=         | true | false  | If true then prettyPrint()   | "true" |
-// |                  |               | is called on page load.      |        |
-// +------------------+---------------+------------------------------+--------+
-// | lang=            | language name | Loads the language handler   | Can    |
-// |                  |               | named "lang-<NAME>.js".      | appear |
-// |                  |               | See available handlers at    | many   |
-// |                  |               | http://code.google.com/p/    | times. |
-// |                  |               | google-code-prettify/source/ |        |
-// |                  |               | browse/trunk/src             |        |
-// +------------------+---------------+------------------------------+--------+
-// | skin=            | skin name     | Loads the skin stylesheet    | none.  |
-// |                  |               | named "<NAME>.css".          |        |
-// |                  |               | http://code.google.com/p/    |        |
-// |                  |               | google-code-prettify/source/ |        |
-// |                  |               | browse/trunk/styles          |        |
-// +------------------+---------------+------------------------------+--------+
-// | callback=        | JS identifier | When "prettyPrint" finishes  | none   |
-// |                  |               | window.exports[js_ident] is  |        |
-// |                  |               | called.                      |        |
-// |                  |               | The callback must be under   |        |
-// |                  |               | exports to reduce the risk   |        |
-// |                  |               | of XSS via query parameter   |        |
-// |                  |               | injection.                   |        |
-// +------------------+---------------+------------------------------+--------+
-
-// Exmaples
-// .../prettify.js?lang=css&skin=sunburst
-//   1. Loads the CSS language handler which can be used to prettify CSS
-//      stylesheets, HTML <style> element bodies and style="..." attributes
-//      values.
-//   2. Loads the sunburst.css stylesheet instead of the default prettify.css
-//      stylesheet.
-//      A gallery of stylesheets is available at
-//      https://google-code-prettify.googlecode.com/svn/trunk/styles/index.html
-//   3. Since autorun=false is not specified, calls prettyPrint() on page load.
-
-
-/** @define {boolean} */
-var IN_GLOBAL_SCOPE = false;
-
-(function () {
-  "use strict";
-
-  var win = window;
-  var setTimeout = win.setTimeout;
-  var doc = document;
-  var root = doc.documentElement;
-  var head = doc['head'] || doc.getElementsByTagName("head")[0] || root;
-
-  // From http://javascript.nwbox.com/ContentLoaded/contentloaded.js
-  // Author: Diego Perini (diego.perini at gmail.com)
-  // Summary: cross-browser wrapper for DOMContentLoaded
-  // Updated: 20101020
-  // License: MIT
-  // Version: 1.2
-  function contentLoaded(callback) {
-    var addEventListener = doc['addEventListener'];
-    var done = false, top = true,
-        add = addEventListener ? 'addEventListener' : 'attachEvent',
-        rem = addEventListener ? 'removeEventListener' : 'detachEvent',
-        pre = addEventListener ? '' : 'on',
-
-        init = function(e) {
-          if (e.type == 'readystatechange' && doc.readyState != 'complete') {
-            return;
-          }
-          (e.type == 'load' ? win : doc)[rem](pre + e.type, init, false);
-          if (!done && (done = true)) { callback.call(win, e.type || e); }
-        },
-
-        poll = function() {
-          try {
-            root.doScroll('left');
-          } catch(e) {
-            setTimeout(poll, 50);
-            return;
-          }
-          init('poll');
-        };
-
-    if (doc.readyState == 'complete') {
-      callback.call(win, 'lazy');
-    } else {
-      if (doc.createEventObject && root.doScroll) {
-        try { top = !win.frameElement; } catch(e) { }
-        if (top) { poll(); }
-      }
-      doc[add](pre + 'DOMContentLoaded', init, false);
-      doc[add](pre + 'readystatechange', init, false);
-      win[add](pre + 'load', init, false);
-    }
-  }
-
-  // Given a list of URLs to stylesheets, loads the first that loads without
-  // triggering an error event.
-  function loadStylesheetsFallingBack(stylesheets) {
-    var n = stylesheets.length;
-    function load(i) {
-      if (i === n) { return; }
-      var link = doc.createElement('link');
-      link.rel = 'stylesheet';
-      link.type = 'text/css';
-      if (i + 1 < n) {
-        // http://pieisgood.org/test/script-link-events/ indicates that many
-        // versions of IE do not support onerror on <link>s, though
-        // http://msdn.microsoft.com/en-us/library/ie/ms535848(v=vs.85).aspx
-        // indicates that recent IEs do support error.
-        link.error = link.onerror = function () { load(i + 1); };
-      }
-      link.href = stylesheets[i];
-      head.appendChild(link);
-    }
-    load(0);
-  }
-
-  var scriptQuery = '';
-  // Look for the <script> node that loads this script to get its parameters.
-  // This starts looking at the end instead of just considering the last
-  // because deferred and async scripts run out of order.
-  // If the script is loaded twice, then this will run in reverse order.
-  for (var scripts = doc.scripts, i = scripts.length; --i >= 0;) {
-    var script = scripts[i];
-    var match = script.src.match(
-        /^[^?#]*\/run_prettify\.js(\?[^#]*)?(?:#.*)?$/);
-    if (match) {
-      scriptQuery = match[1] || '';
-      // Remove the script from the DOM so that multiple runs at least run
-      // multiple times even if parameter sets are interpreted in reverse
-      // order.
-      script.parentNode.removeChild(script);
-      break;
-    }
-  }
-
-  // Pull parameters into local variables.
-  var autorun = true;
-  var langs = [];
-  var skins = [];
-  var callbacks = [];
-  scriptQuery.replace(
-      /[?&]([^&=]+)=([^&]+)/g,
-      function (_, name, value) {
-        value = decodeURIComponent(value);
-        name = decodeURIComponent(name);
-        if (name == 'autorun')   { autorun = !/^[0fn]/i.test(value); } else
-        if (name == 'lang')      { langs.push(value);                } else
-        if (name == 'skin')      { skins.push(value);                } else
-        if (name == 'callback')  { callbacks.push(value);            }
-      });
-
-  // Use https to avoid mixed content warnings in client pages and to
-  // prevent a MITM from rewrite prettify mid-flight.
-  // This only works if this script is loaded via https : something
-  // over which we exercise no control.
-  var LOADER_BASE_URL =
-     'https://google-code-prettify.googlecode.com/svn/loader';
-
-  for (var i = 0, n = langs.length; i < n; ++i) (function (lang) {
-    var script = doc.createElement("script");
-
-    // Excerpted from jQuery.ajaxTransport("script") to fire events when
-    // a script is finished loading.
-    // Attach handlers for each script
-    script.onload = script.onerror = script.onreadystatechange = function () {
-      if (script && (
-            !script.readyState || /loaded|complete/.test(script.readyState))) {
-        // Handle memory leak in IE
-        script.onerror = script.onload = script.onreadystatechange = null;
-
-        --pendingLanguages;
-        checkPendingLanguages();
-
-        // Remove the script
-        if (script.parentNode) {
-          script.parentNode.removeChild(script);
-        }
-
-        script = null;
-      }
-    };
-
-    script.type = 'text/javascript';
-    script.src = LOADER_BASE_URL
-      + '/lang-' + encodeURIComponent(langs[i]) + '.js';
-
-    // Circumvent IE6 bugs with base elements (#2709 and #4378) by prepending
-    head.insertBefore(script, head.firstChild);
-  })(langs[i]);
-
-  var pendingLanguages = langs.length;
-  function checkPendingLanguages() {
-    if (!pendingLanguages) {
-      setTimeout(onLangsLoaded, 0);
-    }
-  }
-
-  var skinUrls = [];
-  for (var i = 0, n = skins.length; i < n; ++i) {
-    skinUrls.push(LOADER_BASE_URL
-        + '/skins/' + encodeURIComponent(skins[i]) + '.css');
-  }
-  skinUrls.push(LOADER_BASE_URL + '/prettify.css');
-  loadStylesheetsFallingBack(skinUrls);
-
-  var prettyPrint = (function () {
-    // Copyright (C) 2006 Google Inc.
-    //
-    // Licensed under the Apache License, Version 2.0 (the "License");
-    // you may not use this file except in compliance with the License.
-    // You may obtain a copy of the License at
-    //
-    //      http://www.apache.org/licenses/LICENSE-2.0
-    //
-    // Unless required by applicable law or agreed to in writing, software
-    // distributed under the License is distributed on an "AS IS" BASIS,
-    // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-    // See the License for the specific language governing permissions and
-    // limitations under the License.
-    
-    
-    /**
-     * @fileoverview
-     * some functions for browser-side pretty printing of code contained in html.
-     *
-     * <p>
-     * For a fairly comprehensive set of languages see the
-     * <a href="http://google-code-prettify.googlecode.com/svn/trunk/README.html#langs">README</a>
-     * file that came with this source.  At a minimum, the lexer should work on a
-     * number of languages including C and friends, Java, Python, Bash, SQL, HTML,
-     * XML, CSS, Javascript, and Makefiles.  It works passably on Ruby, PHP and Awk
-     * and a subset of Perl, but, because of commenting conventions, doesn't work on
-     * Smalltalk, Lisp-like, or CAML-like languages without an explicit lang class.
-     * <p>
-     * Usage: <ol>
-     * <li> include this source file in an html page via
-     *   {@code <script type="text/javascript" src="/path/to/prettify.js"></script>}
-     * <li> define style rules.  See the example page for examples.
-     * <li> mark the {@code <pre>} and {@code <code>} tags in your source with
-     *    {@code class=prettyprint.}
-     *    You can also use the (html deprecated) {@code <xmp>} tag, but the pretty
-     *    printer needs to do more substantial DOM manipulations to support that, so
-     *    some css styles may not be preserved.
-     * </ol>
-     * That's it.  I wanted to keep the API as simple as possible, so there's no
-     * need to specify which language the code is in, but if you wish, you can add
-     * another class to the {@code <pre>} or {@code <code>} element to specify the
-     * language, as in {@code <pre class="prettyprint lang-java">}.  Any class that
-     * starts with "lang-" followed by a file extension, specifies the file type.
-     * See the "lang-*.js" files in this directory for code that implements
-     * per-language file handlers.
-     * <p>
-     * Change log:<br>
-     * cbeust, 2006/08/22
-     * <blockquote>
-     *   Java annotations (start with "@") are now captured as literals ("lit")
-     * </blockquote>
-     * @requires console
-     */
-    
-    // JSLint declarations
-    /*global console, document, navigator, setTimeout, window, define */
-    
-    /**
-     * Split {@code prettyPrint} into multiple timeouts so as not to interfere with
-     * UI events.
-     * If set to {@code false}, {@code prettyPrint()} is synchronous.
-     */
-    window['PR_SHOULD_USE_CONTINUATION'] = true;
-    
-    /**
-     * Pretty print a chunk of code.
-     * @param {string} sourceCodeHtml The HTML to pretty print.
-     * @param {string} opt_langExtension The language name to use.
-     *     Typically, a filename extension like 'cpp' or 'java'.
-     * @param {number|boolean} opt_numberLines True to number lines,
-     *     or the 1-indexed number of the first line in sourceCodeHtml.
-     * @return {string} code as html, but prettier
-     */
-    var prettyPrintOne;
-    /**
-     * Find all the {@code <pre>} and {@code <code>} tags in the DOM with
-     * {@code class=prettyprint} and prettify them.
-     *
-     * @param {Function} opt_whenDone called when prettifying is done.
-     * @param {HTMLElement|HTMLDocument} opt_root an element or document
-     *   containing all the elements to pretty print.
-     *   Defaults to {@code document.body}.
-     */
-    var prettyPrint;
-    
-    
-    (function () {
-      var win = window;
-      // Keyword lists for various languages.
-      // We use things that coerce to strings to make them compact when minified
-      // and to defeat aggressive optimizers that fold large string constants.
-      var FLOW_CONTROL_KEYWORDS = ["break,continue,do,else,for,if,return,while"];
-      var C_KEYWORDS = [FLOW_CONTROL_KEYWORDS,"auto,case,char,const,default," + 
-          "double,enum,extern,float,goto,inline,int,long,register,short,signed," +
-          "sizeof,static,struct,switch,typedef,union,unsigned,void,volatile"];
-      var COMMON_KEYWORDS = [C_KEYWORDS,"catch,class,delete,false,import," +
-          "new,operator,private,protected,public,this,throw,true,try,typeof"];
-      var CPP_KEYWORDS = [COMMON_KEYWORDS,"alignof,align_union,asm,axiom,bool," +
-          "concept,concept_map,const_cast,constexpr,decltype,delegate," +
-          "dynamic_cast,explicit,export,friend,generic,late_check," +
-          "mutable,namespace,nullptr,property,reinterpret_cast,static_assert," +
-          "static_cast,template,typeid,typename,using,virtual,where"];
-      var JAVA_KEYWORDS = [COMMON_KEYWORDS,
-          "abstract,assert,boolean,byte,extends,final,finally,implements,import," +
-          "instanceof,interface,null,native,package,strictfp,super,synchronized," +
-          "throws,transient"];
-      var CSHARP_KEYWORDS = [JAVA_KEYWORDS,
-          "as,base,by,checked,decimal,delegate,descending,dynamic,event," +
-          "fixed,foreach,from,group,implicit,in,internal,into,is,let," +
-          "lock,object,out,override,orderby,params,partial,readonly,ref,sbyte," +
-          "sealed,stackalloc,string,select,uint,ulong,unchecked,unsafe,ushort," +
-          "var,virtual,where"];
-      var COFFEE_KEYWORDS = "all,and,by,catch,class,else,extends,false,finally," +
-          "for,if,in,is,isnt,loop,new,no,not,null,of,off,on,or,return,super,then," +
-          "throw,true,try,unless,until,when,while,yes";
-      var JSCRIPT_KEYWORDS = [COMMON_KEYWORDS,
-          "debugger,eval,export,function,get,null,set,undefined,var,with," +
-          "Infinity,NaN"];
-      var PERL_KEYWORDS = "caller,delete,die,do,dump,elsif,eval,exit,foreach,for," +
-          "goto,if,import,last,local,my,next,no,our,print,package,redo,require," +
-          "sub,undef,unless,until,use,wantarray,while,BEGIN,END";
-      var PYTHON_KEYWORDS = [FLOW_CONTROL_KEYWORDS, "and,as,assert,class,def,del," +
-          "elif,except,exec,finally,from,global,import,in,is,lambda," +
-          "nonlocal,not,or,pass,print,raise,try,with,yield," +
-          "False,True,None"];
-      var RUBY_KEYWORDS = [FLOW_CONTROL_KEYWORDS, "alias,and,begin,case,class," +
-          "def,defined,elsif,end,ensure,false,in,module,next,nil,not,or,redo," +
-          "rescue,retry,self,super,then,true,undef,unless,until,when,yield," +
-          "BEGIN,END"];
-       var RUST_KEYWORDS = [FLOW_CONTROL_KEYWORDS, "as,assert,const,copy,drop," +
-          "enum,extern,fail,false,fn,impl,let,log,loop,match,mod,move,mut,priv," +
-          "pub,pure,ref,self,static,struct,true,trait,type,unsafe,use"];
-      var SH_KEYWORDS = [FLOW_CONTROL_KEYWORDS, "case,done,elif,esac,eval,fi," +
-          "function,in,local,set,then,until"];
-      var ALL_KEYWORDS = [
-          CPP_KEYWORDS, CSHARP_KEYWORDS, JSCRIPT_KEYWORDS, PERL_KEYWORDS,
-          PYTHON_KEYWORDS, RUBY_KEYWORDS, SH_KEYWORDS];
-      var C_TYPES = /^(DIR|FILE|vector|(de|priority_)?queue|list|stack|(const_)?iterator|(multi)?(set|map)|bitset|u?(int|float)\d*)\b/;
-    
-      // token style names.  correspond to css classes
-      /**
-       * token style for a string literal
-       * @const
-       */
-      var PR_STRING = 'str';
-      /**
-       * token style for a keyword
-       * @const
-       */
-      var PR_KEYWORD = 'kwd';
-      /**
-       * token style for a comment
-       * @const
-       */
-      var PR_COMMENT = 'com';
-      /**
-       * token style for a type
-       * @const
-       */
-      var PR_TYPE = 'typ';
-      /**
-       * token style for a literal value.  e.g. 1, null, true.
-       * @const
-       */
-      var PR_LITERAL = 'lit';
-      /**
-       * token style for a punctuation string.
-       * @const
-       */
-      var PR_PUNCTUATION = 'pun';
-      /**
-       * token style for plain text.
-       * @const
-       */
-      var PR_PLAIN = 'pln';
-    
-      /**
-       * token style for an sgml tag.
-       * @const
-       */
-      var PR_TAG = 'tag';
-      /**
-       * token style for a markup declaration such as a DOCTYPE.
-       * @const
-       */
-      var PR_DECLARATION = 'dec';
-      /**
-       * token style for embedded source.
-       * @const
-       */
-      var PR_SOURCE = 'src';
-      /**
-       * token style for an sgml attribute name.
-       * @const
-       */
-      var PR_ATTRIB_NAME = 'atn';
-      /**
-       * token style for an sgml attribute value.
-       * @const
-       */
-      var PR_ATTRIB_VALUE = 'atv';
-    
-      /**
-       * A class that indicates a section of markup that is not code, e.g. to allow
-       * embedding of line numbers within code listings.
-       * @const
-       */
-      var PR_NOCODE = 'nocode';
-    
-      
-      
-      /**
-       * A set of tokens that can precede a regular expression literal in
-       * javascript
-       * http://web.archive.org/web/20070717142515/http://www.mozilla.org/js/language/js20/rationale/syntax.html
-       * has the full list, but I've removed ones that might be problematic when
-       * seen in languages that don't support regular expression literals.
-       *
-       * <p>Specifically, I've removed any keywords that can't precede a regexp
-       * literal in a syntactically legal javascript program, and I've removed the
-       * "in" keyword since it's not a keyword in many languages, and might be used
-       * as a count of inches.
-       *
-       * <p>The link above does not accurately describe EcmaScript rules since
-       * it fails to distinguish between (a=++/b/i) and (a++/b/i) but it works
-       * very well in practice.
-       *
-       * @private
-       * @const
-       */
-      var REGEXP_PRECEDER_PATTERN = '(?:^^\\.?|[+-]|[!=]=?=?|\\#|%=?|&&?=?|\\(|\\*=?|[+\\-]=|->|\\/=?|::?|<<?=?|>>?>?=?|,|;|\\?|@|\\[|~|{|\\^\\^?=?|\\|\\|?=?|break|case|continue|delete|do|else|finally|instanceof|return|throw|try|typeof)\\s*';
-      
-      // CAVEAT: this does not properly handle the case where a regular
-      // expression immediately follows another since a regular expression may
-      // have flags for case-sensitivity and the like.  Having regexp tokens
-      // adjacent is not valid in any language I'm aware of, so I'm punting.
-      // TODO: maybe style special characters inside a regexp as punctuation.
-    
-      /**
-       * Given a group of {@link RegExp}s, returns a {@code RegExp} that globally
-       * matches the union of the sets of strings matched by the input RegExp.
-       * Since it matches globally, if the input strings have a start-of-input
-       * anchor (/^.../), it is ignored for the purposes of unioning.
-       * @param {Array.<RegExp>} regexs non multiline, non-global regexs.
-       * @return {RegExp} a global regex.
-       */
-      function combinePrefixPatterns(regexs) {
-        var capturedGroupIndex = 0;
-      
-        var needToFoldCase = false;
-        var ignoreCase = false;
-        for (var i = 0, n = regexs.length; i < n; ++i) {
-          var regex = regexs[i];
-          if (regex.ignoreCase) {
-            ignoreCase = true;
-          } else if (/[a-z]/i.test(regex.source.replace(
-                         /\\u[0-9a-f]{4}|\\x[0-9a-f]{2}|\\[^ux]/gi, ''))) {
-            needToFoldCase = true;
-            ignoreCase = false;
-            break;
-          }
-        }
-      
-        var escapeCharToCodeUnit = {
-          'b': 8,
-          't': 9,
-          'n': 0xa,
-          'v': 0xb,
-          'f': 0xc,
-          'r': 0xd
-        };
-      
-        function decodeEscape(charsetPart) {
-          var cc0 = charsetPart.charCodeAt(0);
-          if (cc0 !== 92 /* \\ */) {
-            return cc0;
-          }
-          var c1 = charsetPart.charAt(1);
-          cc0 = escapeCharToCodeUnit[c1];
-          if (cc0) {
-            return cc0;
-          } else if ('0' <= c1 && c1 <= '7') {
-            return parseInt(charsetPart.substring(1), 8);
-          } else if (c1 === 'u' || c1 === 'x') {
-            return parseInt(charsetPart.substring(2), 16);
-          } else {
-            return charsetPart.charCodeAt(1);
-          }
-        }
-      
-        function encodeEscape(charCode) {
-          if (charCode < 0x20) {
-            return (charCode < 0x10 ? '\\x0' : '\\x') + charCode.toString(16);
-          }
-          var ch = String.fromCharCode(charCode);
-          return (ch === '\\' || ch === '-' || ch === ']' || ch === '^')
-              ? "\\" + ch : ch;
-        }
-      
-        function caseFoldCharset(charSet) {
-          var charsetParts = charSet.substring(1, charSet.length - 1).match(
-              new RegExp(
-                  '\\\\u[0-9A-Fa-f]{4}'
-                  + '|\\\\x[0-9A-Fa-f]{2}'
-                  + '|\\\\[0-3][0-7]{0,2}'
-                  + '|\\\\[0-7]{1,2}'
-                  + '|\\\\[\\s\\S]'
-                  + '|-'
-                  + '|[^-\\\\]',
-                  'g'));
-          var ranges = [];
-          var inverse = charsetParts[0] === '^';
-      
-          var out = ['['];
-          if (inverse) { out.push('^'); }
-      
-          for (var i = inverse ? 1 : 0, n = charsetParts.length; i < n; ++i) {
-            var p = charsetParts[i];
-            if (/\\[bdsw]/i.test(p)) {  // Don't muck with named groups.
-              out.push(p);
-            } else {
-              var start = decodeEscape(p);
-              var end;
-              if (i + 2 < n && '-' === charsetParts[i + 1]) {
-                end = decodeEscape(charsetParts[i + 2]);
-                i += 2;
-              } else {
-                end = start;
-              }
-              ranges.push([start, end]);
-              // If the range might intersect letters, then expand it.
-              // This case handling is too simplistic.
-              // It does not deal with non-latin case folding.
-              // It works for latin source code identifiers though.
-              if (!(end < 65 || start > 122)) {
-                if (!(end < 65 || start > 90)) {
-                  ranges.push([Math.max(65, start) | 32, Math.min(end, 90) | 32]);
-                }
-                if (!(end < 97 || start > 122)) {
-                  ranges.push([Math.max(97, start) & ~32, Math.min(end, 122) & ~32]);
-                }
-              }
-            }
-          }
-      
-          // [[1, 10], [3, 4], [8, 12], [14, 14], [16, 16], [17, 17]]
-          // -> [[1, 12], [14, 14], [16, 17]]
-          ranges.sort(function (a, b) { return (a[0] - b[0]) || (b[1]  - a[1]); });
-          var consolidatedRanges = [];
-          var lastRange = [];
-          for (var i = 0; i < ranges.length; ++i) {
-            var range = ranges[i];
-            if (range[0] <= lastRange[1] + 1) {
-              lastRange[1] = Math.max(lastRange[1], range[1]);
-            } else {
-              consolidatedRanges.push(lastRange = range);
-            }
-          }
-      
-          for (var i = 0; i < consolidatedRanges.length; ++i) {
-            var range = consolidatedRanges[i];
-            out.push(encodeEscape(range[0]));
-            if (range[1] > range[0]) {
-              if (range[1] + 1 > range[0]) { out.push('-'); }
-              out.push(encodeEscape(range[1]));
-            }
-          }
-          out.push(']');
-          return out.join('');
-        }
-      
-        function allowAnywhereFoldCaseAndRenumberGroups(regex) {
-          // Split into character sets, escape sequences, punctuation strings
-          // like ('(', '(?:', ')', '^'), and runs of characters that do not
-          // include any of the above.
-          var parts = regex.source.match(
-              new RegExp(
-                  '(?:'
-                  + '\\[(?:[^\\x5C\\x5D]|\\\\[\\s\\S])*\\]'  // a character set
-                  + '|\\\\u[A-Fa-f0-9]{4}'  // a unicode escape
-                  + '|\\\\x[A-Fa-f0-9]{2}'  // a hex escape
-                  + '|\\\\[0-9]+'  // a back-reference or octal escape
-                  + '|\\\\[^ux0-9]'  // other escape sequence
-                  + '|\\(\\?[:!=]'  // start of a non-capturing group
-                  + '|[\\(\\)\\^]'  // start/end of a group, or line start
-                  + '|[^\\x5B\\x5C\\(\\)\\^]+'  // run of other characters
-                  + ')',
-                  'g'));
-          var n = parts.length;
-      
-          // Maps captured group numbers to the number they will occupy in
-          // the output or to -1 if that has not been determined, or to
-          // undefined if they need not be capturing in the output.
-          var capturedGroups = [];
-      
-          // Walk over and identify back references to build the capturedGroups
-          // mapping.
-          for (var i = 0, groupIndex = 0; i < n; ++i) {
-            var p = parts[i];
-            if (p === '(') {
-              // groups are 1-indexed, so max group index is count of '('
-              ++groupIndex;
-            } else if ('\\' === p.charAt(0)) {
-              var decimalValue = +p.substring(1);
-              if (decimalValue) {
-                if (decimalValue <= groupIndex) {
-                  capturedGroups[decimalValue] = -1;
-                } else {
-                  // Replace with an unambiguous escape sequence so that
-                  // an octal escape sequence does not turn into a backreference
-                  // to a capturing group from an earlier regex.
-                  parts[i] = encodeEscape(decimalValue);
-                }
-              }
-            }
-          }
-      
-          // Renumber groups and reduce capturing groups to non-capturing groups
-          // where possible.
-          for (var i = 1; i < capturedGroups.length; ++i) {
-            if (-1 === capturedGroups[i]) {
-              capturedGroups[i] = ++capturedGroupIndex;
-            }
-          }
-          for (var i = 0, groupIndex = 0; i < n; ++i) {
-            var p = parts[i];
-            if (p === '(') {
-              ++groupIndex;
-              if (!capturedGroups[groupIndex]) {
-                parts[i] = '(?:';
-              }
-            } else if ('\\' === p.charAt(0)) {
-              var decimalValue = +p.substring(1);
-              if (decimalValue && decimalValue <= groupIndex) {
-                parts[i] = '\\' + capturedGroups[decimalValue];
-              }
-            }
-          }
-      
-          // Remove any prefix anchors so that the output will match anywhere.
-          // ^^ really does mean an anchored match though.
-          for (var i = 0; i < n; ++i) {
-            if ('^' === parts[i] && '^' !== parts[i + 1]) { parts[i] = ''; }
-          }
-      
-          // Expand letters to groups to handle mixing of case-sensitive and
-          // case-insensitive patterns if necessary.
-          if (regex.ignoreCase && needToFoldCase) {
-            for (var i = 0; i < n; ++i) {
-              var p = parts[i];
-              var ch0 = p.charAt(0);
-              if (p.length >= 2 && ch0 === '[') {
-                parts[i] = caseFoldCharset(p);
-              } else if (ch0 !== '\\') {
-                // TODO: handle letters in numeric escapes.
-                parts[i] = p.replace(
-                    /[a-zA-Z]/g,
-                    function (ch) {
-                      var cc = ch.charCodeAt(0);
-                      return '[' + String.fromCharCode(cc & ~32, cc | 32) + ']';
-                    });
-              }
-            }
-          }
-      
-          return parts.join('');
-        }
-      
-        var rewritten = [];
-        for (var i = 0, n = regexs.length; i < n; ++i) {
-          var regex = regexs[i];
-          if (regex.global || regex.multiline) { throw new Error('' + regex); }
-          rewritten.push(
-              '(?:' + allowAnywhereFoldCaseAndRenumberGroups(regex) + ')');
-        }
-      
-        return new RegExp(rewritten.join('|'), ignoreCase ? 'gi' : 'g');
-      }
-    
-      /**
-       * Split markup into a string of source code and an array mapping ranges in
-       * that string to the text nodes in which they appear.
-       *
-       * <p>
-       * The HTML DOM structure:</p>
-       * <pre>
-       * (Element   "p"
-       *   (Element "b"
-       *     (Text  "print "))       ; #1
-       *   (Text    "'Hello '")      ; #2
-       *   (Element "br")            ; #3
-       *   (Text    "  + 'World';")) ; #4
-       * </pre>
-       * <p>
-       * corresponds to the HTML
-       * {@code <p><b>print </b>'Hello '<br>  + 'World';</p>}.</p>
-       *
-       * <p>
-       * It will produce the output:</p>
-       * <pre>
-       * {
-       *   sourceCode: "print 'Hello '\n  + 'World';",
-       *   //                     1          2
-       *   //           012345678901234 5678901234567
-       *   spans: [0, #1, 6, #2, 14, #3, 15, #4]
-       * }
-       * </pre>
-       * <p>
-       * where #1 is a reference to the {@code "print "} text node above, and so
-       * on for the other text nodes.
-       * </p>
-       *
-       * <p>
-       * The {@code} spans array is an array of pairs.  Even elements are the start
-       * indices of substrings, and odd elements are the text nodes (or BR elements)
-       * that contain the text for those substrings.
-       * Substrings continue until the next index or the end of the source.
-       * </p>
-       *
-       * @param {Node} node an HTML DOM subtree containing source-code.
-       * @param {boolean} isPreformatted true if white-space in text nodes should
-       *    be considered significant.
-       * @return {Object} source code and the text nodes in which they occur.
-       */
-      function extractSourceSpans(node, isPreformatted) {
-        var nocode = /(?:^|\s)nocode(?:\s|$)/;
-      
-        var chunks = [];
-        var length = 0;
-        var spans = [];
-        var k = 0;
-      
-        function walk(node) {
-          var type = node.nodeType;
-          if (type == 1) {  // Element
-            if (nocode.test(node.className)) { return; }
-            for (var child = node.firstChild; child; child = child.nextSibling) {
-              walk(child);
-            }
-            var nodeName = node.nodeName.toLowerCase();
-            if ('br' === nodeName || 'li' === nodeName) {
-              chunks[k] = '\n';
-              spans[k << 1] = length++;
-              spans[(k++ << 1) | 1] = node;
-            }
-          } else if (type == 3 || type == 4) {  // Text
-            var text = node.nodeValue;
-            if (text.length) {
-              if (!isPreformatted) {
-                text = text.replace(/[ \t\r\n]+/g, ' ');
-              } else {
-                text = text.replace(/\r\n?/g, '\n');  // Normalize newlines.
-              }
-              // TODO: handle tabs here?
-              chunks[k] = text;
-              spans[k << 1] = length;
-              length += text.length;
-              spans[(k++ << 1) | 1] = node;
-            }
-          }
-        }
-      
-        walk(node);
-      
-        return {
-          sourceCode: chunks.join('').replace(/\n$/, ''),
-          spans: spans
-        };
-      }
-    
-      /**
-       * Apply the given language handler to sourceCode and add the resulting
-       * decorations to out.
-       * @param {number} basePos the index of sourceCode within the chunk of source
-       *    whose decorations are already present on out.
-       */
-      function appendDecorations(basePos, sourceCode, langHandler, out) {
-        if (!sourceCode) { return; }
-        var job = {
-          sourceCode: sourceCode,
-          basePos: basePos
-        };
-        langHandler(job);
-        out.push.apply(out, job.decorations);
-      }
-    
-      var notWs = /\S/;
-    
-      /**
-       * Given an element, if it contains only one child element and any text nodes
-       * it contains contain only space characters, return the sole child element.
-       * Otherwise returns undefined.
-       * <p>
-       * This is meant to return the CODE element in {@code <pre><code ...>} when
-       * there is a single child element that contains all the non-space textual
-       * content, but not to return anything where there are multiple child elements
-       * as in {@code <pre><code>...</code><code>...</code></pre>} or when there
-       * is textual content.
-       */
-      function childContentWrapper(element) {
-        var wrapper = undefined;
-        for (var c = element.firstChild; c; c = c.nextSibling) {
-          var type = c.nodeType;
-          wrapper = (type === 1)  // Element Node
-              ? (wrapper ? element : c)
-              : (type === 3)  // Text Node
-              ? (notWs.test(c.nodeValue) ? element : wrapper)
-              : wrapper;
-        }
-        return wrapper === element ? undefined : wrapper;
-      }
-    
-      /** Given triples of [style, pattern, context] returns a lexing function,
-        * The lexing function interprets the patterns to find token boundaries and
-        * returns a decoration list of the form
-        * [index_0, style_0, index_1, style_1, ..., index_n, style_n]
-        * where index_n is an index into the sourceCode, and style_n is a style
-        * constant like PR_PLAIN.  index_n-1 <= index_n, and style_n-1 applies to
-        * all characters in sourceCode[index_n-1:index_n].
-        *
-        * The stylePatterns is a list whose elements have the form
-        * [style : string, pattern : RegExp, DEPRECATED, shortcut : string].
-        *
-        * Style is a style constant like PR_PLAIN, or can be a string of the
-        * form 'lang-FOO', where FOO is a language extension describing the
-        * language of the portion of the token in $1 after pattern executes.
-        * E.g., if style is 'lang-lisp', and group 1 contains the text
-        * '(hello (world))', then that portion of the token will be passed to the
-        * registered lisp handler for formatting.
-        * The text before and after group 1 will be restyled using this decorator
-        * so decorators should take care that this doesn't result in infinite
-        * recursion.  For example, the HTML lexer rule for SCRIPT elements looks
-        * something like ['lang-js', /<[s]cript>(.+?)<\/script>/].  This may match
-        * '<script>foo()<\/script>', which would cause the current decorator to
-        * be called with '<script>' which would not match the same rule since
-        * group 1 must not be empty, so it would be instead styled as PR_TAG by
-        * the generic tag rule.  The handler registered for the 'js' extension would
-        * then be called with 'foo()', and finally, the current decorator would
-        * be called with '<\/script>' which would not match the original rule and
-        * so the generic tag rule would identify it as a tag.
-        *
-        * Pattern must only match prefixes, and if it matches a prefix, then that
-        * match is considered a token with the same style.
-        *
-        * Context is applied to the last non-whitespace, non-comment token
-        * recognized.
-        *
-        * Shortcut is an optional string of characters, any of which, if the first
-        * character, gurantee that this pattern and only this pattern matches.
-        *
-        * @param {Array} shortcutStylePatterns patterns that always start with
-        *   a known character.  Must have a shortcut string.
-        * @param {Array} fallthroughStylePatterns patterns that will be tried in
-        *   order if the shortcut ones fail.  May have shortcuts.
-        *
-        * @return {function (Object)} a
-        *   function that takes source code and returns a list of decorations.
-        */
-      function createSimpleLexer(shortcutStylePatterns, fallthroughStylePatterns) {
-        var shortcuts = {};
-        var tokenizer;
-        (function () {
-          var allPatterns = shortcutStylePatterns.concat(fallthroughStylePatterns);
-          var allRegexs = [];
-          var regexKeys = {};
-          for (var i = 0, n = allPatterns.length; i < n; ++i) {
-            var patternParts = allPatterns[i];
-            var shortcutChars = patternParts[3];
-            if (shortcutChars) {
-              for (var c = shortcutChars.length; --c >= 0;) {
-                shortcuts[shortcutChars.charAt(c)] = patternParts;
-              }
-            }
-            var regex = patternParts[1];
-            var k = '' + regex;
-            if (!regexKeys.hasOwnProperty(k)) {
-              allRegexs.push(regex);
-              regexKeys[k] = null;
-            }
-          }
-          allRegexs.push(/[\0-\uffff]/);
-          tokenizer = combinePrefixPatterns(allRegexs);
-        })();
-    
-        var nPatterns = fallthroughStylePatterns.length;
-    
-        /**
-         * Lexes job.sourceCode and produces an output array job.decorations of
-         * style classes preceded by the position at which they start in
-         * job.sourceCode in order.
-         *
-         * @param {Object} job an object like <pre>{
-         *    sourceCode: {string} sourceText plain text,
-         *    basePos: {int} position of job.sourceCode in the larger chunk of
-         *        sourceCode.
-         * }</pre>
-         */
-        var decorate = function (job) {
-          var sourceCode = job.sourceCode, basePos = job.basePos;
-          /** Even entries are positions in source in ascending order.  Odd enties
-            * are style markers (e.g., PR_COMMENT) that run from that position until
-            * the end.
-            * @type {Array.<number|string>}
-            */
-          var decorations = [basePos, PR_PLAIN];
-          var pos = 0;  // index into sourceCode
-          var tokens = sourceCode.match(tokenizer) || [];
-          var styleCache = {};
-    
-          for (var ti = 0, nTokens = tokens.length; ti < nTokens; ++ti) {
-            var token = tokens[ti];
-            var style = styleCache[token];
-            var match = void 0;
-    
-            var isEmbedded;
-            if (typeof style === 'string') {
-              isEmbedded = false;
-            } else {
-              var patternParts = shortcuts[token.charAt(0)];
-              if (patternParts) {
-                match = token.match(patternParts[1]);
-                style = patternParts[0];
-              } else {
-                for (var i = 0; i < nPatterns; ++i) {
-                  patternParts = fallthroughStylePatterns[i];
-                  match = token.match(patternParts[1]);
-                  if (match) {
-                    style = patternParts[0];
-                    break;
-                  }
-                }
-    
-                if (!match) {  // make sure that we make progress
-                  style = PR_PLAIN;
-                }
-              }
-    
-              isEmbedded = style.length >= 5 && 'lang-' === style.substring(0, 5);
-              if (isEmbedded && !(match && typeof match[1] === 'string')) {
-                isEmbedded = false;
-                style = PR_SOURCE;
-              }
-    
-              if (!isEmbedded) { styleCache[token] = style; }
-            }
-    
-            var tokenStart = pos;
-            pos += token.length;
-    
-            if (!isEmbedded) {
-              decorations.push(basePos + tokenStart, style);
-            } else {  // Treat group 1 as an embedded block of source code.
-              var embeddedSource = match[1];
-              var embeddedSourceStart = token.indexOf(embeddedSource);
-              var embeddedSourceEnd = embeddedSourceStart + embeddedSource.length;
-              if (match[2]) {
-                // If embeddedSource can be blank, then it would match at the
-                // beginning which would cause us to infinitely recurse on the
-                // entire token, so we catch the right context in match[2].
-                embeddedSourceEnd = token.length - match[2].length;
-                embeddedSourceStart = embeddedSourceEnd - embeddedSource.length;
-              }
-              var lang = style.substring(5);
-              // Decorate the left of the embedded source
-              appendDecorations(
-                  basePos + tokenStart,
-                  token.substring(0, embeddedSourceStart),
-                  decorate, decorations);
-              // Decorate the embedded source
-              appendDecorations(
-                  basePos + tokenStart + embeddedSourceStart,
-                  embeddedSource,
-                  langHandlerForExtension(lang, embeddedSource),
-                  decorations);
-              // Decorate the right of the embedded section
-              appendDecorations(
-                  basePos + tokenStart + embeddedSourceEnd,
-                  token.substring(embeddedSourceEnd),
-                  decorate, decorations);
-            }
-          }
-          job.decorations = decorations;
-        };
-        return decorate;
-      }
-    
-      /** returns a function that produces a list of decorations from source text.
-        *
-        * This code treats ", ', and ` as string delimiters, and \ as a string
-        * escape.  It does not recognize perl's qq() style strings.
-        * It has no special handling for double delimiter escapes as in basic, or
-        * the tripled delimiters used in python, but should work on those regardless
-        * although in those cases a single string literal may be broken up into
-        * multiple adjacent string literals.
-        *
-        * It recognizes C, C++, and shell style comments.
-        *
-        * @param {Object} options a set of optional parameters.
-        * @return {function (Object)} a function that examines the source code
-        *     in the input job and builds the decoration list.
-        */
-      function sourceDecorator(options) {
-        var shortcutStylePatterns = [], fallthroughStylePatterns = [];
-        if (options['tripleQuotedStrings']) {
-          // '''multi-line-string''', 'single-line-string', and double-quoted
-          shortcutStylePatterns.push(
-              [PR_STRING,  /^(?:\'\'\'(?:[^\'\\]|\\[\s\S]|\'{1,2}(?=[^\']))*(?:\'\'\'|$)|\"\"\"(?:[^\"\\]|\\[\s\S]|\"{1,2}(?=[^\"]))*(?:\"\"\"|$)|\'(?:[^\\\']|\\[\s\S])*(?:\'|$)|\"(?:[^\\\"]|\\[\s\S])*(?:\"|$))/,
-               null, '\'"']);
-        } else if (options['multiLineStrings']) {
-          // 'multi-line-string', "multi-line-string"
-          shortcutStylePatterns.push(
-              [PR_STRING,  /^(?:\'(?:[^\\\']|\\[\s\S])*(?:\'|$)|\"(?:[^\\\"]|\\[\s\S])*(?:\"|$)|\`(?:[^\\\`]|\\[\s\S])*(?:\`|$))/,
-               null, '\'"`']);
-        } else {
-          // 'single-line-string', "single-line-string"
-          shortcutStylePatterns.push(
-              [PR_STRING,
-               /^(?:\'(?:[^\\\'\r\n]|\\.)*(?:\'|$)|\"(?:[^\\\"\r\n]|\\.)*(?:\"|$))/,
-               null, '"\'']);
-        }
-        if (options['verbatimStrings']) {
-          // verbatim-string-literal production from the C# grammar.  See issue 93.
-          fallthroughStylePatterns.push(
-              [PR_STRING, /^@\"(?:[^\"]|\"\")*(?:\"|$)/, null]);
-        }
-        var hc = options['hashComments'];
-        if (hc) {
-          if (options['cStyleComments']) {
-            if (hc > 1) {  // multiline hash comments
-              shortcutStylePatterns.push(
-                  [PR_COMMENT, /^#(?:##(?:[^#]|#(?!##))*(?:###|$)|.*)/, null, '#']);
-            } else {
-              // Stop C preprocessor declarations at an unclosed open comment
-              shortcutStylePatterns.push(
-                  [PR_COMMENT, /^#(?:(?:define|e(?:l|nd)if|else|error|ifn?def|include|line|pragma|undef|warning)\b|[^\r\n]*)/,
-                   null, '#']);
-            }
-            // #include <stdio.h>
-            fallthroughStylePatterns.push(
-                [PR_STRING,
-                 /^<(?:(?:(?:\.\.\/)*|\/?)(?:[\w-]+(?:\/[\w-]+)+)?[\w-]+\.h(?:h|pp|\+\+)?|[a-z]\w*)>/,
-                 null]);
-          } else {
-            shortcutStylePatterns.push([PR_COMMENT, /^#[^\r\n]*/, null, '#']);
-          }
-        }
-        if (options['cStyleComments']) {
-          fallthroughStylePatterns.push([PR_COMMENT, /^\/\/[^\r\n]*/, null]);
-          fallthroughStylePatterns.push(
-              [PR_COMMENT, /^\/\*[\s\S]*?(?:\*\/|$)/, null]);
-        }
-        var regexLiterals = options['regexLiterals'];
-        if (regexLiterals) {
-          /**
-           * @const
-           */
-          var regexExcls = regexLiterals > 1
-            ? ''  // Multiline regex literals
-            : '\n\r';
-          /**
-           * @const
-           */
-          var regexAny = regexExcls ? '.' : '[\\S\\s]';
-          /**
-           * @const
-           */
-          var REGEX_LITERAL = (
-              // A regular expression literal starts with a slash that is
-              // not followed by * or / so that it is not confused with
-              // comments.
-              '/(?=[^/*' + regexExcls + '])'
-              // and then contains any number of raw characters,
-              + '(?:[^/\\x5B\\x5C' + regexExcls + ']'
-              // escape sequences (\x5C),
-              +    '|\\x5C' + regexAny
-              // or non-nesting character sets (\x5B\x5D);
-              +    '|\\x5B(?:[^\\x5C\\x5D' + regexExcls + ']'
-              +             '|\\x5C' + regexAny + ')*(?:\\x5D|$))+'
-              // finally closed by a /.
-              + '/');
-          fallthroughStylePatterns.push(
-              ['lang-regex',
-               RegExp('^' + REGEXP_PRECEDER_PATTERN + '(' + REGEX_LITERAL + ')')
-               ]);
-        }
-    
-        var types = options['types'];
-        if (types) {
-          fallthroughStylePatterns.push([PR_TYPE, types]);
-        }
-    
-        var keywords = ("" + options['keywords']).replace(/^ | $/g, '');
-        if (keywords.length) {
-          fallthroughStylePatterns.push(
-              [PR_KEYWORD,
-               new RegExp('^(?:' + keywords.replace(/[\s,]+/g, '|') + ')\\b'),
-               null]);
-        }
-    
-        shortcutStylePatterns.push([PR_PLAIN,       /^\s+/, null, ' \r\n\t\xA0']);
-    
-        var punctuation =
-          // The Bash man page says
-    
-          // A word is a sequence of characters considered as a single
-          // unit by GRUB. Words are separated by metacharacters,
-          // which are the following plus space, tab, and newline: { }
-          // | & $ ; < >
-          // ...
-          
-          // A word beginning with # causes that word and all remaining
-          // characters on that line to be ignored.
-    
-          // which means that only a '#' after /(?:^|[{}|&$;<>\s])/ starts a
-          // comment but empirically
-          // $ echo {#}
-          // {#}
-          // $ echo \$#
-          // $#
-          // $ echo }#
-          // }#
-    
-          // so /(?:^|[|&;<>\s])/ is more appropriate.
-    
-          // http://gcc.gnu.org/onlinedocs/gcc-2.95.3/cpp_1.html#SEC3
-          // suggests that this definition is compatible with a
-          // default mode that tries to use a single token definition
-          // to recognize both bash/python style comments and C
-          // preprocessor directives.
-    
-          // This definition of punctuation does not include # in the list of
-          // follow-on exclusions, so # will not be broken before if preceeded
-          // by a punctuation character.  We could try to exclude # after
-          // [|&;<>] but that doesn't seem to cause many major problems.
-          // If that does turn out to be a problem, we should change the below
-          // when hc is truthy to include # in the run of punctuation characters
-          // only when not followint [|&;<>].
-          '^.[^\\s\\w.$@\'"`/\\\\]*';
-        if (options['regexLiterals']) {
-          punctuation += '(?!\s*\/)';
-        }
-    
-        fallthroughStylePatterns.push(
-            // TODO(mikesamuel): recognize non-latin letters and numerals in idents
-            [PR_LITERAL,     /^@[a-z_$][a-z_$@0-9]*/i, null],
-            [PR_TYPE,        /^(?:[@_]?[A-Z]+[a-z][A-Za-z_$@0-9]*|\w+_t\b)/, null],
-            [PR_PLAIN,       /^[a-z_$][a-z_$@0-9]*/i, null],
-            [PR_LITERAL,
-             new RegExp(
-                 '^(?:'
-                 // A hex number
-                 + '0x[a-f0-9]+'
-                 // or an octal or decimal number,
-                 + '|(?:\\d(?:_\\d+)*\\d*(?:\\.\\d*)?|\\.\\d\\+)'
-                 // possibly in scientific notation
-                 + '(?:e[+\\-]?\\d+)?'
-                 + ')'
-                 // with an optional modifier like UL for unsigned long
-                 + '[a-z]*', 'i'),
-             null, '0123456789'],
-            // Don't treat escaped quotes in bash as starting strings.
-            // See issue 144.
-            [PR_PLAIN,       /^\\[\s\S]?/, null],
-            [PR_PUNCTUATION, new RegExp(punctuation), null]);
-    
-        return createSimpleLexer(shortcutStylePatterns, fallthroughStylePatterns);
-      }
-    
-      var decorateSource = sourceDecorator({
-            'keywords': ALL_KEYWORDS,
-            'hashComments': true,
-            'cStyleComments': true,
-            'multiLineStrings': true,
-            'regexLiterals': true
-          });
-    
-      /**
-       * Given a DOM subtree, wraps it in a list, and puts each line into its own
-       * list item.
-       *
-       * @param {Node} node modified in place.  Its content is pulled into an
-       *     HTMLOListElement, and each line is moved into a separate list item.
-       *     This requires cloning elements, so the input might not have unique
-       *     IDs after numbering.
-       * @param {boolean} isPreformatted true iff white-space in text nodes should
-       *     be treated as significant.
-       */
-      function numberLines(node, opt_startLineNum, isPreformatted) {
-        var nocode = /(?:^|\s)nocode(?:\s|$)/;
-        var lineBreak = /\r\n?|\n/;
-      
-        var document = node.ownerDocument;
-      
-        var li = document.createElement('li');
-        while (node.firstChild) {
-          li.appendChild(node.firstChild);
-        }
-        // An array of lines.  We split below, so this is initialized to one
-        // un-split line.
-        var listItems = [li];
-      
-        function walk(node) {
-          var type = node.nodeType;
-          if (type == 1 && !nocode.test(node.className)) {  // Element
-            if ('br' === node.nodeName) {
-              breakAfter(node);
-              // Discard the <BR> since it is now flush against a </LI>.
-              if (node.parentNode) {
-                node.parentNode.removeChild(node);
-              }
-            } else {
-              for (var child = node.firstChild; child; child = child.nextSibling) {
-                walk(child);
-              }
-            }
-          } else if ((type == 3 || type == 4) && isPreformatted) {  // Text
-            var text = node.nodeValue;
-            var match = text.match(lineBreak);
-            if (match) {
-              var firstLine = text.substring(0, match.index);
-              node.nodeValue = firstLine;
-              var tail = text.substring(match.index + match[0].length);
-              if (tail) {
-                var parent = node.parentNode;
-                parent.insertBefore(
-                  document.createTextNode(tail), node.nextSibling);
-              }
-              breakAfter(node);
-              if (!firstLine) {
-                // Don't leave blank text nodes in the DOM.
-                node.parentNode.removeChild(node);
-              }
-            }
-          }
-        }
-      
-        // Split a line after the given node.
-        function breakAfter(lineEndNode) {
-          // If there's nothing to the right, then we can skip ending the line
-          // here, and move root-wards since splitting just before an end-tag
-          // would require us to create a bunch of empty copies.
-          while (!lineEndNode.nextSibling) {
-            lineEndNode = lineEndNode.parentNode;
-            if (!lineEndNode) { return; }
-          }
-      
-          function breakLeftOf(limit, copy) {
-            // Clone shallowly if this node needs to be on both sides of the break.
-            var rightSide = copy ? limit.cloneNode(false) : limit;
-            var parent = limit.parentNode;
-            if (parent) {
-              // We clone the parent chain.
-              // This helps us resurrect important styling elements that cross lines.
-              // E.g. in <i>Foo<br>Bar</i>
-              // should be rewritten to <li><i>Foo</i></li><li><i>Bar</i></li>.
-              var parentClone = breakLeftOf(parent, 1);
-              // Move the clone and everything to the right of the original
-              // onto the cloned parent.
-              var next = limit.nextSibling;
-              parentClone.appendChild(rightSide);
-              for (var sibling = next; sibling; sibling = next) {
-                next = sibling.nextSibling;
-                parentClone.appendChild(sibling);
-              }
-            }
-            return rightSide;
-          }
-      
-          var copiedListItem = breakLeftOf(lineEndNode.nextSibling, 0);
-      
-          // Walk the parent chain until we reach an unattached LI.
-          for (var parent;
-               // Check nodeType since IE invents document fragments.
-               (parent = copiedListItem.parentNode) && parent.nodeType === 1;) {
-            copiedListItem = parent;
-          }
-          // Put it on the list of lines for later processing.
-          listItems.push(copiedListItem);
-        }
-      
-        // Split lines while there are lines left to split.
-        for (var i = 0;  // Number of lines that have been split so far.
-             i < listItems.length;  // length updated by breakAfter calls.
-             ++i) {
-          walk(listItems[i]);
-        }
-      
-        // Make sure numeric indices show correctly.
-        if (opt_startLineNum === (opt_startLineNum|0)) {
-          listItems[0].setAttribute('value', opt_startLineNum);
-        }
-      
-        var ol = document.createElement('ol');
-        ol.className = 'linenums';
-        var offset = Math.max(0, ((opt_startLineNum - 1 /* zero index */)) | 0) || 0;
-        for (var i = 0, n = listItems.length; i < n; ++i) {
-          li = listItems[i];
-          // Stick a class on the LIs so that stylesheets can
-          // color odd/even rows, or any other row pattern that
-          // is co-prime with 10.
-          li.className = 'L' + ((i + offset) % 10);
-          if (!li.firstChild) {
-            li.appendChild(document.createTextNode('\xA0'));
-          }
-          ol.appendChild(li);
-        }
-      
-        node.appendChild(ol);
-      }    
-      /**
-       * Breaks {@code job.sourceCode} around style boundaries in
-       * {@code job.decorations} and modifies {@code job.sourceNode} in place.
-       * @param {Object} job like <pre>{
-       *    sourceCode: {string} source as plain text,
-       *    sourceNode: {HTMLElement} the element containing the source,
-       *    spans: {Array.<number|Node>} alternating span start indices into source
-       *       and the text node or element (e.g. {@code <BR>}) corresponding to that
-       *       span.
-       *    decorations: {Array.<number|string} an array of style classes preceded
-       *       by the position at which they start in job.sourceCode in order
-       * }</pre>
-       * @private
-       */
-      function recombineTagsAndDecorations(job) {
-        var isIE8OrEarlier = /\bMSIE\s(\d+)/.exec(navigator.userAgent);
-        isIE8OrEarlier = isIE8OrEarlier && +isIE8OrEarlier[1] <= 8;
-        var newlineRe = /\n/g;
-      
-        var source = job.sourceCode;
-        var sourceLength = source.length;
-        // Index into source after the last code-unit recombined.
-        var sourceIndex = 0;
-      
-        var spans = job.spans;
-        var nSpans = spans.length;
-        // Index into spans after the last span which ends at or before sourceIndex.
-        var spanIndex = 0;
-      
-        var decorations = job.decorations;
-        var nDecorations = decorations.length;
-        // Index into decorations after the last decoration which ends at or before
-        // sourceIndex.
-        var decorationIndex = 0;
-      
-        // Remove all zero-length decorations.
-        decorations[nDecorations] = sourceLength;
-        var decPos, i;
-        for (i = decPos = 0; i < nDecorations;) {
-          if (decorations[i] !== decorations[i + 2]) {
-            decorations[decPos++] = decorations[i++];
-            decorations[decPos++] = decorations[i++];
-          } else {
-            i += 2;
-          }
-        }
-        nDecorations = decPos;
-      
-        // Simplify decorations.
-        for (i = decPos = 0; i < nDecorations;) {
-          var startPos = decorations[i];
-          // Conflate all adjacent decorations that use the same style.
-          var startDec = decorations[i + 1];
-          var end = i + 2;
-          while (end + 2 <= nDecorations && decorations[end + 1] === startDec) {
-            end += 2;
-          }
-          decorations[decPos++] = startPos;
-          decorations[decPos++] = startDec;
-          i = end;
-        }
-      
-        nDecorations = decorations.length = decPos;
-      
-        var sourceNode = job.sourceNode;
-        var oldDisplay;
-        if (sourceNode) {
-          oldDisplay = sourceNode.style.display;
-          sourceNode.style.display = 'none';
-        }
-        try {
-          var decoration = null;
-          while (spanIndex < nSpans) {
-            var spanStart = spans[spanIndex];
-            var spanEnd = spans[spanIndex + 2] || sourceLength;
-      
-            var decEnd = decorations[decorationIndex + 2] || sourceLength;
-      
-            var end = Math.min(spanEnd, decEnd);
-      
-            var textNode = spans[spanIndex + 1];
-            var styledText;
-            if (textNode.nodeType !== 1  // Don't muck with <BR>s or <LI>s
-                // Don't introduce spans around empty text nodes.
-                && (styledText = source.substring(sourceIndex, end))) {
-              // This may seem bizarre, and it is.  Emitting LF on IE causes the
-              // code to display with spaces instead of line breaks.
-              // Emitting Windows standard issue linebreaks (CRLF) causes a blank
-              // space to appear at the beginning of every line but the first.
-              // Emitting an old Mac OS 9 line separator makes everything spiffy.
-              if (isIE8OrEarlier) {
-                styledText = styledText.replace(newlineRe, '\r');
-              }
-              textNode.nodeValue = styledText;
-              var document = textNode.ownerDocument;
-              var span = document.createElement('span');
-              span.className = decorations[decorationIndex + 1];
-              var parentNode = textNode.parentNode;
-              parentNode.replaceChild(span, textNode);
-              span.appendChild(textNode);
-              if (sourceIndex < spanEnd) {  // Split off a text node.
-                spans[spanIndex + 1] = textNode
-                    // TODO: Possibly optimize by using '' if there's no flicker.
-                    = document.createTextNode(source.substring(end, spanEnd));
-                parentNode.insertBefore(textNode, span.nextSibling);
-              }
-            }
-      
-            sourceIndex = end;
-      
-            if (sourceIndex >= spanEnd) {
-              spanIndex += 2;
-            }
-            if (sourceIndex >= decEnd) {
-              decorationIndex += 2;
-            }
-          }
-        } finally {
-          if (sourceNode) {
-            sourceNode.style.display = oldDisplay;
-          }
-        }
-      }
-    
-      /** Maps language-specific file extensions to handlers. */
-      var langHandlerRegistry = {};
-      /** Register a language handler for the given file extensions.
-        * @param {function (Object)} handler a function from source code to a list
-        *      of decorations.  Takes a single argument job which describes the
-        *      state of the computation.   The single parameter has the form
-        *      {@code {
-        *        sourceCode: {string} as plain text.
-        *        decorations: {Array.<number|string>} an array of style classes
-        *                     preceded by the position at which they start in
-        *                     job.sourceCode in order.
-        *                     The language handler should assigned this field.
-        *        basePos: {int} the position of source in the larger source chunk.
-        *                 All positions in the output decorations array are relative
-        *                 to the larger source chunk.
-        *      } }
-        * @param {Array.<string>} fileExtensions
-        */
-      function registerLangHandler(handler, fileExtensions) {
-        for (var i = fileExtensions.length; --i >= 0;) {
-          var ext = fileExtensions[i];
-          if (!langHandlerRegistry.hasOwnProperty(ext)) {
-            langHandlerRegistry[ext] = handler;
-          } else if (win['console']) {
-            console['warn']('cannot override language handler %s', ext);
-          }
-        }
-      }
-      function langHandlerForExtension(extension, source) {
-        if (!(extension && langHandlerRegistry.hasOwnProperty(extension))) {
-          // Treat it as markup if the first non whitespace character is a < and
-          // the last non-whitespace character is a >.
-          extension = /^\s*</.test(source)
-              ? 'default-markup'
-              : 'default-code';
-        }
-        return langHandlerRegistry[extension];
-      }
-      registerLangHandler(decorateSource, ['default-code']);
-      registerLangHandler(
-          createSimpleLexer(
-              [],
-              [
-               [PR_PLAIN,       /^[^<?]+/],
-               [PR_DECLARATION, /^<!\w[^>]*(?:>|$)/],
-               [PR_COMMENT,     /^<\!--[\s\S]*?(?:-\->|$)/],
-               // Unescaped content in an unknown language
-               ['lang-',        /^<\?([\s\S]+?)(?:\?>|$)/],
-               ['lang-',        /^<%([\s\S]+?)(?:%>|$)/],
-               [PR_PUNCTUATION, /^(?:<[%?]|[%?]>)/],
-               ['lang-',        /^<xmp\b[^>]*>([\s\S]+?)<\/xmp\b[^>]*>/i],
-               // Unescaped content in javascript.  (Or possibly vbscript).
-               ['lang-js',      /^<script\b[^>]*>([\s\S]*?)(<\/script\b[^>]*>)/i],
-               // Contains unescaped stylesheet content
-               ['lang-css',     /^<style\b[^>]*>([\s\S]*?)(<\/style\b[^>]*>)/i],
-               ['lang-in.tag',  /^(<\/?[a-z][^<>]*>)/i]
-              ]),
-          ['default-markup', 'htm', 'html', 'mxml', 'xhtml', 'xml', 'xsl']);
-      registerLangHandler(
-          createSimpleLexer(
-              [
-               [PR_PLAIN,        /^[\s]+/, null, ' \t\r\n'],
-               [PR_ATTRIB_VALUE, /^(?:\"[^\"]*\"?|\'[^\']*\'?)/, null, '\"\'']
-               ],
-              [
-               [PR_TAG,          /^^<\/?[a-z](?:[\w.:-]*\w)?|\/?>$/i],
-               [PR_ATTRIB_NAME,  /^(?!style[\s=]|on)[a-z](?:[\w:-]*\w)?/i],
-               ['lang-uq.val',   /^=\s*([^>\'\"\s]*(?:[^>\'\"\s\/]|\/(?=\s)))/],
-               [PR_PUNCTUATION,  /^[=<>\/]+/],
-               ['lang-js',       /^on\w+\s*=\s*\"([^\"]+)\"/i],
-               ['lang-js',       /^on\w+\s*=\s*\'([^\']+)\'/i],
-               ['lang-js',       /^on\w+\s*=\s*([^\"\'>\s]+)/i],
-               ['lang-css',      /^style\s*=\s*\"([^\"]+)\"/i],
-               ['lang-css',      /^style\s*=\s*\'([^\']+)\'/i],
-               ['lang-css',      /^style\s*=\s*([^\"\'>\s]+)/i]
-               ]),
-          ['in.tag']);
-      registerLangHandler(
-          createSimpleLexer([], [[PR_ATTRIB_VALUE, /^[\s\S]+/]]), ['uq.val']);
-      registerLangHandler(sourceDecorator({
-              'keywords': CPP_KEYWORDS,
-              'hashComments': true,
-              'cStyleComments': true,
-              'types': C_TYPES
-            }), ['c', 'cc', 'cpp', 'cxx', 'cyc', 'm']);
-      registerLangHandler(sourceDecorator({
-              'keywords': 'null,true,false'
-            }), ['json']);
-      registerLangHandler(sourceDecorator({
-              'keywords': CSHARP_KEYWORDS,
-              'hashComments': true,
-              'cStyleComments': true,
-              'verbatimStrings': true,
-              'types': C_TYPES
-            }), ['cs']);
-      registerLangHandler(sourceDecorator({
-              'keywords': JAVA_KEYWORDS,
-              'cStyleComments': true
-            }), ['java']);
-      registerLangHandler(sourceDecorator({
-              'keywords': SH_KEYWORDS,
-              'hashComments': true,
-              'multiLineStrings': true
-            }), ['bash', 'bsh', 'csh', 'sh']);
-      registerLangHandler(sourceDecorator({
-              'keywords': PYTHON_KEYWORDS,
-              'hashComments': true,
-              'multiLineStrings': true,
-              'tripleQuotedStrings': true
-            }), ['cv', 'py', 'python']);
-      registerLangHandler(sourceDecorator({
-              'keywords': PERL_KEYWORDS,
-              'hashComments': true,
-              'multiLineStrings': true,
-              'regexLiterals': 2  // multiline regex literals
-            }), ['perl', 'pl', 'pm']);
-      registerLangHandler(sourceDecorator({
-              'keywords': RUBY_KEYWORDS,
-              'hashComments': true,
-              'multiLineStrings': true,
-              'regexLiterals': true
-            }), ['rb', 'ruby']);
-      registerLangHandler(sourceDecorator({
-              'keywords': JSCRIPT_KEYWORDS,
-              'cStyleComments': true,
-              'regexLiterals': true
-            }), ['javascript', 'js']);
-      registerLangHandler(sourceDecorator({
-              'keywords': COFFEE_KEYWORDS,
-              'hashComments': 3,  // ### style block comments
-              'cStyleComments': true,
-              'multilineStrings': true,
-              'tripleQuotedStrings': true,
-              'regexLiterals': true
-            }), ['coffee']);
-      registerLangHandler(sourceDecorator({
-              'keywords': RUST_KEYWORDS,
-              'cStyleComments': true,
-              'multilineStrings': true
-            }), ['rc', 'rs', 'rust']);
-      registerLangHandler(
-          createSimpleLexer([], [[PR_STRING, /^[\s\S]+/]]), ['regex']);
-    
-      function applyDecorator(job) {
-        var opt_langExtension = job.langExtension;
-    
-        try {
-          // Extract tags, and convert the source code to plain text.
-          var sourceAndSpans = extractSourceSpans(job.sourceNode, job.pre);
-          /** Plain text. @type {string} */
-          var source = sourceAndSpans.sourceCode;
-          job.sourceCode = source;
-          job.spans = sourceAndSpans.spans;
-          job.basePos = 0;
-    
-          // Apply the appropriate language handler
-          langHandlerForExtension(opt_langExtension, source)(job);
-    
-          // Integrate the decorations and tags back into the source code,
-          // modifying the sourceNode in place.
-          recombineTagsAndDecorations(job);
-        } catch (e) {
-          if (win['console']) {
-            console['log'](e && e['stack'] || e);
-          }
-        }
-      }
-    
-      /**
-       * Pretty print a chunk of code.
-       * @param sourceCodeHtml {string} The HTML to pretty print.
-       * @param opt_langExtension {string} The language name to use.
-       *     Typically, a filename extension like 'cpp' or 'java'.
-       * @param opt_numberLines {number|boolean} True to number lines,
-       *     or the 1-indexed number of the first line in sourceCodeHtml.
-       */
-      function $prettyPrintOne(sourceCodeHtml, opt_langExtension, opt_numberLines) {
-        var container = document.createElement('div');
-        // This could cause images to load and onload listeners to fire.
-        // E.g. <img onerror="alert(1337)" src="nosuchimage.png">.
-        // We assume that the inner HTML is from a trusted source.
-        // The pre-tag is required for IE8 which strips newlines from innerHTML
-        // when it is injected into a <pre> tag.
-        // http://stackoverflow.com/questions/451486/pre-tag-loses-line-breaks-when-setting-innerhtml-in-ie
-        // http://stackoverflow.com/questions/195363/inserting-a-newline-into-a-pre-tag-ie-javascript
-        container.innerHTML = '<pre>' + sourceCodeHtml + '</pre>';
-        container = container.firstChild;
-        if (opt_numberLines) {
-          numberLines(container, opt_numberLines, true);
-        }
-    
-        var job = {
-          langExtension: opt_langExtension,
-          numberLines: opt_numberLines,
-          sourceNode: container,
-          pre: 1
-        };
-        applyDecorator(job);
-        return container.innerHTML;
-      }
-    
-       /**
-        * Find all the {@code <pre>} and {@code <code>} tags in the DOM with
-        * {@code class=prettyprint} and prettify them.
-        *
-        * @param {Function} opt_whenDone called when prettifying is done.
-        * @param {HTMLElement|HTMLDocument} opt_root an element or document
-        *   containing all the elements to pretty print.
-        *   Defaults to {@code document.body}.
-        */
-      function $prettyPrint(opt_whenDone, opt_root) {
-        var root = opt_root || document.body;
-        var doc = root.ownerDocument || document;
-        function byTagName(tn) { return root.getElementsByTagName(tn); }
-        // fetch a list of nodes to rewrite
-        var codeSegments = [byTagName('pre'), byTagName('code'), byTagName('xmp')];
-        var elements = [];
-        for (var i = 0; i < codeSegments.length; ++i) {
-          for (var j = 0, n = codeSegments[i].length; j < n; ++j) {
-            elements.push(codeSegments[i][j]);
-          }
-        }
-        codeSegments = null;
-    
-        var clock = Date;
-        if (!clock['now']) {
-          clock = { 'now': function () { return +(new Date); } };
-        }
-    
-        // The loop is broken into a series of continuations to make sure that we
-        // don't make the browser unresponsive when rewriting a large page.
-        var k = 0;
-        var prettyPrintingJob;
-    
-        var langExtensionRe = /\blang(?:uage)?-([\w.]+)(?!\S)/;
-        var prettyPrintRe = /\bprettyprint\b/;
-        var prettyPrintedRe = /\bprettyprinted\b/;
-        var preformattedTagNameRe = /pre|xmp/i;
-        var codeRe = /^code$/i;
-        var preCodeXmpRe = /^(?:pre|code|xmp)$/i;
-        var EMPTY = {};
-    
-        function doWork() {
-          var endTime = (win['PR_SHOULD_USE_CONTINUATION'] ?
-                         clock['now']() + 250 /* ms */ :
-                         Infinity);
-          for (; k < elements.length && clock['now']() < endTime; k++) {
-            var cs = elements[k];
-    
-            // Look for a preceding comment like
-            // <?prettify lang="..." linenums="..."?>
-            var attrs = EMPTY;
-            {
-              for (var preceder = cs; (preceder = preceder.previousSibling);) {
-                var nt = preceder.nodeType;
-                // <?foo?> is parsed by HTML 5 to a comment node (8)
-                // like <!--?foo?-->, but in XML is a processing instruction
-                var value = (nt === 7 || nt === 8) && preceder.nodeValue;
-                if (value
-                    ? !/^\??prettify\b/.test(value)
-                    : (nt !== 3 || /\S/.test(preceder.nodeValue))) {
-                  // Skip over white-space text nodes but not others.
-                  break;
-                }
-                if (value) {
-                  attrs = {};
-                  value.replace(
-                      /\b(\w+)=([\w:.%+-]+)/g,
-                    function (_, name, value) { attrs[name] = value; });
-                  break;
-                }
-              }
-            }
-    
-            var className = cs.className;
-            if ((attrs !== EMPTY || prettyPrintRe.test(className))
-                // Don't redo this if we've already done it.
-                // This allows recalling pretty print to just prettyprint elements
-                // that have been added to the page since last call.
-                && !prettyPrintedRe.test(className)) {
-    
-              // make sure this is not nested in an already prettified element
-              var nested = false;
-              for (var p = cs.parentNode; p; p = p.parentNode) {
-                var tn = p.tagName;
-                if (preCodeXmpRe.test(tn)
-                    && p.className && prettyPrintRe.test(p.className)) {
-                  nested = true;
-                  break;
-                }
-              }
-              if (!nested) {
-                // Mark done.  If we fail to prettyprint for whatever reason,
-                // we shouldn't try again.
-                cs.className += ' prettyprinted';
-    
-                // If the classes includes a language extensions, use it.
-                // Language extensions can be specified like
-                //     <pre class="prettyprint lang-cpp">
-                // the language extension "cpp" is used to find a language handler
-                // as passed to PR.registerLangHandler.
-                // HTML5 recommends that a language be specified using "language-"
-                // as the prefix instead.  Google Code Prettify supports both.
-                // http://dev.w3.org/html5/spec-author-view/the-code-element.html
-                var langExtension = attrs['lang'];
-                if (!langExtension) {
-                  langExtension = className.match(langExtensionRe);
-                  // Support <pre class="prettyprint"><code class="language-c">
-                  var wrapper;
-                  if (!langExtension && (wrapper = childContentWrapper(cs))
-                      && codeRe.test(wrapper.tagName)) {
-                    langExtension = wrapper.className.match(langExtensionRe);
-                  }
-    
-                  if (langExtension) { langExtension = langExtension[1]; }
-                }
-    
-                var preformatted;
-                if (preformattedTagNameRe.test(cs.tagName)) {
-                  preformatted = 1;
-                } else {
-                  var currentStyle = cs['currentStyle'];
-                  var defaultView = doc.defaultView;
-                  var whitespace = (
-                      currentStyle
-                      ? currentStyle['whiteSpace']
-                      : (defaultView
-                         && defaultView.getComputedStyle)
-                      ? defaultView.getComputedStyle(cs, null)
-                      .getPropertyValue('white-space')
-                      : 0);
-                  preformatted = whitespace
-                      && 'pre' === whitespace.substring(0, 3);
-                }
-    
-                // Look for a class like linenums or linenums:<n> where <n> is the
-                // 1-indexed number of the first line.
-                var lineNums = attrs['linenums'];
-                if (!(lineNums = lineNums === 'true' || +lineNums)) {
-                  lineNums = className.match(/\blinenums\b(?::(\d+))?/);
-                  lineNums =
-                    lineNums
-                    ? lineNums[1] && lineNums[1].length
-                      ? +lineNums[1] : true
-                    : false;
-                }
-                if (lineNums) { numberLines(cs, lineNums, preformatted); }
-    
-                // do the pretty printing
-                prettyPrintingJob = {
-                  langExtension: langExtension,
-                  sourceNode: cs,
-                  numberLines: lineNums,
-                  pre: preformatted
-                };
-                applyDecorator(prettyPrintingJob);
-              }
-            }
-          }
-          if (k < elements.length) {
-            // finish up in a continuation
-            setTimeout(doWork, 250);
-          } else if ('function' === typeof opt_whenDone) {
-            opt_whenDone();
-          }
-        }
-    
-        doWork();
-      }
-    
-      /**
-       * Contains functions for creating and registering new language handlers.
-       * @type {Object}
-       */
-      var PR = win['PR'] = {
-            'createSimpleLexer': createSimpleLexer,
-            'registerLangHandler': registerLangHandler,
-            'sourceDecorator': sourceDecorator,
-            'PR_ATTRIB_NAME': PR_ATTRIB_NAME,
-            'PR_ATTRIB_VALUE': PR_ATTRIB_VALUE,
-            'PR_COMMENT': PR_COMMENT,
-            'PR_DECLARATION': PR_DECLARATION,
-            'PR_KEYWORD': PR_KEYWORD,
-            'PR_LITERAL': PR_LITERAL,
-            'PR_NOCODE': PR_NOCODE,
-            'PR_PLAIN': PR_PLAIN,
-            'PR_PUNCTUATION': PR_PUNCTUATION,
-            'PR_SOURCE': PR_SOURCE,
-            'PR_STRING': PR_STRING,
-            'PR_TAG': PR_TAG,
-            'PR_TYPE': PR_TYPE,
-            'prettyPrintOne':
-               IN_GLOBAL_SCOPE
-                 ? (win['prettyPrintOne'] = $prettyPrintOne)
-                 : (prettyPrintOne = $prettyPrintOne),
-            'prettyPrint': prettyPrint =
-               IN_GLOBAL_SCOPE
-                 ? (win['prettyPrint'] = $prettyPrint)
-                 : (prettyPrint = $prettyPrint)
-          };
-    
-      // Make PR available via the Asynchronous Module Definition (AMD) API.
-      // Per https://github.com/amdjs/amdjs-api/wiki/AMD:
-      // The Asynchronous Module Definition (AMD) API specifies a
-      // mechanism for defining modules such that the module and its
-      // dependencies can be asynchronously loaded.
-      // ...
-      // To allow a clear indicator that a global define function (as
-      // needed for script src browser loading) conforms to the AMD API,
-      // any global define function SHOULD have a property called "amd"
-      // whose value is an object. This helps avoid conflict with any
-      // other existing JavaScript code that could have defined a define()
-      // function that does not conform to the AMD API.
-      if (typeof define === "function" && define['amd']) {
-        define("google-code-prettify", [], function () {
-          return PR; 
-        });
-      }
-    })();
-    return prettyPrint;
-  })();
-
-  // If this script is deferred or async and the document is already
-  // loaded we need to wait for language handlers to load before performing
-  // any autorun.
-  function onLangsLoaded() {
-    if (autorun) {
-      contentLoaded(
-        function () {
-          var n = callbacks.length;
-          var callback = n ? function () {
-            for (var i = 0; i < n; ++i) {
-              (function (i) {
-                 setTimeout(
-                   function () {
-                     win['exports'][callbacks[i]].apply(win, arguments);
-                   }, 0);
-               })(i);
-            }
-          } : void 0;
-          prettyPrint(callback);
-        });
-    }
-  }
-  checkPendingLanguages();
-
-}());
diff --git a/civicrm/bower_components/google-code-prettify/styles/demo.html b/civicrm/bower_components/google-code-prettify/styles/demo.html
deleted file mode 100644
index 9c9acadcfac360879664f3fcb5cc09b96ecaa2ee..0000000000000000000000000000000000000000
--- a/civicrm/bower_components/google-code-prettify/styles/demo.html
+++ /dev/null
@@ -1,61 +0,0 @@
-<!DOCTYPE HTML PUBLIC "-//IETF//DTD HTML//EN">
-<html><head>
-<script src="../src/prettify.js"></script>
-<script src="../src/lang-css.js"></script>
-<style>
-body { margin: 0; padding: 0 }
-pre { margin: 0 }
-</style>
-</head>
-<script>
-// This page displays some code styled using a theme named in the
-// query part of the URL.
-var themeName = decodeURIComponent(document.location.search.replace(/^\?/, ''));
-
-// Call out to the parent so that it can resize the iframe once this
-// document's body is loaded.
-function adjustHeightInParent() {
-  if (parent !== window) {
-    try {
-      var div = document.body.getElementsByTagName('div')[0];
-      parent.adjustChildIframeSize(
-          themeName, div.offsetWidth, div.offsetHeight);
-    } catch (ex) {
-      // Can happen when this page is opened in its own tab.
-    }
-  }
-}
-
-// Load the necessary CSS
-(function () {
-  document.title = 'Theme ' + themeName;
-  // Load the stylesheet that we're demoing.
-  var link = document.createElement('link');
-  link.rel = 'stylesheet';
-  link.type = 'text/css';
-  link.href = themeName === 'default'
-      ? '../src/prettify.css' : themeName + '.css';
-  document.getElementsByTagName('head')[0].appendChild(link);
-})();
-</script>
-
-<body onload="prettyPrint(); adjustHeightInParent()">
-<div style="width: 40em; display: inline-block">
-<pre class="prettyprint lang-html linenums">
-&lt;script type="text/javascript"&gt;
-// Say hello world until the user starts questioning
-// the meaningfulness of their existence.
-function helloWorld(world) {
-  for (var i = 42; --i &gt;= 0;) {
-    alert('Hello ' + String(world));
-  }
-}
-&lt;/script&gt;
-&lt;style&gt;
-p { color: pink }
-b { color: blue }
-u { color: "umber" }
-&lt;/style&gt;
-</pre>
-</div>
-</body></html>
diff --git a/civicrm/bower_components/google-code-prettify/styles/index.html b/civicrm/bower_components/google-code-prettify/styles/index.html
deleted file mode 100644
index abd6ef52652717df520315b87c6e8e158671b6a9..0000000000000000000000000000000000000000
--- a/civicrm/bower_components/google-code-prettify/styles/index.html
+++ /dev/null
@@ -1,89 +0,0 @@
-<!DOCTYPE HTML PUBLIC "-//IETF//DTD HTML//EN">
-<html><head>
-<title>Prettify Themes Gallery</title>
-<style type="text/css">
-iframe { width: 100%; border-style: none; margin: 0; padding: 0 }
-</style>
-<script>
-var allThemes = [
-  { name: 'default' },
-  { name: 'desert',
-    authorHtml: '<a href="http://code.google.com/u/@VhJeSlJYBhVMWgF7/">'
-        + 'techto&hellip;@<\/a>' },
-  { name: 'sunburst', authorHtml: 'David Leibovic' },
-  { name: 'sons-of-obsidian',
-    authorHtml: '<a href="http://CodeTunnel.com/blog/post/71'
-        + '/google-code-prettify-obsidian-theme">Alex Ford<\/a>' },
-  { name: 'doxy', authorHtml: 'Robert Sperberg' },
-];
-
-// Called by the demo.html frames loaded per theme to
-// size the iframes properly and to allow them to tile
-// the page nicely.
-function adjustChildIframeSize(themeName, width, height) {
-  if (typeof console != 'undefined') {
-    try {
-      console.log('adjusting ' + themeName + ' to ' + width + 'x' + height);
-    } catch (ex) {
-      // Don't bother logging log failure.
-    }
-  }
-
-  var container = document.getElementById(themeName).parentNode;
-  container.style.width = (+width + 16) + 'px';
-  container.style.display = 'inline-block';
-  var iframe = container.getElementsByTagName('iframe')[0];
-  iframe.style.height = (+height + 16) + 'px';
-}
-</script>
-</head>
-
-<body>
-<noscript>This page requires JavaScript</noscript>
-
-<h1>Gallery of themes for
-<a href="http://code.google.com/p/google-code-prettify/">code prettify</a></h1>
-<p>
-Click on a theme name for a link to the file in revision control.
-Print preview this page to see how the themes work on the printed page.
-</p>
-<script>(function () {
-  // Produce an iframe per theme.
-  // We pass the threme name to the iframe via its URI query, and
-  // it loads prettify and the theme CSS, and calls back to this page
-  // to resize the iframe.
-  for (var i = 0, n = allThemes.length; i < n; ++i) {
-    var theme = allThemes[i];
-    if (!theme) { continue; }
-    var iframe = document.createElement('iframe');
-    iframe.name = theme.name;
-    iframe.src = 'demo.html?' + encodeURIComponent(theme.name);
-    var header = document.createElement('h2');
-    header.id = theme.name;
-    var linkToThemeSrc = document.createElement('a');
-    linkToThemeSrc.href = (
-        'http://code.google.com/p/google-code-prettify/source/browse/trunk/' +
-        (theme.name === 'default'
-         ? 'src/prettify.css'
-         : 'styles/' + encodeURIComponent(theme.name) + '.css'));
-    linkToThemeSrc.appendChild(document.createTextNode(
-       theme.name.replace(/\b[a-z]/g,  // Capitalize first letter of each word
-       function (letter) { return letter.toUpperCase(); })));
-    header.appendChild(linkToThemeSrc);
-
-    var attribution;
-    if (theme.authorHtml) {
-      attribution = document.createElement('span');
-      attribution.className = 'attribution';
-      attribution.innerHTML = 'by ' + theme.authorHtml;
-    }
-
-    var div = document.createElement('div');
-    div.appendChild(header);
-    if (attribution) { div.appendChild(attribution); }
-    div.appendChild(iframe);
-    document.body.appendChild(div);
-  }
-})()</script>
-
-</body></html>
diff --git a/civicrm/bower_components/jquery-ui/.composer-downloads/jquery-ui-f4e47df9c6fa2e82f5987f78dc64c392.json b/civicrm/bower_components/jquery-ui/.composer-downloads/jquery-ui-f4e47df9c6fa2e82f5987f78dc64c392.json
index a0bb4e854bf8bac10ace426303ca633923be060a..337dca1c85ff82d198b2138e9c77b53da83fc457 100644
--- a/civicrm/bower_components/jquery-ui/.composer-downloads/jquery-ui-f4e47df9c6fa2e82f5987f78dc64c392.json
+++ b/civicrm/bower_components/jquery-ui/.composer-downloads/jquery-ui-f4e47df9c6fa2e82f5987f78dc64c392.json
@@ -1,4 +1,6 @@
 {
     "name": "civicrm/civicrm-core:jquery-ui",
-    "url": "https://github.com/components/jqueryui/archive/1.12.1.zip"
+    "url": "https://github.com/components/jqueryui/archive/1.12.1.zip",
+    "checksum": "2c957f462009a2b2827387be1fcf4634b62da428a7fd5c0d0e6a67b668000a90",
+    "ignore": null
 }
\ No newline at end of file
diff --git a/civicrm/bower_components/jquery-validation/.composer-downloads/jquery-validation-134dc18b66d427be700a9e1241688102.json b/civicrm/bower_components/jquery-validation/.composer-downloads/jquery-validation-134dc18b66d427be700a9e1241688102.json
index 57affa2efd25ace8693181ba6b1466a56b8b5321..97ada7c03558867cc86cbd1f8a42908dc8f0d015 100644
--- a/civicrm/bower_components/jquery-validation/.composer-downloads/jquery-validation-134dc18b66d427be700a9e1241688102.json
+++ b/civicrm/bower_components/jquery-validation/.composer-downloads/jquery-validation-134dc18b66d427be700a9e1241688102.json
@@ -1,4 +1,13 @@
 {
     "name": "civicrm/civicrm-core:jquery-validation",
-    "url": "https://github.com/jquery-validation/jquery-validation/archive/1.13.1.zip"
+    "url": "https://github.com/jquery-validation/jquery-validation/archive/1.13.1.zip",
+    "checksum": "674d447514392228eae53e2c56ae4ddb293c4276786adabc4242a843fc49a471",
+    "ignore": [
+        ".*",
+        "node_modules",
+        "bower_components",
+        "test",
+        "demo",
+        "lib"
+    ]
 }
\ No newline at end of file
diff --git a/civicrm/bower_components/jquery/.composer-downloads/jquery-d223e1439188e478349d52476506c22e.json b/civicrm/bower_components/jquery/.composer-downloads/jquery-d223e1439188e478349d52476506c22e.json
index 7a1a3609f711dad70f31733249ccb7ebe7a5c54c..7d3d738c4f6d7c062185d587f7d5870555cde102 100644
--- a/civicrm/bower_components/jquery/.composer-downloads/jquery-d223e1439188e478349d52476506c22e.json
+++ b/civicrm/bower_components/jquery/.composer-downloads/jquery-d223e1439188e478349d52476506c22e.json
@@ -1,4 +1,6 @@
 {
     "name": "civicrm/civicrm-core:jquery",
-    "url": "https://github.com/civicrm/jquery/archive/1.12.4-civicrm-1.2.zip"
+    "url": "https://github.com/civicrm/jquery/archive/1.12.4-civicrm-1.2.zip",
+    "checksum": "c93dbcf60dbcae6a36249a2e46f84e616b52579007abe35739c361f9cf3e9994",
+    "ignore": null
 }
\ No newline at end of file
diff --git a/civicrm/bower_components/js-yaml/.composer-downloads/js-yaml-8f40118e302f5c6e07340a961de7f161.json b/civicrm/bower_components/js-yaml/.composer-downloads/js-yaml-8f40118e302f5c6e07340a961de7f161.json
index 7b7f8ac789785f7d29b35aa6419379ce8d95cd09..7d497a7e8be30f80541867ff514541a862e33424 100644
--- a/civicrm/bower_components/js-yaml/.composer-downloads/js-yaml-8f40118e302f5c6e07340a961de7f161.json
+++ b/civicrm/bower_components/js-yaml/.composer-downloads/js-yaml-8f40118e302f5c6e07340a961de7f161.json
@@ -1,4 +1,14 @@
 {
     "name": "civicrm/civicrm-core:js-yaml",
-    "url": "https://github.com/nodeca/js-yaml/archive/3.13.1.zip"
+    "url": "https://github.com/nodeca/js-yaml/archive/3.13.1.zip",
+    "checksum": "76c61a4e5cb0ebcab218eea78f2a87f35d3b1683deecee6338fd746dbc82fef4",
+    "ignore": [
+        "benchmark",
+        "bin",
+        "demo",
+        "examples",
+        "lib",
+        "support",
+        "test"
+    ]
 }
\ No newline at end of file
diff --git a/civicrm/bower_components/jstree/.composer-downloads/jstree-50d46fdfc87493925fbba33deede1c4b.json b/civicrm/bower_components/jstree/.composer-downloads/jstree-50d46fdfc87493925fbba33deede1c4b.json
index fe930393c3d67a46d2e5cf952c1bffafc3ba4e33..84d4b583343c5b3ccb2057a31541adf32c62f8b9 100644
--- a/civicrm/bower_components/jstree/.composer-downloads/jstree-50d46fdfc87493925fbba33deede1c4b.json
+++ b/civicrm/bower_components/jstree/.composer-downloads/jstree-50d46fdfc87493925fbba33deede1c4b.json
@@ -1,4 +1,21 @@
 {
     "name": "civicrm/civicrm-core:jstree",
-    "url": "https://github.com/vakata/jstree/archive/3.3.8.zip"
+    "url": "https://github.com/vakata/jstree/archive/3.3.8.zip",
+    "checksum": "54ea10f0fb10ed8f97875c5dd916b767b0f26e7290a183098add5f496f18c29e",
+    "ignore": [
+        ".*",
+        "docs",
+        "demo",
+        "libs",
+        "node_modules",
+        "test",
+        "libs",
+        "jstree.jquery.json",
+        "gruntfile.js",
+        "package.json",
+        "bower.json",
+        "component.json",
+        "LICENCE-MIT",
+        "README.md"
+    ]
 }
\ No newline at end of file
diff --git a/civicrm/bower_components/lodash-compat/.composer-downloads/lodash-compat-bf9d53c8a06b2909c0053b89d9bcce3b.json b/civicrm/bower_components/lodash-compat/.composer-downloads/lodash-compat-bf9d53c8a06b2909c0053b89d9bcce3b.json
index 0fb35c76cff2811772789fcae9a04492b48202f2..959b0f8363c6834c3ebdeb4d190180780e885273 100644
--- a/civicrm/bower_components/lodash-compat/.composer-downloads/lodash-compat-bf9d53c8a06b2909c0053b89d9bcce3b.json
+++ b/civicrm/bower_components/lodash-compat/.composer-downloads/lodash-compat-bf9d53c8a06b2909c0053b89d9bcce3b.json
@@ -1,4 +1,13 @@
 {
     "name": "civicrm/civicrm-core:lodash-compat",
-    "url": "https://github.com/lodash/lodash-compat/archive/3.0.1.zip"
+    "url": "https://github.com/lodash/lodash-compat/archive/3.0.1.zip",
+    "checksum": "23bf4958a67f29b5c4a9864a5b52320817c7150f0eba6e169d5b5b3636d124cc",
+    "ignore": [
+        ".*",
+        "*.log",
+        "*.md",
+        "component.json",
+        "package.json",
+        "node_modules"
+    ]
 }
\ No newline at end of file
diff --git a/civicrm/bower_components/marked/.composer-downloads/marked-5bbf2d6725b29ad8ddb7c3ab47c50930.json b/civicrm/bower_components/marked/.composer-downloads/marked-5bbf2d6725b29ad8ddb7c3ab47c50930.json
index 890bab87408a5fafa052c9b7e0570cf0d3f92313..0ba14c9c1536966590237541d3a8ad3fcfc5aeb4 100644
--- a/civicrm/bower_components/marked/.composer-downloads/marked-5bbf2d6725b29ad8ddb7c3ab47c50930.json
+++ b/civicrm/bower_components/marked/.composer-downloads/marked-5bbf2d6725b29ad8ddb7c3ab47c50930.json
@@ -1,4 +1,12 @@
 {
     "name": "civicrm/civicrm-core:marked",
-    "url": "https://github.com/markedjs/marked/archive/v0.8.0.zip"
+    "url": "https://github.com/markedjs/marked/archive/v0.8.0.zip",
+    "checksum": "fa5270a192bf88c02e698f2b20f8b15bc556bd8c3ca2e77baefba5c5c7c91904",
+    "ignore": [
+        ".*",
+        "*.json",
+        "*.md",
+        "Makefile",
+        "*/*"
+    ]
 }
\ No newline at end of file
diff --git a/civicrm/bower_components/phantomjs-polyfill/.composer-downloads/phantomjs-polyfill-dce4e52b3d79fc404e0b05c8674afd11.json b/civicrm/bower_components/phantomjs-polyfill/.composer-downloads/phantomjs-polyfill-dce4e52b3d79fc404e0b05c8674afd11.json
index 1ec7a2f5f767dd0c73f7b5d2125d21225db883e7..d943cb157db88bb70685cc3dd7f6c2cac40c9f21 100644
--- a/civicrm/bower_components/phantomjs-polyfill/.composer-downloads/phantomjs-polyfill-dce4e52b3d79fc404e0b05c8674afd11.json
+++ b/civicrm/bower_components/phantomjs-polyfill/.composer-downloads/phantomjs-polyfill-dce4e52b3d79fc404e0b05c8674afd11.json
@@ -1,4 +1,6 @@
 {
     "name": "civicrm/civicrm-core:phantomjs-polyfill",
-    "url": "https://github.com/conversocial/phantomjs-polyfill/archive/v0.0.2.zip"
+    "url": "https://github.com/conversocial/phantomjs-polyfill/archive/v0.0.2.zip",
+    "checksum": "faa401d8f3b21b18a709a506d709202ad5795753d593e7a0d269082d6a7444a0",
+    "ignore": null
 }
\ No newline at end of file
diff --git a/civicrm/bower_components/qunit/.composer-downloads/qunit-4f8ae0790a302e5ed86ca7b079f3ab20.json b/civicrm/bower_components/qunit/.composer-downloads/qunit-4f8ae0790a302e5ed86ca7b079f3ab20.json
deleted file mode 100644
index 2438bdbaff9c6fbb373a0c6a3059a6bd4edb85d8..0000000000000000000000000000000000000000
--- a/civicrm/bower_components/qunit/.composer-downloads/qunit-4f8ae0790a302e5ed86ca7b079f3ab20.json
+++ /dev/null
@@ -1,4 +0,0 @@
-{
-    "name": "civicrm/civicrm-core:qunit",
-    "url": "https://github.com/jquery/qunit/archive/v1.10.0.zip"
-}
\ No newline at end of file
diff --git a/civicrm/bower_components/qunit/.gitignore b/civicrm/bower_components/qunit/.gitignore
deleted file mode 100644
index e41c37d57a1b19a30d6acaed9282af4520f26009..0000000000000000000000000000000000000000
--- a/civicrm/bower_components/qunit/.gitignore
+++ /dev/null
@@ -1,8 +0,0 @@
-.project
-*~
-*.diff
-*.patch
-.DS_Store
-.settings
-node_modules
-dist/
diff --git a/civicrm/bower_components/qunit/AUTHORS.txt b/civicrm/bower_components/qunit/AUTHORS.txt
deleted file mode 100644
index 2b56decbcb02ca69e55f0c0caef02ef826fd5c01..0000000000000000000000000000000000000000
--- a/civicrm/bower_components/qunit/AUTHORS.txt
+++ /dev/null
@@ -1,55 +0,0 @@
-Jörn Zaefferer <joern.zaefferer@gmail.com>
-Ariel Flesler <aflesler@gmail.com>
-Scott González <scott.gonzalez@gmail.com>
-Richard Worth <rdworth@gmail.com>
-Philippe Rathé <prathe@gmail.com>
-John Resig <jeresig@gmail.com>
-Will Moffat <will_git@hamstersoup.com>
-Jan Kassens <jan@kassens.net>
-Ziling Zhao <zizhao@cisco.com>
-Ryan Szulczewski <musicmanryan@gmail.com>
-Chris Lloyd <christopher.lloyd@gmail.com>
-Louis-Rémi Babé <public@lrbabe.com>
-Jake Archibald <jake.archibald@bbc.co.uk>
-Frances Berriman <frances.berriman@bbc.co.uk>
-Rune Halvorsen <runefh@gmail.com>
-Chris Thatcher <thatcher.christopher@gmail.com>
-Fábio Rehm <fgrehm@gmail.com>
-Leon Sorokin <leeoniya@gmail.com>
-Douglas Neiner <doug@pixelgraphics.us>
-Paul Elliott <paul@hashrocket.com>
-Nikita Vasilyev <me@elv1s.ru>
-Benjamin Lee <leebenjp@gmail.com>
-Paul Irish <paul.irish@gmail.com>
-Oleg Slobodskoi <oleg008@gmail.com>
-Anton Matzneller <obhvsbypqghgc@gmail.com>
-Aurélien Bombo
-Mathias Bynens <mathias@qiwi.be>
-Erik Vold <erikvvold@gmail.com>
-Wesley Walser <waw325@gmail.com>
-Rob Kinninmont <robk@twitter.com>
-Marc Portier <marc.portier@gmail.com>
-Michael Righi <michael@righi.me>
-Timo Tijhof <krinklemail@gmail.com>
-Jan Alonzo <jmalonzo@taguchimail.com>
-Daniel Trebbien <dtrebbien@gmail.com>
-Bob Fanger <bfanger@gmail.com>
-Markus Messner-Chaney <markus.messner-chaney@xing.com>
-Trevor Parscal <trevorparscal@gmail.com>
-Ashar Voultoiz <hashar@free.fr>
-Jimmy Mabey <jimmy@velsoft.com>
-Domenic Denicola <domenic@domenicdenicola.com>
-Mike Sherov <mike.sherov@gmail.com>
-Seong-A Kong <simonz@daumcorp.com>
-Graham Conzett <conzett@gmail.com>
-Niall Smart <niall@pobox.com>
-Johan Sörlin <spocke@moxiecode.com>
-Gijs Kruitbosch <gijskruitbosch@gmail.com>
-Erkan Yilmaz <erkan77@gmail.com>
-Jonathan Sanchez <jsanchezpando@cirb.irisnet.be>
-Keith Cirkel <github@keithcirkel.co.uk>
-Rick Waldron <waldron.rick@gmail.com>
-Herbert Vojčík <herby@mailbox.sk>
-Richard Gibson <richard.gibson@gmail.com>
-Alex J Burke <alex@alexjeffburke.com>
-Sergii Kliuchnyk <sergiikliuchnyk@gmail.com>
diff --git a/civicrm/bower_components/qunit/History.md b/civicrm/bower_components/qunit/History.md
deleted file mode 100644
index 94568f4c02736d5b8a18179f4894c6e06579ba38..0000000000000000000000000000000000000000
--- a/civicrm/bower_components/qunit/History.md
+++ /dev/null
@@ -1,462 +0,0 @@
-1.10.0 / 2012-08-30 
-==================
-
-  * Simplify licensing: Only MIT, no more MIT/GPL dual licensing.
-  * Scroll the window back to top after tests finished running. Fixes #304
-  * Simplify phantomjs runner to use module property in testDone callback
-  * Adds module and test name to the information that is returned in the callback provided to QUnit.log(Function). Fixes #296
-  * Make QUnit.expect() (without arguments) a getter. Fixes #226
-  * Compare the ES6 sticky (y) property for RegExp. Can't add to tests yet. Fixes #284 - deepEqual for RegExp should compare
-  * onerror: force display of global errors despite URL parameters. Fixes #288 - Global failures can be filtered out by test-limiting URL parameters
-  * Remove conditional codepath based on jQuery presence from reset().
-  * Add module filter to UI
-  * Keep a local reference to Date. Fixes #283.
-  * Update copyright to jQuery Foundation.
-
-1.9.0 / 2012-07-11
-==================
-  * added jsdoc for QUnit.assert functions
-  * Styling: radius to 5px and small pass/error border, remove inner shadow
-  * Move checkboxes into toolbar and give them labels and descriptions (as tooltip). Fixes #274 - Improve urlFilter API and UI
-  * Where we recieve no exception in throws() use a relevant message.
-  * Also make module filter case-insensitive. Follow-up to #252
-  * Banner: Link should ignore "testNumber" and "module". Fixes #270
-  * Rename assert.raises to assert.throws. Fixes #267
-  * Change package.json name property to 'qunitjs' to avoid conflicht with node-qunit; will publish next release to npm
-
-1.8.0 / 2012-06-14
-==================
-  * Improve window.onerror handling
-  * (issue #260) config.current should be reset at the right time.
-  * Filter: Implement 'module' url parameter. Fixes #252
-  * raises: ignore global exceptions stemming from test. Fixes #257 - Globally-executed errors sneak past raises in IE
-
-1.7.0 / 2012-06-07
-==================
-
-  * Add config.requireExpects. Fixes #207 - Add option to require all tests to call expect().
-  * Improve extractStacktrace() implementation. Fixes #254 - Include all relevant stack lines
-  * Make filters case-insensitive. Partial fix for #252
-  * is() expects lowercase types. Fixes #250 - Expected Date value is not displayed properly
-  * Fix phantomjs addon header and add readme. Fixes #239
-  * Add some hints to composite addon readme. Fixes #251
-  * Track tests by the order in which they were run and create rerun links based on that number. Fixes #241 - Make Rerun link run only a single test.
-  * Use QUnit.push for raises implementation. Fixes #243
-  * CLI runner for phantomjs
-  * Fix jshint validation until they deal with /** */ comments properly
-  * Update validTest() : Simplify logic, clarify vars and add comments
-  * Refactor assertion helpers into QUnit.assert (backwards compatible)
-  * Add Rerun link to placeholders. Fixes #240
-
-1.6.0 / 2012-05-04
-==================
-
-  * Save stack for each test, use that for failed expect() results, points at the line where test() was called. Fixes #209
-  * Prefix test-output id and ignore that in noglobals check. Fixes #212
-  * Only check for an exports object to detect a CommonJS enviroment. Fixes #237 - Incompatibility with require.js
-  * Add testswarm integration as grunt task
-  * Added padding on URL config checkboxes.
-  * Cleanup composite addon: Use callback registration instead of overwriting them. Set the correct src on rerun link (and dblclick). Remove the composite test itself, as that was a crazy hack not worth maintaining
-  * Cleanup reset() test and usage - run testDone callback first, to allow listeneres ignoring reset assertions
-  * Double clicking on composite test rows opens individual test page
-  * test-message for all message-bearing API reporting details
-
-1.5.0 / 2012-04-04
-==================
-
-  * Modify "Running..." to display test name. Fixes #220
-  * Fixed clearing of sessionStorage in Firefox 3.6.
-  * Fixes #217 by calling "block" with config.current.testEnvironment
-  * Add stats results to data. QUnit.jUnitReport function take one argument {   xml:'<?xml ...',   results:{failed:0, passed:0, total:0, time:0} }
-  * Add link to MDN about stack property
-
-1.4.0 / 2012-03-10
-==================
-
-  * Prefix test-related session-storage items to make removal more specific. Fixes #213 - Keep hide-passed state when clearing session storage
-  * Update grunt.js with seperate configs for qunit.js and grunt.js, also add tests but disable for now, not passing yet. Add grunt to devDependencies
-  * typo
-  * Cleanup grunt.js, no need for the banner
-  * Fix lint errors and some formatting issues. Use QUnit.pushFailure for noglobals and global error handler.
-  * Fix a missing expect in logs test
-  * Add grunt.js configuration and include some usage instructions in the readme
-  * Update package.json
-  * Partially revert af27eae841c3e1c01c46de72d676f1047e1ee375 - can't move reset around, so also don't wrap in try-catch, as the result of that is effectively swallowed. Can't output the result as the outputting is already done.
-  * Add QUnit.pushFailure to log error conditions like exceptions. Accepts stacktrace as second argument, allowing extraction with catched exceptions (useful even in Safari). Remove old fail() function that would just log to console, not useful anymore as regular test output is much more useful by now. Move up QUnit.reset() call to just make that another failed assertion. Used to not make a test fail. Fixes #210
-  * Update equals and same deprecations to use QUnit.push to provide correct source lines. Fixes #211
-  * Add a test file for narwhal integration. Has to use print instead of console.log. Fails when an assertion fails, something about setInterval...
-  * Apply notrycatch option to setup and teardown as well. Fixes #203. Reorder noglobals check to allow teardown to remove globals that were introduced intentionally. Fixes #204
-  * Extend exports object with QUnit properties at the end of the file to export everything.
-  * Output source line for ok() assertions. Fixes #202
-  * Make test fail if no assertions run. Fixes #178
-  * Sort object output alphabetically in order to improve diffs of objects where properties were set in a different order. Fixes #206
-  * Revert "Change fixture reset behavior", changing #194 and #195 to wontfix.
-
-1.3.0 / 2012-02-26
-==================
-
-  * Cleanup test markup
-  * Fix the jQuery branch of fixture reset. Would break when no fixture exists.
-  * Added initial version of a junitlogger addon.
-  * Escape document.title before inserting into markup. Extends fix for #127
-  * Catch assertions running outside of test() context, make sure source is provided even for ok(). Fixes #98
-  * Improve global object access, based on comments for 1a9120651d5464773256d8a1f2cf2eabe38ea5b3
-  * Clear all sessionStorage entries once all tests passed. Helps getting rid of items from renamed tests. Fixes #101
-  * Set fixed dimensions for #qunit-fixture. Fixes #114
-  * Extend nodejs test runner to check for stacktrace output, twice
-  * Extend nodejs test runner to check for stacktrace output
-  * Generate more base markup, but allow the user to exclude that completelty or choose their own. Fixes #127
-  * Add a simple test file to check basic nodejs integration works
-  * Check for global object to find setTimeout in node
-  * Fix CommonJS export by assigning QUnit to module.exports.
-  * Remove the testEnviromentArg to test(). Most obscure, never used anywhere. test() is still heavily overloaded with argument shifting, this makes it a little more sane. Fixes #172
-  * Serialize expected and actual values only when test fails. Speeds up output of valid tests, especially for lots of large objects. Fixes #183
-  * Fix sourceFromsTacktrace to get the right line in Firefox. Shift the 'error' line away in Chrome to get a match.
-  * Fix references to test/deepEqual.js
-  * In autorun mode, moduleDone is called without matching moduleStart. Fix issue #184
-  * Fixture test: allow anything falsy in test as getAttribute in oldIE will return empty string instead of null. We don't really care.
-  * Keep label and checkbox together ( http://i.imgur.com/5Wk3A.png )
-  * Add readme for themes
-  * Fix bad global in reset()
-  * Some cleanup in theme addons
-  * Update headers
-  * Update nv.html, add gabe theme based on https://github.com/jquery/qunit/pull/188
-  * Experiemental custom theme based on https://github.com/jquery/qunit/pull/62 by NV
-  * Replace deprecated same and equals aliases with placeholders that just throw errors, providing a hint at what to use instead. Rename test file to match that.
-  * Can't rely on outerHTML for Firefox < 11. Use cloneNode instead.
-  * Merge remote branch 'conzett/master'
-  * Cleanup whitespace
-  * Update sessionStorage support test to latest version from Modernizr, trying to setItem to avoid QUOTA_EXCEEDED_EXCEPTION
-  * Change fixture reset behavior
-  * Merge pull request #181 from simonz/development
-  * Escaping test names
-  * Show exception stack when test failed
-
-1.2.0 / 2011-11-24
-==================
-
-  * remove uses of equals(), as it's deprecated in favor of equal()
-  * Code review of "Allow objects with no prototype to be tested against object literals."
-  * Allow objects with no prototype to tested against object literals.
-  * Fix IE8 "Member not found" error
-  * Using node-qunit port, the start/stop function are not exposed so we need to prefix any call to them with 'QUnit'. Aka: start() -> QUnit.start()
-  * Remove the 'let teardown clean up globals test' - IE<9 doesn't support (==buggy) deleting window properties, and that's not worth the trouble, as everything else passes just fine. Fixes #155
-  * Fix globals in test.js, part 2
-  * Fix globals in test.js. ?tell wwalser to use ?noglobals everyonce in a while
-  * Extend readme regarding release process
-
-1.1.0 / 2011-10-11
-==================
-
-  * Fixes #134 - Add a window.onerror handler. Makes uncaught errors actually fail the testsuite, instead of going by unnoticed.
-  * Whitespace cleanup
-  * Merge remote branch 'trevorparscal/master'
-  * Fixed IE compatibility issues with using toString on NodeList objects, which in some browsers results in [object Object] rather than [object NodeList]. Now using duck typing for NodeList objects based on the presence of length, length being a number, presence of item method (which will be typeof string in IE and function in others, so we just check that it's not undefined) and that item(0) returns the same value as [0], unless it's empty, in which case item(0) will return 0, while [0] would return undefined. Tested in IE6, IE8, Firefox 6, Safari 5 and Chrome 16.
-  * Update readme with basic notes on releases
-  * More whitespace/parens cleanup
-  * Check if setTimeout is available before trying to delay running the next task. Fixes #160
-  * Whitespace/formatting fix, remove unnecessary parens
-  * Use alias for Object.prototype.toString
-  * Merge remote branch 'trevorparscal/master'
-  * Merge remote branch 'wwalser/recursionBug'
-  * Default 'expected' to null in asyncTest(), same as in test() itself.
-  * Whitespace cleanup
-  * Merge remote branch 'mmchaney/master'
-  * Merge remote branch 'Krinkle/master'
-  * Using === instead of ==
-  * Added more strict array type detection for dump output, and allowed NodeList objects to be output as arrays
-  * Fixes a bug where after an async test, assertions could move between test cases because of internal state (config.current) being incorrectly set
-  * Simplified check for assertion count and adjusted whitespace
-  * Redo of fixing issue #156 (Support Object.prototype extending environment). * QUnit.diff: Throws exception without this if Object.prototype is set (Property 'length' of undefined. Since Object.prototype.foo doesn't have a property 'rows') * QUnit.url: Without this fix, if Object.prototype.foo is set, the url will be set to ?foo=...&the=rest. * saveGlobals: Without this fix, whenever a member is added to Object.prototype, saveGlobals will think it was a global variable in this loop. --- This time using the call method instead of obj.hasOwnProperty(key), which may fail if the object has that as it's own property (touché!).
-  * Handle expect(0) as expected, i.e. expect(0); ok(true, foo); will cause a test to fail
-
-1.0.0 / 2011-10-06
-==================
-
-  * Make QUnit work with TestSwarm
-  * Run other addons tests as composite addon demo. Need to move that to /test folder once this setup actually works
-  * Add-on: New assertion-type: step()
-  * added parameter to start and stop allowing a user to increment/decrement the semaphore more than once per call
-  * Update readmes with .md extension for GitHub to render them as markdown
-  * Update close-enough addon to include readme and match (new) naming convetions
-  * Merge remote branch 'righi/close-enough-addon'
-  * Canvas addon: Update file referneces
-  * Update canvas addon: Rename files and add README
-  * Merge remote branch 'wwalser/composite'
-  * Fix #142 - Backslash characters in messages should not be escaped
-  * Add module name to testStart and testDone callbacks
-  * Removed extra columns in object literals. Closes #153
-  * Remove dead links in comments.
-  * Merge remote branch 'wwalser/multipleCallbacks'
-  * Fixed syntax error and CommonJS incompatibilities in package.json
-  * Allow multiple callbacks to be registered.
-  * Add placeholder for when Safari may end up providing useful error handling
-  * changed file names to match addon naming convention
-  * Whitespace
-  * Created the composite addon.
-  * Using array and object literals.
-  * Issue #140: Make toggle system configurable.
-  * Merge remote branch 'tweetdeck/master'
-  * Adds the 'close enough' addon to determine if numbers are acceptably close enough in value.
-  * Fix recursion support in jsDump, along with tests. Fixes #63 and #100
-  * Adding a QUnit.config.altertitle flag which will allow users to opt-out of the functionality introduced in 60147ca0164e3d810b8a9bf46981c3d9cc569efc
-  * Refactor window.load handler into QUnit.load, makes it possible to call it manually.
-  * More whitespace cleanup
-  * Merge remote branch 'erikvold/one-chk-in-title'
-  * Whitespace
-  * Merge remote branch 'wwalser/syncStopCalls'
-  * Introducing the first QUnit addon, based on https://github.com/jquery/qunit/pull/84 - adds QUnit.pixelEqual assertion method, along with example tests.
-  * Remove config.hidepassed setting in test.js, wasn't intended to land in master.
-  * Expose QUnit.config.hidepassed setting. Overrides sessionStorage and enables enabling the feature programmatically. Fixes #133
-  * Fix formatting (css whitespace) for tracebacks.
-  * Expose extend, id, and addEvent methods.
-  * minor comment typo correction
-  * Ignore Eclipse WTP .settings
-  * Set 'The jQuery Project' as author in package.json
-  * Fixes a bug where synchronous calls to stop would cause tests to end before start was called again
-  * Point to planning testing wiki in readme
-  * only add one checkmark to the document.title
-  * Escape the stacktrace output before setting it as innerHTML, since it tends to contain `<` and `>` characters.
-  * Cleanup whitespace
-  * Run module.teardown before checking for pollution. Fixes #109 - noglobals should run after module teardown
-  * Fix accidental global variable "not"
-  * Update document.title status to use more robust unicode escape sequences, works even when served with non-utf-8-charset.
-  * Modify document.title when suite is done to show success/failure in tab, allows you to see the overall result without seeing the tab content.
-  * Merge pull request #107 from sexyprout/master
-  * Set a generic font
-  * Add/update headers
-  * Drop support for deprecated #main in favor of #qunit-fixture. If this breaks your testsuite, replace id="main" with id="qunit-fixture". Fixes #103
-  * Remove the same key as the one being set. Partial fix for #101
-  * Don't modify expected-count when checking pollution. The failing assertion isn't expected, so shouldn't be counted. And if expect wasn't used, the count is misleading.
-  * Fix order of noglobals check to produce correct introduced/delete error messages
-  * Prepend module name to sessionStorage keys to avoid conflicts
-  * Store filter-tests only when checked
-  * Write to sessionStorage only bad tests
-  * Moved QUnit.url() defintion after QUnit properties are merged into the global scope. Fixes #93 - QUnit url/extend function breaking urls in jQuery ajax test component
-  * Add a "Rerun" link to each test to replce the dblclick (still supported, for now).
-  * Fixed the regex for parsing the name of a test when double clicking to filter.
-  * Merge remote branch 'scottgonzalez/url'
-  * Added checkboxes to show which flags are currently on and allow toggling them.
-  * Retain all querystring parameters when filtering a test via double click.
-  * Added better querystring parsing. Now storing all querystring params in QUnit.urlParams so that we can carry the params forward when filtering to a specific test. This removes the ability to specify multiple filters.
-  * Make reordering optional (QUnit.config.reorder = false) and optimize "Hide passed tests" mode by also hiding "Running [testname]" entries.
-  * Added missing semicolons and wrapped undefined key in quotes.
-  * Optimize test hiding, add class on page load if stored in sessionStorage
-  * Optimize the hiding of passed tests.
-  * Position test results above test list, making it visible without ever having to scroll. Create a placeholder to avoid pushing down results later.
-  * Don't check for existing qunit-testresult element, it gets killed on init anyway.
-  * Added URL flag ?notrycatch (ala ?noglobals) for debugging exceptions. Won't try/catch test code, giving better debugging changes on the original exceptions. Fixes #72
-  * Always show quni-toolbar (if at all specified), persist checkbox via sessionStorage. Fixes #47
-  * Use non-html testname for calls to fail(). Fixes #77
-  * Overhaul of QUnit.callbacks. Consistent single argument with related properties, with additonal runtime property for QUnit.done
-  * Extended test/logs.html to capture more of the callbacks.
-  * Fixed moduleStart/Done callbacks. Added test/logs.html to test these callbacks. To be extended.
-  * Update copyright and license header. Fixes #61
-  * Formatting fix.
-  * Use a semaphore to synchronize stop() and start() calls. Fixes #76
-  * Merge branch 'master' of https://github.com/paulirish/qunit into paulirish-master
-  * Added two tests for previous QUnit.raises behaviour. For #69
-  * add optional 2. arg to QUnit.raises #69.
-  * fix references inside Complex Instances Nesting to what was originally intended.
-  * Qualify calls to ok() in raises() for compability with CLI enviroments.
-  * Fix done() handling, check for blocking, not block property
-  * Fix moduleStart/Done and done callbacks.
-  * Replacing sessionStorage test with the one from Modernizr/master (instead of current release). Here's hoping it'll work for some time.
-  * Updated test for availibility of sessionStorage, based on test from Modernizr. Fixes #64
-  * Defer test execution when previous run passed, persisted via sessionStorage. Fixes #49
-  * Refactored module handling and queuing to enable selective defer of test runs.
-  * Move assertions property from config to Test
-  * Move expected-tests property from config to Test
-  * Refactored test() method to delegate to a Test object to encapsulate all properties and methods of a single test, allowing further modifications.
-  * Adding output of sourcefile and linenumber of failed assertions (except ok()). Only limited cross-browser support for now. Fixes #60
-  * Drop 'hide missing tests' feature. Fixes #48
-  * Adding readme. Fixes #58
-  * Merge branch 'prettydiff'
-  * Improve jsDump output with formatted diffs.
-  * Cleanup whitespace
-  * Cleanup whitespace
-  * Added additional guards around browser specific code and cleaned up jsDump code
-  * Added guards around tests which are only for browsers
-  * cleaned up setTimeout undefined checking and double done on test finish
-  * fixing .gitignore
-  * making window setTimeout query more consistent
-  * Moved expect-code back to beginning of function, where it belongs. Fixes #52
-  * Bread crumb in header: Link to suite without filters, add link to current page based on the filter, if present. Fixes #50
-  * Make the toolbar element optional when checking for show/hide of test results. Fixes #46
-  * Adding headless.html to manually test logging and verify that QUnit works without output elements. Keeping #qunit-fixture as a few tests actually use that.
-  * Fix for QUnit.moduleDone, get rid of initial bogus log. Fixes #33
-  * Pass raw data (result, message, actual, expected) as third argument to QUnit.log. Fixes #32
-  * Dump full exception. Not pretty, but functional (see issue Pretty diff for pretty output). Fixes #31
-  * Don't let QUnit.reset() cause assertions to run. Manually applied from Scott Gonzalez branch. Fixes #34
-  * Added missing semicolons. Fixes #37
-  * Show okay/failed instead of undefined. Fixes #38
-  * Expose push as QUnit.push to build custom assertions. Fixes #39
-  * Respect filter pass selection when writing new results. Fixes #43
-  * Cleanup tests, removing asyncTest-undefined check and formatting
-  * Reset: Fall back to innerHTML when jQuery isn't available. Fixes #44
-  * Merge branch 'master' of github.com:jquery/qunit
-  * reset doesn't exist here - fixes #28.
-  * - less css cruft, better readability - replaced inline style for test counts with "counts" class - test counts now use a "failed"/"passed" vs "pass"/"fail", shorter/more distinct selectors - pulled all test counts styling together and up (they're always the same regardless of section pass/fail state)
-  * Adding .gitignore file
-  * Removing diff test - diffing works fine, as the browser collapses whitespace in its output, but the test can't do that and isn't worth fixing.
-  * Always synchronize the done-step (it'll set the timeout when necessary), fixes timing race conditions.
-  * Insert location.href as an anchor around the header. Fixes issue #29
-  * - kill double ;; in escapeHtml. oops
-  * Removed html escaping from QUnit.diff, as input is already escaped, only leads to double escaping. Replaced newlines with single whitespace.
-  * Optimized and cleaned up CSS file
-  * Making the reset-method non-global (only module, test and assertions should be global), and fixing the fixture reset by using jQuery's html() method again, doesn't work with innerHTML, yet
-  * Introducing #qunit-fixture element, deprecating the (never documented) #main element. Doesn't require inline styles and is now independent of jQuery.
-  * Ammending previous commit: Remove jQuery-core specific resets (will be replaced within jQuery testsuite). Fixes issue #19 - QUnit.reset() removes global jQuery ajax event handlers
-  * Remove jQuery-core specific resets (will be replaced within jQuery testsuite). Fixes issue #19 - QUnit.reset() removes global jQuery ajax event handlers
-  * Cleaning up rubble from the previous commit.
-  * Added raises assertion, reusing some of kennsnyder's code.
-  * Merged kensnyder's object detection code. Original message: Streamlined object detection and exposed QUnit.objectType as a function.
-  * Fixed some bad formatting.
-  * Move various QUnit properties below the globals-export to avoid init becoming a global method. Fixes issue #11 - Remove 'init' function from a global namespace
-  * Improved output when expected != actual: Output both only then, and add a diff. Fixes issue #10 - Show diff if equal() or deepEqual() failed
-  * Expand failed tests on load. Fixes issue #8 - Failed tests expanded on load
-  * Set location.search for url-filtering instead of location.href. Fixes issue #7 - Modify location.search instead of location.href on test double-click
-  * Add QUnit.begin() callback. Fixes issue #6 - Add 'start' callback.
-  * add css style for result (".test-actual") in passed tests
-  * Fixed output escaping by using leeoniya's custom escaping along with innerHTML. Also paves the way for outputting diffs.
-  * Cleanup
-  * Revert "Revert part of bad merge, back to using createTextNode"
-  * Revert part of bad merge, back to using createTextNode
-  * Fixed doubleclick-handler and filtering to rerun only a single test.
-  * Add ability to css style a test's messages, expected and actual results. Merged from Leon Sorokin (leeoniya).
-  * Remove space between module name and colon
-  * - removed "module" wording from reports (unneeded and cluttery) - added and modified css to make module & test names styleable
-  * Logging support for  Each test can extend the module testEnvironment
-  * Fixing whitespace
-  * Update tests to use equal() and deepEqual() rather than the deprecated equals() and same()
-  * Consistent argument names for deepEqual
-  * Skip DOM part of jsDump test if using a SSJS environment without a DOM
-  * Improve async testing by creating the result element before running the test, updating it later. If the test fails, its clear which test is the culprit.
-  * Add autostart option to config. Set via QUnit.config.autostart = false; start later via QUnit.start()
-  * Expose QUnit.config, but don't make config a global
-  * Expose QUnit.config as global to make external workarounds easier
-  * Merge branch 'asyncsetup'
-  * Allowing async setup and teardown. Fixes http://github.com/jquery/qunit/issues#issue/20
-  * Always output expected and actual result (no reason not to). Fixes http://github.com/jquery/qunit/issues#issue/21
-  * More changes to the detection of types in jsDump's typeOf.
-  * Change the typeOf checks in QUnit to be more accurate.
-  * Added test for jsDump and modified its options to properly output results when document.createTextNode is used; currently tests for DOM elements cause a stackoverflow error in IEs, works fine, with the correct output, elsewhere
-  * Always use jsDump to output result objects into messages, making the output for passing assertions more useful
-  * Make it so that the display is updated, at least, once a second - also prevents scripts from executing for too long and causing problems.
-  * added tests and patch for qunit.equiv to avoid circular references in objects and arrays
-  * No reason to continue looping, we can stop at this point. Thanks to Chris Thatcher for the suggestion.
-  * Use createTextNode instead of innerHTML for showing test result since expected and actual might be something that looks like a tag.
-  * 'Test card' design added
-  * switched green to blue for top-level pass + reduced padding
-  * Bringing the QUnit API in line with the CommonJS API.
-  * Explicitly set list-style-position: inside on result LIs.
-  * Madness with border-radius.
-  * Corrected banner styles for new class names
-  * Added rounded corners and removed body rules for embedded tests
-  * Resolving merge conflicts.
-  * added colouring for value summary
-  * adding some extra text colours
-  * added styles for toolbar
-  * added new styles
-  * IE 6 and 7 weren't respecting the CSS rules for the banner, used a different technique instead.
-  * Went a bit further and made extra-sure that the target was specified correctly.
-  * Fixed problem where double-clicking an entry in IE caused an error to occur.
-  * Path for http://dev.jquery.com/ticket/5426 - fix the microformat test result
-  * Fixed test() to use 'expected' 2nd param
-  * Remove the named function expressions, to stop Safari 2 from freaking out. Fixes #5.
-  * Each test can extend the module testEnvironment
-  * Extra test for current test environment
-  * Make the current testEnvironment available to utility functions
-  * typeOf in QUnit.jsDump now uses QUnit.is
-  * hoozit in QUnit.equiv now uses QUnit.is
-  * Properly set label attributes.
-  * Some minor tweaks to RyanS' GETParams change.
-  * left a console.log in :(
-  * Took into account a fringe case when using qunit with testswarm. Trying to run all the tests with the extra url params from testswarm would make qunit look for a testsuite that did not exist
-  * need to set config.currentModule to have correct names and working filters
-  * Support logging of testEnvironment
-  * async tests aren't possible on rhino
-  * Fixed a missing QUnit.reset().
-  * The QUnit. prefix was missing from the uses of the start() method.
-  * Merged lifecycle object into testEnvironment
-  * "replacing totally wrong diff algorithm with a working one" Patch from kassens (manually applied).
-  * fixing jslint errors in test.js
-  * Fixed: testDone() was always called with 0 failures in CommonJS mode
-  * Fixed: moduleDone() was invoked on first call to module()
-  * Added a new asyncTest method - removes the need for having to call start() at the beginning of an asynchronous test.
-  * Added support for expected numbers in the test method.
-  * Fixed broken dynamic loading of tests (can now dynamically load tests and done still works properly).
-  * Simplified the logic for calling 'done' and pushing off new tests - was causing too many inconsistencies otherwise.
-  * Simplified the markup for the QUnit test test suite.
-  * Realized that it's really easy to handle the case where stop() has been called and then an exception is thrown.
-  * Added in better logging support. Now handle moduleStart/moduleDone and testStart/testDone. Also make sure that done only fires once at the end.
-  * Made it so that you can reset the suite to an initial state (at which point tests can be dynamically loaded and run, for example).
-  * Re-worked QUnit to handle dynamic loading of additional code (the 'done' code will be re-run after additional code is loaded).
-  * Removed the old SVN version stuff.
-  * Moved the QUnit source into a separate directory and updated the test suite/packages files.
-  * Added in CommonJS support for exporting the QUnit functionality.
-  * Missing quote from package.json.
-  * Fixed trailing comma in package.json.
-  * Added a CommonJS/Narwhal package.json file.
-  * Accidentally reverted the jsDump/equiv changes that had been made.
-  * Hide the filter toolbar if it's not needed. Also exposed the jsDump and equiv objects on QUnit.
-  * Retooled the QUnit CSS to be more generic.
-  * Renamed the QUnit files from testrunner/testsuite to QUnit.
-  * Expose QUnit.equiv and QUnit.jsDump in QUnit.
-  * Moved the QUnit test directory into the QUnit directory.
-  * Reworked the QUnit CSS (moved jQuery-specific stuff out, made all the other selectors more specific).
-  * Removed the #main reset for non-jQuery code (QUnit.reset can be overwritten with your own reset code).
-  * Moved the QUnit toolbar inline.
-  * Switched to using a qunit- prefix for special elements (banner, userAgent, and tests).
-  * Missed a case in QUnit where an element was assumed to exist.
-  * QUnit's isSet and isObj are no longer needed - you should use same instead.
-  * Make sure that QUnit's equiv entity escaping is enabled by default (otherwise the output gets kind of crazy).
-  * Refactored QUnit, completely reorganized the structure of the file. Additionally made it so that QUnit can run outside of a browser (inside Rhino, for example).
-  * Removed some legacy and jQuery-specific test methods.
-  * Added callbacks for tests and modules. It's now possible to reproduce the full display of the testrunner without using the regular rendering.
-  * QUnit no longer depends upon rendering the results (it can work simply by using the logging callbacks).
-  * Made QUnit no longer require jQuery (it is now a standalone, framework independent, test runner).
-  * Reverted the noglobals changed from QUnit - causing chaos in the jQuery test suite.
-  * qunit: removed noglobals flag, instead always check for globals after teardown; if a test has to introduce a global "myVar", use delete window.myVar in teardown or at the end of a test
-  * qunit: don't child selectors when IE should behave nicely, too
-  * qunit: improvment for the test-scope: create a new object and call setup, the test, and teardown in the scope of that object - allows you to provide test fixtures to each test without messing with global data; kudos to Martin Häcker for the contribution
-  * qunit: added missing semicolons
-  * qunit: fixed a semicolon, that should have been a comma
-  * QUnit: implemented error handling for Opera as proposed by #3628
-  * qunit: fix for http://dev.jquery.com/ticket/3215 changing wording of testresults, to something more positive (x of y passed, z failed)
-  * QUnit: testrunner.js: Ensures equality of types (String, Boolean, Number) declared with the 'new' prefix. See comments #3, #4 and #5 on http://philrathe.com/articles/equiv
-  * qunit: wrap name of test in span when a module is used for better styling
-  * qunit: auto-prepend default mark (#header, #banner, #userAgent, #tests) when not present
-  * Landing some changes to add logging to QUnit (so that it's easier to hook in to when a test finishes).
-  * Added checkbox for hiding missing tests (tests that fail with the text 'missing test - untested code is broken code')
-  * qunit: eol-style:native and mime-type
-  * HTML being injected for the test result wasn't valid HTML.
-  * qunit: setting mimetype for testsuite.css
-  * qunit: update to Ariel's noglobals patch to support async tests as well
-  * Landing Ariel's change - checks for global variable leakage.
-  * qunit: run module-teardown in its own synchronize block to synchronize with async tests (ugh)
-  * qunit: same: equiv - completely refactored in the testrunner.
-  * testrunner.js:     - Update equiv to support Date and RegExp.     - Change behavior when comparing function:         - abort when in an instance of Object (when references comparison failed)         - skip otherwise (like before)
-  * qunit: code refactoring and cleanup
-  * QUnit: update equiv to latest version, handling multiple arguments and NaN, see http://philrathe.com/articles/equiv
-  * QUnit: cleanup, deprecating compare, compare2 and serialArray: usage now throws an error with a helpful message
-  * QUnit: optional timeout argument for stop, while making tests undetermined, useful for debugging
-  * QUnit: added toolbar with "hide passed tests" checkbox to help focus on failed tests
-  * QUnit: minor output formatting
-  * QUnit: adding same-assertion for a recursive comparsion of primite values, arrays  and objects, thanks to Philippe Rathé for the contribution, including tests
-  * QUnit: adding same-assertion for a recursive comparsion of primite values, arrays  and objects, thanks to Philippe Rathé for the contribution, including tests
-  * QUnit: adding same-assertion for a recursive comparsion of primite values, arrays  and objects, thanks to Philippe Rathé for the contribution, including tests
-  * qunit: use window.load to initialize tests, allowing other code to run on document-ready before starting to run tests
-  * qunit: allow either setup or teardown, instead of both or nothing
-  * qunit: make everything private by default, expose only public API; removed old timeout-option (non-deterministic, disabled for a long time anyway); use local $ reference instead of global jQuery reference; minor code cleanup (var config instead of _config; queue.shift instead of slice)
-  * qunit: added support for module level setup/teardown callbacks
-  * qunit: modified example for equals to avoid confusion with parameter ordering
-  * qunit: added id/classes to result element to enable integration with browser automation tools, see http://docs.jquery.com/QUnit#Integration_into_Browser_Automation_Tools
-  * qunit: replaced $ alias with jQuery (merged from jquery/test/data/testrunner.js)
-  * qunit: fixed inline documentation for equals
-  * qunit testrunner - catch and log possible error during reset()
-  * QUnit: Switched out Date and Rev for Id.
-  * qunit: when errors are thrown in a test, the message is successfully show on all browsers.
-  * qunit: added license header
-  * qunit: moved jquery testrunner to top-level project, see http://docs.jquery.com/QUnit
-  * Share project 'qunit' into 'https://jqueryjs.googlecode.com/svn'
diff --git a/civicrm/bower_components/qunit/README.md b/civicrm/bower_components/qunit/README.md
deleted file mode 100644
index 57ff29e1f996d65ce1776bd068ca0a172ec79ef8..0000000000000000000000000000000000000000
--- a/civicrm/bower_components/qunit/README.md
+++ /dev/null
@@ -1,59 +0,0 @@
-[QUnit](http://qunitjs.com) - A JavaScript Unit Testing framework.
-================================
-
-QUnit is a powerful, easy-to-use, JavaScript test suite. It's used by the jQuery
-project to test its code and plugins but is capable of testing any generic
-JavaScript code (and even capable of testing JavaScript code on the server-side).
-
-QUnit is especially useful for regression testing: Whenever a bug is reported,
-write a test that asserts the existence of that particular bug. Then fix it and
-commit both. Every time you work on the code again, run the tests. If the bug
-comes up again - a regression - you'll spot it immediately and know how to fix
-it, because you know what code you just changed.
-
-Having good unit test coverage makes safe refactoring easy and cheap. You can
-run the tests after each small refactoring step and always know what change
-broke something.
-
-QUnit is similar to other unit testing frameworks like JUnit, but makes use of
-the features JavaScript provides and helps with testing code in the browser, e.g.
-with its stop/start facilities for testing asynchronous code.
-
-If you are interested in helping developing QUnit, you are in the right place.
-For related discussions, visit the
-[QUnit and Testing forum](http://forum.jquery.com/qunit-and-testing).
-
-Planning for a qunitjs.com site and other testing tools related work now happens
-on the [jQuery Testing Team planning wiki](http://jquerytesting.pbworks.com/w/page/41556026/FrontPage).
-
-Development
------------
-
-To submit patches, fork the repository, create a branch for the change. Then implement
-the change, run `grunt` to lint and test it, then commit, push and create a pull request.
-
-Include some background for the change in the commit message and `Fixes #nnn`, referring
-to the issue number you're addressing.
-
-To run `grunt`, you need `node` and `npm`, then `npm install grunt -g`. That gives you a global
-grunt binary. For additional grunt tasks, also run `npm install`.
-
-Releases
---------
-
-Install git-extras and run `git changelog` to update History.md.
-Update qunit/qunit.js|css and package.json to the release version, commit and
-tag, update them again to the next version, commit and push commits and tags
-(`git push --tags origin master`).
-
-Put the 'v' in front of the tag, e.g. `v1.8.0`. Clean up the changelog, removing merge commits
-or whitespace cleanups.
-
-To upload to code.jquery.com (replace $version accordingly):
-
-	scp -q qunit/qunit.js jqadmin@code.origin.jquery.com:/var/www/html/code.jquery.com/qunit/qunit-$version.js
-	scp -q qunit/qunit.css jqadmin@code.origin.jquery.com:/var/www/html/code.jquery.com/qunit/qunit-$version.css
-
-Then update /var/www/html/code.jquery.com/index.html and purge it with:
-
-	curl -s http://code.origin.jquery.com/?reload
\ No newline at end of file
diff --git a/civicrm/bower_components/qunit/addons/canvas/README.md b/civicrm/bower_components/qunit/addons/canvas/README.md
deleted file mode 100644
index 7c0f3663dda2c775ee9937ffc950e2de12181012..0000000000000000000000000000000000000000
--- a/civicrm/bower_components/qunit/addons/canvas/README.md
+++ /dev/null
@@ -1,16 +0,0 @@
-Canvas - A QUnit Addon For Testing Canvas Rendering
-================================
-
-This addon for QUnit adds a pixelEqual method that allows you to assert
-individual pixel values in a given canvas.
-
-Usage:
-
-    pixelEqual(canvas, x, y, r, g, b, a, message)
-
-Where:
-
-  * canvas: Reference to a canvas element
-  * x, y: Coordinates of the pixel to test
-  * r, g, b, a: The color and opacity value of the pixel that you except
-  * message: Optional message, same as for other assertions
diff --git a/civicrm/bower_components/qunit/addons/canvas/canvas-test.js b/civicrm/bower_components/qunit/addons/canvas/canvas-test.js
deleted file mode 100644
index 72ad66f44e04ee0ce3c37674ef3d8b7ab4a9415a..0000000000000000000000000000000000000000
--- a/civicrm/bower_components/qunit/addons/canvas/canvas-test.js
+++ /dev/null
@@ -1,76 +0,0 @@
-test("Canvas pixels", function () {
-	var canvas = document.getElementById('qunit-canvas'), context;
-	try {
-		context = canvas.getContext('2d');
-	} catch(e) {
-		// propably no canvas support, just exit
-		return;
-	}
-	context.fillStyle = 'rgba(0, 0, 0, 0)';
-	context.fillRect(0, 0, 5, 5);
-	QUnit.pixelEqual(canvas, 0, 0, 0, 0, 0, 0);
-	context.clearRect(0,0,5,5);
-	context.fillStyle = 'rgba(255, 0, 0, 0)';
-	context.fillRect(0, 0, 5, 5);
-	QUnit.pixelEqual(canvas, 0, 0, 0, 0, 0, 0);
-	context.clearRect(0,0,5,5);
-	context.fillStyle = 'rgba(0, 255, 0, 0)';
-	context.fillRect(0, 0, 5, 5);
-	QUnit.pixelEqual(canvas, 0, 0, 0, 0, 0, 0);
-	context.clearRect(0,0,5,5);
-	context.fillStyle = 'rgba(0, 0, 255, 0)';
-	context.fillRect(0, 0, 5, 5);
-	QUnit.pixelEqual(canvas, 0, 0, 0, 0, 0, 0);
-	context.clearRect(0,0,5,5);
-
-	context.fillStyle = 'rgba(0, 0, 0, 0.5)';
-	context.fillRect(0, 0, 5, 5);
-	QUnit.pixelEqual(canvas, 0, 0, 0, 0, 0, 127);
-	context.clearRect(0,0,5,5);
-	context.fillStyle = 'rgba(255, 0, 0, 0.5)';
-	context.fillRect(0, 0, 5, 5);
-	QUnit.pixelEqual(canvas, 0, 0, 255, 0, 0, 127);
-	context.clearRect(0,0,5,5);
-	context.fillStyle = 'rgba(0, 255, 0, 0.5)';
-	context.fillRect(0, 0, 5, 5);
-	QUnit.pixelEqual(canvas, 0, 0, 0, 255, 0, 127);
-	context.clearRect(0,0,5,5);
-	context.fillStyle = 'rgba(0, 0, 255, 0.5)';
-	context.fillRect(0, 0, 5, 5);
-	QUnit.pixelEqual(canvas, 0, 0, 0, 0, 255, 127);
-	context.clearRect(0,0,5,5);
-
-	context.fillStyle = 'rgba(0, 0, 0, 0.5)';
-	context.fillRect(0, 0, 5, 5);
-	QUnit.pixelEqual(canvas, 2, 2, 0, 0, 0, 127);
-	context.clearRect(0,0,5,5);
-	context.fillStyle = 'rgba(255, 0, 0, 0.5)';
-	context.fillRect(0, 0, 5, 5);
-	QUnit.pixelEqual(canvas, 2, 2, 255, 0, 0, 127);
-	context.clearRect(0,0,5,5);
-	context.fillStyle = 'rgba(0, 255, 0, 0.5)';
-	context.fillRect(0, 0, 5, 5);
-	QUnit.pixelEqual(canvas, 2, 2, 0, 255, 0, 127);
-	context.clearRect(0,0,5,5);
-	context.fillStyle = 'rgba(0, 0, 255, 0.5)';
-	context.fillRect(0, 0, 5, 5);
-	QUnit.pixelEqual(canvas, 2, 2, 0, 0, 255, 127);
-	context.clearRect(0,0,5,5);
-
-	context.fillStyle = 'rgba(0, 0, 0, 1)';
-	context.fillRect(0, 0, 5, 5);
-	QUnit.pixelEqual(canvas, 4, 4, 0, 0, 0, 255);
-	context.clearRect(0,0,5,5);
-	context.fillStyle = 'rgba(255, 0, 0, 1)';
-	context.fillRect(0, 0, 5, 5);
-	QUnit.pixelEqual(canvas, 4, 4, 255, 0, 0, 255);
-	context.clearRect(0,0,5,5);
-	context.fillStyle = 'rgba(0, 255, 0, 1)';
-	context.fillRect(0, 0, 5, 5);
-	QUnit.pixelEqual(canvas, 4, 4, 0, 255, 0, 255);
-	context.clearRect(0,0,5,5);
-	context.fillStyle = 'rgba(0, 0, 255, 1)';
-	context.fillRect(0, 0, 5, 5);
-	QUnit.pixelEqual(canvas, 4, 4, 0, 0, 255, 255);
-	context.clearRect(0,0,5,5);
-});
diff --git a/civicrm/bower_components/qunit/addons/canvas/canvas.html b/civicrm/bower_components/qunit/addons/canvas/canvas.html
deleted file mode 100644
index 5d253b8c15652ba9791cbcb0338bb36f7c35d3eb..0000000000000000000000000000000000000000
--- a/civicrm/bower_components/qunit/addons/canvas/canvas.html
+++ /dev/null
@@ -1,15 +0,0 @@
-<!DOCTYPE html>
-<html>
-<head>
-	<meta charset="UTF-8" />
-	<title>QUnit Test Suite - Canvas Addon</title>
-	<link rel="stylesheet" href="../../qunit/qunit.css" type="text/css" media="screen">
-	<script type="text/javascript" src="../../qunit/qunit.js"></script>
-	<script type="text/javascript" src="qunit-canvas.js"></script>
-	<script type="text/javascript" src="canvas-test.js"></script>
-</head>
-<body>
-	<div id="qunit"></div>
-	<canvas id="qunit-canvas" width="5" height="5"></canvas>
-</body>
-</html>
diff --git a/civicrm/bower_components/qunit/addons/canvas/qunit-canvas.js b/civicrm/bower_components/qunit/addons/canvas/qunit-canvas.js
deleted file mode 100644
index bc26c4caf847fdd7f3bc59b533811f2a567ade2b..0000000000000000000000000000000000000000
--- a/civicrm/bower_components/qunit/addons/canvas/qunit-canvas.js
+++ /dev/null
@@ -1,6 +0,0 @@
-QUnit.extend( QUnit, {
-	pixelEqual: function(canvas, x, y, r, g, b, a, message) {
-		var actual = Array.prototype.slice.apply(canvas.getContext('2d').getImageData(x, y, 1, 1).data), expected = [r, g, b, a];
-		QUnit.push(QUnit.equiv(actual, expected), actual, expected, message);
-	}
-});
diff --git a/civicrm/bower_components/qunit/addons/close-enough/README.md b/civicrm/bower_components/qunit/addons/close-enough/README.md
deleted file mode 100644
index d490b2508d312799cabf052b4b94d0c3512592eb..0000000000000000000000000000000000000000
--- a/civicrm/bower_components/qunit/addons/close-enough/README.md
+++ /dev/null
@@ -1,17 +0,0 @@
-Close-Enough - A QUnit Addon For Number Approximations
-================================
-
-This addon for QUnit adds close and notClose assertion methods, to test that
-numbers are close enough (or different enough) from an expected number, with
-a specified accuracy.
-
-Usage:
-
-    close(actual, expected, maxDifference, message)
-    notClose(actual, expected, minDifference, message)
-
-Where:
-
-  * maxDifference: the maximum inclusive difference allowed between the actual and expected numbers
-  * minDifference: the minimum exclusive difference allowed between the actual and expected numbers
-  * actual, expected, message: The usual
diff --git a/civicrm/bower_components/qunit/addons/close-enough/close-enough-test.js b/civicrm/bower_components/qunit/addons/close-enough/close-enough-test.js
deleted file mode 100644
index fc6a9a82eb49b64405434808e5e80c1799ac2482..0000000000000000000000000000000000000000
--- a/civicrm/bower_components/qunit/addons/close-enough/close-enough-test.js
+++ /dev/null
@@ -1,35 +0,0 @@
-test("Close Numbers", function () {
-	var halfPi = Math.PI / 2,
-		sqrt2 = Math.sqrt(2);
-
-	QUnit.close(7, 7, 0);
-	QUnit.close(7, 7.1, 0.1);
-	QUnit.close(7, 7.1, 0.2);
-
-	QUnit.close(3.141, Math.PI, 0.001);
-	QUnit.close(3.1, Math.PI, 0.1);
-
-	QUnit.close(halfPi, 1.57, 0.001);
-
-	QUnit.close(sqrt2, 1.4142, 0.0001);
-
-	QUnit.close(Infinity, Infinity, 1);
-});
-
-test("Distant Numbers", function () {
-	var halfPi = Math.PI / 2,
-		sqrt2 = Math.sqrt(2);
-
-	QUnit.notClose(6, 7, 0);
-	QUnit.notClose(7, 7.2, 0.1);
-	QUnit.notClose(7, 7.2, 0.19999999999);
-
-	QUnit.notClose(3.141, Math.PI, 0.0001);
-	QUnit.notClose(3.1, Math.PI, 0.001);
-
-	QUnit.notClose(halfPi, 1.57, 0.0001);
-
-	QUnit.notClose(sqrt2, 1.4142, 0.00001);
-
-	QUnit.notClose(Infinity, -Infinity, 5);
-});
\ No newline at end of file
diff --git a/civicrm/bower_components/qunit/addons/close-enough/close-enough.html b/civicrm/bower_components/qunit/addons/close-enough/close-enough.html
deleted file mode 100644
index f5683201227123fcc7bf0eccb8f19e1831509bc0..0000000000000000000000000000000000000000
--- a/civicrm/bower_components/qunit/addons/close-enough/close-enough.html
+++ /dev/null
@@ -1,14 +0,0 @@
-<!DOCTYPE html>
-<html>
-<head>
-	<meta charset="UTF-8" />
-	<title>QUnit Test Suite - Close Enough Addon</title>
-	<link rel="stylesheet" href="../../qunit/qunit.css" type="text/css" media="screen">
-	<script type="text/javascript" src="../../qunit/qunit.js"></script>
-	<script type="text/javascript" src="qunit-close-enough.js"></script>
-	<script type="text/javascript" src="close-enough-test.js"></script>
-</head>
-<body>
-	<div id="qunit"></div>
-</body>
-</html>
diff --git a/civicrm/bower_components/qunit/addons/close-enough/qunit-close-enough.js b/civicrm/bower_components/qunit/addons/close-enough/qunit-close-enough.js
deleted file mode 100644
index ddb5a584f90d8ce1806c164605950c24230655f7..0000000000000000000000000000000000000000
--- a/civicrm/bower_components/qunit/addons/close-enough/qunit-close-enough.js
+++ /dev/null
@@ -1,32 +0,0 @@
-QUnit.extend( QUnit, {
-	/**
-	 * Checks that the first two arguments are equal, or are numbers close enough to be considered equal
-	 * based on a specified maximum allowable difference.
-	 *
-	 * @example close(3.141, Math.PI, 0.001);
-	 *
-	 * @param Number actual
-	 * @param Number expected
-	 * @param Number maxDifference (the maximum inclusive difference allowed between the actual and expected numbers)
-	 * @param String message (optional)
-	 */
-	close: function(actual, expected, maxDifference, message) {
-		var passes = (actual === expected) || Math.abs(actual - expected) <= maxDifference;
-		QUnit.push(passes, actual, expected, message);
-	},
-
-	/**
-	 * Checks that the first two arguments are numbers with differences greater than the specified
-	 * minimum difference.
-	 *
-	 * @example notClose(3.1, Math.PI, 0.001);
-	 *
-	 * @param Number actual
-	 * @param Number expected
-	 * @param Number minDifference (the minimum exclusive difference allowed between the actual and expected numbers)
-	 * @param String message (optional)
-	 */
-	notClose: function(actual, expected, minDifference, message) {
-		QUnit.push(Math.abs(actual - expected) > minDifference, actual, expected, message);
-	}
-});
\ No newline at end of file
diff --git a/civicrm/bower_components/qunit/addons/composite/README.md b/civicrm/bower_components/qunit/addons/composite/README.md
deleted file mode 100644
index 2e2d2fd746879b0ccfd2325d0825f55bf57ead1c..0000000000000000000000000000000000000000
--- a/civicrm/bower_components/qunit/addons/composite/README.md
+++ /dev/null
@@ -1,12 +0,0 @@
-Composite - A QUnit Addon For Running Multiple Test Files
-================================
-
-Composite is a QUnit addon that, when handed an array of files, will
-open each of those files inside of an iframe, run the tests and
-display the results as a single suite of QUnit tests.
-
-The Rerun link next to each suite allows you to quickly rerun that suite,
-outside the composite runner.
-
-If you want to see what assertion failed in a long list of assertions,
-just use the regular "Hide passed tests" checkbox.
\ No newline at end of file
diff --git a/civicrm/bower_components/qunit/addons/composite/composite-demo-test.html b/civicrm/bower_components/qunit/addons/composite/composite-demo-test.html
deleted file mode 100644
index ad964c9dae344e411eb1ed06ddcac7f1fc1ed4ef..0000000000000000000000000000000000000000
--- a/civicrm/bower_components/qunit/addons/composite/composite-demo-test.html
+++ /dev/null
@@ -1,26 +0,0 @@
-<!doctype html>
-<html lang="en">
-<head>
-	<meta charset="UTF-8" />
-	<title>QUnit SubsuiteRunner Test Suite</title>
-
-	<link rel="stylesheet" href="../../qunit/qunit.css" type="text/css" media="screen">
-	<link rel="stylesheet" href="qunit-composite.css">
-	<script src="../../qunit/qunit.js"></script>
-	<script src="qunit-composite.js"></script>
-
-	<script>
-	QUnit.testSuites([
-		"../../test/index.html",
-		"../canvas/canvas.html",
-		"../close-enough/close-enough.html",
-		"../step/step.html"
-   	]);
-	</script>
-</head>
-<body>
-	<div id="qunit"></div>
-	<div id="qunit-fixture">
-</div>
-</body>
-</html>
diff --git a/civicrm/bower_components/qunit/addons/composite/index.html b/civicrm/bower_components/qunit/addons/composite/index.html
deleted file mode 100644
index b08f5e97579eb57ad67b537f2065f780e2f5da1c..0000000000000000000000000000000000000000
--- a/civicrm/bower_components/qunit/addons/composite/index.html
+++ /dev/null
@@ -1,33 +0,0 @@
-<!DOCTYPE html>
-<html>
-	<head>
-		<meta charset="UTF-8" />
-		<title>Composite</title>
-	</head>
-	<body>
-		<h1>Composite</h1>
-		<h3>A QUnit Addon For Running Multiple Test Files</h3>
-		<p>Composite is a QUnit addon that, when handed an array of
-		files, will open each of those files inside of an iframe, run
-		the tests and display the results as a single suite of QUnit
-		tests.</p>
-		<h4>Using Composite</h4>
-		<p>To use Composite, setup a standard QUnit html page as you
-		would with other QUnit tests. Remember to include composite.js
-		and composite.css. Then, inside of either an external js file,
-		or a script block call the only new method that Composite
-		exposes, QUnit.testSuites().</p><p>QUnit.testSuites() is
-		passed an array of test files to run as follows:</p>
-		<pre>
-QUnit.testSuites([
-    "test-file-1.html",
-    "test-file-2.html",
-    "test-file-3.html"
-]);
-		</pre>
-		<h4>Tests</h4>
-		<p>
-			<a href="composite-demo-test.html">Composite Demo</a>: A suite which demoes how Composite is bootstrapped and run.
-		</p>
-	</body>
-</html>
diff --git a/civicrm/bower_components/qunit/addons/composite/qunit-composite.css b/civicrm/bower_components/qunit/addons/composite/qunit-composite.css
deleted file mode 100644
index df47362db1836759e93a16982e3b6fe5c29f9223..0000000000000000000000000000000000000000
--- a/civicrm/bower_components/qunit/addons/composite/qunit-composite.css
+++ /dev/null
@@ -1,13 +0,0 @@
-iframe.qunit-subsuite{
-    position: fixed;
-    bottom: 0;
-    left: 0;
-    
-    margin: 0;
-    padding: 0;
-    border-width: 1px 0 0;
-    height: 45%;
-    width: 100%;
-
-    background: #fff;
-}
\ No newline at end of file
diff --git a/civicrm/bower_components/qunit/addons/composite/qunit-composite.js b/civicrm/bower_components/qunit/addons/composite/qunit-composite.js
deleted file mode 100644
index 89c47eb299475c31711ea91d7a2591cb1b77b2b3..0000000000000000000000000000000000000000
--- a/civicrm/bower_components/qunit/addons/composite/qunit-composite.js
+++ /dev/null
@@ -1,102 +0,0 @@
-(function( QUnit ) {
-
-QUnit.extend( QUnit, {
-	testSuites: function( suites ) {
-		QUnit.begin(function() {
-			QUnit.initIframe();
-		});
-
-		for ( var i = 0; i < suites.length; i++ ) {
-			QUnit.runSuite( suites[i] );
-		}
-
-		QUnit.done(function() {
-			this.iframe.style.display = "none";
-		});
-	},
-
-	runSuite: function( suite ) {
-		asyncTest( suite, function() {
-			QUnit.iframe.setAttribute( "src", suite );
-		});
-	},
-
-	initIframe: function() {
-		var body = document.body,
-			iframe = this.iframe = document.createElement( "iframe" ),
-			iframeWin;
-
-		iframe.className = "qunit-subsuite";
-		body.appendChild( iframe );
-
-		function onIframeLoad() {
-			var module, test,
-				count = 0;
-
-
-			iframeWin.QUnit.moduleStart(function( data ) {
-				// capture module name for messages
-				module = data.name;
-			});
-
-			iframeWin.QUnit.testStart(function( data ) {
-				// capture test name for messages
-				test = data.name;
-			});
-			iframeWin.QUnit.testDone(function() {
-				test = null;
-			});
-
-			iframeWin.QUnit.log(function( data ) {
-				if (test === null) {
-					return;
-				}
-				// pass all test details through to the main page
-				var message = module + ": " + test + ": " + data.message;
-				expect( ++count );
-				QUnit.push( data.result, data.actual, data.expected, message );
-			});
-
-			iframeWin.QUnit.done(function() {
-				// start the wrapper test from the main page
-				start();
-			});
-		}
-		QUnit.addEvent( iframe, "load", onIframeLoad );
-
-		iframeWin = iframe.contentWindow;
-	}
-});
-
-QUnit.testStart(function( data ) {
-	// update the test status to show which test suite is running
-	QUnit.id( "qunit-testresult" ).innerHTML = "Running " + data.name + "...<br>&nbsp;";
-});
-
-QUnit.testDone(function() {
-	var i,
-		current = QUnit.id( this.config.current.id ),
-		children = current.children,
-		src = this.iframe.src;
-
-	// undo the auto-expansion of failed tests
-	for ( i = 0; i < children.length; i++ ) {
-		if ( children[i].nodeName === "OL" ) {
-			children[i].style.display = "none";
-		}
-	}
-
-	QUnit.addEvent(current, "dblclick", function( e ) {
-		var target = e && e.target ? e.target : window.event.srcElement;
-		if ( target.nodeName.toLowerCase() === "span" || target.nodeName.toLowerCase() === "b" ) {
-			target = target.parentNode;
-		}
-		if ( window.location && target.nodeName.toLowerCase() === "strong" ) {
-			window.location = src;
-		}
-	});
-
-	current.getElementsByTagName('a')[0].href = src;
-});
-
-}( QUnit ) );
diff --git a/civicrm/bower_components/qunit/addons/junitlogger/index.html b/civicrm/bower_components/qunit/addons/junitlogger/index.html
deleted file mode 100644
index fe78af37a0fa2da83fd6b99fce9dab3ab254adf5..0000000000000000000000000000000000000000
--- a/civicrm/bower_components/qunit/addons/junitlogger/index.html
+++ /dev/null
@@ -1,44 +0,0 @@
-<!DOCTYPE html>
-<html>
-<head>
-<meta charset="UTF-8" />
-<title>QUnit Test Suite - JUnit report</title>
-<link rel="stylesheet" href="../../qunit/qunit.css" type="text/css" media="screen">
-<script type="text/javascript" src="../../qunit/qunit.js"></script>
-<script type="text/javascript" src="junitlogger.js"></script>
-<script type="text/javascript">
-QUnit.jUnitReport = function(data) {
-	console.log(data.xml);
-};
-
-module('Module 1');
-
-test("test 1", 2, function () {
-	equal(1, 1, "Assert 1 = 1");
-	equal(1, 2, "Assert fail 1 = 2");
-});
-
-test("test 2", 3, function () {
-	equal(1, 1, "Assert 1 = 1");
-	equal(1, 2, "Assert fail 1 = 2");
-	equal(1, 1, "Assert 1 = 1");
-});
-
-module('Module 2');
-
-test("test 3", 2, function () {
-	equal(1, 1, "Assert 1 = 1");
-	equal(1, 2, "Assert fail 1 = 2");
-});
-
-test("test 4", 3, function () {
-	equal(1, 1, "Assert 1 = 1");
-	equal(1, 2, "Assert fail 1 = 2");
-	equal(1, 3, "Assert fail 1 = 3");
-});
-</script>
-</head>
-<body>
-	<div id="qunit"></div>
-</body>
-</html>
diff --git a/civicrm/bower_components/qunit/addons/junitlogger/junitlogger.js b/civicrm/bower_components/qunit/addons/junitlogger/junitlogger.js
deleted file mode 100644
index dde47079560badb97f2e80b514c37d4e71d1d3d4..0000000000000000000000000000000000000000
--- a/civicrm/bower_components/qunit/addons/junitlogger/junitlogger.js
+++ /dev/null
@@ -1,268 +0,0 @@
-(function() {
-	var count = 0, suiteCount = 0, currentSuite, currentTest, suites = [], assertCount, start, results = {failed:0, passed:0, total:0, time:0};
-
-	QUnit.jUnitReport = function(data) {
-		// Gets called when a report is generated
-	};
-
-	QUnit.moduleStart(function(data) {
-		currentSuite = {
-			name: data.name,
-			tests: [],
-			failures: 0,
-			time: 0,
-			stdout : '',
-			stderr : ''
-		};
-
-		suites.push(currentSuite);
-	});
-
-	QUnit.moduleDone(function(data) {
-	});
-
-	QUnit.testStart(function(data) {
-		if(!start){ start = new Date(); }
-
-		assertCount = 0;
-
-		currentTest = {
-			name: data.name,
-			failures: [],
-			start: new Date()
-		};
-
-		// Setup default suite if no module was specified
-		if (!currentSuite) {
-			currentSuite = {
-				name: "default",
-				tests: [],
-				failures: 0,
-				time: 0,
-				stdout : '',
-				stderr : ''
-			};
-
-			suites.push(currentSuite);
-		}
-
-		currentSuite.tests.push(currentTest);
-	});
-
-	QUnit.testDone(function(data) {
-		currentTest.failed = data.failed;
-		currentTest.total = data.total;
-		currentSuite.failures += data.failed;
-
-		results.failed += data.failed;
-		results.passed += data.passed;
-		results.total += data.total;
-	});
-
-	QUnit.log(function(data) {
-		assertCount++;
-
-		if (!data.result) {
-			currentTest.failures.push(data.message);
-
-			// Add log message of failure to make it easier to find in jenkins UI
-			currentSuite.stdout += '[' + currentSuite.name + ', ' + currentTest.name + ', ' + assertCount + '] ' + data.message + '\n';
-		}
-	});
-
-	QUnit.done(function(data) {
-		function ISODateString(d) {
-			function pad(n) {
-				return n < 10 ? '0' + n : n;
-			}
-
-			return d.getUTCFullYear() + '-' +
-				pad(d.getUTCMonth() + 1)+'-' +
-				pad(d.getUTCDate()) + 'T' +
-				pad(d.getUTCHours()) + ':' +
-				pad(d.getUTCMinutes()) + ':' +
-				pad(d.getUTCSeconds()) + 'Z';
-		}
-
-		// Generate XML report
-		var i, ti, fi, test, suite,
-			xmlWriter = new XmlWriter({
-				linebreak_at : "testsuites,testsuite,testcase,failure,system-out,system-err"
-			}),
-			now = new Date();
-
-		xmlWriter.start('testsuites');
-
-		for (i = 0; i < suites.length; i++) {
-			suite = suites[i];
-
-			// Calculate time
-			for (ti = 0; ti < suite.tests.length; ti++) {
-				test = suite.tests[ti];
-
-				test.time = (now.getTime() - test.start.getTime()) / 1000;
-				suite.time += test.time;
-			}
-
-			xmlWriter.start('testsuite', {
-				id: "" + i,
-				name: suite.name,
-				errors: "0",
-				failures: suite.failures,
-				hostname: "localhost",
-				tests: suite.tests.length,
-				time: Math.round(suite.time * 1000) / 1000,
-				timestamp: ISODateString(now)
-			});
-
-			for (ti = 0; ti < suite.tests.length; ti++) {
-				test = suite.tests[ti];
-
-				xmlWriter.start('testcase', {
-					name: test.name,
-					total: test.total,
-					failed: test.failed,
-					time: Math.round(test.time * 1000) / 1000
-				});
-
-				for (fi = 0; fi < test.failures.length; fi++) {
-					xmlWriter.start('failure', {type: "AssertionFailedError", message: test.failures[fi]}, true);
-				}
-
-				xmlWriter.end('testcase');
-			}
-
-			if (suite.stdout) {
-				xmlWriter.start('system-out');
-				xmlWriter.cdata('\n' + suite.stdout);
-				xmlWriter.end('system-out');
-			}
-
-			if (suite.stderr) {
-				xmlWriter.start('system-err');
-				xmlWriter.cdata('\n' + suite.stderr);
-				xmlWriter.end('system-err');
-			}
-
-			xmlWriter.end('testsuite');
-		}
-
-		xmlWriter.end('testsuites');
-
-        results.time = new Date() - start;
-
-		QUnit.jUnitReport({
-			results:results,
-			xml: xmlWriter.getString()
-		});
-	});
-
-	function XmlWriter(settings) {
-		function addLineBreak(name) {
-			if (lineBreakAt[name] && data[data.length - 1] !== '\n') {
-				data.push('\n');
-			}
-		}
-
-		function makeMap(items, delim, map) {
-			var i;
-
-			items = items || [];
-
-			if (typeof(items) === "string") {
-				items = items.split(',');
-			}
-
-			map = map || {};
-
-			i = items.length;
-			while (i--) {
-				map[items[i]] = {};
-			}
-
-			return map;
-		}
-
-		function encode(text) {
-			var baseEntities = {
-				'"' : '&quot;',
-				"'" : '&apos;',
-				'<' : '&lt;',
-				'>' : '&gt;',
-				'&' : '&amp;'
-			};
-
-			return ('' + text).replace(/[<>&\"\']/g, function(chr) {
-				return baseEntities[chr] || chr;
-			});
-		}
-
-		var data = [], stack = [], lineBreakAt;
-
-		settings = settings || {};
-		lineBreakAt = makeMap(settings.linebreak_at || 'mytag');
-
-		this.start = function(name, attrs, empty) {
-			if (!empty) {
-				stack.push(name);
-			}
-
-			data.push('<', name);
-
-			for (var aname in attrs) {
-				data.push(" " + encode(aname), '="', encode(attrs[aname]), '"');
-			}
-
-			data.push(empty ? ' />' : '>');
-			addLineBreak(name);
-		};
-
-		this.end = function(name) {
-			stack.pop();
-			addLineBreak(name);
-			data.push('</', name, '>');
-			addLineBreak(name);
-		};
-
-		this.text = function(text) {
-			data.push(encode(text));
-		};
-
-		this.cdata = function(text) {
-			data.push('<![CDATA[', text, ']]>');
-		};
-
-		this.comment = function(text) {
-			data.push('<!--', text, '-->');
-		};
-
-		this.pi = function(name, text) {
-			if (text) {
-				data.push('<?', name, ' ', text, '?>\n');
-			} else {
-				data.push('<?', name, '?>\n');
-			}
-		};
-
-		this.doctype = function(text) {
-			data.push('<!DOCTYPE', text, '>\n');
-		};
-
-		this.getString = function() {
-			for (var i = stack.length - 1; i >= 0; i--) {
-				this.end(stack[i]);
-			}
-
-			stack = [];
-
-			return data.join('').replace(/\n$/, '');
-		};
-
-		this.reset = function() {
-			data = [];
-			stack = [];
-		};
-
-		this.pi(settings.xmldecl || 'xml version="1.0" encoding="UTF-8"');
-	}
-})();
\ No newline at end of file
diff --git a/civicrm/bower_components/qunit/addons/phantomjs/README.md b/civicrm/bower_components/qunit/addons/phantomjs/README.md
deleted file mode 100644
index ed6a4467da13352047b1c990a07a3a055a81996e..0000000000000000000000000000000000000000
--- a/civicrm/bower_components/qunit/addons/phantomjs/README.md
+++ /dev/null
@@ -1,14 +0,0 @@
-PhantomJS Runner
-================
-
-A runner for PhantomJS, providing console output for tests.
-
-Usage:
-
-	phantomjs runner.js url
-
-Example:
-
-	phantomjs runner.js http://localhost/qunit/test
-
-If you're using Grunt, you should take a look at its [qunit task](https://github.com/cowboy/grunt/blob/master/docs/task_qunit.md).
\ No newline at end of file
diff --git a/civicrm/bower_components/qunit/addons/phantomjs/runner.js b/civicrm/bower_components/qunit/addons/phantomjs/runner.js
deleted file mode 100644
index fdc824282696b02a0ce3680b28a699af7e3dd0b4..0000000000000000000000000000000000000000
--- a/civicrm/bower_components/qunit/addons/phantomjs/runner.js
+++ /dev/null
@@ -1,97 +0,0 @@
-/*
- * Qt+WebKit powered headless test runner using Phantomjs
- *
- * Phantomjs installation: http://code.google.com/p/phantomjs/wiki/BuildInstructions
- *
- * Run with:
- *  phantomjs runner.js [url-of-your-qunit-testsuite]
- *
- * E.g.
- *      phantomjs runner.js http://localhost/qunit/test
- */
-
-var url = phantom.args[0];
-
-var page = require('webpage').create();
-
-// Route "console.log()" calls from within the Page context to the main Phantom context (i.e. current "this")
-page.onConsoleMessage = function(msg) {
-	console.log(msg);
-};
-
-page.onInitialized = function() {
-	page.evaluate(addLogging);
-};
-page.open(url, function(status){
-	if (status !== "success") {
-		console.log("Unable to access network: " + status);
-		phantom.exit(1);
-	} else {
-		// page.evaluate(addLogging);
-		var interval = setInterval(function() {
-			if (finished()) {
-				clearInterval(interval);
-				onfinishedTests();
-			}
-		}, 500);
-	}
-});
-
-function finished() {
-	return page.evaluate(function(){
-		return !!window.qunitDone;
-	});
-}
-
-function onfinishedTests() {
-	var output = page.evaluate(function() {
-			return JSON.stringify(window.qunitDone);
-	});
-	phantom.exit(JSON.parse(output).failed > 0 ? 1 : 0);
-}
-
-function addLogging() {
-	window.document.addEventListener( "DOMContentLoaded", function() {
-		var current_test_assertions = [];
-
-		QUnit.testDone(function(result) {
-			var name = result.module + ': ' + result.name;
-			var i;
-
-			if (result.failed) {
-				console.log('Assertion Failed: ' + name);
-
-				for (i = 0; i < current_test_assertions.length; i++) {
-					console.log('    ' + current_test_assertions[i]);
-				}
-			}
-
-			current_test_assertions = [];
-		});
-
-		QUnit.log(function(details) {
-			var response;
-
-			if (details.result) {
-				return;
-			}
-
-			response = details.message || '';
-
-			if (typeof details.expected !== 'undefined') {
-				if (response) {
-					response += ', ';
-				}
-
-				response += 'expected: ' + details.expected + ', but was: ' + details.actual;
-			}
-
-			current_test_assertions.push('Failed assertion: ' + response);
-		});
-
-		QUnit.done(function(result){
-			console.log('Took ' + result.runtime +  'ms to run ' + result.total + ' tests. ' + result.passed + ' passed, ' + result.failed + ' failed.');
-			window.qunitDone = result;
-		});
-	}, false );
-}
diff --git a/civicrm/bower_components/qunit/addons/step/README.md b/civicrm/bower_components/qunit/addons/step/README.md
deleted file mode 100644
index 37af9df63fb2c7d219e725cf3260424a2ad64c7d..0000000000000000000000000000000000000000
--- a/civicrm/bower_components/qunit/addons/step/README.md
+++ /dev/null
@@ -1,18 +0,0 @@
-QUnit.step() - A QUnit Addon For Testing execution in order
-============================================================
-
-This addon for QUnit adds a step method that allows you to assert
-the proper sequence in which the code should execute.
-
-Example:
-
-    test("example test", function () {
-      function x() {
-        QUnit.step(2, "function y should be called first");
-      }
-      function y() {
-        QUnit.step(1);
-      }
-      y();
-      x();
-    });
\ No newline at end of file
diff --git a/civicrm/bower_components/qunit/addons/step/qunit-step.js b/civicrm/bower_components/qunit/addons/step/qunit-step.js
deleted file mode 100644
index 1ed3ff066c960588f368de38fbd106dbfa4ab40d..0000000000000000000000000000000000000000
--- a/civicrm/bower_components/qunit/addons/step/qunit-step.js
+++ /dev/null
@@ -1,25 +0,0 @@
-QUnit.extend( QUnit, {
-
-	/**
-	 * Check the sequence/order
-	 *
-	 * @example step(1); setTimeout(function () { step(3); }, 100); step(2);
-	 * @param Number expected  The excepted step within the test()
-	 * @param String message (optional)
-	 */
-	step: function (expected, message) {
-		this.config.current.step++; // increment internal step counter.
-		if (typeof message === "undefined") {
-			message = "step " + expected;
-		}
-		var actual = this.config.current.step;
-		QUnit.push(QUnit.equiv(actual, expected), actual, expected, message);
-	}
-});
-
-/**
- * Reset the step counter for every test()
- */
-QUnit.testStart(function () {
-	this.config.current.step = 0;
-});
diff --git a/civicrm/bower_components/qunit/addons/step/step-test.js b/civicrm/bower_components/qunit/addons/step/step-test.js
deleted file mode 100644
index a78c534b98e6aa65d1a1b322a3a8ed57be82e1d5..0000000000000000000000000000000000000000
--- a/civicrm/bower_components/qunit/addons/step/step-test.js
+++ /dev/null
@@ -1,13 +0,0 @@
-module('Step Addon');
-test("step", 3, function () {
-	QUnit.step(1, "step starts at 1");
-	setTimeout(function () {
-		start();
-		QUnit.step(3);
-	}, 100);
-	QUnit.step(2, "before the setTimeout callback is run");
-	stop();
-});
-test("step counter", 1, function () {
-	QUnit.step(1, "each test has its own step counter");
-});
\ No newline at end of file
diff --git a/civicrm/bower_components/qunit/addons/step/step.html b/civicrm/bower_components/qunit/addons/step/step.html
deleted file mode 100644
index 95ba492dfa050d721b4d5c2a5bacd82c1ac9d0c1..0000000000000000000000000000000000000000
--- a/civicrm/bower_components/qunit/addons/step/step.html
+++ /dev/null
@@ -1,14 +0,0 @@
-<!DOCTYPE html>
-<html>
-<head>
-	<meta charset="UTF-8" />
-	<title>QUnit Test Suite - Step Addon</title>
-	<link rel="stylesheet" href="../../qunit/qunit.css" type="text/css" media="screen">
-	<script type="text/javascript" src="../../qunit/qunit.js"></script>
-	<script type="text/javascript" src="qunit-step.js"></script>
-	<script type="text/javascript" src="step-test.js"></script>
-</head>
-<body>
-	<div id="qunit"></div>
-</body>
-</html>
diff --git a/civicrm/bower_components/qunit/addons/themes/README.md b/civicrm/bower_components/qunit/addons/themes/README.md
deleted file mode 100644
index 8bc1862c2476c59c3142230315d72dc9d11bc935..0000000000000000000000000000000000000000
--- a/civicrm/bower_components/qunit/addons/themes/README.md
+++ /dev/null
@@ -1,6 +0,0 @@
-Themes
-======
-
-These custom themes fully replace the default qunit.css file and should work
-with the default markup. To see them in action, open the html file for each.
-They'll run the QUnit testsuite itself.
\ No newline at end of file
diff --git a/civicrm/bower_components/qunit/addons/themes/gabe.css b/civicrm/bower_components/qunit/addons/themes/gabe.css
deleted file mode 100644
index e66aa1f172369fb4eb0456d262932a7fd57cc71a..0000000000000000000000000000000000000000
--- a/civicrm/bower_components/qunit/addons/themes/gabe.css
+++ /dev/null
@@ -1,362 +0,0 @@
-/**
- * QUnit Theme by Gabe Hendry
- *
- * http://docs.jquery.com/QUnit
- *
- * Copyright 2012 jQuery Foundation and other contributors
- * Released under the MIT license.
- * http://jquery.org/license
- */
-
-/** General Styles and Page Sturcture */
-body {
-	font-family:Arial, 'sans serif';
-    padding:20px 20px 0 20px;
-    position:relative;
-}
-
-h1, h2, h3, h4, h5, h6, #qunit-header, #qunit-banner {
-    font-family:Calibri, Arial, 'sans-serif';
-}
-
-h2 #qunit-tests, h2 #qunit-testrunner-toolbar, h2 #qunit-userAgent, #qunit-testresult {
-	font-family: Arial, 'sans-serif';
-}
-
-#qunit-testrunner-toolbar, #qunit-userAgent, #qunit-testresult, #qunit-tests li { font-size: small; }
-#qunit-tests { font-size: smaller; }
-
-
-/** Resets */
-
-#qunit-tests, #qunit-tests ol, #qunit-header, #qunit-banner, #qunit-userAgent, #qunit-testresult {
-	margin: 0;
-	padding: 0;
-}
-
-
-/** Headers */
-
-#qunit-header {
-	padding: 10px 0px 25px 0px;
-	color: #3B73B9;
-	font-size: 1.8em;
-	font-weight: normal;
-    height:2em;
-}
-
-#qunit-header a {
-    text-decoration: none;
-	color: #3B73B9;
-    font-weight:bold;
-    padding-right:22px;
-    float:left;
-
-}
-
-#qunit-header label {
-    font-size:14px;
-    color:#6BC9ED;
-    float:right;
-    font-family:Arial, 'sans-serif';
-    display: inline-block;
-}
-
-#qunit-header a + label:after {
-    content: ' }';
-}
-
-#qunit-header label + label {
-    margin-right:8px;
-}
-
-#qunit-header a:hover, #qunit-header a:focus {
-	color: #3B73B9;
-    background: url('data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABAAAAAcCAYAAABoMT8aAAAAGXRFWHRTb2Z0d2FyZQBBZG9iZSBJbWFnZVJlYWR5ccllPAAAA2RpVFh0WE1MOmNvbS5hZG9iZS54bXAAAAAAADw/eHBhY2tldCBiZWdpbj0i77u/IiBpZD0iVzVNME1wQ2VoaUh6cmVTek5UY3prYzlkIj8+IDx4OnhtcG1ldGEgeG1sbnM6eD0iYWRvYmU6bnM6bWV0YS8iIHg6eG1wdGs9IkFkb2JlIFhNUCBDb3JlIDUuMC1jMDYwIDYxLjEzNDc3NywgMjAxMC8wMi8xMi0xNzozMjowMCAgICAgICAgIj4gPHJkZjpSREYgeG1sbnM6cmRmPSJodHRwOi8vd3d3LnczLm9yZy8xOTk5LzAyLzIyLXJkZi1zeW50YXgtbnMjIj4gPHJkZjpEZXNjcmlwdGlvbiByZGY6YWJvdXQ9IiIgeG1sbnM6eG1wTU09Imh0dHA6Ly9ucy5hZG9iZS5jb20veGFwLzEuMC9tbS8iIHhtbG5zOnN0UmVmPSJodHRwOi8vbnMuYWRvYmUuY29tL3hhcC8xLjAvc1R5cGUvUmVzb3VyY2VSZWYjIiB4bWxuczp4bXA9Imh0dHA6Ly9ucy5hZG9iZS5jb20veGFwLzEuMC8iIHhtcE1NOk9yaWdpbmFsRG9jdW1lbnRJRD0ieG1wLmRpZDo4RjRENzREMkRFMzBFMTExQkZCM0YxOUI1MEUyRUQ0OCIgeG1wTU06RG9jdW1lbnRJRD0ieG1wLmRpZDpERkFDNTFBMjMwREYxMUUxQTA3RjlDQkNDQzY3MkI4MCIgeG1wTU06SW5zdGFuY2VJRD0ieG1wLmlpZDpERkFDNTFBMTMwREYxMUUxQTA3RjlDQkNDQzY3MkI4MCIgeG1wOkNyZWF0b3JUb29sPSJBZG9iZSBQaG90b3Nob3AgQ1M1IFdpbmRvd3MiPiA8eG1wTU06RGVyaXZlZEZyb20gc3RSZWY6aW5zdGFuY2VJRD0ieG1wLmlpZDo4RjRENzREMkRFMzBFMTExQkZCM0YxOUI1MEUyRUQ0OCIgc3RSZWY6ZG9jdW1lbnRJRD0ieG1wLmRpZDo4RjRENzREMkRFMzBFMTExQkZCM0YxOUI1MEUyRUQ0OCIvPiA8L3JkZjpEZXNjcmlwdGlvbj4gPC9yZGY6UkRGPiA8L3g6eG1wbWV0YT4gPD94cGFja2V0IGVuZD0iciI/PjKftvwAAAFqSURBVHja5NTNKwVRHMbxey9X3rrXStlY2ljJRiQLGytLIkUpIks7lIUFC9laCX+DhUiSlMRdsFBSdkqSt4u8ju+vnqkxZriZheTUp1NzzvxmzjnPTNxxnFiUlohFbL9fIL9xeOUf7EEiSgEbf8XUTwv04A59mIuyB2VowyqKvytQjkU8YwaFul6CJmQ+5MB38zSGUIAs8vCi3loc6bA3mECvJl2o0Jhn/B47qAorMIgU9lGJBc/YDZbQgNugAt1I4gGtepq1ZTxiHu2B34L6LpRiD6ee8UPUqfe2lPbl0i1Qoz4T8JCgm89hf6IKdwnX6tM5ZGIEb1py1i2wporNORToUDa2LStugVntdPKr3GvMUnmFUe8p2No3FNOBkCIWsn7NOcC6Pwd2EicoUiZsnVvYxZNutpM601F/CpIFpNazH5bIel1LqOAmqrWEwG/BirQorp3KgL3yMSZxFBYkf7OJ43/jp/ouwAB8JktCUeXXIAAAAABJRU5ErkJggg==') center right no-repeat;
-}
-
-h2, p {
-    padding: 10px 0 10px 0;
-    margin:0;
-    font-size:1.3em;
-}
-
-p {
-    padding-top:0;
-    font-size:small;
-    color:#7B7979;
-    line-height:1.6em;
-}
-
-h2#qunit-banner {
-	height: 16px;
-    padding:5px 5px 5px 25px;
-    line-height:16px;
-    margin:0px 0 15px 0;
-    border-radius: 5px;
-	-moz-border-radius: 5px;
-	-webkit-border-radius: 5px;
-    background-position:0px;
-    background-repeat:no-repeat;
-    font-size:1em;
-    font-weight:normal;
-}
-
-h2#qunit-banner.qunit-pass {
-    background-image:url('data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABAAAAAQCAYAAAAf8/9hAAAAGXRFWHRTb2Z0d2FyZQBBZG9iZSBJbWFnZVJlYWR5ccllPAAAAyBpVFh0WE1MOmNvbS5hZG9iZS54bXAAAAAAADw/eHBhY2tldCBiZWdpbj0i77u/IiBpZD0iVzVNME1wQ2VoaUh6cmVTek5UY3prYzlkIj8+IDx4OnhtcG1ldGEgeG1sbnM6eD0iYWRvYmU6bnM6bWV0YS8iIHg6eG1wdGs9IkFkb2JlIFhNUCBDb3JlIDUuMC1jMDYwIDYxLjEzNDc3NywgMjAxMC8wMi8xMi0xNzozMjowMCAgICAgICAgIj4gPHJkZjpSREYgeG1sbnM6cmRmPSJodHRwOi8vd3d3LnczLm9yZy8xOTk5LzAyLzIyLXJkZi1zeW50YXgtbnMjIj4gPHJkZjpEZXNjcmlwdGlvbiByZGY6YWJvdXQ9IiIgeG1sbnM6eG1wPSJodHRwOi8vbnMuYWRvYmUuY29tL3hhcC8xLjAvIiB4bWxuczp4bXBNTT0iaHR0cDovL25zLmFkb2JlLmNvbS94YXAvMS4wL21tLyIgeG1sbnM6c3RSZWY9Imh0dHA6Ly9ucy5hZG9iZS5jb20veGFwLzEuMC9zVHlwZS9SZXNvdXJjZVJlZiMiIHhtcDpDcmVhdG9yVG9vbD0iQWRvYmUgUGhvdG9zaG9wIENTNSBXaW5kb3dzIiB4bXBNTTpJbnN0YW5jZUlEPSJ4bXAuaWlkOjc1RjgyNEY5MzE2NzExRTFCQTA0RTIzMEVFNkY4ODM2IiB4bXBNTTpEb2N1bWVudElEPSJ4bXAuZGlkOjc1RjgyNEZBMzE2NzExRTFCQTA0RTIzMEVFNkY4ODM2Ij4gPHhtcE1NOkRlcml2ZWRGcm9tIHN0UmVmOmluc3RhbmNlSUQ9InhtcC5paWQ6NzVGODI0RjczMTY3MTFFMUJBMDRFMjMwRUU2Rjg4MzYiIHN0UmVmOmRvY3VtZW50SUQ9InhtcC5kaWQ6NzVGODI0RjgzMTY3MTFFMUJBMDRFMjMwRUU2Rjg4MzYiLz4gPC9yZGY6RGVzY3JpcHRpb24+IDwvcmRmOlJERj4gPC94OnhtcG1ldGE+IDw/eHBhY2tldCBlbmQ9InIiPz4C94F5AAAAwklEQVR42mL8//8/AyWAiYFCQLEBLOW7GEnVYwzEaUC8B4hXs5CoWRCIVwGxEtQQE1K9ANMMN5AUAzqA2AWJ/x6IzxJrAMi55WhiriBDYAYoEQi0DjSxdJDtsGgESd4F4jNYDAIF2m4oDQOzoBieDsqRbDoDpWEAXfMeqO0oCWkPmo1noH6eiWbYPSAOw5YSQYKr0cRnQg1BDvEwKI1hAEyyAk9AVsACDV9e6MRhSydyoBHKTKuh8bsHSTM+lzEABBgAXD0oIFydPtEAAAAASUVORK5CYII=');
-    color:#76B900;
-}
-
-h2#qunit-banner.qunit-pass:after {
-    content:'Congrats!  All of your tests passed!';
-}
-
-h2#qunit-banner.qunit-fail {
-    background-image:url('data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABAAAAAQCAYAAAAf8/9hAAAAGXRFWHRTb2Z0d2FyZQBBZG9iZSBJbWFnZVJlYWR5ccllPAAAAyBpVFh0WE1MOmNvbS5hZG9iZS54bXAAAAAAADw/eHBhY2tldCBiZWdpbj0i77u/IiBpZD0iVzVNME1wQ2VoaUh6cmVTek5UY3prYzlkIj8+IDx4OnhtcG1ldGEgeG1sbnM6eD0iYWRvYmU6bnM6bWV0YS8iIHg6eG1wdGs9IkFkb2JlIFhNUCBDb3JlIDUuMC1jMDYwIDYxLjEzNDc3NywgMjAxMC8wMi8xMi0xNzozMjowMCAgICAgICAgIj4gPHJkZjpSREYgeG1sbnM6cmRmPSJodHRwOi8vd3d3LnczLm9yZy8xOTk5LzAyLzIyLXJkZi1zeW50YXgtbnMjIj4gPHJkZjpEZXNjcmlwdGlvbiByZGY6YWJvdXQ9IiIgeG1sbnM6eG1wPSJodHRwOi8vbnMuYWRvYmUuY29tL3hhcC8xLjAvIiB4bWxuczp4bXBNTT0iaHR0cDovL25zLmFkb2JlLmNvbS94YXAvMS4wL21tLyIgeG1sbnM6c3RSZWY9Imh0dHA6Ly9ucy5hZG9iZS5jb20veGFwLzEuMC9zVHlwZS9SZXNvdXJjZVJlZiMiIHhtcDpDcmVhdG9yVG9vbD0iQWRvYmUgUGhvdG9zaG9wIENTNSBXaW5kb3dzIiB4bXBNTTpJbnN0YW5jZUlEPSJ4bXAuaWlkOjU5QUIzNEU2MzE2NzExRTE4ODc3OEVFNEY2NzhDMjM4IiB4bXBNTTpEb2N1bWVudElEPSJ4bXAuZGlkOjU5QUIzNEU3MzE2NzExRTE4ODc3OEVFNEY2NzhDMjM4Ij4gPHhtcE1NOkRlcml2ZWRGcm9tIHN0UmVmOmluc3RhbmNlSUQ9InhtcC5paWQ6NTlBQjM0RTQzMTY3MTFFMTg4Nzc4RUU0RjY3OEMyMzgiIHN0UmVmOmRvY3VtZW50SUQ9InhtcC5kaWQ6NTlBQjM0RTUzMTY3MTFFMTg4Nzc4RUU0RjY3OEMyMzgiLz4gPC9yZGY6RGVzY3JpcHRpb24+IDwvcmRmOlJERj4gPC94OnhtcG1ldGE+IDw/eHBhY2tldCBlbmQ9InIiPz46NEjgAAAAzElEQVR42mL8//8/AyWABUS8N1EFUS5AfA+KcQFBIE6DsjsFz9yGGAAEu6EGgEA6EM/CoRmkzhiJX8EE5bggKZyJZAsuzQwwNhMOp6IbsgpNM9jn8DCAOnsmFkNgNrlg0dyJbMAsNE0MOPgwza5AfBbdC7OgLsEHUDRjCwNChqBoxhWIxngMQI8dDAPKsSlCM2AmLgNAkh04/I3TECZcJiNFrys+Q2AGhOLQPAsaaLgMwZkS0fMDLkPgBqzGoxnZEBMg3gM1CBzdAAEGABpTMr+umvCXAAAAAElFTkSuQmCC');
-    color:#ee3324;
-}
-
-h2#qunit-banner.qunit-fail:after {
-    content:'Oops!  One or more tests failed!';
-}
-
-/** Test Runner Result Styles */
-
-#qunit-testrunner-toolbar {
-    position:absolute;
-    top:55px;
-    right:20px;
-    color:#6BC9ED;
-    font-size:14px;
-}
-
-#qunit-testrunner-toolbar:after {
-    content:' }';
-}
-
-h2#qunit-userAgent {
-	padding: 0;
-	color: #7B7979;
-    border:0;
-    font-size:small;
-    font-family: Arial, 'sans-serif';
-    font-weight:normal;
-    font-style:italic;
-}
-
-h2#qunit-userAgent:before {
-    content:'User Agents: ';
-}
-
-
-/** Tests: Pass/Fail */
-
-#qunit-tests {
-	list-style-position: inside;
-    list-style-type:none;
-}
-
-#qunit-tests li {
-	padding: 4px 10px;
-	list-style-position:outside;
-    border-radius: 5px;
-	-moz-border-radius: 5px;
-	-webkit-border-radius: 5px;
-    margin-bottom:5px;
-    position:relative;
-    *zoom:1;
-    list-style-type:none;
-}
-
-#qunit-tests.hidepass li.pass, #qunit-tests.hidepass li.running  {
-	display: none;
-}
-
-#qunit-tests li strong {
-	cursor: pointer;
-}
-
-#qunit-tests li a {
-    display:block;
-	position:absolute;
-    right:10px;
-    padding:0px 16px 0 0;
-    font-size:0.8em;
-    background:url('data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAwAAAAYCAYAAADOMhxqAAAAGXRFWHRTb2Z0d2FyZQBBZG9iZSBJbWFnZVJlYWR5ccllPAAAA2RpVFh0WE1MOmNvbS5hZG9iZS54bXAAAAAAADw/eHBhY2tldCBiZWdpbj0i77u/IiBpZD0iVzVNME1wQ2VoaUh6cmVTek5UY3prYzlkIj8+IDx4OnhtcG1ldGEgeG1sbnM6eD0iYWRvYmU6bnM6bWV0YS8iIHg6eG1wdGs9IkFkb2JlIFhNUCBDb3JlIDUuMC1jMDYwIDYxLjEzNDc3NywgMjAxMC8wMi8xMi0xNzozMjowMCAgICAgICAgIj4gPHJkZjpSREYgeG1sbnM6cmRmPSJodHRwOi8vd3d3LnczLm9yZy8xOTk5LzAyLzIyLXJkZi1zeW50YXgtbnMjIj4gPHJkZjpEZXNjcmlwdGlvbiByZGY6YWJvdXQ9IiIgeG1sbnM6eG1wTU09Imh0dHA6Ly9ucy5hZG9iZS5jb20veGFwLzEuMC9tbS8iIHhtbG5zOnN0UmVmPSJodHRwOi8vbnMuYWRvYmUuY29tL3hhcC8xLjAvc1R5cGUvUmVzb3VyY2VSZWYjIiB4bWxuczp4bXA9Imh0dHA6Ly9ucy5hZG9iZS5jb20veGFwLzEuMC8iIHhtcE1NOk9yaWdpbmFsRG9jdW1lbnRJRD0ieG1wLmRpZDo4RjRENzREMkRFMzBFMTExQkZCM0YxOUI1MEUyRUQ0OCIgeG1wTU06RG9jdW1lbnRJRD0ieG1wLmRpZDpENEZDRDdDQTMxODUxMUUxOTc3NEQ0OTUxNjc4REFEQiIgeG1wTU06SW5zdGFuY2VJRD0ieG1wLmlpZDpENEZDRDdDOTMxODUxMUUxOTc3NEQ0OTUxNjc4REFEQiIgeG1wOkNyZWF0b3JUb29sPSJBZG9iZSBQaG90b3Nob3AgQ1M1IFdpbmRvd3MiPiA8eG1wTU06RGVyaXZlZEZyb20gc3RSZWY6aW5zdGFuY2VJRD0ieG1wLmlpZDo5MDRENzREMkRFMzBFMTExQkZCM0YxOUI1MEUyRUQ0OCIgc3RSZWY6ZG9jdW1lbnRJRD0ieG1wLmRpZDo4RjRENzREMkRFMzBFMTExQkZCM0YxOUI1MEUyRUQ0OCIvPiA8L3JkZjpEZXNjcmlwdGlvbj4gPC9yZGY6UkRGPiA8L3g6eG1wbWV0YT4gPD94cGFja2V0IGVuZD0iciI/PpE8SAQAAAD3SURBVHjaYsw5+YYBC5gGxN+BuBhdgoUBO1AFYlMgFgXiOGQJJjSFrEDcC8RaQMwPxEFAvBuXDSDFP6D4F1SMG4gtgFgBiB+g2/ATiL8C8UIgPgMV+wvEujDFyBoWQRVPB+IsqOa3QCyFrBhZgysQMwLxFCjfB4hFgPgVlH8DiOcha/jHgBu0ALEMEH9G1rAXqikHi4ZkIP4DxEuQNaQBMReUngjEdkAcDPU8KKROAPFp5GAFBSUPNHZToZEFM+wsEHtgiziQJmYg7gPiy0B8HIiTgNgRX0yD/FFzYdXZK0B8Fchei5GWgBI40xJQbjQtjdi0BBBgAAsUYVWmfe1CAAAAAElFTkSuQmCC') bottom right no-repeat;
-	color: #3b73b9;
-	text-decoration: none;
-    height:12px;
-    top:5px;
-}
-#qunit-tests li a:hover,
-#qunit-tests li a:focus {
-	color: #6bc9ed;
-    background:url('data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAwAAAAYCAYAAADOMhxqAAAAGXRFWHRTb2Z0d2FyZQBBZG9iZSBJbWFnZVJlYWR5ccllPAAAA2RpVFh0WE1MOmNvbS5hZG9iZS54bXAAAAAAADw/eHBhY2tldCBiZWdpbj0i77u/IiBpZD0iVzVNME1wQ2VoaUh6cmVTek5UY3prYzlkIj8+IDx4OnhtcG1ldGEgeG1sbnM6eD0iYWRvYmU6bnM6bWV0YS8iIHg6eG1wdGs9IkFkb2JlIFhNUCBDb3JlIDUuMC1jMDYwIDYxLjEzNDc3NywgMjAxMC8wMi8xMi0xNzozMjowMCAgICAgICAgIj4gPHJkZjpSREYgeG1sbnM6cmRmPSJodHRwOi8vd3d3LnczLm9yZy8xOTk5LzAyLzIyLXJkZi1zeW50YXgtbnMjIj4gPHJkZjpEZXNjcmlwdGlvbiByZGY6YWJvdXQ9IiIgeG1sbnM6eG1wTU09Imh0dHA6Ly9ucy5hZG9iZS5jb20veGFwLzEuMC9tbS8iIHhtbG5zOnN0UmVmPSJodHRwOi8vbnMuYWRvYmUuY29tL3hhcC8xLjAvc1R5cGUvUmVzb3VyY2VSZWYjIiB4bWxuczp4bXA9Imh0dHA6Ly9ucy5hZG9iZS5jb20veGFwLzEuMC8iIHhtcE1NOk9yaWdpbmFsRG9jdW1lbnRJRD0ieG1wLmRpZDo4RjRENzREMkRFMzBFMTExQkZCM0YxOUI1MEUyRUQ0OCIgeG1wTU06RG9jdW1lbnRJRD0ieG1wLmRpZDpENEZDRDdDQTMxODUxMUUxOTc3NEQ0OTUxNjc4REFEQiIgeG1wTU06SW5zdGFuY2VJRD0ieG1wLmlpZDpENEZDRDdDOTMxODUxMUUxOTc3NEQ0OTUxNjc4REFEQiIgeG1wOkNyZWF0b3JUb29sPSJBZG9iZSBQaG90b3Nob3AgQ1M1IFdpbmRvd3MiPiA8eG1wTU06RGVyaXZlZEZyb20gc3RSZWY6aW5zdGFuY2VJRD0ieG1wLmlpZDo5MDRENzREMkRFMzBFMTExQkZCM0YxOUI1MEUyRUQ0OCIgc3RSZWY6ZG9jdW1lbnRJRD0ieG1wLmRpZDo4RjRENzREMkRFMzBFMTExQkZCM0YxOUI1MEUyRUQ0OCIvPiA8L3JkZjpEZXNjcmlwdGlvbj4gPC9yZGY6UkRGPiA8L3g6eG1wbWV0YT4gPD94cGFja2V0IGVuZD0iciI/PpE8SAQAAAD3SURBVHjaYsw5+YYBC5gGxN+BuBhdgoUBO1AFYlMgFgXiOGQJJjSFrEDcC8RaQMwPxEFAvBuXDSDFP6D4F1SMG4gtgFgBiB+g2/ATiL8C8UIgPgMV+wvEujDFyBoWQRVPB+IsqOa3QCyFrBhZgysQMwLxFCjfB4hFgPgVlH8DiOcha/jHgBu0ALEMEH9G1rAXqikHi4ZkIP4DxEuQNaQBMReUngjEdkAcDPU8KKROAPFp5GAFBSUPNHZToZEFM+wsEHtgiziQJmYg7gPiy0B8HIiTgNgRX0yD/FFzYdXZK0B8Fchei5GWgBI40xJQbjQtjdi0BBBgAAsUYVWmfe1CAAAAAElFTkSuQmCC') top right no-repeat;
-}
-#qunit-tests li.pass strong > span {color:#76B900;}
-#qunit-tests li.pass strong:first-child {
-    padding-left:20px;
-    background:url('data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAwAAAAMCAYAAABWdVznAAAAGXRFWHRTb2Z0d2FyZQBBZG9iZSBJbWFnZVJlYWR5ccllPAAAA2RpVFh0WE1MOmNvbS5hZG9iZS54bXAAAAAAADw/eHBhY2tldCBiZWdpbj0i77u/IiBpZD0iVzVNME1wQ2VoaUh6cmVTek5UY3prYzlkIj8+IDx4OnhtcG1ldGEgeG1sbnM6eD0iYWRvYmU6bnM6bWV0YS8iIHg6eG1wdGs9IkFkb2JlIFhNUCBDb3JlIDUuMC1jMDYwIDYxLjEzNDc3NywgMjAxMC8wMi8xMi0xNzozMjowMCAgICAgICAgIj4gPHJkZjpSREYgeG1sbnM6cmRmPSJodHRwOi8vd3d3LnczLm9yZy8xOTk5LzAyLzIyLXJkZi1zeW50YXgtbnMjIj4gPHJkZjpEZXNjcmlwdGlvbiByZGY6YWJvdXQ9IiIgeG1sbnM6eG1wTU09Imh0dHA6Ly9ucy5hZG9iZS5jb20veGFwLzEuMC9tbS8iIHhtbG5zOnN0UmVmPSJodHRwOi8vbnMuYWRvYmUuY29tL3hhcC8xLjAvc1R5cGUvUmVzb3VyY2VSZWYjIiB4bWxuczp4bXA9Imh0dHA6Ly9ucy5hZG9iZS5jb20veGFwLzEuMC8iIHhtcE1NOk9yaWdpbmFsRG9jdW1lbnRJRD0ieG1wLmRpZDo5MTRENzREMkRFMzBFMTExQkZCM0YxOUI1MEUyRUQ0OCIgeG1wTU06RG9jdW1lbnRJRD0ieG1wLmRpZDozODgyNDY5QzMxN0ExMUUxOTdFMkVCQkNENjFBMjc3RSIgeG1wTU06SW5zdGFuY2VJRD0ieG1wLmlpZDozODgyNDY5QjMxN0ExMUUxOTdFMkVCQkNENjFBMjc3RSIgeG1wOkNyZWF0b3JUb29sPSJBZG9iZSBQaG90b3Nob3AgQ1M1IFdpbmRvd3MiPiA8eG1wTU06RGVyaXZlZEZyb20gc3RSZWY6aW5zdGFuY2VJRD0ieG1wLmlpZDo5MTRENzREMkRFMzBFMTExQkZCM0YxOUI1MEUyRUQ0OCIgc3RSZWY6ZG9jdW1lbnRJRD0ieG1wLmRpZDo5MTRENzREMkRFMzBFMTExQkZCM0YxOUI1MEUyRUQ0OCIvPiA8L3JkZjpEZXNjcmlwdGlvbj4gPC9yZGY6UkRGPiA8L3g6eG1wbWV0YT4gPD94cGFja2V0IGVuZD0iciI/Pv7qI08AAAClSURBVHjaYvz//z8DKYClfBcjMeqUgFgQiM+yEKEYpHA3VFMYExEaVkEVg20ipKEDiF2g7LNAPIsJaqUgFsVpQFwOZb8H4nQQzQR13zuoAhgwhpoOA2FQGxiYkNw3E4phnoTZWgHEe2A6maC63yM54y6S4llA3InsTiaobhOYlUiKz0JNZ0DXAAL3gNgViFcjeRLZZkRMI7FhioyhBrzHFs4AAQYAz08iXvWgossAAAAASUVORK5CYII=') center left no-repeat;
-}
-
-#qunit-tests li.fail strong > span {color:#EE3324;}
-#qunit-tests li.fail strong:first-child {
-    padding-left:20px;
-    background:url('data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAwAAAAMCAYAAABWdVznAAAAGXRFWHRTb2Z0d2FyZQBBZG9iZSBJbWFnZVJlYWR5ccllPAAAA2RpVFh0WE1MOmNvbS5hZG9iZS54bXAAAAAAADw/eHBhY2tldCBiZWdpbj0i77u/IiBpZD0iVzVNME1wQ2VoaUh6cmVTek5UY3prYzlkIj8+IDx4OnhtcG1ldGEgeG1sbnM6eD0iYWRvYmU6bnM6bWV0YS8iIHg6eG1wdGs9IkFkb2JlIFhNUCBDb3JlIDUuMC1jMDYwIDYxLjEzNDc3NywgMjAxMC8wMi8xMi0xNzozMjowMCAgICAgICAgIj4gPHJkZjpSREYgeG1sbnM6cmRmPSJodHRwOi8vd3d3LnczLm9yZy8xOTk5LzAyLzIyLXJkZi1zeW50YXgtbnMjIj4gPHJkZjpEZXNjcmlwdGlvbiByZGY6YWJvdXQ9IiIgeG1sbnM6eG1wTU09Imh0dHA6Ly9ucy5hZG9iZS5jb20veGFwLzEuMC9tbS8iIHhtbG5zOnN0UmVmPSJodHRwOi8vbnMuYWRvYmUuY29tL3hhcC8xLjAvc1R5cGUvUmVzb3VyY2VSZWYjIiB4bWxuczp4bXA9Imh0dHA6Ly9ucy5hZG9iZS5jb20veGFwLzEuMC8iIHhtcE1NOk9yaWdpbmFsRG9jdW1lbnRJRD0ieG1wLmRpZDo5MTRENzREMkRFMzBFMTExQkZCM0YxOUI1MEUyRUQ0OCIgeG1wTU06RG9jdW1lbnRJRD0ieG1wLmRpZDo0MzNBNEM0QzMxN0ExMUUxQjk0MUYyOEJCODA0OTM1OSIgeG1wTU06SW5zdGFuY2VJRD0ieG1wLmlpZDo0MzNBNEM0QjMxN0ExMUUxQjk0MUYyOEJCODA0OTM1OSIgeG1wOkNyZWF0b3JUb29sPSJBZG9iZSBQaG90b3Nob3AgQ1M1IFdpbmRvd3MiPiA8eG1wTU06RGVyaXZlZEZyb20gc3RSZWY6aW5zdGFuY2VJRD0ieG1wLmlpZDo5MTRENzREMkRFMzBFMTExQkZCM0YxOUI1MEUyRUQ0OCIgc3RSZWY6ZG9jdW1lbnRJRD0ieG1wLmRpZDo5MTRENzREMkRFMzBFMTExQkZCM0YxOUI1MEUyRUQ0OCIvPiA8L3JkZjpEZXNjcmlwdGlvbj4gPC9yZGY6UkRGPiA8L3g6eG1wbWV0YT4gPD94cGFja2V0IGVuZD0iciI/PnO7dSIAAACtSURBVHjaYnxnrMIABEpA/B6K0YEgEBsD8VnBM7ffM0E5d6HYGIvi3UiYgQkqiCyJrAmZbwzTcBaKYZrOAHEaEM9E05wOIlig7nZFM20mmtM6gXgWzAYGJE1nsXgapLACxmFCkniPQwOKGLKGmVC3owMUcZiGDjTFs9BMhmuCxUM5muJ0qJ9Wo2lCcRII7IEFH9RPYbDQgaUCFqjVYdDkMQuLH9Khau6BOAABBgDmhyuetyQ3ywAAAABJRU5ErkJggg==') center left no-repeat;
-}
-
-#qunit-tests li ol {
-	margin:0;
-	padding:10px 0 0 0;
-	background-color: #fff;
-}
-
-#qunit-tests li ol li {
-    list-style-position: inside;
-    list-style-type:decimal;
-    *list-style-position: outside;
-}
-
-#qunit-tests table {
-	border-collapse: collapse;
-	margin-top: .2em;
-}
-
-#qunit-tests th {
-	text-align: right;
-	vertical-align: top;
-	padding: 0 .5em 0 0;
-}
-
-#qunit-tests td {
-	vertical-align: top;
-}
-
-#qunit-tests pre {
-	margin: 0;
-	white-space: pre-wrap;
-	word-wrap: break-word;
-}
-
-#qunit-tests del {
-	background-color: #add566;
-	color: #555;
-	text-decoration: none;
-}
-
-#qunit-tests ins {
-	background-color: #f5857c;
-	color: #555;
-	text-decoration: none;
-}
-
-/*** Test Counts */
-
-#qunit-tests b.counts {
-    color: #7B7979;
-    font-size:0.8em;
-    margin-left:10px;
-}
-
-b.counts b.passed, b.counts b.failed {
-    display:inline-block;
-    padding:0px 1px;
-    border-radius: 3px;
-	-moz-border-radius: 3px;
-	-webkit-border-radius: 3px;
-    color:#FFF;
-}
-
-b.counts b.passed {
-    background:#76b900;
-}
-
-b.counts b.failed {
-    background:#ee3324;
- }
-
-
-#qunit-tests li li {
-	margin:0 0 5px;
-	padding: 0.4em 0.5em 0.4em 0.5em;
-	background-color: #fff;
-	border-bottom: none;
-    border-radius: 3px;
-	-moz-border-radius: 3px;
-	-webkit-border-radius: 3px;
-    overflow:auto;
-}
-
-/*** Passing Styles */
-
-#qunit-tests li li.pass {
-	color: #7B7979;
-	background-color: #fff;
-	border-left: 20px solid #76B900;
-}
-
-#qunit-tests .pass                          { color: #76B900; background-color: #FFF; border: 1px solid #add566; }
-
-#qunit-tests .pass .test-actual,
-#qunit-tests .pass .test-expected           { color: #999999; }
-
-
-/*** Failing Styles */
-#qunit-tests li.fail ol {
-    background:#f7f7f7;
-}
-
-#qunit-tests li li.fail {
-	color: #7B7979;
-	background-color: #fff;
-	border-left: 20px solid #EE3324;
-	white-space: pre;
-}
-
-#qunit-tests .fail                          { color: #EE3324; border: 1px solid #f5857c; background-color: #f7f7f7; }
-
-
-#qunit-tests .fail .test-actual,
-#qunit-tests .fail .test-expected           { color: #999999;   }
-
-
-
-/** Result */
-
-p#qunit-testresult {
-	padding: 10px 0;
-    font-weight:bold;
-    line-height:1.6em;
-	color: #7B7979;
-}
-
-p#qunit-testresult span.passed, p#qunit-testresult span.failed {
-    font-size:1.5em;
-    font-weight:bold;
-    display:inline-block;
-    padding:3px;
-    border-radius: 5px;
-	-moz-border-radius: 5px;
-	-webkit-border-radius: 5px;
-}
-
-p#qunit-testresult span.passed {
-    color:#FFF;
-    background:#76b900
-}
-
-p#qunit-testresult span.failed {
-    color:#FFF;
-    background:#ee3324;
-}
-
-
-/** Fixture */
-
-#qunit-fixture {
-	position: absolute;
-	top: -10000px;
-	left: -10000px;
-    width: 1000px;
-    height: 1000px;
-}
diff --git a/civicrm/bower_components/qunit/addons/themes/gabe.html b/civicrm/bower_components/qunit/addons/themes/gabe.html
deleted file mode 100644
index ea532475baf72910a886314404ffc8e7238d366a..0000000000000000000000000000000000000000
--- a/civicrm/bower_components/qunit/addons/themes/gabe.html
+++ /dev/null
@@ -1,14 +0,0 @@
-<!DOCTYPE html>
-<html>
-<head>
-	<title>QUnit Test Suite - Gabe Theme</title>
-	<link rel="stylesheet" href="gabe.css" type="text/css" media="screen">
-	<script type="text/javascript" src="../../qunit/qunit.js"></script>
-	<script type="text/javascript" src="../../test/test.js"></script>
-	<script type="text/javascript" src="../../test/deepEqual.js"></script>
-</head>
-<body>
-	<div id="qunit"></div>
-	<div id="qunit-fixture">test markup</div>
-</body>
-</html>
diff --git a/civicrm/bower_components/qunit/addons/themes/nv.css b/civicrm/bower_components/qunit/addons/themes/nv.css
deleted file mode 100644
index 1453e4c03e36e1042031528948b4a67eacaffd8d..0000000000000000000000000000000000000000
--- a/civicrm/bower_components/qunit/addons/themes/nv.css
+++ /dev/null
@@ -1,208 +0,0 @@
-/**
- * QUnit Theme by NV
- *
- * http://docs.jquery.com/QUnit
- *
- * Copyright 2012 jQuery Foundation and other contributors
- * Released under the MIT license.
- * http://jquery.org/license
- */
-
-/** Font Family and Sizes */
-
-#qunit-tests, #qunit-header, #qunit-banner, #qunit-testrunner-toolbar, #qunit-userAgent, #qunit-testresult {
-	font-family: "Helvetica Neue", Helvetica, sans-serif;
-}
-
-#qunit-testrunner-toolbar, #qunit-userAgent, #qunit-testresult, #qunit-tests li { font-size: small; }
-#qunit-tests { font-size: smaller; }
-
-
-/** Resets */
-
-#qunit-wrapper, #qunit-tests, #qunit-tests ol, #qunit-header, #qunit-banner, #qunit-userAgent, #qunit-testresult {
-	margin: 0;
-	padding: 0;
-}
-
-
-/** Header */
-
-#qunit-header {
-	font-family: "Helvetica Neue Light", "HelveticaNeue-Light", "Helvetica Neue", Helvetica, sans-serif;
-	padding: 0.5em 0 0.5em 1.3em;
-
-	color: #8699a4;
-	background-color: #0d3349;
-
-	font-size: 1.5em;
-	line-height: 1em;
-	font-weight: normal;
-}
-
-#qunit-header a {
-	text-decoration: none;
-	color: #c2ccd1;
-}
-
-#qunit-header a:hover,
-#qunit-header a:focus {
-	color: #fff;
-}
-
-#qunit-header label {
-	display: inline-block;
-}
-
-#qunit-banner.qunit-pass {
-	height: 3px;
-}
-#qunit-banner.qunit-fail {
-	height: 5px;
-}
-
-#qunit-testrunner-toolbar {
-	padding: 0 0 0.5em 2em;
-}
-
-#qunit-testrunner-toolbar label {
-	margin-right: 1em;
-}
-
-#qunit-userAgent {
-	padding: 0.5em 0 0.5em 2.5em;
-	font-weight: normal;
-	color: #666;
-}
-
-
-/** Tests: Pass/Fail */
-
-#qunit-tests {
-	list-style-type: none;
-	background-color: #D2E0E6;
-}
-
-#qunit-tests li {
-	padding: 0.4em 0.5em 0.4em 2.5em;
-}
-
-#qunit-tests li strong {
-	font-weight: normal;
-	cursor: pointer;
-}
-
-#qunit-tests ol {
-	margin: 0.5em 0 1em;
-	background-color: #fff;
-}
-
-#qunit-tests table {
-	border-collapse: collapse;
-	margin-top: .2em;
-}
-
-#qunit-tests th {
-	text-align: right;
-	vertical-align: top;
-	padding: 0 .5em 0 0;
-}
-
-#qunit-tests td {
-	vertical-align: top;
-}
-
-#qunit-tests pre {
-	margin: 0;
-	white-space: pre-wrap;
-	word-wrap: break-word;
-}
-
-#qunit-tests del {
-	background-color: #e0f2be;
-	color: #374e0c;
-	text-decoration: none;
-}
-
-#qunit-tests ins {
-	background-color: #ffcaca;
-	color: #500;
-	text-decoration: none;
-}
-
-/*** Test Counts */
-
-#qunit-tests b.passed                       { color: #5E740B; }
-#qunit-tests b.failed {
-	color: #710909;
-}
-#qunit-tests li.fail .failed {
-	color: #E48989;
-}
-#qunit-tests li.fail .passed {
-	color: #E3C987;
-}
-
-#qunit-tests li li {
-	margin-left: 2.5em;
-	padding: 0.7em 0.5em 0.7em 0;
-	background-color: #fff;
-	border-bottom: none;
-}
-
-#qunit-tests b.counts {
-	font-weight: normal;
-}
-
-/*** Passing Styles */
-
-#qunit-tests li li.pass {
-	color: #5E740B;
-	background-color: #fff;
-}
-
-#qunit-tests .pass                          { color: #2f3424; background-color: #d9dec3; }
-#qunit-tests .pass .module-name             { color: #636b51; }
-
-#qunit-tests .pass .test-actual,
-#qunit-tests .pass .test-expected           { color: #999999; }
-
-#qunit-banner.qunit-pass                    { background-color: #C6E746; }
-
-/*** Failing Styles */
-
-#qunit-tests li li.fail {
-	color: #710909;
-	background-color: #fff;
-}
-
-#qunit-tests .fail                          { color: #fff; background-color: #962323; }
-#qunit-tests .fail .module-name,
-#qunit-tests .fail .counts                  { color: #DEC1C1; }
-
-#qunit-tests .fail .test-actual             { color: #B72F2F; }
-#qunit-tests .fail .test-expected           { color: green;   }
-
-#qunit-banner.qunit-fail,
-#qunit-testrunner-toolbar                   { color: #dec1c1; background-color: #962323; }
-
-
-/** Footer */
-
-#qunit-testresult {
-	padding: 0.5em 0.5em 0.5em 2.5em;
-	color: #333;
-}
-#qunit-testresult .module-name {
-	font-weight: bold;
-}
-
-/** Fixture */
-
-#qunit-fixture {
-	position: absolute;
-	top: -10000px;
-	left: -10000px;
-	width: 1000px;
-	height: 1000px;
-}
diff --git a/civicrm/bower_components/qunit/addons/themes/nv.html b/civicrm/bower_components/qunit/addons/themes/nv.html
deleted file mode 100644
index 42084508bedf60f945bd338d1ad2c898ee21adfe..0000000000000000000000000000000000000000
--- a/civicrm/bower_components/qunit/addons/themes/nv.html
+++ /dev/null
@@ -1,14 +0,0 @@
-<!DOCTYPE html>
-<html>
-<head>
-	<title>QUnit Test Suite - NV Theme</title>
-	<link rel="stylesheet" href="nv.css" type="text/css" media="screen">
-	<script type="text/javascript" src="../../qunit/qunit.js"></script>
-	<script type="text/javascript" src="../../test/test.js"></script>
-	<script type="text/javascript" src="../../test/deepEqual.js"></script>
-</head>
-<body>
-	<div id="qunit"></div>
-	<div id="qunit-fixture">test markup</div>
-</body>
-</html>
diff --git a/civicrm/bower_components/qunit/grunt.js b/civicrm/bower_components/qunit/grunt.js
deleted file mode 100644
index 448cbf2b630332ec3040f0d54e02ec1ca38174af..0000000000000000000000000000000000000000
--- a/civicrm/bower_components/qunit/grunt.js
+++ /dev/null
@@ -1,114 +0,0 @@
-/*global config:true, task:true*/
-module.exports = function( grunt ) {
-
-grunt.loadNpmTasks( "grunt-git-authors" );
-
-grunt.initConfig({
-	pkg: '<json:package.json>',
-	qunit: {
-		// TODO include 'test/logs.html' as well
-		qunit: 'test/index.html',
-		addons: [
-			'addons/canvas/canvas.html',
-			'addons/close-enough/close-enough.html',
-			'addons/composite/composite-demo-test.html'
-		]
-	},
-	lint: {
-		qunit: 'qunit/qunit.js',
-		// addons: 'addons/**/*.js',
-		grunt: 'grunt.js'
-		// TODO need to figure out which warnings to fix and which to disable
-		// tests: 'test/test.js'
-	},
-	jshint: {
-		qunit: {
-			options: {
-				onevar: true,
-				browser: true,
-				bitwise: true,
-				curly: true,
-				trailing: true,
-				immed: true,
-				latedef: false,
-				newcap: true,
-				noarg: false,
-				noempty: true,
-				nonew: true,
-				sub: true,
-				undef: true,
-				eqnull: true,
-				proto: true,
-				smarttabs: true
-			},
-			globals: {
-				jQuery: true,
-				exports: true
-			}
-		},
-		addons: {
-			options: {
-				browser: true,
-				curly: true,
-				eqnull: true,
-				eqeqeq: true,
-				expr: true,
-				evil: true,
-				jquery: true,
-				latedef: true,
-				noarg: true,
-				onevar: true,
-				smarttabs: true,
-				trailing: true,
-				undef: true
-			},
-			globals: {
-				module: true,
-				test: true,
-				asyncTest: true,
-				expect: true,
-				start: true,
-				stop: true,
-				QUnit: true
-			}
-		},
-		tests: {
-		}
-	}
-});
-
-grunt.registerTask( "build-git", function( sha ) {
-	function processor( content ) {
-		var tagline = " - A JavaScript Unit Testing Framework";
-		return content.replace( tagline, "-" + sha + " " + grunt.template.today('isoDate') + tagline );
-	}
-	grunt.file.copy( "qunit/qunit.css", "dist/qunit-git.css", {
-		process: processor
-	});
-	grunt.file.copy( "qunit/qunit.js", "dist/qunit-git.js", {
-		process: processor
-	});
-});
-
-grunt.registerTask( "testswarm", function( commit, configFile ) {
-	var testswarm = require( "testswarm" ),
-		config = grunt.file.readJSON( configFile ).qunit;
-	testswarm({
-		url: config.swarmUrl,
-		pollInterval: 10000,
-		timeout: 1000 * 60 * 30,
-		done: this.async()
-	}, {
-		authUsername: "qunit",
-		authToken: config.authToken,
-		jobName: 'QUnit commit #<a href="https://github.com/jquery/qunit/commit/' + commit + '">' + commit.substr( 0, 10 ) + '</a>',
-		runMax: config.runMax,
-		"runNames[]": "QUnit",
-		"runUrls[]": config.testUrl + commit + "/test/index.html",
-		"browserSets[]": ["popular"]
-	});
-});
-
-grunt.registerTask('default', 'lint qunit');
-
-};
diff --git a/civicrm/bower_components/qunit/package.json b/civicrm/bower_components/qunit/package.json
deleted file mode 100644
index fb6abe2bb6c8e83d6ad29cdd672c1770b726cabd..0000000000000000000000000000000000000000
--- a/civicrm/bower_components/qunit/package.json
+++ /dev/null
@@ -1,37 +0,0 @@
-{
-  "name": "qunitjs",
-  "title": "QUnit",
-  "description": "An easy-to-use JavaScript Unit Testing framework.",
-  "version": "1.10.0",
-  "author": {
-    "name": "jQuery Foundation and other contributors",
-    "url": "https://github.com/jquery/qunit/blob/master/AUTHORS.txt"
-  },
-  "contributors": [
-    "John Resig <jeresig@gmail.com> (http://ejohn.org/)",
-    "Jörn Zaefferer <joern.zaefferer@gmail.com> (http://bassistance.de/)"
-  ],
-  "homepage": "http://qunitjs.com",
-  "repository": {
-    "type": "git",
-    "url": "git://github.com/jquery/qunit.git"
-  },
-  "bugs": {
-    "url": "https://github.com/jquery/qunit/issues"
-  },
-  "license": {
-    "name": "MIT",
-    "url": "http://www.opensource.org/licenses/mit-license.php"
-  },
-  "keywords": [
-    "testing",
-    "unit",
-    "jquery"
-  ],
-  "main": "qunit/qunit.js",
-  "devDependencies": {
-    "grunt": "0.3.x",
-    "grunt-git-authors": "1.0.0",
-    "testswarm": "0.2.2"
-  }
-}
diff --git a/civicrm/bower_components/qunit/qunit/qunit.css b/civicrm/bower_components/qunit/qunit/qunit.css
deleted file mode 100644
index 55970e00659ee82fd180064211a881d3aa53cf08..0000000000000000000000000000000000000000
--- a/civicrm/bower_components/qunit/qunit/qunit.css
+++ /dev/null
@@ -1,235 +0,0 @@
-/**
- * QUnit v1.10.0 - A JavaScript Unit Testing Framework
- *
- * http://qunitjs.com
- *
- * Copyright 2012 jQuery Foundation and other contributors
- * Released under the MIT license.
- * http://jquery.org/license
- */
-
-/** Font Family and Sizes */
-
-#qunit-tests, #qunit-header, #qunit-banner, #qunit-testrunner-toolbar, #qunit-userAgent, #qunit-testresult {
-	font-family: "Helvetica Neue Light", "HelveticaNeue-Light", "Helvetica Neue", Calibri, Helvetica, Arial, sans-serif;
-}
-
-#qunit-testrunner-toolbar, #qunit-userAgent, #qunit-testresult, #qunit-tests li { font-size: small; }
-#qunit-tests { font-size: smaller; }
-
-
-/** Resets */
-
-#qunit-tests, #qunit-tests ol, #qunit-header, #qunit-banner, #qunit-userAgent, #qunit-testresult, #qunit-modulefilter {
-	margin: 0;
-	padding: 0;
-}
-
-
-/** Header */
-
-#qunit-header {
-	padding: 0.5em 0 0.5em 1em;
-
-	color: #8699a4;
-	background-color: #0d3349;
-
-	font-size: 1.5em;
-	line-height: 1em;
-	font-weight: normal;
-
-	border-radius: 5px 5px 0 0;
-	-moz-border-radius: 5px 5px 0 0;
-	-webkit-border-top-right-radius: 5px;
-	-webkit-border-top-left-radius: 5px;
-}
-
-#qunit-header a {
-	text-decoration: none;
-	color: #c2ccd1;
-}
-
-#qunit-header a:hover,
-#qunit-header a:focus {
-	color: #fff;
-}
-
-#qunit-testrunner-toolbar label {
-	display: inline-block;
-	padding: 0 .5em 0 .1em;
-}
-
-#qunit-banner {
-	height: 5px;
-}
-
-#qunit-testrunner-toolbar {
-	padding: 0.5em 0 0.5em 2em;
-	color: #5E740B;
-	background-color: #eee;
-	overflow: hidden;
-}
-
-#qunit-userAgent {
-	padding: 0.5em 0 0.5em 2.5em;
-	background-color: #2b81af;
-	color: #fff;
-	text-shadow: rgba(0, 0, 0, 0.5) 2px 2px 1px;
-}
-
-#qunit-modulefilter-container {
-	float: right;
-}
-
-/** Tests: Pass/Fail */
-
-#qunit-tests {
-	list-style-position: inside;
-}
-
-#qunit-tests li {
-	padding: 0.4em 0.5em 0.4em 2.5em;
-	border-bottom: 1px solid #fff;
-	list-style-position: inside;
-}
-
-#qunit-tests.hidepass li.pass, #qunit-tests.hidepass li.running  {
-	display: none;
-}
-
-#qunit-tests li strong {
-	cursor: pointer;
-}
-
-#qunit-tests li a {
-	padding: 0.5em;
-	color: #c2ccd1;
-	text-decoration: none;
-}
-#qunit-tests li a:hover,
-#qunit-tests li a:focus {
-	color: #000;
-}
-
-#qunit-tests ol {
-	margin-top: 0.5em;
-	padding: 0.5em;
-
-	background-color: #fff;
-
-	border-radius: 5px;
-	-moz-border-radius: 5px;
-	-webkit-border-radius: 5px;
-}
-
-#qunit-tests table {
-	border-collapse: collapse;
-	margin-top: .2em;
-}
-
-#qunit-tests th {
-	text-align: right;
-	vertical-align: top;
-	padding: 0 .5em 0 0;
-}
-
-#qunit-tests td {
-	vertical-align: top;
-}
-
-#qunit-tests pre {
-	margin: 0;
-	white-space: pre-wrap;
-	word-wrap: break-word;
-}
-
-#qunit-tests del {
-	background-color: #e0f2be;
-	color: #374e0c;
-	text-decoration: none;
-}
-
-#qunit-tests ins {
-	background-color: #ffcaca;
-	color: #500;
-	text-decoration: none;
-}
-
-/*** Test Counts */
-
-#qunit-tests b.counts                       { color: black; }
-#qunit-tests b.passed                       { color: #5E740B; }
-#qunit-tests b.failed                       { color: #710909; }
-
-#qunit-tests li li {
-	padding: 5px;
-	background-color: #fff;
-	border-bottom: none;
-	list-style-position: inside;
-}
-
-/*** Passing Styles */
-
-#qunit-tests li li.pass {
-	color: #3c510c;
-	background-color: #fff;
-	border-left: 10px solid #C6E746;
-}
-
-#qunit-tests .pass                          { color: #528CE0; background-color: #D2E0E6; }
-#qunit-tests .pass .test-name               { color: #366097; }
-
-#qunit-tests .pass .test-actual,
-#qunit-tests .pass .test-expected           { color: #999999; }
-
-#qunit-banner.qunit-pass                    { background-color: #C6E746; }
-
-/*** Failing Styles */
-
-#qunit-tests li li.fail {
-	color: #710909;
-	background-color: #fff;
-	border-left: 10px solid #EE5757;
-	white-space: pre;
-}
-
-#qunit-tests > li:last-child {
-	border-radius: 0 0 5px 5px;
-	-moz-border-radius: 0 0 5px 5px;
-	-webkit-border-bottom-right-radius: 5px;
-	-webkit-border-bottom-left-radius: 5px;
-}
-
-#qunit-tests .fail                          { color: #000000; background-color: #EE5757; }
-#qunit-tests .fail .test-name,
-#qunit-tests .fail .module-name             { color: #000000; }
-
-#qunit-tests .fail .test-actual             { color: #EE5757; }
-#qunit-tests .fail .test-expected           { color: green;   }
-
-#qunit-banner.qunit-fail                    { background-color: #EE5757; }
-
-
-/** Result */
-
-#qunit-testresult {
-	padding: 0.5em 0.5em 0.5em 2.5em;
-
-	color: #2b81af;
-	background-color: #D2E0E6;
-
-	border-bottom: 1px solid white;
-}
-#qunit-testresult .module-name {
-	font-weight: bold;
-}
-
-/** Fixture */
-
-#qunit-fixture {
-	position: absolute;
-	top: -10000px;
-	left: -10000px;
-	width: 1000px;
-	height: 1000px;
-}
diff --git a/civicrm/bower_components/qunit/qunit/qunit.js b/civicrm/bower_components/qunit/qunit/qunit.js
deleted file mode 100644
index d4f17b5ae571ee985b5df967e3af1a36a75a5a3f..0000000000000000000000000000000000000000
--- a/civicrm/bower_components/qunit/qunit/qunit.js
+++ /dev/null
@@ -1,1977 +0,0 @@
-/**
- * QUnit v1.10.0 - A JavaScript Unit Testing Framework
- *
- * http://qunitjs.com
- *
- * Copyright 2012 jQuery Foundation and other contributors
- * Released under the MIT license.
- * http://jquery.org/license
- */
-
-(function( window ) {
-
-var QUnit,
-	config,
-	onErrorFnPrev,
-	testId = 0,
-	fileName = (sourceFromStacktrace( 0 ) || "" ).replace(/(:\d+)+\)?/, "").replace(/.+\//, ""),
-	toString = Object.prototype.toString,
-	hasOwn = Object.prototype.hasOwnProperty,
-	// Keep a local reference to Date (GH-283)
-	Date = window.Date,
-	defined = {
-	setTimeout: typeof window.setTimeout !== "undefined",
-	sessionStorage: (function() {
-		var x = "qunit-test-string";
-		try {
-			sessionStorage.setItem( x, x );
-			sessionStorage.removeItem( x );
-			return true;
-		} catch( e ) {
-			return false;
-		}
-	}())
-};
-
-function Test( settings ) {
-	extend( this, settings );
-	this.assertions = [];
-	this.testNumber = ++Test.count;
-}
-
-Test.count = 0;
-
-Test.prototype = {
-	init: function() {
-		var a, b, li,
-        tests = id( "qunit-tests" );
-
-		if ( tests ) {
-			b = document.createElement( "strong" );
-			b.innerHTML = this.name;
-
-			// `a` initialized at top of scope
-			a = document.createElement( "a" );
-			a.innerHTML = "Rerun";
-			a.href = QUnit.url({ testNumber: this.testNumber });
-
-			li = document.createElement( "li" );
-			li.appendChild( b );
-			li.appendChild( a );
-			li.className = "running";
-			li.id = this.id = "qunit-test-output" + testId++;
-
-			tests.appendChild( li );
-		}
-	},
-	setup: function() {
-		if ( this.module !== config.previousModule ) {
-			if ( config.previousModule ) {
-				runLoggingCallbacks( "moduleDone", QUnit, {
-					name: config.previousModule,
-					failed: config.moduleStats.bad,
-					passed: config.moduleStats.all - config.moduleStats.bad,
-					total: config.moduleStats.all
-				});
-			}
-			config.previousModule = this.module;
-			config.moduleStats = { all: 0, bad: 0 };
-			runLoggingCallbacks( "moduleStart", QUnit, {
-				name: this.module
-			});
-		} else if ( config.autorun ) {
-			runLoggingCallbacks( "moduleStart", QUnit, {
-				name: this.module
-			});
-		}
-
-		config.current = this;
-
-		this.testEnvironment = extend({
-			setup: function() {},
-			teardown: function() {}
-		}, this.moduleTestEnvironment );
-
-		runLoggingCallbacks( "testStart", QUnit, {
-			name: this.testName,
-			module: this.module
-		});
-
-		// allow utility functions to access the current test environment
-		// TODO why??
-		QUnit.current_testEnvironment = this.testEnvironment;
-
-		if ( !config.pollution ) {
-			saveGlobal();
-		}
-		if ( config.notrycatch ) {
-			this.testEnvironment.setup.call( this.testEnvironment );
-			return;
-		}
-		try {
-			this.testEnvironment.setup.call( this.testEnvironment );
-		} catch( e ) {
-			QUnit.pushFailure( "Setup failed on " + this.testName + ": " + e.message, extractStacktrace( e, 1 ) );
-		}
-	},
-	run: function() {
-		config.current = this;
-
-		var running = id( "qunit-testresult" );
-
-		if ( running ) {
-			running.innerHTML = "Running: <br/>" + this.name;
-		}
-
-		if ( this.async ) {
-			QUnit.stop();
-		}
-
-		if ( config.notrycatch ) {
-			this.callback.call( this.testEnvironment, QUnit.assert );
-			return;
-		}
-
-		try {
-			this.callback.call( this.testEnvironment, QUnit.assert );
-		} catch( e ) {
-			QUnit.pushFailure( "Died on test #" + (this.assertions.length + 1) + " " + this.stack + ": " + e.message, extractStacktrace( e, 0 ) );
-			// else next test will carry the responsibility
-			saveGlobal();
-
-			// Restart the tests if they're blocking
-			if ( config.blocking ) {
-				QUnit.start();
-			}
-		}
-	},
-	teardown: function() {
-		config.current = this;
-		if ( config.notrycatch ) {
-			this.testEnvironment.teardown.call( this.testEnvironment );
-			return;
-		} else {
-			try {
-				this.testEnvironment.teardown.call( this.testEnvironment );
-			} catch( e ) {
-				QUnit.pushFailure( "Teardown failed on " + this.testName + ": " + e.message, extractStacktrace( e, 1 ) );
-			}
-		}
-		checkPollution();
-	},
-	finish: function() {
-		config.current = this;
-		if ( config.requireExpects && this.expected == null ) {
-			QUnit.pushFailure( "Expected number of assertions to be defined, but expect() was not called.", this.stack );
-		} else if ( this.expected != null && this.expected != this.assertions.length ) {
-			QUnit.pushFailure( "Expected " + this.expected + " assertions, but " + this.assertions.length + " were run", this.stack );
-		} else if ( this.expected == null && !this.assertions.length ) {
-			QUnit.pushFailure( "Expected at least one assertion, but none were run - call expect(0) to accept zero assertions.", this.stack );
-		}
-
-		var assertion, a, b, i, li, ol,
-			test = this,
-			good = 0,
-			bad = 0,
-			tests = id( "qunit-tests" );
-
-		config.stats.all += this.assertions.length;
-		config.moduleStats.all += this.assertions.length;
-
-		if ( tests ) {
-			ol = document.createElement( "ol" );
-
-			for ( i = 0; i < this.assertions.length; i++ ) {
-				assertion = this.assertions[i];
-
-				li = document.createElement( "li" );
-				li.className = assertion.result ? "pass" : "fail";
-				li.innerHTML = assertion.message || ( assertion.result ? "okay" : "failed" );
-				ol.appendChild( li );
-
-				if ( assertion.result ) {
-					good++;
-				} else {
-					bad++;
-					config.stats.bad++;
-					config.moduleStats.bad++;
-				}
-			}
-
-			// store result when possible
-			if ( QUnit.config.reorder && defined.sessionStorage ) {
-				if ( bad ) {
-					sessionStorage.setItem( "qunit-test-" + this.module + "-" + this.testName, bad );
-				} else {
-					sessionStorage.removeItem( "qunit-test-" + this.module + "-" + this.testName );
-				}
-			}
-
-			if ( bad === 0 ) {
-				ol.style.display = "none";
-			}
-
-			// `b` initialized at top of scope
-			b = document.createElement( "strong" );
-			b.innerHTML = this.name + " <b class='counts'>(<b class='failed'>" + bad + "</b>, <b class='passed'>" + good + "</b>, " + this.assertions.length + ")</b>";
-
-			addEvent(b, "click", function() {
-				var next = b.nextSibling.nextSibling,
-					display = next.style.display;
-				next.style.display = display === "none" ? "block" : "none";
-			});
-
-			addEvent(b, "dblclick", function( e ) {
-				var target = e && e.target ? e.target : window.event.srcElement;
-				if ( target.nodeName.toLowerCase() == "span" || target.nodeName.toLowerCase() == "b" ) {
-					target = target.parentNode;
-				}
-				if ( window.location && target.nodeName.toLowerCase() === "strong" ) {
-					window.location = QUnit.url({ testNumber: test.testNumber });
-				}
-			});
-
-			// `li` initialized at top of scope
-			li = id( this.id );
-			li.className = bad ? "fail" : "pass";
-			li.removeChild( li.firstChild );
-			a = li.firstChild;
-			li.appendChild( b );
-			li.appendChild ( a );
-			li.appendChild( ol );
-
-		} else {
-			for ( i = 0; i < this.assertions.length; i++ ) {
-				if ( !this.assertions[i].result ) {
-					bad++;
-					config.stats.bad++;
-					config.moduleStats.bad++;
-				}
-			}
-		}
-
-		runLoggingCallbacks( "testDone", QUnit, {
-			name: this.testName,
-			module: this.module,
-			failed: bad,
-			passed: this.assertions.length - bad,
-			total: this.assertions.length
-		});
-
-		QUnit.reset();
-
-		config.current = undefined;
-	},
-
-	queue: function() {
-		var bad,
-			test = this;
-
-		synchronize(function() {
-			test.init();
-		});
-		function run() {
-			// each of these can by async
-			synchronize(function() {
-				test.setup();
-			});
-			synchronize(function() {
-				test.run();
-			});
-			synchronize(function() {
-				test.teardown();
-			});
-			synchronize(function() {
-				test.finish();
-			});
-		}
-
-		// `bad` initialized at top of scope
-		// defer when previous test run passed, if storage is available
-		bad = QUnit.config.reorder && defined.sessionStorage &&
-						+sessionStorage.getItem( "qunit-test-" + this.module + "-" + this.testName );
-
-		if ( bad ) {
-			run();
-		} else {
-			synchronize( run, true );
-		}
-	}
-};
-
-// Root QUnit object.
-// `QUnit` initialized at top of scope
-QUnit = {
-
-	// call on start of module test to prepend name to all tests
-	module: function( name, testEnvironment ) {
-		config.currentModule = name;
-		config.currentModuleTestEnvironment = testEnvironment;
-		config.modules[name] = true;
-	},
-
-	asyncTest: function( testName, expected, callback ) {
-		if ( arguments.length === 2 ) {
-			callback = expected;
-			expected = null;
-		}
-
-		QUnit.test( testName, expected, callback, true );
-	},
-
-	test: function( testName, expected, callback, async ) {
-		var test,
-			name = "<span class='test-name'>" + escapeInnerText( testName ) + "</span>";
-
-		if ( arguments.length === 2 ) {
-			callback = expected;
-			expected = null;
-		}
-
-		if ( config.currentModule ) {
-			name = "<span class='module-name'>" + config.currentModule + "</span>: " + name;
-		}
-
-		test = new Test({
-			name: name,
-			testName: testName,
-			expected: expected,
-			async: async,
-			callback: callback,
-			module: config.currentModule,
-			moduleTestEnvironment: config.currentModuleTestEnvironment,
-			stack: sourceFromStacktrace( 2 )
-		});
-
-		if ( !validTest( test ) ) {
-			return;
-		}
-
-		test.queue();
-	},
-
-	// Specify the number of expected assertions to gurantee that failed test (no assertions are run at all) don't slip through.
-	expect: function( asserts ) {
-		if (arguments.length === 1) {
-			config.current.expected = asserts;
-		} else {
-			return config.current.expected;
-		}
-	},
-
-	start: function( count ) {
-		config.semaphore -= count || 1;
-		// don't start until equal number of stop-calls
-		if ( config.semaphore > 0 ) {
-			return;
-		}
-		// ignore if start is called more often then stop
-		if ( config.semaphore < 0 ) {
-			config.semaphore = 0;
-		}
-		// A slight delay, to avoid any current callbacks
-		if ( defined.setTimeout ) {
-			window.setTimeout(function() {
-				if ( config.semaphore > 0 ) {
-					return;
-				}
-				if ( config.timeout ) {
-					clearTimeout( config.timeout );
-				}
-
-				config.blocking = false;
-				process( true );
-			}, 13);
-		} else {
-			config.blocking = false;
-			process( true );
-		}
-	},
-
-	stop: function( count ) {
-		config.semaphore += count || 1;
-		config.blocking = true;
-
-		if ( config.testTimeout && defined.setTimeout ) {
-			clearTimeout( config.timeout );
-			config.timeout = window.setTimeout(function() {
-				QUnit.ok( false, "Test timed out" );
-				config.semaphore = 1;
-				QUnit.start();
-			}, config.testTimeout );
-		}
-	}
-};
-
-// Asssert helpers
-// All of these must call either QUnit.push() or manually do:
-// - runLoggingCallbacks( "log", .. );
-// - config.current.assertions.push({ .. });
-QUnit.assert = {
-	/**
-	 * Asserts rough true-ish result.
-	 * @name ok
-	 * @function
-	 * @example ok( "asdfasdf".length > 5, "There must be at least 5 chars" );
-	 */
-	ok: function( result, msg ) {
-		if ( !config.current ) {
-			throw new Error( "ok() assertion outside test context, was " + sourceFromStacktrace(2) );
-		}
-		result = !!result;
-
-		var source,
-			details = {
-				module: config.current.module,
-				name: config.current.testName,
-				result: result,
-				message: msg
-			};
-
-		msg = escapeInnerText( msg || (result ? "okay" : "failed" ) );
-		msg = "<span class='test-message'>" + msg + "</span>";
-
-		if ( !result ) {
-			source = sourceFromStacktrace( 2 );
-			if ( source ) {
-				details.source = source;
-				msg += "<table><tr class='test-source'><th>Source: </th><td><pre>" + escapeInnerText( source ) + "</pre></td></tr></table>";
-			}
-		}
-		runLoggingCallbacks( "log", QUnit, details );
-		config.current.assertions.push({
-			result: result,
-			message: msg
-		});
-	},
-
-	/**
-	 * Assert that the first two arguments are equal, with an optional message.
-	 * Prints out both actual and expected values.
-	 * @name equal
-	 * @function
-	 * @example equal( format( "Received {0} bytes.", 2), "Received 2 bytes.", "format() replaces {0} with next argument" );
-	 */
-	equal: function( actual, expected, message ) {
-		QUnit.push( expected == actual, actual, expected, message );
-	},
-
-	/**
-	 * @name notEqual
-	 * @function
-	 */
-	notEqual: function( actual, expected, message ) {
-		QUnit.push( expected != actual, actual, expected, message );
-	},
-
-	/**
-	 * @name deepEqual
-	 * @function
-	 */
-	deepEqual: function( actual, expected, message ) {
-		QUnit.push( QUnit.equiv(actual, expected), actual, expected, message );
-	},
-
-	/**
-	 * @name notDeepEqual
-	 * @function
-	 */
-	notDeepEqual: function( actual, expected, message ) {
-		QUnit.push( !QUnit.equiv(actual, expected), actual, expected, message );
-	},
-
-	/**
-	 * @name strictEqual
-	 * @function
-	 */
-	strictEqual: function( actual, expected, message ) {
-		QUnit.push( expected === actual, actual, expected, message );
-	},
-
-	/**
-	 * @name notStrictEqual
-	 * @function
-	 */
-	notStrictEqual: function( actual, expected, message ) {
-		QUnit.push( expected !== actual, actual, expected, message );
-	},
-
-	throws: function( block, expected, message ) {
-		var actual,
-			ok = false;
-
-		// 'expected' is optional
-		if ( typeof expected === "string" ) {
-			message = expected;
-			expected = null;
-		}
-
-		config.current.ignoreGlobalErrors = true;
-		try {
-			block.call( config.current.testEnvironment );
-		} catch (e) {
-			actual = e;
-		}
-		config.current.ignoreGlobalErrors = false;
-
-		if ( actual ) {
-			// we don't want to validate thrown error
-			if ( !expected ) {
-				ok = true;
-			// expected is a regexp
-			} else if ( QUnit.objectType( expected ) === "regexp" ) {
-				ok = expected.test( actual );
-			// expected is a constructor
-			} else if ( actual instanceof expected ) {
-				ok = true;
-			// expected is a validation function which returns true is validation passed
-			} else if ( expected.call( {}, actual ) === true ) {
-				ok = true;
-			}
-
-			QUnit.push( ok, actual, null, message );
-		} else {
-			QUnit.pushFailure( message, null, 'No exception was thrown.' );
-		}
-	}
-};
-
-/**
- * @deprecate since 1.8.0
- * Kept assertion helpers in root for backwards compatibility
- */
-extend( QUnit, QUnit.assert );
-
-/**
- * @deprecated since 1.9.0
- * Kept global "raises()" for backwards compatibility
- */
-QUnit.raises = QUnit.assert.throws;
-
-/**
- * @deprecated since 1.0.0, replaced with error pushes since 1.3.0
- * Kept to avoid TypeErrors for undefined methods.
- */
-QUnit.equals = function() {
-	QUnit.push( false, false, false, "QUnit.equals has been deprecated since 2009 (e88049a0), use QUnit.equal instead" );
-};
-QUnit.same = function() {
-	QUnit.push( false, false, false, "QUnit.same has been deprecated since 2009 (e88049a0), use QUnit.deepEqual instead" );
-};
-
-// We want access to the constructor's prototype
-(function() {
-	function F() {}
-	F.prototype = QUnit;
-	QUnit = new F();
-	// Make F QUnit's constructor so that we can add to the prototype later
-	QUnit.constructor = F;
-}());
-
-/**
- * Config object: Maintain internal state
- * Later exposed as QUnit.config
- * `config` initialized at top of scope
- */
-config = {
-	// The queue of tests to run
-	queue: [],
-
-	// block until document ready
-	blocking: true,
-
-	// when enabled, show only failing tests
-	// gets persisted through sessionStorage and can be changed in UI via checkbox
-	hidepassed: false,
-
-	// by default, run previously failed tests first
-	// very useful in combination with "Hide passed tests" checked
-	reorder: true,
-
-	// by default, modify document.title when suite is done
-	altertitle: true,
-
-	// when enabled, all tests must call expect()
-	requireExpects: false,
-
-	// add checkboxes that are persisted in the query-string
-	// when enabled, the id is set to `true` as a `QUnit.config` property
-	urlConfig: [
-		{
-			id: "noglobals",
-			label: "Check for Globals",
-			tooltip: "Enabling this will test if any test introduces new properties on the `window` object. Stored as query-strings."
-		},
-		{
-			id: "notrycatch",
-			label: "No try-catch",
-			tooltip: "Enabling this will run tests outside of a try-catch block. Makes debugging exceptions in IE reasonable. Stored as query-strings."
-		}
-	],
-
-	// Set of all modules.
-	modules: {},
-
-	// logging callback queues
-	begin: [],
-	done: [],
-	log: [],
-	testStart: [],
-	testDone: [],
-	moduleStart: [],
-	moduleDone: []
-};
-
-// Initialize more QUnit.config and QUnit.urlParams
-(function() {
-	var i,
-		location = window.location || { search: "", protocol: "file:" },
-		params = location.search.slice( 1 ).split( "&" ),
-		length = params.length,
-		urlParams = {},
-		current;
-
-	if ( params[ 0 ] ) {
-		for ( i = 0; i < length; i++ ) {
-			current = params[ i ].split( "=" );
-			current[ 0 ] = decodeURIComponent( current[ 0 ] );
-			// allow just a key to turn on a flag, e.g., test.html?noglobals
-			current[ 1 ] = current[ 1 ] ? decodeURIComponent( current[ 1 ] ) : true;
-			urlParams[ current[ 0 ] ] = current[ 1 ];
-		}
-	}
-
-	QUnit.urlParams = urlParams;
-
-	// String search anywhere in moduleName+testName
-	config.filter = urlParams.filter;
-
-	// Exact match of the module name
-	config.module = urlParams.module;
-
-	config.testNumber = parseInt( urlParams.testNumber, 10 ) || null;
-
-	// Figure out if we're running the tests from a server or not
-	QUnit.isLocal = location.protocol === "file:";
-}());
-
-// Export global variables, unless an 'exports' object exists,
-// in that case we assume we're in CommonJS (dealt with on the bottom of the script)
-if ( typeof exports === "undefined" ) {
-	extend( window, QUnit );
-
-	// Expose QUnit object
-	window.QUnit = QUnit;
-}
-
-// Extend QUnit object,
-// these after set here because they should not be exposed as global functions
-extend( QUnit, {
-	config: config,
-
-	// Initialize the configuration options
-	init: function() {
-		extend( config, {
-			stats: { all: 0, bad: 0 },
-			moduleStats: { all: 0, bad: 0 },
-			started: +new Date(),
-			updateRate: 1000,
-			blocking: false,
-			autostart: true,
-			autorun: false,
-			filter: "",
-			queue: [],
-			semaphore: 0
-		});
-
-		var tests, banner, result,
-			qunit = id( "qunit" );
-
-		if ( qunit ) {
-			qunit.innerHTML =
-				"<h1 id='qunit-header'>" + escapeInnerText( document.title ) + "</h1>" +
-				"<h2 id='qunit-banner'></h2>" +
-				"<div id='qunit-testrunner-toolbar'></div>" +
-				"<h2 id='qunit-userAgent'></h2>" +
-				"<ol id='qunit-tests'></ol>";
-		}
-
-		tests = id( "qunit-tests" );
-		banner = id( "qunit-banner" );
-		result = id( "qunit-testresult" );
-
-		if ( tests ) {
-			tests.innerHTML = "";
-		}
-
-		if ( banner ) {
-			banner.className = "";
-		}
-
-		if ( result ) {
-			result.parentNode.removeChild( result );
-		}
-
-		if ( tests ) {
-			result = document.createElement( "p" );
-			result.id = "qunit-testresult";
-			result.className = "result";
-			tests.parentNode.insertBefore( result, tests );
-			result.innerHTML = "Running...<br/>&nbsp;";
-		}
-	},
-
-	// Resets the test setup. Useful for tests that modify the DOM.
-	reset: function() {
-		var fixture = id( "qunit-fixture" );
-		if ( fixture ) {
-			fixture.innerHTML = config.fixture;
-		}
-	},
-
-	// Trigger an event on an element.
-	// @example triggerEvent( document.body, "click" );
-	triggerEvent: function( elem, type, event ) {
-		if ( document.createEvent ) {
-			event = document.createEvent( "MouseEvents" );
-			event.initMouseEvent(type, true, true, elem.ownerDocument.defaultView,
-				0, 0, 0, 0, 0, false, false, false, false, 0, null);
-
-			elem.dispatchEvent( event );
-		} else if ( elem.fireEvent ) {
-			elem.fireEvent( "on" + type );
-		}
-	},
-
-	// Safe object type checking
-	is: function( type, obj ) {
-		return QUnit.objectType( obj ) == type;
-	},
-
-	objectType: function( obj ) {
-		if ( typeof obj === "undefined" ) {
-				return "undefined";
-		// consider: typeof null === object
-		}
-		if ( obj === null ) {
-				return "null";
-		}
-
-		var type = toString.call( obj ).match(/^\[object\s(.*)\]$/)[1] || "";
-
-		switch ( type ) {
-			case "Number":
-				if ( isNaN(obj) ) {
-					return "nan";
-				}
-				return "number";
-			case "String":
-			case "Boolean":
-			case "Array":
-			case "Date":
-			case "RegExp":
-			case "Function":
-				return type.toLowerCase();
-		}
-		if ( typeof obj === "object" ) {
-			return "object";
-		}
-		return undefined;
-	},
-
-	push: function( result, actual, expected, message ) {
-		if ( !config.current ) {
-			throw new Error( "assertion outside test context, was " + sourceFromStacktrace() );
-		}
-
-		var output, source,
-			details = {
-				module: config.current.module,
-				name: config.current.testName,
-				result: result,
-				message: message,
-				actual: actual,
-				expected: expected
-			};
-
-		message = escapeInnerText( message ) || ( result ? "okay" : "failed" );
-		message = "<span class='test-message'>" + message + "</span>";
-		output = message;
-
-		if ( !result ) {
-			expected = escapeInnerText( QUnit.jsDump.parse(expected) );
-			actual = escapeInnerText( QUnit.jsDump.parse(actual) );
-			output += "<table><tr class='test-expected'><th>Expected: </th><td><pre>" + expected + "</pre></td></tr>";
-
-			if ( actual != expected ) {
-				output += "<tr class='test-actual'><th>Result: </th><td><pre>" + actual + "</pre></td></tr>";
-				output += "<tr class='test-diff'><th>Diff: </th><td><pre>" + QUnit.diff( expected, actual ) + "</pre></td></tr>";
-			}
-
-			source = sourceFromStacktrace();
-
-			if ( source ) {
-				details.source = source;
-				output += "<tr class='test-source'><th>Source: </th><td><pre>" + escapeInnerText( source ) + "</pre></td></tr>";
-			}
-
-			output += "</table>";
-		}
-
-		runLoggingCallbacks( "log", QUnit, details );
-
-		config.current.assertions.push({
-			result: !!result,
-			message: output
-		});
-	},
-
-	pushFailure: function( message, source, actual ) {
-		if ( !config.current ) {
-			throw new Error( "pushFailure() assertion outside test context, was " + sourceFromStacktrace(2) );
-		}
-
-		var output,
-			details = {
-				module: config.current.module,
-				name: config.current.testName,
-				result: false,
-				message: message
-			};
-
-		message = escapeInnerText( message ) || "error";
-		message = "<span class='test-message'>" + message + "</span>";
-		output = message;
-
-		output += "<table>";
-
-		if ( actual ) {
-			output += "<tr class='test-actual'><th>Result: </th><td><pre>" + escapeInnerText( actual ) + "</pre></td></tr>";
-		}
-
-		if ( source ) {
-			details.source = source;
-			output += "<tr class='test-source'><th>Source: </th><td><pre>" + escapeInnerText( source ) + "</pre></td></tr>";
-		}
-
-		output += "</table>";
-
-		runLoggingCallbacks( "log", QUnit, details );
-
-		config.current.assertions.push({
-			result: false,
-			message: output
-		});
-	},
-
-	url: function( params ) {
-		params = extend( extend( {}, QUnit.urlParams ), params );
-		var key,
-			querystring = "?";
-
-		for ( key in params ) {
-			if ( !hasOwn.call( params, key ) ) {
-				continue;
-			}
-			querystring += encodeURIComponent( key ) + "=" +
-				encodeURIComponent( params[ key ] ) + "&";
-		}
-		return window.location.pathname + querystring.slice( 0, -1 );
-	},
-
-	extend: extend,
-	id: id,
-	addEvent: addEvent
-	// load, equiv, jsDump, diff: Attached later
-});
-
-/**
- * @deprecated: Created for backwards compatibility with test runner that set the hook function
- * into QUnit.{hook}, instead of invoking it and passing the hook function.
- * QUnit.constructor is set to the empty F() above so that we can add to it's prototype here.
- * Doing this allows us to tell if the following methods have been overwritten on the actual
- * QUnit object.
- */
-extend( QUnit.constructor.prototype, {
-
-	// Logging callbacks; all receive a single argument with the listed properties
-	// run test/logs.html for any related changes
-	begin: registerLoggingCallback( "begin" ),
-
-	// done: { failed, passed, total, runtime }
-	done: registerLoggingCallback( "done" ),
-
-	// log: { result, actual, expected, message }
-	log: registerLoggingCallback( "log" ),
-
-	// testStart: { name }
-	testStart: registerLoggingCallback( "testStart" ),
-
-	// testDone: { name, failed, passed, total }
-	testDone: registerLoggingCallback( "testDone" ),
-
-	// moduleStart: { name }
-	moduleStart: registerLoggingCallback( "moduleStart" ),
-
-	// moduleDone: { name, failed, passed, total }
-	moduleDone: registerLoggingCallback( "moduleDone" )
-});
-
-if ( typeof document === "undefined" || document.readyState === "complete" ) {
-	config.autorun = true;
-}
-
-QUnit.load = function() {
-	runLoggingCallbacks( "begin", QUnit, {} );
-
-	// Initialize the config, saving the execution queue
-	var banner, filter, i, label, len, main, ol, toolbar, userAgent, val, urlConfigCheckboxes, moduleFilter,
-	    numModules = 0,
-	    moduleFilterHtml = "",
-		urlConfigHtml = "",
-		oldconfig = extend( {}, config );
-
-	QUnit.init();
-	extend(config, oldconfig);
-
-	config.blocking = false;
-
-	len = config.urlConfig.length;
-
-	for ( i = 0; i < len; i++ ) {
-		val = config.urlConfig[i];
-		if ( typeof val === "string" ) {
-			val = {
-				id: val,
-				label: val,
-				tooltip: "[no tooltip available]"
-			};
-		}
-		config[ val.id ] = QUnit.urlParams[ val.id ];
-		urlConfigHtml += "<input id='qunit-urlconfig-" + val.id + "' name='" + val.id + "' type='checkbox'" + ( config[ val.id ] ? " checked='checked'" : "" ) + " title='" + val.tooltip + "'><label for='qunit-urlconfig-" + val.id + "' title='" + val.tooltip + "'>" + val.label + "</label>";
-	}
-
-	moduleFilterHtml += "<label for='qunit-modulefilter'>Module: </label><select id='qunit-modulefilter' name='modulefilter'><option value='' " + ( config.module === undefined  ? "selected" : "" ) + ">< All Modules ></option>";
-	for ( i in config.modules ) {
-		if ( config.modules.hasOwnProperty( i ) ) {
-			numModules += 1;
-			moduleFilterHtml += "<option value='" + encodeURIComponent(i) + "' " + ( config.module === i ? "selected" : "" ) + ">" + i + "</option>";
-		}
-	}
-	moduleFilterHtml += "</select>";
-
-	// `userAgent` initialized at top of scope
-	userAgent = id( "qunit-userAgent" );
-	if ( userAgent ) {
-		userAgent.innerHTML = navigator.userAgent;
-	}
-
-	// `banner` initialized at top of scope
-	banner = id( "qunit-header" );
-	if ( banner ) {
-		banner.innerHTML = "<a href='" + QUnit.url({ filter: undefined, module: undefined, testNumber: undefined }) + "'>" + banner.innerHTML + "</a> ";
-	}
-
-	// `toolbar` initialized at top of scope
-	toolbar = id( "qunit-testrunner-toolbar" );
-	if ( toolbar ) {
-		// `filter` initialized at top of scope
-		filter = document.createElement( "input" );
-		filter.type = "checkbox";
-		filter.id = "qunit-filter-pass";
-
-		addEvent( filter, "click", function() {
-			var tmp,
-				ol = document.getElementById( "qunit-tests" );
-
-			if ( filter.checked ) {
-				ol.className = ol.className + " hidepass";
-			} else {
-				tmp = " " + ol.className.replace( /[\n\t\r]/g, " " ) + " ";
-				ol.className = tmp.replace( / hidepass /, " " );
-			}
-			if ( defined.sessionStorage ) {
-				if (filter.checked) {
-					sessionStorage.setItem( "qunit-filter-passed-tests", "true" );
-				} else {
-					sessionStorage.removeItem( "qunit-filter-passed-tests" );
-				}
-			}
-		});
-
-		if ( config.hidepassed || defined.sessionStorage && sessionStorage.getItem( "qunit-filter-passed-tests" ) ) {
-			filter.checked = true;
-			// `ol` initialized at top of scope
-			ol = document.getElementById( "qunit-tests" );
-			ol.className = ol.className + " hidepass";
-		}
-		toolbar.appendChild( filter );
-
-		// `label` initialized at top of scope
-		label = document.createElement( "label" );
-		label.setAttribute( "for", "qunit-filter-pass" );
-		label.setAttribute( "title", "Only show tests and assertons that fail. Stored in sessionStorage." );
-		label.innerHTML = "Hide passed tests";
-		toolbar.appendChild( label );
-
-		urlConfigCheckboxes = document.createElement( 'span' );
-		urlConfigCheckboxes.innerHTML = urlConfigHtml;
-		addEvent( urlConfigCheckboxes, "change", function( event ) {
-			var params = {};
-			params[ event.target.name ] = event.target.checked ? true : undefined;
-			window.location = QUnit.url( params );
-		});
-		toolbar.appendChild( urlConfigCheckboxes );
-
-		if (numModules > 1) {
-			moduleFilter = document.createElement( 'span' );
-			moduleFilter.setAttribute( 'id', 'qunit-modulefilter-container' );
-			moduleFilter.innerHTML = moduleFilterHtml;
-			addEvent( moduleFilter, "change", function() {
-				var selectBox = moduleFilter.getElementsByTagName("select")[0],
-				    selectedModule = decodeURIComponent(selectBox.options[selectBox.selectedIndex].value);
-
-				window.location = QUnit.url( { module: ( selectedModule === "" ) ? undefined : selectedModule } );
-			});
-			toolbar.appendChild(moduleFilter);
-		}
-	}
-
-	// `main` initialized at top of scope
-	main = id( "qunit-fixture" );
-	if ( main ) {
-		config.fixture = main.innerHTML;
-	}
-
-	if ( config.autostart ) {
-		QUnit.start();
-	}
-};
-
-addEvent( window, "load", QUnit.load );
-
-// `onErrorFnPrev` initialized at top of scope
-// Preserve other handlers
-onErrorFnPrev = window.onerror;
-
-// Cover uncaught exceptions
-// Returning true will surpress the default browser handler,
-// returning false will let it run.
-window.onerror = function ( error, filePath, linerNr ) {
-	var ret = false;
-	if ( onErrorFnPrev ) {
-		ret = onErrorFnPrev( error, filePath, linerNr );
-	}
-
-	// Treat return value as window.onerror itself does,
-	// Only do our handling if not surpressed.
-	if ( ret !== true ) {
-		if ( QUnit.config.current ) {
-			if ( QUnit.config.current.ignoreGlobalErrors ) {
-				return true;
-			}
-			QUnit.pushFailure( error, filePath + ":" + linerNr );
-		} else {
-			QUnit.test( "global failure", extend( function() {
-				QUnit.pushFailure( error, filePath + ":" + linerNr );
-			}, { validTest: validTest } ) );
-		}
-		return false;
-	}
-
-	return ret;
-};
-
-function done() {
-	config.autorun = true;
-
-	// Log the last module results
-	if ( config.currentModule ) {
-		runLoggingCallbacks( "moduleDone", QUnit, {
-			name: config.currentModule,
-			failed: config.moduleStats.bad,
-			passed: config.moduleStats.all - config.moduleStats.bad,
-			total: config.moduleStats.all
-		});
-	}
-
-	var i, key,
-		banner = id( "qunit-banner" ),
-		tests = id( "qunit-tests" ),
-		runtime = +new Date() - config.started,
-		passed = config.stats.all - config.stats.bad,
-		html = [
-			"Tests completed in ",
-			runtime,
-			" milliseconds.<br/>",
-			"<span class='passed'>",
-			passed,
-			"</span> tests of <span class='total'>",
-			config.stats.all,
-			"</span> passed, <span class='failed'>",
-			config.stats.bad,
-			"</span> failed."
-		].join( "" );
-
-	if ( banner ) {
-		banner.className = ( config.stats.bad ? "qunit-fail" : "qunit-pass" );
-	}
-
-	if ( tests ) {
-		id( "qunit-testresult" ).innerHTML = html;
-	}
-
-	if ( config.altertitle && typeof document !== "undefined" && document.title ) {
-		// show ✖ for good, ✔ for bad suite result in title
-		// use escape sequences in case file gets loaded with non-utf-8-charset
-		document.title = [
-			( config.stats.bad ? "\u2716" : "\u2714" ),
-			document.title.replace( /^[\u2714\u2716] /i, "" )
-		].join( " " );
-	}
-
-	// clear own sessionStorage items if all tests passed
-	if ( config.reorder && defined.sessionStorage && config.stats.bad === 0 ) {
-		// `key` & `i` initialized at top of scope
-		for ( i = 0; i < sessionStorage.length; i++ ) {
-			key = sessionStorage.key( i++ );
-			if ( key.indexOf( "qunit-test-" ) === 0 ) {
-				sessionStorage.removeItem( key );
-			}
-		}
-	}
-
-	// scroll back to top to show results
-	if ( window.scrollTo ) {
-		window.scrollTo(0, 0);
-	}
-
-	runLoggingCallbacks( "done", QUnit, {
-		failed: config.stats.bad,
-		passed: passed,
-		total: config.stats.all,
-		runtime: runtime
-	});
-}
-
-/** @return Boolean: true if this test should be ran */
-function validTest( test ) {
-	var include,
-		filter = config.filter && config.filter.toLowerCase(),
-		module = config.module && config.module.toLowerCase(),
-		fullName = (test.module + ": " + test.testName).toLowerCase();
-
-	// Internally-generated tests are always valid
-	if ( test.callback && test.callback.validTest === validTest ) {
-		delete test.callback.validTest;
-		return true;
-	}
-
-	if ( config.testNumber ) {
-		return test.testNumber === config.testNumber;
-	}
-
-	if ( module && ( !test.module || test.module.toLowerCase() !== module ) ) {
-		return false;
-	}
-
-	if ( !filter ) {
-		return true;
-	}
-
-	include = filter.charAt( 0 ) !== "!";
-	if ( !include ) {
-		filter = filter.slice( 1 );
-	}
-
-	// If the filter matches, we need to honour include
-	if ( fullName.indexOf( filter ) !== -1 ) {
-		return include;
-	}
-
-	// Otherwise, do the opposite
-	return !include;
-}
-
-// so far supports only Firefox, Chrome and Opera (buggy), Safari (for real exceptions)
-// Later Safari and IE10 are supposed to support error.stack as well
-// See also https://developer.mozilla.org/en/JavaScript/Reference/Global_Objects/Error/Stack
-function extractStacktrace( e, offset ) {
-	offset = offset === undefined ? 3 : offset;
-
-	var stack, include, i, regex;
-
-	if ( e.stacktrace ) {
-		// Opera
-		return e.stacktrace.split( "\n" )[ offset + 3 ];
-	} else if ( e.stack ) {
-		// Firefox, Chrome
-		stack = e.stack.split( "\n" );
-		if (/^error$/i.test( stack[0] ) ) {
-			stack.shift();
-		}
-		if ( fileName ) {
-			include = [];
-			for ( i = offset; i < stack.length; i++ ) {
-				if ( stack[ i ].indexOf( fileName ) != -1 ) {
-					break;
-				}
-				include.push( stack[ i ] );
-			}
-			if ( include.length ) {
-				return include.join( "\n" );
-			}
-		}
-		return stack[ offset ];
-	} else if ( e.sourceURL ) {
-		// Safari, PhantomJS
-		// hopefully one day Safari provides actual stacktraces
-		// exclude useless self-reference for generated Error objects
-		if ( /qunit.js$/.test( e.sourceURL ) ) {
-			return;
-		}
-		// for actual exceptions, this is useful
-		return e.sourceURL + ":" + e.line;
-	}
-}
-function sourceFromStacktrace( offset ) {
-	try {
-		throw new Error();
-	} catch ( e ) {
-		return extractStacktrace( e, offset );
-	}
-}
-
-function escapeInnerText( s ) {
-	if ( !s ) {
-		return "";
-	}
-	s = s + "";
-	return s.replace( /[\&<>]/g, function( s ) {
-		switch( s ) {
-			case "&": return "&amp;";
-			case "<": return "&lt;";
-			case ">": return "&gt;";
-			default: return s;
-		}
-	});
-}
-
-function synchronize( callback, last ) {
-	config.queue.push( callback );
-
-	if ( config.autorun && !config.blocking ) {
-		process( last );
-	}
-}
-
-function process( last ) {
-	function next() {
-		process( last );
-	}
-	var start = new Date().getTime();
-	config.depth = config.depth ? config.depth + 1 : 1;
-
-	while ( config.queue.length && !config.blocking ) {
-		if ( !defined.setTimeout || config.updateRate <= 0 || ( ( new Date().getTime() - start ) < config.updateRate ) ) {
-			config.queue.shift()();
-		} else {
-			window.setTimeout( next, 13 );
-			break;
-		}
-	}
-	config.depth--;
-	if ( last && !config.blocking && !config.queue.length && config.depth === 0 ) {
-		done();
-	}
-}
-
-function saveGlobal() {
-	config.pollution = [];
-
-	if ( config.noglobals ) {
-		for ( var key in window ) {
-			// in Opera sometimes DOM element ids show up here, ignore them
-			if ( !hasOwn.call( window, key ) || /^qunit-test-output/.test( key ) ) {
-				continue;
-			}
-			config.pollution.push( key );
-		}
-	}
-}
-
-function checkPollution( name ) {
-	var newGlobals,
-		deletedGlobals,
-		old = config.pollution;
-
-	saveGlobal();
-
-	newGlobals = diff( config.pollution, old );
-	if ( newGlobals.length > 0 ) {
-		QUnit.pushFailure( "Introduced global variable(s): " + newGlobals.join(", ") );
-	}
-
-	deletedGlobals = diff( old, config.pollution );
-	if ( deletedGlobals.length > 0 ) {
-		QUnit.pushFailure( "Deleted global variable(s): " + deletedGlobals.join(", ") );
-	}
-}
-
-// returns a new Array with the elements that are in a but not in b
-function diff( a, b ) {
-	var i, j,
-		result = a.slice();
-
-	for ( i = 0; i < result.length; i++ ) {
-		for ( j = 0; j < b.length; j++ ) {
-			if ( result[i] === b[j] ) {
-				result.splice( i, 1 );
-				i--;
-				break;
-			}
-		}
-	}
-	return result;
-}
-
-function extend( a, b ) {
-	for ( var prop in b ) {
-		if ( b[ prop ] === undefined ) {
-			delete a[ prop ];
-
-		// Avoid "Member not found" error in IE8 caused by setting window.constructor
-		} else if ( prop !== "constructor" || a !== window ) {
-			a[ prop ] = b[ prop ];
-		}
-	}
-
-	return a;
-}
-
-function addEvent( elem, type, fn ) {
-	if ( elem.addEventListener ) {
-		elem.addEventListener( type, fn, false );
-	} else if ( elem.attachEvent ) {
-		elem.attachEvent( "on" + type, fn );
-	} else {
-		fn();
-	}
-}
-
-function id( name ) {
-	return !!( typeof document !== "undefined" && document && document.getElementById ) &&
-		document.getElementById( name );
-}
-
-function registerLoggingCallback( key ) {
-	return function( callback ) {
-		config[key].push( callback );
-	};
-}
-
-// Supports deprecated method of completely overwriting logging callbacks
-function runLoggingCallbacks( key, scope, args ) {
-	//debugger;
-	var i, callbacks;
-	if ( QUnit.hasOwnProperty( key ) ) {
-		QUnit[ key ].call(scope, args );
-	} else {
-		callbacks = config[ key ];
-		for ( i = 0; i < callbacks.length; i++ ) {
-			callbacks[ i ].call( scope, args );
-		}
-	}
-}
-
-// Test for equality any JavaScript type.
-// Author: Philippe Rathé <prathe@gmail.com>
-QUnit.equiv = (function() {
-
-	// Call the o related callback with the given arguments.
-	function bindCallbacks( o, callbacks, args ) {
-		var prop = QUnit.objectType( o );
-		if ( prop ) {
-			if ( QUnit.objectType( callbacks[ prop ] ) === "function" ) {
-				return callbacks[ prop ].apply( callbacks, args );
-			} else {
-				return callbacks[ prop ]; // or undefined
-			}
-		}
-	}
-
-	// the real equiv function
-	var innerEquiv,
-		// stack to decide between skip/abort functions
-		callers = [],
-		// stack to avoiding loops from circular referencing
-		parents = [],
-
-		getProto = Object.getPrototypeOf || function ( obj ) {
-			return obj.__proto__;
-		},
-		callbacks = (function () {
-
-			// for string, boolean, number and null
-			function useStrictEquality( b, a ) {
-				if ( b instanceof a.constructor || a instanceof b.constructor ) {
-					// to catch short annotaion VS 'new' annotation of a
-					// declaration
-					// e.g. var i = 1;
-					// var j = new Number(1);
-					return a == b;
-				} else {
-					return a === b;
-				}
-			}
-
-			return {
-				"string": useStrictEquality,
-				"boolean": useStrictEquality,
-				"number": useStrictEquality,
-				"null": useStrictEquality,
-				"undefined": useStrictEquality,
-
-				"nan": function( b ) {
-					return isNaN( b );
-				},
-
-				"date": function( b, a ) {
-					return QUnit.objectType( b ) === "date" && a.valueOf() === b.valueOf();
-				},
-
-				"regexp": function( b, a ) {
-					return QUnit.objectType( b ) === "regexp" &&
-						// the regex itself
-						a.source === b.source &&
-						// and its modifers
-						a.global === b.global &&
-						// (gmi) ...
-						a.ignoreCase === b.ignoreCase &&
-						a.multiline === b.multiline &&
-						a.sticky === b.sticky;
-				},
-
-				// - skip when the property is a method of an instance (OOP)
-				// - abort otherwise,
-				// initial === would have catch identical references anyway
-				"function": function() {
-					var caller = callers[callers.length - 1];
-					return caller !== Object && typeof caller !== "undefined";
-				},
-
-				"array": function( b, a ) {
-					var i, j, len, loop;
-
-					// b could be an object literal here
-					if ( QUnit.objectType( b ) !== "array" ) {
-						return false;
-					}
-
-					len = a.length;
-					if ( len !== b.length ) {
-						// safe and faster
-						return false;
-					}
-
-					// track reference to avoid circular references
-					parents.push( a );
-					for ( i = 0; i < len; i++ ) {
-						loop = false;
-						for ( j = 0; j < parents.length; j++ ) {
-							if ( parents[j] === a[i] ) {
-								loop = true;// dont rewalk array
-							}
-						}
-						if ( !loop && !innerEquiv(a[i], b[i]) ) {
-							parents.pop();
-							return false;
-						}
-					}
-					parents.pop();
-					return true;
-				},
-
-				"object": function( b, a ) {
-					var i, j, loop,
-						// Default to true
-						eq = true,
-						aProperties = [],
-						bProperties = [];
-
-					// comparing constructors is more strict than using
-					// instanceof
-					if ( a.constructor !== b.constructor ) {
-						// Allow objects with no prototype to be equivalent to
-						// objects with Object as their constructor.
-						if ( !(( getProto(a) === null && getProto(b) === Object.prototype ) ||
-							( getProto(b) === null && getProto(a) === Object.prototype ) ) ) {
-								return false;
-						}
-					}
-
-					// stack constructor before traversing properties
-					callers.push( a.constructor );
-					// track reference to avoid circular references
-					parents.push( a );
-
-					for ( i in a ) { // be strict: don't ensures hasOwnProperty
-									// and go deep
-						loop = false;
-						for ( j = 0; j < parents.length; j++ ) {
-							if ( parents[j] === a[i] ) {
-								// don't go down the same path twice
-								loop = true;
-							}
-						}
-						aProperties.push(i); // collect a's properties
-
-						if (!loop && !innerEquiv( a[i], b[i] ) ) {
-							eq = false;
-							break;
-						}
-					}
-
-					callers.pop(); // unstack, we are done
-					parents.pop();
-
-					for ( i in b ) {
-						bProperties.push( i ); // collect b's properties
-					}
-
-					// Ensures identical properties name
-					return eq && innerEquiv( aProperties.sort(), bProperties.sort() );
-				}
-			};
-		}());
-
-	innerEquiv = function() { // can take multiple arguments
-		var args = [].slice.apply( arguments );
-		if ( args.length < 2 ) {
-			return true; // end transition
-		}
-
-		return (function( a, b ) {
-			if ( a === b ) {
-				return true; // catch the most you can
-			} else if ( a === null || b === null || typeof a === "undefined" ||
-					typeof b === "undefined" ||
-					QUnit.objectType(a) !== QUnit.objectType(b) ) {
-				return false; // don't lose time with error prone cases
-			} else {
-				return bindCallbacks(a, callbacks, [ b, a ]);
-			}
-
-			// apply transition with (1..n) arguments
-		}( args[0], args[1] ) && arguments.callee.apply( this, args.splice(1, args.length - 1 )) );
-	};
-
-	return innerEquiv;
-}());
-
-/**
- * jsDump Copyright (c) 2008 Ariel Flesler - aflesler(at)gmail(dot)com |
- * http://flesler.blogspot.com Licensed under BSD
- * (http://www.opensource.org/licenses/bsd-license.php) Date: 5/15/2008
- *
- * @projectDescription Advanced and extensible data dumping for Javascript.
- * @version 1.0.0
- * @author Ariel Flesler
- * @link {http://flesler.blogspot.com/2008/05/jsdump-pretty-dump-of-any-javascript.html}
- */
-QUnit.jsDump = (function() {
-	function quote( str ) {
-		return '"' + str.toString().replace( /"/g, '\\"' ) + '"';
-	}
-	function literal( o ) {
-		return o + "";
-	}
-	function join( pre, arr, post ) {
-		var s = jsDump.separator(),
-			base = jsDump.indent(),
-			inner = jsDump.indent(1);
-		if ( arr.join ) {
-			arr = arr.join( "," + s + inner );
-		}
-		if ( !arr ) {
-			return pre + post;
-		}
-		return [ pre, inner + arr, base + post ].join(s);
-	}
-	function array( arr, stack ) {
-		var i = arr.length, ret = new Array(i);
-		this.up();
-		while ( i-- ) {
-			ret[i] = this.parse( arr[i] , undefined , stack);
-		}
-		this.down();
-		return join( "[", ret, "]" );
-	}
-
-	var reName = /^function (\w+)/,
-		jsDump = {
-			parse: function( obj, type, stack ) { //type is used mostly internally, you can fix a (custom)type in advance
-				stack = stack || [ ];
-				var inStack, res,
-					parser = this.parsers[ type || this.typeOf(obj) ];
-
-				type = typeof parser;
-				inStack = inArray( obj, stack );
-
-				if ( inStack != -1 ) {
-					return "recursion(" + (inStack - stack.length) + ")";
-				}
-				//else
-				if ( type == "function" )  {
-					stack.push( obj );
-					res = parser.call( this, obj, stack );
-					stack.pop();
-					return res;
-				}
-				// else
-				return ( type == "string" ) ? parser : this.parsers.error;
-			},
-			typeOf: function( obj ) {
-				var type;
-				if ( obj === null ) {
-					type = "null";
-				} else if ( typeof obj === "undefined" ) {
-					type = "undefined";
-				} else if ( QUnit.is( "regexp", obj) ) {
-					type = "regexp";
-				} else if ( QUnit.is( "date", obj) ) {
-					type = "date";
-				} else if ( QUnit.is( "function", obj) ) {
-					type = "function";
-				} else if ( typeof obj.setInterval !== undefined && typeof obj.document !== "undefined" && typeof obj.nodeType === "undefined" ) {
-					type = "window";
-				} else if ( obj.nodeType === 9 ) {
-					type = "document";
-				} else if ( obj.nodeType ) {
-					type = "node";
-				} else if (
-					// native arrays
-					toString.call( obj ) === "[object Array]" ||
-					// NodeList objects
-					( typeof obj.length === "number" && typeof obj.item !== "undefined" && ( obj.length ? obj.item(0) === obj[0] : ( obj.item( 0 ) === null && typeof obj[0] === "undefined" ) ) )
-				) {
-					type = "array";
-				} else {
-					type = typeof obj;
-				}
-				return type;
-			},
-			separator: function() {
-				return this.multiline ?	this.HTML ? "<br />" : "\n" : this.HTML ? "&nbsp;" : " ";
-			},
-			indent: function( extra ) {// extra can be a number, shortcut for increasing-calling-decreasing
-				if ( !this.multiline ) {
-					return "";
-				}
-				var chr = this.indentChar;
-				if ( this.HTML ) {
-					chr = chr.replace( /\t/g, "   " ).replace( / /g, "&nbsp;" );
-				}
-				return new Array( this._depth_ + (extra||0) ).join(chr);
-			},
-			up: function( a ) {
-				this._depth_ += a || 1;
-			},
-			down: function( a ) {
-				this._depth_ -= a || 1;
-			},
-			setParser: function( name, parser ) {
-				this.parsers[name] = parser;
-			},
-			// The next 3 are exposed so you can use them
-			quote: quote,
-			literal: literal,
-			join: join,
-			//
-			_depth_: 1,
-			// This is the list of parsers, to modify them, use jsDump.setParser
-			parsers: {
-				window: "[Window]",
-				document: "[Document]",
-				error: "[ERROR]", //when no parser is found, shouldn"t happen
-				unknown: "[Unknown]",
-				"null": "null",
-				"undefined": "undefined",
-				"function": function( fn ) {
-					var ret = "function",
-						name = "name" in fn ? fn.name : (reName.exec(fn) || [])[1];//functions never have name in IE
-
-					if ( name ) {
-						ret += " " + name;
-					}
-					ret += "( ";
-
-					ret = [ ret, QUnit.jsDump.parse( fn, "functionArgs" ), "){" ].join( "" );
-					return join( ret, QUnit.jsDump.parse(fn,"functionCode" ), "}" );
-				},
-				array: array,
-				nodelist: array,
-				"arguments": array,
-				object: function( map, stack ) {
-					var ret = [ ], keys, key, val, i;
-					QUnit.jsDump.up();
-					if ( Object.keys ) {
-						keys = Object.keys( map );
-					} else {
-						keys = [];
-						for ( key in map ) {
-							keys.push( key );
-						}
-					}
-					keys.sort();
-					for ( i = 0; i < keys.length; i++ ) {
-						key = keys[ i ];
-						val = map[ key ];
-						ret.push( QUnit.jsDump.parse( key, "key" ) + ": " + QUnit.jsDump.parse( val, undefined, stack ) );
-					}
-					QUnit.jsDump.down();
-					return join( "{", ret, "}" );
-				},
-				node: function( node ) {
-					var a, val,
-						open = QUnit.jsDump.HTML ? "&lt;" : "<",
-						close = QUnit.jsDump.HTML ? "&gt;" : ">",
-						tag = node.nodeName.toLowerCase(),
-						ret = open + tag;
-
-					for ( a in QUnit.jsDump.DOMAttrs ) {
-						val = node[ QUnit.jsDump.DOMAttrs[a] ];
-						if ( val ) {
-							ret += " " + a + "=" + QUnit.jsDump.parse( val, "attribute" );
-						}
-					}
-					return ret + close + open + "/" + tag + close;
-				},
-				functionArgs: function( fn ) {//function calls it internally, it's the arguments part of the function
-					var args,
-						l = fn.length;
-
-					if ( !l ) {
-						return "";
-					}
-
-					args = new Array(l);
-					while ( l-- ) {
-						args[l] = String.fromCharCode(97+l);//97 is 'a'
-					}
-					return " " + args.join( ", " ) + " ";
-				},
-				key: quote, //object calls it internally, the key part of an item in a map
-				functionCode: "[code]", //function calls it internally, it's the content of the function
-				attribute: quote, //node calls it internally, it's an html attribute value
-				string: quote,
-				date: quote,
-				regexp: literal, //regex
-				number: literal,
-				"boolean": literal
-			},
-			DOMAttrs: {
-				//attributes to dump from nodes, name=>realName
-				id: "id",
-				name: "name",
-				"class": "className"
-			},
-			HTML: false,//if true, entities are escaped ( <, >, \t, space and \n )
-			indentChar: "  ",//indentation unit
-			multiline: true //if true, items in a collection, are separated by a \n, else just a space.
-		};
-
-	return jsDump;
-}());
-
-// from Sizzle.js
-function getText( elems ) {
-	var i, elem,
-		ret = "";
-
-	for ( i = 0; elems[i]; i++ ) {
-		elem = elems[i];
-
-		// Get the text from text nodes and CDATA nodes
-		if ( elem.nodeType === 3 || elem.nodeType === 4 ) {
-			ret += elem.nodeValue;
-
-		// Traverse everything else, except comment nodes
-		} else if ( elem.nodeType !== 8 ) {
-			ret += getText( elem.childNodes );
-		}
-	}
-
-	return ret;
-}
-
-// from jquery.js
-function inArray( elem, array ) {
-	if ( array.indexOf ) {
-		return array.indexOf( elem );
-	}
-
-	for ( var i = 0, length = array.length; i < length; i++ ) {
-		if ( array[ i ] === elem ) {
-			return i;
-		}
-	}
-
-	return -1;
-}
-
-/*
- * Javascript Diff Algorithm
- *  By John Resig (http://ejohn.org/)
- *  Modified by Chu Alan "sprite"
- *
- * Released under the MIT license.
- *
- * More Info:
- *  http://ejohn.org/projects/javascript-diff-algorithm/
- *
- * Usage: QUnit.diff(expected, actual)
- *
- * QUnit.diff( "the quick brown fox jumped over", "the quick fox jumps over" ) == "the  quick <del>brown </del> fox <del>jumped </del><ins>jumps </ins> over"
- */
-QUnit.diff = (function() {
-	function diff( o, n ) {
-		var i,
-			ns = {},
-			os = {};
-
-		for ( i = 0; i < n.length; i++ ) {
-			if ( ns[ n[i] ] == null ) {
-				ns[ n[i] ] = {
-					rows: [],
-					o: null
-				};
-			}
-			ns[ n[i] ].rows.push( i );
-		}
-
-		for ( i = 0; i < o.length; i++ ) {
-			if ( os[ o[i] ] == null ) {
-				os[ o[i] ] = {
-					rows: [],
-					n: null
-				};
-			}
-			os[ o[i] ].rows.push( i );
-		}
-
-		for ( i in ns ) {
-			if ( !hasOwn.call( ns, i ) ) {
-				continue;
-			}
-			if ( ns[i].rows.length == 1 && typeof os[i] != "undefined" && os[i].rows.length == 1 ) {
-				n[ ns[i].rows[0] ] = {
-					text: n[ ns[i].rows[0] ],
-					row: os[i].rows[0]
-				};
-				o[ os[i].rows[0] ] = {
-					text: o[ os[i].rows[0] ],
-					row: ns[i].rows[0]
-				};
-			}
-		}
-
-		for ( i = 0; i < n.length - 1; i++ ) {
-			if ( n[i].text != null && n[ i + 1 ].text == null && n[i].row + 1 < o.length && o[ n[i].row + 1 ].text == null &&
-						n[ i + 1 ] == o[ n[i].row + 1 ] ) {
-
-				n[ i + 1 ] = {
-					text: n[ i + 1 ],
-					row: n[i].row + 1
-				};
-				o[ n[i].row + 1 ] = {
-					text: o[ n[i].row + 1 ],
-					row: i + 1
-				};
-			}
-		}
-
-		for ( i = n.length - 1; i > 0; i-- ) {
-			if ( n[i].text != null && n[ i - 1 ].text == null && n[i].row > 0 && o[ n[i].row - 1 ].text == null &&
-						n[ i - 1 ] == o[ n[i].row - 1 ]) {
-
-				n[ i - 1 ] = {
-					text: n[ i - 1 ],
-					row: n[i].row - 1
-				};
-				o[ n[i].row - 1 ] = {
-					text: o[ n[i].row - 1 ],
-					row: i - 1
-				};
-			}
-		}
-
-		return {
-			o: o,
-			n: n
-		};
-	}
-
-	return function( o, n ) {
-		o = o.replace( /\s+$/, "" );
-		n = n.replace( /\s+$/, "" );
-
-		var i, pre,
-			str = "",
-			out = diff( o === "" ? [] : o.split(/\s+/), n === "" ? [] : n.split(/\s+/) ),
-			oSpace = o.match(/\s+/g),
-			nSpace = n.match(/\s+/g);
-
-		if ( oSpace == null ) {
-			oSpace = [ " " ];
-		}
-		else {
-			oSpace.push( " " );
-		}
-
-		if ( nSpace == null ) {
-			nSpace = [ " " ];
-		}
-		else {
-			nSpace.push( " " );
-		}
-
-		if ( out.n.length === 0 ) {
-			for ( i = 0; i < out.o.length; i++ ) {
-				str += "<del>" + out.o[i] + oSpace[i] + "</del>";
-			}
-		}
-		else {
-			if ( out.n[0].text == null ) {
-				for ( n = 0; n < out.o.length && out.o[n].text == null; n++ ) {
-					str += "<del>" + out.o[n] + oSpace[n] + "</del>";
-				}
-			}
-
-			for ( i = 0; i < out.n.length; i++ ) {
-				if (out.n[i].text == null) {
-					str += "<ins>" + out.n[i] + nSpace[i] + "</ins>";
-				}
-				else {
-					// `pre` initialized at top of scope
-					pre = "";
-
-					for ( n = out.n[i].row + 1; n < out.o.length && out.o[n].text == null; n++ ) {
-						pre += "<del>" + out.o[n] + oSpace[n] + "</del>";
-					}
-					str += " " + out.n[i].text + nSpace[i] + pre;
-				}
-			}
-		}
-
-		return str;
-	};
-}());
-
-// for CommonJS enviroments, export everything
-if ( typeof exports !== "undefined" ) {
-	extend(exports, QUnit);
-}
-
-// get at whatever the global object is, like window in browsers
-}( (function() {return this;}.call()) ));
diff --git a/civicrm/bower_components/select2/.composer-downloads/select2-35368a19f307e4af02d0df055846840d.json b/civicrm/bower_components/select2/.composer-downloads/select2-35368a19f307e4af02d0df055846840d.json
index 0ec2bae6e593850dc9a6dd22830ecd2e01d7e20c..8111bbe7ba8a1b42fd73c08ce07d30ae9f113070 100644
--- a/civicrm/bower_components/select2/.composer-downloads/select2-35368a19f307e4af02d0df055846840d.json
+++ b/civicrm/bower_components/select2/.composer-downloads/select2-35368a19f307e4af02d0df055846840d.json
@@ -1,4 +1,6 @@
 {
     "name": "civicrm/civicrm-core:select2",
-    "url": "https://github.com/colemanw/select2/archive/v3.5-civicrm-1.0.zip"
+    "url": "https://github.com/colemanw/select2/archive/v3.5-civicrm-1.0.zip",
+    "checksum": "63db8d7cc9e9229adb5e6adaeec23bdebb485f70abe76a6bce0b0f35b94811fc",
+    "ignore": null
 }
\ No newline at end of file
diff --git a/civicrm/bower_components/smartmenus/.composer-downloads/smartmenus-b6b012dd2c05e4df06d5f6aa2ef2b36e.json b/civicrm/bower_components/smartmenus/.composer-downloads/smartmenus-b6b012dd2c05e4df06d5f6aa2ef2b36e.json
index 16db09c03c9ef1534dfa01b5419a07c3686e9e5d..bfc6f265516798dca6779f804f485b4d2f165786 100644
--- a/civicrm/bower_components/smartmenus/.composer-downloads/smartmenus-b6b012dd2c05e4df06d5f6aa2ef2b36e.json
+++ b/civicrm/bower_components/smartmenus/.composer-downloads/smartmenus-b6b012dd2c05e4df06d5f6aa2ef2b36e.json
@@ -1,4 +1,9 @@
 {
     "name": "civicrm/civicrm-core:smartmenus",
-    "url": "https://github.com/vadikom/smartmenus/archive/1.1.0.zip"
+    "url": "https://github.com/vadikom/smartmenus/archive/1.1.0.zip",
+    "checksum": "b533a0234fdaa0ff5c6e0e690cff71248e46520a35339315ba098a505c824b12",
+    "ignore": [
+        ".gitignore",
+        "Gruntfile.js"
+    ]
 }
\ No newline at end of file
diff --git a/civicrm/civicrm-version.php b/civicrm/civicrm-version.php
index 47090da1eb10dddd60de84f1323f32370cf91b38..63aca177a02df8f8427250ad0315ef03e027c6d0 100644
--- a/civicrm/civicrm-version.php
+++ b/civicrm/civicrm-version.php
@@ -1,7 +1,7 @@
 <?php
 /** @deprecated */
 function civicrmVersion( ) {
-  return array( 'version'  => '5.24.2',
+  return array( 'version'  => '5.24.3',
                 'cms'      => 'Wordpress',
                 'revision' => '' );
 }
diff --git a/civicrm/composer.json b/civicrm/composer.json
index 8d94f744f9b3eb11bd14833b3f1723dd443bca03..e904c396cc56aae3a68c6516cb64d349b08c38f0 100644
--- a/civicrm/composer.json
+++ b/civicrm/composer.json
@@ -74,7 +74,8 @@
     "civicrm/composer-downloads-plugin": "^2.0",
     "league/csv": "^9.2",
     "tplaner/when": "~3.0.0",
-    "xkerman/restricted-unserialize": "~1.1"
+    "xkerman/restricted-unserialize": "~1.1",
+    "typo3/phar-stream-wrapper": "^3.0"
   },
   "scripts": {
     "post-install-cmd": [
@@ -200,7 +201,7 @@
       },
       "google-code-prettify": {
         "url": "https://github.com/tcollard/google-code-prettify/archive/v1.0.5.zip",
-        "ignore": ["closure-compiler", "js-modules", "tests", "yui-compressor", "Makefile"]
+        "ignore": ["closure-compiler", "js-modules", "tests", "yui-compressor", "Makefile", "examples", "*.html", "run_prettify*js"]
       },
       "jquery": {
         "url": "https://github.com/civicrm/jquery/archive/1.12.4-civicrm-1.2.zip"
@@ -223,9 +224,6 @@
       "phantomjs-polyfill": {
         "url": "https://github.com/conversocial/phantomjs-polyfill/archive/v0.0.2.zip"
       },
-      "qunit": {
-        "url": "https://github.com/jquery/qunit/archive/v1.10.0.zip"
-      },
       "select2": {
         "url": "https://github.com/colemanw/select2/archive/v3.5-civicrm-1.0.zip"
       },
diff --git a/civicrm/composer.lock b/civicrm/composer.lock
index a6992774825759792b47c6d4c5f725dca8e05c6d..3c11836e7f366c495f10afcc33d98a9a99dd1880 100644
--- a/civicrm/composer.lock
+++ b/civicrm/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": "50e07f942de796516f50da3b20ce018b",
+    "content-hash": "7607feb9bdda80a25ebc8c84fb737c58",
     "packages": [
         {
             "name": "cache/integration-tests",
@@ -166,16 +166,16 @@
         },
         {
             "name": "civicrm/composer-downloads-plugin",
-            "version": "v2.0.0",
+            "version": "v2.1.1",
             "source": {
                 "type": "git",
                 "url": "https://github.com/civicrm/composer-downloads-plugin.git",
-                "reference": "869b7a12f57b2d912f0ea77d5c33c1518b8de27d"
+                "reference": "8722bc7d547315be39397a3078bb51ee053ca269"
             },
             "dist": {
                 "type": "zip",
-                "url": "https://api.github.com/repos/civicrm/composer-downloads-plugin/zipball/869b7a12f57b2d912f0ea77d5c33c1518b8de27d",
-                "reference": "869b7a12f57b2d912f0ea77d5c33c1518b8de27d",
+                "url": "https://api.github.com/repos/civicrm/composer-downloads-plugin/zipball/8722bc7d547315be39397a3078bb51ee053ca269",
+                "reference": "8722bc7d547315be39397a3078bb51ee053ca269",
                 "shasum": ""
             },
             "require": {
@@ -213,7 +213,7 @@
                 }
             ],
             "description": "Composer plugin for downloading additional files within any composer package.",
-            "time": "2019-08-22T10:56:51+00:00"
+            "time": "2019-08-28T00:33:51+00:00"
         },
         {
             "name": "cweagans/composer-patches",
@@ -2380,9 +2380,7 @@
             "version": "3.0.0+php53",
             "dist": {
                 "type": "zip",
-                "url": "https://github.com/tplaner/When/archive/c1ec099f421bff354cc5c929f83b94031423fc80.zip",
-                "reference": null,
-                "shasum": null
+                "url": "https://github.com/tplaner/When/archive/c1ec099f421bff354cc5c929f83b94031423fc80.zip"
             },
             "require": {
                 "php": ">=5.3.0"
@@ -2414,6 +2412,56 @@
                 "time"
             ]
         },
+        {
+            "name": "typo3/phar-stream-wrapper",
+            "version": "v3.1.4",
+            "source": {
+                "type": "git",
+                "url": "https://github.com/TYPO3/phar-stream-wrapper.git",
+                "reference": "e0c1b495cfac064f4f5c4bcb6bf67bb7f345ed04"
+            },
+            "dist": {
+                "type": "zip",
+                "url": "https://api.github.com/repos/TYPO3/phar-stream-wrapper/zipball/e0c1b495cfac064f4f5c4bcb6bf67bb7f345ed04",
+                "reference": "e0c1b495cfac064f4f5c4bcb6bf67bb7f345ed04",
+                "shasum": ""
+            },
+            "require": {
+                "ext-json": "*",
+                "php": "^7.0"
+            },
+            "require-dev": {
+                "ext-xdebug": "*",
+                "phpunit/phpunit": "^6.5"
+            },
+            "suggest": {
+                "ext-fileinfo": "For PHP builtin file type guessing, otherwise uses internal processing"
+            },
+            "type": "library",
+            "extra": {
+                "branch-alias": {
+                    "dev-master": "v3.x-dev"
+                }
+            },
+            "autoload": {
+                "psr-4": {
+                    "TYPO3\\PharStreamWrapper\\": "src/"
+                }
+            },
+            "notification-url": "https://packagist.org/downloads/",
+            "license": [
+                "MIT"
+            ],
+            "description": "Interceptors for PHP's native phar:// stream handling",
+            "homepage": "https://typo3.org/",
+            "keywords": [
+                "phar",
+                "php",
+                "security",
+                "stream-wrapper"
+            ],
+            "time": "2019-12-10T11:53:27+00:00"
+        },
         {
             "name": "xkerman/restricted-unserialize",
             "version": "1.1.12",
@@ -2670,5 +2718,6 @@
     "platform-dev": [],
     "platform-overrides": {
         "php": "7.0.10"
-    }
+    },
+    "plugin-api-version": "1.1.0"
 }
diff --git a/civicrm/release-notes.md b/civicrm/release-notes.md
index 79515f2bddfd7d5fd9e0a7339c611268f38b17a7..39a9660f5683eb53ecb885ec682c3071e25ab9d4 100644
--- a/civicrm/release-notes.md
+++ b/civicrm/release-notes.md
@@ -15,6 +15,12 @@ Other resources for identifying changes are:
     * https://github.com/civicrm/civicrm-joomla
     * https://github.com/civicrm/civicrm-wordpress
 
+## CiviCRM 5.24.3
+
+Released April 15, 2020
+
+- **[Security advisories](release-notes/5.24.3.md#security)**
+
 ## CiviCRM 5.24.2
 
 Released April 9, 2020
diff --git a/civicrm/release-notes/5.24.2.md b/civicrm/release-notes/5.24.2.md
index 9cb2e60ef9c73e57e7aecf90f813e598424828a3..8a417b00ffe863699fa441d573f6f839cba6ec72 100644
--- a/civicrm/release-notes/5.24.2.md
+++ b/civicrm/release-notes/5.24.2.md
@@ -1,4 +1,4 @@
-# CiviCRM 5.24.1
+# CiviCRM 5.24.2
 
 Released April 9, 2020
 
diff --git a/civicrm/release-notes/5.24.3.md b/civicrm/release-notes/5.24.3.md
new file mode 100644
index 0000000000000000000000000000000000000000..806729bb8935307e058deed209b1b8edf5c06b9c
--- /dev/null
+++ b/civicrm/release-notes/5.24.3.md
@@ -0,0 +1,40 @@
+# CiviCRM 5.24.3
+
+Released April 15, 2020
+
+- **[Security advisories](#security)**
+- **[Credits](#credits)**
+
+## <a name="synopsis"></a>Synopsis
+
+| *Does this version...?*                                         |         |
+|:--------------------------------------------------------------- |:-------:|
+| **Fix security vulnerabilities?**                               | **yes** |
+| Change the database schema?                                     |   no    |
+| Alter the API?                                                  |   no    |
+| Require attention to configuration options?                     |   no    |
+| Fix problems installing or upgrading to a previous version?     |   no    |
+| Introduce features?                                             |   no    |
+| Fix bugs?                                                       |   no    |
+
+## <a name="security"></a>Security advisories
+
+- **[CIVI-SA-2020-01](https://civicrm.org/advisory/civi-sa-2020-01): Improve Entity Name sanitisation when used as part of API**
+- **[CIVI-SA-2020-02](https://civicrm.org/advisory/civi-sa-2020-02): API Key Disclosure**
+- **[CIVI-SA-2020-03](https://civicrm.org/advisory/civi-sa-2020-03): PHP Code Execution via Phar Deserialization**
+- **[CIVI-SA-2020-04](https://civicrm.org/advisory/civi-sa-2020-04): Cross Site Scripting within CiviCase Reports**
+- **[CIVI-SA-2020-05](https://civicrm.org/advisory/civi-sa-2020-05): SQL Injection in Campaign Summary and Delete Activity**
+- **[CIVI-SA-2020-06](https://civicrm.org/advisory/civi-sa-2020-06): SQLI in Query Builder**
+- **[CIVI-SA-2020-07](https://civicrm.org/advisory/civi-sa-2020-07): CSRF in Scheduled Jobs**
+- **[CIVI-SA-2020-08](https://civicrm.org/advisory/civi-sa-2020-08): XSS via JS libraries**
+
+## <a name="credits"></a>Credits
+
+This release was developed by the following people, who participated in
+various stages of reporting, analysis, development, review, and testing:
+
+Cure53; Mozilla Open Source Support (MOSS); Dennis Brinkrolf - RIPS Technologies;
+Kevin Cristiano - Tadpole Collective; Rich Lott - Artful Robot;
+Eileen McNaughton - Wikipedia Foundation; Sean Colsen - Left Join Labs;
+Mark Burdett - Electronic Frontier Foundation; Patrick Figel - Greenpeace CEE; 
+Seamus Lee - CiviCRM and JMA Consulting; Tim Otten - CiviCRM
diff --git a/civicrm/sql/civicrm_data.mysql b/civicrm/sql/civicrm_data.mysql
index 68f66e95826e78ea10ed0d8fae655e5021fb993f..61251a0735205de2f6dafe90137d37d458444019 100644
--- a/civicrm/sql/civicrm_data.mysql
+++ b/civicrm/sql/civicrm_data.mysql
@@ -23896,4 +23896,4 @@ INSERT INTO `civicrm_report_instance`
     ( `domain_id`, `title`, `report_id`, `description`, `permission`, `form_values`)
 VALUES
     (  @domainID, 'Survey Details', 'survey/detail', 'Detailed report for canvassing, phone-banking, walk lists or other surveys.', 'access CiviReport', 'a:39:{s:6:"fields";a:2:{s:9:"sort_name";s:1:"1";s:6:"result";s:1:"1";}s:22:"assignee_contact_id_op";s:2:"eq";s:25:"assignee_contact_id_value";s:0:"";s:12:"sort_name_op";s:3:"has";s:15:"sort_name_value";s:0:"";s:17:"street_number_min";s:0:"";s:17:"street_number_max";s:0:"";s:16:"street_number_op";s:3:"lte";s:19:"street_number_value";s:0:"";s:14:"street_name_op";s:3:"has";s:17:"street_name_value";s:0:"";s:15:"postal_code_min";s:0:"";s:15:"postal_code_max";s:0:"";s:14:"postal_code_op";s:3:"lte";s:17:"postal_code_value";s:0:"";s:7:"city_op";s:3:"has";s:10:"city_value";s:0:"";s:20:"state_province_id_op";s:2:"in";s:23:"state_province_id_value";a:0:{}s:13:"country_id_op";s:2:"in";s:16:"country_id_value";a:0:{}s:12:"survey_id_op";s:2:"in";s:15:"survey_id_value";a:0:{}s:12:"status_id_op";s:2:"eq";s:15:"status_id_value";s:1:"1";s:11:"custom_1_op";s:2:"in";s:14:"custom_1_value";a:0:{}s:11:"custom_2_op";s:2:"in";s:14:"custom_2_value";a:0:{}s:17:"custom_3_relative";s:1:"0";s:13:"custom_3_from";s:0:"";s:11:"custom_3_to";s:0:"";s:11:"description";s:75:"Detailed report for canvassing, phone-banking, walk lists or other surveys.";s:13:"email_subject";s:0:"";s:8:"email_to";s:0:"";s:8:"email_cc";s:0:"";s:10:"permission";s:17:"access CiviReport";s:6:"groups";s:0:"";s:9:"domain_id";i:1;}');
-UPDATE civicrm_domain SET version = '5.24.2';
+UPDATE civicrm_domain SET version = '5.24.3';
diff --git a/civicrm/sql/civicrm_generated.mysql b/civicrm/sql/civicrm_generated.mysql
index 184fb426c623054b920ad2aeccbb588df735f700..db950731157033d81996d2936ab17195231f71b1 100644
--- a/civicrm/sql/civicrm_generated.mysql
+++ b/civicrm/sql/civicrm_generated.mysql
@@ -398,7 +398,7 @@ UNLOCK TABLES;
 
 LOCK TABLES `civicrm_domain` WRITE;
 /*!40000 ALTER TABLE `civicrm_domain` DISABLE KEYS */;
-INSERT INTO `civicrm_domain` (`id`, `name`, `description`, `version`, `contact_id`, `locales`, `locale_custom_strings`) VALUES (1,'Default Domain Name',NULL,'5.24.2',1,NULL,'a:1:{s:5:\"en_US\";a:0:{}}');
+INSERT INTO `civicrm_domain` (`id`, `name`, `description`, `version`, `contact_id`, `locales`, `locale_custom_strings`) VALUES (1,'Default Domain Name',NULL,'5.24.3',1,NULL,'a:1:{s:5:\"en_US\";a:0:{}}');
 /*!40000 ALTER TABLE `civicrm_domain` ENABLE KEYS */;
 UNLOCK TABLES;
 
diff --git a/civicrm/templates/CRM/Admin/Form/Job.tpl b/civicrm/templates/CRM/Admin/Form/Job.tpl
index 3c319aba56984d9e094d390dfd98d5c7763a4ebe..0fb95d4655da5cd1081b3a9733f16f1fcde2ec15 100644
--- a/civicrm/templates/CRM/Admin/Form/Job.tpl
+++ b/civicrm/templates/CRM/Admin/Form/Job.tpl
@@ -8,7 +8,7 @@
  +--------------------------------------------------------------------+
 *}
 {* This template is used for adding/configuring Scheduled Jobs.  *}
-<h3>{if $action eq 1}{ts}New Scheduled Job{/ts}{elseif $action eq 2}{ts}Edit Scheduled Job{/ts}{elseif $action eq 128}{ts}Execute Scheduled Job{/ts}{else}{ts}Delete Scheduled Job{/ts}{/if}</h3>
+<h3>{if $action eq 1}{ts}New Scheduled Job{/ts}{elseif $action eq 2}{ts}Edit Scheduled Job{/ts}{elseif $action eq 4}{ts}Execute Scheduled Job{/ts}{else}{ts}Delete Scheduled Job{/ts}{/if}</h3>
 <div class="crm-block crm-form-block crm-job-form-block">
  <div class="crm-submit-buttons">{include file="CRM/common/formButtons.tpl" location="top"}</div>
 
@@ -17,10 +17,10 @@
       <div class="icon inform-icon"></div>
         {ts}WARNING: Deleting this Scheduled Job will cause some important site functionality to stop working.{/ts} {ts}Do you want to continue?{/ts}
   </div>
-{elseif $action eq 128}
+{elseif $action eq 4}
   <div class="messages status no-popup">
       <div class="icon inform-icon"></div>
-        {ts}Are you sure you would like to execute this job?{/ts}
+        {ts 1=$jobName}Are you sure you would like to execute %1 job?{/ts}
   </div>
 {else}
   <table class="form-layout-compressed">
diff --git a/civicrm/templates/CRM/Admin/Page/Job.tpl b/civicrm/templates/CRM/Admin/Page/Job.tpl
index 94856e34aeb18fd9df5bf27c78b84b5a4ed5d716..c0812feff152bbb4f2554864174e78675212caf3 100644
--- a/civicrm/templates/CRM/Admin/Page/Job.tpl
+++ b/civicrm/templates/CRM/Admin/Page/Job.tpl
@@ -12,7 +12,7 @@
     {ts 1=$runAllURL}You can configure scheduled jobs (cron tasks) for your CiviCRM installation. For most sites, your system administrator should set up one or more 'cron' tasks to run the enabled jobs. However, you can also <a href="%1">run all scheduled jobs manually</a>, or run specific jobs from this screen (click 'more' and then 'Execute Now').{/ts} {docURL page="sysadmin/setup/jobs" text="(Job parameters and command line syntax documentation...)"}
 </div>
 
-{if $action eq 1 or $action eq 2 or $action eq 8}
+{if $action eq 1 or $action eq 2 or $action eq 8 or $action eq 4}
    {include file="CRM/Admin/Form/Job.tpl"}
 {else}
 
diff --git a/civicrm/templates/CRM/Case/Form/ActivityView.tpl b/civicrm/templates/CRM/Case/Form/ActivityView.tpl
index 5a7e78ff63c0d66795c47be283a35413b79dfac9..68979f60a6538fa53ba242d1f38de8e8b29e1cfc 100644
--- a/civicrm/templates/CRM/Case/Form/ActivityView.tpl
+++ b/civicrm/templates/CRM/Case/Form/ActivityView.tpl
@@ -41,7 +41,7 @@
                 {if $parentID}<a class="open-inline-noreturn" href="{crmURL p='civicrm/case/activity/view' h=0 q="cid=$contactID&aid=$parentID"}">&raquo; {ts}Prompted by{/ts}</a>{/if}
               </td>
             {else}
-              <td colspan="2">{if $row.label eq 'Details'}{$row.value|crmStripAlternatives|nl2br}{elseif $row.type eq 'Date'}{$row.value|crmDate}{else}{$row.value}{/if}</td>
+              <td colspan="2">{if $row.label eq 'Details'}{$row.value|crmStripAlternatives|nl2br|purify}{elseif $row.type eq 'Date'}{$row.value|crmDate}{else}{$row.value}{/if}</td>
             {/if}
           </tr>
         {/foreach}
diff --git a/civicrm/vendor/autoload.php b/civicrm/vendor/autoload.php
index 06a410ba496672eda3ca85eb51aa2dbe64664ea9..2ca946ceef0f91e8b66ee270dd39f3498433bddc 100644
--- a/civicrm/vendor/autoload.php
+++ b/civicrm/vendor/autoload.php
@@ -4,4 +4,4 @@
 
 require_once __DIR__ . '/composer/autoload_real.php';
 
-return ComposerAutoloaderInit54e8d40c2296214b3ccf5202f594b467::getLoader();
+return ComposerAutoloaderInit1b2d18b3e6be91a2f49531a488d4d621::getLoader();
diff --git a/civicrm/vendor/civicrm/composer-downloads-plugin/README.md b/civicrm/vendor/civicrm/composer-downloads-plugin/README.md
index 9a4530db0c2a3446de07d1d029e66dec75ba6012..9292beb966306a7b9530aa43cb4ef44d3d46e72c 100644
--- a/civicrm/vendor/civicrm/composer-downloads-plugin/README.md
+++ b/civicrm/vendor/civicrm/composer-downloads-plugin/README.md
@@ -6,7 +6,7 @@ Composer Downloads Plugin
 
 This `composer` plugin allows you to download extra files (`*.zip` or `*.tar.gz`) and extract them within your package.
 
-For example, suppose you publish a PHP package `foo/bar` which relies on an external artifact (such as JS, CSS, or image library). Place this configuration in the `composer.json` for `foo/bar`:
+For example, suppose you publish a PHP package `foo/bar` which relies on an external artifact `examplelib-0.1.zip` (containing some JS, CSS, or image). Place this configuration in the `composer.json` for `foo/bar`:
 
 ```json
 {
@@ -45,16 +45,24 @@ The `downloads` approach is most appropriate if (a) you publish an intermediate
 
 The `downloads` contains a list of files to download. Each extra-file as a symbolic ID (e.g. `examplelib` above) and some mix of properties:
 
-* `url`: The URL to fetch the content from.  If it points to a tarball or zip file, it will be unpacked automatically.
+* `url`: The URL to fetch the content from.
 
 * `path`: The releative path where content will be extracted.
 
-* `type`: Determines how the download is handled
+* `type`: (*Optional*) Determines how the download is handled
     * `archive`: The `url` references a zip or tarball which should be extracted at the given `path`. (Default for URLs involving `*.zip`, `*.tar.gz`, or `*.tgz`.)
-    * `file`: The `url` should be downloaded to the given `path`.
+    * `file`: The `url` should be downloaded to the given `path`. (Default for all other URLs.)
     * `phar`: The `url` references a PHP executable which should be installed at the given `path`.
 
-* `ignore`: A list of a files that should be omited from the extracted folder. (This supports a subset of `.gitignore` notation.)
+* `ignore`: (*Optional*) A list of a files that should be omited from the extracted folder. (This supports a subset of `.gitignore` notation.)
+
+* `version`: (*Optional*) A version number for the downloaded artifact. This has no functional impact on the lifecycle of the artifact, but
+   it can affect the console output, and it can be optionally used as a variable when setting `url` or `path`.
+
+Values in `url` and `path` support the following variables:
+
+* `{$id}`: The symbolic identifier of the download. (In the introductory example, it would be `examplelib`.)
+* `{$version}`: The displayed/simulated/pretty version number of the package.
 
 ## Configuration: Defaults
 
@@ -81,14 +89,60 @@ You may set default values for downloaded files using the `*` entry.
 
 ## Tips
 
-In each downloaded folder, this plugin will create a small metadata file (`.composer-downloads.json`) to track the origin of the current code. If you modify the `composer.json` to use a different URL, then it will re-download the file.
+In each downloaded folder, this plugin will create a small metadata folder (`.composer-downloads`) to track the origin of the current code. If you modify the `composer.json` to use a different URL, then it will re-download the file.
 
 Download each extra file to a distinct `path`. Don't try to download into overlapping paths. (*This has not been tested, but it may lead to extraneous deletions/re-downloads.*)
 
-What should you do if you *normally* download the extra-file as `*.tgz` but sometimes (for local dev) need to grab bleeding edge content from somewhere else?  Simply delete the autodownloaded folder and replace it with your own.  `composer-downloads` will detect that conflict (by virtue of the absent `.composer-downloads.json`) and leave your code in place (until you choose to get rid of it). To switch back, you can simply delete the code and run `composer install` again.
+What should you do if you *normally* download the extra-file as `*.tgz` but sometimes (for local dev) need to grab bleeding edge content from somewhere else?  Simply delete the autodownloaded folder and replace it with your own.  `composer-downloads-plugin` will detect that conflict (by virtue of the absent `.composer-downloads`) and leave your code in place (until you choose to get rid of it). To switch back, you can simply delete the code and run `composer install` again.
 
 ## Known Limitations
 
-If you use `downloads` in a root-project (or in symlinked dev repo), it will create+update downloads, but it will not remove orphaned items automatically.  This could be addressed by doing a file-scan for `.composer-downloads.json` (and deleting any orphan folders).  Since the edge-case is not particularly common right now, and since a file-scan could be time-consuming, it might make sense as a separate subcommand.
+If you use `downloads` in a root-project (or in symlinked dev repo), it will create+update downloads, but it will not remove orphaned items automatically.  This could be addressed by doing a file-scan for `.composer-downloads` (and deleting any orphan folders).  Since the edge-case is not particularly common right now, and since a file-scan could be time-consuming, it might make sense as a separate subcommand.
+
+I believe the limitation does *not* affect downstream consumers of a dependency. In that case, the regular `composer` install/update/removal mechanics should take care of any nested downloads.
+
+## Automated Tests
+
+The `tests/` folder includes unit-tests and integration-tests written with
+PHPUnit.  Each integration-test generates a new folder/project with a
+plausible, representative `composer.json` file and executes `composer
+install`.  It checks the output has the expected files.
+
+To run the tests, you will need `composer` and `phpunit` in the `PATH`.
+
+```
+[~/src/composer-downloads-plugin] which composer
+/Users/myuser/bin/composer
+
+[~/src/composer-downloads-plugin] which phpunit
+/Users/myuser/bin/phpunit
+
+[~/src/composer-downloads-plugin] phpunit
+PHPUnit 5.7.27 by Sebastian Bergmann and contributors.
+
+.....                                                               5 / 5 (100%)
 
-I believe the limitation does *not* affect downstream consumers of a dependency. In that case, the regular `composer` install/update/removal mechanics should take care of any nested downloads. However, this is a little tricky to test right now.
+Time: 40.35 seconds, Memory: 10.00MB
+
+OK (5 tests, 7 assertions)
+```
+
+The integration tests can be a bit large/slow. To monitor the tests more
+closesly, set the `DEBUG` variable, as in:
+
+```
+[~/src/composer-downloads-plugin] env DEBUG=2 phpunit
+```
+
+## Local Dev Harness
+
+What if you want to produce an environment which uses the current plugin
+code - one where you can quickly re-run `composer` commands while
+iterating on code?
+
+You may use any of the integration-tests to initialize a baseline
+environment:
+
+```
+env USE_TEST_PROJECT=$HOME/src/myprj DEBUG=2 phpunit tests/SniffTest.php
+```
diff --git a/civicrm/vendor/civicrm/composer-downloads-plugin/src/DownloadsParser.php b/civicrm/vendor/civicrm/composer-downloads-plugin/src/DownloadsParser.php
index 212a6d9e07c20e2abdd1893f106f39a22932cb62..614882e97e8d753758b3dcdef5fff01e289748e4 100644
--- a/civicrm/vendor/civicrm/composer-downloads-plugin/src/DownloadsParser.php
+++ b/civicrm/vendor/civicrm/composer-downloads-plugin/src/DownloadsParser.php
@@ -37,12 +37,14 @@ class DownloadsParser
             foreach ((array) $extra['downloads'] as $id => $extraFile) {
                 if ($id === '*') continue;
 
-                $vars = ['{$id}' => $id];
                 $extraFile = array_merge($defaults, $extraFile);
                 $extraFile['id'] = $id;
                 foreach (['url', 'path'] as $prop) {
                     if (isset($extraFile[$prop])) {
-                        $extraFile[$prop] = strtr($extraFile[$prop], $vars);
+                        $extraFile[$prop] = strtr($extraFile[$prop], [
+                            '{$id}' => $extraFile['id'],
+                            '{$version}' => isset($extraFile['version']) ? $extraFile['version'] : '',
+                        ]);
                     }
                 }
 
diff --git a/civicrm/vendor/civicrm/composer-downloads-plugin/src/Handler/ArchiveHandler.php b/civicrm/vendor/civicrm/composer-downloads-plugin/src/Handler/ArchiveHandler.php
index 19f95c26fe5e064e77cd39d90ad09d4d160231b1..81b99a0209f9a142c0796337a97792a5345c54e8 100644
--- a/civicrm/vendor/civicrm/composer-downloads-plugin/src/Handler/ArchiveHandler.php
+++ b/civicrm/vendor/civicrm/composer-downloads-plugin/src/Handler/ArchiveHandler.php
@@ -38,6 +38,20 @@ class ArchiveHandler extends BaseHandler
             DIRECTORY_SEPARATOR . $file;
     }
 
+    public function createTrackingData()
+    {
+        $meta = parent::createTrackingData();
+        $meta['ignore'] = $this->findIgnores();
+        return $meta;
+    }
+
+
+    public function getChecksum() {
+        $ignore = empty($this->extraFile['ignore']) ? [] : array_values($this->extraFile['ignore']);
+        sort($ignore);
+        return hash('sha256', parent::getChecksum() . serialize($ignore));
+    }
+
     /**
      * @return string[]|NULL
      *   List of files to exclude. Use '**' to match subdirectories.
diff --git a/civicrm/vendor/civicrm/composer-downloads-plugin/src/Handler/BaseHandler.php b/civicrm/vendor/civicrm/composer-downloads-plugin/src/Handler/BaseHandler.php
index 020fff8303e91bb7cd140bdb951ca91e67943189..032cc99ec889649421e1cc25422284ba4ee850f1 100644
--- a/civicrm/vendor/civicrm/composer-downloads-plugin/src/Handler/BaseHandler.php
+++ b/civicrm/vendor/civicrm/composer-downloads-plugin/src/Handler/BaseHandler.php
@@ -72,14 +72,28 @@ abstract class BaseHandler
         $extraFile = $this->extraFile;
         $parent = $this->parent;
 
+        if (isset($extraFile['version'])) {
+            // $version = $versionParser->normalize($extraFile['version']);
+            $version = $versionParser->normalize(self::FAKE_VERSION);
+            $prettyVersion = $extraFile['version'];
+        }
+        elseif ($parent instanceof RootPackageInterface) {
+            $version = $versionParser->normalize(self::FAKE_VERSION);
+            $prettyVersion = self::FAKE_VERSION;
+        }
+        else {
+            $version = $parent->getVersion();
+            $prettyVersion = $parent->getPrettyVersion();
+        }
+
         $package = new Subpackage(
             $parent,
             $extraFile['id'],
             $extraFile['url'],
             NULL,
             $extraFile['path'],
-            $parent instanceof RootPackageInterface ? $versionParser->normalize(self::FAKE_VERSION) : $parent->getVersion(),
-            $parent instanceof RootPackageInterface ? self::FAKE_VERSION : $parent->getPrettyVersion()
+            $version,
+            $prettyVersion
         );
 
         return $package;
@@ -89,9 +103,26 @@ abstract class BaseHandler
         return [
             'name' => $this->getSubpackage()->getName(),
             'url' => $this->getSubpackage()->getDistUrl(),
+            'checksum' => $this->getChecksum(),
         ];
     }
 
+    /**
+     * @return string
+     *   A unique identifier for this configuration of this asset.
+     *   If the identifier changes, that implies that the asset should be
+     *   replaced/redownloaded.
+     */
+    public function getChecksum() {
+        $extraFile = $this->extraFile;
+        return hash('sha256', serialize([
+            get_class($this),
+            $extraFile['id'],
+            $extraFile['url'],
+            $extraFile['path'],
+        ]));
+    }
+
     /**
      * @return string
      */
diff --git a/civicrm/vendor/civicrm/composer-downloads-plugin/src/Plugin.php b/civicrm/vendor/civicrm/composer-downloads-plugin/src/Plugin.php
index 90f10503a408a8fbeb55631a3fc8c670a2b11556..083cdb916913307077413678c4128d1275257d2d 100644
--- a/civicrm/vendor/civicrm/composer-downloads-plugin/src/Plugin.php
+++ b/civicrm/vendor/civicrm/composer-downloads-plugin/src/Plugin.php
@@ -104,7 +104,7 @@ class Plugin implements PluginInterface, EventSubscriberInterface
 
             if (file_exists($targetPath) && file_exists($trackingFile)) {
                 $meta = @json_decode(file_get_contents($trackingFile), 1);
-                if ($meta['url'] === $extraFilePkg->getDistUrl()) {
+                if (isset($meta['checksum']) && $meta['checksum'] === $extraFileHandler->getChecksum()) {
                     $this->io->write(sprintf("<info>Skip extra file <comment>%s</comment></info>", $extraFilePkg->getName()), TRUE, IOInterface::VERY_VERBOSE);
                     continue;
                 }
diff --git a/civicrm/vendor/composer/autoload_psr4.php b/civicrm/vendor/composer/autoload_psr4.php
index 2385da0bde2734dfc5d44834101ce8ab904e1e45..97050d2fbb0aa992a76453107723c895f6c4010b 100644
--- a/civicrm/vendor/composer/autoload_psr4.php
+++ b/civicrm/vendor/composer/autoload_psr4.php
@@ -10,6 +10,7 @@ return array(
     'cweagans\\Composer\\' => array($vendorDir . '/cweagans/composer-patches/src'),
     'Zend\\Escaper\\' => array($vendorDir . '/zendframework/zend-escaper/src'),
     'When\\' => array($vendorDir . '/tplaner/when/src'),
+    'TYPO3\\PharStreamWrapper\\' => array($vendorDir . '/typo3/phar-stream-wrapper/src'),
     'Symfony\\Polyfill\\Iconv\\' => array($vendorDir . '/symfony/polyfill-iconv'),
     'Symfony\\Polyfill\\Ctype\\' => array($vendorDir . '/symfony/polyfill-ctype'),
     'Symfony\\Component\\Process\\' => array($vendorDir . '/symfony/process'),
diff --git a/civicrm/vendor/composer/autoload_real.php b/civicrm/vendor/composer/autoload_real.php
index df3b7936be49d943806c1bc6199732536d1d91f0..38761b460335e7179543506606c86cd2f0f4eecd 100644
--- a/civicrm/vendor/composer/autoload_real.php
+++ b/civicrm/vendor/composer/autoload_real.php
@@ -2,7 +2,7 @@
 
 // autoload_real.php @generated by Composer
 
-class ComposerAutoloaderInit54e8d40c2296214b3ccf5202f594b467
+class ComposerAutoloaderInit1b2d18b3e6be91a2f49531a488d4d621
 {
     private static $loader;
 
@@ -19,9 +19,9 @@ class ComposerAutoloaderInit54e8d40c2296214b3ccf5202f594b467
             return self::$loader;
         }
 
-        spl_autoload_register(array('ComposerAutoloaderInit54e8d40c2296214b3ccf5202f594b467', 'loadClassLoader'), true, true);
+        spl_autoload_register(array('ComposerAutoloaderInit1b2d18b3e6be91a2f49531a488d4d621', 'loadClassLoader'), true, true);
         self::$loader = $loader = new \Composer\Autoload\ClassLoader();
-        spl_autoload_unregister(array('ComposerAutoloaderInit54e8d40c2296214b3ccf5202f594b467', 'loadClassLoader'));
+        spl_autoload_unregister(array('ComposerAutoloaderInit1b2d18b3e6be91a2f49531a488d4d621', 'loadClassLoader'));
 
         $includePaths = require __DIR__ . '/include_paths.php';
         $includePaths[] = get_include_path();
@@ -31,7 +31,7 @@ class ComposerAutoloaderInit54e8d40c2296214b3ccf5202f594b467
         if ($useStaticLoader) {
             require_once __DIR__ . '/autoload_static.php';
 
-            call_user_func(\Composer\Autoload\ComposerStaticInit54e8d40c2296214b3ccf5202f594b467::getInitializer($loader));
+            call_user_func(\Composer\Autoload\ComposerStaticInit1b2d18b3e6be91a2f49531a488d4d621::getInitializer($loader));
         } else {
             $map = require __DIR__ . '/autoload_namespaces.php';
             foreach ($map as $namespace => $path) {
@@ -52,19 +52,19 @@ class ComposerAutoloaderInit54e8d40c2296214b3ccf5202f594b467
         $loader->register(true);
 
         if ($useStaticLoader) {
-            $includeFiles = Composer\Autoload\ComposerStaticInit54e8d40c2296214b3ccf5202f594b467::$files;
+            $includeFiles = Composer\Autoload\ComposerStaticInit1b2d18b3e6be91a2f49531a488d4d621::$files;
         } else {
             $includeFiles = require __DIR__ . '/autoload_files.php';
         }
         foreach ($includeFiles as $fileIdentifier => $file) {
-            composerRequire54e8d40c2296214b3ccf5202f594b467($fileIdentifier, $file);
+            composerRequire1b2d18b3e6be91a2f49531a488d4d621($fileIdentifier, $file);
         }
 
         return $loader;
     }
 }
 
-function composerRequire54e8d40c2296214b3ccf5202f594b467($fileIdentifier, $file)
+function composerRequire1b2d18b3e6be91a2f49531a488d4d621($fileIdentifier, $file)
 {
     if (empty($GLOBALS['__composer_autoload_files'][$fileIdentifier])) {
         require $file;
diff --git a/civicrm/vendor/composer/autoload_static.php b/civicrm/vendor/composer/autoload_static.php
index 5fa40a0ee3392219aa826fde2aaae6998d06d663..1bd83f11fea5a5ebd6537a44c41ab6fabe99f8de 100644
--- a/civicrm/vendor/composer/autoload_static.php
+++ b/civicrm/vendor/composer/autoload_static.php
@@ -4,7 +4,7 @@
 
 namespace Composer\Autoload;
 
-class ComposerStaticInit54e8d40c2296214b3ccf5202f594b467
+class ComposerStaticInit1b2d18b3e6be91a2f49531a488d4d621
 {
     public static $files = array (
         '320cde22f66dd4f5d3fd621d3e88b98f' => __DIR__ . '/..' . '/symfony/polyfill-ctype/bootstrap.php',
@@ -35,6 +35,10 @@ class ComposerStaticInit54e8d40c2296214b3ccf5202f594b467
         array (
             'When\\' => 5,
         ),
+        'T' => 
+        array (
+            'TYPO3\\PharStreamWrapper\\' => 24,
+        ),
         'S' => 
         array (
             'Symfony\\Polyfill\\Iconv\\' => 23,
@@ -107,6 +111,10 @@ class ComposerStaticInit54e8d40c2296214b3ccf5202f594b467
         array (
             0 => __DIR__ . '/..' . '/tplaner/when/src',
         ),
+        'TYPO3\\PharStreamWrapper\\' => 
+        array (
+            0 => __DIR__ . '/..' . '/typo3/phar-stream-wrapper/src',
+        ),
         'Symfony\\Polyfill\\Iconv\\' => 
         array (
             0 => __DIR__ . '/..' . '/symfony/polyfill-iconv',
@@ -480,11 +488,11 @@ class ComposerStaticInit54e8d40c2296214b3ccf5202f594b467
     public static function getInitializer(ClassLoader $loader)
     {
         return \Closure::bind(function () use ($loader) {
-            $loader->prefixLengthsPsr4 = ComposerStaticInit54e8d40c2296214b3ccf5202f594b467::$prefixLengthsPsr4;
-            $loader->prefixDirsPsr4 = ComposerStaticInit54e8d40c2296214b3ccf5202f594b467::$prefixDirsPsr4;
-            $loader->prefixesPsr0 = ComposerStaticInit54e8d40c2296214b3ccf5202f594b467::$prefixesPsr0;
-            $loader->fallbackDirsPsr0 = ComposerStaticInit54e8d40c2296214b3ccf5202f594b467::$fallbackDirsPsr0;
-            $loader->classMap = ComposerStaticInit54e8d40c2296214b3ccf5202f594b467::$classMap;
+            $loader->prefixLengthsPsr4 = ComposerStaticInit1b2d18b3e6be91a2f49531a488d4d621::$prefixLengthsPsr4;
+            $loader->prefixDirsPsr4 = ComposerStaticInit1b2d18b3e6be91a2f49531a488d4d621::$prefixDirsPsr4;
+            $loader->prefixesPsr0 = ComposerStaticInit1b2d18b3e6be91a2f49531a488d4d621::$prefixesPsr0;
+            $loader->fallbackDirsPsr0 = ComposerStaticInit1b2d18b3e6be91a2f49531a488d4d621::$fallbackDirsPsr0;
+            $loader->classMap = ComposerStaticInit1b2d18b3e6be91a2f49531a488d4d621::$classMap;
 
         }, null, ClassLoader::class);
     }
diff --git a/civicrm/vendor/composer/installed.json b/civicrm/vendor/composer/installed.json
index 80ebf3db88a1899c6c37c44e0dd063d1af22acfa..1f4846cbb7bd9ae6dd580b18ab2b5395caa3882e 100644
--- a/civicrm/vendor/composer/installed.json
+++ b/civicrm/vendor/composer/installed.json
@@ -165,17 +165,17 @@
     },
     {
         "name": "civicrm/composer-downloads-plugin",
-        "version": "v2.0.0",
-        "version_normalized": "2.0.0.0",
+        "version": "v2.1.1",
+        "version_normalized": "2.1.1.0",
         "source": {
             "type": "git",
             "url": "https://github.com/civicrm/composer-downloads-plugin.git",
-            "reference": "869b7a12f57b2d912f0ea77d5c33c1518b8de27d"
+            "reference": "8722bc7d547315be39397a3078bb51ee053ca269"
         },
         "dist": {
             "type": "zip",
-            "url": "https://api.github.com/repos/civicrm/composer-downloads-plugin/zipball/869b7a12f57b2d912f0ea77d5c33c1518b8de27d",
-            "reference": "869b7a12f57b2d912f0ea77d5c33c1518b8de27d",
+            "url": "https://api.github.com/repos/civicrm/composer-downloads-plugin/zipball/8722bc7d547315be39397a3078bb51ee053ca269",
+            "reference": "8722bc7d547315be39397a3078bb51ee053ca269",
             "shasum": ""
         },
         "require": {
@@ -189,7 +189,7 @@
             "phpunit/phpunit": "^5.7",
             "totten/process-helper": "^1.0.1"
         },
-        "time": "2019-08-22T10:56:51+00:00",
+        "time": "2019-08-28T00:33:51+00:00",
         "type": "composer-plugin",
         "extra": {
             "class": "LastCall\\DownloadsPlugin\\Plugin"
@@ -2497,6 +2497,58 @@
             "time"
         ]
     },
+    {
+        "name": "typo3/phar-stream-wrapper",
+        "version": "v3.1.4",
+        "version_normalized": "3.1.4.0",
+        "source": {
+            "type": "git",
+            "url": "https://github.com/TYPO3/phar-stream-wrapper.git",
+            "reference": "e0c1b495cfac064f4f5c4bcb6bf67bb7f345ed04"
+        },
+        "dist": {
+            "type": "zip",
+            "url": "https://api.github.com/repos/TYPO3/phar-stream-wrapper/zipball/e0c1b495cfac064f4f5c4bcb6bf67bb7f345ed04",
+            "reference": "e0c1b495cfac064f4f5c4bcb6bf67bb7f345ed04",
+            "shasum": ""
+        },
+        "require": {
+            "ext-json": "*",
+            "php": "^7.0"
+        },
+        "require-dev": {
+            "ext-xdebug": "*",
+            "phpunit/phpunit": "^6.5"
+        },
+        "suggest": {
+            "ext-fileinfo": "For PHP builtin file type guessing, otherwise uses internal processing"
+        },
+        "time": "2019-12-10T11:53:27+00:00",
+        "type": "library",
+        "extra": {
+            "branch-alias": {
+                "dev-master": "v3.x-dev"
+            }
+        },
+        "installation-source": "dist",
+        "autoload": {
+            "psr-4": {
+                "TYPO3\\PharStreamWrapper\\": "src/"
+            }
+        },
+        "notification-url": "https://packagist.org/downloads/",
+        "license": [
+            "MIT"
+        ],
+        "description": "Interceptors for PHP's native phar:// stream handling",
+        "homepage": "https://typo3.org/",
+        "keywords": [
+            "phar",
+            "php",
+            "security",
+            "stream-wrapper"
+        ]
+    },
     {
         "name": "xkerman/restricted-unserialize",
         "version": "1.1.12",
diff --git a/civicrm/vendor/typo3/phar-stream-wrapper/LICENSE b/civicrm/vendor/typo3/phar-stream-wrapper/LICENSE
new file mode 100644
index 0000000000000000000000000000000000000000..d71267a1adb5529500cd0750e6d1d09544fadd38
--- /dev/null
+++ b/civicrm/vendor/typo3/phar-stream-wrapper/LICENSE
@@ -0,0 +1,21 @@
+MIT License
+
+Copyright (c) 2018 TYPO3 project - https://typo3.org/
+
+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/civicrm/vendor/typo3/phar-stream-wrapper/README.md b/civicrm/vendor/typo3/phar-stream-wrapper/README.md
new file mode 100644
index 0000000000000000000000000000000000000000..ae1c5cfaee14f8ad90eec4d671cd5ebf7bdd32f3
--- /dev/null
+++ b/civicrm/vendor/typo3/phar-stream-wrapper/README.md
@@ -0,0 +1,221 @@
+[![Scrutinizer Code Quality](https://scrutinizer-ci.com/g/TYPO3/phar-stream-wrapper/badges/quality-score.png?b=master)](https://scrutinizer-ci.com/g/TYPO3/phar-stream-wrapper/?branch=master)
+[![Travis CI Build Status](https://travis-ci.org/TYPO3/phar-stream-wrapper.svg?branch=master)](https://travis-ci.org/TYPO3/phar-stream-wrapper)
+[![AppVeyor Build status](https://ci.appveyor.com/api/projects/status/q4ls5tg4w1d6sf4i/branch/master?svg=true)](https://ci.appveyor.com/project/ohader/phar-stream-wrapper)
+
+# PHP Phar Stream Wrapper
+
+## Abstract & History
+
+Based on Sam Thomas' findings concerning
+[insecure deserialization in combination with obfuscation strategies](https://blog.secarma.co.uk/labs/near-phar-dangerous-unserialization-wherever-you-are)
+allowing to hide Phar files inside valid image resources, the TYPO3 project
+decided back then to introduce a `PharStreamWrapper` to intercept invocations
+of the `phar://` stream in PHP and only allow usage for defined locations in
+the file system.
+
+Since the TYPO3 mission statement is **inspiring people to share**, we thought
+it would be helpful for others to release our `PharStreamWrapper` as standalone
+package to the PHP community.
+
+The mentioned security issue was reported to TYPO3 on 10th June 2018 by Sam Thomas
+and has been addressed concerning the specific attack vector and for this generic
+`PharStreamWrapper` in TYPO3 versions 7.6.30 LTS, 8.7.17 LTS and 9.3.1 on 12th
+July 2018.
+
+* https://blog.secarma.co.uk/labs/near-phar-dangerous-unserialization-wherever-you-are
+* https://youtu.be/GePBmsNJw6Y
+* https://typo3.org/security/advisory/typo3-psa-2018-001/
+* https://typo3.org/security/advisory/typo3-psa-2019-007/
+* https://typo3.org/security/advisory/typo3-psa-2019-008/
+
+## License
+
+In general the TYPO3 core is released under the GNU General Public License version
+2 or any later version (`GPL-2.0-or-later`). In order to avoid licensing issues and
+incompatibilities this `PharStreamWrapper` is licenced under the MIT License. In case
+you duplicate or modify source code, credits are not required but really appreciated.
+
+## Credits
+
+Thanks to [Alex Pott](https://github.com/alexpott), Drupal for creating
+back-ports of all sources in order to provide compatibility with PHP v5.3.
+
+## Installation
+
+The `PharStreamWrapper` is provided as composer package `typo3/phar-stream-wrapper`
+and has minimum requirements of PHP v5.3 ([`v2`](https://github.com/TYPO3/phar-stream-wrapper/tree/v2) branch) and PHP v7.0 ([`master`](https://github.com/TYPO3/phar-stream-wrapper) branch).
+
+### Installation for PHP v7.0
+
+```
+composer require typo3/phar-stream-wrapper ^3.0
+```
+
+### Installation for PHP v5.3
+
+```
+composer require typo3/phar-stream-wrapper ^2.0
+```
+
+## Example
+
+The following example is bundled within this package, the shown
+`PharExtensionInterceptor` denies all stream wrapper invocations files
+not having the `.phar` suffix. Interceptor logic has to be individual and
+adjusted to according requirements.
+
+```
+\TYPO3\PharStreamWrapper\Manager::initialize(
+    (new \TYPO3\PharStreamWrapper\Behavior())
+        ->withAssertion(new \TYPO3\PharStreamWrapper\Interceptor\PharExtensionInterceptor())
+);
+
+if (in_array('phar', stream_get_wrappers())) {
+    stream_wrapper_unregister('phar');
+    stream_wrapper_register('phar', \TYPO3\PharStreamWrapper\PharStreamWrapper::class);
+}
+```
+
+* `PharStreamWrapper` defined as class reference will be instantiated each time
+  `phar://` streams shall be processed.
+* `Manager` as singleton pattern being called by `PharStreamWrapper` instances
+  in order to retrieve individual behavior and settings.
+* `Behavior` holds reference to interceptor(s) that shall assert correct/allowed
+  invocation of a given `$path` for a given `$command`. Interceptors implement
+  the interface `Assertable`. Interceptors can act individually on following
+  commands or handle all of them in case not defined specifically:  
+  + `COMMAND_DIR_OPENDIR`
+  + `COMMAND_MKDIR`
+  + `COMMAND_RENAME`
+  + `COMMAND_RMDIR`
+  + `COMMAND_STEAM_METADATA`
+  + `COMMAND_STREAM_OPEN`
+  + `COMMAND_UNLINK`
+  + `COMMAND_URL_STAT`
+
+## Interceptors
+
+The following interceptor is shipped with the package and ready to use in order
+to block any Phar invocation of files not having a `.phar` suffix. Besides that
+individual interceptors are possible of course.
+
+```
+class PharExtensionInterceptor implements Assertable
+{
+    /**
+     * Determines whether the base file name has a ".phar" suffix.
+     *
+     * @param string $path
+     * @param string $command
+     * @return bool
+     * @throws Exception
+     */
+    public function assert(string $path, string $command): bool
+    {
+        if ($this->baseFileContainsPharExtension($path)) {
+            return true;
+        }
+        throw new Exception(
+            sprintf(
+                'Unexpected file extension in "%s"',
+                $path
+            ),
+            1535198703
+        );
+    }
+
+    /**
+     * @param string $path
+     * @return bool
+     */
+    private function baseFileContainsPharExtension(string $path): bool
+    {
+        $baseFile = Helper::determineBaseFile($path);
+        if ($baseFile === null) {
+            return false;
+        }
+        $fileExtension = pathinfo($baseFile, PATHINFO_EXTENSION);
+        return strtolower($fileExtension) === 'phar';
+    }
+}
+```
+
+### ConjunctionInterceptor
+
+This interceptor combines multiple interceptors implementing `Assertable`.
+It succeeds when all nested interceptors succeed as well (logical `AND`).
+
+```
+\TYPO3\PharStreamWrapper\Manager::initialize(
+    (new \TYPO3\PharStreamWrapper\Behavior())
+        ->withAssertion(new ConjunctionInterceptor([
+            new PharExtensionInterceptor(),
+            new PharMetaDataInterceptor(),
+        ]))
+);
+```
+
+### PharExtensionInterceptor
+
+This (basic) interceptor just checks whether the invoked Phar archive has
+an according `.phar` file extension. Resolving symbolic links as well as
+Phar internal alias resolving are considered as well.
+
+```
+\TYPO3\PharStreamWrapper\Manager::initialize(
+    (new \TYPO3\PharStreamWrapper\Behavior())
+        ->withAssertion(new PharExtensionInterceptor())
+);
+```
+
+### PharMetaDataInterceptor
+
+This interceptor is actually checking serialized Phar meta-data against
+PHP objects and would consider a Phar archive malicious in case not only
+scalar values are found. A custom low-level `Phar\Reader` is used in order to
+avoid using PHP's `Phar` object which would trigger the initial vulnerability.
+
+```
+\TYPO3\PharStreamWrapper\Manager::initialize(
+    (new \TYPO3\PharStreamWrapper\Behavior())
+        ->withAssertion(new PharMetaDataInterceptor())
+);
+```
+
+## Reader
+
+* `Phar\Reader::__construct(string $fileName)`: Creates low-level reader for Phar archive
+* `Phar\Reader::resolveContainer(): Phar\Container`: Resolves model representing Phar archive
+* `Phar\Container::getStub(): Phar\Stub`: Resolves (plain PHP) stub section of Phar archive
+* `Phar\Container::getManifest(): Phar\Manifest`: Resolves parsed Phar archive manifest as
+  documented at http://php.net/manual/en/phar.fileformat.manifestfile.php
+* `Phar\Stub::getMappedAlias(): string`: Resolves internal Phar archive alias defined in stub
+  using `Phar::mapPhar('alias.phar')` - actually the plain PHP source is analyzed here
+* `Phar\Manifest::getAlias(): string` - Resolves internal Phar archive alias defined in manifest
+  using `Phar::setAlias('alias.phar')`
+* `Phar\Manifest::getMetaData(): string`: Resolves serialized Phar archive meta-data
+* `Phar\Manifest::deserializeMetaData(): mixed`: Resolves deserialized Phar archive meta-data
+  containing only scalar values - in case an object is determined, an according
+  `Phar\DeserializationException` will be thrown
+
+```
+$reader = new Phar\Reader('example.phar');
+var_dump($reader->resolveContainer()->getManifest()->deserializeMetaData());
+```
+
+## Helper
+
+* `Helper::determineBaseFile(string $path): string`: Determines base file that can be
+  accessed using the regular file system. For instance the following path
+  `phar:///home/user/bundle.phar/content.txt` would be resolved to
+  `/home/user/bundle.phar`.
+* `Helper::resetOpCache()`: Resets PHP's OPcache if enabled as work-around for
+  issues in `include()` or `require()` calls and OPcache delivering wrong
+  results. More details can be found in PHP's bug tracker, for instance like
+  https://bugs.php.net/bug.php?id=66569
+
+## Security Contact
+
+In case of finding additional security issues in the TYPO3 project or in this
+`PharStreamWrapper` package in particular, please get in touch with the
+[TYPO3 Security Team](mailto:security@typo3.org).
diff --git a/civicrm/vendor/typo3/phar-stream-wrapper/_config.yml b/civicrm/vendor/typo3/phar-stream-wrapper/_config.yml
new file mode 100644
index 0000000000000000000000000000000000000000..c7418817439b2f071c93a4a6cee831e996123c0b
--- /dev/null
+++ b/civicrm/vendor/typo3/phar-stream-wrapper/_config.yml
@@ -0,0 +1 @@
+theme: jekyll-theme-slate
\ No newline at end of file
diff --git a/civicrm/vendor/typo3/phar-stream-wrapper/composer.json b/civicrm/vendor/typo3/phar-stream-wrapper/composer.json
new file mode 100644
index 0000000000000000000000000000000000000000..6c1b61d86e1aa06d40fde69ddb038fc5a30be31f
--- /dev/null
+++ b/civicrm/vendor/typo3/phar-stream-wrapper/composer.json
@@ -0,0 +1,34 @@
+{
+    "name": "typo3/phar-stream-wrapper",
+    "description": "Interceptors for PHP's native phar:// stream handling",
+    "type": "library",
+    "license": "MIT",
+    "homepage": "https://typo3.org/",
+    "keywords": ["php", "phar", "stream-wrapper", "security"],
+    "require": {
+        "php": "^7.0",
+        "ext-json": "*"
+    },
+    "require-dev": {
+        "ext-xdebug": "*",
+        "phpunit/phpunit": "^6.5"
+    },
+    "suggest": {
+        "ext-fileinfo": "For PHP builtin file type guessing, otherwise uses internal processing"
+    },
+    "autoload": {
+        "psr-4": {
+            "TYPO3\\PharStreamWrapper\\": "src/"
+        }
+    },
+    "autoload-dev": {
+        "psr-4": {
+            "TYPO3\\PharStreamWrapper\\Tests\\": "tests/"
+        }
+    },
+    "extra": {
+        "branch-alias": {
+            "dev-master": "v3.x-dev"
+        }
+    }
+}
diff --git a/civicrm/vendor/typo3/phar-stream-wrapper/src/Assertable.php b/civicrm/vendor/typo3/phar-stream-wrapper/src/Assertable.php
new file mode 100644
index 0000000000000000000000000000000000000000..32add3e8209a70fe0d8ab350990e7571a8578c45
--- /dev/null
+++ b/civicrm/vendor/typo3/phar-stream-wrapper/src/Assertable.php
@@ -0,0 +1,23 @@
+<?php
+declare(strict_types=1);
+namespace TYPO3\PharStreamWrapper;
+
+/*
+ * This file is part of the TYPO3 project.
+ *
+ * It is free software; you can redistribute it and/or modify it under the terms
+ * of the MIT License (MIT). For the full copyright and license information,
+ * please read the LICENSE file that was distributed with this source code.
+ *
+ * The TYPO3 project - inspiring people to share!
+ */
+
+interface Assertable
+{
+    /**
+     * @param string $path
+     * @param string $command
+     * @return bool
+     */
+    public function assert(string $path, string $command): bool;
+}
diff --git a/civicrm/vendor/typo3/phar-stream-wrapper/src/Behavior.php b/civicrm/vendor/typo3/phar-stream-wrapper/src/Behavior.php
new file mode 100644
index 0000000000000000000000000000000000000000..a145e26cc76e5211b0786e5c05c0123851bb0bf8
--- /dev/null
+++ b/civicrm/vendor/typo3/phar-stream-wrapper/src/Behavior.php
@@ -0,0 +1,124 @@
+<?php
+declare(strict_types=1);
+namespace TYPO3\PharStreamWrapper;
+
+/*
+ * This file is part of the TYPO3 project.
+ *
+ * It is free software; you can redistribute it and/or modify it under the terms
+ * of the MIT License (MIT). For the full copyright and license information,
+ * please read the LICENSE file that was distributed with this source code.
+ *
+ * The TYPO3 project - inspiring people to share!
+ */
+
+class Behavior implements Assertable
+{
+    const COMMAND_DIR_OPENDIR = 'dir_opendir';
+    const COMMAND_MKDIR = 'mkdir';
+    const COMMAND_RENAME = 'rename';
+    const COMMAND_RMDIR = 'rmdir';
+    const COMMAND_STEAM_METADATA = 'stream_metadata';
+    const COMMAND_STREAM_OPEN = 'stream_open';
+    const COMMAND_UNLINK = 'unlink';
+    const COMMAND_URL_STAT = 'url_stat';
+
+    /**
+     * @var string[]
+     */
+    private $availableCommands = [
+        self::COMMAND_DIR_OPENDIR,
+        self::COMMAND_MKDIR,
+        self::COMMAND_RENAME,
+        self::COMMAND_RMDIR,
+        self::COMMAND_STEAM_METADATA,
+        self::COMMAND_STREAM_OPEN,
+        self::COMMAND_UNLINK,
+        self::COMMAND_URL_STAT,
+    ];
+
+    /**
+     * @var Assertable[]
+     */
+    private $assertions;
+
+    /**
+     * @param Assertable $assertable
+     * @param string ...$commands
+     * @return static
+     */
+    public function withAssertion(Assertable $assertable, string ...$commands): self
+    {
+        $this->assertCommands($commands);
+        $commands = $commands ?: $this->availableCommands;
+
+        $target = clone $this;
+        foreach ($commands as $command) {
+            $target->assertions[$command] = $assertable;
+        }
+        return $target;
+    }
+
+    /**
+     * @param string $path
+     * @param string $command
+     * @return bool
+     */
+    public function assert(string $path, string $command): bool
+    {
+        $this->assertCommand($command);
+        $this->assertAssertionCompleteness();
+
+        return $this->assertions[$command]->assert($path, $command);
+    }
+
+    /**
+     * @param array $commands
+     */
+    private function assertCommands(array $commands)
+    {
+        $unknownCommands = array_diff($commands, $this->availableCommands);
+        if (empty($unknownCommands)) {
+            return;
+        }
+        throw new \LogicException(
+            sprintf(
+                'Unknown commands: %s',
+                implode(', ', $unknownCommands)
+            ),
+            1535189881
+        );
+    }
+
+    private function assertCommand(string $command)
+    {
+        if (in_array($command, $this->availableCommands, true)) {
+            return;
+        }
+        throw new \LogicException(
+            sprintf(
+                'Unknown command "%s"',
+                $command
+            ),
+            1535189882
+        );
+    }
+
+    private function assertAssertionCompleteness()
+    {
+        $undefinedAssertions = array_diff(
+            $this->availableCommands,
+            array_keys($this->assertions)
+        );
+        if (empty($undefinedAssertions)) {
+            return;
+        }
+        throw new \LogicException(
+            sprintf(
+                'Missing assertions for commands: %s',
+                implode(', ', $undefinedAssertions)
+            ),
+            1535189883
+        );
+    }
+}
diff --git a/civicrm/vendor/typo3/phar-stream-wrapper/src/Collectable.php b/civicrm/vendor/typo3/phar-stream-wrapper/src/Collectable.php
new file mode 100644
index 0000000000000000000000000000000000000000..97c9356f812135363d6629d568d5a2d56efa3d9b
--- /dev/null
+++ b/civicrm/vendor/typo3/phar-stream-wrapper/src/Collectable.php
@@ -0,0 +1,38 @@
+<?php
+declare(strict_types=1);
+namespace TYPO3\PharStreamWrapper;
+
+/*
+ * This file is part of the TYPO3 project.
+ *
+ * It is free software; you can redistribute it and/or modify it under the terms
+ * of the MIT License (MIT). For the full copyright and license information,
+ * please read the LICENSE file that was distributed with this source code.
+ *
+ * The TYPO3 project - inspiring people to share!
+ */
+
+use TYPO3\PharStreamWrapper\Resolver\PharInvocation;
+
+interface Collectable
+{
+    /**
+     * @param PharInvocation $invocation
+     * @return bool
+     */
+    public function has(PharInvocation $invocation): bool;
+
+    /**
+     * @param PharInvocation $invocation
+     * @param int|null $flags
+     * @return bool
+     */
+    public function collect(PharInvocation $invocation, int $flags = null): bool;
+
+    /**
+     * @param callable $callback
+     * @param bool $reverse
+     * @return null|PharInvocation
+     */
+    public function findByCallback(callable $callback, $reverse = false);
+}
diff --git a/civicrm/vendor/typo3/phar-stream-wrapper/src/Exception.php b/civicrm/vendor/typo3/phar-stream-wrapper/src/Exception.php
new file mode 100644
index 0000000000000000000000000000000000000000..859a04275ddce5e02e232618fe36f01500a70ed7
--- /dev/null
+++ b/civicrm/vendor/typo3/phar-stream-wrapper/src/Exception.php
@@ -0,0 +1,17 @@
+<?php
+declare(strict_types=1);
+namespace TYPO3\PharStreamWrapper;
+
+/*
+ * This file is part of the TYPO3 project.
+ *
+ * It is free software; you can redistribute it and/or modify it under the terms
+ * of the MIT License (MIT). For the full copyright and license information,
+ * please read the LICENSE file that was distributed with this source code.
+ *
+ * The TYPO3 project - inspiring people to share!
+ */
+
+class Exception extends \RuntimeException
+{
+}
diff --git a/civicrm/vendor/typo3/phar-stream-wrapper/src/Helper.php b/civicrm/vendor/typo3/phar-stream-wrapper/src/Helper.php
new file mode 100644
index 0000000000000000000000000000000000000000..92e2f77871d83a711d0c70d71f24333a7d16dee8
--- /dev/null
+++ b/civicrm/vendor/typo3/phar-stream-wrapper/src/Helper.php
@@ -0,0 +1,198 @@
+<?php
+declare(strict_types=1);
+namespace TYPO3\PharStreamWrapper;
+
+/*
+ * This file is part of the TYPO3 project.
+ *
+ * It is free software; you can redistribute it and/or modify it under the terms
+ * of the MIT License (MIT). For the full copyright and license information,
+ * please read the LICENSE file that was distributed with this source code.
+ *
+ * The TYPO3 project - inspiring people to share!
+ */
+
+/**
+ * Helper provides low-level tools on file name resolving. However it does not
+ * (and should not) maintain any runtime state information. In order to resolve
+ * Phar archive paths according resolvers have to be used.
+ *
+ * @see \TYPO3\PharStreamWrapper\Resolvable::resolve()
+ */
+class Helper
+{
+    /*
+     * Resets PHP's OPcache if enabled as work-around for issues in `include()`
+     * or `require()` calls and OPcache delivering wrong results.
+     *
+     * @see https://bugs.php.net/bug.php?id=66569
+     */
+    public static function resetOpCache()
+    {
+        if (function_exists('opcache_reset')
+            && function_exists('opcache_get_status')
+            && !empty(opcache_get_status()['opcache_enabled'])
+        ) {
+            opcache_reset();
+        }
+    }
+
+    /**
+     * Determines base file that can be accessed using the regular file system.
+     * For e.g. "phar:///home/user/bundle.phar/content.txt" that would result
+     * into "/home/user/bundle.phar".
+     *
+     * @param string $path
+     * @return string|null
+     */
+    public static function determineBaseFile(string $path)
+    {
+        $parts = explode('/', static::normalizePath($path));
+
+        while (count($parts)) {
+            $currentPath = implode('/', $parts);
+            if (@is_file($currentPath) && realpath($currentPath) !== false) {
+                return $currentPath;
+            }
+            array_pop($parts);
+        }
+
+        return null;
+    }
+
+    /**
+     * @param string $path
+     * @return bool
+     */
+    public static function hasPharPrefix(string $path): bool
+    {
+        return stripos($path, 'phar://') === 0;
+    }
+
+    /**
+     * @param string $path
+     * @return string
+     */
+    public static function removePharPrefix(string $path): string
+    {
+        $path = trim($path);
+        if (!static::hasPharPrefix($path)) {
+            return $path;
+        }
+        return substr($path, 7);
+    }
+
+    /**
+     * Normalizes a path, removes phar:// prefix, fixes Windows directory
+     * separators. Result is without trailing slash.
+     *
+     * @param string $path
+     * @return string
+     */
+    public static function normalizePath(string $path): string
+    {
+        return rtrim(
+            static::normalizeWindowsPath(
+                static::removePharPrefix($path)
+            ),
+            '/'
+        );
+    }
+
+    /**
+     * Fixes a path for windows-backslashes and reduces double-slashes to single slashes
+     *
+     * @param string $path File path to process
+     * @return string
+     */
+    public static function normalizeWindowsPath(string $path): string
+    {
+        return str_replace('\\', '/', $path);
+    }
+
+    /**
+     * Resolves all dots, slashes and removes spaces after or before a path...
+     *
+     * @param string $path Input string
+     * @return string Canonical path, always without trailing slash
+     */
+    private static function getCanonicalPath($path): string
+    {
+        $path = static::normalizeWindowsPath($path);
+
+        $absolutePathPrefix = '';
+        if (static::isAbsolutePath($path)) {
+            if (static::isWindows() && strpos($path, ':/') === 1) {
+                $absolutePathPrefix = substr($path, 0, 3);
+                $path = substr($path, 3);
+            } else {
+                $path = ltrim($path, '/');
+                $absolutePathPrefix = '/';
+            }
+        }
+
+        $pathParts = explode('/', $path);
+        $pathPartsLength = count($pathParts);
+        for ($partCount = 0; $partCount < $pathPartsLength; $partCount++) {
+            // double-slashes in path: remove element
+            if ($pathParts[$partCount] === '') {
+                array_splice($pathParts, $partCount, 1);
+                $partCount--;
+                $pathPartsLength--;
+            }
+            // "." in path: remove element
+            if (($pathParts[$partCount] ?? '') === '.') {
+                array_splice($pathParts, $partCount, 1);
+                $partCount--;
+                $pathPartsLength--;
+            }
+            // ".." in path:
+            if (($pathParts[$partCount] ?? '') === '..') {
+                if ($partCount === 0) {
+                    array_splice($pathParts, $partCount, 1);
+                    $partCount--;
+                    $pathPartsLength--;
+                } elseif ($partCount >= 1) {
+                    // Rremove this and previous element
+                    array_splice($pathParts, $partCount - 1, 2);
+                    $partCount -= 2;
+                    $pathPartsLength -= 2;
+                } elseif ($absolutePathPrefix) {
+                    // can't go higher than root dir
+                    // simply remove this part and continue
+                    array_splice($pathParts, $partCount, 1);
+                    $partCount--;
+                    $pathPartsLength--;
+                }
+            }
+        }
+
+        return $absolutePathPrefix . implode('/', $pathParts);
+    }
+
+    /**
+     * Checks if the $path is absolute or relative (detecting either '/' or
+     * 'x:/' as first part of string) and returns TRUE if so.
+     *
+     * @param string $path File path to evaluate
+     * @return bool
+     */
+    private static function isAbsolutePath($path): bool
+    {
+        // Path starting with a / is always absolute, on every system
+        // On Windows also a path starting with a drive letter is absolute: X:/
+        return ($path[0] ?? null) === '/'
+            || static::isWindows() && (
+                strpos($path, ':/') === 1
+                || strpos($path, ':\\') === 1
+            );
+    }
+
+    /**
+     * @return bool
+     */
+    private static function isWindows(): bool
+    {
+        return stripos(PHP_OS, 'WIN') === 0;
+    }
+}
\ No newline at end of file
diff --git a/civicrm/vendor/typo3/phar-stream-wrapper/src/Interceptor/ConjunctionInterceptor.php b/civicrm/vendor/typo3/phar-stream-wrapper/src/Interceptor/ConjunctionInterceptor.php
new file mode 100644
index 0000000000000000000000000000000000000000..1a85f597bdfeeb5e51c2ac2ce6d97ef0bc5092c7
--- /dev/null
+++ b/civicrm/vendor/typo3/phar-stream-wrapper/src/Interceptor/ConjunctionInterceptor.php
@@ -0,0 +1,89 @@
+<?php
+declare(strict_types=1);
+namespace TYPO3\PharStreamWrapper\Interceptor;
+
+/*
+ * This file is part of the TYPO3 project.
+ *
+ * It is free software; you can redistribute it and/or modify it under the terms
+ * of the MIT License (MIT). For the full copyright and license information,
+ * please read the LICENSE file that was distributed with this source code.
+ *
+ * The TYPO3 project - inspiring people to share!
+ */
+
+use TYPO3\PharStreamWrapper\Assertable;
+use TYPO3\PharStreamWrapper\Exception;
+
+class ConjunctionInterceptor implements Assertable
+{
+    /**
+     * @var Assertable[]
+     */
+    private $assertions;
+
+    public function __construct(array $assertions)
+    {
+        $this->assertAssertions($assertions);
+        $this->assertions = $assertions;
+    }
+
+    /**
+     * Executes assertions based on all contained assertions.
+     *
+     * @param string $path
+     * @param string $command
+     * @return bool
+     * @throws Exception
+     */
+    public function assert(string $path, string $command): bool
+    {
+        if ($this->invokeAssertions($path, $command)) {
+            return true;
+        }
+        throw new Exception(
+            sprintf(
+                'Assertion failed in "%s"',
+                $path
+            ),
+            1539625084
+        );
+    }
+
+    /**
+     * @param Assertable[] $assertions
+     */
+    private function assertAssertions(array $assertions)
+    {
+        foreach ($assertions as $assertion) {
+            if (!$assertion instanceof Assertable) {
+                throw new \InvalidArgumentException(
+                    sprintf(
+                        'Instance %s must implement Assertable',
+                        get_class($assertion)
+                    ),
+                    1539624719
+                );
+            }
+        }
+    }
+
+    /**
+     * @param string $path
+     * @param string $command
+     * @return bool
+     */
+    private function invokeAssertions(string $path, string $command): bool
+    {
+        try {
+            foreach ($this->assertions as $assertion) {
+                if (!$assertion->assert($path, $command)) {
+                    return false;
+                }
+            }
+        } catch (Exception $exception) {
+            return false;
+        }
+        return true;
+    }
+}
diff --git a/civicrm/vendor/typo3/phar-stream-wrapper/src/Interceptor/PharExtensionInterceptor.php b/civicrm/vendor/typo3/phar-stream-wrapper/src/Interceptor/PharExtensionInterceptor.php
new file mode 100644
index 0000000000000000000000000000000000000000..df2c4483d6221e6fd9089735124fa2665f5206a6
--- /dev/null
+++ b/civicrm/vendor/typo3/phar-stream-wrapper/src/Interceptor/PharExtensionInterceptor.php
@@ -0,0 +1,56 @@
+<?php
+declare(strict_types=1);
+namespace TYPO3\PharStreamWrapper\Interceptor;
+
+/*
+ * This file is part of the TYPO3 project.
+ *
+ * It is free software; you can redistribute it and/or modify it under the terms
+ * of the MIT License (MIT). For the full copyright and license information,
+ * please read the LICENSE file that was distributed with this source code.
+ *
+ * The TYPO3 project - inspiring people to share!
+ */
+
+use TYPO3\PharStreamWrapper\Assertable;
+use TYPO3\PharStreamWrapper\Exception;
+use TYPO3\PharStreamWrapper\Manager;
+
+class PharExtensionInterceptor implements Assertable
+{
+    /**
+     * Determines whether the base file name has a ".phar" suffix.
+     *
+     * @param string $path
+     * @param string $command
+     * @return bool
+     * @throws Exception
+     */
+    public function assert(string $path, string $command): bool
+    {
+        if ($this->baseFileContainsPharExtension($path)) {
+            return true;
+        }
+        throw new Exception(
+            sprintf(
+                'Unexpected file extension in "%s"',
+                $path
+            ),
+            1535198703
+        );
+    }
+
+    /**
+     * @param string $path
+     * @return bool
+     */
+    private function baseFileContainsPharExtension(string $path): bool
+    {
+        $invocation = Manager::instance()->resolve($path);
+        if ($invocation === null) {
+            return false;
+        }
+        $fileExtension = pathinfo($invocation->getBaseName(), PATHINFO_EXTENSION);
+        return strtolower($fileExtension) === 'phar';
+    }
+}
diff --git a/civicrm/vendor/typo3/phar-stream-wrapper/src/Interceptor/PharMetaDataInterceptor.php b/civicrm/vendor/typo3/phar-stream-wrapper/src/Interceptor/PharMetaDataInterceptor.php
new file mode 100644
index 0000000000000000000000000000000000000000..e818215d5ce85491c195e066131df757677c83ff
--- /dev/null
+++ b/civicrm/vendor/typo3/phar-stream-wrapper/src/Interceptor/PharMetaDataInterceptor.php
@@ -0,0 +1,74 @@
+<?php
+declare(strict_types=1);
+namespace TYPO3\PharStreamWrapper\Interceptor;
+
+/*
+ * This file is part of the TYPO3 project.
+ *
+ * It is free software; you can redistribute it and/or modify it under the terms
+ * of the MIT License (MIT). For the full copyright and license information,
+ * please read the LICENSE file that was distributed with this source code.
+ *
+ * The TYPO3 project - inspiring people to share!
+ */
+
+use TYPO3\PharStreamWrapper\Assertable;
+use TYPO3\PharStreamWrapper\Exception;
+use TYPO3\PharStreamWrapper\Manager;
+use TYPO3\PharStreamWrapper\Phar\DeserializationException;
+use TYPO3\PharStreamWrapper\Phar\Reader;
+
+/**
+ * @internal Experimental implementation of checking against serialized objects in Phar meta-data
+ * @internal This functionality has not been 100% pentested...
+ */
+class PharMetaDataInterceptor implements Assertable
+{
+    /**
+     * Determines whether the according Phar archive contains
+     * (potential insecure) serialized objects.
+     *
+     * @param string $path
+     * @param string $command
+     * @return bool
+     * @throws Exception
+     */
+    public function assert(string $path, string $command): bool
+    {
+        if ($this->baseFileDoesNotHaveMetaDataIssues($path)) {
+            return true;
+        }
+        throw new Exception(
+            sprintf(
+                'Problematic meta-data in "%s"',
+                $path
+            ),
+            1539632368
+        );
+    }
+
+    /**
+     * @param string $path
+     * @return bool
+     */
+    private function baseFileDoesNotHaveMetaDataIssues(string $path): bool
+    {
+        $invocation = Manager::instance()->resolve($path);
+        if ($invocation === null) {
+            return false;
+        }
+        // directly return in case invocation was checked before
+        if ($invocation->getVariable(self::class) === true) {
+            return true;
+        }
+        // otherwise analyze meta-data
+        try {
+            $reader = new Reader($invocation->getBaseName());
+            $reader->resolveContainer()->getManifest()->deserializeMetaData();
+            $invocation->setVariable(self::class, true);
+        } catch (DeserializationException $exception) {
+            return false;
+        }
+        return true;
+    }
+}
diff --git a/civicrm/vendor/typo3/phar-stream-wrapper/src/Manager.php b/civicrm/vendor/typo3/phar-stream-wrapper/src/Manager.php
new file mode 100644
index 0000000000000000000000000000000000000000..aad63b5eae2438f994260f1311586023c6a98c81
--- /dev/null
+++ b/civicrm/vendor/typo3/phar-stream-wrapper/src/Manager.php
@@ -0,0 +1,130 @@
+<?php
+declare(strict_types=1);
+namespace TYPO3\PharStreamWrapper;
+
+/*
+ * This file is part of the TYPO3 project.
+ *
+ * It is free software; you can redistribute it and/or modify it under the terms
+ * of the MIT License (MIT). For the full copyright and license information,
+ * please read the LICENSE file that was distributed with this source code.
+ *
+ * The TYPO3 project - inspiring people to share!
+ */
+
+use TYPO3\PharStreamWrapper\Resolver\PharInvocationResolver;
+use TYPO3\PharStreamWrapper\Resolver\PharInvocation;
+use TYPO3\PharStreamWrapper\Resolver\PharInvocationCollection;
+
+class Manager
+{
+    /**
+     * @var self
+     */
+    private static $instance;
+
+    /**
+     * @var Behavior
+     */
+    private $behavior;
+
+    /**
+     * @var Resolvable
+     */
+    private $resolver;
+
+    /**
+     * @var Collectable
+     */
+    private $collection;
+
+    /**
+     * @param Behavior $behaviour
+     * @param Resolvable $resolver
+     * @param Collectable $collection
+     * @return self
+     */
+    public static function initialize(
+        Behavior $behaviour,
+        Resolvable $resolver = null,
+        Collectable $collection = null
+    ): self {
+        if (self::$instance === null) {
+            self::$instance = new self($behaviour, $resolver, $collection);
+            return self::$instance;
+        }
+        throw new \LogicException(
+            'Manager can only be initialized once',
+            1535189871
+        );
+    }
+
+    /**
+     * @return self
+     */
+    public static function instance(): self
+    {
+        if (self::$instance !== null) {
+            return self::$instance;
+        }
+        throw new \LogicException(
+            'Manager needs to be initialized first',
+            1535189872
+        );
+    }
+
+    /**
+     * @return bool
+     */
+    public static function destroy(): bool
+    {
+        if (self::$instance === null) {
+            return false;
+        }
+        self::$instance = null;
+        return true;
+    }
+
+    /**
+     * @param Behavior $behaviour
+     * @param Resolvable $resolver
+     * @param Collectable $collection
+     */
+    private function __construct(
+        Behavior $behaviour,
+        Resolvable $resolver = null,
+        Collectable $collection = null
+    ) {
+        $this->collection = $collection ?? new PharInvocationCollection();
+        $this->resolver = $resolver ?? new PharInvocationResolver();
+        $this->behavior = $behaviour;
+    }
+
+    /**
+     * @param string $path
+     * @param string $command
+     * @return bool
+     */
+    public function assert(string $path, string $command): bool
+    {
+        return $this->behavior->assert($path, $command);
+    }
+
+    /**
+     * @param string $path
+     * @param null|int $flags
+     * @return PharInvocation|null
+     */
+    public function resolve(string $path, int $flags = null)
+    {
+        return $this->resolver->resolve($path, $flags);
+    }
+
+    /**
+     * @return Collectable
+     */
+    public function getCollection(): Collectable
+    {
+        return $this->collection;
+    }
+}
diff --git a/civicrm/vendor/typo3/phar-stream-wrapper/src/Phar/Container.php b/civicrm/vendor/typo3/phar-stream-wrapper/src/Phar/Container.php
new file mode 100644
index 0000000000000000000000000000000000000000..e1abf995c26c619025d04500fe9890a70e1aafa9
--- /dev/null
+++ b/civicrm/vendor/typo3/phar-stream-wrapper/src/Phar/Container.php
@@ -0,0 +1,60 @@
+<?php
+declare(strict_types=1);
+namespace TYPO3\PharStreamWrapper\Phar;
+
+/*
+ * This file is part of the TYPO3 project.
+ *
+ * It is free software; you can redistribute it and/or modify it under the terms
+ * of the MIT License (MIT). For the full copyright and license information,
+ * please read the LICENSE file that was distributed with this source code.
+ *
+ * The TYPO3 project - inspiring people to share!
+ */
+
+class Container
+{
+    /**
+     * @var Stub
+     */
+    private $stub;
+
+    /**
+     * @var Manifest
+     */
+    private $manifest;
+
+    /**
+     * @param Stub $stub
+     * @param Manifest $manifest
+     */
+    public function __construct(Stub $stub, Manifest $manifest)
+    {
+        $this->stub = $stub;
+        $this->manifest = $manifest;
+    }
+
+    /**
+     * @return Stub
+     */
+    public function getStub(): Stub
+    {
+        return $this->stub;
+    }
+
+    /**
+     * @return Manifest
+     */
+    public function getManifest(): Manifest
+    {
+        return $this->manifest;
+    }
+
+    /**
+     * @return string
+     */
+    public function getAlias(): string
+    {
+        return $this->manifest->getAlias() ?: $this->stub->getMappedAlias();
+    }
+}
diff --git a/civicrm/vendor/typo3/phar-stream-wrapper/src/Phar/DeserializationException.php b/civicrm/vendor/typo3/phar-stream-wrapper/src/Phar/DeserializationException.php
new file mode 100644
index 0000000000000000000000000000000000000000..c12e276ba59268ef92a14af3316590a5411b4c60
--- /dev/null
+++ b/civicrm/vendor/typo3/phar-stream-wrapper/src/Phar/DeserializationException.php
@@ -0,0 +1,19 @@
+<?php
+declare(strict_types=1);
+namespace TYPO3\PharStreamWrapper\Phar;
+
+/*
+ * This file is part of the TYPO3 project.
+ *
+ * It is free software; you can redistribute it and/or modify it under the terms
+ * of the MIT License (MIT). For the full copyright and license information,
+ * please read the LICENSE file that was distributed with this source code.
+ *
+ * The TYPO3 project - inspiring people to share!
+ */
+
+use TYPO3\PharStreamWrapper\Exception;
+
+class DeserializationException extends Exception
+{
+}
diff --git a/civicrm/vendor/typo3/phar-stream-wrapper/src/Phar/Manifest.php b/civicrm/vendor/typo3/phar-stream-wrapper/src/Phar/Manifest.php
new file mode 100644
index 0000000000000000000000000000000000000000..91968f9eb64a2264f56d46295c83517b9a6ed01f
--- /dev/null
+++ b/civicrm/vendor/typo3/phar-stream-wrapper/src/Phar/Manifest.php
@@ -0,0 +1,175 @@
+<?php
+declare(strict_types=1);
+namespace TYPO3\PharStreamWrapper\Phar;
+
+/*
+ * This file is part of the TYPO3 project.
+ *
+ * It is free software; you can redistribute it and/or modify it under the terms
+ * of the MIT License (MIT). For the full copyright and license information,
+ * please read the LICENSE file that was distributed with this source code.
+ *
+ * The TYPO3 project - inspiring people to share!
+ */
+
+class Manifest
+{
+    /**
+     * @param string $content
+     * @return self
+     * @see http://php.net/manual/en/phar.fileformat.phar.php
+     */
+    public static function fromContent(string $content): self
+    {
+        $target = new static();
+        $target->manifestLength = Reader::resolveFourByteLittleEndian($content, 0);
+        $target->amountOfFiles = Reader::resolveFourByteLittleEndian($content, 4);
+        $target->flags = Reader::resolveFourByteLittleEndian($content, 10);
+        $target->aliasLength = Reader::resolveFourByteLittleEndian($content, 14);
+        $target->alias = substr($content, 18, $target->aliasLength);
+        $target->metaDataLength = Reader::resolveFourByteLittleEndian($content, 18 + $target->aliasLength);
+        $target->metaData = substr($content, 22 + $target->aliasLength, $target->metaDataLength);
+
+        $apiVersionNibbles = Reader::resolveTwoByteBigEndian($content, 8);
+        $target->apiVersion = implode('.', [
+            ($apiVersionNibbles & 0xf000) >> 12,
+            ($apiVersionNibbles & 0x0f00) >> 8,
+            ($apiVersionNibbles & 0x00f0) >> 4,
+        ]);
+
+        return $target;
+    }
+
+    /**
+     * @var int
+     */
+    private $manifestLength;
+
+    /**
+     * @var int
+     */
+    private $amountOfFiles;
+
+    /**
+     * @var string
+     */
+    private $apiVersion;
+
+    /**
+     * @var int
+     */
+    private $flags;
+
+    /**
+     * @var int
+     */
+    private $aliasLength;
+
+    /**
+     * @var string
+     */
+    private $alias;
+
+    /**
+     * @var int
+     */
+    private $metaDataLength;
+
+    /**
+     * @var string
+     */
+    private $metaData;
+
+    /**
+     * Avoid direct instantiation.
+     */
+    private function __construct()
+    {
+    }
+
+    /**
+     * @return int
+     */
+    public function getManifestLength(): int
+    {
+        return $this->manifestLength;
+    }
+
+    /**
+     * @return int
+     */
+    public function getAmountOfFiles(): int
+    {
+        return $this->amountOfFiles;
+    }
+
+    /**
+     * @return string
+     */
+    public function getApiVersion(): string
+    {
+        return $this->apiVersion;
+    }
+
+    /**
+     * @return int
+     */
+    public function getFlags(): int
+    {
+        return $this->flags;
+    }
+
+    /**
+     * @return int
+     */
+    public function getAliasLength(): int
+    {
+        return $this->aliasLength;
+    }
+
+    /**
+     * @return string
+     */
+    public function getAlias(): string
+    {
+        return $this->alias;
+    }
+
+    /**
+     * @return int
+     */
+    public function getMetaDataLength(): int
+    {
+        return $this->metaDataLength;
+    }
+
+    /**
+     * @return string
+     */
+    public function getMetaData(): string
+    {
+        return $this->metaData;
+    }
+
+    /**
+     * @return mixed|null
+     */
+    public function deserializeMetaData()
+    {
+        if (empty($this->metaData)) {
+            return null;
+        }
+
+        $result = unserialize($this->metaData, ['allowed_classes' => false]);
+
+        $serialized = json_encode($result);
+        if (strpos($serialized, '__PHP_Incomplete_Class_Name') !== false) {
+            throw new DeserializationException(
+                'Meta-data contains serialized object',
+                1539623382
+            );
+        }
+
+        return $result;
+    }
+}
diff --git a/civicrm/vendor/typo3/phar-stream-wrapper/src/Phar/Reader.php b/civicrm/vendor/typo3/phar-stream-wrapper/src/Phar/Reader.php
new file mode 100644
index 0000000000000000000000000000000000000000..ca3cbbf178ae0f0740ab9578eeaf392333f65b42
--- /dev/null
+++ b/civicrm/vendor/typo3/phar-stream-wrapper/src/Phar/Reader.php
@@ -0,0 +1,255 @@
+<?php
+declare(strict_types=1);
+namespace TYPO3\PharStreamWrapper\Phar;
+
+/*
+ * This file is part of the TYPO3 project.
+ *
+ * It is free software; you can redistribute it and/or modify it under the terms
+ * of the MIT License (MIT). For the full copyright and license information,
+ * please read the LICENSE file that was distributed with this source code.
+ *
+ * The TYPO3 project - inspiring people to share!
+ */
+
+class Reader
+{
+    /**
+     * @var string
+     */
+    private $fileName;
+
+    /**
+     * Mime-type in order to use zlib, bzip2 or no compression.
+     * In case ext-fileinfo is not present only the relevant types
+     * 'application/x-gzip' and 'application/x-bzip2' are assigned
+     * to this class property.
+     *
+     * @var string
+     */
+    private $fileType;
+
+    /**
+     * @param string $fileName
+     */
+    public function __construct(string $fileName)
+    {
+        if (strpos($fileName, '://') !== false) {
+            throw new ReaderException(
+                'File name must not contain stream prefix',
+                1539623708
+            );
+        }
+
+        $this->fileName = $fileName;
+        $this->fileType = $this->determineFileType();
+    }
+
+    /**
+     * @return Container
+     */
+    public function resolveContainer(): Container
+    {
+        $data = $this->extractData($this->resolveStream() . $this->fileName);
+
+        if ($data['stubContent'] === null) {
+            throw new ReaderException(
+                'Cannot resolve stub',
+                1547807881
+            );
+        }
+        if ($data['manifestContent'] === null || $data['manifestLength'] === null) {
+            throw new ReaderException(
+                'Cannot resolve manifest',
+                1547807882
+            );
+        }
+        if (strlen($data['manifestContent']) < $data['manifestLength']) {
+            throw new ReaderException(
+                sprintf(
+                    'Exected manifest length %d, got %d',
+                    strlen($data['manifestContent']),
+                    $data['manifestLength']
+                ),
+                1547807883
+            );
+        }
+
+        return new Container(
+            Stub::fromContent($data['stubContent']),
+            Manifest::fromContent($data['manifestContent'])
+        );
+    }
+
+    /**
+     * @param string $fileName e.g. '/path/file.phar' or 'compress.zlib:///path/file.phar'
+     * @return array
+     */
+    private function extractData(string $fileName): array
+    {
+        $stubContent = null;
+        $manifestContent = null;
+        $manifestLength = null;
+
+        $resource = fopen($fileName, 'r');
+        if (!is_resource($resource)) {
+            throw new ReaderException(
+                sprintf('Resource %s could not be opened', $fileName),
+                1547902055
+            );
+        }
+
+        while (!feof($resource)) {
+            $line = fgets($resource);
+            // stop reading file when manifest can be extracted
+            if ($manifestLength !== null && $manifestContent !== null && strlen($manifestContent) >= $manifestLength) {
+                break;
+            }
+
+            $manifestPosition = strpos($line, '__HALT_COMPILER();');
+
+            // first line contains start of manifest
+            if ($stubContent === null && $manifestContent === null && $manifestPosition !== false) {
+                $stubContent = substr($line, 0, $manifestPosition - 1);
+                $manifestContent = preg_replace('#^.*__HALT_COMPILER\(\);(?>[ \n]\?>(?>\r\n|\n)?)?#', '', $line);
+                $manifestLength = $this->resolveManifestLength($manifestContent);
+            // line contains start of stub
+            } elseif ($stubContent === null) {
+                $stubContent = $line;
+            // line contains start of manifest
+            } elseif ($manifestContent === null && $manifestPosition !== false) {
+                $manifestContent = preg_replace('#^.*__HALT_COMPILER\(\);(?>[ \n]\?>(?>\r\n|\n)?)?#', '', $line);
+                $manifestLength = $this->resolveManifestLength($manifestContent);
+            // manifest has been started (thus is cannot be stub anymore), add content
+            } elseif ($manifestContent !== null) {
+                $manifestContent .= $line;
+                $manifestLength = $this->resolveManifestLength($manifestContent);
+            // stub has been started (thus cannot be manifest here, yet), add content
+            } elseif ($stubContent !== null) {
+                $stubContent .= $line;
+            }
+        }
+        fclose($resource);
+
+        return [
+            'stubContent' => $stubContent,
+            'manifestContent' => $manifestContent,
+            'manifestLength' => $manifestLength,
+        ];
+    }
+
+    /**
+     * Resolves stream in order to handle compressed Phar archives.
+     *
+     * @return string
+     */
+    private function resolveStream(): string
+    {
+        if ($this->fileType === 'application/x-gzip' || $this->fileType === 'application/gzip') {
+            return 'compress.zlib://';
+        } elseif ($this->fileType === 'application/x-bzip2') {
+            return 'compress.bzip2://';
+        }
+        return '';
+    }
+
+    /**
+     * @return string
+     */
+    private function determineFileType()
+    {
+        if (class_exists('\\finfo')) {
+            $fileInfo = new \finfo();
+            return $fileInfo->file($this->fileName, FILEINFO_MIME_TYPE);
+        }
+        return $this->determineFileTypeByHeader();
+    }
+
+    /**
+     * In case ext-fileinfo is not present only the relevant types
+     * 'application/x-gzip' and 'application/x-bzip2' are resolved.
+     *
+     * @return string
+     */
+    private function determineFileTypeByHeader(): string
+    {
+        $resource = fopen($this->fileName, 'r');
+        if (!is_resource($resource)) {
+            throw new ReaderException(
+                sprintf('Resource %s could not be opened', $this->fileName),
+                1557753055
+            );
+        }
+        $header = fgets($resource, 4);
+        fclose($resource);
+        $mimeType = '';
+        if (strpos($header, "\x42\x5a\x68") === 0) {
+            $mimeType = 'application/x-bzip2';
+        } elseif (strpos($header, "\x1f\x8b") === 0) {
+            $mimeType = 'application/x-gzip';
+        }
+        return $mimeType;
+    }
+
+    /**
+     * @param string $content
+     * @return int|null
+     */
+    private function resolveManifestLength(string $content)
+    {
+        if (strlen($content) < 4) {
+            return null;
+        }
+        return static::resolveFourByteLittleEndian($content, 0);
+    }
+
+    /**
+     * @param string $content
+     * @param int $start
+     * @return int
+     */
+    public static function resolveFourByteLittleEndian(string $content, int $start): int
+    {
+        $payload = substr($content, $start, 4);
+        if (!is_string($payload)) {
+            throw new ReaderException(
+                sprintf('Cannot resolve value at offset %d', $start),
+                1539614260
+            );
+        }
+
+        $value = unpack('V', $payload);
+        if (!isset($value[1])) {
+            throw new ReaderException(
+                sprintf('Cannot resolve value at offset %d', $start),
+                1539614261
+            );
+        }
+        return $value[1];
+    }
+
+    /**
+     * @param string $content
+     * @param int $start
+     * @return int
+     */
+    public static function resolveTwoByteBigEndian(string $content, int $start): int
+    {
+        $payload = substr($content, $start, 2);
+        if (!is_string($payload)) {
+            throw new ReaderException(
+                sprintf('Cannot resolve value at offset %d', $start),
+                1539614263
+            );
+        }
+
+        $value = unpack('n', $payload);
+        if (!isset($value[1])) {
+            throw new ReaderException(
+                sprintf('Cannot resolve value at offset %d', $start),
+                1539614264
+            );
+        }
+        return $value[1];
+    }
+}
diff --git a/civicrm/vendor/typo3/phar-stream-wrapper/src/Phar/ReaderException.php b/civicrm/vendor/typo3/phar-stream-wrapper/src/Phar/ReaderException.php
new file mode 100644
index 0000000000000000000000000000000000000000..3eeeb78e555a04485e0ae42b4020593d1e9e10e8
--- /dev/null
+++ b/civicrm/vendor/typo3/phar-stream-wrapper/src/Phar/ReaderException.php
@@ -0,0 +1,19 @@
+<?php
+declare(strict_types=1);
+namespace TYPO3\PharStreamWrapper\Phar;
+
+/*
+ * This file is part of the TYPO3 project.
+ *
+ * It is free software; you can redistribute it and/or modify it under the terms
+ * of the MIT License (MIT). For the full copyright and license information,
+ * please read the LICENSE file that was distributed with this source code.
+ *
+ * The TYPO3 project - inspiring people to share!
+ */
+
+use TYPO3\PharStreamWrapper\Exception;
+
+class ReaderException extends Exception
+{
+}
diff --git a/civicrm/vendor/typo3/phar-stream-wrapper/src/Phar/Stub.php b/civicrm/vendor/typo3/phar-stream-wrapper/src/Phar/Stub.php
new file mode 100644
index 0000000000000000000000000000000000000000..764d286c54d919d9efa68d0784866664e6bc8a0c
--- /dev/null
+++ b/civicrm/vendor/typo3/phar-stream-wrapper/src/Phar/Stub.php
@@ -0,0 +1,66 @@
+<?php
+declare(strict_types=1);
+namespace TYPO3\PharStreamWrapper\Phar;
+
+/*
+ * This file is part of the TYPO3 project.
+ *
+ * It is free software; you can redistribute it and/or modify it under the terms
+ * of the MIT License (MIT). For the full copyright and license information,
+ * please read the LICENSE file that was distributed with this source code.
+ *
+ * The TYPO3 project - inspiring people to share!
+ */
+
+/**
+ * @internal Experimental implementation of Phar archive internals
+ */
+class Stub
+{
+    /**
+     * @param string $content
+     * @return self
+     */
+    public static function fromContent(string $content): self
+    {
+        $target = new static();
+        $target->content = $content;
+
+        if (
+            stripos($content, 'Phar::mapPhar(') !== false
+            && preg_match('#Phar\:\:mapPhar\(([^)]+)\)#', $content, $matches)
+        ) {
+            // remove spaces, single & double quotes
+            // @todo `'my' . 'alias' . '.phar'` is not evaluated here
+            $target->mappedAlias = trim($matches[1], ' \'"');
+        }
+
+        return $target;
+    }
+
+    /**
+     * @var string
+     */
+    private $content;
+
+    /**
+     * @var string
+     */
+    private $mappedAlias = '';
+
+    /**
+     * @return string
+     */
+    public function getContent()
+    {
+        return $this->content;
+    }
+
+    /**
+     * @return string
+     */
+    public function getMappedAlias(): string
+    {
+        return $this->mappedAlias;
+    }
+}
diff --git a/civicrm/vendor/typo3/phar-stream-wrapper/src/PharStreamWrapper.php b/civicrm/vendor/typo3/phar-stream-wrapper/src/PharStreamWrapper.php
new file mode 100644
index 0000000000000000000000000000000000000000..0b3fca4ac14a18daf1e9a92f8b4ad354ab246f41
--- /dev/null
+++ b/civicrm/vendor/typo3/phar-stream-wrapper/src/PharStreamWrapper.php
@@ -0,0 +1,506 @@
+<?php
+declare(strict_types=1);
+namespace TYPO3\PharStreamWrapper;
+
+/*
+ * This file is part of the TYPO3 project.
+ *
+ * It is free software; you can redistribute it and/or modify it under the terms
+ * of the MIT License (MIT). For the full copyright and license information,
+ * please read the LICENSE file that was distributed with this source code.
+ *
+ * The TYPO3 project - inspiring people to share!
+ */
+
+use TYPO3\PharStreamWrapper\Resolver\PharInvocation;
+
+class PharStreamWrapper
+{
+    /**
+     * Internal stream constants that are not exposed to PHP, but used...
+     * @see https://github.com/php/php-src/blob/e17fc0d73c611ad0207cac8a4a01ded38251a7dc/main/php_streams.h
+     */
+    const STREAM_OPEN_FOR_INCLUDE = 128;
+
+    /**
+     * @var resource
+     */
+    public $context;
+
+    /**
+     * @var resource
+     */
+    protected $internalResource;
+
+    /**
+     * @var PharInvocation
+     */
+    protected $invocation;
+
+    /**
+     * @return bool
+     */
+    public function dir_closedir(): bool
+    {
+        if (!is_resource($this->internalResource)) {
+            return false;
+        }
+
+        $this->invokeInternalStreamWrapper(
+            'closedir',
+            $this->internalResource
+        );
+        return !is_resource($this->internalResource);
+    }
+
+    /**
+     * @param string $path
+     * @param int $options
+     * @return bool
+     */
+    public function dir_opendir(string $path, int $options): bool
+    {
+        $this->assert($path, Behavior::COMMAND_DIR_OPENDIR);
+        $this->internalResource = $this->invokeInternalStreamWrapper(
+            'opendir',
+            $path,
+            $this->context
+        );
+        return is_resource($this->internalResource);
+    }
+
+    /**
+     * @return string|false
+     */
+    public function dir_readdir()
+    {
+        return $this->invokeInternalStreamWrapper(
+            'readdir',
+            $this->internalResource
+        );
+    }
+
+    /**
+     * @return bool
+     */
+    public function dir_rewinddir(): bool
+    {
+        if (!is_resource($this->internalResource)) {
+            return false;
+        }
+
+        $this->invokeInternalStreamWrapper(
+            'rewinddir',
+            $this->internalResource
+        );
+        return is_resource($this->internalResource);
+    }
+
+    /**
+     * @param string $path
+     * @param int $mode
+     * @param int $options
+     * @return bool
+     */
+    public function mkdir(string $path, int $mode, int $options): bool
+    {
+        $this->assert($path, Behavior::COMMAND_MKDIR);
+        return $this->invokeInternalStreamWrapper(
+            'mkdir',
+            $path,
+            $mode,
+            (bool) ($options & STREAM_MKDIR_RECURSIVE),
+            $this->context
+        );
+    }
+
+    /**
+     * @param string $path_from
+     * @param string $path_to
+     * @return bool
+     */
+    public function rename(string $path_from, string $path_to): bool
+    {
+        $this->assert($path_from, Behavior::COMMAND_RENAME);
+        $this->assert($path_to, Behavior::COMMAND_RENAME);
+        return $this->invokeInternalStreamWrapper(
+            'rename',
+            $path_from,
+            $path_to,
+            $this->context
+        );
+    }
+
+    /**
+     * @param string $path
+     * @param int $options
+     * @return bool
+     */
+    public function rmdir(string $path, int $options): bool
+    {
+        $this->assert($path, Behavior::COMMAND_RMDIR);
+        return $this->invokeInternalStreamWrapper(
+            'rmdir',
+            $path,
+            $this->context
+        );
+    }
+
+    /**
+     * @param int $cast_as
+     */
+    public function stream_cast(int $cast_as)
+    {
+        throw new Exception(
+            'Method stream_select() cannot be used',
+            1530103999
+        );
+    }
+
+    public function stream_close()
+    {
+        $this->invokeInternalStreamWrapper(
+            'fclose',
+            $this->internalResource
+        );
+    }
+
+    /**
+     * @return bool
+     */
+    public function stream_eof(): bool
+    {
+        return $this->invokeInternalStreamWrapper(
+            'feof',
+            $this->internalResource
+        );
+    }
+
+    /**
+     * @return bool
+     */
+    public function stream_flush(): bool
+    {
+        return $this->invokeInternalStreamWrapper(
+            'fflush',
+            $this->internalResource
+        );
+    }
+
+    /**
+     * @param int $operation
+     * @return bool
+     */
+    public function stream_lock(int $operation): bool
+    {
+        return $this->invokeInternalStreamWrapper(
+            'flock',
+            $this->internalResource,
+            $operation
+        );
+    }
+
+    /**
+     * @param string $path
+     * @param int $option
+     * @param string|int $value
+     * @return bool
+     */
+    public function stream_metadata(string $path, int $option, $value): bool
+    {
+        $this->assert($path, Behavior::COMMAND_STEAM_METADATA);
+        if ($option === STREAM_META_TOUCH) {
+            return $this->invokeInternalStreamWrapper(
+                'touch',
+                $path,
+                ...$value
+            );
+        }
+        if ($option === STREAM_META_OWNER_NAME || $option === STREAM_META_OWNER) {
+            return $this->invokeInternalStreamWrapper(
+                'chown',
+                $path,
+                $value
+            );
+        }
+        if ($option === STREAM_META_GROUP_NAME || $option === STREAM_META_GROUP) {
+            return $this->invokeInternalStreamWrapper(
+                'chgrp',
+                $path,
+                $value
+            );
+        }
+        if ($option === STREAM_META_ACCESS) {
+            return $this->invokeInternalStreamWrapper(
+                'chmod',
+                $path,
+                $value
+            );
+        }
+        return false;
+    }
+
+    /**
+     * @param string $path
+     * @param string $mode
+     * @param int $options
+     * @param string|null $opened_path
+     * @return bool
+     */
+    public function stream_open(
+        string $path,
+        string $mode,
+        int $options,
+        string &$opened_path = null
+    ): bool {
+        $this->assert($path, Behavior::COMMAND_STREAM_OPEN);
+        $arguments = [$path, $mode, (bool) ($options & STREAM_USE_PATH)];
+        // only add stream context for non include/require calls
+        if (!($options & static::STREAM_OPEN_FOR_INCLUDE)) {
+            $arguments[] = $this->context;
+        // work around https://bugs.php.net/bug.php?id=66569
+        // for including files from Phar stream with OPcache enabled
+        } else {
+            Helper::resetOpCache();
+        }
+        $this->internalResource = $this->invokeInternalStreamWrapper(
+            'fopen',
+            ...$arguments
+        );
+        if (!is_resource($this->internalResource)) {
+            return false;
+        }
+        if ($opened_path !== null) {
+            $metaData = stream_get_meta_data($this->internalResource);
+            $opened_path = $metaData['uri'];
+        }
+        return true;
+    }
+
+    /**
+     * @param int $count
+     * @return string
+     */
+    public function stream_read(int $count): string
+    {
+        return $this->invokeInternalStreamWrapper(
+            'fread',
+            $this->internalResource,
+            $count
+        );
+    }
+
+    /**
+     * @param int $offset
+     * @param int $whence
+     * @return bool
+     */
+    public function stream_seek(int $offset, int $whence = SEEK_SET): bool
+    {
+        return $this->invokeInternalStreamWrapper(
+            'fseek',
+            $this->internalResource,
+            $offset,
+            $whence
+        ) !== -1;
+    }
+
+    /**
+     * @param int $option
+     * @param int $arg1
+     * @param int $arg2
+     * @return bool
+     */
+    public function stream_set_option(int $option, int $arg1, int $arg2): bool
+    {
+        if ($option === STREAM_OPTION_BLOCKING) {
+            return $this->invokeInternalStreamWrapper(
+                'stream_set_blocking',
+                $this->internalResource,
+                $arg1
+            );
+        }
+        if ($option === STREAM_OPTION_READ_TIMEOUT) {
+            return $this->invokeInternalStreamWrapper(
+                'stream_set_timeout',
+                $this->internalResource,
+                $arg1,
+                $arg2
+            );
+        }
+        if ($option === STREAM_OPTION_WRITE_BUFFER) {
+            return $this->invokeInternalStreamWrapper(
+                'stream_set_write_buffer',
+                $this->internalResource,
+                $arg2
+            ) === 0;
+        }
+        return false;
+    }
+
+    /**
+     * @return array
+     */
+    public function stream_stat(): array
+    {
+        return $this->invokeInternalStreamWrapper(
+            'fstat',
+            $this->internalResource
+        );
+    }
+
+    /**
+     * @return int
+     */
+    public function stream_tell(): int
+    {
+        return $this->invokeInternalStreamWrapper(
+            'ftell',
+            $this->internalResource
+        );
+    }
+
+    /**
+     * @param int $new_size
+     * @return bool
+     */
+    public function stream_truncate(int $new_size): bool
+    {
+        return $this->invokeInternalStreamWrapper(
+            'ftruncate',
+            $this->internalResource,
+            $new_size
+        );
+    }
+
+    /**
+     * @param string $data
+     * @return int
+     */
+    public function stream_write(string $data): int
+    {
+        return $this->invokeInternalStreamWrapper(
+            'fwrite',
+            $this->internalResource,
+            $data
+        );
+    }
+
+    /**
+     * @param string $path
+     * @return bool
+     */
+    public function unlink(string $path): bool
+    {
+        $this->assert($path, Behavior::COMMAND_UNLINK);
+        return $this->invokeInternalStreamWrapper(
+            'unlink',
+            $path,
+            $this->context
+        );
+    }
+
+    /**
+     * @param string $path
+     * @param int $flags
+     * @return array|false
+     */
+    public function url_stat(string $path, int $flags)
+    {
+        $this->assert($path, Behavior::COMMAND_URL_STAT);
+        $functionName = $flags & STREAM_URL_STAT_QUIET ? '@stat' : 'stat';
+        return $this->invokeInternalStreamWrapper($functionName, $path);
+    }
+
+    /**
+     * @param string $path
+     * @param string $command
+     */
+    protected function assert(string $path, string $command)
+    {
+        if (Manager::instance()->assert($path, $command) === true) {
+            $this->collectInvocation($path);
+            return;
+        }
+
+        throw new Exception(
+            sprintf(
+                'Denied invocation of "%s" for command "%s"',
+                $path,
+                $command
+            ),
+            1535189880
+        );
+    }
+
+    /**
+     * @param string $path
+     */
+    protected function collectInvocation(string $path)
+    {
+        if (isset($this->invocation)) {
+            return;
+        }
+
+        $manager = Manager::instance();
+        $this->invocation = $manager->resolve($path);
+        if ($this->invocation === null) {
+            throw new Exception(
+                'Expected invocation could not be resolved',
+                1556389591
+            );
+        }
+        // confirm, previous interceptor(s) validated invocation
+        $this->invocation->confirm();
+        $collection = $manager->getCollection();
+        if (!$collection->has($this->invocation)) {
+            $collection->collect($this->invocation);
+        }
+    }
+
+    /**
+     * @return Manager|Assertable
+     * @deprecated Use Manager::instance() directly
+     */
+    protected function resolveAssertable(): Assertable
+    {
+        return Manager::instance();
+    }
+
+    /**
+     * Invokes commands on the native PHP Phar stream wrapper.
+     *
+     * @param string $functionName
+     * @param mixed ...$arguments
+     * @return mixed
+     */
+    private function invokeInternalStreamWrapper(string $functionName, ...$arguments)
+    {
+        $silentExecution = $functionName[0] === '@';
+        $functionName = ltrim($functionName, '@');
+        $this->restoreInternalSteamWrapper();
+
+        try {
+            if ($silentExecution) {
+                $result = @call_user_func_array($functionName, $arguments);
+            } else {
+                $result = call_user_func_array($functionName, $arguments);
+            }
+        } finally {
+            $this->registerStreamWrapper();
+        }
+
+        return $result;
+    }
+
+    private function restoreInternalSteamWrapper()
+    {
+        stream_wrapper_restore('phar');
+    }
+
+    private function registerStreamWrapper()
+    {
+        stream_wrapper_unregister('phar');
+        stream_wrapper_register('phar', static::class);
+    }
+}
diff --git a/civicrm/vendor/typo3/phar-stream-wrapper/src/Resolvable.php b/civicrm/vendor/typo3/phar-stream-wrapper/src/Resolvable.php
new file mode 100644
index 0000000000000000000000000000000000000000..6247fe9bda298cf345af229b615bf96b4b53636d
--- /dev/null
+++ b/civicrm/vendor/typo3/phar-stream-wrapper/src/Resolvable.php
@@ -0,0 +1,25 @@
+<?php
+declare(strict_types=1);
+namespace TYPO3\PharStreamWrapper;
+
+/*
+ * This file is part of the TYPO3 project.
+ *
+ * It is free software; you can redistribute it and/or modify it under the terms
+ * of the MIT License (MIT). For the full copyright and license information,
+ * please read the LICENSE file that was distributed with this source code.
+ *
+ * The TYPO3 project - inspiring people to share!
+ */
+
+use TYPO3\PharStreamWrapper\Resolver\PharInvocation;
+
+interface Resolvable
+{
+    /**
+     * @param string $path
+     * @param null|int $flags
+     * @return null|PharInvocation
+     */
+    public function resolve(string $path, int $flags = null);
+}
diff --git a/civicrm/vendor/typo3/phar-stream-wrapper/src/Resolver/PharInvocation.php b/civicrm/vendor/typo3/phar-stream-wrapper/src/Resolver/PharInvocation.php
new file mode 100644
index 0000000000000000000000000000000000000000..00b6a83ec26ae7d201f125fd375c990c057aa134
--- /dev/null
+++ b/civicrm/vendor/typo3/phar-stream-wrapper/src/Resolver/PharInvocation.php
@@ -0,0 +1,123 @@
+<?php
+declare(strict_types=1);
+namespace TYPO3\PharStreamWrapper\Resolver;
+
+/*
+ * This file is part of the TYPO3 project.
+ *
+ * It is free software; you can redistribute it and/or modify it under the terms
+ * of the MIT License (MIT). For the full copyright and license information,
+ * please read the LICENSE file that was distributed with this source code.
+ *
+ * The TYPO3 project - inspiring people to share!
+ */
+
+use TYPO3\PharStreamWrapper\Exception;
+
+class PharInvocation
+{
+    /**
+     * @var string
+     */
+    private $baseName;
+
+    /**
+     * @var string
+     */
+    private $alias;
+
+    /**
+     * @var bool
+     * @see \TYPO3\PharStreamWrapper\PharStreamWrapper::collectInvocation()
+     */
+    private $confirmed = false;
+
+    /**
+     * Arbitrary variables to be used by interceptors as registry
+     * (e.g. in order to avoid duplicate processing and assertions)
+     *
+     * @var array
+     */
+    private $variables;
+
+    /**
+     * @param string $baseName
+     * @param string $alias
+     */
+    public function __construct(string $baseName, string $alias = '')
+    {
+        if ($baseName === '') {
+            throw new Exception(
+                'Base-name cannot be empty',
+                1551283689
+            );
+        }
+        $this->baseName = $baseName;
+        $this->alias = $alias;
+    }
+
+    /**
+     * @return string
+     */
+    public function __toString(): string
+    {
+        return $this->baseName;
+    }
+
+    /**
+     * @return string
+     */
+    public function getBaseName(): string
+    {
+        return $this->baseName;
+    }
+
+    /**
+     * @return null|string
+     */
+    public function getAlias(): string
+    {
+        return $this->alias;
+    }
+
+    /**
+     * @return bool
+     */
+    public function isConfirmed(): bool
+    {
+        return $this->confirmed;
+    }
+
+    public function confirm()
+    {
+        $this->confirmed = true;
+    }
+
+    /**
+     * @param string $name
+     * @return mixed|null
+     */
+    public function getVariable(string $name)
+    {
+        return $this->variables[$name] ?? null;
+    }
+
+    /**
+     * @param string $name
+     * @param mixed $value
+     */
+    public function setVariable(string $name, $value)
+    {
+        $this->variables[$name] = $value;
+    }
+
+    /**
+     * @param PharInvocation $other
+     * @return bool
+     */
+    public function equals(PharInvocation $other): bool
+    {
+        return $other->baseName === $this->baseName
+            && $other->alias === $this->alias;
+    }
+}
diff --git a/civicrm/vendor/typo3/phar-stream-wrapper/src/Resolver/PharInvocationCollection.php b/civicrm/vendor/typo3/phar-stream-wrapper/src/Resolver/PharInvocationCollection.php
new file mode 100644
index 0000000000000000000000000000000000000000..d7d2b273460a18843ee20b77a545091ef213bd18
--- /dev/null
+++ b/civicrm/vendor/typo3/phar-stream-wrapper/src/Resolver/PharInvocationCollection.php
@@ -0,0 +1,157 @@
+<?php
+declare(strict_types=1);
+namespace TYPO3\PharStreamWrapper\Resolver;
+
+/*
+ * This file is part of the TYPO3 project.
+ *
+ * It is free software; you can redistribute it and/or modify it under the terms
+ * of the MIT License (MIT). For the full copyright and license information,
+ * please read the LICENSE file that was distributed with this source code.
+ *
+ * The TYPO3 project - inspiring people to share!
+ */
+
+use TYPO3\PharStreamWrapper\Collectable;
+
+class PharInvocationCollection implements Collectable
+{
+    const UNIQUE_INVOCATION = 1;
+    const UNIQUE_BASE_NAME = 2;
+    const DUPLICATE_ALIAS_WARNING = 32;
+
+    /**
+     * @var PharInvocation[]
+     */
+    private $invocations = [];
+
+    /**
+     * @param PharInvocation $invocation
+     * @return bool
+     */
+    public function has(PharInvocation $invocation): bool
+    {
+        return in_array($invocation, $this->invocations, true);
+    }
+
+    /**
+     * @param PharInvocation $invocation
+     * @param null|int $flags
+     * @return bool
+     */
+    public function collect(PharInvocation $invocation, int $flags = null): bool
+    {
+        if ($flags === null) {
+            $flags = static::UNIQUE_INVOCATION | static::DUPLICATE_ALIAS_WARNING;
+        }
+        if ($invocation->getBaseName() === ''
+            || $invocation->getAlias() === ''
+            || !$this->assertUniqueBaseName($invocation, $flags)
+            || !$this->assertUniqueInvocation($invocation, $flags)
+        ) {
+            return false;
+        }
+        if ($flags & static::DUPLICATE_ALIAS_WARNING) {
+            $this->triggerDuplicateAliasWarning($invocation);
+        }
+
+        $this->invocations[] = $invocation;
+        return true;
+    }
+
+    /**
+     * @param callable $callback
+     * @param bool $reverse
+     * @return null|PharInvocation
+     */
+    public function findByCallback(callable $callback, $reverse = false)
+    {
+        foreach ($this->getInvocations($reverse) as $invocation) {
+            if (call_user_func($callback, $invocation) === true) {
+                return $invocation;
+            }
+        }
+        return null;
+    }
+
+    /**
+     * Asserts that base-name is unique. This disallows having multiple invocations for
+     * same base-name but having different alias names.
+     *
+     * @param PharInvocation $invocation
+     * @param int $flags
+     * @return bool
+     */
+    private function assertUniqueBaseName(PharInvocation $invocation, int $flags): bool
+    {
+        if (!($flags & static::UNIQUE_BASE_NAME)) {
+            return true;
+        }
+        return $this->findByCallback(
+            function (PharInvocation $candidate) use ($invocation) {
+                return $candidate->getBaseName() === $invocation->getBaseName();
+            }
+        ) === null;
+    }
+
+    /**
+     * Asserts that combination of base-name and alias is unique. This allows having multiple
+     * invocations for same base-name but having different alias names (for whatever reason).
+     *
+     * @param PharInvocation $invocation
+     * @param int $flags
+     * @return bool
+     */
+    private function assertUniqueInvocation(PharInvocation $invocation, int $flags): bool
+    {
+        if (!($flags & static::UNIQUE_INVOCATION)) {
+            return true;
+        }
+        return $this->findByCallback(
+            function (PharInvocation $candidate) use ($invocation) {
+                return $candidate->equals($invocation);
+            }
+        ) === null;
+    }
+
+    /**
+     * Triggers warning for invocations with same alias and same confirmation state.
+     *
+     * @param PharInvocation $invocation
+     * @see \TYPO3\PharStreamWrapper\PharStreamWrapper::collectInvocation()
+     */
+    private function triggerDuplicateAliasWarning(PharInvocation $invocation)
+    {
+        $sameAliasInvocation = $this->findByCallback(
+            function (PharInvocation $candidate) use ($invocation) {
+                return $candidate->isConfirmed() === $invocation->isConfirmed()
+                    && $candidate->getAlias() === $invocation->getAlias();
+            },
+            true
+        );
+        if ($sameAliasInvocation === null) {
+            return;
+        }
+        trigger_error(
+            sprintf(
+                'Alias %s cannot be used by %s, already used by %s',
+                $invocation->getAlias(),
+                $invocation->getBaseName(),
+                $sameAliasInvocation->getBaseName()
+            ),
+            E_USER_WARNING
+        );
+    }
+
+    /**
+     * @param bool $reverse
+     * @return PharInvocation[]
+     */
+    private function getInvocations(bool $reverse = false): array
+    {
+        if ($reverse) {
+            return array_reverse($this->invocations);
+        }
+        return $this->invocations;
+    }
+}
diff --git a/civicrm/vendor/typo3/phar-stream-wrapper/src/Resolver/PharInvocationResolver.php b/civicrm/vendor/typo3/phar-stream-wrapper/src/Resolver/PharInvocationResolver.php
new file mode 100644
index 0000000000000000000000000000000000000000..1f6de876c6b8bba267cde1282c042102d41ea6c9
--- /dev/null
+++ b/civicrm/vendor/typo3/phar-stream-wrapper/src/Resolver/PharInvocationResolver.php
@@ -0,0 +1,246 @@
+<?php
+declare(strict_types=1);
+namespace TYPO3\PharStreamWrapper\Resolver;
+
+/*
+ * This file is part of the TYPO3 project.
+ *
+ * It is free software; you can redistribute it and/or modify it under the terms
+ * of the MIT License (MIT). For the full copyright and license information,
+ * please read the LICENSE file that was distributed with this source code.
+ *
+ * The TYPO3 project - inspiring people to share!
+ */
+
+use TYPO3\PharStreamWrapper\Helper;
+use TYPO3\PharStreamWrapper\Manager;
+use TYPO3\PharStreamWrapper\Phar\Reader;
+use TYPO3\PharStreamWrapper\Phar\ReaderException;
+use TYPO3\PharStreamWrapper\Resolvable;
+
+class PharInvocationResolver implements Resolvable
+{
+    const RESOLVE_REALPATH = 1;
+    const RESOLVE_ALIAS = 2;
+    const ASSERT_INTERNAL_INVOCATION = 32;
+
+    /**
+     * @var string[]
+     */
+    private $invocationFunctionNames = [
+        'include',
+        'include_once',
+        'require',
+        'require_once'
+    ];
+
+    /**
+     * Contains resolved base names in order to reduce file IO.
+     *
+     * @var string[]
+     */
+    private $baseNames = [];
+
+    /**
+     * Resolves PharInvocation value object (baseName and optional alias).
+     *
+     * Phar aliases are intended to be used only inside Phar archives, however
+     * PharStreamWrapper needs this information exposed outside of Phar as well
+     * It is possible that same alias is used for different $baseName values.
+     * That's why PharInvocationCollection behaves like a stack when resolving
+     * base-name for a given alias. On the other hand it is not possible that
+     * one $baseName is referring to multiple aliases.
+     * @see https://secure.php.net/manual/en/phar.setalias.php
+     * @see https://secure.php.net/manual/en/phar.mapphar.php
+     *
+     * @param string $path
+     * @param int|null $flags
+     * @return null|PharInvocation
+     */
+    public function resolve(string $path, int $flags = null)
+    {
+        $hasPharPrefix = Helper::hasPharPrefix($path);
+        $flags = $flags ?? static::RESOLVE_REALPATH | static::RESOLVE_ALIAS;
+
+        if ($hasPharPrefix && $flags & static::RESOLVE_ALIAS) {
+            $invocation = $this->findByAlias($path);
+            if ($invocation !== null) {
+                return $invocation;
+            }
+        }
+
+        $baseName = $this->resolveBaseName($path, $flags);
+        if ($baseName === null) {
+            return null;
+        }
+
+        if ($flags & static::RESOLVE_REALPATH) {
+            $baseName = $this->baseNames[$baseName];
+        }
+
+        return $this->retrieveInvocation($baseName, $flags);
+    }
+
+    /**
+     * Retrieves PharInvocation, either existing in collection or created on demand
+     * with resolving a potential alias name used in the according Phar archive.
+     *
+     * @param string $baseName
+     * @param int $flags
+     * @return PharInvocation
+     */
+    private function retrieveInvocation(string $baseName, int $flags): PharInvocation
+    {
+        $invocation = $this->findByBaseName($baseName);
+        if ($invocation !== null) {
+            return $invocation;
+        }
+
+        if ($flags & static::RESOLVE_ALIAS) {
+            $alias = (new Reader($baseName))->resolveContainer()->getAlias();
+        } else {
+            $alias = '';
+        }
+        // add unconfirmed(!) new invocation to collection
+        $invocation = new PharInvocation($baseName, $alias);
+        Manager::instance()->getCollection()->collect($invocation);
+        return $invocation;
+    }
+
+    /**
+     * @param string $path
+     * @param int $flags
+     * @return null|string
+     */
+    private function resolveBaseName(string $path, int $flags)
+    {
+        $baseName = $this->findInBaseNames($path);
+        if ($baseName !== null) {
+            return $baseName;
+        }
+
+        $baseName = Helper::determineBaseFile($path);
+        if ($baseName !== null) {
+            $this->addBaseName($baseName);
+            return $baseName;
+        }
+
+        $possibleAlias = $this->resolvePossibleAlias($path);
+        if (!($flags & static::RESOLVE_ALIAS) || $possibleAlias === null) {
+            return null;
+        }
+
+        $trace = debug_backtrace();
+        foreach ($trace as $item) {
+            if (!isset($item['function']) || !isset($item['args'][0])
+                || !in_array($item['function'], $this->invocationFunctionNames, true)) {
+                continue;
+            }
+            $currentPath = $item['args'][0];
+            if (Helper::hasPharPrefix($currentPath)) {
+                continue;
+            }
+            $currentBaseName = Helper::determineBaseFile($currentPath);
+            if ($currentBaseName === null) {
+                continue;
+            }
+            // ensure the possible alias name (how we have been called initially) matches
+            // the resolved alias name that was retrieved by the current possible base name
+            try {
+                $currentAlias = (new Reader($currentBaseName))->resolveContainer()->getAlias();
+            } catch (ReaderException $exception) {
+                // most probably that was not a Phar file
+                continue;
+            }
+            if (empty($currentAlias) || $currentAlias !== $possibleAlias) {
+                continue;
+            }
+            $this->addBaseName($currentBaseName);
+            return $currentBaseName;
+        }
+
+        return null;
+    }
+
+    /**
+     * @param string $path
+     * @return null|string
+     */
+    private function resolvePossibleAlias(string $path)
+    {
+        $normalizedPath = Helper::normalizePath($path);
+        return strstr($normalizedPath, '/', true) ?: null;
+    }
+
+    /**
+     * @param string $baseName
+     * @return null|PharInvocation
+     */
+    private function findByBaseName(string $baseName)
+    {
+        return Manager::instance()->getCollection()->findByCallback(
+            function (PharInvocation $candidate) use ($baseName) {
+                return $candidate->getBaseName() === $baseName;
+            },
+            true
+        );
+    }
+
+    /**
+     * @param string $path
+     * @return null|string
+     */
+    private function findInBaseNames(string $path)
+    {
+        // return directly if the resolved base name was submitted
+        if (in_array($path, $this->baseNames, true)) {
+            return $path;
+        }
+
+        $parts = explode('/', Helper::normalizePath($path));
+
+        while (count($parts)) {
+            $currentPath = implode('/', $parts);
+            if (isset($this->baseNames[$currentPath])) {
+                return $currentPath;
+            }
+            array_pop($parts);
+        }
+
+        return null;
+    }
+
+    /**
+     * @param string $baseName
+     */
+    private function addBaseName(string $baseName)
+    {
+        if (isset($this->baseNames[$baseName])) {
+            return;
+        }
+        $this->baseNames[$baseName] = Helper::normalizeWindowsPath(
+            realpath($baseName)
+        );
+    }
+
+    /**
+     * Finds confirmed(!) invocations by alias.
+     *
+     * @param string $path
+     * @return null|PharInvocation
+     * @see \TYPO3\PharStreamWrapper\PharStreamWrapper::collectInvocation()
+     */
+    private function findByAlias(string $path)
+    {
+        $possibleAlias = $this->resolvePossibleAlias($path);
+        if ($possibleAlias === null) {
+            return null;
+        }
+        return Manager::instance()->getCollection()->findByCallback(
+            function (PharInvocation $candidate) use ($possibleAlias) {
+                return $candidate->isConfirmed() && $candidate->getAlias() === $possibleAlias;
+            },
+            true
+        );
+    }
+}
diff --git a/civicrm/xml/version.xml b/civicrm/xml/version.xml
index cd37d9af198a262eda8cd952862f39999671fae4..d95f8594d936913633765cf2dfb438bc59ece794 100644
--- a/civicrm/xml/version.xml
+++ b/civicrm/xml/version.xml
@@ -1,4 +1,4 @@
 <?xml version="1.0" encoding="iso-8859-1" ?>
 <version>
-  <version_no>5.24.2</version_no>
+  <version_no>5.24.3</version_no>
 </version>
diff --git a/includes/civicrm.compat.php b/includes/civicrm.compat.php
deleted file mode 100644
index 151761de7cf99bfed6fd64765342d41c44e4c8dc..0000000000000000000000000000000000000000
--- a/includes/civicrm.compat.php
+++ /dev/null
@@ -1,154 +0,0 @@
-<?php
-/*
- +--------------------------------------------------------------------+
- | Copyright CiviCRM LLC. All rights reserved.                        |
- |                                                                    |
- | This work is published under the GNU AGPLv3 license with some      |
- | permitted exceptions and without any warranty. For full license    |
- | and copyright information, see https://civicrm.org/licensing       |
- +--------------------------------------------------------------------+
-*/
-
-/**
- *
- * @package CRM
- * @copyright CiviCRM LLC https://civicrm.org/licensing
- *
- */
-
-
-// This file must not accessed directly
-if ( ! defined( 'ABSPATH' ) ) exit;
-
-
-/**
- * Define CiviCRM_For_WordPress_Compat Class.
- *
- * @since 5.24
- */
-class CiviCRM_For_WordPress_Compat {
-
-  /**
-   * Plugin object reference.
-   *
-   * @since 5.24
-   * @access public
-   * @var object $civi The plugin object reference.
-   */
-  public $civi;
-
-
-  /**
-   * Instance constructor.
-   *
-   * @since 5.24
-   */
-  public function __construct() {
-
-    // Store reference to CiviCRM plugin object.
-    $this->civi = civi_wp();
-
-    // Register plugin compatibility hooks.
-    $this->register_hooks();
-
-  }
-
-
-  /**
-   * Register plugin compatibility hooks.
-   *
-   * This is called via the constructor during the "plugins_loaded" action which
-   * is much earlier that CiviCRM's own internal hooks. The reason for this is
-   * that compability may need callbacks for events that fire well before "init"
-   * which is when CiviCRM begins to load.
-   *
-   * @since 5.24
-   */
-  public function register_hooks() {
-
-    // Bail if CiviCRM not installed yet.
-    if ( ! CIVICRM_INSTALLED ) {
-      return;
-    }
-
-    // Support Clean URLs when Polylang is active.
-    add_action( 'civicrm_after_rewrite_rules', array( $this, 'rewrite_rules_polylang' ), 10, 2 );
-
-  }
-
-
-  /**
-   * Support Polylang.
-   *
-   * @since 5.24
-   *
-   * @param bool $flush_rewrite_rules True if rules flushed, false otherwise.
-   * @param WP_Post $basepage The Basepage post object.
-   */
-  public function rewrite_rules_polylang( $flush_rewrite_rules, $basepage ) {
-
-    // Bail if Polylang is not present.
-    if (!function_exists('pll_languages_list')) {
-      return;
-    }
-
-    /*
-     * Collect all rewrite rules into an array.
-     *
-     * Because the array of specific Post IDs is added *after* the array of
-     * paths for the Basepage ID, those specific rewrite rules will "win" over
-     * the more general Basepage rules.
-     */
-    $collected_rewrites = [];
-
-    // Support prefixes for a single Basepage.
-    $basepage_url = get_permalink( $basepage->ID );
-    $basepage_raw_url = PLL()->links_model->remove_language_from_link( $basepage_url );
-    $language_slugs = pll_languages_list();
-    foreach ($language_slugs as $slug) {
-      $language = PLL()->model->get_language( $slug );
-      $language_url = PLL()->links_model->add_language_to_link( $basepage_raw_url, $language );
-      $parsed_url = wp_parse_url( $language_url, PHP_URL_PATH );
-      $regex_path = substr( $parsed_url, 1 );
-      $collected_rewrites[$basepage->ID][] = $regex_path;
-      $post_id = pll_get_post( $basepage->ID, $slug );
-      if (!empty($post_id)) {
-        $collected_rewrites[$post_id][] = $regex_path;
-      }
-    };
-
-    // Support prefixes for Basepages in multiple languages.
-    foreach ($language_slugs as $slug) {
-      $post_id = pll_get_post( $basepage->ID, $slug );
-      if (empty($post_id)) {
-        continue;
-      }
-      $url = get_permalink( $post_id );
-      $parsed_url = wp_parse_url( $url, PHP_URL_PATH );
-      $regex_path = substr( $parsed_url, 1 );
-      $collected_rewrites[$basepage->ID][] = $regex_path;
-      $collected_rewrites[$post_id][] = $regex_path;
-    };
-
-    // Make collection unique and add remaining rewrite rules.
-    $rewrites = array_map('array_unique', $collected_rewrites);
-    if (!empty($rewrites)) {
-      foreach ($rewrites as $post_id => $rewrite) {
-        foreach ($rewrite as $path) {
-          add_rewrite_rule(
-            '^' . $path . '([^?]*)?',
-            'index.php?page_id=' . $post_id . '&page=CiviCRM&q=civicrm%2F$matches[1]',
-            'top'
-          );
-        }
-      }
-    }
-
-    // Maybe force flush
-    if ($flush_rewrite_rules) {
-      flush_rewrite_rules();
-    }
-
-  }
-
-} // Class CiviCRM_For_WordPress_Compat ends
diff --git a/wp-rest/.editorconfig b/wp-rest/.editorconfig
deleted file mode 100644
index 09dc3747d33a42560841336306fc106d96b39a47..0000000000000000000000000000000000000000
--- a/wp-rest/.editorconfig
+++ /dev/null
@@ -1,9 +0,0 @@
-# EditorConfig is awesome: https://editorconfig.org
-
-# Not top-most EditorConfig file
-root = false
-
-# Tab indentation
-[*.php]
-indent_style = tab
-indent_size = 4
diff --git a/wp-rest/Autoloader.php b/wp-rest/Autoloader.php
deleted file mode 100644
index 01118666154c90313681973608f4d3444fd69a6b..0000000000000000000000000000000000000000
--- a/wp-rest/Autoloader.php
+++ /dev/null
@@ -1,115 +0,0 @@
-<?php
-/**
- * Autoloader class.
- *
- * @since 0.1
- */
-
-namespace CiviCRM_WP_REST;
-
-class Autoloader {
-
-	/**
-	 * Instance.
-	 *
-	 * @since 0.1
-	 * @var string
-	 */
-	private static $instance = null;
-
-	/**
-	 * Namespace.
-	 *
-	 * @since 0.1
-	 * @var string
-	 */
-	private $namespace = 'CiviCRM_WP_REST';
-
-	/**
-	 * Autoloader directory sources.
-	 *
-	 * @since 0.1
-	 * @var array
-	 */
-	private static $source_directories = [];
-
-	/**
-	 * Constructor.
-	 *
-	 * @since 0.1
-	 */
-	private function __construct() {
-
-		$this->register_autoloader();
-
-	}
-
-	/**
-	 * Creates an instance of this class.
-	 *
-	 * @since 0.1
-	 */
-	private static function instance() {
-
-		if ( ! self::$instance ) self::$instance = new self;
-
-	}
-
-	/**
-	 * Adds a directory source.
-	 *
-	 * @since 0.1
-	 * @param string $source The source path
-	 */
-	public static function add_source( string $source_path ) {
-
-		// make sure we have an instance
-		self::instance();
-
-		if ( ! is_readable( trailingslashit( $source_path ) ) )
-			return \WP_Error( 'civicrm_wp_rest_error', sprintf( __( 'The source %s is not readable.', 'civicrm' ), $source ) );
-
-		self::$source_directories[] = $source_path;
-
-	}
-
-	/**
-	 * Registers the autoloader.
-	 *
-	 * @since 0.1
-	 * @return bool Wehather the autoloader has been registered or not
-	 */
-	private function register_autoloader() {
-
-		return spl_autoload_register( [ $this, 'autoload' ] );
-
-	}
-
-	/**
-	 * Loads the classes.
-	 *
-	 * @since 0.1
-	 * @param string $class_name The class name to load
-	 */
-	private function autoload( $class_name ) {
-
-		$parts = explode( '\\', $class_name );
-
-		if ( $this->namespace !== $parts[0] ) return;
-
-		// remove namespace and join class path
-		$class_path = str_replace( '_', '-', implode( DIRECTORY_SEPARATOR, array_slice( $parts, 1 ) ) );
-
-		array_map( function( $source_path ) use ( $class_path ) {
-
-			$path = $source_path . $class_path . '.php';
-
-			if ( ! file_exists( $path ) ) return;
-
-			require $path;
-
-		}, static::$source_directories );
-
-	}
-
-}
diff --git a/wp-rest/Civi/Mailing-Hooks.php b/wp-rest/Civi/Mailing-Hooks.php
deleted file mode 100644
index b765e1c91194118a2e265819ddd9bf1099d6a603..0000000000000000000000000000000000000000
--- a/wp-rest/Civi/Mailing-Hooks.php
+++ /dev/null
@@ -1,197 +0,0 @@
-<?php
-/**
- * CiviCRM Mailing_Hooks class.
- *
- * @since 0.1
- */
-
-namespace CiviCRM_WP_REST\Civi;
-
-class Mailing_Hooks {
-
-	/**
-	 * Mailing Url endpoint.
-	 *
-	 * @since 0.1
-	 * @var string
-	 */
-	public $url_endpoint;
-
-	/**
-	 * Mailing Open endpoint.
-	 *
-	 * @since 0.1
-	 * @var string
-	 */
-	public $open_endpoint;
-
-	/**
-	 * The parsed WordPress REST url.
-	 *
-	 * @since 1.0
-	 * @var array
-	 */
-	public $parsed_rest_url;
-
-	/**
-	 * Constructor.
-	 *
-	 * @since 0.1
-	 */
-	public function __construct() {
-
-		$this->url_endpoint = rest_url( 'civicrm/v3/url' );
-
-		$this->open_endpoint = rest_url( 'civicrm/v3/open' );
-
-		$this->parsed_rest_url = parse_url( rest_url() );
-
-	}
-
-	/**
-	 * Register hooks.
-	 *
-	 * @since 0.1
-	 */
-	public function register_hooks() {
-
-		add_filter( 'civicrm_alterMailParams', [ $this, 'do_mailing_urls' ], 10, 2 );
-
-		add_filter( 'civicrm_alterExternUrl', [ $this, 'alter_mailing_extern_urls' ], 10, 6 );
-
-	}
-
-	/**
-	 * Replaces the open, and click
-	 * tracking URLs for a mailing (CiviMail)
-	 * with thier REST counterparts.
-	 *
-	 * @uses 'civicrm_alterExternUrl' filter
-	 *
-	 * @param \GuzzleHttp\Psr7\Uri $url
-	 * @param string|null $path
-	 * @param string|null $query
-	 * @param string|null $fragment
-	 * @param bool|null $absolute
-	 * @param bool|null $isSSL
-	 */
-	public function alter_mailing_extern_urls( &$url, $path, $query, $fragment, $absolute, $isSSL ) {
-
-		if ( $path == 'extern/url' ) {
-			$url = $url
-				->withHost( $this->parsed_rest_url['host'] )
-				->withPath( "{$this->parsed_rest_url['path']}civicrm/v3/url" );
-		}
-
-		if ( $path == 'extern/open' ) {
-			$url = $url
-				->withHost( $this->parsed_rest_url['host'] )
-				->withPath( "{$this->parsed_rest_url['path']}civicrm/v3/open" );
-		}
-
-	}
-
-	/**
-	 * Filters the mailing html and replaces calls to 'extern/url.php' and
-	 * 'extern/open.php' with their REST counterparts 'civicrm/v3/url' and 'civicrm/v3/open'.
-	 *
-	 * @uses 'civicrm_alterMailParams'
-	 *
-	 * @since 0.1
-	 * @param array &$params Mail params
-	 * @param string $context The Context
-	 * @return array $params The filtered Mail params
-	 */
-	public function do_mailing_urls( &$params, $context ) {
-
-		if ( in_array( $context, [ 'civimail', 'flexmailer' ] ) ) {
-
-			$params['html'] = $this->is_mail_tracking_url_alterable( $params['html'] )
-				? $this->replace_html_mailing_tracking_urls( $params['html'] )
-				: $params['html'];
-
-			$params['text'] = $this->is_mail_tracking_url_alterable( $params['text'] )
-				? $this->replace_text_mailing_tracking_urls( $params['text'] )
-				: $params['text'];
-
-		}
-
-		return $params;
-
-	}
-
-	/**
-	 * Replace html mailing tracking urls.
-	 *
-	 * @since 0.1
-	 * @param string $contnet The mailing content
-	 * @return string $content The mailing content
-	 */
-	public function replace_html_mailing_tracking_urls( string $content ) {
-
-		$doc = \phpQuery::newDocument( $content );
-
-		foreach ( $doc[ '[href*="civicrm/extern/url.php"], [src*="civicrm/extern/open.php"]' ] as $element ) {
-
-			$href = pq( $element )->attr( 'href' );
-			$src = pq( $element )->attr( 'src' );
-
-			// replace extern/url
-			if ( strpos( $href, 'civicrm/extern/url.php' ) )	{
-
-				$query_string = strstr( $href, '?' );
-				pq( $element )->attr( 'href', $this->url_endpoint . $query_string );
-
-			}
-
-			// replace extern/open
-			if ( strpos( $src, 'civicrm/extern/open.php' ) ) {
-
-				$query_string = strstr( $src, '?' );
-				pq( $element )->attr( 'src', $this->open_endpoint . $query_string );
-
-			}
-
-			unset( $href, $src, $query_string );
-
-		}
-
-		return $doc->html();
-
-	}
-
-	/**
-	 * Replace text mailing tracking urls.
-	 *
-	 * @since 0.1
-	 * @param string $contnet The mailing content
-	 * @return string $content The mailing content
-	 */
-	public function replace_text_mailing_tracking_urls( string $content ) {
-
-		// replace extern url
-		$content = preg_replace( '/http.*civicrm\/extern\/url\.php/i', $this->url_endpoint, $content );
-
-		// replace open url
-		$content = preg_replace( '/http.*civicrm\/extern\/open\.php/i', $this->open_endpoint, $content );
-
-		return $content;
-
-	}
-
-	/**
-	 * Checks whether for a given mail
-	 * content (text or html) the tracking URLs
-	 * are alterable/need to be altered.
-	 *
-	 * @since 0.1
-	 * @param string $content The mail content (text or  html)
-	 * @return bool $is_alterable
-	 */
-	public function is_mail_tracking_url_alterable( string $content ) {
-
-		return strpos( $content, 'civicrm/extern/url.php' ) || strpos( $content, 'civicrm/extern/open.php' );
-
-	}
-
-}
diff --git a/wp-rest/Controller/AuthorizeIPN.php b/wp-rest/Controller/AuthorizeIPN.php
deleted file mode 100644
index 4cd9da9a97786f3176f55ec59c2528a77b774554..0000000000000000000000000000000000000000
--- a/wp-rest/Controller/AuthorizeIPN.php
+++ /dev/null
@@ -1,123 +0,0 @@
-<?php
-/**
- * AuthorizeIPN controller class.
- *
- * Replacement for CiviCRM's 'extern/authorizeIPN.php'.
- *
- * @see https://docs.civicrm.org/sysadmin/en/latest/setup/payment-processors/authorize-net/#shell-script-testing-method
- *
- * @since 0.1
- */
-
-namespace CiviCRM_WP_REST\Controller;
-
-class AuthorizeIPN extends Base {
-
-	/**
-	 * The base route.
-	 *
-	 * @since 0.1
-	 * @var string
-	 */
-	protected $rest_base = 'authorizeIPN';
-
-	/**
-	 * Registers routes.
-	 *
-	 * @since 0.1
-	 */
-	public function register_routes() {
-
-		register_rest_route( $this->get_namespace(), $this->get_rest_base(), [
-			[
-				'methods' => \WP_REST_Server::ALLMETHODS,
-				'callback' => [ $this, 'get_item' ]
-			]
-		] );
-
-	}
-
-	/**
-	 * Get items.
-	 *
-	 * @since 0.1
-	 * @param WP_REST_Request $request
-	 */
-	public function get_item( $request ) {
-
-		/**
-		 * Filter request params.
-		 *
-		 * @since 0.1
-		 * @param array $params
-		 * @param WP_REST_Request $request
-		 */
-		$params = apply_filters( 'civi_wp_rest/controller/authorizeIPN/params', $request->get_params(), $request );
-
-		$authorize_IPN = new \CRM_Core_Payment_AuthorizeNetIPN( $params );
-
-		// log notification
-		\Civi::log()->alert( 'payment_notification processor_name=AuthNet', $params );
-
-		/**
-		 * Filter AuthorizeIPN object.
-		 *
-		 * @param CRM_Core_Payment_AuthorizeNetIPN $authorize_IPN
-		 * @param array $params
-		 * @param WP_REST_Request $request
-		 */
-		$authorize_IPN = apply_filters( 'civi_wp_rest/controller/authorizeIPN/instance', $authorize_IPN, $params, $request );
-
-		try {
-
-			if ( ! method_exists( $authorize_IPN, 'main' ) || ! $this->instance_of_crm_base_ipn( $authorize_IPN ) )
-				return $this->civi_rest_error( sprintf( __( '%s must implement a "main" method.', 'civicrm' ), get_class( $authorize_IPN ) ) );
-
-			$result = $authorize_IPN->main();
-
-		} catch ( \CRM_Core_Exception $e ) {
-
-			\Civi::log()->error( $e->getMessage() );
-			\Civi::log()->error( 'error data ', [ 'data' => $e->getErrorData() ] );
-			\Civi::log()->error( 'REQUEST ', [ 'params' => $params ] );
-
-			return $this->civi_rest_error( $e->getMessage() );
-
-		}
-
-		return rest_ensure_response( $result );
-
-	}
-
-	/**
-	 * Checks whether object is an instance of CRM_Core_Payment_AuthorizeNetIPN or CRM_Core_Payment_BaseIPN.
-	 *
-	 * Needed because the instance is being filtered through 'civi_wp_rest/controller/authorizeIPN/instance'.
-	 *
-	 * @since 0.1
-	 * @param CRM_Core_Payment_AuthorizeNetIPN|CRM_Core_Payment_BaseIPN $object
-	 * @return bool
-	 */
-	public function instance_of_crm_base_ipn( $object ) {
-
-		return $object instanceof \CRM_Core_Payment_BaseIPN || $object instanceof \CRM_Core_Payment_AuthorizeNetIPN;
-
-	}
-
-	/**
-	 * Item schema.
-	 *
-	 * @since 0.1
-	 * @return array $schema
-	 */
-	public function get_item_schema() {}
-
-	/**
-	 * Item arguments.
-	 *
-	 * @since 0.1
-	 * @return array $arguments
-	 */
-	public function get_item_args() {}
-
-}
diff --git a/wp-rest/Controller/Base.php b/wp-rest/Controller/Base.php
deleted file mode 100644
index 61ab9b3c63d6f239992cb464bdff3e1224b8d50a..0000000000000000000000000000000000000000
--- a/wp-rest/Controller/Base.php
+++ /dev/null
@@ -1,111 +0,0 @@
-<?php
-/**
- * Base controller class.
- *
- * @since 0.1
- */
-
-namespace CiviCRM_WP_REST\Controller;
-
-use CiviCRM_WP_REST\Endpoint\Endpoint_Interface;
-
-abstract class Base extends \WP_REST_Controller implements Endpoint_Interface {
-
-	/**
-	 * Route namespace.
-	 *
-	 * @since 0.1
-	 * @var string
-	 */
-	protected $namespace = 'civicrm/v3';
-
-	/**
-	 * Gets the endpoint namespace.
-	 *
-	 * @since 0.1
-	 * @return string $namespace
-	 */
-	public function get_namespace() {
-
-		return $this->namespace;
-
-	}
-
-	/**
-	 * Gets the rest base route.
-	 *
-	 * @since 0.1
-	 * @return string $rest_base
-	 */
-	public function get_rest_base() {
-
-		return '/' . $this->rest_base;
-
-	}
-
-	/**
-	 * Retrieves the endpoint ie. '/civicrm/v3/rest'.
-	 *
-	 * @since 0.1
-	 * @return string $rest_base
-	 */
-	public function get_endpoint() {
-
-		return '/' . $this->get_namespace() . $this->get_rest_base();
-
-	}
-
-	/**
-	 * Checks whether the requested route is equal to this endpoint.
-	 *
-	 * @since 0.1
-	 * @param WP_REST_Request $request
-	 * @return bool $is_current_endpoint True if it's equal, false otherwise
-	 */
-	public function is_current_endpoint( $request ) {
-
-		return $this->get_endpoint() == $request->get_route();
-
-	}
-
-	/**
-	 * Authorization status code.
-	 *
-	 * @since 0.1
-	 * @return int $status
-	 */
-	protected function authorization_status_code() {
-
-		$status = 401;
-
-		if ( is_user_logged_in() ) $status = 403;
-
-		return $status;
-
-	}
-
-	/**
-	 * Wrapper for WP_Error.
-	 *
-	 * @since 0.1
-	 * @param string|\CiviCRM_API3_Exception|\WP_Error $error
-	 * @param mixed $data Error data
-	 * @return WP_Error $error
-	 */
-	protected function civi_rest_error( $error, $data = [] ) {
-
-		if ( $error instanceof \CiviCRM_API3_Exception ) {
-
-			return $error->getExtraParams();
-
-		} elseif ( $error instanceof \WP_Error ) {
-
-			return $error;
-
-		}
-
-		return new \WP_Error( 'civicrm_rest_api_error', $error, empty( $data ) ? [ 'status' => $this->authorization_status_code() ] : $data );
-
-	}
-
-}
diff --git a/wp-rest/Controller/Cxn.php b/wp-rest/Controller/Cxn.php
deleted file mode 100644
index 7f7cca5c5621c3eb3441ca7060d5e1048eb85ade..0000000000000000000000000000000000000000
--- a/wp-rest/Controller/Cxn.php
+++ /dev/null
@@ -1,125 +0,0 @@
-<?php
-/**
- * Cxn controller class.
- *
- * CiviConnect endpoint, replacement for CiviCRM's 'extern/cxn.php'.
- *
- * @since 0.1
- */
-
-namespace CiviCRM_WP_REST\Controller;
-
-class Cxn extends Base {
-
-	/**
-	 * The base route.
-	 *
-	 * @since 0.1
-	 * @var string
-	 */
-	protected $rest_base = 'cxn';
-
-	/**
-	 * Registers routes.
-	 *
-	 * @since 0.1
-	 */
-	public function register_routes() {
-
-		register_rest_route( $this->get_namespace(), $this->get_rest_base(), [
-			[
-				'methods' => \WP_REST_Server::ALLMETHODS,
-				'callback' => [ $this, 'get_item' ]
-			]
-		] );
-
-	}
-
-	/**
-	 * Get items.
-	 *
-	 * @since 0.1
-	 * @param WP_REST_Request $request
-	 */
-	public function get_item( $request ) {
-
-		/**
-		 * Filter request params.
-		 *
-		 * @since 0.1
-		 * @param array $params
-		 * @param WP_REST_Request $request
-		 */
-		$params = apply_filters( 'civi_wp_rest/controller/cxn/params', $request->get_params(), $request );
-
-		// init connection server
-		$cxn = \CRM_Cxn_BAO_Cxn::createApiServer();
-
-		/**
-		 * Filter connection server object.
-		 *
-		 * @param Civi\Cxn\Rpc\ApiServer $cxn
-		 * @param array $params
-		 * @param WP_REST_Request $request
-		 */
-		$cxn = apply_filters( 'civi_wp_rest/controller/cxn/instance', $cxn, $params, $request );
-
-		try {
-
-			$result = $cxn->handle( $request->get_body() );
-
-		} catch ( Civi\Cxn\Rpc\Exception\CxnException $e ) {
-
-			return $this->civi_rest_error( $e->getMessage() );
-
-		} catch ( Civi\Cxn\Rpc\Exception\ExpiredCertException $e ) {
-
-			return $this->civi_rest_error( $e->getMessage() );
-
-		} catch ( Civi\Cxn\Rpc\Exception\InvalidCertException $e ) {
-
-			return $this->civi_rest_error( $e->getMessage() );
-
-		} catch ( Civi\Cxn\Rpc\Exception\InvalidMessageException $e ) {
-
-			return $this->civi_rest_error( $e->getMessage() );
-
-		} catch ( Civi\Cxn\Rpc\Exception\GarbledMessageException $e ) {
-
-			return $this->civi_rest_error( $e->getMessage() );
-
-		}
-
-		/**
-		 * Bypass WP and send request from Cxn.
-		 */
-		add_filter( 'rest_pre_serve_request', function( $served, $response, $request, $server ) use ( $result ) {
-
-			// Civi\Cxn\Rpc\Message->send()
-			$result->send();
-
-			return true;
-
-		}, 10, 4 );
-
-		return rest_ensure_response( $result );
-
-	}
-
-	/**
-	 * Item schema.
-	 *
-	 * @since 0.1
-	 * @return array $schema
-	 */
-	public function get_item_schema() {}
-
-	/**
-	 * Item arguments.
-	 *
-	 * @since 0.1
-	 * @return array $arguments
-	 */
-	public function get_item_args() {}
-
-}
diff --git a/wp-rest/Controller/Open.php b/wp-rest/Controller/Open.php
deleted file mode 100644
index 450ef991a34897a169761dc9c1fdfcc57b4a0bf5..0000000000000000000000000000000000000000
--- a/wp-rest/Controller/Open.php
+++ /dev/null
@@ -1,129 +0,0 @@
-<?php
-/**
- * Open controller class.
- *
- * @since 0.1
- */
-
-namespace CiviCRM_WP_REST\Controller;
-
-class Open extends Base {
-
-	/**
-	 * The base route.
-	 *
-	 * @since 0.1
-	 * @var string
-	 */
-	protected $rest_base = 'open';
-
-	/**
-	 * Registers routes.
-	 *
-	 * @since 0.1
-	 */
-	public function register_routes() {
-
-		register_rest_route( $this->get_namespace(), $this->get_rest_base(), [
-			[
-				'methods' => \WP_REST_Server::READABLE,
-				'callback' => [ $this, 'get_item' ],
-				'args' => $this->get_item_args()
-			],
-			'schema' => [ $this, 'get_item_schema' ]
-		] );
-
-	}
-
-	/**
-	 * Get item.
-	 *
-	 * @since 0.1
-	 * @param WP_REST_Request $request
-	 */
-	public function get_item( $request ) {
-
-		$queue_id = $request->get_param( 'q' );
-
-		// track open
-		\CRM_Mailing_Event_BAO_Opened::open( $queue_id );
-
-		// serve tracker file
-		add_filter( 'rest_pre_serve_request', [ $this, 'serve_tracker_file' ], 10, 4 );
-
-	}
-
-	/**
-	 * Serves the tracker gif file.
-	 *
-	 * @since 0.1
-	 * @param bool $served Whether the request has been served
-	 * @param WP_REST_Response $result
-	 * @param WP_REST_Request $request
-	 * @param WP_REST_Server $server
-	 * @return bool $served Whether the request has been served
-	 */
-	public function serve_tracker_file( $served, $result, $request, $server ) {
-
-		// tracker file path
-		$file = CIVICRM_PLUGIN_DIR . 'civicrm/i/tracker.gif';
-
-		// set headers
-		$server->send_header( 'Content-type', 'image/gif' );
-		$server->send_header( 'Cache-Control', 'must-revalidate, post-check=0, pre-check=0' );
-		$server->send_header( 'Content-Description', 'File Transfer' );
-		$server->send_header( 'Content-Disposition', 'inline; filename=tracker.gif' );
-		$server->send_header( 'Content-Length', filesize( $file ) );
-
-		$buffer = readfile( $file );
-
-		return true;
-
-	}
-
-	/**
-	 * Item schema.
-	 *
-	 * @since 0.1
-	 * @return array $schema
-	 */
-	public function get_item_schema() {
-
-		return [
-			'$schema' => 'http://json-schema.org/draft-04/schema#',
-			'title' => 'civicrm/v3/open',
-			'description' => __( 'CiviCRM Open endpoint', 'civicrm' ),
-			'type' => 'object',
-			'required' => [ 'q' ],
-			'properties' => [
-				'q' => [
-					'type' => 'integer'
-				]
-			]
-		];
-
-	}
-
-	/**
-	 * Item arguments.
-	 *
-	 * @since 0.1
-	 * @return array $arguments
-	 */
-	public function get_item_args() {
-
-		return [
-			'q' => [
-				'type' => 'integer',
-				'required' => true,
-				'validate_callback' => function( $value, $request, $key ) {
-
-					return is_numeric( $value );
-
-				}
-			]
-		];
-
-	}
-
-}
diff --git a/wp-rest/Controller/PayPalIPN.php b/wp-rest/Controller/PayPalIPN.php
deleted file mode 100644
index 5b5c38004525287b69024d51ea378cb5615f60bc..0000000000000000000000000000000000000000
--- a/wp-rest/Controller/PayPalIPN.php
+++ /dev/null
@@ -1,134 +0,0 @@
-<?php
-/**
- * PayPalIPN controller class.
- *
- * PayPal IPN endpoint, replacement for CiviCRM's 'extern/ipn.php'.
- *
- * @since 0.1
- */
-
-namespace CiviCRM_WP_REST\Controller;
-
-class PayPalIPN extends Base {
-
-	/**
-	 * The base route.
-	 *
-	 * @since 0.1
-	 * @var string
-	 */
-	protected $rest_base = 'ipn';
-
-	/**
-	 * Registers routes.
-	 *
-	 * @since 0.1
-	 */
-	public function register_routes() {
-
-		register_rest_route( $this->get_namespace(), $this->get_rest_base(), [
-			[
-				'methods' => \WP_REST_Server::ALLMETHODS,
-				'callback' => [ $this, 'get_item' ]
-			]
-		] );
-
-	}
-
-	/**
-	 * Get items.
-	 *
-	 * @since 0.1
-	 * @param WP_REST_Request $request
-	 */
-	public function get_item( $request ) {
-
-		/**
-		 * Filter request params.
-		 *
-		 * @since 0.1
-		 * @param array $params
-		 * @param WP_REST_Request $request
-		 */
-		$params = apply_filters( 'civi_wp_rest/controller/ipn/params', $request->get_params(), $request );
-
-		if ( $request->get_method() == 'GET' ) {
-
-			// paypal standard
-			$paypal_IPN = new \CRM_Core_Payment_PayPalIPN( $params );
-
-			// log notification
-			\Civi::log()->alert( 'payment_notification processor_name=PayPal_Standard', $params );
-
-		} else {
-
-			// paypal pro
-			$paypal_IPN = new \CRM_Core_Payment_PayPalProIPN( $params );
-
-			// log notification
-			\Civi::log()->alert( 'payment_notification processor_name=PayPal', $params );
-
-		}
-
-		/**
-		 * Filter PayPalIPN object.
-		 *
-		 * @param CRM_Core_Payment_PayPalIPN|CRM_Core_Payment_PayPalProIPN $paypal_IPN
-		 * @param array $params
-		 * @param WP_REST_Request $request
-		 */
-		$paypal_IPN = apply_filters( 'civi_wp_rest/controller/ipn/instance', $paypal_IPN, $params, $request );
-
-		try {
-
-			if ( ! method_exists( $paypal_IPN, 'main' ) || ! $this->instance_of_crm_base_ipn( $paypal_IPN ) )
-				return $this->civi_rest_error( sprintf( __( '%s must implement a "main" method.', 'civicrm' ), get_class( $paypal_IPN ) ) );
-
-			$result = $paypal_IPN->main();
-
-		} catch ( \CRM_Core_Exception $e ) {
-
-			\Civi::log()->error( $e->getMessage() );
-			\Civi::log()->error( 'error data ', [ 'data' => $e->getErrorData() ] );
-			\Civi::log()->error( 'REQUEST ', [ 'params' => $params ] );
-
-			return $this->civi_rest_error( $e->getMessage() );
-
-		}
-
-		return rest_ensure_response( $result );
-
-	}
-
-	/**
-	 * Checks whether object is an instance of CRM_Core_Payment_BaseIPN|CRM_Core_Payment_PayPalProIPN|CRM_Core_Payment_PayPalIPN.
-	 *
-	 * Needed because the instance is being filtered through 'civi_wp_rest/controller/ipn/instance'.
-	 *
-	 * @since 0.1
-	 * @param CRM_Core_Payment_BaseIPN|CRM_Core_Payment_PayPalProIPN|CRM_Core_Payment_PayPalIPN $object
-	 * @return bool
-	 */
-	public function instance_of_crm_base_ipn( $object ) {
-
-		return $object instanceof \CRM_Core_Payment_BaseIPN || $object instanceof \CRM_Core_Payment_PayPalProIPN || $object instanceof \CRM_Core_Payment_PayPalIPN;
-
-	}
-
-	/**
-	 * Item schema.
-	 *
-	 * @since 0.1
-	 * @return array $schema
-	 */
-	public function get_item_schema() {}
-
-	/**
-	 * Item arguments.
-	 *
-	 * @since 0.1
-	 * @return array $arguments
-	 */
-	public function get_item_args() {}
-
-}
diff --git a/wp-rest/Controller/PxIPN.php b/wp-rest/Controller/PxIPN.php
deleted file mode 100644
index d68fc8d787ae3e87eb449f36b459e0b8d24d845a..0000000000000000000000000000000000000000
--- a/wp-rest/Controller/PxIPN.php
+++ /dev/null
@@ -1,139 +0,0 @@
-<?php
-/**
- * PxIPN controller class.
- *
- * PxPay IPN endpoint, replacement for CiviCRM's 'extern/pxIPN.php'.
- *
- * @since 0.1
- */
-
-namespace CiviCRM_WP_REST\Controller;
-
-class PxIPN extends Base {
-
-	/**
-	 * The base route.
-	 *
-	 * @since 0.1
-	 * @var string
-	 */
-	protected $rest_base = 'pxIPN';
-
-	/**
-	 * Registers routes.
-	 *
-	 * @since 0.1
-	 */
-	public function register_routes() {
-
-		register_rest_route( $this->get_namespace(), $this->get_rest_base(), [
-			[
-				'methods' => \WP_REST_Server::ALLMETHODS,
-				'callback' => [ $this, 'get_item' ]
-			]
-		] );
-
-	}
-
-	/**
-	 * Get items.
-	 *
-	 * @since 0.1
-	 * @param WP_REST_Request $request
-	 */
-	public function get_item( $request ) {
-
-		/**
-		 * Filter payment processor params.
-		 *
-		 * @since 0.1
-		 * @param array $params
-		 * @param WP_REST_Request $request
-		 */
-		$params = apply_filters(
-			'civi_wp_rest/controller/pxIPN/params',
-			$this->get_payment_processor_args( $request ),
-			$request
-		);
-
-		// log notification
-		\Civi::log()->alert( 'payment_notification processor_name=Payment_Express', $params );
-
-		try {
-
-			$result = \CRM_Core_Payment_PaymentExpressIPN::main( ...$params );
-
-		} catch ( \CRM_Core_Exception $e ) {
-
-			\Civi::log()->error( $e->getMessage() );
-			\Civi::log()->error( 'error data ', [ 'data' => $e->getErrorData() ] );
-			\Civi::log()->error( 'REQUEST ', [ 'params' => $params ] );
-
-			return $this->civi_rest_error( $e->getMessage() );
-
-		}
-
-		return rest_ensure_response( $result );
-
-	}
-
-	/**
-	 * Get payment processor necessary params.
-	 *
-	 * @since 0.1
-	 * @param WP_REST_Resquest $request
-	 * @return array $args
-	 */
-	public function get_payment_processor_args( $request ) {
-
-		// get payment processor types
-		$payment_processor_types = civicrm_api3( 'PaymentProcessor', 'getoptions', [
-			'field' => 'payment_processor_type_id'
-		] );
-
-		// payment processor params
-		$params = apply_filters( 'civi_wp_rest/controller/pxIPN/payment_processor_params', [
-			'user_name' => $request->get_param( 'userid' ),
-			'payment_processor_type_id' => array_search(
-				'DPS Payment Express',
-				$payment_processor_types['values']
-			),
-			'is_active' => 1,
-			'is_test' => 0
-		] );
-
-		// get payment processor
-		$payment_processor = civicrm_api3( 'PaymentProcessor', 'get', $params );
-
-		$args = $payment_processor['values'][$payment_processor['id']];
-
-		$method = empty( $args['signature'] ) ? 'pxpay' : 'pxaccess';
-
-		return [
-			$method,
-			$request->get_param( 'result' ),
-			$args['url_site'],
-			$args['user_name'],
-			$args['password'],
-			$args['signature']
-		];
-
-	}
-
-	/**
-	 * Item schema.
-	 *
-	 * @since 0.1
-	 * @return array $schema
-	 */
-	public function get_item_schema() {}
-
-	/**
-	 * Item arguments.
-	 *
-	 * @since 0.1
-	 * @return array $arguments
-	 */
-	public function get_item_args() {}
-
-}
diff --git a/wp-rest/Controller/Rest.php b/wp-rest/Controller/Rest.php
deleted file mode 100644
index 68b669895b465e2563c34630ea13ddb70417a52e..0000000000000000000000000000000000000000
--- a/wp-rest/Controller/Rest.php
+++ /dev/null
@@ -1,497 +0,0 @@
-<?php
-/**
- * Rest controller class.
- *
- * @since 0.1
- */
-
-namespace CiviCRM_WP_REST\Controller;
-
-class Rest extends Base {
-
-	/**
-	 * The base route.
-	 *
-	 * @since 0.1
-	 * @var string
-	 */
-	protected $rest_base = 'rest';
-
-	/**
-	 * Registers routes.
-	 *
-	 * @since 0.1
-	 */
-	public function register_routes() {
-
-		register_rest_route( $this->get_namespace(), $this->get_rest_base(), [
-			[
-				'methods' => \WP_REST_Server::ALLMETHODS,
-				'callback' => [ $this, 'get_items' ],
-				'permission_callback' => [ $this, 'permissions_check' ],
-				'args' => $this->get_item_args()
-			],
-			'schema' => [ $this, 'get_item_schema' ]
-		] );
-
-	}
-
-	/**
-	 * Check get permission.
-	 *
-	 * @since 0.1
-	 * @param WP_REST_Request $request
-	 * @return bool
-	 */
-	public function permissions_check( $request ) {
-
-		/**
-		 * Opportunity to bypass CiviCRM's
-		 * authentication ('api_key' and 'site_key'),
-		 * return 'true' or 'false' to grant
-		 * or deny access to this endpoint.
-		 *
-		 * To deny and throw an error, return either
-		 * a string, an array, or a \WP_Error.
-		 *
-		 * NOTE: if you use your won authentication,
-		 * you still must log in the user in order
-		 * to respect/apply CiviCRM ACLs.
-		 *
-		 * @since 0.1
-		 * @param null|bool|string|array|\WP_Error $grant_auth Grant, deny, or error
-		 * @param \WP_REST_Request $request The request
-		 */
-		$grant_auth = apply_filters( 'civi_wp_rest/controller/rest/permissions_check', null, $request );
-
-		if ( is_bool( $grant_auth ) ) {
-
-			return $grant_auth;
-
-		} elseif ( is_string( $grant_auth ) ) {
-
-			return $this->civi_rest_error( $grant_auth );
-
-		} elseif ( is_array( $grant_auth ) ) {
-
-			return $this->civi_rest_error( __( 'CiviCRM WP REST permission check error.', 'civicrm' ), $grant_auth );
-
-		} elseif ( $grant_auth instanceof \WP_Error ) {
-
-			return $grant_auth;
-
-		} else {
-
-			if ( ! $this->is_valid_api_key( $request ) )
-				return $this->civi_rest_error( __( 'Param api_key is not valid.', 'civicrm' ) );
-
-			if ( ! $this->is_valid_site_key() )
-				return $this->civi_rest_error( __( 'Param key is not valid.', 'civicrm' ) );
-
-			return true;
-
-		}
-
-	}
-
-	/**
-	 * Get items.
-	 *
-	 * @since 0.1
-	 * @param WP_REST_Request $request
-	 */
-	public function get_items( $request ) {
-
-		/**
-		 * Filter formatted api params.
-		 *
-		 * @since 0.1
-		 * @param array $params
-		 * @param WP_REST_Request $request
-		 */
-		$params = apply_filters( 'civi_wp_rest/controller/rest/api_params', $this->get_formatted_api_params( $request ), $request );
-
-		try {
-
-			$items = civicrm_api3( ...$params );
-
-		} catch ( \CiviCRM_API3_Exception $e ) {
-
-			$items = $this->civi_rest_error( $e );
-
-		}
-
-		if ( ! isset( $items ) || empty( $items ) )
-			return rest_ensure_response( [] );
-
-		/**
-		 * Filter civi api result.
-		 *
-		 * @since 0.1
-		 * @param array $items
-		 * @param WP_REST_Request $request
-		 */
-		$data = apply_filters( 'civi_wp_rest/controller/rest/api_result', $items, $params, $request );
-
-		// only collections of items, ie any action but 'getsingle'
-		if ( isset( $data['values'] ) ) {
-
-			$data['values'] = array_reduce( $items['values'] ?? $items, function( $items, $item ) use ( $request ) {
-
-				$response = $this->prepare_item_for_response( $item, $request );
-
-				$items[] = $this->prepare_response_for_collection( $response );
-
-				return $items;
-
-			}, [] );
-
-		}
-
-		$response = rest_ensure_response( $data );
-
-		// check wheather we need to serve xml or json
-		if ( ! in_array( 'json', array_keys( $request->get_params() ) ) ) {
-
-			/**
-			 * Adds our response holding Civi data before dispatching.
-			 *
-			 * @since 0.1
-			 * @param WP_HTTP_Response $result Result to send to client
-			 * @param WP_REST_Server $server The REST server
-			 * @param WP_REST_Request $request The request
-			 * @return WP_HTTP_Response $result Result to send to client
-			 */
-			add_filter( 'rest_post_dispatch', function( $result, $server, $request ) use ( $response ) {
-
-				return $response;
-
-			}, 10, 3 );
-
-			// serve xml
-			add_filter( 'rest_pre_serve_request', [ $this, 'serve_xml_response' ], 10, 4 );
-
-		} else {
-
-			// return json
-			return $response;
-
-		}
-
-	}
-
-	/**
-	 * Get formatted api params.
-	 *
-	 * @since 0.1
-	 * @param WP_REST_Resquest $request
-	 * @return array $params
-	 */
-	public function get_formatted_api_params( $request ) {
-
-		$args = $request->get_params();
-
-		$entity = $args['entity'];
-		$action = $args['action'];
-
-		// unset unnecessary args
-		unset( $args['entity'], $args['action'], $args['key'], $args['api_key'] );
-
-		if ( ! isset( $args['json'] ) || is_numeric( $args['json'] ) ) {
-
-			$params = $args;
-
-		} else {
-
-			$params = is_string( $args['json'] ) ? json_decode( $args['json'], true ) : [];
-
-		}
-
-		// ensure check permissions is enabled
-		$params['check_permissions'] = true;
-
-		return [ $entity, $action, $params ];
-
-	}
-
-	/**
-	 * Matches the item data to the schema.
-	 *
-	 * @since 0.1
-	 * @param object $item
-	 * @param WP_REST_Request $request
-	 */
-	public function prepare_item_for_response( $item, $request ) {
-
-		return rest_ensure_response( $item );
-
-	}
-
-	/**
-	 * Serves XML response.
-	 *
-	 * @since 0.1
-	 * @param bool $served Whether the request has already been served
-	 * @param WP_REST_Response $result
-	 * @param WP_REST_Request $request
-	 * @param WP_REST_Server $server
-	 */
-	public function serve_xml_response( $served, $result, $request, $server ) {
-
-		// get xml from response
-		$xml = $this->get_xml_formatted_data( $result->get_data() );
-
-		// set content type header
-		$server->send_header( 'Content-Type', 'text/xml' );
-
-		echo $xml;
-
-		return true;
-
-	}
-
-	/**
-	 * Formats CiviCRM API result to XML.
-	 *
-	 * @since 0.1
-	 * @param array $data The CiviCRM api result
-	 * @return string $xml The formatted xml
-	 */
-	protected function get_xml_formatted_data( array $data ) {
-
-		// xml document
-		$xml = new \DOMDocument();
-
-		// result set element <ResultSet>
-		$result_set = $xml->createElement( 'ResultSet' );
-
-		// xmlns:xsi attribute
-		$result_set->setAttribute( 'xmlns:xsi', 'http://www.w3.org/2001/XMLSchema-instance' );
-
-		// count attribute
-		if ( isset( $data['count'] ) ) $result_set->setAttribute( 'count', $data['count'] );
-
-		// build result from result => values
-		if ( isset( $data['values'] ) ) {
-
-			array_map( function( $item ) use ( $result_set, $xml ) {
-
-				// result element <Result>
-				$result = $xml->createElement( 'Result' );
-
-				// format item
-				$result = $this->get_xml_formatted_item( $item, $result, $xml );
-
-				// append result to result set
-				$result_set->appendChild( $result );
-
-			}, $data['values'] );
-
-		} else {
-
-			// result element <Result>
-			$result = $xml->createElement( 'Result' );
-
-			// format item
-			$result = $this->get_xml_formatted_item( $data, $result, $xml );
-
-			// append result to result set
-			$result_set->appendChild( $result );
-
-		}
-
-		// append result set
-		$xml->appendChild( $result_set );
-
-		return $xml->saveXML();
-
-	}
-
-	/**
-	 * Formats a single api result to xml.
-	 *
-	 * @since 0.1
-	 * @param array $item The single api result
-	 * @param DOMElement $parent The parent element to append to
-	 * @param DOMDocument $doc The document
-	 * @return DOMElement $parent The parent element
-	 */
-	public function get_xml_formatted_item( array $item, \DOMElement $parent, \DOMDocument $doc ) {
-
-		// build field => values
-		array_map( function( $field, $value ) use ( $parent, $doc ) {
-
-			// entity field element
-			$element = $doc->createElement( $field );
-
-			// handle array values
-			if ( is_array( $value ) ) {
-
-				array_map( function( $key, $val ) use ( $element, $doc ) {
-
-					// child element, append underscore '_' otherwise createElement
-					// will throw an Invalid character exception as elements cannot start with a number
-					$child = $doc->createElement( '_' . $key, $val );
-
-					// append child
-					$element->appendChild( $child );
-
-				}, array_keys( $value ), $value );
-
-			} else {
-
-				// assign value
-				$element->nodeValue = $value;
-
-			}
-
-			// append element
-			$parent->appendChild( $element );
-
-		}, array_keys( $item ), $item );
-
-		return $parent;
-
-	}
-
-	/**
-	 * Item schema.
-	 *
-	 * @since 0.1
-	 * @return array $schema
-	 */
-	public function get_item_schema() {
-
-		return [
-			'$schema' => 'http://json-schema.org/draft-04/schema#',
-			'title' => 'civicrm/v3/rest',
-			'description' => __( 'CiviCRM API3 WP rest endpoint wrapper', 'civicrm' ),
-			'type' => 'object',
-			'required' => [ 'entity', 'action', 'params' ],
-			'properties' => [
-				'is_error' => [
-					'type' => 'integer'
-				],
-				'version' => [
-					'type' => 'integer'
-				],
-				'count' => [
-					'type' => 'integer'
-				],
-				'values' => [
-					'type' => 'array'
-				]
-			]
-		];
-
-	}
-
-	/**
-	 * Item arguments.
-	 *
-	 * @since 0.1
-	 * @return array $arguments
-	 */
-	public function get_item_args() {
-
-		return [
-			'key' => [
-				'type' => 'string',
-				'required' => false,
-				'validate_callback' => function( $value, $request, $key ) {
-
-					return $this->is_valid_site_key();
-
-				}
-			],
-			'api_key' => [
-				'type' => 'string',
-				'required' => false,
-				'validate_callback' => function( $value, $request, $key ) {
-
-					return $this->is_valid_api_key( $request );
-
-				}
-			],
-			'entity' => [
-				'type' => 'string',
-				'required' => true,
-				'validate_callback' => function( $value, $request, $key ) {
-
-					return is_string( $value );
-
-				}
-			],
-			'action' => [
-				'type' => 'string',
-				'required' => true,
-				'validate_callback' => function( $value, $request, $key ) {
-
-					return is_string( $value );
-
-				}
-			],
-			'json' => [
-				'type' => ['integer', 'string', 'array'],
-				'required' => false,
-				'validate_callback' => function( $value, $request, $key ) {
-
-					return is_numeric( $value ) || is_array( $value ) || $this->is_valid_json( $value );
-
-				}
-			]
-		];
-
-	}
-
-	/**
-	 * Checks if string is a valid json.
-	 *
-	 * @since 0.1
-	 * @param string $param
-	 * @return bool
-	 */
-	public function is_valid_json( $param ) {
-
-		$param = json_decode( $param, true );
-
-		if ( ! is_array( $param ) ) return false;
-
- 		return ( json_last_error() == JSON_ERROR_NONE );
-
-	}
-
-	/**
-	 * Validates the site key.
-	 *
-	 * @since 0.1
-	 * @return bool $is_valid_site_key
-	 */
-	public function is_valid_site_key() {
-
-		return \CRM_Utils_System::authenticateKey( false );
-
-	}
-
-	/**
-	 * Validates the api key.
-	 *
-	 * @since 0.1
-	 * @param WP_REST_Resquest $request
-	 * @return bool $is_valid_api_key
-	 */
-	public function is_valid_api_key( $request ) {
-
-		$api_key = $request->get_param( 'api_key' );
-
-		if ( ! $api_key ) return false;
-
-		$contact_id = \CRM_Core_DAO::getFieldValue( 'CRM_Contact_DAO_Contact', $api_key, 'id', 'api_key' );
-
-		if ( ! $contact_id ) return false;
-
-		return true;
-
-	}
-
-}
diff --git a/wp-rest/Controller/Soap.php b/wp-rest/Controller/Soap.php
deleted file mode 100644
index 17402cc579a834ca8854014e683a53aad5011399..0000000000000000000000000000000000000000
--- a/wp-rest/Controller/Soap.php
+++ /dev/null
@@ -1,98 +0,0 @@
-<?php
-/**
- * Soap controller class.
- *
- * Soap endpoint, replacement for CiviCRM's 'extern/soap.php'.
- *
- * @since 0.1
- */
-
-namespace CiviCRM_WP_REST\Controller;
-
-class Soap extends Base {
-
-	/**
-	 * The base route.
-	 *
-	 * @since 0.1
-	 * @var string
-	 */
-	protected $rest_base = 'soap';
-
-	/**
-	 * Registers routes.
-	 *
-	 * @since 0.1
-	 */
-	public function register_routes() {
-
-		register_rest_route( $this->get_namespace(), $this->get_rest_base(), [
-			[
-				'methods' => \WP_REST_Server::ALLMETHODS,
-				'callback' => [ $this, 'get_item' ]
-			]
-		] );
-
-	}
-
-	/**
-	 * Get items.
-	 *
-	 * @since 0.1
-	 * @param WP_REST_Request $request
-	 */
-	public function get_item( $request ) {
-
-		/**
-		 * Filter request params.
-		 *
-		 * @since 0.1
-		 * @param array $params
-		 * @param WP_REST_Request $request
-		 */
-		$params = apply_filters( 'civi_wp_rest/controller/soap/params', $request->get_params(), $request );
-
-		// init soap server
-		$soap_server = new \SoapServer(
-			NULL,
-			[
-				'uri' => 'urn:civicrm',
-				'soap_version' => SOAP_1_2,
-			]
-		);
-
-		$crm_soap_server = new \CRM_Utils_SoapServer();
-
-		$soap_server->setClass( 'CRM_Utils_SoapServer', \CRM_Core_Config::singleton()->userFrameworkClass );
-		$soap_server->setPersistence( SOAP_PERSISTENCE_SESSION );
-
-		/**
-		 * Bypass WP and send request from Soap server.
-		 */
-		add_filter( 'rest_pre_serve_request', function( $served, $response, $request, $server ) use ( $soap_server ) {
-
-			$soap_server->handle();
-
-			return true;
-
-		}, 10, 4 );
-
-	}
-
-	/**
-	 * Item schema.
-	 *
-	 * @since 0.1
-	 * @return array $schema
-	 */
-	public function get_item_schema() {}
-
-	/**
-	 * Item arguments.
-	 *
-	 * @since 0.1
-	 * @return array $arguments
-	 */
-	public function get_item_args() {}
-
-}
diff --git a/wp-rest/Controller/Url.php b/wp-rest/Controller/Url.php
deleted file mode 100644
index 6f1009f8fdb321c0f9a79b2d569372e629936e59..0000000000000000000000000000000000000000
--- a/wp-rest/Controller/Url.php
+++ /dev/null
@@ -1,216 +0,0 @@
-<?php
-/**
- * Url controller class.
- *
- * @since 0.1
- */
-
-namespace CiviCRM_WP_REST\Controller;
-
-class Url extends Base {
-
-	/**
-	 * The base route.
-	 *
-	 * @since 0.1
-	 * @var string
-	 */
-	protected $rest_base = 'url';
-
-	/**
-	 * Registers routes.
-	 *
-	 * @since 0.1
-	 */
-	public function register_routes() {
-
-		register_rest_route( $this->get_namespace(), $this->get_rest_base(), [
-			[
-				'methods' => \WP_REST_Server::READABLE,
-				'callback' => [ $this, 'get_item' ],
-				'args' => $this->get_item_args()
-			],
-			'schema' => [ $this, 'get_item_schema' ]
-		] );
-
-	}
-
-	/**
-	 * Get items.
-	 *
-	 * @since 0.1
-	 * @param WP_REST_Request $request
-	 */
-	public function get_item( $request ) {
-
-		/**
-		 * Filter formatted api params.
-		 *
-		 * @since 0.1
-		 * @param array $params
-		 * @param WP_REST_Request $request
-		 */
-		$params = apply_filters( 'civi_wp_rest/controller/url/params', $this->get_formatted_params( $request ), $request );
-
-		// track url
-		$url = \CRM_Mailing_Event_BAO_TrackableURLOpen::track( $params['queue_id'], $params['url_id'] );
-
-		/**
-		 * Filter url.
-		 *
-		 * @param string $url
-		 * @param array $params
-		 * @param WP_REST_Request $request
-		 */
-		$url = apply_filters( 'civi_wp_rest/controller/url/before_parse_url', $url, $params, $request );
-
-		// parse url
-		$url = $this->parse_url( $url, $params );
-
-		$this->do_redirect( $url );
-
-	}
-
-	/**
-	 * Get formatted api params.
-	 *
-	 * @since 0.1
-	 * @param WP_REST_Resquest $request
-	 * @return array $params
-	 */
-	protected function get_formatted_params( $request ) {
-
-		$args = $request->get_params();
-
-		$params = [
-			'queue_id' => isset( $args['qid'] ) ? $args['qid'] ?? '' : $args['q'] ?? '',
-			'url_id' => $args['u']
-		];
-
-		// unset unnecessary args
-		unset( $args['qid'], $args['u'], $args['q'] );
-
-		if ( ! empty( $args ) ) {
-
-			$params['query'] = http_build_query( $args );
-
-		}
-
-		return $params;
-
-	}
-
-	/**
-	 * Parses the url.
-	 *
-	 * @since 0.1
-	 * @param string $url
-	 * @param array $params
-	 * @return string $url
-	 */
-	protected function parse_url( $url, $params ) {
-
-		// CRM-18320 - Fix encoded ampersands
-		$url = str_replace( '&amp;', '&', $url );
-
-		// CRM-7103 - Look for additional query variables and append them
-		if ( isset( $params['query'] ) && strpos( $url, '?' ) ) {
-
-			$url .= '&' . $params['query'];
-
-		} elseif ( isset( $params['query'] ) ) {
-
-			$url .= '?' . $params['query'];
-
-		}
-
-		if ( strpos( $url, 'mailto' ) ) $url = strstr( $url, 'mailto' );
-
-		return apply_filters( 'civi_wp_rest/controller/url/parsed_url', $url, $params );
-
-	}
-
-	/**
-	 * Do redirect.
-	 *
-	 * @since 0.1
-	 * @param string $url
-	 */
-	protected function do_redirect( $url ) {
-
-		wp_redirect( $url );
-
-		exit;
-
-	}
-
-	/**
-	 * Item schema.
-	 *
-	 * @since 0.1
-	 * @return array $schema
-	 */
-	public function get_item_schema() {
-
-		return [
-			'$schema' => 'http://json-schema.org/draft-04/schema#',
-			'title' => 'civicrm_api3/v3/url',
-			'description' => __( 'CiviCRM API3 wrapper', 'civicrm' ),
-			'type' => 'object',
-			'required' => [ 'qid', 'u' ],
-			'properties' => [
-				'qid' => [
-					'type' => 'integer'
-				],
-				'q' => [
-					'type' => 'integer'
-				],
-				'u' => [
-					'type' => 'integer'
-				]
-			]
-		];
-
-	}
-
-	/**
-	 * Item arguments.
-	 *
-	 * @since 0.1
-	 * @return array $arguments
-	 */
-	public function get_item_args() {
-
-		return [
-			'qid' => [
-				'type' => 'integer',
-				'required' => false,
-				'validate_callback' => function( $value, $request, $key ) {
-
-					return is_numeric( $value );
-
-				}
-			],
-			'q' => [
-				'type' => 'integer',
-				'required' => false,
-				'validate_callback' => function( $value, $request, $key ) {
-
-					return is_numeric( $value );
-
-				}
-			],
-			'u' => [
-				'type' => 'integer',
-				'required' => true,
-				'validate_callback' => function( $value, $request, $key ) {
-
-					return is_numeric( $value );
-
-				}
-			]
-		];
-
-	}
-
-}
diff --git a/wp-rest/Controller/Widget.php b/wp-rest/Controller/Widget.php
deleted file mode 100644
index 13fa1e2adde648de8c24b1278039385569bd5c21..0000000000000000000000000000000000000000
--- a/wp-rest/Controller/Widget.php
+++ /dev/null
@@ -1,214 +0,0 @@
-<?php
-/**
- * Widget controller class.
- *
- * Widget endpoint, replacement for CiviCRM's 'extern/widget.php'
- *
- * @since 0.1
- */
-
-namespace CiviCRM_WP_REST\Controller;
-
-class Widget extends Base {
-
-	/**
-	 * The base route.
-	 *
-	 * @since 0.1
-	 * @var string
-	 */
-	protected $rest_base = 'widget';
-
-	/**
-	 * Registers routes.
-	 *
-	 * @since 0.1
-	 */
-	public function register_routes() {
-
-		register_rest_route( $this->get_namespace(), $this->get_rest_base(), [
-			[
-				'methods' => \WP_REST_Server::READABLE,
-				'callback' => [ $this, 'get_item' ],
-				'args' => $this->get_item_args()
-			],
-			'schema' => [ $this, 'get_item_schema' ]
-		] );
-
-	}
-
-	/**
-	 * Get item.
-	 *
-	 * @since 0.1
-	 * @param WP_REST_Request $request
-	 */
-	public function get_item( $request ) {
-
-		/**
-		 * Filter mandatory params.
-		 *
-		 * @since 0.1
-		 * @param array $params
-		 * @param WP_REST_Request $request
-		 */
-		$params = apply_filters(
-			'civi_wp_rest/controller/widget/params',
-			$this->get_mandatory_params( $request ),
-			$request
-		);
-
-		$jsonvar = 'jsondata';
-
-		if ( ! empty( $request->get_param( 'format' ) ) ) $jsonvar .= $request->get_param( 'cpageId' );
-
-		$data = \CRM_Contribute_BAO_Widget::getContributionPageData( ...$params );
-
-		$response = 'var ' . $jsonvar . ' = ' . json_encode( $data ) . ';';
-
-		/**
-		 * Adds our response data before dispatching.
-		 *
-		 * @since 0.1
-		 * @param WP_HTTP_Response $result Result to send to client
-		 * @param WP_REST_Server $server The REST server
-		 * @param WP_REST_Request $request The request
-		 * @return WP_HTTP_Response $result Result to send to client
-		 */
-		add_filter( 'rest_post_dispatch', function( $result, $server, $request ) use ( $response ) {
-
-			return rest_ensure_response( $response );
-
-		}, 10, 3 );
-
-		// serve javascript
-		add_filter( 'rest_pre_serve_request', [ $this, 'serve_javascript' ], 10, 4 );
-
-	}
-
-	/**
-	 * Get mandatory params from request.
-	 *
-	 * @since 0.1
-	 * @param WP_REST_Resquest $request
-	 * @return array $params The widget params
-	 */
-	protected function get_mandatory_params( $request ) {
-
-		$args = $request->get_params();
-
-		return [
-			$args['cpageId'],
-			$args['widgetId'],
-			$args['includePending'] ?? false
-		];
-
-	}
-
-	/**
-	 * Serve jsondata response.
-	 *
-	 * @since 0.1
-	 * @param bool $served Whether the request has already been served
-	 * @param WP_REST_Response $result
-	 * @param WP_REST_Request $request
-	 * @param WP_REST_Server $server
-	 * @return bool $served
-	 */
-	public function serve_javascript( $served, $result, $request, $server ) {
-
-		// set content type header
-		$server->send_header( 'Expires', gmdate( 'D, d M Y H:i:s \G\M\T', time() + 60 ) );
-		$server->send_header( 'Content-Type', 'application/javascript' );
-		$server->send_header( 'Cache-Control', 'max-age=60, public' );
-
-		echo $result->get_data();
-
-		return true;
-
-	}
-
-	/**
-	 * Item schema.
-	 *
-	 * @since 0.1
-	 * @return array $schema
-	 */
-	public function get_item_schema() {
-
-		return [
-			'$schema' => 'http://json-schema.org/draft-04/schema#',
-			'title' => 'civicrm_api3/v3/widget',
-			'description' => __( 'CiviCRM API3 wrapper', 'civicrm' ),
-			'type' => 'object',
-			'required' => [ 'cpageId', 'widgetId' ],
-			'properties' => [
-				'cpageId' => [
-					'type' => 'integer',
-					'minimum' => 1
-				],
-				'widgetId' => [
-					'type' => 'integer',
-					'minimum' => 1
-				],
-				'format' => [
-					'type' => 'integer'
-				],
-				'includePending' => [
-					'type' => 'boolean'
-				]
-			]
-		];
-
-	}
-
-	/**
-	 * Item arguments.
-	 *
-	 * @since 0.1
-	 * @return array $arguments
-	 */
-	public function get_item_args() {
-
-		return [
-			'cpageId' => [
-				'type' => 'integer',
-				'required' => true,
-				'validate_callback' => function( $value, $request, $key ) {
-
-					return is_numeric( $value );
-
-				}
-			],
-			'widgetId' => [
-				'type' => 'integer',
-				'required' => true,
-				'validate_callback' => function( $value, $request, $key ) {
-
-					return is_numeric( $value );
-
-				}
-			],
-			'format' => [
-				'type' => 'integer',
-				'required' => false,
-				'validate_callback' => function( $value, $request, $key ) {
-
-					return is_numeric( $value );
-
-				}
-			],
-			'includePending' => [
-				'type' => 'boolean',
-				'required' => false,
-				'validate_callback' => function( $value, $request, $key ) {
-
-					return is_string( $value );
-
-				}
-			]
-		];
-
-	}
-
-}
diff --git a/wp-rest/Endpoint/Endpoint-Interface.php b/wp-rest/Endpoint/Endpoint-Interface.php
deleted file mode 100644
index 9497cde5099ecbd7936571b0b73e318652abea7f..0000000000000000000000000000000000000000
--- a/wp-rest/Endpoint/Endpoint-Interface.php
+++ /dev/null
@@ -1,35 +0,0 @@
-<?php
-/**
- * Endpoint Interface class.
- *
- * @since 0.1
- */
-
-namespace CiviCRM_WP_REST\Endpoint;
-
-interface Endpoint_Interface {
-
-	/**
-	 * Registers routes.
-	 *
-	 * @since 0.1
-	 */
-	public function register_routes();
-
-	/**
-	 * Item schema.
-	 *
-	 * @since 0.1
-	 * @return array $schema
-	 */
-	public function get_item_schema();
-
-	/**
-	 * Item arguments.
-	 *
-	 * @since 0.1
-	 * @return array $arguments
-	 */
-	public function get_item_args();
-
-}
diff --git a/wp-rest/Plugin.php b/wp-rest/Plugin.php
deleted file mode 100644
index 3531e597e40aae1b9b58562263ca0fc122b06540..0000000000000000000000000000000000000000
--- a/wp-rest/Plugin.php
+++ /dev/null
@@ -1,379 +0,0 @@
-<?php
-/**
- * Main plugin class.
- *
- * @since 0.1
- */
-
-namespace CiviCRM_WP_REST;
-
-use CiviCRM_WP_REST\Civi\Mailing_Hooks;
-
-class Plugin {
-
-	/**
-	 * Constructor.
-	 *
-	 * @since 0.1
-	 */
-	public function __construct() {
-
-		$this->register_hooks();
-
-		$this->setup_objects();
-
-	}
-
-	/**
-	 * Register hooks.
-	 *
-	 * @since 1.0
-	 */
-	protected function register_hooks() {
-
-		add_action( 'rest_api_init', [ $this, 'register_rest_routes' ] );
-
-		add_filter( 'rest_pre_dispatch', [ $this, 'bootstrap_civi' ], 10, 3 );
-
-		add_filter( 'rest_post_dispatch',  [ $this, 'maybe_reset_wp_timezone' ], 10, 3);
-
-	}
-
-	/**
-	 * Bootstrap CiviCRM when hitting a the 'civicrm' namespace.
-	 *
-	 * @since 0.1
-	 * @param mixed $result
-	 * @param WP_REST_Server $server REST server instance
-	 * @param WP_REST_Request $request The request
-	 * @return mixed $result
-	 */
-	public function bootstrap_civi( $result, $server, $request ) {
-
-		if ( false !== strpos( $request->get_route(), 'civicrm' ) ) {
-
-			$this->maybe_set_user_timezone( $request );
-
-			civi_wp()->initialize();
-
-			// rest calls need a wp user, do login
-			if ( false !== strpos( $request->get_route(), 'rest' ) ) {
-
-				$logged_in_wp_user = $this->do_user_login( $request );
-
-				// return error
-				if ( is_wp_error( $logged_in_wp_user ) ) {
-					return $logged_in_wp_user;
-				}
-			}
-
-		}
-
-		return $result;
-
-	}
-
-	/**
-	 * Setup objects.
-	 *
-	 * @since 0.1
-	 */
-	private function setup_objects() {
-
-		/**
- 		 * Filter to replace the mailing tracking URLs.
- 		 *
- 		 * @since 0.1
- 		 * @param bool $replace_mailing_tracking_urls
- 		 */
- 		$replace_mailing_tracking_urls = apply_filters( 'civi_wp_rest/plugin/replace_mailing_tracking_urls', false );
-
- 		// keep CIVICRM_WP_REST_REPLACE_MAILING_TRACKING for backwards compatibility
- 		if (
- 			$replace_mailing_tracking_urls
- 			|| ( defined( 'CIVICRM_WP_REST_REPLACE_MAILING_TRACKING' ) && CIVICRM_WP_REST_REPLACE_MAILING_TRACKING )
- 		) {
-			// register mailing hooks
-			$mailing_hooks = ( new Mailing_Hooks )->register_hooks();
-
-		}
-
-	}
-
-	/**
-	 * Registers Rest API routes.
-	 *
-	 * @since 0.1
-	 */
-	public function register_rest_routes() {
-
-		// rest endpoint
-		$rest_controller = new Controller\Rest;
-		$rest_controller->register_routes();
-
-		// url controller
-		$url_controller = new Controller\Url;
-		$url_controller->register_routes();
-
-		// open controller
-		$open_controller = new Controller\Open;
-		$open_controller->register_routes();
-
-		// authorizenet controller
-		$authorizeIPN_controller = new Controller\AuthorizeIPN;
-		$authorizeIPN_controller->register_routes();
-
-		// paypal controller
-		$paypalIPN_controller = new Controller\PayPalIPN;
-		$paypalIPN_controller->register_routes();
-
-		// pxpay controller
-		$paypalIPN_controller = new Controller\PxIPN;
-		$paypalIPN_controller->register_routes();
-
-		// civiconnect controller
-		$cxn_controller = new Controller\Cxn;
-		$cxn_controller->register_routes();
-
-		// widget controller
-		$widget_controller = new Controller\Widget;
-		$widget_controller->register_routes();
-
-		// soap controller
-		$soap_controller = new Controller\Soap;
-		$soap_controller->register_routes();
-
-		/**
-		 * Opportunity to add more rest routes.
-		 *
-		 * @since 0.1
-		 */
-		do_action( 'civi_wp_rest/plugin/rest_routes_registered' );
-
-	}
-
-	/**
-	 * Sets the timezone to the users timezone when
-	 * calling the civicrm/v3/rest endpoint.
-	 *
-	 * @since 0.1
-	 * @param WP_REST_Request $request The request
-	 */
-	private function maybe_set_user_timezone( $request ) {
-
-		if ( $request->get_route() != '/civicrm/v3/rest' ) return;
-
-		$timezones = [
-			'wp_timezone' => date_default_timezone_get(),
-			'user_timezone' => get_option( 'timezone_string', false )
-		];
-
-		// filter timezones
-		add_filter( 'civi_wp_rest/plugin/timezones', function() use ( $timezones ) {
-
-			return $timezones;
-
-		} );
-
-		if ( empty( $timezones['user_timezone'] ) ) return;
-
-		/**
-		 * CRM-12523
-		 * CRM-18062
-		 * CRM-19115
-		 */
-		date_default_timezone_set( $timezones['user_timezone'] );
-		\CRM_Core_Config::singleton()->userSystem->setMySQLTimeZone();
-
-	}
-
-	/**
-	 * Resets the timezone to the original WP
-	 * timezone after calling the civicrm/v3/rest endpoint.
-	 *
-	 * @since 0.1
-	 * @param mixed $result
-	 * @param WP_REST_Server $server REST server instance
-	 * @param WP_REST_Request $request The request
-	 * @return mixed $result
-	 */
-	public function maybe_reset_wp_timezone( $result, $server, $request ) {
-
-		if ( $request->get_route() != '/civicrm/v3/rest' ) return $result;
-
-		$timezones = apply_filters( 'civi_wp_rest/plugin/timezones', null );
-
-		if ( empty( $timezones['wp_timezone'] ) ) return $result;
-
-		// reset wp timezone
-		date_default_timezone_set( $timezones['wp_timezone'] );
-
-		return $result;
-
-	}
-
-	/**
-	 * Performs the necessary checks and
-	 * data retrieval to login a WordPress user.
-	 *
-	 * @since 0.1
-	 * @param \WP_REST_Request $request The request
-	 * @return \WP_User|\WP_Error|void $logged_in_wp_user The logged in WordPress user object, \Wp_Error, or nothing
-	 */
-	public function do_user_login( $request ) {
-
-		/**
-		 * Filter and opportunity to bypass
-		 * the default user login.
-		 *
-		 * @since 0.1
-		 * @param bool $login
-		 */
-		$logged_in = apply_filters( 'civi_wp_rest/plugin/do_user_login', false, $request );
-
-		if ( $logged_in ) return;
-
-		// default login based on contact's api_key
-		if ( ! ( new Controller\Rest )->is_valid_api_key( $request ) ) {
-			return new \WP_Error(
-				'civicrm_rest_api_error',
-				__( 'Missing or invalid param "api_key".', 'civicrm' )
-			);
-		}
-
-		$contact_id = \CRM_Core_DAO::getFieldValue(
-			'CRM_Contact_DAO_Contact',
-			$request->get_param( 'api_key' ),
-			'id',
-			'api_key'
-		);
-
-		$wp_user = $this->get_wp_user( $contact_id );
-
-		if ( is_wp_error( $wp_user ) ) {
-			return $wp_user;
-		}
-
-		return $this->login_wp_user( $wp_user, $request );
-
-	}
-
-	/**
-	 * Get WordPress user data.
-	 *
-	 * @since 0.1
-	 * @param int $contact_id The contact id
-	 * @return WP_User|WP_Error $user The WordPress user data or WP_Error object
-	 */
-	public function get_wp_user( int $contact_id ) {
-
-		try {
-
-			// Call API.
-			$uf_match = civicrm_api3( 'UFMatch', 'getsingle', [
-				'contact_id' => $contact_id,
-				'domain_id' => $this->get_civi_domain_id(),
-			] );
-
-		} catch ( \CiviCRM_API3_Exception $e ) {
-
-			return new \WP_Error(
-				'civicrm_rest_api_error',
-				__( 'A WordPress user must be associated with the contact for the provided API key.', 'civicrm' )
-			);
-
-		}
-
-		// filter uf_match
-		add_filter( 'civi_wp_rest/plugin/uf_match', function() use ( $uf_match ) {
-
-			return ! empty( $uf_match ) ? $uf_match : null;
-
-		} );
-
-		return get_userdata( $uf_match['uf_id'] );
-
-	}
-
-	/**
-	 * Logs in the WordPress user, and
-	 * syncs it with it's CiviCRM contact.
-	 *
-	 * @since 0.1
-	 * @param \WP_User $user The WordPress user object
-	 * @param \WP_REST_Request|null $request The request object or null
-	 * @return \WP_User|void $wp_user The logged in WordPress user object or nothing
-	 */
-	public function login_wp_user( \WP_User $wp_user, $request = null ) {
-
-		/**
-		 * Filter the user about to be logged in.
-		 *
-		 * @since 0.1
-		 * @param \WP_User $user The WordPress user object
-		 * @param \WP_REST_Request|null $request The request object or null
-		 */
-		$wp_user = apply_filters( 'civi_wp_rest/plugin/wp_user_login', $wp_user, $request );
-
-		wp_set_current_user( $wp_user->ID, $wp_user->user_login );
-
-		wp_set_auth_cookie( $wp_user->ID );
-
-		do_action( 'wp_login', $wp_user->user_login, $wp_user );
-
-		$this->set_civi_user_session( $wp_user );
-
-		return $wp_user;
-
-	}
-
-	/**
-	 * Sets the necessary user
-	 * session variables for CiviCRM.
-	 *
-	 * @since 0.1
-	 * @param \WP_User $wp_user The WordPress user
-	 * @return void
-	 */
-	public function set_civi_user_session( $wp_user ): void {
-
-		$uf_match = apply_filters( 'civi_wp_rest/plugin/uf_match', null );
-
-		if ( ! $uf_match ) {
-
-			// Call API.
-			$uf_match = civicrm_api3( 'UFMatch', 'getsingle', [
-				'uf_id' => $wp_user->ID,
-				'domain_id' => $this->get_civi_domain_id(),
-			] );
-		}
-
-		// Set necessary session variables.
-		$session = \CRM_Core_Session::singleton();
-		$session->set( 'ufID', $wp_user->ID );
-		$session->set( 'userID', $uf_match['contact_id'] );
-		$session->set( 'ufUniqID', $uf_match['uf_name'] );
-
-	}
-
-	/**
-	 * Retrieves the CiviCRM domain_id.
-	 *
-	 * @since 0.1
-	 * @return int $domain_id The domain id
-	 */
-	public function get_civi_domain_id(): int {
-
-		// Get CiviCRM domain group ID from constant, if set.
-		$domain_id = defined( 'CIVICRM_DOMAIN_ID' ) ? CIVICRM_DOMAIN_ID : 0;
-
-		// If this fails, get it from config.
-		if ( $domain_id === 0 ) {
-			$domain_id = \CRM_Core_Config::domainID();
-		}
-
-		return $domain_id;
-
-	}
-
-}
diff --git a/wp-rest/README.md b/wp-rest/README.md
deleted file mode 100644
index 77234de84a195dc6fbb22e1e7d460ff7d44587f2..0000000000000000000000000000000000000000
--- a/wp-rest/README.md
+++ /dev/null
@@ -1,59 +0,0 @@
-# CiviCRM WP REST API Wrapper
-
-This is a WordPress plugin that aims to expose CiviCRM's [extern](https://github.com/civicrm/civicrm-core/tree/master/extern) scripts as WordPress REST endpoints.
-
-This plugin requires:
-
--   PHP 7.1+
--   WordPress 4.7+
--   CiviCRM to be installed and activated.
-
-### Endpoints
-
-1. `civicrm/v3/rest` - a wrapper around `civicrm_api3()`
-
-    **Parameters**:
-
-    - `key` - **required**, the site key
-    - `api_key` - **required**, the contact api key
-    - `entity` - **required**, the API entity
-    - `action` - **required**, the API action
-    - `json` - **optional**, json formatted string with the API parameters/argumets, or `1` as in `json=1`
-
-    By default all calls to `civicrm/v3/rest` return XML formatted results, to get `json` formatted result pass `json=1` or a json formatted string with the API parameters, like in the example 2 below.
-
-    **Examples**:
-
-    1. `https://example.com/wp-json/civicrm/v3/rest?entity=Contact&action=get&key=<site_key>&api_key=<api_key>&group=Administrators`
-
-    2. `https://example.com/wp-json/civicrm/v3/rest?entity=Contact&action=get&key=<site_key>&api_key=<api_key>&json={"group": "Administrators"}`
-
-2. `civicrm/v3/url` - a substition for `civicrm/extern/url.php` mailing tracking
-
-3. `civicrm/v3/open` - a substition for `civicrm/extern/open.php` mailing tracking
-
-4. `civicrm/v3/authorizeIPN` - a substition for `civicrm/extern/authorizeIPN.php` (for testing Authorize.net as per [docs](https://docs.civicrm.org/sysadmin/en/latest/setup/payment-processors/authorize-net/#shell-script-testing-method))
-
-    **_Note_**: this endpoint has **not been tested**
-
-5. `civicrm/v3/ipn` - a substition for `civicrm/extern/ipn.php` (for PayPal Standard and Pro live transactions)
-
-    **_Note_**: this endpoint has **not been tested**
-
-6. `civicrm/v3/cxn` - a substition for `civicrm/extern/cxn.php`
-
-7. `civicrm/v3/pxIPN` - a substition for `civicrm/extern/pxIPN.php`
-
-    **_Note_**: this endpoint has **not been tested**
-
-8. `civicrm/v3/widget` - a substition for `civicrm/extern/widget.php`
-
-9. `civicrm/v3/soap` - a substition for `civicrm/extern/soap.php`
-
-    **_Note_**: this endpoint has **not been tested**
-
-### Settings
-
-Set the `CIVICRM_WP_REST_REPLACE_MAILING_TRACKING` constant to `true` to replace mailing url and open tracking calls with their counterpart REST endpoints, `civicrm/v3/url` and `civicrm/v3/open`.
-
-_Note: use this setting with caution, it may affect performance on large mailings, see `CiviCRM_WP_REST\Civi\Mailing_Hooks` class._