.
diff --git a/wp/wp-content/plugins/imagify/inc/Dependencies/ActionScheduler/readme.txt b/wp/wp-content/plugins/imagify/inc/Dependencies/ActionScheduler/readme.txt
new file mode 100644
index 00000000..7e0cc7e7
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/Dependencies/ActionScheduler/readme.txt
@@ -0,0 +1,185 @@
+=== Action Scheduler ===
+Contributors: Automattic, wpmuguru, claudiosanches, peterfabian1000, vedjain, jamosova, obliviousharmony, konamiman, sadowski, royho, barryhughes-1
+Tags: scheduler, cron
+Stable tag: 3.7.1
+License: GPLv3
+Requires at least: 6.2
+Tested up to: 6.4
+Requires PHP: 5.6
+
+Action Scheduler - Job Queue for WordPress
+
+== Description ==
+
+Action Scheduler is a scalable, traceable job queue for background processing large sets of actions in WordPress. It's specially designed to be distributed in WordPress plugins.
+
+Action Scheduler works by triggering an action hook to run at some time in the future. Each hook can be scheduled with unique data, to allow callbacks to perform operations on that data. The hook can also be scheduled to run on one or more occassions.
+
+Think of it like an extension to `do_action()` which adds the ability to delay and repeat a hook.
+
+## Battle-Tested Background Processing
+
+Every month, Action Scheduler processes millions of payments for [Subscriptions](https://woocommerce.com/products/woocommerce-subscriptions/), webhooks for [WooCommerce](https://wordpress.org/plugins/woocommerce/), as well as emails and other events for a range of other plugins.
+
+It's been seen on live sites processing queues in excess of 50,000 jobs and doing resource intensive operations, like processing payments and creating orders, at a sustained rate of over 10,000 / hour without negatively impacting normal site operations.
+
+This is all on infrastructure and WordPress sites outside the control of the plugin author.
+
+If your plugin needs background processing, especially of large sets of tasks, Action Scheduler can help.
+
+## Learn More
+
+To learn more about how to Action Scheduler works, and how to use it in your plugin, check out the docs on [ActionScheduler.org](https://actionscheduler.org).
+
+There you will find:
+
+* [Usage guide](https://actionscheduler.org/usage/): instructions on installing and using Action Scheduler
+* [WP CLI guide](https://actionscheduler.org/wp-cli/): instructions on running Action Scheduler at scale via WP CLI
+* [API Reference](https://actionscheduler.org/api/): complete reference guide for all API functions
+* [Administration Guide](https://actionscheduler.org/admin/): guide to managing scheduled actions via the administration screen
+* [Guide to Background Processing at Scale](https://actionscheduler.org/perf/): instructions for running Action Scheduler at scale via the default WP Cron queue runner
+
+## Credits
+
+Action Scheduler is developed and maintained by [Automattic](http://automattic.com/) with significant early development completed by [Flightless](https://flightless.us/).
+
+Collaboration is cool. We'd love to work with you to improve Action Scheduler. [Pull Requests](https://github.com/woocommerce/action-scheduler/pulls) welcome.
+
+== Changelog ==
+
+= 3.7.1 - 2023-12-13 =
+* Release/3.7.0.
+* Tweak - WP 6.4 compatibility.
+* update semver to 5.7.2 because of a security vulnerability in 5.7.1.
+
+= 3.7.0 - 2023-11-20 =
+* Important: starting with this release, Action Scheduler follows an L-2 version policy (WordPress, and consequently PHP).
+* Add extended indexes for hook_status_scheduled_date_gmt and status_sheduled_date_gmt.
+* Catch and log exceptions thrown when actions can't be created, e.g. under a corrupt database schema.
+* Release/3.6.4.
+* Tweak - WP 6.4 compatibility.
+* Update unit tests for upcoming dependency version policy.
+* make sure hook action_scheduler_failed_execution can access original exception object.
+* mention dependency version policy in usage.md.
+
+= 3.6.4 - 2023-10-11 =
+* Performance improvements when bulk cancelling actions.
+* Dev-related fixes.
+
+= 3.6.3 - 2023-09-13 =
+* Use `_doing_it_wrong` in initialization check.
+
+= 3.6.2 - 2023-08-09 =
+* Add guidance about passing arguments.
+* Atomic option locking.
+* Improve bulk delete handling.
+* Include database error in the exception message.
+* Tweak - WP 6.3 compatibility.
+
+= 3.6.1 - 2023-06-14 =
+* Document new optional `$priority` arg for various API functions.
+* Document the new `--exclude-groups` WP CLI option.
+* Document the new `action_scheduler_init` hook.
+* Ensure actions within each claim are executed in the expected order.
+* Fix incorrect text domain.
+* Remove SHOW TABLES usage when checking if tables exist.
+
+= 3.6.0 - 2023-05-10 =
+* Add $unique parameter to function signatures.
+* Add a cast-to-int for extra safety before forming new DateTime object.
+* Add a hook allowing exceptions for consistently failing recurring actions.
+* Add action priorities.
+* Add init hook.
+* Always raise the time limit.
+* Bump minimatch from 3.0.4 to 3.0.8.
+* Bump yaml from 2.2.1 to 2.2.2.
+* Defensive coding relating to gaps in declared schedule types.
+* Do not process an action if it cannot be set to `in-progress`.
+* Filter view labels (status names) should be translatable | #919.
+* Fix WPCLI progress messages.
+* Improve data-store initialization flow.
+* Improve error handling across all supported PHP versions.
+* Improve logic for flushing the runtime cache.
+* Support exclusion of multiple groups.
+* Update lint-staged and Node/NPM requirements.
+* add CLI clean command.
+* add CLI exclude-group filter.
+* exclude past-due from list table all filter count.
+* throwing an exception if as_schedule_recurring_action interval param is not of type integer.
+
+= 3.5.4 - 2023-01-17 =
+* Add pre filters during action registration.
+* Async scheduling.
+* Calculate timeouts based on total actions.
+* Correctly order the parameters for `ActionScheduler_ActionFactory`'s calls to `single_unique`.
+* Fetch action in memory first before releasing claim to avoid deadlock.
+* PHP 8.2: declare property to fix creation of dynamic property warning.
+* PHP 8.2: fix "Using ${var} in strings is deprecated, use {$var} instead".
+* Prevent `undefined variable` warning for `$num_pastdue_actions`.
+
+= 3.5.3 - 2022-11-09 =
+* Query actions with partial match.
+
+= 3.5.2 - 2022-09-16 =
+* Fix - erroneous 3.5.1 release.
+
+= 3.5.1 - 2022-09-13 =
+* Maintenance on A/S docs.
+* fix: PHP 8.2 deprecated notice.
+
+= 3.5.0 - 2022-08-25 =
+* Add - The active view link within the "Tools > Scheduled Actions" screen is now clickable.
+* Add - A warning when there are past-due actions.
+* Enhancement - Added the ability to schedule unique actions via an atomic operation.
+* Enhancement - Improvements to cache invalidation when processing batches (when running on WordPress 6.0+).
+* Enhancement - If a recurring action is found to be consistently failing, it will stop being rescheduled.
+* Enhancement - Adds a new "Past Due" view to the scheduled actions list table.
+
+= 3.4.2 - 2022-06-08 =
+* Fix - Change the include for better linting.
+* Fix - update: Added Action scheduler completed action hook.
+
+= 3.4.1 - 2022-05-24 =
+* Fix - Change the include for better linting.
+* Fix - Fix the documented return type.
+
+= 3.4.0 - 2021-10-29 =
+* Enhancement - Number of items per page can now be set for the Scheduled Actions view (props @ovidiul). #771
+* Fix - Do not lower the max_execution_time if it is already set to 0 (unlimited) (props @barryhughes). #755
+* Fix - Avoid triggering autoloaders during the version resolution process (props @olegabr). #731 & #776
+* Dev - ActionScheduler_wcSystemStatus PHPCS fixes (props @ovidiul). #761
+* Dev - ActionScheduler_DBLogger.php PHPCS fixes (props @ovidiul). #768
+* Dev - Fixed phpcs for ActionScheduler_Schedule_Deprecated (props @ovidiul). #762
+* Dev - Improve actions table indicies (props @glagonikas). #774 & #777
+* Dev - PHPCS fixes for ActionScheduler_DBStore.php (props @ovidiul). #769 & #778
+* Dev - PHPCS Fixes for ActionScheduler_Abstract_ListTable (props @ovidiul). #763 & #779
+* Dev - Adds new filter action_scheduler_claim_actions_order_by to allow tuning of the claim query (props @glagonikas). #773
+* Dev - PHPCS fixes for ActionScheduler_WpPostStore class (props @ovidiul). #780
+
+= 3.3.0 - 2021-09-15 =
+* Enhancement - Adds as_has_scheduled_action() to provide a performant way to test for existing actions. #645
+* Fix - Improves compatibility with environments where NO_ZERO_DATE is enabled. #519
+* Fix - Adds safety checks to guard against errors when our database tables cannot be created. #645
+* Dev - Now supports queries that use multiple statuses. #649
+* Dev - Minimum requirements for WordPress and PHP bumped (to 5.2 and 5.6 respectively). #723
+
+= 3.2.1 - 2021-06-21 =
+* Fix - Add extra safety/account for different versions of AS and different loading patterns. #714
+* Fix - Handle hidden columns (Tools → Scheduled Actions) | #600.
+
+= 3.2.0 - 2021-06-03 =
+* Fix - Add "no ordering" option to as_next_scheduled_action().
+* Fix - Add secondary scheduled date checks when claiming actions (DBStore) | #634.
+* Fix - Add secondary scheduled date checks when claiming actions (wpPostStore) | #634.
+* Fix - Adds a new index to the action table, reducing the potential for deadlocks (props: @glagonikas).
+* Fix - Fix unit tests infrastructure and adapt tests to PHP 8.
+* Fix - Identify in-use data store.
+* Fix - Improve test_migration_is_scheduled.
+* Fix - PHP notice on list table.
+* Fix - Speed up clean up and batch selects.
+* Fix - Update pending dependencies.
+* Fix - [PHP 8.0] Only pass action arg values through to do_action_ref_array().
+* Fix - [PHP 8] Set the PHP version to 7.1 in composer.json for PHP 8 compatibility.
+* Fix - add is_initialized() to docs.
+* Fix - fix file permissions.
+* Fix - fixes #664 by replacing __ with esc_html__.
diff --git a/wp/wp-content/plugins/imagify/inc/admin/custom-folders.php b/wp/wp-content/plugins/imagify/inc/admin/custom-folders.php
new file mode 100644
index 00000000..0111b109
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/admin/custom-folders.php
@@ -0,0 +1,85 @@
+can_operate() || ! $files_db->can_operate() ) {
+ return;
+ }
+
+ foreach ( $folders_to_sync as $folder_path ) {
+ $folder_path = trailingslashit( $folder_path );
+
+ if ( Imagify_Files_Scan::is_path_forbidden( $folder_path ) ) {
+ // This theme or plugin must not be optimized.
+ continue;
+ }
+
+ // Get the related folder.
+ $placeholder = Imagify_Files_Scan::add_placeholder( $folder_path );
+ $folder = Imagify_Folders_DB::get_instance()->get_in( 'path', $placeholder );
+
+ if ( ! $folder ) {
+ // This theme or plugin is not in the database.
+ continue;
+ }
+
+ // Sync the folder files.
+ Imagify_Custom_Folders::synchronize_files_from_folders( array(
+ $folder['folder_id'] => array(
+ 'folder_id' => $folder['folder_id'],
+ 'path' => $placeholder,
+ 'active' => $folder['active'],
+ 'folder_path' => $folder_path,
+ ),
+ ) );
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/inc/admin/media.php b/wp/wp-content/plugins/imagify/inc/admin/media.php
new file mode 100644
index 00000000..31f52d05
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/admin/media.php
@@ -0,0 +1,98 @@
+current_user_can( 'manual-optimize', $post->ID ) ) {
+ return $form_fields;
+ }
+
+ $process = imagify_get_optimization_process( $post->ID, 'wp' );
+
+ $form_fields['imagify'] = array(
+ 'label' => 'Imagify',
+ 'input' => 'html',
+ 'html' => get_imagify_media_column_content( $process ),
+ 'show_in_edit' => true,
+ 'show_in_modal' => true,
+ );
+
+ return $form_fields;
+}
+
+add_filter( 'media_row_actions', '_imagify_add_actions_to_media_list_row', IMAGIFY_INT_MAX, 2 );
+/**
+ * Add "Compare Original VS Optimized" link to the media row action
+ *
+ * @since 1.4.3
+ * @author Geoffrey Crofte
+ * @param array $actions An array of action links for each attachment.
+ * Default 'Edit', 'Delete Permanently', 'View'.
+ * @param object $post WP_Post object for the current attachment.
+ * @return array
+ */
+function _imagify_add_actions_to_media_list_row( $actions, $post ) {
+ if ( ! imagify_get_context( 'wp' )->current_user_can( 'manual-optimize', $post->ID ) ) {
+ return $actions;
+ }
+
+ $process = imagify_get_optimization_process( $post->ID, 'wp' );
+
+ if ( ! $process->is_valid() ) {
+ return $actions;
+ }
+
+ $media = $process->get_media();
+
+ // If this media is not an image, do nothing.
+ if ( ! $media->is_supported() || ! $media->is_image() ) {
+ return $actions;
+ }
+
+ $data = $process->get_data();
+
+ // If Imagify license not valid, or image is not optimized, do nothing.
+ if ( ! Imagify_Requirements::is_api_key_valid() || ! $data->is_optimized() ) {
+ return $actions;
+ }
+
+ // If no backup, do nothing.
+ if ( ! $media->has_backup() ) {
+ return $actions;
+ }
+
+ $dimensions = $media->get_dimensions();
+
+ // If full image is too small. See get_imagify_localize_script_translations().
+ if ( $dimensions['width'] < 360 ) {
+ return $actions;
+ }
+
+ // Else, add action link for comparison (JS triggered).
+ $actions['imagify-compare'] = Imagify_Views::get_instance()->get_template( 'button/compare-images', [
+ 'url' => get_edit_post_link( $media->get_id() ) . '#imagify-compare',
+ 'backup_url' => $media->get_backup_url(),
+ 'original_url' => $media->get_fullsize_url(),
+ 'media_id' => $media->get_id(),
+ 'width' => $dimensions['width'],
+ 'height' => $dimensions['height'],
+ ] );
+
+ return $actions;
+}
diff --git a/wp/wp-content/plugins/imagify/inc/admin/meta-boxes.php b/wp/wp-content/plugins/imagify/inc/admin/meta-boxes.php
new file mode 100644
index 00000000..daf801d3
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/admin/meta-boxes.php
@@ -0,0 +1,90 @@
+current_user_can( 'manual-optimize', $post->ID ) ) {
+ return;
+ }
+
+ $process = imagify_get_optimization_process( $post->ID, 'wp' );
+
+ if ( ! $process->is_valid() ) {
+ return;
+ }
+
+ $media = $process->get_media();
+
+ if ( ! $media->is_supported() ) {
+ return;
+ }
+
+ if ( ! $media->has_required_media_data() ) {
+ return;
+ }
+
+ $data = $process->get_data();
+ $views = Imagify_Views::get_instance();
+
+ if ( ! Imagify_Requirements::is_api_key_valid() && ! $data->is_optimized() ) {
+ ?>
+
+
+ is_locked();
+
+ if ( $is_locked ) {
+ switch ( $is_locked ) {
+ case 'optimizing':
+ $lock_label = __( 'Optimizing...', 'imagify' );
+ break;
+ case 'restoring':
+ $lock_label = __( 'Restoring...', 'imagify' );
+ break;
+ default:
+ $lock_label = __( 'Processing...', 'imagify' );
+ }
+ ?>
+
+ print_template( 'button/processing', [ 'label' => $lock_label ] ); ?>
+
+ is_optimized() || $data->is_already_optimized() || $data->is_error() ) {
+ ?>
+
+
+
+
+ $post->ID ) );
+ ?>
+
+ has_backup() && $data->is_optimized() ) {
+ ?>
+
+
+
+ get( 'version' );
+ // Version stored at the site level.
+ $site_version = Imagify_Data::get_instance()->get( 'version' );
+
+ if ( ! $network_version ) {
+ // First install (network).
+
+ /**
+ * Triggered on Imagify first install (network).
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ */
+ do_action( 'imagify_first_network_install' );
+ } elseif ( IMAGIFY_VERSION !== $network_version ) {
+ // Already installed but got updated (network).
+
+ /**
+ * Triggered on Imagify upgrade (network).
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ *
+ * @param string $network_version Previous version stored on the network.
+ * @param string $site_version Previous version stored on site level.
+ */
+ do_action( 'imagify_network_upgrade', $network_version, $site_version );
+ }
+
+ // If any upgrade has been done, we flush and update version.
+ if ( did_action( 'imagify_first_network_install' ) || did_action( 'imagify_network_upgrade' ) ) {
+ Imagify_Options::get_instance()->set( 'version', IMAGIFY_VERSION );
+ }
+
+ if ( ! $site_version ) {
+ // First install (site level).
+
+ /**
+ * Triggered on Imagify first install (site level).
+ *
+ * @since 1.0
+ */
+ do_action( 'imagify_first_install' );
+ } elseif ( IMAGIFY_VERSION !== $site_version ) {
+ // Already installed but got updated (site level).
+
+ /**
+ * Triggered on Imagify upgrade (site level).
+ *
+ * @since 1.0
+ * @since 1.7 $network_version replaces the "new version" (which can easily be grabbed with the constant).
+ *
+ * @param string $network_version Previous version stored on the network.
+ * @param string $site_version Previous version stored on site level.
+ */
+ do_action( 'imagify_upgrade', $network_version, $site_version );
+ }
+
+ // If any upgrade has been done, we flush and update version.
+ if ( did_action( 'imagify_first_install' ) || did_action( 'imagify_upgrade' ) ) {
+ Imagify_Data::get_instance()->set( 'version', IMAGIFY_VERSION );
+ }
+}
+add_action( 'admin_init', '_imagify_upgrader' );
+
+/**
+ * Upgrade the upgrader:
+ * Imagify 1.7 splits "network version" and "site version". Since the "site version" didn't exist before 1.7, we need to provide a version based on the "network version".
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ */
+function imagify_upgrader_upgrade() {
+ global $wpdb;
+
+ // Version stored on the network.
+ $network_version = Imagify_Options::get_instance()->get( 'version' );
+
+ if ( ! $network_version ) {
+ // Really first install.
+ return;
+ }
+
+ // Version stored at the site level.
+ $site_version = Imagify_Data::get_instance()->get( 'version' );
+
+ if ( $site_version ) {
+ // This site's upgrader is already upgraded.
+ return;
+ }
+
+ if ( ! is_multisite() ) {
+ // Not a multisite, so both versions must have the same value.
+ Imagify_Data::get_instance()->set( 'version', $network_version );
+ return;
+ }
+
+ $sites = get_site_option( 'imagify_old_version' );
+
+ if ( IMAGIFY_VERSION !== $network_version && ! $sites ) {
+ // The network is not up-to-date yet: store the site IDs that must be updated.
+ $network_id = function_exists( 'get_current_network_id' ) ? get_current_network_id() : $wpdb->siteid;
+ $sites = $wpdb->get_col( $wpdb->prepare( "SELECT blog_id FROM $wpdb->blogs WHERE site_id = %d AND archived = 0 AND deleted = 0", $network_id ) );
+ $sites = array_map( 'absint', $sites );
+ $sites = array_filter( $sites );
+
+ if ( ! $sites ) {
+ // Uh?
+ return;
+ }
+
+ // We store the old network version and the site Ids: those sites will need to be upgraded from this version.
+ $sites['version'] = $network_version;
+
+ add_site_option( 'imagify_old_version', $sites );
+ }
+
+ if ( empty( $sites['version'] ) ) {
+ // WTF.
+ delete_site_option( 'imagify_old_version' );
+ return;
+ }
+
+ $network_version = $sites['version'];
+ unset( $sites['version'] );
+
+ $sites = array_flip( $sites );
+ $site_id = get_current_blog_id();
+
+ if ( ! isset( $sites[ $site_id ] ) ) {
+ // This site is already upgraded.
+ return;
+ }
+
+ unset( $sites[ $site_id ] );
+
+ if ( ! $sites ) {
+ // We're done, all the sites have been upgraded.
+ delete_site_option( 'imagify_old_version' );
+ } else {
+ // Some sites still need to be upgraded.
+ $sites = array_flip( $sites );
+ $sites['version'] = $network_version;
+ update_site_option( 'imagify_old_version', $sites );
+ }
+
+ Imagify_Data::get_instance()->set( 'version', $network_version );
+}
+
+/**
+ * Keeps this function up to date at each version.
+ *
+ * @since 1.0
+ */
+function _imagify_first_install() {
+ // Set a transient to know when we will have to display a notice to ask the user to rate the plugin.
+ set_site_transient( 'imagify_seen_rating_notice', true, DAY_IN_SECONDS * 3 );
+}
+add_action( 'imagify_first_network_install', '_imagify_first_install' );
+
+/**
+ * What to do when Imagify is updated, depending on versions.
+ *
+ * @since 1.0
+ * @since 1.7 $network_version replaces the "new version" (which can easily be grabbed with the constant).
+ *
+ * @param string $network_version Previous version stored on the network.
+ * @param string $site_version Previous version stored on site level.
+ */
+function _imagify_new_upgrade( $network_version, $site_version ) {
+ global $wpdb;
+
+ $options = Imagify_Options::get_instance();
+
+ // 1.2
+ if ( version_compare( $site_version, '1.2' ) < 0 ) {
+ // Update all already optimized images status from 'error' to 'already_optimized'.
+ $query = new WP_Query( array(
+ 'is_imagify' => true,
+ 'post_type' => 'attachment',
+ 'post_status' => imagify_get_post_statuses(),
+ 'post_mime_type' => imagify_get_mime_types(),
+ 'meta_key' => '_imagify_status',
+ 'meta_value' => 'error',
+ 'posts_per_page' => -1,
+ 'update_post_term_cache' => false,
+ 'no_found_rows' => true,
+ 'fields' => 'ids',
+ ) );
+
+ if ( $query->posts ) {
+ foreach ( (array) $query->posts as $id ) {
+ $data = get_post_meta( $id, '_imagify_data', true );
+ $error = ! empty( $data['sizes']['full']['error'] ) ? $data['sizes']['full']['error'] : '';
+
+ if ( false !== strpos( $error, 'This image is already compressed' ) ) {
+ update_post_meta( $id, '_imagify_status', 'already_optimized' );
+ }
+ }
+ }
+
+ // Auto-activate the Admin Bar option.
+ $options->set( 'admin_bar_menu', 1 );
+ }
+
+ // 1.3.2
+ if ( version_compare( $site_version, '1.3.2' ) < 0 ) {
+ // Update all already optimized images status from 'error' to 'already_optimized'.
+ $query = new WP_Query( array(
+ 'is_imagify' => true,
+ 'post_type' => 'attachment',
+ 'post_status' => imagify_get_post_statuses(),
+ 'post_mime_type' => imagify_get_mime_types(),
+ 'meta_query' => array(
+ 'relation' => 'AND',
+ array(
+ 'key' => '_imagify_data',
+ 'compare' => 'EXISTS',
+ ),
+ array(
+ 'key' => '_imagify_optimization_level',
+ 'compare' => 'NOT EXISTS',
+ ),
+ ),
+ 'posts_per_page' => -1,
+ 'update_post_term_cache' => false,
+ 'no_found_rows' => true,
+ 'fields' => 'ids',
+ ) );
+
+ if ( $query->posts ) {
+ foreach ( (array) $query->posts as $id ) {
+ $data = get_post_meta( $id, '_imagify_data', true );
+ $stats = isset( $data['stats'] ) ? $data['stats'] : [];
+
+ if ( isset( $stats['aggressive'] ) ) {
+ update_post_meta( $id, '_imagify_optimization_level', (int) $stats['aggressive'] );
+ }
+ }
+ }
+ }
+
+ // 1.4.5
+ if ( version_compare( $site_version, '1.4.5' ) < 0 ) {
+ // Delete all transients used for async optimization.
+ $wpdb->query( $wpdb->prepare( "DELETE from $wpdb->options WHERE option_name LIKE %s", Imagify_DB::esc_like( '_transient_imagify-async-in-progress-' ) . '%' ) );
+ }
+
+ // 1.7
+ if ( version_compare( $site_version, '1.7' ) < 0 ) {
+ // Migrate data.
+ Imagify_Cron_Library_Size::get_instance()->do_event();
+
+ if ( ! imagify_is_active_for_network() ) {
+ // Make sure the settings are autoloaded.
+ $wpdb->query( $wpdb->prepare( "UPDATE {$wpdb->options} SET `autoload` = 'yes' WHERE `autoload` != 'yes' AND option_name = %s", $options->get_option_name() ) );
+ }
+
+ // Rename the option that stores the NGG table version. Since the table is also updated in 1.7, let's simply delete the option.
+ delete_option( $wpdb->prefix . 'ngg_imagify_data_db_version' );
+ }
+
+ // 1.8.1
+ if ( version_compare( $site_version, '1.8.1' ) < 0 ) {
+ // Custom folders: replace `{{ABSPATH}}/` by `{{ROOT}}/`.
+ $filesystem = imagify_get_filesystem();
+ $replacement = '{{ROOT}}/';
+
+ if ( $filesystem->has_wp_its_own_directory() ) {
+ $replacement .= preg_replace( '@^' . preg_quote( $filesystem->get_site_root(), '@' ) . '@', '', $filesystem->get_abspath() );
+ }
+
+ $replacement = Imagify_DB::esc_like( $replacement );
+
+ $wpdb->query( $wpdb->prepare( "UPDATE {$wpdb->base_prefix}imagify_files SET path = REPLACE( path, '{{ABSPATH}}/', %s ) WHERE path LIKE %s", $replacement, '{{ABSPATH}}/%' ) );
+ $wpdb->query( $wpdb->prepare( "UPDATE {$wpdb->base_prefix}imagify_folders SET path = REPLACE( path, '{{ABSPATH}}/', %s ) WHERE path LIKE %s", $replacement, '{{ABSPATH}}/%' ) );
+ }
+
+ // 1.8.2
+ if ( version_compare( $site_version, '1.8.2' ) < 0 ) {
+ $options->set( 'partner_links', 1 );
+ }
+
+ // 1.9.6
+ if ( version_compare( $site_version, '1.9.6' ) < 0 ) {
+ \Imagify\Stats\OptimizedMediaWithoutNextGen::get_instance()->clear_cache();
+ }
+
+ // 1.9.11
+ if ( version_compare( $site_version, '1.9.11' ) < 0 ) {
+ imagify_secure_custom_directories();
+ }
+
+ if ( version_compare( $site_version, '2.0' ) < 0 ) {
+ $options->set( 'optimization_level', 2 );
+ }
+
+ if ( version_compare( $site_version, '2.2' ) < 0 ) {
+ $options->set( 'display_nextgen', $options->get( 'display_webp', 0 ) );
+ $options->set( 'display_nextgen_method', $options->get( 'display_webp_method' ) );
+ }
+
+ if ( version_compare( $site_version, '2.2.2', '<' ) ) {
+ if ( $options->get( 'convert_to_avif' ) ) {
+ $options->set( 'optimization_format', 'avif' );
+ } else {
+ $options->set( 'optimization_format', 'webp' );
+ }
+ }
+}
+add_action( 'imagify_upgrade', '_imagify_new_upgrade', 10, 2 );
+
+/**
+ * Scan imagify directories and add `index.php` files where missing.
+ *
+ * @since 1.9.11
+ *
+ * @return void
+ */
+function imagify_secure_custom_directories() {
+ $filesystem = imagify_get_filesystem();
+
+ Imagify_Custom_Folders::add_indexes();
+
+ $conf_dir = $filesystem->get_site_root() . 'conf';
+ Imagify_Custom_Folders::add_indexes( $conf_dir );
+
+ $backup_dir = get_imagify_backup_dir_path();
+ Imagify_Custom_Folders::add_indexes( $backup_dir );
+}
+add_action( 'imagify_activation', 'imagify_secure_custom_directories' );
diff --git a/wp/wp-content/plugins/imagify/inc/admin/upload.php b/wp/wp-content/plugins/imagify/inc/admin/upload.php
new file mode 100644
index 00000000..b24249a5
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/admin/upload.php
@@ -0,0 +1,131 @@
+current_user_can( 'optimize' ) ) {
+ $columns['imagify_optimized_file'] = __( 'Imagify', 'imagify' );
+ }
+
+ return $columns;
+}
+
+add_action( 'manage_media_custom_column', '_imagify_manage_media_custom_column', 10, 2 );
+/**
+ * Add content to the "Imagify" columns in upload.php.
+ *
+ * @since 1.0
+ * @author Jonathan Buttigieg
+ *
+ * @param string $column_name Name of the custom column.
+ * @param int $attachment_id Attachment ID.
+ */
+function _imagify_manage_media_custom_column( $column_name, $attachment_id ) {
+ if ( 'imagify_optimized_file' !== $column_name ) {
+ return;
+ }
+
+ $process = imagify_get_optimization_process( $attachment_id, 'wp' );
+
+ echo get_imagify_media_column_content( $process );
+}
+
+add_action( 'restrict_manage_posts', '_imagify_attachments_filter_dropdown' );
+/**
+ * Adds a dropdown that allows filtering on the attachments Imagify status.
+ *
+ * @since 1.0
+ * @author Jonathan Buttigieg
+ */
+function _imagify_attachments_filter_dropdown() {
+ if ( ! Imagify_Views::get_instance()->is_wp_library_page() ) {
+ return;
+ }
+
+ $optimized = imagify_count_optimized_attachments();
+ $unoptimized = imagify_count_unoptimized_attachments();
+ $errors = imagify_count_error_attachments();
+ $status = isset( $_GET['imagify-status'] ) ? wp_unslash( $_GET['imagify-status'] ) : 0; // WPCS: CSRF ok.
+ $options = array(
+ 'optimized' => _x( 'Optimized', 'Media Files', 'imagify' ),
+ 'unoptimized' => _x( 'Unoptimized', 'Media Files', 'imagify' ),
+ 'errors' => _x( 'Errors', 'Media Files', 'imagify' ),
+ );
+
+ echo '' . __( 'Filter by status', 'imagify' ) . ' ';
+ echo '';
+ echo '' . __( 'All Media Files', 'imagify' ) . ' ';
+
+ foreach ( $options as $value => $label ) {
+ echo '' . $label . ' (' . ${$value} . ') ';
+ }
+ echo ' ';
+}
+
+add_filter( 'request', '_imagify_sort_attachments_by_status' );
+/**
+ * Modify the query based on the imagify-status variable in $_GET.
+ *
+ * @since 1.0
+ * @author Jonathan Buttigieg
+ *
+ * @param array $vars The array of requested query variables.
+ * @return array
+ */
+function _imagify_sort_attachments_by_status( $vars ) {
+ if ( empty( $_GET['imagify-status'] ) || ! Imagify_Views::get_instance()->is_wp_library_page() ) { // WPCS: CSRF ok.
+ return $vars;
+ }
+
+ $status = wp_unslash( $_GET['imagify-status'] ); // WPCS: CSRF ok.
+ $meta_key = '_imagify_status';
+ $meta_compare = '=';
+ $relation = array();
+
+ switch ( $status ) {
+ case 'unoptimized':
+ $meta_key = '_imagify_data';
+ $meta_compare = 'NOT EXISTS';
+ break;
+ case 'optimized':
+ $status = 'success';
+ $relation = array(
+ 'key' => $meta_key,
+ 'value' => 'already_optimized',
+ 'compare' => $meta_compare,
+ );
+ break;
+ case 'errors':
+ $status = 'error';
+ break;
+ default:
+ return $vars;
+ }
+
+ $vars = array_merge( $vars, array(
+ 'meta_query' => array(
+ 'relation' => 'or',
+ array(
+ 'key' => $meta_key,
+ 'value' => $status,
+ 'compare' => $meta_compare,
+ ),
+ $relation,
+ ),
+ ) );
+
+ if ( ! key_exists( 'post_mime_type', $vars ) ) {
+ $vars['post_mime_type'] = imagify_get_mime_types();
+ }
+
+ return $vars;
+}
diff --git a/wp/wp-content/plugins/imagify/inc/classes/Dependencies/.gitkeep b/wp/wp-content/plugins/imagify/inc/classes/Dependencies/.gitkeep
new file mode 100644
index 00000000..e69de29b
diff --git a/wp/wp-content/plugins/imagify/inc/classes/Dependencies/deliciousbrains/wp-background-processing/classes/wp-async-request.php b/wp/wp-content/plugins/imagify/inc/classes/Dependencies/deliciousbrains/wp-background-processing/classes/wp-async-request.php
new file mode 100644
index 00000000..083c4209
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/classes/Dependencies/deliciousbrains/wp-background-processing/classes/wp-async-request.php
@@ -0,0 +1,208 @@
+identifier = $this->prefix . '_' . $this->action;
+
+ add_action( 'wp_ajax_' . $this->identifier, array( $this, 'maybe_handle' ) );
+ add_action( 'wp_ajax_nopriv_' . $this->identifier, array( $this, 'maybe_handle' ) );
+ }
+
+ /**
+ * Set data used during the request.
+ *
+ * @param array $data Data.
+ *
+ * @return $this
+ */
+ public function data( $data ) {
+ $this->data = $data;
+
+ return $this;
+ }
+
+ /**
+ * Dispatch the async request.
+ *
+ * @return array|WP_Error|false HTTP Response array, WP_Error on failure, or false if not attempted.
+ */
+ public function dispatch() {
+ $url = add_query_arg( $this->get_query_args(), $this->get_query_url() );
+ $args = $this->get_post_args();
+
+ return wp_remote_post( esc_url_raw( $url ), $args );
+ }
+
+ /**
+ * Get query args.
+ *
+ * @return array
+ */
+ protected function get_query_args() {
+ if ( property_exists( $this, 'query_args' ) ) {
+ return $this->query_args;
+ }
+
+ $args = array(
+ 'action' => $this->identifier,
+ 'nonce' => wp_create_nonce( $this->identifier ),
+ );
+
+ /**
+ * Filters the post arguments used during an async request.
+ *
+ * @param array $url
+ */
+ return apply_filters( $this->identifier . '_query_args', $args );
+ }
+
+ /**
+ * Get query URL.
+ *
+ * @return string
+ */
+ protected function get_query_url() {
+ if ( property_exists( $this, 'query_url' ) ) {
+ return $this->query_url;
+ }
+
+ $url = admin_url( 'admin-ajax.php' );
+
+ /**
+ * Filters the post arguments used during an async request.
+ *
+ * @param string $url
+ */
+ return apply_filters( $this->identifier . '_query_url', $url );
+ }
+
+ /**
+ * Get post args.
+ *
+ * @return array
+ */
+ protected function get_post_args() {
+ if ( property_exists( $this, 'post_args' ) ) {
+ return $this->post_args;
+ }
+
+ $args = array(
+ 'timeout' => 5,
+ 'blocking' => false,
+ 'body' => $this->data,
+ 'cookies' => $_COOKIE, // Passing cookies ensures request is performed as initiating user.
+ 'sslverify' => apply_filters( 'https_local_ssl_verify', false ), // Local requests, fine to pass false.
+ );
+
+ /**
+ * Filters the post arguments used during an async request.
+ *
+ * @param array $args
+ */
+ return apply_filters( $this->identifier . '_post_args', $args );
+ }
+
+ /**
+ * Maybe handle a dispatched request.
+ *
+ * Check for correct nonce and pass to handler.
+ *
+ * @return void|mixed
+ */
+ public function maybe_handle() {
+ // Don't lock up other requests while processing.
+ session_write_close();
+
+ check_ajax_referer( $this->identifier, 'nonce' );
+
+ $this->handle();
+
+ return $this->maybe_wp_die();
+ }
+
+ /**
+ * Should the process exit with wp_die?
+ *
+ * @param mixed $return What to return if filter says don't die, default is null.
+ *
+ * @return void|mixed
+ * @noinspection ForgottenDebugOutputInspection
+ */
+ protected function maybe_wp_die( $return = null ) {
+ /**
+ * Should wp_die be used?
+ *
+ * @return bool
+ */
+ if ( apply_filters( $this->identifier . '_wp_die', true ) ) {
+ wp_die();
+ }
+
+ return $return;
+ }
+
+ /**
+ * Handle a dispatched request.
+ *
+ * Override this method to perform any actions required
+ * during the async request.
+ */
+ abstract protected function handle();
+}
diff --git a/wp/wp-content/plugins/imagify/inc/classes/Dependencies/deliciousbrains/wp-background-processing/classes/wp-background-process.php b/wp/wp-content/plugins/imagify/inc/classes/Dependencies/deliciousbrains/wp-background-processing/classes/wp-background-process.php
new file mode 100644
index 00000000..56bbe847
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/classes/Dependencies/deliciousbrains/wp-background-processing/classes/wp-background-process.php
@@ -0,0 +1,739 @@
+cron_hook_identifier = $this->identifier . '_cron';
+ $this->cron_interval_identifier = $this->identifier . '_cron_interval';
+
+ add_action( $this->cron_hook_identifier, array( $this, 'handle_cron_healthcheck' ) );
+ // phpcs:ignore WordPress.WP.CronInterval.ChangeDetected
+ add_filter( 'cron_schedules', array( $this, 'schedule_cron_healthcheck' ) );
+ }
+
+ /**
+ * Schedule the cron healthcheck and dispatch an async request to start processing the queue.
+ *
+ * @access public
+ * @return array|WP_Error|false HTTP Response array, WP_Error on failure, or false if not attempted.
+ */
+ public function dispatch() {
+ if ( $this->is_processing() ) {
+ // Process already running.
+ return false;
+ }
+
+ // Schedule the cron healthcheck.
+ $this->schedule_event();
+
+ // Perform remote post.
+ return parent::dispatch();
+ }
+
+ /**
+ * Push to the queue.
+ *
+ * Note, save must be called in order to persist queued items to a batch for processing.
+ *
+ * @param mixed $data Data.
+ *
+ * @return $this
+ */
+ public function push_to_queue( $data ) {
+ $this->data[] = $data;
+
+ return $this;
+ }
+
+ /**
+ * Save the queued items for future processing.
+ *
+ * @return $this
+ */
+ public function save() {
+ $key = $this->generate_key();
+
+ if ( ! empty( $this->data ) ) {
+ update_site_option( $key, $this->data );
+ }
+
+ // Clean out data so that new data isn't prepended with closed session's data.
+ $this->data = array();
+
+ return $this;
+ }
+
+ /**
+ * Update a batch's queued items.
+ *
+ * @param string $key Key.
+ * @param array $data Data.
+ *
+ * @return $this
+ */
+ public function update( $key, $data ) {
+ if ( ! empty( $data ) ) {
+ update_site_option( $key, $data );
+ }
+
+ return $this;
+ }
+
+ /**
+ * Delete a batch of queued items.
+ *
+ * @param string $key Key.
+ *
+ * @return $this
+ */
+ public function delete( $key ) {
+ delete_site_option( $key );
+
+ return $this;
+ }
+
+ /**
+ * Delete entire job queue.
+ */
+ public function delete_all() {
+ $batches = $this->get_batches();
+
+ foreach ( $batches as $batch ) {
+ $this->delete( $batch->key );
+ }
+
+ delete_site_option( $this->get_status_key() );
+
+ $this->cancelled();
+ }
+
+ /**
+ * Cancel job on next batch.
+ */
+ public function cancel() {
+ update_site_option( $this->get_status_key(), self::STATUS_CANCELLED );
+
+ // Just in case the job was paused at the time.
+ $this->dispatch();
+ }
+
+ /**
+ * Has the process been cancelled?
+ *
+ * @return bool
+ */
+ public function is_cancelled() {
+ $status = get_site_option( $this->get_status_key(), 0 );
+
+ return absint( $status ) === self::STATUS_CANCELLED;
+ }
+
+ /**
+ * Called when background process has been cancelled.
+ */
+ protected function cancelled() {
+ do_action( $this->identifier . '_cancelled' );
+ }
+
+ /**
+ * Pause job on next batch.
+ */
+ public function pause() {
+ update_site_option( $this->get_status_key(), self::STATUS_PAUSED );
+ }
+
+ /**
+ * Is the job paused?
+ *
+ * @return bool
+ */
+ public function is_paused() {
+ $status = get_site_option( $this->get_status_key(), 0 );
+
+ return absint( $status ) === self::STATUS_PAUSED;
+ }
+
+ /**
+ * Called when background process has been paused.
+ */
+ protected function paused() {
+ do_action( $this->identifier . '_paused' );
+ }
+
+ /**
+ * Resume job.
+ */
+ public function resume() {
+ delete_site_option( $this->get_status_key() );
+
+ $this->schedule_event();
+ $this->dispatch();
+ $this->resumed();
+ }
+
+ /**
+ * Called when background process has been resumed.
+ */
+ protected function resumed() {
+ do_action( $this->identifier . '_resumed' );
+ }
+
+ /**
+ * Is queued?
+ *
+ * @return bool
+ */
+ public function is_queued() {
+ return ! $this->is_queue_empty();
+ }
+
+ /**
+ * Is the tool currently active, e.g. starting, working, paused or cleaning up?
+ *
+ * @return bool
+ */
+ public function is_active() {
+ return $this->is_queued() || $this->is_processing() || $this->is_paused() || $this->is_cancelled();
+ }
+
+ /**
+ * Generate key for a batch.
+ *
+ * Generates a unique key based on microtime. Queue items are
+ * given a unique key so that they can be merged upon save.
+ *
+ * @param int $length Optional max length to trim key to, defaults to 64 characters.
+ * @param string $key Optional string to append to identifier before hash, defaults to "batch".
+ *
+ * @return string
+ */
+ protected function generate_key( $length = 64, $key = 'batch' ) {
+ $unique = md5( microtime() . wp_rand() );
+ $prepend = $this->identifier . '_' . $key . '_';
+
+ return substr( $prepend . $unique, 0, $length );
+ }
+
+ /**
+ * Get the status key.
+ *
+ * @return string
+ */
+ protected function get_status_key() {
+ return $this->identifier . '_status';
+ }
+
+ /**
+ * Maybe process a batch of queued items.
+ *
+ * Checks whether data exists within the queue and that
+ * the process is not already running.
+ */
+ public function maybe_handle() {
+ // Don't lock up other requests while processing.
+ session_write_close();
+
+ if ( $this->is_processing() ) {
+ // Background process already running.
+ return $this->maybe_wp_die();
+ }
+
+ if ( $this->is_cancelled() ) {
+ $this->clear_scheduled_event();
+ $this->delete_all();
+
+ return $this->maybe_wp_die();
+ }
+
+ if ( $this->is_paused() ) {
+ $this->clear_scheduled_event();
+ $this->paused();
+
+ return $this->maybe_wp_die();
+ }
+
+ if ( $this->is_queue_empty() ) {
+ // No data to process.
+ return $this->maybe_wp_die();
+ }
+
+ check_ajax_referer( $this->identifier, 'nonce' );
+
+ $this->handle();
+
+ return $this->maybe_wp_die();
+ }
+
+ /**
+ * Is queue empty?
+ *
+ * @return bool
+ * @noinspection IsEmptyFunctionUsageInspection
+ */
+ protected function is_queue_empty() {
+ return empty( $this->get_batch() );
+ }
+
+ /**
+ * Is process running?
+ *
+ * Check whether the current process is already running
+ * in a background process.
+ *
+ * @return bool
+ *
+ * @deprecated 1.1.0 Superseded.
+ * @see is_processing()
+ * @noinspection PhpUnused
+ */
+ protected function is_process_running() {
+ return $this->is_processing();
+ }
+
+ /**
+ * Is the background process currently running?
+ *
+ * @return bool
+ */
+ public function is_processing() {
+ if ( get_site_transient( $this->identifier . '_process_lock' ) ) {
+ // Process already running.
+ return true;
+ }
+
+ return false;
+ }
+
+ /**
+ * Lock process.
+ *
+ * Lock the process so that multiple instances can't run simultaneously.
+ * Override if applicable, but the duration should be greater than that
+ * defined in the time_exceeded() method.
+ */
+ protected function lock_process() {
+ $this->start_time = time(); // Set start time of current process.
+
+ $lock_duration = ( property_exists( $this, 'queue_lock_time' ) ) ? $this->queue_lock_time : 60; // 1 minute
+ $lock_duration = apply_filters( $this->identifier . '_queue_lock_time', $lock_duration );
+
+ set_site_transient( $this->identifier . '_process_lock', microtime(), $lock_duration );
+ }
+
+ /**
+ * Unlock process.
+ *
+ * Unlock the process so that other instances can spawn.
+ *
+ * @return $this
+ */
+ protected function unlock_process() {
+ delete_site_transient( $this->identifier . '_process_lock' );
+
+ return $this;
+ }
+
+ /**
+ * Get batch.
+ *
+ * @return stdClass Return the first batch of queued items.
+ */
+ protected function get_batch() {
+ return array_reduce(
+ $this->get_batches( 1 ),
+ static function ( $carry, $batch ) {
+ return $batch;
+ },
+ array()
+ );
+ }
+
+ /**
+ * Get batches.
+ *
+ * @param int $limit Number of batches to return, defaults to all.
+ *
+ * @return array of stdClass
+ */
+ public function get_batches( $limit = 0 ) {
+ global $wpdb;
+
+ if ( empty( $limit ) || ! is_int( $limit ) ) {
+ $limit = 0;
+ }
+
+ $table = $wpdb->options;
+ $column = 'option_name';
+ $key_column = 'option_id';
+ $value_column = 'option_value';
+
+ if ( is_multisite() ) {
+ $table = $wpdb->sitemeta;
+ $column = 'meta_key';
+ $key_column = 'meta_id';
+ $value_column = 'meta_value';
+ }
+
+ $key = $wpdb->esc_like( $this->identifier . '_batch_' ) . '%';
+
+ $sql = '
+ SELECT *
+ FROM ' . $table . '
+ WHERE ' . $column . ' LIKE %s
+ ORDER BY ' . $key_column . '
+ ';
+
+ $args = array( $key );
+
+ if ( ! empty( $limit ) ) {
+ $sql .= ' LIMIT %d';
+
+ $args[] = $limit;
+ }
+
+ $items = $wpdb->get_results( $wpdb->prepare( $sql, $args ) ); // phpcs:ignore WordPress.DB.PreparedSQL.NotPrepared
+
+ $batches = array();
+
+ if ( ! empty( $items ) ) {
+ $batches = array_map(
+ static function ( $item ) use ( $column, $value_column ) {
+ $batch = new stdClass();
+ $batch->key = $item->{$column};
+ $batch->data = maybe_unserialize( $item->{$value_column} );
+
+ return $batch;
+ },
+ $items
+ );
+ }
+
+ return $batches;
+ }
+
+ /**
+ * Handle a dispatched request.
+ *
+ * Pass each queue item to the task handler, while remaining
+ * within server memory and time limit constraints.
+ *
+ * @noinspection DisconnectedForeachInstructionInspection
+ */
+ protected function handle() {
+ $this->lock_process();
+
+ /**
+ * Number of seconds to sleep between batches. Defaults to 0 seconds, minimum 0.
+ *
+ * @param int $seconds
+ */
+ $throttle_seconds = max(
+ 0,
+ apply_filters(
+ $this->identifier . '_seconds_between_batches',
+ apply_filters(
+ $this->prefix . '_seconds_between_batches',
+ 0
+ )
+ )
+ );
+
+ do {
+ $batch = $this->get_batch();
+
+ foreach ( $batch->data as $key => $value ) {
+ $task = $this->task( $value );
+
+ if ( false !== $task ) {
+ $batch->data[ $key ] = $task;
+ } else {
+ unset( $batch->data[ $key ] );
+ }
+
+ // Keep the batch up to date while processing it.
+ if ( ! empty( $batch->data ) ) {
+ $this->update( $batch->key, $batch->data );
+ }
+
+ // Let the server breathe a little.
+ sleep( $throttle_seconds );
+
+ // Batch limits reached, or pause or cancel request.
+ if ( $this->time_exceeded() || $this->memory_exceeded() || $this->is_paused() || $this->is_cancelled() ) {
+ break;
+ }
+ }
+
+ // Delete current batch if fully processed.
+ if ( empty( $batch->data ) ) {
+ $this->delete( $batch->key );
+ }
+ } while ( ! $this->time_exceeded() && ! $this->memory_exceeded() && ! $this->is_queue_empty() && ! $this->is_paused() && ! $this->is_cancelled() );
+
+ $this->unlock_process();
+
+ // Start next batch or complete process.
+ if ( ! $this->is_queue_empty() ) {
+ $this->dispatch();
+ } else {
+ $this->complete();
+ }
+
+ return $this->maybe_wp_die();
+ }
+
+ /**
+ * Memory exceeded?
+ *
+ * Ensures the batch process never exceeds 90%
+ * of the maximum WordPress memory.
+ *
+ * @return bool
+ */
+ protected function memory_exceeded() {
+ $memory_limit = $this->get_memory_limit() * 0.9; // 90% of max memory
+ $current_memory = memory_get_usage( true );
+ $return = false;
+
+ if ( $current_memory >= $memory_limit ) {
+ $return = true;
+ }
+
+ return apply_filters( $this->identifier . '_memory_exceeded', $return );
+ }
+
+ /**
+ * Get memory limit in bytes.
+ *
+ * @return int
+ */
+ protected function get_memory_limit() {
+ if ( function_exists( 'ini_get' ) ) {
+ $memory_limit = ini_get( 'memory_limit' );
+ } else {
+ // Sensible default.
+ $memory_limit = '128M';
+ }
+
+ if ( ! $memory_limit || -1 === (int) $memory_limit ) {
+ // Unlimited, set to 32GB.
+ $memory_limit = '32000M';
+ }
+
+ return wp_convert_hr_to_bytes( $memory_limit );
+ }
+
+ /**
+ * Time limit exceeded?
+ *
+ * Ensures the batch never exceeds a sensible time limit.
+ * A timeout limit of 30s is common on shared hosting.
+ *
+ * @return bool
+ */
+ protected function time_exceeded() {
+ $finish = $this->start_time + apply_filters( $this->identifier . '_default_time_limit', 20 ); // 20 seconds
+ $return = false;
+
+ if (
+ ! ( defined( 'WP_CLI' ) && WP_CLI ) &&
+ time() >= $finish
+ ) {
+ $return = true;
+ }
+
+ return apply_filters( $this->identifier . '_time_exceeded', $return );
+ }
+
+ /**
+ * Complete processing.
+ *
+ * Override if applicable, but ensure that the below actions are
+ * performed, or, call parent::complete().
+ */
+ protected function complete() {
+ delete_site_option( $this->get_status_key() );
+
+ // Remove the cron healthcheck job from the cron schedule.
+ $this->clear_scheduled_event();
+
+ $this->completed();
+ }
+
+ /**
+ * Called when background process has completed.
+ */
+ protected function completed() {
+ do_action( $this->identifier . '_completed' );
+ }
+
+ /**
+ * Schedule the cron healthcheck job.
+ *
+ * @access public
+ *
+ * @param mixed $schedules Schedules.
+ *
+ * @return mixed
+ */
+ public function schedule_cron_healthcheck( $schedules ) {
+ $interval = apply_filters( $this->cron_interval_identifier, 5 );
+
+ if ( property_exists( $this, 'cron_interval' ) ) {
+ $interval = apply_filters( $this->cron_interval_identifier, $this->cron_interval );
+ }
+
+ if ( 1 === $interval ) {
+ $display = __( 'Every Minute' );
+ } else {
+ $display = sprintf( __( 'Every %d Minutes' ), $interval );
+ }
+
+ // Adds an "Every NNN Minute(s)" schedule to the existing cron schedules.
+ $schedules[ $this->cron_interval_identifier ] = array(
+ 'interval' => MINUTE_IN_SECONDS * $interval,
+ 'display' => $display,
+ );
+
+ return $schedules;
+ }
+
+ /**
+ * Handle cron healthcheck event.
+ *
+ * Restart the background process if not already running
+ * and data exists in the queue.
+ */
+ public function handle_cron_healthcheck() {
+ if ( $this->is_processing() ) {
+ // Background process already running.
+ exit;
+ }
+
+ if ( $this->is_queue_empty() ) {
+ // No data to process.
+ $this->clear_scheduled_event();
+ exit;
+ }
+
+ $this->dispatch();
+ }
+
+ /**
+ * Schedule the cron healthcheck event.
+ */
+ protected function schedule_event() {
+ if ( ! wp_next_scheduled( $this->cron_hook_identifier ) ) {
+ wp_schedule_event( time(), $this->cron_interval_identifier, $this->cron_hook_identifier );
+ }
+ }
+
+ /**
+ * Clear scheduled cron healthcheck event.
+ */
+ protected function clear_scheduled_event() {
+ $timestamp = wp_next_scheduled( $this->cron_hook_identifier );
+
+ if ( $timestamp ) {
+ wp_unschedule_event( $timestamp, $this->cron_hook_identifier );
+ }
+ }
+
+ /**
+ * Cancel the background process.
+ *
+ * Stop processing queue items, clear cron job and delete batch.
+ *
+ * @deprecated 1.1.0 Superseded.
+ * @see cancel()
+ * @noinspection PhpUnused
+ */
+ public function cancel_process() {
+ $this->cancel();
+ }
+
+ /**
+ * Perform task with queued item.
+ *
+ * Override this method to perform any actions required on each
+ * queue item. Return the modified item for further processing
+ * in the next pass through. Or, return false to remove the
+ * item from the queue.
+ *
+ * @param mixed $item Queue item to iterate over.
+ *
+ * @return mixed
+ */
+ abstract protected function task( $item );
+}
diff --git a/wp/wp-content/plugins/imagify/inc/classes/Dependencies/wp-media/event-manager/EventManager.php b/wp/wp-content/plugins/imagify/inc/classes/Dependencies/wp-media/event-manager/EventManager.php
new file mode 100644
index 00000000..5b593e5a
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/classes/Dependencies/wp-media/event-manager/EventManager.php
@@ -0,0 +1,135 @@
+
+ */
+class EventManager {
+ /**
+ * Adds a callback to a specific hook of the WordPress plugin API.
+ *
+ * @uses add_filter()
+ *
+ * @param string $hook_name Name of the hook.
+ * @param callable $callback Callback function.
+ * @param int $priority Priority.
+ * @param int $accepted_args Number of arguments.
+ */
+ public function add_callback( $hook_name, $callback, $priority = 10, $accepted_args = 1 ) {
+ add_filter( $hook_name, $callback, $priority, $accepted_args );
+ }
+
+ /**
+ * Add an event subscriber.
+ *
+ * The event manager registers all the hooks that the given subscriber
+ * wants to register with the WordPress Plugin API.
+ *
+ * @param SubscriberInterface $subscriber SubscriberInterface implementation.
+ */
+ public function add_subscriber( SubscriberInterface $subscriber ) {
+ if ( $subscriber instanceof EventManagerAwareSubscriberInterface ) {
+ $subscriber->set_event_manager( $this );
+ }
+
+ $events = $subscriber->get_subscribed_events();
+
+ if ( empty( $events ) ) {
+ return;
+ }
+
+ foreach ( $subscriber->get_subscribed_events() as $hook_name => $parameters ) {
+ $this->add_subscriber_callback( $subscriber, $hook_name, $parameters );
+ }
+ }
+
+ /**
+ * Checks the WordPress plugin API to see if the given hook has
+ * the given callback. The priority of the callback will be returned
+ * or false. If no callback is given will return true or false if
+ * there's any callbacks registered to the hook.
+ *
+ * @uses has_filter()
+ *
+ * @param string $hook_name Hook name.
+ * @param mixed $callback Callback.
+ *
+ * @return bool|int
+ */
+ public function has_callback( $hook_name, $callback = false ) {
+ return has_filter( $hook_name, $callback );
+ }
+
+ /**
+ * Removes the given callback from the given hook. The WordPress plugin API only
+ * removes the hook if the callback and priority match a registered hook.
+ *
+ * @uses remove_filter()
+ *
+ * @param string $hook_name Hook name.
+ * @param callable $callback Callback.
+ * @param int $priority Priority.
+ *
+ * @return bool
+ */
+ public function remove_callback( $hook_name, $callback, $priority = 10 ) {
+ return remove_filter( $hook_name, $callback, $priority );
+ }
+
+ /**
+ * Remove an event subscriber.
+ *
+ * The event manager removes all the hooks that the given subscriber
+ * wants to register with the WordPress Plugin API.
+ *
+ * @param SubscriberInterface $subscriber SubscriberInterface implementation.
+ */
+ public function remove_subscriber( SubscriberInterface $subscriber ) {
+ foreach ( $subscriber->get_subscribed_events() as $hook_name => $parameters ) {
+ $this->remove_subscriber_callback( $subscriber, $hook_name, $parameters );
+ }
+ }
+
+ /**
+ * Adds the given subscriber's callback to a specific hook
+ * of the WordPress plugin API.
+ *
+ * @param SubscriberInterface $subscriber SubscriberInterface implementation.
+ * @param string $hook_name Hook name.
+ * @param mixed $parameters Parameters, can be a string, an array or a multidimensional array.
+ */
+ private function add_subscriber_callback( SubscriberInterface $subscriber, $hook_name, $parameters ) {
+ if ( is_string( $parameters ) ) {
+ $this->add_callback( $hook_name, [ $subscriber, $parameters ] );
+ } elseif ( is_array( $parameters ) && count( $parameters ) !== count( $parameters, COUNT_RECURSIVE ) ) {
+ foreach ( $parameters as $parameter ) {
+ $this->add_subscriber_callback( $subscriber, $hook_name, $parameter );
+ }
+ } elseif ( is_array( $parameters ) && isset( $parameters[0] ) ) {
+ $this->add_callback( $hook_name, [ $subscriber, $parameters[0] ], isset( $parameters[1] ) ? $parameters[1] : 10, isset( $parameters[2] ) ? $parameters[2] : 1 );
+ }
+ }
+
+ /**
+ * Removes the given subscriber's callback to a specific hook
+ * of the WordPress plugin API.
+ *
+ * @param SubscriberInterface $subscriber SubscriberInterface implementation.
+ * @param string $hook_name Hook name.
+ * @param mixed $parameters Parameters, can be a string, an array or a multidimensional array.
+ */
+ private function remove_subscriber_callback( SubscriberInterface $subscriber, $hook_name, $parameters ) {
+ if ( is_string( $parameters ) ) {
+ $this->remove_callback( $hook_name, [ $subscriber, $parameters ] );
+ } elseif ( is_array( $parameters ) && count( $parameters ) !== count( $parameters, COUNT_RECURSIVE ) ) {
+ foreach ( $parameters as $parameter ) {
+ $this->remove_subscriber_callback( $subscriber, $hook_name, $parameter );
+ }
+ } elseif ( is_array( $parameters ) && isset( $parameters[0] ) ) {
+ $this->remove_callback( $hook_name, [ $subscriber, $parameters[0] ], isset( $parameters[1] ) ? $parameters[1] : 10 );
+ }
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/inc/classes/Dependencies/wp-media/event-manager/EventManagerAwareSubscriberInterface.php b/wp/wp-content/plugins/imagify/inc/classes/Dependencies/wp-media/event-manager/EventManagerAwareSubscriberInterface.php
new file mode 100644
index 00000000..b0920182
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/classes/Dependencies/wp-media/event-manager/EventManagerAwareSubscriberInterface.php
@@ -0,0 +1,14 @@
+
+ */
+interface SubscriberInterface {
+ /**
+ * Returns an array of events that this subscriber wants to listen to.
+ *
+ * The array key is the event name. The value can be:
+ *
+ * * The method name
+ * * An array with the method name and priority
+ * * An array with the method name, priority and number of accepted arguments
+ *
+ * For instance:
+ *
+ * * array('hook_name' => 'method_name')
+ * * array('hook_name' => array('method_name', $priority))
+ * * array('hook_name' => array('method_name', $priority, $accepted_args))
+ * * array('hook_name' => array(array('method_name_1', $priority_1, $accepted_args_1)), array('method_name_2', $priority_2, $accepted_args_2)))
+ *
+ * @return array
+ */
+ public static function get_subscribed_events();
+}
diff --git a/wp/wp-content/plugins/imagify/inc/classes/class-imagify-abstract-background-process.php b/wp/wp-content/plugins/imagify/inc/classes/class-imagify-abstract-background-process.php
new file mode 100644
index 00000000..08c1a7f7
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/classes/class-imagify-abstract-background-process.php
@@ -0,0 +1,165 @@
+save()
+ * @see $this->maybe_save_and_dispatch()
+ */
+ protected $auto_dispatch = false;
+
+ /**
+ * Init: launch a hook that will clear the scheduled events and empty the queue when the plugin is disabled.
+ * This is only a precaution in case something went wrong.
+ *
+ * @since 1.8.1
+ */
+ public function init() {
+ $this->query_url = admin_url( 'admin-ajax.php' );
+
+ /**
+ * Filter the URL to use for background processes.
+ *
+ * @since 1.9.5
+ *
+ * @param string $query_url An URL.
+ * @param object $this This class instance.
+ */
+ $this->query_url = apply_filters( 'imagify_background_process_url', $this->query_url, $this );
+
+ if ( ! $this->query_url || ! is_string( $this->query_url ) || ! preg_match( '@^https?://@', $this->query_url ) ) {
+ $this->query_url = admin_url( 'admin-ajax.php' );
+ }
+
+ // Deactivation hook.
+ if ( did_action( static::get_deactivation_hook_name() ) ) {
+ $this->cancel_process();
+ } else {
+ add_action( static::get_deactivation_hook_name(), [ $this, 'cancel_process' ] );
+ }
+
+ // Automatically save and dispatch at the end of the page if the queue is not empty.
+ add_action( 'shutdown', [ $this, 'maybe_save_and_dispatch' ], 666 ); // Evil magic number.
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** OVERRIDES =============================================================================== */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Cancel Process.
+ * Stop processing queue items, clear cronjob and delete batch.
+ * This is a copy of the parent's method, in case an older version of WP_Background_Process is loaded instead of this one (an old version without this method).
+ *
+ * @since 1.8.1
+ */
+ public function cancel_process() {
+ if ( method_exists( $this, 'cancel_process' ) ) {
+ parent::cancel_process();
+ return;
+ }
+
+ if ( ! $this->is_queue_empty() ) {
+ $batch = $this->get_batch();
+
+ $this->delete( $batch->key );
+
+ wp_clear_scheduled_hook( $this->get_event_name() );
+ }
+ }
+
+ /**
+ * Save the queen. No, I meant the queue.
+ * Also empty the queue to avoid to create several batches with the same items.
+ *
+ * @since 1.9
+ *
+ * @return $this
+ */
+ public function save() {
+ if ( empty( $this->data ) ) {
+ return $this;
+ }
+
+ parent::save();
+
+ $this->auto_dispatch = true;
+ $this->data = [];
+
+ return $this;
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** TOOLS =================================================================================== */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Save and dispatch if the queue is not empty.
+ *
+ * @since 1.9
+ */
+ public function maybe_save_and_dispatch() {
+ $this->save();
+
+ if ( $this->auto_dispatch ) {
+ $this->dispatch();
+ }
+ }
+
+ /**
+ * Get the cron name.
+ *
+ * @since 1.8.1
+ *
+ * @return string
+ */
+ public function get_event_name() {
+ return $this->cron_hook_identifier;
+ }
+
+ /**
+ * Get the deactivation hook name.
+ *
+ * @since 1.8.1
+ *
+ * @return string
+ */
+ public static function get_deactivation_hook_name() {
+ static $deactivation_hook;
+
+ if ( ! isset( $deactivation_hook ) ) {
+ $deactivation_hook = 'deactivate_' . plugin_basename( IMAGIFY_FILE );
+ }
+
+ return $deactivation_hook;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/inc/classes/class-imagify-abstract-cron.php b/wp/wp-content/plugins/imagify/inc/classes/class-imagify-abstract-cron.php
new file mode 100644
index 00000000..0ae6d7be
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/classes/class-imagify-abstract-cron.php
@@ -0,0 +1,299 @@
+get_event_name(), array( $this, 'do_event' ) );
+ add_filter( 'cron_schedules', array( $this, 'maybe_add_recurrence' ) );
+
+ if ( did_action( static::get_deactivation_hook_name() ) ) {
+ $this->unschedule_event();
+ } else {
+ add_action( static::get_deactivation_hook_name(), array( $this, 'unschedule_event' ) );
+ }
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** HOOKS =================================================================================== */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Initiate the event.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ */
+ public function schedule_event() {
+ if ( ! wp_next_scheduled( $this->get_event_name() ) ) {
+ wp_schedule_event( $this->get_event_timestamp(), $this->get_event_recurrence(), $this->get_event_name() );
+ }
+ }
+
+ /**
+ * The event action.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ */
+ abstract public function do_event();
+
+ /**
+ * Unschedule the event at plugin or submodule deactivation.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ */
+ public function unschedule_event() {
+ wp_clear_scheduled_hook( $this->get_event_name() );
+ }
+
+ /**
+ * Add the event recurrence schedule.
+ *
+ * @since 1.7
+ * @access public
+ * @see wp_get_schedules()
+ * @author Grégory Viguier
+ *
+ * @param array $schedules An array of non-default cron schedules. Default empty.
+ *
+ * @return array
+ */
+ public function maybe_add_recurrence( $schedules ) {
+ $default_schedules = array(
+ 'hourly' => 1,
+ 'twicedaily' => 1,
+ 'daily' => 1,
+ );
+
+ $event_recurrence = $this->get_event_recurrence();
+
+ if ( ! empty( $schedules[ $event_recurrence ] ) || ! empty( $default_schedules[ $event_recurrence ] ) ) {
+ return $schedules;
+ }
+
+ $recurrences = array(
+ 'weekly' => array(
+ 'interval' => WEEK_IN_SECONDS,
+ 'display' => __( 'Once Weekly', 'imagify' ),
+ ),
+ );
+
+ if ( method_exists( $this, 'get_event_recurrence_attributes' ) ) {
+ $recurrences[ $event_recurrence ] = $this->get_event_recurrence_attributes();
+ }
+
+ if ( ! empty( $recurrences[ $event_recurrence ] ) ) {
+ $schedules[ $event_recurrence ] = $recurrences[ $event_recurrence ];
+ }
+
+ return $schedules;
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** TOOLS =================================================================================== */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Get the cron name.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return string
+ */
+ public function get_event_name() {
+ return $this->event_name;
+ }
+
+ /**
+ * Get the cron recurrence.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return string
+ */
+ public function get_event_recurrence() {
+ /**
+ * Filter the recurrence of the event.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ *
+ * @param string $event_recurrence The recurrence.
+ * @param string $event_name Name of the event this recurrence is used for.
+ */
+ return apply_filters( 'imagify_event_recurrence', $this->event_recurrence, $this->get_event_name() );
+ }
+
+ /**
+ * Get the time to schedule the event.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return string
+ */
+ public function get_event_time() {
+ /**
+ * Filter the time at which the event is triggered (WordPress time).
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ *
+ * @param string $event_time A 24H formated time: `hour:minute`.
+ * @param string $event_name Name of the event this time is used for.
+ */
+ return apply_filters( 'imagify_event_time', $this->event_time, $this->get_event_name() );
+ }
+
+ /**
+ * Get the timestamp to schedule the event.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return int Timestamp.
+ */
+ public function get_event_timestamp() {
+ return self::get_next_timestamp( $this->get_event_time() );
+ }
+
+ /**
+ * Get the timestamp of the next (event) date for the given hour.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ * @source secupress_get_next_cron_timestamp()
+ *
+ * @param string $event_time Time when the event callback should be triggered (WordPress time), formated like `hh:mn` (hour:minute).
+ *
+ * @return int Timestamp.
+ */
+ public static function get_next_timestamp( $event_time = '00:00' ) {
+ $current_time_int = (int) gmdate( 'Gis' );
+ $event_time_int = (int) str_replace( ':', '', $event_time . '00' );
+ $event_time = explode( ':', $event_time );
+ $event_hour = (int) $event_time[0];
+ $event_minute = (int) $event_time[1];
+ $offset = get_option( 'gmt_offset' ) * HOUR_IN_SECONDS;
+
+ if ( $event_time_int <= $current_time_int ) {
+ // The event time is passed, we need to schedule the event tomorrow.
+ return mktime( $event_hour, $event_minute, 0, (int) gmdate( 'n' ), (int) gmdate( 'j' ) + 1 ) - $offset;
+ }
+
+ // We haven't passed the event time yet, schedule the event today.
+ return mktime( $event_hour, $event_minute, 0 ) - $offset;
+ }
+
+ /**
+ * Get the deactivation hook name.
+ *
+ * @since 1.9
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return string
+ */
+ public static function get_deactivation_hook_name() {
+ static $deactivation_hook;
+
+ if ( ! isset( $deactivation_hook ) ) {
+ $deactivation_hook = 'deactivate_' . plugin_basename( IMAGIFY_FILE );
+ }
+
+ return $deactivation_hook;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/inc/classes/class-imagify-abstract-db.php b/wp/wp-content/plugins/imagify/inc/classes/class-imagify-abstract-db.php
new file mode 100644
index 00000000..f4e6a9a0
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/classes/class-imagify-abstract-db.php
@@ -0,0 +1,883 @@
+table_is_global ? $wpdb->base_prefix : $wpdb->prefix;
+
+ $this->table_name = $prefix . $this->table;
+
+ if ( ! $this->table_is_up_to_date() ) {
+ /**
+ * The option doesn't exist or is not up-to-date: we must upgrade the table before declaring it ready.
+ * See self::maybe_upgrade_table() for the upgrade.
+ */
+ return;
+ }
+
+ $this->set_table_ready();
+ }
+
+ /**
+ * Get the main Instance.
+ *
+ * @since 1.6.5
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return object Main instance.
+ */
+ public static function get_instance() {
+ if ( ! isset( self::$_instance ) ) {
+ self::$_instance = new self();
+ }
+
+ return self::$_instance;
+ }
+
+ /**
+ * Init:
+ * - Launch hooks.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ */
+ public function init() {
+ add_action( 'admin_init', array( $this, 'maybe_upgrade_table' ) );
+ }
+
+ /**
+ * Tell if we can work with the tables.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return bool
+ */
+ public function can_operate() {
+ return $this->table_created;
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** TABLE SPECIFICS ========================================================================= */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Get the column placeholders.
+ *
+ * @since 1.5
+ * @access public
+ *
+ * @return array
+ */
+ abstract public function get_columns();
+
+ /**
+ * Default column values.
+ *
+ * @since 1.5
+ * @access public
+ *
+ * @return array
+ */
+ abstract public function get_column_defaults();
+
+ /**
+ * Get the query to create the table fields.
+ *
+ * @since 1.7
+ * @access protected
+ * @author Grégory Viguier
+ *
+ * @return string
+ */
+ abstract protected function get_table_schema();
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** QUERIES ================================================================================= */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Tell if the table is empty or not.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return bool True if the table contains at least one row.
+ */
+ public function has_items() {
+ global $wpdb;
+
+ $column = esc_sql( $this->primary_key );
+
+ return (bool) $wpdb->get_var( "SELECT $column FROM $this->table_name LIMIT 1;" ); // WPCS: unprepared SQL ok.
+ }
+
+ /**
+ * Retrieve a row by the primary key.
+ *
+ * @since 1.5
+ * @access public
+ *
+ * @param string $row_id A primary key.
+ * @return array
+ */
+ public function get( $row_id ) {
+ if ( $row_id <= 0 ) {
+ return array();
+ }
+
+ return $this->get_by( $this->primary_key, $row_id );
+ }
+
+ /**
+ * Retrieve a row by a specific column / value.
+ *
+ * @since 1.5
+ * @access public
+ *
+ * @param string $column_where A column name.
+ * @param mixed $column_value A value.
+ * @return array
+ */
+ public function get_by( $column_where, $column_value ) {
+ global $wpdb;
+
+ $placeholder = $this->get_placeholder( $column_where );
+ $column_where = esc_sql( $column_where );
+
+ $result = $wpdb->get_row( $wpdb->prepare( "SELECT * FROM $this->table_name WHERE $column_where = $placeholder LIMIT 1;", $column_value ), ARRAY_A ); // WPCS: unprepared SQL ok, PreparedSQLPlaceholders replacement count ok.
+
+ return (array) $this->cast_row( $result );
+ }
+
+ /**
+ * Retrieve a row by the specified column / values.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param string $column_where A column name.
+ * @param array $column_values An array of values.
+ * @return array
+ */
+ public function get_in( $column_where, $column_values ) {
+ global $wpdb;
+
+ $column_where = esc_sql( $column_where );
+ $column_values = Imagify_DB::prepare_values_list( $column_values );
+
+ $result = $wpdb->get_row( "SELECT * FROM $this->table_name WHERE $column_where IN ( $column_values ) LIMIT 1;", ARRAY_A ); // WPCS: unprepared SQL ok.
+
+ return (array) $this->cast_row( $result );
+ }
+
+ /**
+ * Retrieve a var by the primary key.
+ * Previously named get_column().
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param string $column_select A column name.
+ * @param string $row_id A primary key.
+ * @return mixed
+ */
+ public function get_var( $column_select, $row_id ) {
+ if ( $row_id <= 0 ) {
+ return false;
+ }
+
+ return $this->get_var_by( $column_select, $this->primary_key, $row_id );
+ }
+
+ /**
+ * Retrieve a var by the specified column / value.
+ * Previously named get_column_by().
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param string $column_select A column name.
+ * @param string $column_where A column name.
+ * @param string $column_value A value.
+ * @return mixed
+ */
+ public function get_var_by( $column_select, $column_where, $column_value ) {
+ global $wpdb;
+
+ $placeholder = $this->get_placeholder( $column_where );
+ $column = esc_sql( $column_select );
+ $column_where = esc_sql( $column_where );
+
+ $result = $wpdb->get_var( $wpdb->prepare( "SELECT $column FROM $this->table_name WHERE $column_where = $placeholder LIMIT 1;", $column_value ) ); // WPCS: unprepared SQL ok, PreparedSQLPlaceholders replacement count ok.
+
+ return $this->cast( $result, $column_select );
+ }
+
+ /**
+ * Retrieve a var by the specified column / values.
+ * Previously named get_column_in().
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param string $column_select A column name.
+ * @param string $column_where A column name.
+ * @param array $column_values An array of values.
+ * @return mixed
+ */
+ public function get_var_in( $column_select, $column_where, $column_values ) {
+ global $wpdb;
+
+ $column = esc_sql( $column_select );
+ $column_where = esc_sql( $column_where );
+ $column_values = Imagify_DB::prepare_values_list( $column_values );
+
+ $result = $wpdb->get_var( "SELECT $column FROM $this->table_name WHERE $column_where IN ( $column_values ) LIMIT 1;" ); // WPCS: unprepared SQL ok.
+
+ return $this->cast( $result, $column_select );
+ }
+
+ /**
+ * Retrieve values by the specified column / values.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param string $column_select A column name.
+ * @param string $column_where A column name.
+ * @param array $column_values An array of values.
+ * @return array
+ */
+ public function get_column_in( $column_select, $column_where, $column_values ) {
+ global $wpdb;
+
+ $column = esc_sql( $column_select );
+ $column_where = esc_sql( $column_where );
+ $column_values = Imagify_DB::prepare_values_list( $column_values );
+
+ $result = $wpdb->get_col( "SELECT $column FROM $this->table_name WHERE $column_where IN ( $column_values );" ); // WPCS: unprepared SQL ok.
+
+ return $this->cast_col( $result, $column_select );
+ }
+
+ /**
+ * Retrieve values by the specified column / values.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param string $column_select A column name.
+ * @param string $column_where A column name.
+ * @param array $column_values An array of values.
+ * @return array
+ */
+ public function get_column_not_in( $column_select, $column_where, $column_values ) {
+ global $wpdb;
+
+ $column = esc_sql( $column_select );
+ $column_where = esc_sql( $column_where );
+ $column_values = Imagify_DB::prepare_values_list( $column_values );
+
+ $result = $wpdb->get_col( "SELECT $column FROM $this->table_name WHERE $column_where NOT IN ( $column_values );" ); // WPCS: unprepared SQL ok.
+
+ return $this->cast_col( $result, $column_select );
+ }
+
+ /**
+ * Insert a new row.
+ *
+ * @since 1.5
+ * @access public
+ *
+ * @param string $data New data.
+ * @return int The ID.
+ */
+ public function insert( $data ) {
+ global $wpdb;
+
+ // Initialise column format array.
+ $column_formats = $this->get_columns();
+
+ // Set default values.
+ $data = wp_parse_args( $data, $this->get_column_defaults() );
+
+ // Force fields to lower case.
+ $data = array_change_key_case( $data );
+
+ // White list columns.
+ $data = array_intersect_key( $data, $column_formats );
+
+ // Maybe serialize some values.
+ $data = $this->serialize_columns( $data );
+
+ // Reorder $column_formats to match the order of columns given in $data.
+ $column_formats = array_merge( $data, $column_formats );
+
+ $wpdb->insert( $this->table_name, $data, $column_formats );
+
+ return (int) $wpdb->insert_id;
+ }
+
+ /**
+ * Update a row.
+ *
+ * @since 1.5
+ * @access public
+ *
+ * @param int $row_id A primary key.
+ * @param array $data New data.
+ * @param string $where A column name.
+ * @return bool
+ */
+ public function update( $row_id, $data = array(), $where = '' ) {
+ global $wpdb;
+
+ if ( $row_id <= 0 ) {
+ return false;
+ }
+
+ if ( ! $this->get( $row_id ) ) {
+ $this->insert( $data );
+ return true;
+ }
+
+ if ( empty( $where ) ) {
+ $where = $this->primary_key;
+ }
+
+ // Initialise column format array.
+ $column_formats = $this->get_columns();
+
+ // Force fields to lower case.
+ $data = array_change_key_case( $data );
+
+ // White list columns.
+ $data = array_intersect_key( $data, $column_formats );
+
+ // Maybe serialize some values.
+ $data = $this->serialize_columns( $data );
+
+ // Reorder $column_formats to match the order of columns given in $data.
+ $column_formats = array_merge( $data, $column_formats );
+
+ return (bool) $wpdb->update( $this->table_name, $data, array( $where => $row_id ), $column_formats, $this->get_placeholder( $where ) );
+ }
+
+ /**
+ * Delete a row identified by the primary key.
+ *
+ * @since 1.5
+ * @access public
+ *
+ * @param string $row_id A primary key.
+ * @return bool
+ */
+ public function delete( $row_id = 0 ) {
+ global $wpdb;
+
+ if ( $row_id <= 0 ) {
+ return false;
+ }
+
+ $placeholder = $this->get_placeholder( $this->primary_key );
+
+ return (bool) $wpdb->query( $wpdb->prepare( "DELETE FROM $this->table_name WHERE $this->primary_key = $placeholder", $row_id ) ); // WPCS: unprepared SQL ok, PreparedSQLPlaceholders replacement count ok.
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** TABLE CREATION ========================================================================== */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Maybe create/upgrade the table in the database.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ */
+ public function maybe_upgrade_table() {
+ global $wpdb;
+
+ if ( $this->table_is_up_to_date() ) {
+ // The table has the right version.
+ $this->set_table_ready();
+ return;
+ }
+
+ // Create the table.
+ $this->create_table();
+ }
+
+ /**
+ * Create/Upgrade the table in the database.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ */
+ public function create_table() {
+ if ( ! Imagify_DB::create_table( $this->get_table_name(), $this->get_table_schema() ) ) {
+ // Failure.
+ $this->set_table_not_ready();
+ $this->delete_db_version();
+ return;
+ }
+
+ // Table successfully created/upgraded.
+ $this->set_table_ready();
+ $this->update_db_version();
+ }
+
+ /**
+ * Set various properties to tell the table is ready to be used.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ */
+ protected function set_table_ready() {
+ global $wpdb;
+
+ $this->table_created = true;
+ $wpdb->{$this->table} = $this->table_name;
+
+ if ( $this->table_is_global ) {
+ $wpdb->global_tables[] = $this->table;
+ } else {
+ $wpdb->tables[] = $this->table;
+ }
+ }
+
+ /**
+ * Unset various properties to tell the table is NOT ready to be used.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ */
+ protected function set_table_not_ready() {
+ global $wpdb;
+
+ $this->table_created = false;
+ unset( $wpdb->{$this->table} );
+
+ if ( $this->table_is_global ) {
+ $wpdb->global_tables = array_diff( $wpdb->global_tables, array( $this->table ) );
+ } else {
+ $wpdb->tables = array_diff( $wpdb->tables, array( $this->table ) );
+ }
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** TABLE VERSION =========================================================================== */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Get the table version.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return int
+ */
+ public function get_table_version() {
+ return $this->table_version;
+ }
+
+ /**
+ * Tell if the table is up-to-date (we don't "downgrade" the tables).
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return bool
+ */
+ public function table_is_up_to_date() {
+ return $this->get_db_version() >= $this->get_table_version();
+ }
+
+ /**
+ * Get the table version stored in DB.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return int|bool The version. False if not set yet.
+ */
+ public function get_db_version() {
+ $option_name = $this->table . self::TABLE_VERSION_OPTION_SUFFIX;
+
+ if ( $this->table_is_global && is_multisite() ) {
+ return get_site_option( $option_name );
+ }
+
+ return get_option( $option_name );
+ }
+
+ /**
+ * Update the table version stored in DB.
+ *
+ * @since 1.7
+ * @access protected
+ * @author Grégory Viguier
+ */
+ protected function update_db_version() {
+ $option_name = $this->table . self::TABLE_VERSION_OPTION_SUFFIX;
+
+ if ( $this->table_is_global && is_multisite() ) {
+ update_site_option( $option_name, $this->get_table_version() );
+ } else {
+ update_option( $option_name, $this->get_table_version() );
+ }
+ }
+
+ /**
+ * Delete the table version stored in DB.
+ *
+ * @since 1.7
+ * @access protected
+ * @author Grégory Viguier
+ */
+ protected function delete_db_version() {
+ $option_name = $this->table . self::TABLE_VERSION_OPTION_SUFFIX;
+
+ if ( $this->table_is_global && is_multisite() ) {
+ delete_site_option( $option_name );
+ } else {
+ delete_option( $option_name );
+ }
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** TOOLS =================================================================================== */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Get the table name.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return string
+ */
+ public function get_table_name() {
+ return $this->table_name;
+ }
+
+ /**
+ * Tell if the table is the same for each site of a Multisite.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return bool
+ */
+ public function is_table_global() {
+ return $this->table_is_global;
+ }
+
+ /**
+ * Get the primary column name.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return string
+ */
+ public function get_primary_key() {
+ return $this->primary_key;
+ }
+
+ /**
+ * Get the formats related to the given columns.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param array $columns An array of column names (as keys).
+ * @return array
+ */
+ public function get_column_formats( $columns ) {
+ if ( ! is_array( $columns ) ) {
+ $columns = array_flip( (array) $columns );
+ }
+
+ // White list columns.
+ return array_intersect_key( $this->get_columns(), $columns );
+ }
+
+ /**
+ * Get the placeholder corresponding to the given key.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param string $key The key.
+ * @return string
+ */
+ public function get_placeholder( $key ) {
+ $columns = $this->get_columns();
+ return isset( $columns[ $key ] ) ? $columns[ $key ] : '%s';
+ }
+
+ /**
+ * Tell if the column value must be (un)serialized.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param string $key The key.
+ * @return bool
+ */
+ public function is_column_serialized( $key ) {
+ $columns = $this->get_column_defaults();
+ return isset( $columns[ $key ] ) && is_array( $columns[ $key ] );
+ }
+
+ /**
+ * Cast a value.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param mixed $value The value to cast.
+ * @param string $key The corresponding key.
+ * @return mixed
+ */
+ public function cast( $value, $key ) {
+ if ( null === $value || is_bool( $value ) ) {
+ return $value;
+ }
+
+ $placeholder = $this->get_placeholder( $key );
+
+ if ( '%d' === $placeholder ) {
+ return (int) $value;
+ }
+
+ if ( '%f' === $placeholder ) {
+ return (float) $value;
+ }
+
+ if ( $value && $this->is_column_serialized( $key ) ) {
+ return maybe_unserialize( $value );
+ }
+
+ return $value;
+ }
+
+ /**
+ * Cast a column.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param array $values The values to cast.
+ * @param string $column The corresponding column name.
+ * @return array
+ */
+ public function cast_col( $values, $column ) {
+ if ( ! $values ) {
+ return $values;
+ }
+
+ foreach ( $values as $i => $value ) {
+ $values[ $i ] = $this->cast( $value, $column );
+ }
+
+ return $values;
+ }
+
+ /**
+ * Cast a row.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param array|object $row_fields A row from the DB.
+ * @return array|object
+ */
+ public function cast_row( $row_fields ) {
+ if ( ! $row_fields ) {
+ return $row_fields;
+ }
+
+ if ( is_array( $row_fields ) ) {
+ foreach ( $row_fields as $field => $value ) {
+ $row_fields[ $field ] = $this->cast( $value, $field );
+ }
+ } elseif ( is_object( $row_fields ) ) {
+ foreach ( $row_fields as $field => $value ) {
+ $row_fields->$field = $this->cast( $value, $field );
+ }
+ }
+
+ return $row_fields;
+ }
+
+ /**
+ * Serialize columns that need to be.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param array $data An array of values.
+ * @return array
+ */
+ public function serialize_columns( $data ) {
+ if ( ! isset( $this->to_serialize ) ) {
+ $this->to_serialize = array_filter( $this->get_column_defaults(), 'is_array' );
+ }
+
+ if ( ! $this->to_serialize ) {
+ return $data;
+ }
+
+ $serialized_data = array_intersect_key( $data, $this->to_serialize );
+
+ if ( ! $serialized_data ) {
+ return $data;
+ }
+
+ $serialized_data = array_map( function( $array ) {
+ // Try not to store empty serialized arrays.
+ return [] === $array ? null : maybe_serialize( $array );
+ }, $serialized_data );
+
+ return array_merge( $data, $serialized_data );
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/inc/classes/class-imagify-abstract-options.php b/wp/wp-content/plugins/imagify/inc/classes/class-imagify-abstract-options.php
new file mode 100644
index 00000000..2caeeaab
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/classes/class-imagify-abstract-options.php
@@ -0,0 +1,623 @@
+hook_identifier = rtrim( strtolower( str_replace( 'Imagify_', '', get_class( $this ) ) ), 's' );
+
+ if ( ! is_string( $this->autoload ) ) {
+ $this->autoload = $this->autoload ? 'yes' : 'no';
+ }
+
+ $this->default_values = array_merge( array(
+ 'version' => '',
+ ), $this->default_values );
+ }
+
+ /**
+ * Get the main Instance.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ * @access public
+ *
+ * @return object Main instance.
+ */
+ public static function get_instance() {
+ if ( ! isset( self::$_instance ) ) {
+ self::$_instance = new self();
+ }
+
+ return self::$_instance;
+ }
+
+ /**
+ * Launch the hooks.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ * @access public
+ */
+ public function init() {
+ add_filter( 'sanitize_option_' . $this->get_option_name(), array( $this, 'sanitize_and_validate_on_update' ), 50 );
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** GET/SET/DELETE OPTION(S) ================================================================ */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Get an Imagify option.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ * @access public
+ *
+ * @param string $key The option name.
+ * @return mixed The option value.
+ */
+ public function get( $key ) {
+ $default_values = $this->get_default_values();
+
+ if ( ! isset( $default_values[ $key ] ) ) {
+ return null;
+ }
+
+ $default = $default_values[ $key ];
+
+ /**
+ * Pre-filter any Imagify option before read.
+ *
+ * @since 1.0
+ *
+ * @param mixed $value Value to return instead of the option value. Default null to skip it.
+ * @param mixed $default The default value.
+ */
+ $value = apply_filters( 'pre_get_imagify_' . $this->get_hook_identifier() . '_' . $key, null, $default );
+
+ if ( isset( $value ) ) {
+ return $value;
+ }
+
+ // Get all values.
+ $values = $this->get_all();
+
+ // Sanitize and validate the value.
+ $value = $this->sanitize_and_validate( $key, $values[ $key ], $default );
+
+ /**
+ * Filter any Imagify option after read.
+ *
+ * @since 1.0
+ *
+ * @param mixed $value Value of the option.
+ * @param mixed $default The default value. Default false.
+ */
+ return apply_filters( 'get_imagify_' . $this->get_hook_identifier() . '_' . $key, $value, $default );
+ }
+
+ /**
+ * Get all options (no cast, no sanitization, no validation).
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ * @access public
+ *
+ * @return array The options.
+ */
+ public function get_all() {
+ $values = $this->get_raw();
+
+ if ( ! $values ) {
+ return $this->get_reset_values();
+ }
+
+ return imagify_merge_intersect( $values, $this->get_default_values() );
+ }
+
+ /**
+ * Set one or multiple options.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ * @access public
+ *
+ * @param array $values An array of option name / option value pairs.
+ */
+ public function set( $values ) {
+ $args = func_get_args();
+
+ if ( isset( $args[1] ) && is_string( $args[0] ) ) {
+ $values = array( $args[0] => $args[1] );
+ }
+
+ if ( ! is_array( $values ) ) {
+ // PABKAC.
+ return;
+ }
+
+ $values = array_merge( $this->get_all(), $values );
+ $values = array_intersect_key( $values, $this->get_default_values() );
+
+ $this->set_raw( $values );
+ }
+
+ /**
+ * Delete one or multiple options.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ * @access public
+ *
+ * @param array|string $keys An array of option names or a single option name.
+ */
+ public function delete( $keys ) {
+ $values = $this->get_raw();
+
+ if ( ! $values ) {
+ if ( false !== $values ) {
+ $this->delete_raw();
+ }
+ return;
+ }
+
+ $keys = array_flip( (array) $keys );
+ $values = array_diff_key( $values, $keys );
+
+ $this->set_raw( $values );
+ }
+
+ /**
+ * Checks if the option with the given name exists or not.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ * @access public
+ *
+ * @param string $key The option name.
+ * @return bool
+ */
+ public function has( $key ) {
+ return null !== $this->get( $key );
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** GET / UPDATE / DELETE RAW VALUES ======================================================== */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Get the name of the option that stores the settings.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ * @access public
+ *
+ * @return string
+ */
+ public function get_option_name() {
+ return IMAGIFY_SLUG . '_' . $this->identifier;
+ }
+
+ /**
+ * Get the identifier used in the hook names.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ * @access public
+ *
+ * @return string
+ */
+ public function get_hook_identifier() {
+ return $this->hook_identifier;
+ }
+
+ /**
+ * Tell if the option is autoloaded.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ * @access public
+ *
+ * @return bool
+ */
+ public function is_autoloaded() {
+ return 'yes' === $this->autoload;
+ }
+
+ /**
+ * Tell if the option is a network option.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ * @access public
+ *
+ * @return bool
+ */
+ public function is_network_option() {
+ return (bool) $this->network_option;
+ }
+
+ /**
+ * Get the raw value of all Imagify options.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ * @access public
+ *
+ * @return array|bool The options. False if not set yet. An empty array if invalid.
+ */
+ public function get_raw() {
+ $values = $this->is_network_option() ? get_site_option( $this->get_option_name() ) : get_option( $this->get_option_name() );
+
+ if ( false !== $values && ! is_array( $values ) ) {
+ return array();
+ }
+
+ return $values;
+ }
+
+ /**
+ * Update the Imagify options.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ * @access public
+ *
+ * @param array $values An array of option name / option value pairs.
+ */
+ public function set_raw( $values ) {
+ if ( ! $values ) {
+ // The option is empty: delete it.
+ $this->delete_raw();
+
+ } elseif ( $this->is_network_option() ) {
+ // Network option.
+ update_site_option( $this->get_option_name(), $values );
+
+ } elseif ( false === get_option( $this->get_option_name() ) ) {
+ // Compat' with WP < 4.2 + autoload: the option doesn't exist in the database.
+ add_option( $this->get_option_name(), $values, '', $this->autoload );
+ } else {
+ // Update the current value.
+ update_option( $this->get_option_name(), $values, $this->autoload );
+ }
+ }
+
+ /**
+ * Delete all Imagify options.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ * @access public
+ */
+ public function delete_raw() {
+ $this->is_network_option() ? delete_site_option( $this->get_option_name() ) : delete_option( $this->get_option_name() );
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** DEFAULT + RESET VALUES ================================================================== */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Get default option values.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ * @access public
+ *
+ * @return array
+ */
+ public function get_default_values() {
+ $default_values = $this->default_values;
+
+ if ( ! empty( $default_values['cached'] ) ) {
+ unset( $default_values['cached'] );
+ return $default_values;
+ }
+
+ /**
+ * Allow to add more default option values.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ *
+ * @param array $new_values New default option values.
+ * @param array $default_values Plugin default option values.
+ */
+ $new_values = apply_filters( 'imagify_default_' . $this->get_hook_identifier() . '_values', array(), $default_values );
+ $new_values = is_array( $new_values ) ? $new_values : array();
+
+ if ( $new_values ) {
+ // Don't allow new values to overwrite the plugin values.
+ $new_values = array_diff_key( $new_values, $default_values );
+ }
+
+ if ( $new_values ) {
+ $default_values = array_merge( $default_values, $new_values );
+ $this->default_values = $default_values;
+ }
+
+ $this->default_values['cached'] = 1;
+
+ return $default_values;
+ }
+
+ /**
+ * Get the values used when the option is empty.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ * @access public
+ *
+ * @return array
+ */
+ public function get_reset_values() {
+ $reset_values = $this->reset_values;
+
+ if ( ! empty( $reset_values['cached'] ) ) {
+ unset( $reset_values['cached'] );
+ return $reset_values;
+ }
+
+ $default_values = $this->get_default_values();
+ $reset_values = array_merge( $default_values, $reset_values );
+
+ /**
+ * Allow to filter the "reset" option values.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ *
+ * @param array $reset_values Plugin reset option values.
+ */
+ $new_values = apply_filters( 'imagify_reset_' . $this->get_hook_identifier() . '_values', $reset_values );
+
+ if ( $new_values && is_array( $new_values ) ) {
+ $reset_values = array_merge( $reset_values, $new_values );
+ }
+
+ $this->reset_values = $reset_values;
+ $this->reset_values['cached'] = 1;
+
+ return $reset_values;
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** SANITIZATION, VALIDATION ================================================================ */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Sanitize and validate an option value.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ * @access public
+ *
+ * @param string $key The option key.
+ * @param mixed $value The value.
+ * @param mixed $default The default value.
+ * @return mixed
+ */
+ public function sanitize_and_validate( $key, $value, $default = null ) {
+ if ( ! isset( $default ) ) {
+ $default_values = $this->get_default_values();
+ $default = $default_values[ $key ];
+ }
+
+ // Cast the value.
+ $value = self::cast( $value, $default );
+
+ if ( $value === $default ) {
+ return $value;
+ }
+
+ // Version.
+ if ( 'version' === $key ) {
+ return sanitize_text_field( $value );
+ }
+
+ return $this->sanitize_and_validate_value( $key, $value, $default );
+ }
+
+ /**
+ * Sanitize and validate an option value. Basic casts have been made.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ * @access public
+ *
+ * @param string $key The option key.
+ * @param mixed $value The value.
+ * @param mixed $default The default value.
+ * @return mixed
+ */
+ abstract public function sanitize_and_validate_value( $key, $value, $default );
+
+ /**
+ * Sanitize and validate Imagify's options before storing them.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ * @access public
+ *
+ * @param string $values The option value.
+ * @return array
+ */
+ public function sanitize_and_validate_on_update( $values ) {
+ $values = is_array( $values ) ? $values : array();
+ $default_values = $this->get_default_values();
+
+ if ( $values ) {
+ foreach ( $default_values as $key => $default ) {
+ if ( isset( $values[ $key ] ) ) {
+ $values[ $key ] = $this->sanitize_and_validate( $key, $values[ $key ], $default );
+ }
+ }
+ }
+
+ $values = array_intersect_key( $values, $default_values );
+
+ // Version.
+ if ( empty( $values['version'] ) ) {
+ $values['version'] = IMAGIFY_VERSION;
+ }
+
+ return $this->validate_values_on_update( $values );
+ }
+
+ /**
+ * Validate Imagify's options before storing them. Basic sanitization and validation have been made, row by row.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ * @access public
+ *
+ * @param string $values The option value.
+ * @return array
+ */
+ public function validate_values_on_update( $values ) {
+ return $values;
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** TOOLS =================================================================================== */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Cast a value, depending on its default value type.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ * @access public
+ *
+ * @param mixed $value The value to cast.
+ * @param mixed $default The default value.
+ * @return mixed
+ */
+ public static function cast( $value, $default ) {
+ if ( is_array( $default ) ) {
+ return is_array( $value ) ? $value : array();
+ }
+
+ if ( is_int( $default ) ) {
+ return (int) $value;
+ }
+
+ if ( is_bool( $default ) ) {
+ return (bool) $value;
+ }
+
+ if ( is_float( $default ) ) {
+ return round( (float) $value, 3 );
+ }
+
+ return $value;
+ }
+
+ /**
+ * Cast a float like 3.000 into an integer.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ * @access public
+ *
+ * @param float $float The float.
+ * @return float|int
+ */
+ public static function maybe_cast_float_as_int( $float ) {
+ return ( $float / (int) $float ) === (float) 1 ? (int) $float : $float;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/inc/classes/class-imagify-admin-ajax-post.php b/wp/wp-content/plugins/imagify/inc/classes/class-imagify-admin-ajax-post.php
new file mode 100644
index 00000000..420ebbcb
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/classes/class-imagify-admin-ajax-post.php
@@ -0,0 +1,1310 @@
+filesystem = Imagify_Filesystem::get_instance();
+ }
+
+ /**
+ * Launch the hooks.
+ *
+ * @since 1.6.11
+ */
+ public function init() {
+ $doing_ajax = wp_doing_ajax();
+
+ foreach ( $this->ajax_post_actions as $action ) {
+ $action_callback = "{$action}_callback";
+ if ( $doing_ajax ) {
+ add_action( 'wp_ajax_' . $action, array( $this, $action_callback ) );
+ }
+ add_action( 'admin_post_' . $action, array( $this, $action_callback ) );
+ }
+
+ // Actions triggered only on admin ajax.
+ if ( $doing_ajax ) {
+ foreach ( $this->ajax_only_actions as $action ) {
+ add_action( 'wp_ajax_' . $action, array( $this, $action . '_callback' ) );
+ }
+ }
+
+ // Actions triggered on admin post.
+ foreach ( $this->post_only_actions as $action ) {
+ add_action( 'admin_post_' . $action, array( $this, $action . '_callback' ) );
+ }
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** OPTIMIZATION PROCESSES ================================================================== */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Optimize one media.
+ *
+ * @since 1.9
+ *
+ * @param int $media_id The media ID.
+ * @param string $context The context.
+ * @return bool|WP_Error True if successfully launched. A \WP_Error instance on failure.
+ */
+ protected function optimize_media( $media_id, $context ) {
+ return imagify_get_optimization_process( $media_id, $context )->optimize();
+ }
+
+ /**
+ * Re-optimize a media to a different optimization level.
+ *
+ * @since 1.9
+ *
+ * @param int $media_id The media ID.
+ * @param string $context The context.
+ * @param int $level The optimization level.
+ * @return bool|WP_Error True if successfully launched. A \WP_Error instance on failure.
+ */
+ protected function reoptimize_media( $media_id, $context, $level ) {
+ return imagify_get_optimization_process( $media_id, $context )->reoptimize( $level );
+ }
+
+ /**
+ * Optimize all files from a media, whatever this media’s previous optimization status (will be restored if needed).
+ * This is used by the bulk optimization page.
+ *
+ * @since 1.9
+ *
+ * @param int $media_id The media ID.
+ * @param string $context The context.
+ * @param int $level The optimization level.
+ * @return bool|WP_Error True if successfully launched. A \WP_Error instance on failure.
+ */
+ protected function force_optimize( $media_id, $context, $level ) {
+ $process = imagify_get_optimization_process( $media_id, $context );
+ $data = $process->get_data();
+
+ // Restore before re-optimizing.
+ if ( $data->is_optimized() ) {
+ $result = $process->restore();
+
+ if ( is_wp_error( $result ) ) {
+ // Return an error message.
+ return $result;
+ }
+ }
+
+ return $process->optimize( $level );
+ }
+
+ /**
+ * Optimize one or some thumbnails that are not optimized yet.
+ *
+ * @since 1.9
+ *
+ * @param int $media_id The media ID.
+ * @param string $context The context.
+ * @return bool|WP_Error True if successfully launched. A \WP_Error instance on failure.
+ */
+ protected function optimize_missing_sizes( $media_id, $context ) {
+ return imagify_get_optimization_process( $media_id, $context )->optimize_missing_thumbnails();
+ }
+
+ /**
+ * Generate next-gen images if they are missing.
+ *
+ * @since 1.9
+ *
+ * @param int $media_id The media ID.
+ * @param string $context The context.
+ * @return bool|WP_Error True if successfully launched. A \WP_Error instance on failure.
+ */
+ protected function generate_nextgen_versions( $media_id, $context ) {
+ return imagify_get_optimization_process( $media_id, $context )->generate_nextgen_versions();
+ }
+
+ /**
+ * Delete Next gen images for media that are "already_optimize".
+ *
+ * @since 1.9.6
+ *
+ * @param int $media_id The media ID.
+ * @param string $context The context.
+ * @return bool|WP_Error True if successfully launched. A \WP_Error instance on failure.
+ */
+ protected function delete_nextgen_versions( $media_id, $context ) {
+ $process = imagify_get_optimization_process( $media_id, $context );
+
+ if ( ! $process->is_valid() ) {
+ return new WP_Error( 'invalid_media', __( 'This media is not valid.', 'imagify' ) );
+ }
+
+ $data = $process->get_data();
+
+ if ( ! $data->is_already_optimized() ) {
+ return new WP_Error( 'not_already_optimized', __( 'This media does not have the right optimization status.', 'imagify' ) );
+ }
+
+ if ( ! $process->has_next_gen() ) {
+ return true;
+ }
+
+ $data->delete_optimization_data();
+ $deleted = $process->delete_nextgen_files( false, true );
+
+ if ( is_wp_error( $deleted ) ) {
+ return new WP_Error( 'nextgen_not_deleted', __( 'Previous next-gen files could not be deleted.', 'imagify' ) );
+ }
+
+ return true;
+ }
+
+ /**
+ * Restore a media.
+ *
+ * @since 1.9
+ *
+ * @param int $media_id The media ID.
+ * @param string $context The context.
+ * @return bool|WP_Error True on success. A \WP_Error instance on failure.
+ */
+ protected function restore_media( $media_id, $context ) {
+ return imagify_get_optimization_process( $media_id, $context )->restore();
+ }
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** WP OPTIMIZATION CALLBACKS =============================================================== */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Optimize all thumbnails of a specific image with the manual method.
+ *
+ * @since 1.6.11
+ */
+ public function imagify_manual_optimize_callback() {
+ $context = $this->get_context();
+ $media_id = $this->get_media_id();
+
+ if ( ! $media_id || ! $context ) {
+ imagify_die( __( 'Invalid request', 'imagify' ) );
+ }
+
+ imagify_check_nonce( 'imagify-optimize-' . $media_id . '-' . $context );
+
+ if ( ! imagify_get_context( $context )->current_user_can( 'manual-optimize', $media_id ) ) {
+ imagify_die();
+ }
+
+ $result = $this->optimize_media( $media_id, $context );
+
+ imagify_maybe_redirect( is_wp_error( $result ) ? $result : false );
+
+ if ( is_wp_error( $result ) ) {
+ // Return an error message.
+ $output = $result->get_error_message();
+
+ wp_send_json_error( [ 'html' => $output ] );
+ }
+
+ wp_send_json_success();
+ }
+
+ /**
+ * Optimize all thumbnails of a specific image with a different optimization level.
+ *
+ * @since 1.6.11
+ */
+ public function imagify_manual_reoptimize_callback() {
+ $context = $this->get_context();
+ $media_id = $this->get_media_id();
+
+ if ( ! $media_id || ! $context ) {
+ imagify_die( __( 'Invalid request', 'imagify' ) );
+ }
+
+ imagify_check_nonce( 'imagify-manual-reoptimize-' . $media_id . '-' . $context );
+
+ if ( ! imagify_get_context( $context )->current_user_can( 'manual-optimize', $media_id ) ) {
+ imagify_die();
+ }
+
+ $result = $this->reoptimize_media( $media_id, $context, $this->get_optimization_level() );
+
+ imagify_maybe_redirect( is_wp_error( $result ) ? $result : false );
+
+ if ( is_wp_error( $result ) ) {
+ // Return an error message.
+ $output = $result->get_error_message();
+
+ wp_send_json_error( [ 'html' => $output ] );
+ }
+
+ wp_send_json_success();
+ }
+
+ /**
+ * Optimize one or some thumbnails that are not optimized yet.
+ *
+ * @since 1.6.11
+ */
+ public function imagify_optimize_missing_sizes_callback() {
+ $context = $this->get_context();
+ $media_id = $this->get_media_id();
+
+ if ( ! $media_id || ! $context ) {
+ imagify_die( __( 'Invalid request', 'imagify' ) );
+ }
+
+ imagify_check_nonce( 'imagify-optimize-missing-sizes-' . $media_id . '-' . $context );
+
+ if ( ! imagify_get_context( $context )->current_user_can( 'manual-optimize', $media_id ) ) {
+ imagify_die();
+ }
+
+ $result = $this->optimize_missing_sizes( $media_id, $context );
+
+ imagify_maybe_redirect( is_wp_error( $result ) ? $result : false );
+
+ if ( is_wp_error( $result ) ) {
+ // Return an error message.
+ $output = $result->get_error_message();
+
+ wp_send_json_error( [ 'html' => $output ] );
+ }
+
+ wp_send_json_success();
+ }
+
+ /**
+ * Generate next-gen images if they are missing.
+ *
+ * @since 1.9
+ */
+ public function imagify_generate_nextgen_versions_callback() {
+ $context = $this->get_context();
+ $media_id = $this->get_media_id();
+
+ if ( ! $media_id || ! $context ) {
+ imagify_die( __( 'Invalid request', 'imagify' ) );
+ }
+
+ imagify_check_nonce( 'imagify-generate-nextgen-versions-' . $media_id . '-' . $context );
+
+ if ( ! imagify_get_context( $context )->current_user_can( 'manual-optimize', $media_id ) ) {
+ imagify_die();
+ }
+
+ $result = $this->generate_nextgen_versions( $media_id, $context );
+
+ imagify_maybe_redirect( is_wp_error( $result ) ? $result : false );
+
+ if ( is_wp_error( $result ) ) {
+ // Return an error message.
+ $output = $result->get_error_message();
+
+ wp_send_json_error( [ 'html' => $output ] );
+ }
+
+ wp_send_json_success();
+ }
+
+ /**
+ * Generate next-gen images if they are missing.
+ *
+ * @since 1.9.6
+ */
+ public function imagify_delete_nextgen_versions_callback() {
+ $context = $this->get_context();
+ $media_id = $this->get_media_id();
+
+ if ( ! $media_id || ! $context ) {
+ imagify_die( __( 'Invalid request', 'imagify' ) );
+ }
+
+ imagify_check_nonce( 'imagify-delete-nextgen-versions-' . $media_id . '-' . $context );
+
+ if ( ! imagify_get_context( $context )->current_user_can( 'manual-restore', $media_id ) ) {
+ imagify_die();
+ }
+
+ $result = $this->delete_nextgen_versions( $media_id, $context );
+
+ imagify_maybe_redirect( is_wp_error( $result ) ? $result : false );
+
+ if ( is_wp_error( $result ) ) {
+ // Return an error message.
+ $output = $result->get_error_message();
+
+ wp_send_json_error( [ 'html' => $output ] );
+ }
+
+ wp_send_json_success();
+ }
+
+ /**
+ * Process a restoration to the original attachment.
+ *
+ * @since 1.6.11
+ */
+ public function imagify_restore_callback() {
+ $context = $this->get_context();
+ $media_id = $this->get_media_id();
+
+ if ( ! $media_id || ! $context ) {
+ imagify_die( __( 'Invalid request', 'imagify' ) );
+ }
+
+ imagify_check_nonce( 'imagify-restore-' . $media_id . '-' . $context );
+
+ if ( ! imagify_get_context( $context )->current_user_can( 'manual-restore', $media_id ) ) {
+ imagify_die();
+ }
+
+ $result = $this->restore_media( $media_id, $context );
+
+ imagify_maybe_redirect( is_wp_error( $result ) ? $result : false );
+
+ if ( is_wp_error( $result ) ) {
+ // Return an error message.
+ $output = $result->get_error_message();
+
+ wp_send_json_error( [ 'html' => $output ] );
+ }
+
+ // Return the optimization button.
+ $output = Imagify_Views::get_instance()->get_template( 'button/optimize', [
+ 'url' => get_imagify_admin_url( 'optimize', array(
+ 'attachment_id' => $media_id,
+ 'context' => $context,
+ ) ),
+ ] );
+
+ wp_send_json_success( [ 'html' => $output ] );
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** CUSTOM FOLDERS OPTIMIZATION CALLBACKS =================================================== */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Optimize a file.
+ *
+ * @since 1.7
+ */
+ public function imagify_optimize_file_callback() {
+ imagify_check_nonce( 'imagify_optimize_file' );
+
+ $media_id = $this->get_media_id( 'GET', 'id' );
+
+ if ( ! $media_id ) {
+ imagify_die( __( 'Invalid request', 'imagify' ) );
+ }
+
+ if ( ! imagify_get_context( 'custom-folders' )->current_user_can( 'manual-optimize', $media_id ) ) {
+ imagify_die();
+ }
+
+ $result = $this->optimize_media( $media_id, 'custom-folders' );
+
+ imagify_maybe_redirect( is_wp_error( $result ) ? $result : false );
+
+ if ( is_wp_error( $result ) ) {
+ // Return an error message.
+ wp_send_json_error( $result->get_error_message() );
+ }
+
+ wp_send_json_success();
+ }
+
+ /**
+ * Re-optimize a file.
+ *
+ * @since 1.7
+ */
+ public function imagify_reoptimize_file_callback() {
+ imagify_check_nonce( 'imagify_reoptimize_file' );
+
+ $media_id = $this->get_media_id( 'GET', 'id' );
+
+ if ( ! $media_id ) {
+ imagify_die( __( 'Invalid request', 'imagify' ) );
+ }
+
+ if ( ! imagify_get_context( 'custom-folders' )->current_user_can( 'manual-optimize', $media_id ) ) {
+ imagify_die();
+ }
+
+ $level = $this->get_optimization_level( 'GET', 'level' );
+
+ $result = $this->reoptimize_media( $media_id, 'custom-folders', $level );
+
+ imagify_maybe_redirect( is_wp_error( $result ) ? $result : false );
+
+ if ( is_wp_error( $result ) ) {
+ // Return an error message.
+ wp_send_json_error( $result->get_error_message() );
+ }
+
+ wp_send_json_success();
+ }
+
+ /**
+ * Restore a file.
+ *
+ * @since 1.7
+ */
+ public function imagify_restore_file_callback() {
+ imagify_check_nonce( 'imagify_restore_file' );
+
+ $media_id = $this->get_media_id( 'GET', 'id' );
+
+ if ( ! $media_id ) {
+ imagify_die( __( 'Invalid request', 'imagify' ) );
+ }
+
+ if ( ! imagify_get_context( 'custom-folders' )->current_user_can( 'manual-restore', $media_id ) ) {
+ imagify_die();
+ }
+
+ $result = $this->restore_media( $media_id, 'custom-folders' );
+
+ imagify_maybe_redirect( is_wp_error( $result ) ? $result : false );
+
+ if ( is_wp_error( $result ) ) {
+ // Return an error message.
+ wp_send_json_error( $result->get_error_message() );
+ }
+
+ $process = imagify_get_optimization_process( $media_id, 'custom-folders' );
+ $this->file_optimization_output( $process );
+ }
+
+ /**
+ * Check if a file has been modified, and update the database accordingly.
+ *
+ * @since 1.7
+ */
+ public function imagify_refresh_file_modified_callback() {
+ imagify_check_nonce( 'imagify_refresh_file_modified' );
+
+ $media_id = $this->get_media_id( 'GET', 'id' );
+
+ if ( ! $media_id ) {
+ imagify_die( __( 'Invalid request', 'imagify' ) );
+ }
+
+ if ( ! imagify_get_context( 'custom-folders' )->current_user_can( 'manual-optimize', $media_id ) ) {
+ imagify_die();
+ }
+
+ $process = imagify_get_optimization_process( $media_id, 'custom-folders' );
+ $result = Imagify_Custom_Folders::refresh_file( $process );
+
+ if ( is_wp_error( $result ) ) {
+ // The media is not valid or has been removed from the database.
+ $message = $result->get_error_message();
+
+ imagify_maybe_redirect( $message );
+
+ wp_send_json_error( array(
+ 'row' => $message,
+ ) );
+ }
+
+ imagify_maybe_redirect();
+
+ // Return some HTML to the ajax call.
+ $this->file_optimization_output( $process );
+ }
+
+ /**
+ * Look for new files in custom folders.
+ *
+ * @since 1.7
+ */
+ public function imagify_scan_custom_folders_callback() {
+ imagify_check_nonce( 'imagify_scan_custom_folders' );
+
+ if ( ! imagify_get_context( 'custom-folders' )->current_user_can( 'optimize' ) ) {
+ imagify_die();
+ }
+
+ $folder = (int) filter_input( INPUT_GET, 'folder', FILTER_VALIDATE_INT );
+
+ if ( $folder > 0 ) {
+ // A specific custom folder (selected or not).
+ $folders_db = Imagify_Folders_DB::get_instance();
+ $folders_key = $folders_db->get_primary_key();
+ $folder = $folders_db->get( $folder );
+
+ if ( ! $folder ) {
+ // This should not happen.
+ imagify_maybe_redirect( __( 'This folder is not in the database.', 'imagify' ) );
+ }
+
+ $folder['folder_path'] = Imagify_Files_Scan::remove_placeholder( $folder['path'] );
+
+ $folders = array(
+ $folder[ $folders_key ] => $folder,
+ );
+
+ Imagify_Custom_Folders::get_files_from_folders( $folders, array(
+ 'add_inactive_folder_files' => true,
+ ) );
+
+ imagify_maybe_redirect();
+ }
+
+ // All selected custom folders.
+ $folders = Imagify_Custom_Folders::get_folders( array(
+ 'active' => true,
+ ) );
+ Imagify_Custom_Folders::get_files_from_folders( $folders );
+
+ imagify_maybe_redirect();
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** SETTINGS PAGE CALLBACKS ================================================================= */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Check if the backup directory is writable.
+ * This is used to display an error message in the plugin's settings page.
+ *
+ * @since 1.6.11
+ */
+ public function imagify_check_backup_dir_is_writable_callback() {
+ imagify_check_nonce( 'imagify_check_backup_dir_is_writable' );
+
+ if ( ! imagify_get_context( 'wp' )->current_user_can( 'manage' ) ) {
+ imagify_die();
+ }
+
+ wp_send_json_success( array(
+ 'is_writable' => (int) Imagify_Requirements::attachments_backup_dir_is_writable(),
+ ) );
+ }
+
+ /**
+ * Get files and folders that are direct children of a given folder.
+ *
+ * @since 1.7
+ */
+ public function imagify_get_files_tree_callback() {
+ imagify_check_nonce( 'get-files-tree' );
+
+ if ( ! imagify_get_context( 'custom-folders' )->current_user_can( 'manage' ) ) {
+ imagify_die();
+ }
+
+ if ( ! isset( $_POST['folder'] ) || '' === $_POST['folder'] ) {
+ imagify_die( __( 'Invalid request', 'imagify' ) );
+ }
+
+ $folder = wp_unslash( $_POST['folder'] );
+ $folder = trailingslashit( sanitize_text_field( $folder ) );
+ $folder = realpath( $this->filesystem->get_site_root() . ltrim( $folder, '/' ) );
+
+ if ( ! $folder ) {
+ imagify_die( __( 'This folder doesn\'t exist.', 'imagify' ) );
+ }
+
+ if ( ! $this->filesystem->is_dir( $folder ) ) {
+ imagify_die( __( 'This file is not a folder.', 'imagify' ) );
+ }
+
+ $folder = $this->filesystem->normalize_dir_path( $folder );
+
+ if ( Imagify_Files_Scan::is_path_forbidden( $folder ) ) {
+ imagify_die( __( 'This folder is not allowed.', 'imagify' ) );
+ }
+
+ // Finally we made all our validations.
+ $selected = ! empty( $_POST['selected'] ) && is_array( $_POST['selected'] ) ? array_flip( wp_unslash( $_POST['selected'] ) ) : array();
+ $views = Imagify_Views::get_instance();
+ $output = '';
+
+ if ( $this->filesystem->is_site_root( $folder ) ) {
+ $output .= $views->get_template( 'part-settings-files-tree-row', array(
+ 'relative_path' => '/',
+ // Value #///# Label.
+ 'checkbox_value' => '{{ROOT}}/#///#' . esc_attr__( 'Site\'s root', 'imagify' ),
+ 'checkbox_id' => 'ABSPATH',
+ 'checkbox_selected' => isset( $selected['{{ROOT}}/'] ),
+ 'label' => __( 'Site\'s root', 'imagify' ),
+ 'no_button' => true,
+ ) );
+ }
+
+ $dir = new DirectoryIterator( $folder );
+ $dir = new Imagify_Files_Iterator( $dir );
+ $images = 0;
+
+ foreach ( new IteratorIterator( $dir ) as $file ) {
+ if ( ! $file->isDir() ) {
+ ++$images;
+ continue;
+ }
+
+ $folder_path = trailingslashit( $file->getPathname() );
+ $relative_path = $this->filesystem->make_path_relative( $folder_path );
+ $placeholder = Imagify_Files_Scan::add_placeholder( $folder_path );
+
+ $output .= $views->get_template( 'part-settings-files-tree-row', array(
+ 'relative_path' => esc_attr( $relative_path ),
+ // Value #///# Label.
+ 'checkbox_value' => esc_attr( $placeholder ) . '#///#' . esc_attr( $relative_path ),
+ 'checkbox_id' => sanitize_html_class( $placeholder ),
+ 'checkbox_selected' => isset( $selected[ $placeholder ] ),
+ 'label' => $this->filesystem->file_name( $folder_path ),
+ ) );
+ }
+
+ if ( $images ) {
+ /* translators: %s is a formatted number, dont use %d. */
+ $output .= ' ' . sprintf( _n( '%s Media File', '%s Media Files', $images, 'imagify' ), number_format_i18n( $images ) ) . ' ';
+ }
+
+ if ( ! $output ) {
+ $output .= '' . __( 'No optimizable files', 'imagify' ) . ' ';
+ }
+
+ wp_send_json_success( $output );
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** IMAGIFY ACCOUNT CALLBACKS =============================================================== */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Create a new Imagify account.
+ *
+ * @since 1.6.11
+ */
+ public function imagify_signup_callback() {
+ imagify_check_nonce( 'imagify-signup', 'imagifysignupnonce' );
+
+ if ( ! imagify_get_context( 'wp' )->current_user_can( 'manage' ) ) {
+ imagify_die();
+ }
+
+ if ( empty( $_GET['email'] ) ) {
+ imagify_die( __( 'Empty email address.', 'imagify' ) );
+ }
+
+ $email = wp_unslash( $_GET['email'] );
+
+ if ( ! is_email( $email ) ) {
+ imagify_die( __( 'Not a valid email address.', 'imagify' ) );
+ }
+
+ $data = array(
+ 'email' => $email,
+ 'password' => wp_generate_password( 12, false ),
+ 'lang' => imagify_get_locale(),
+ );
+
+ $response = add_imagify_user( $data );
+
+ if ( is_wp_error( $response ) ) {
+ imagify_die( $response );
+ }
+
+ wp_send_json_success();
+ }
+
+ /**
+ * Check the API key validity.
+ *
+ * @since 1.6.11
+ */
+ public function imagify_check_api_key_validity_callback() {
+ imagify_check_nonce( 'imagify-check-api-key', 'imagifycheckapikeynonce' );
+
+ if ( ! imagify_get_context( 'wp' )->current_user_can( 'manage' ) ) {
+ imagify_die();
+ }
+
+ if ( empty( $_GET['api_key'] ) ) {
+ imagify_die( __( 'Empty API key.', 'imagify' ) );
+ }
+
+ $api_key = wp_unslash( $_GET['api_key'] );
+ $response = get_imagify_status( $api_key );
+
+ if ( is_wp_error( $response ) ) {
+ imagify_die( $response );
+ }
+
+ update_imagify_option( 'api_key', $api_key );
+
+ wp_send_json_success();
+ }
+
+ /**
+ * Get pricings from API for Onetime and Plans at the same time.
+ *
+ * @since 1.6.11
+ */
+ public function imagify_get_prices_callback() {
+ imagify_check_nonce( 'imagify_get_pricing_' . get_current_user_id(), 'imagifynonce' );
+
+ if ( ! imagify_get_context( 'wp' )->current_user_can( 'manage' ) ) {
+ imagify_die();
+ }
+
+ $prices_all = get_imagify_all_prices();
+
+ if ( is_wp_error( $prices_all ) ) {
+ imagify_die( $prices_all );
+ }
+
+ if ( ! is_object( $prices_all ) ) {
+ imagify_die( __( 'Wrongly formatted response from our server.', 'imagify' ) );
+ }
+
+ wp_send_json_success( array(
+ 'monthlies' => $prices_all->Plans,
+ ) );
+ }
+
+ /**
+ * Check Coupon code on modal popin.
+ *
+ * @since 1.6.11
+ */
+ public function imagify_check_coupon_callback() {
+ imagify_check_nonce( 'imagify_get_pricing_' . get_current_user_id(), 'imagifynonce' );
+
+ if ( ! imagify_get_context( 'wp' )->current_user_can( 'manage' ) ) {
+ imagify_die();
+ }
+
+ if ( empty( $_POST['coupon'] ) ) {
+ wp_send_json_success( array(
+ 'success' => false,
+ 'detail' => __( 'Coupon is empty.', 'imagify' ),
+ ) );
+ }
+
+ $coupon = wp_unslash( $_POST['coupon'] );
+ $coupon = check_imagify_coupon_code( $coupon );
+
+ if ( is_wp_error( $coupon ) ) {
+ imagify_die( $coupon );
+ }
+
+ wp_send_json_success( imagify_translate_api_message( $coupon ) );
+ }
+
+ /**
+ * Get current discount promotion to display information on payment modal.
+ *
+ * @since 1.6.11
+ */
+ public function imagify_get_discount_callback() {
+ imagify_check_nonce( 'imagify_get_pricing_' . get_current_user_id(), 'imagifynonce' );
+
+ if ( ! imagify_get_context( 'wp' )->current_user_can( 'manage' ) ) {
+ imagify_die();
+ }
+
+ wp_send_json_success( imagify_translate_api_message( check_imagify_discount() ) );
+ }
+
+ /**
+ * Get estimated sizes from the WordPress library.
+ *
+ * @since 1.6.11
+ */
+ public function imagify_get_images_counts_callback() {
+ imagify_check_nonce( 'imagify_get_pricing_' . get_current_user_id(), 'imagifynonce' );
+
+ if ( ! imagify_get_context( 'wp' )->current_user_can( 'manage' ) ) {
+ imagify_die();
+ }
+
+ $raw_total_size_in_library = imagify_calculate_total_size_images_library() + Imagify_Files_Stats::get_overall_original_size();
+ $raw_average_per_month = imagify_calculate_average_size_images_per_month() + Imagify_Files_Stats::calculate_average_size_per_month();
+
+ Imagify_Data::get_instance()->set( array(
+ 'total_size_images_library' => $raw_total_size_in_library,
+ 'average_size_images_per_month' => $raw_average_per_month,
+ ) );
+
+ wp_send_json_success( array(
+ 'total_library_size' => array(
+ 'raw' => $raw_total_size_in_library,
+ 'human' => imagify_size_format( $raw_total_size_in_library ),
+ ),
+ 'average_month_size' => array(
+ 'raw' => $raw_average_per_month,
+ 'human' => imagify_size_format( $raw_average_per_month ),
+ ),
+ ) );
+ }
+
+ /**
+ * Estimate sizes and update the options values for them.
+ *
+ * @since 1.6.11
+ */
+ public function imagify_update_estimate_sizes_callback() {
+ imagify_check_nonce( 'update_estimate_sizes' );
+
+ if ( ! imagify_get_context( 'wp' )->current_user_can( 'manage' ) ) {
+ imagify_die();
+ }
+
+ $raw_total_size_in_library = imagify_calculate_total_size_images_library() + Imagify_Files_Stats::get_overall_original_size();
+ $raw_average_per_month = imagify_calculate_average_size_images_per_month() + Imagify_Files_Stats::calculate_average_size_per_month();
+
+ Imagify_Data::get_instance()->set( array(
+ 'total_size_images_library' => $raw_total_size_in_library,
+ 'average_size_images_per_month' => $raw_average_per_month,
+ ) );
+
+ die( 1 );
+ }
+
+ /**
+ * Get the Imagify User data.
+ *
+ * @since 1.7
+ */
+ public function imagify_get_user_data_callback() {
+ imagify_check_nonce( 'imagify_get_user_data' );
+
+ if ( ! imagify_get_context( 'wp' )->current_user_can( 'manage' ) ) {
+ imagify_die();
+ }
+
+ $user = imagify_cache_user();
+
+ if ( ! $user || ! $user->id ) {
+ imagify_die( __( 'Couldn\'t get user data.', 'imagify' ) );
+ }
+
+ // Remove useless sensitive data.
+ unset( $user->email );
+
+ if ( ! $user->get_percent_unconsumed_quota ) {
+ $user->best_plan_title = __( 'Oops, It\'s Over!', 'imagify' );
+ } elseif ( $user->get_percent_unconsumed_quota <= 20 ) {
+ $user->best_plan_title = __( 'Oops, It\'s almost over!', 'imagify' );
+ } else {
+ $user->best_plan_title = __( 'You\'re new to Imagify?', 'imagify' );
+ }
+
+ wp_send_json_success( $user );
+ }
+
+ /**
+ * Delete the Imagify User data cache.
+ *
+ * @since 1.9.5
+ */
+ public function imagify_delete_user_data_cache_callback() {
+ imagify_check_nonce( 'imagify_delete_user_data_cache' );
+
+ if ( ! imagify_get_context( 'wp' )->current_user_can( 'manage' ) ) {
+ imagify_die();
+ }
+
+ imagify_delete_cached_user();
+
+ wp_send_json_success();
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** VARIOUS CALLBACKS ======================================================================= */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Bridge between XML-RPC and actions triggered by imagify_do_async_job().
+ * When XML-RPC is used, a current user is set, but no cookies are set, so they cannot be sent with the request. Instead we stored the user ID in a transient.
+ *
+ * @since 1.6.11
+ * @see imagify_do_async_job()
+ */
+ public function nopriv_imagify_rpc_callback() {
+ if ( empty( $_POST['imagify_rpc_action'] ) || empty( $_POST['imagify_rpc_id'] ) ) {
+ imagify_die( __( 'Invalid request', 'imagify' ) );
+ }
+
+ $action = wp_unslash( $_POST['imagify_rpc_action'] ); // WPCS: CSRF ok.
+
+ if ( 32 !== strlen( $action ) ) {
+ imagify_die( __( 'Invalid request', 'imagify' ) );
+ }
+
+ // Not necessary but just in case, whitelist the original action.
+ $actions = array_flip( $this->ajax_only_actions );
+ unset( $actions['nopriv_imagify_rpc'] );
+
+ if ( ! isset( $actions[ $action ] ) ) {
+ imagify_die( __( 'Invalid request', 'imagify' ) );
+ }
+
+ // Get the user ID.
+ $rpc_id = sanitize_key( $_POST['imagify_rpc_id'] );
+ $user_id = absint( get_transient( 'imagify_rpc_' . $rpc_id ) );
+ $user = $user_id ? get_userdata( $user_id ) : false;
+
+ delete_transient( 'imagify_rpc_' . $rpc_id );
+
+ if ( ! $user || ! $user->exists() ) {
+ imagify_die( __( 'Invalid request', 'imagify' ) );
+ }
+
+ // The current user must be set before verifying the nonce.
+ wp_set_current_user( $user_id );
+
+ imagify_check_nonce( 'imagify_rpc_' . $rpc_id, 'imagify_rpc_nonce' );
+
+ // Trigger the action we originally wanted.
+ $_POST['action'] = $action;
+ unset( $_POST['imagify_rpc_action'], $_POST['imagify_rpc_id'], $_POST['imagify_rpc_nonce'] );
+
+ /** This hook is documented in wp-admin/admin-ajax.php. */
+ do_action( 'wp_ajax_' . $action );
+ }
+
+ /**
+ * Store the "closed" status of the ads.
+ *
+ * @since 1.7
+ */
+ public function imagify_dismiss_ad_callback() {
+ imagify_check_nonce( 'imagify-dismiss-ad' );
+
+ if ( ! imagify_get_context( 'wp' )->current_user_can( 'manage' ) ) {
+ imagify_die();
+ }
+
+ $notice = htmlspecialchars( wp_unslash( $_GET['ad'] ) );
+
+ if ( ! $notice ) {
+ imagify_maybe_redirect();
+ wp_send_json_error();
+ }
+
+ $user_id = get_current_user_id();
+ $notices = get_user_meta( $user_id, '_imagify_ignore_ads', true );
+ $notices = $notices && is_array( $notices ) ? array_flip( $notices ) : array();
+
+ if ( isset( $notices[ $notice ] ) ) {
+ imagify_maybe_redirect();
+ wp_send_json_success();
+ }
+
+ $notices = array_flip( $notices );
+ $notices[] = $notice;
+ $notices = array_filter( $notices );
+ $notices = array_values( $notices );
+
+ update_user_meta( $user_id, '_imagify_ignore_ads', $notices );
+
+ imagify_maybe_redirect();
+ wp_send_json_success();
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** VARIOUS HELPERS ========================================================================= */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Get the submitted optimization level.
+ *
+ * @since 1.7
+ * @since 1.9 Added $method and $parameter parameters.
+ *
+ * @param string $method The method used: 'GET' (default), or 'POST'.
+ * @param string $parameter The name of the parameter to look for.
+ * @return int
+ */
+ public function get_optimization_level( $method = 'GET', $parameter = 'optimization_level' ) {
+ $method = 'POST' === $method ? INPUT_POST : INPUT_GET;
+ $level = filter_input( $method, $parameter );
+
+ if ( ! is_numeric( $level ) || $level < 0 || $level > 2 ) {
+ if ( get_imagify_option( 'lossless' ) ) {
+ return 0;
+ }
+
+ return get_imagify_option( 'optimization_level' );
+ }
+
+ return (int) $level;
+ }
+
+ /**
+ * Get the submitted context.
+ *
+ * @since 1.9
+ *
+ * @param string $method The method used: 'GET' (default), or 'POST'.
+ * @param string $parameter The name of the parameter to look for.
+ * @return string
+ */
+ public function get_context( $method = 'GET', $parameter = 'context' ) {
+ $context = 'POST' === $method ? wp_unslash( $_POST[ $parameter ] ) : wp_unslash( $_GET[ $parameter ] ); // phpcs:ignore WordPress.Security.NonceVerification.Missing, WordPress.Security.NonceVerification.Recommended
+ $context = htmlspecialchars( $context );
+
+ return imagify_sanitize_context( $context );
+ }
+
+ /**
+ * Get the submitted media ID.
+ *
+ * @since 1.9
+ *
+ * @param string $method The method used: 'GET' (default), or 'POST'.
+ * @param string $parameter The name of the parameter to look for.
+ * @return int
+ */
+ public function get_media_id( $method = 'GET', $parameter = 'attachment_id' ) {
+ $method = 'POST' === $method ? INPUT_POST : INPUT_GET;
+ $media_id = filter_input( $method, $parameter );
+
+ if ( ! is_numeric( $media_id ) || $media_id < 0 ) {
+ return 0;
+ }
+
+ return (int) $media_id;
+ }
+
+ /**
+ * Get the submitted folder_type.
+ *
+ * @since 1.9
+ *
+ * @param string $method The method used: 'GET' (default), or 'POST'.
+ * @param string $parameter The name of the parameter to look for.
+ *
+ * @return string
+ */
+ public function get_folder_type( $method = 'GET', $parameter = 'folder_type' ) {
+ $folder_type = 'POST' === $method ? wp_unslash( $_POST[ $parameter ] ) : wp_unslash( $_GET[ $parameter ] ); // phpcs:ignore WordPress.Security.NonceVerification.Missing, WordPress.Security.NonceVerification.Recommended
+
+ return htmlspecialchars( $folder_type );
+ }
+
+ /**
+ * Get the submitted imagify action.
+ *
+ * @since 1.9
+ *
+ * @param string $method The method used: 'GET' (default), or 'POST'.
+ * @param string $parameter The name of the parameter to look for.
+ *
+ * @return string
+ */
+ public function get_imagify_action( $method = 'GET', $parameter = 'imagify_action' ) {
+ $action = 'POST' === $method ? wp_unslash( $_POST[ $parameter ] ) : wp_unslash( $_GET[ $parameter ] ); // phpcs:ignore WordPress.Security.NonceVerification.Missing, WordPress.Security.NonceVerification.Recommended
+ $action = htmlspecialchars( $action );
+
+ return $action ? $action : 'optimize';
+ }
+
+ /**
+ * Get the Bulk class name depending on a context.
+ *
+ * @since 1.9
+ *
+ * @param string $context The context name. Default values are 'wp' and 'custom-folders'.
+ * @return string The Bulk class name.
+ */
+ public function get_bulk_class_name( $context ) {
+ switch ( $context ) {
+ case 'wp':
+ $class_name = '\\Imagify\\Bulk\\WP';
+ break;
+
+ case 'custom-folders':
+ $class_name = '\\Imagify\\Bulk\\CustomFolders';
+ break;
+
+ default:
+ $class_name = '\\Imagify\\Bulk\\Noop';
+ }
+
+ /**
+ * Filter the name of the class to use for bulk process.
+ *
+ * @since 1.9
+ *
+ * @param int $class_name The class name.
+ * @param string $context The context name.
+ */
+ $class_name = apply_filters( 'imagify_bulk_class_name', $class_name, $context );
+
+ return '\\' . ltrim( $class_name, '\\' );
+ }
+
+ /**
+ * Get the Bulk instance depending on a context.
+ *
+ * @since 1.9
+ *
+ * @param string $context The context name. Default values are 'wp' and 'custom-folders'.
+ * @return BulkInterface The optimization process instance.
+ */
+ public function get_bulk_instance( $context ) {
+ $class_name = $this->get_bulk_class_name( $context );
+ return new $class_name();
+ }
+
+ /**
+ * Check if the user has a valid account and has quota. Die on failure.
+ *
+ * @since 1.7
+ */
+ public function check_can_optimize() {
+ if ( ! Imagify_Requirements::is_api_key_valid() ) {
+ if ( defined( 'DOING_AJAX' ) && DOING_AJAX ) {
+ wp_send_json_error( array( 'message' => 'invalid-api-key' ) );
+ }
+
+ imagify_die( __( 'Your API key is not valid!', 'imagify' ) );
+ }
+
+ if ( Imagify_Requirements::is_over_quota() ) {
+ if ( defined( 'DOING_AJAX' ) && DOING_AJAX ) {
+ wp_send_json_error( array( 'message' => 'over-quota' ) );
+ }
+
+ imagify_die( __( 'You have used all your credits!', 'imagify' ) );
+ }
+ }
+
+ /**
+ * Get a media columns for the "Other Media" page.
+ *
+ * @since 1.9
+ *
+ * @param object $process A \Imagify\Optimization\Process\CustomFolders object.
+ * @param object $list_table A Imagify_Files_List_Table object.
+ * @return array An array of HTML, keyed by column name.
+ */
+ public function get_media_columns( $process, $list_table ) {
+ $item = (object) [ 'process' => $process ];
+
+ return [
+ 'folder' => $list_table->get_column( 'folder', $item ),
+ 'optimization' => $list_table->get_column( 'optimization', $item ),
+ 'status' => $list_table->get_column( 'status', $item ),
+ 'optimization_level' => $list_table->get_column( 'optimization_level', $item ),
+ 'actions' => $list_table->get_column( 'actions', $item ),
+ 'title' => $list_table->get_column( 'title', $item ), // This one must remain after the "optimization" column, otherwize the data for the comparison tool won't be up-to-date.
+ ];
+ }
+
+ /**
+ * After a file optimization, restore, or whatever, redirect the user or output HTML for ajax.
+ *
+ * @since 1.7
+ * @since 1.9 Removed parameter $result.
+ * @since 1.9 Added $folder in the returned JSON.
+ *
+ * @param object $process A \Imagify\Optimization\Process\CustomFolders object.
+ */
+ protected function file_optimization_output( $process ) {
+ $list_table = new Imagify_Files_List_Table( [
+ 'screen' => 'imagify-files',
+ ] );
+
+ wp_send_json_success( [
+ 'columns' => $this->get_media_columns( $process, $list_table ),
+ ] );
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/inc/classes/class-imagify-assets.php b/wp/wp-content/plugins/imagify/inc/classes/class-imagify-assets.php
new file mode 100644
index 00000000..7d5e1fc2
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/classes/class-imagify-assets.php
@@ -0,0 +1,797 @@
+is_admin_bar_item_showing() ) {
+ return;
+ }
+
+ $this->register_style( 'admin-bar' );
+ $this->register_script( 'admin-bar', 'admin-bar', [ 'jquery' ] );
+
+ $this->enqueue_assets( 'admin-bar' )->localize( 'imagifyAdminBar' );
+ }
+
+ /**
+ * Register stylesheets and scripts for the administration area.
+ *
+ * @since 1.6.10
+ */
+ public function register_styles_and_scripts() {
+ static $done = false;
+
+ if ( $done ) {
+ return;
+ }
+ $done = true;
+
+ /**
+ * 3rd Party Styles.
+ */
+ $this->register_style( 'sweetalert-core', 'sweetalert2', [], '4.6.6' );
+
+ /**
+ * Imagify Styles.
+ */
+ $this->register_style( 'sweetalert', 'sweetalert-custom', [ 'sweetalert-core' ] );
+
+ $this->register_style( 'admin-bar' );
+
+ $this->register_style( 'admin' );
+
+ $this->register_style( 'notices', 'notices', [ 'admin' ] ); // Needs SweetAlert on some cases.
+
+ $this->register_style( 'twentytwenty', 'twentytwenty', [ 'admin' ] );
+
+ $this->register_style( 'pricing-modal', 'pricing-modal', [ 'admin' ] );
+
+ $this->register_style( 'bulk', 'bulk', [ 'sweetalert', 'admin' ] );
+
+ $this->register_style( 'options', 'options', [ 'sweetalert', 'admin' ] );
+
+ $this->register_style( 'files-list', 'files-list', [ 'admin' ] );
+
+ /**
+ * 3rd Party Scripts.
+ */
+ $this->register_script( 'promise-polyfill', 'es6-promise.auto', [], '4.1.1' );
+
+ $this->register_script( 'sweetalert', 'sweetalert2', [ 'promise-polyfill' ], '4.6.6' )->localize( 'imagifySwal' );
+
+ $this->register_bud_script( 'runtime', 'runtime' );
+ $this->register_bud_script( 'chart', 'chart', [ 'runtime' ], '4.4.0' );
+
+ $this->register_script( 'event-move', 'jquery.event.move', [ 'jquery' ], '2.0.1' );
+
+ /**
+ * Imagify Scripts.
+ */
+ $this->register_script( 'admin-bar', 'admin-bar', [ 'jquery' ] )->defer_localization( 'imagifyAdminBar' );
+
+ $this->register_script( 'admin', 'admin', [ 'jquery' ] );
+
+ $this->register_script( 'notices', 'notices', [ 'jquery', 'admin' ] )->defer_localization( 'imagifyNotices' ); // Needs SweetAlert on some cases.
+
+ $this->register_script( 'twentytwenty', 'jquery.twentytwenty', [ 'jquery', 'event-move', 'chart', 'admin' ] )->defer_localization( 'imagifyTTT' );
+
+ $this->register_script( 'beat', 'beat', [ 'jquery' ] )->localize( 'imagifybeatSettings' );
+
+ $this->register_script( 'media-modal', 'media-modal', [ 'jquery', 'beat', 'underscore', 'chart', 'admin' ] )->localize( 'imagifyModal' );
+
+ $this->register_script( 'pricing-modal', 'pricing-modal', [ 'jquery', 'admin' ] )->defer_localization( 'imagifyPricingModal' );
+
+ $this->register_script( 'library', 'library', [ 'jquery', 'media-modal' ] )->defer_localization( 'imagifyLibrary' );
+
+ $this->register_script( 'async', 'imagify-gulp' );
+
+ $this->register_bud_script( 'bulk', 'bulk', [ 'jquery', 'beat', 'underscore', 'chart', 'sweetalert', 'async', 'admin' ] )->defer_localization( 'imagifyBulk' );
+
+ $this->register_script( 'options', 'options', [ 'jquery', 'beat', 'sweetalert', 'underscore', 'admin' ] )->defer_localization( 'imagifyOptions' );
+
+ $this->register_script( 'files-list', 'files-list', [ 'jquery', 'beat', 'underscore', 'chart', 'admin' ] )->defer_localization( 'imagifyFiles' );
+ }
+
+ /**
+ * Enqueue stylesheets and scripts for the administration area.
+ *
+ * @since 1.6.10
+ */
+ public function enqueue_styles_and_scripts() {
+ static $done = false;
+
+ if ( $done ) {
+ return;
+ }
+ $done = true;
+
+ /*
+ * Register stylesheets and scripts.
+ */
+ $this->register_styles_and_scripts();
+
+ /**
+ * Admin bar.
+ */
+ if ( $this->is_admin_bar_item_showing() ) {
+ $this->enqueue_assets( 'admin-bar' );
+ }
+
+ /**
+ * Notices.
+ */
+ $notices = Notices::get_instance();
+
+ if ( $notices->has_notices() ) {
+ if ( $notices->display_welcome_steps() || $notices->display_wrong_api_key() ) {
+ // This is where we display things about the API key.
+ $this->enqueue_assets( 'sweetalert' );
+ }
+
+ $this->enqueue_assets( 'notices' );
+ }
+
+ /**
+ * Loaded in the library and attachment edition.
+ */
+ if ( imagify_is_screen( 'library' ) || imagify_is_screen( 'attachment' ) ) {
+ $this->enqueue_assets( 'twentytwenty' );
+ }
+
+ /**
+ * Loaded in the library.
+ */
+ if ( imagify_is_screen( 'library' ) ) {
+ $this->enqueue_style( 'admin' )->enqueue_script( 'library' );
+ }
+
+ /**
+ * Loaded in the bulk optimization page.
+ */
+ if ( imagify_is_screen( 'bulk' ) ) {
+ $this->enqueue_assets( [ 'pricing-modal', 'bulk' ] );
+ }
+
+ /*
+ * Loaded in the settings page.
+ */
+ if ( imagify_is_screen( 'imagify-settings' ) ) {
+ $this->enqueue_assets( [ 'sweetalert', 'notices', 'twentytwenty', 'pricing-modal', 'options' ] );
+ }
+
+ /*
+ * Loaded in the files list page.
+ */
+ if ( imagify_is_screen( 'files-list' ) ) {
+ $this->enqueue_assets( [ 'files-list', 'twentytwenty' ] );
+ }
+
+ /**
+ * Triggered after Imagify CSS and JS have been enqueued.
+ *
+ * @since 1.6.10
+ */
+ do_action( 'imagify_assets_enqueued' );
+ }
+
+ /**
+ * Enqueue stylesheets and scripts for the media modal.
+ *
+ * @since 1.6.10
+ */
+ public function enqueue_media_modal() {
+ static $done = false;
+
+ if ( $done ) {
+ return;
+ }
+ $done = true;
+
+ /*
+ * Register stylesheets and scripts.
+ */
+ $this->register_styles_and_scripts();
+
+ $this->enqueue_style( 'admin' )->enqueue_script( 'media-modal' );
+
+ // When the optimization buttons are displayed in the media modal, they are fetched through ajax, so they can’t print the "processing" button template in the footer.
+ Imagify_Views::get_instance()->print_js_template_in_footer( 'button/processing' );
+
+ /**
+ * Triggered after Imagify CSS and JS have been enqueued for the media modal.
+ *
+ * @since 1.6.10
+ */
+ do_action( 'imagify_media_modal_assets_enqueued' );
+ }
+
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** PUBLIC TOOLS ============================================================================ */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Register a style.
+ *
+ * @since 1.6.10
+ *
+ * @param string $handle Name of the stylesheet. Should be unique.
+ * @param string|null $file_name The file name, without the extension. If null, $handle is used.
+ * @param array $dependencies An array of registered stylesheet handles this stylesheet depends on.
+ * @param string|null $version String specifying stylesheet version number. If set to null, the plugin version is used. If SCRIPT_DEBUG is true, a random string is used.
+ * @return object This class instance.
+ */
+ public function register_style( $handle, $file_name = null, $dependencies = [], $version = null ) {
+ // If we register it, it's one of our styles.
+ $this->styles[ $handle ] = 1;
+ $this->current_handle = $handle;
+ $this->current_handle_type = 'css';
+
+ $file_name = $file_name ? $file_name : $handle;
+ $version = $version ? $version : IMAGIFY_VERSION;
+ $version = $this->is_debug() ? self::$version : $version;
+ $extension = $this->is_debug() ? '.css' : '.min.css';
+ $handle = self::CSS_PREFIX . $handle;
+ $dependencies = $this->prefix_dependencies( $dependencies, 'css' );
+
+ wp_register_style(
+ $handle,
+ IMAGIFY_URL . 'assets/css/' . $file_name . $extension,
+ $dependencies,
+ $version
+ );
+
+ return $this;
+ }
+
+ /**
+ * Enqueue a style.
+ *
+ * @since 1.6.10
+ *
+ * @param string|array $handles Name of the stylesheet. Should be unique. Can be an array to enqueue several stylesheets.
+ * @return object This class instance.
+ */
+ public function enqueue_style( $handles ) {
+ $handles = (array) $handles;
+
+ foreach ( $handles as $handle ) {
+ $this->current_handle = $handle;
+ $this->current_handle_type = 'css';
+
+ if ( ! empty( $this->styles[ $handle ] ) ) {
+ // If we registered it, it's one of our styles.
+ $handle = self::CSS_PREFIX . $handle;
+ }
+
+ wp_enqueue_style( $handle );
+ }
+
+ return $this;
+ }
+
+ /**
+ * Dequeue a style.
+ *
+ * @since 1.6.10
+ *
+ * @param string|array $handles Name of the stylesheet. Should be unique. Can be an array to dequeue several stylesheets.
+ * @return object This class instance.
+ */
+ public function dequeue_style( $handles ) {
+ $handles = (array) $handles;
+
+ foreach ( $handles as $handle ) {
+ $this->current_handle = $handle;
+ $this->current_handle_type = 'css';
+
+ if ( ! empty( $this->styles[ $handle ] ) ) {
+ // If we registered it, it's one of our styles.
+ $handle = self::CSS_PREFIX . $handle;
+ }
+
+ wp_dequeue_style( $handle );
+ }
+
+ return $this;
+ }
+
+ /**
+ * Register a script.
+ *
+ * @since 1.6.10
+ *
+ * @param string $handle Name of the script. Should be unique.
+ * @param string|null $file_name The file name, without the extension. If null, $handle is used.
+ * @param array $dependencies An array of registered script handles this script depends on.
+ * @param string|null $version String specifying script version number. If set to null, the plugin version is used. If SCRIPT_DEBUG is true, a random string is used.
+ * @return object This class instance.
+ */
+ public function register_script( $handle, $file_name = null, $dependencies = [], $version = null ) {
+ // If we register it, it's one of our scripts.
+ $this->scripts[ $handle ] = 1;
+ // Set the current handler and handler type.
+ $this->current_handle = $handle;
+ $this->current_handle_type = 'js';
+
+ $file_name = $file_name ? $file_name : $handle;
+ $version = $version ? $version : IMAGIFY_VERSION;
+ $version = $this->is_debug() ? self::$version : $version;
+ $extension = $this->is_debug() ? '.js' : '.min.js';
+ $handle = self::JS_PREFIX . $handle;
+ $dependencies = $this->prefix_dependencies( $dependencies );
+
+ wp_register_script(
+ $handle,
+ IMAGIFY_URL . 'assets/js/' . $file_name . $extension,
+ $dependencies,
+ $version,
+ true
+ );
+
+ return $this;
+ }
+
+ /**
+ * Register a script.
+ *
+ * @since 1.6.10
+ *
+ * @param string $handle Name of the script. Should be unique.
+ * @param string|null $file_name The file name, without the extension. If null, $handle is used.
+ * @param array $dependencies An array of registered script handles this script depends on.
+ * @param string|null $version String specifying script version number. If set to null, the plugin version is used. If SCRIPT_DEBUG is true, a random string is used.
+ * @return object This class instance.
+ */
+ public function register_bud_script( $handle, $file_name = null, $dependencies = [], $version = null ) {
+ // If we register it, it's one of our scripts.
+ $this->scripts[ $handle ] = 1;
+ // Set the current handler and handler type.
+ $this->current_handle = $handle;
+ $this->current_handle_type = 'js';
+
+ $file_name = $file_name ? $file_name : $handle;
+ $version = $version ? $version : IMAGIFY_VERSION;
+ $version = $this->is_debug() ? self::$version : $version;
+ $extension = '.js';
+ $handle = self::JS_PREFIX . $handle;
+ $dependencies = $this->prefix_dependencies( $dependencies );
+
+ wp_register_script(
+ $handle,
+ IMAGIFY_URL . 'assets/admin/js/' . $file_name . $extension,
+ $dependencies,
+ $version,
+ true
+ );
+
+ return $this;
+ }
+
+ /**
+ * Enqueue a script.
+ *
+ * @since 1.6.10
+ *
+ * @param string|array $handles Name of the script. Should be unique. Can be an array to enqueue several scripts.
+ * @return object This class instance.
+ */
+ public function enqueue_script( $handles ) {
+ $handles = (array) $handles;
+
+ foreach ( $handles as $handle ) {
+ // Enqueue the corresponding style.
+ if ( ! empty( $this->styles[ $handle ] ) ) {
+ $this->enqueue_style( $handle );
+ }
+
+ $this->current_handle = $handle;
+ $this->current_handle_type = 'js';
+
+ if ( ! empty( $this->scripts[ $handle ] ) ) {
+ // If we registered it, it's one of our scripts.
+ $handle = self::JS_PREFIX . $handle;
+ }
+
+ wp_enqueue_script( $handle );
+
+ // Deferred localization.
+ if ( ! empty( $this->deferred_localizations[ $this->current_handle ] ) ) {
+ array_map( [ $this, 'localize' ], $this->deferred_localizations[ $this->current_handle ] );
+ unset( $this->deferred_localizations[ $this->current_handle ] );
+ }
+ }
+
+ return $this;
+ }
+
+ /**
+ * Dequeue a script.
+ *
+ * @since 1.6.10
+ *
+ * @param string|array $handles Name of the script. Should be unique. Can be an array to dequeue several scripts.
+ * @return object This class instance.
+ */
+ public function dequeue_script( $handles ) {
+ $handles = (array) $handles;
+
+ foreach ( $handles as $handle ) {
+ // Enqueue the corresponding style.
+ if ( ! empty( $this->styles[ $handle ] ) ) {
+ $this->dequeue_style( $handle );
+ }
+
+ $this->current_handle = $handle;
+ $this->current_handle_type = 'js';
+
+ if ( ! empty( $this->scripts[ $handle ] ) ) {
+ // If we registered it, it's one of our scripts.
+ $handle = self::JS_PREFIX . $handle;
+ }
+
+ wp_dequeue_script( $handle );
+ }
+
+ return $this;
+ }
+
+ /**
+ * Localize a script.
+ *
+ * @since 1.6.10
+ *
+ * @param string $handle Name of the script. Should be unique.
+ * @param string $object_name Name for the JavaScript object. Passed directly, so it should be qualified JS variable. Example: '/[a-zA-Z0-9_]+/'.
+ * @param string|array|null $l10n The data itself. The data can be either a single or multi-dimensional array. If null, $handle is used.
+ * @return object This class instance.
+ */
+ public function localize_script( $handle, $object_name, $l10n = null ) {
+ $this->current_handle = $handle;
+ $this->current_handle_type = 'js';
+
+ if ( ! isset( $l10n ) ) {
+ $l10n = $handle;
+ }
+
+ if ( is_string( $l10n ) ) {
+ $l10n = $this->get_localization_data( $l10n );
+ }
+
+ if ( ! $l10n ) {
+ return $this;
+ }
+
+ if ( ! empty( $this->scripts[ $handle ] ) ) {
+ // If we registered it, it's one of our scripts.
+ $handle = self::JS_PREFIX . $handle;
+ }
+
+ wp_localize_script( $handle, $object_name, $l10n );
+
+ return $this;
+ }
+
+ /**
+ * Enqueue a style and a script that have the same handle.
+ *
+ * @since 1.6.10
+ *
+ * @param string|array $handles Name of the script. Should be unique. Can be an array to enqueue several scripts.
+ * @return object This class instance.
+ */
+ public function enqueue_assets( $handles ) {
+ $handles = (array) $handles;
+
+ foreach ( $handles as $handle ) {
+ $this->enqueue_script( $handle );
+ }
+
+ return $this;
+ }
+
+ /**
+ * Dequeue a style and a script that have the same handle.
+ *
+ * @since 1.6.10
+ *
+ * @param string|array $handles Name of the script. Should be unique. Can be an array to dequeue several scripts.
+ * @return object This class instance.
+ */
+ public function dequeue_assets( $handles ) {
+ $handles = (array) $handles;
+
+ foreach ( $handles as $handle ) {
+ $this->dequeue_style( $handle );
+ $this->dequeue_script( $handle );
+ }
+
+ return $this;
+ }
+
+ /**
+ * Enqueue the current script or style.
+ *
+ * @since 1.6.10
+ *
+ * @return object This class instance.
+ */
+ public function enqueue() {
+ if ( 'js' === $this->current_handle_type ) {
+ $this->enqueue_script( $this->current_handle );
+ } elseif ( 'css' === $this->current_handle_type ) {
+ $this->enqueue_style( $this->current_handle );
+ }
+
+ return $this;
+ }
+
+ /**
+ * Localize the current script.
+ *
+ * @since 1.6.10
+ *
+ * @param string $object_name Name for the JavaScript object. Passed directly, so it should be qualified JS variable. Example: '/[a-zA-Z0-9_]+/'.
+ * @param string|array|null $l10n The data itself. The data can be either a single or multi-dimensional array. If null, $handle is used.
+ * @return object This class instance.
+ */
+ public function localize( $object_name, $l10n = null ) {
+ return $this->localize_script( $this->current_handle, $object_name, $l10n );
+ }
+
+ /**
+ * Localize the current script when it is enqueued with `$this->enqueue()` or `$this->enqueue_script()`. This should be used right after `$this->register_script()`.
+ * Be careful, it won't work if the script is enqueued because it's a dependency.
+ * This is handy to not forget to localize the script later. It also prevents to localize the script right away, and maybe execute all localizations while the script is not enqueued (so we localize for nothing).
+ *
+ * @since 1.6.10
+ *
+ * @param string $object_name Name for the JavaScript object. Passed directly, so it should be qualified JS variable. Example: '/[a-zA-Z0-9_]+/'.
+ * @return object This class instance.
+ */
+ public function defer_localization( $object_name ) {
+ if ( ! isset( $this->deferred_localizations[ $this->current_handle ] ) ) {
+ $this->deferred_localizations[ $this->current_handle ] = [];
+ }
+
+ $this->deferred_localizations[ $this->current_handle ][ $object_name ] = $object_name;
+
+ return $this;
+ }
+
+ /**
+ * Remove a deferred localization.
+ *
+ * @since 1.6.10
+ *
+ * @param string $handle Name of the script. Should be unique.
+ * @param string $object_name Name for the JavaScript object. Passed directly, so it should be qualified JS variable. Example: '/[a-zA-Z0-9_]+/'.
+ * @return object This class instance.
+ */
+ public function remove_deferred_localization( $handle, $object_name = null ) {
+ if ( empty( $this->deferred_localizations[ $handle ] ) ) {
+ return $this;
+ }
+
+ if ( $object_name ) {
+ unset( $this->deferred_localizations[ $handle ][ $object_name ] );
+ } else {
+ unset( $this->deferred_localizations[ $handle ] );
+ }
+
+ return $this;
+ }
+
+ /**
+ * Get all translations we can use with wp_localize_script().
+ *
+ * @since 1.6.10
+ *
+ * @param string $context The translation context.
+ * @param array $more_data More data to merge.
+ * @return array $translations The translations.
+ */
+ public function get_localization_data( $context, $more_data = [] ) {
+ $data = get_imagify_localize_script_translations( $context );
+
+ if ( $more_data ) {
+ return array_merge( $data, $more_data );
+ }
+
+ return $data;
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** INTERNAL TOOLS ========================================================================== */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Prefix the dependencies if they are ours.
+ *
+ * @since 1.6.10
+ *
+ * @param array $dependencies An array of registered script handles this script depends on.
+ * @param string $type Type of dependency: css or js.
+ * @return array
+ */
+ protected function prefix_dependencies( $dependencies, $type = 'js' ) {
+ if ( ! $dependencies ) {
+ return [];
+ }
+
+ if ( 'js' === $type ) {
+ $prefix = self::JS_PREFIX;
+ $scripts = $this->scripts;
+ } else {
+ $prefix = self::CSS_PREFIX;
+ $scripts = $this->styles;
+ }
+
+ $depts = [];
+
+ foreach ( $dependencies as $dept ) {
+ if ( ! empty( $scripts[ $dept ] ) ) {
+ $depts[] = $prefix . $dept;
+ } else {
+ $depts[] = $dept;
+ }
+ }
+
+ return $depts;
+ }
+
+ /**
+ * Tell if debug is on.
+ *
+ * @since 1.6.10
+ *
+ * @return bool
+ */
+ protected function is_debug() {
+ return defined( 'IMAGIFY_DEBUG' ) && IMAGIFY_DEBUG || defined( 'SCRIPT_DEBUG' ) && SCRIPT_DEBUG;
+ }
+
+ /**
+ * Tell if the admin bar item is displaying.
+ *
+ * @since 1.6.10
+ *
+ * @return bool
+ */
+ protected function is_admin_bar_item_showing() {
+ if ( defined( 'IMAGIFY_HIDDEN_ACCOUNT' ) && IMAGIFY_HIDDEN_ACCOUNT ) {
+ return false;
+ }
+
+ return get_imagify_option( 'api_key' ) && is_admin_bar_showing() && imagify_get_context( 'wp' )->current_user_can( 'manage' ) && get_imagify_option( 'admin_bar_menu' );
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/inc/classes/class-imagify-auto-optimization.php b/wp/wp-content/plugins/imagify/inc/classes/class-imagify-auto-optimization.php
new file mode 100644
index 00000000..0d4cf1a3
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/classes/class-imagify-auto-optimization.php
@@ -0,0 +1,652 @@
+is_wp_53 = version_compare( $wp_version, '5.3-alpha1' ) >= 0;
+
+ // Automatic optimization tunel.
+ add_action( 'add_attachment', [ $this, 'store_upload_ids' ], $priority );
+ add_filter( 'wp_generate_attachment_metadata', [ $this, 'maybe_store_generate_step' ], $priority, 2 );
+ add_filter( 'wp_update_attachment_metadata', [ $this, 'store_ids_to_optimize' ], $priority, 2 );
+
+ if ( $this->is_wp_53 ) {
+ // WP 5.3+.
+ add_action( 'imagify_after_auto_optimization_init', [ $this, 'do_auto_optimization' ], $priority, 2 );
+ // Upload failure recovering.
+ add_action( 'wp_ajax_media-create-image-subsizes', [ $this, 'prevent_auto_optimization_when_recovering_from_upload_failure' ], -5 ); // Before WP’s hook (priority 1).
+ } else {
+ add_action( 'updated_post_meta', [ $this, 'do_auto_optimization_after_meta_update' ], $priority, 4 );
+ add_action( 'added_post_meta', [ $this, 'do_auto_optimization_after_meta_update' ], $priority, 4 );
+ }
+
+ add_action( 'deleted_post_meta', [ $this, 'unset_optimization' ], $priority, 3 );
+
+ // Prevent to re-optimize when updating the image width and height (when resizing the full image).
+ add_action( 'imagify_before_update_wp_media_data_dimensions', [ __CLASS__, 'prevent_optimization' ], 5 );
+ add_action( 'imagify_after_update_wp_media_data_dimensions', [ __CLASS__, 'allow_optimization' ], 5 );
+ }
+
+ /**
+ * Remove the hooks.
+ *
+ * @since 1.8.4
+ */
+ public function remove_hooks() {
+ $priority = IMAGIFY_INT_MAX - 30;
+
+ // Automatic optimization tunel.
+ remove_action( 'add_attachment', [ $this, 'store_upload_ids' ], $priority );
+ remove_filter( 'wp_generate_attachment_metadata', [ $this, 'maybe_store_generate_step' ], $priority );
+ remove_filter( 'wp_update_attachment_metadata', [ $this, 'store_ids_to_optimize' ], $priority );
+
+ if ( $this->is_wp_53 ) {
+ // WP 5.3+.
+ remove_action( 'imagify_after_auto_optimization_init', [ $this, 'do_auto_optimization' ], $priority );
+ // Upload failure recovering.
+ remove_action( 'wp_ajax_media-create-image-subsizes', [ $this, 'prevent_auto_optimization_when_recovering_from_upload_failure' ], -5 );
+ } else {
+ remove_action( 'updated_post_meta', [ $this, 'do_auto_optimization_after_meta_update' ], $priority );
+ remove_action( 'added_post_meta', [ $this, 'do_auto_optimization_after_meta_update' ], $priority );
+ }
+
+ remove_action( 'deleted_post_meta', [ $this, 'unset_optimization' ], $priority );
+
+ // Prevent to re-optimize when updating the image width and height (when resizing the full image).
+ remove_action( 'imagify_before_update_wp_media_data_dimensions', [ __CLASS__, 'prevent_optimization' ], 5 );
+ remove_action( 'imagify_after_update_wp_media_data_dimensions', [ __CLASS__, 'allow_optimization' ], 5 );
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** HOOKS =================================================================================== */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Store the "upload step" when an attachment has just been uploaded.
+ *
+ * @since 1.8.4
+ * @see $this->store_ids_to_optimize()
+ *
+ * @param int $attachment_id Current attachment ID.
+ */
+ public function store_upload_ids( $attachment_id ) {
+ if ( ! self::is_optimization_prevented( $attachment_id ) && imagify_is_attachment_mime_type_supported( $attachment_id ) ) {
+ $this->set_step( $attachment_id, 'upload' );
+ }
+ }
+
+ /**
+ * Store the "generate step" when wp_generate_attachment_metadata() is used.
+ *
+ * @since 1.9.10
+ *
+ * @param array $metadata An array of attachment meta data.
+ * @param int $attachment_id Current attachment ID.
+ * @return array
+ */
+ public function maybe_store_generate_step( $metadata, $attachment_id ) {
+ if ( self::is_optimization_prevented( $attachment_id ) ) {
+ return $metadata;
+ }
+
+ if ( empty( $metadata ) || ! imagify_is_attachment_mime_type_supported( $attachment_id ) ) {
+ $this->unset_steps( $attachment_id );
+ return $metadata;
+ }
+
+ $this->set_step( $attachment_id, 'generate' );
+
+ return $metadata;
+ }
+
+ /**
+ * After the attachment meta data has been generated (partially, since WP 5.3), init the auto-optimization.
+ * Two cases are possible to trigger the optimization:
+ * - It's a new upload and auto-optimization is enabled.
+ * - It's not a new upload (it is regenerated) and the attachment is already optimized.
+ *
+ * @since 1.8.4
+ *
+ * @param array $metadata An array of attachment meta data.
+ * @param int $attachment_id Current attachment ID.
+ * @return array
+ */
+ public function store_ids_to_optimize( $metadata, $attachment_id ) {
+ static $auto_optimize;
+
+ if ( self::is_optimization_prevented( $attachment_id ) ) {
+ return $metadata;
+ }
+
+ if ( empty( $metadata ) || ! imagify_is_attachment_mime_type_supported( $attachment_id ) ) {
+ $this->unset_steps( $attachment_id );
+ return $metadata;
+ }
+
+ if ( ! $this->has_step( $attachment_id, 'generate' ) ) {
+ return $metadata;
+ }
+
+ $is_new_upload = $this->has_step( $attachment_id, 'upload' );
+
+ if ( $is_new_upload ) {
+ // It's a new upload.
+ if ( ! isset( $auto_optimize ) ) {
+ $auto_optimize = get_imagify_option( 'auto_optimize' );
+ }
+
+ if ( ! $auto_optimize ) {
+ /**
+ * Fires when a new attachment is uploaded but auto-optimization is disabled.
+ *
+ * @since 1.8.4
+ *
+ * @param int $attachment_id Attachment ID.
+ * @param array $metadata An array of attachment meta data.
+ */
+ do_action( 'imagify_new_attachment_auto_optimization_disabled', $attachment_id, $metadata );
+
+ return $metadata;
+ }
+
+ /**
+ * Allow to prevent automatic optimization for a specific attachment.
+ *
+ * @since 1.6.12
+ *
+ * @param bool $optimize True to optimize, false otherwise.
+ * @param int $attachment_id Attachment ID.
+ * @param array $metadata An array of attachment meta data.
+ */
+ $optimize = apply_filters( 'imagify_auto_optimize_attachment', true, $attachment_id, $metadata );
+
+ if ( ! $optimize ) {
+ return $metadata;
+ }
+
+ /**
+ * It's a new upload and auto-optimization is enabled.
+ */
+ }
+
+ if ( ! $is_new_upload ) {
+ // An existing attachment being regenerated (or something).
+ $process = imagify_get_optimization_process( $attachment_id, 'wp' );
+
+ if ( ! $process->is_valid() ) {
+ // Uh?
+ return $metadata;
+ }
+
+ if ( ! $process->get_data()->get_optimization_status() ) {
+ /**
+ * Fires when an attachment is updated but not optimized yet.
+ *
+ * @since 1.8.4
+ *
+ * @param int $attachment_id Attachment ID.
+ * @param array $metadata An array of attachment meta data.
+ */
+ do_action( 'imagify_not_optimized_attachment_updated', $attachment_id, $metadata );
+
+ return $metadata;
+ }
+
+ /**
+ * Allow to prevent automatic reoptimization for a specific attachment.
+ *
+ * @since 1.8.4
+ *
+ * @param bool $optimize True to optimize, false otherwise.
+ * @param int $attachment_id Attachment ID.
+ * @param array $metadata An array of attachment meta data.
+ */
+ $optimize = apply_filters( 'imagify_auto_optimize_optimized_attachment', true, $attachment_id, $metadata );
+
+ if ( ! $optimize ) {
+ return $metadata;
+ }
+
+ /**
+ * The attachment already exists and was already optimized.
+ */
+ }
+
+ // Ready for the next step.
+ $this->set_step( $attachment_id, 'update' );
+
+ /**
+ * Triggered after a media auto-optimization init.
+ *
+ * @since 1.9.8
+ *
+ * @param int $attachment_id The media ID.
+ * @param bool $is_new_upload True if it's a new upload. False otherwize.
+ */
+ do_action( 'imagify_after_auto_optimization_init', $attachment_id, $is_new_upload );
+
+ return $metadata;
+ }
+
+ /**
+ * Launch auto optimization immediately after the post meta '_wp_attachment_metadata' is added or updated.
+ *
+ * @since 1.9
+ * @since 1.9 Previously named do_auto_optimization().
+ *
+ * @param int $meta_id ID of the metadata entry.
+ * @param int $attachment_id Current attachment ID.
+ * @param string $meta_key Meta key.
+ * @param mixed $metadata Meta value.
+ */
+ public function do_auto_optimization_after_meta_update( $meta_id, $attachment_id, $meta_key, $metadata ) {
+ if ( '_wp_attachment_metadata' !== $meta_key ) {
+ return;
+ }
+
+ if ( self::is_optimization_prevented( $attachment_id ) ) {
+ return;
+ }
+
+ if ( ! $this->has_step( $attachment_id, 'update' ) ) {
+ return;
+ }
+
+ $this->do_auto_optimization( $attachment_id, $this->has_step( $attachment_id, 'upload' ) );
+ }
+
+ /**
+ * Launch auto optimization immediately after the post meta '_wp_attachment_metadata' is added or updated.
+ *
+ * @since 1.8.4
+ * @since 1.9.8 Changed signature.
+ *
+ * @param int $attachment_id The media ID.
+ * @param bool $is_new_upload True if it's a new upload. False otherwize.
+ */
+ public function do_auto_optimization( $attachment_id, $is_new_upload ) {
+ $this->unset_steps( $attachment_id );
+
+ $process = imagify_get_optimization_process( $attachment_id, 'wp' );
+
+ /**
+ * Fires before an attachment auto-optimization is triggered.
+ *
+ * @since 1.8.4
+ *
+ * @param int $attachment_id The attachment ID.
+ * @param bool $is_new_upload True if it's a new upload. False otherwize.
+ */
+ do_action_deprecated( 'imagify_before_auto_optimization_launch', [ $attachment_id, $is_new_upload ], '1.9', 'imagify_before_auto_optimization' );
+
+ /**
+ * Triggered before a media is auto-optimized.
+ *
+ * @since 1.8.4
+ *
+ * @param int $attachment_id The media ID.
+ * @param bool $is_new_upload True if it's a new upload. False otherwize.
+ */
+ do_action( 'imagify_before_auto_optimization', $attachment_id, $is_new_upload );
+
+ if ( $is_new_upload ) {
+ /**
+ * It's a new upload.
+ */
+ // Optimize.
+ $process->optimize( null, [ 'is_new_upload' => 1 ] );
+ } else {
+ /**
+ * The media has already been optimized (or at least it has been tried).
+ */
+ $process_data = $process->get_data();
+
+ // Get the optimization level before deleting the optimization data.
+ $optimization_level = $process_data->get_optimization_level();
+
+ // Some specifics for the image editor.
+ if ( isset( $_POST['action'], $_POST['do'], $_POST['postid'] ) && 'image-editor' === $_POST['action'] && (int) $_POST['postid'] === $attachment_id ) { // WPCS: CSRF ok.
+ check_ajax_referer( 'image_editor-' . $attachment_id );
+
+ if ( ! current_user_can( 'edit_post', $attachment_id ) ) {
+ imagify_die();
+ }
+
+ // Restore the backup file.
+ $result = $process->restore();
+
+ if ( is_wp_error( $result ) ) {
+ // Restoration failed, there is no good way to handle this case.
+ $process_data->delete_optimization_data();
+ }
+ } else {
+ // Remove old optimization data.
+ $process_data->delete_optimization_data();
+ }
+
+ // Optimize.
+ $process->optimize( $optimization_level );
+ }
+
+ /**
+ * Triggered after a media auto-optimization is launched.
+ *
+ * @since 1.8.4
+ *
+ * @param int $attachment_id The media ID.
+ * @param bool $is_new_upload True if it's a new upload. False otherwize.
+ */
+ do_action( 'imagify_after_auto_optimization', $attachment_id, $is_new_upload );
+ }
+
+ /**
+ * Remove the attachment ID from the $attachments property if the post meta '_wp_attachment_metadata' is deleted.
+ *
+ * @since 1.8.4
+ *
+ * @param int $meta_ids An array of deleted metadata entry IDs.
+ * @param int $attachment_id Current attachment ID.
+ * @param string $meta_key Meta key.
+ */
+ public function unset_optimization( $meta_ids, $attachment_id, $meta_key ) {
+ if ( '_wp_attachment_metadata' !== $meta_key ) {
+ return;
+ }
+
+ $this->unset_steps( $attachment_id );
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** HOOKS FOR WP 5.3+’S UPLOAD FAILURE RECOVERING =========================================== */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * With WP 5.3+, prevent auto-optimization when WP tries to create thumbnails after an upload error, because it triggers wp_update_attachment_metadata() for each thumbnail size.
+ *
+ * @since 1.9.8
+ * @see wp_ajax_media_create_image_subsizes()
+ * @see wp_update_image_subsizes()
+ */
+ public function prevent_auto_optimization_when_recovering_from_upload_failure() {
+ if ( ! check_ajax_referer( 'media-form', false, false ) ) {
+ return;
+ }
+
+ if ( ! current_user_can( 'upload_files' ) ) {
+ return;
+ }
+
+ if ( ! imagify_get_context( 'wp' )->current_user_can( 'auto-optimize' ) ) {
+ return;
+ }
+
+ $attachment_id = ! empty( $_POST['attachment_id'] ) ? (int) $_POST['attachment_id'] : 0;
+
+ if ( empty( $attachment_id ) ) {
+ return;
+ }
+
+ if ( ! imagify_is_attachment_mime_type_supported( $attachment_id ) ) {
+ return;
+ }
+
+ $this->upload_failure_id = $attachment_id;
+
+ // Auto-optimization will be done on shutdown.
+ ob_start( [ $this, 'maybe_do_auto_optimization_after_recovering_from_upload_failure' ] );
+ }
+
+ /**
+ * Maybe launch auto-optimization after recovering from an upload failure, when all thumbnails are created.
+ *
+ * @since 1.9.8
+ * @see wp_ajax_media_create_image_subsizes()
+ *
+ * @param string $content Buffer’s content.
+ * @return string Buffer’s content.
+ */
+ public function maybe_do_auto_optimization_after_recovering_from_upload_failure( $content ) {
+ if ( empty( $content ) ) {
+ return $content;
+ }
+
+ if ( empty( $this->upload_failure_id ) ) {
+ // Uh?
+ return $content;
+ }
+
+ if ( ! get_post( $this->upload_failure_id ) ) {
+ return $content;
+ }
+
+ $json = @json_decode( $content );
+
+ if ( empty( $json->success ) ) {
+ return $content;
+ }
+
+ $attachment_id = $this->upload_failure_id;
+ $metadata = wp_get_attachment_metadata( $attachment_id );
+
+ // Launch the process.
+ $this->upload_failure_id = 0;
+ $this->set_step( $attachment_id, 'generate' );
+ $this->store_ids_to_optimize( $metadata, $attachment_id );
+
+ return $content;
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** TOOLS =================================================================================== */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Set a "step" for an attachment.
+ *
+ * @since 1.9.10
+ * @see $this->attachments
+ *
+ * @param int $attachment_id Current attachment ID.
+ * @param string $step The step to add.
+ */
+ public function set_step( $attachment_id, $step ) {
+ if ( empty( $this->attachments[ $attachment_id ] ) ) {
+ $this->attachments[ $attachment_id ] = [];
+ }
+
+ $this->attachments[ $attachment_id ][ $step ] = 1;
+ }
+
+ /**
+ * Unset a "step" for an attachment.
+ *
+ * @since 1.9.10
+ * @see $this->attachments
+ *
+ * @param int $attachment_id Current attachment ID.
+ * @param string $step The step to add.
+ */
+ public function unset_step( $attachment_id, $step ) {
+ unset( $this->attachments[ $attachment_id ][ $step ] );
+
+ if ( empty( $this->attachments[ $attachment_id ] ) ) {
+ $this->unset_steps( $attachment_id );
+ }
+ }
+
+ /**
+ * Unset all "steps" for an attachment.
+ *
+ * @since 1.9.10
+ * @see $this->attachments
+ *
+ * @param int $attachment_id Current attachment ID.
+ */
+ public function unset_steps( $attachment_id ) {
+ unset( $this->attachments[ $attachment_id ] );
+ }
+
+ /**
+ * Tell if a "step" for an attachment exists.
+ *
+ * @since 1.9.10
+ * @see $this->attachments
+ *
+ * @param int $attachment_id Current attachment ID.
+ * @param string $step The step to add.
+ * @return bool
+ */
+ public function has_step( $attachment_id, $step ) {
+ return ! empty( $this->attachments[ $attachment_id ][ $step ] );
+ }
+
+ /**
+ * Prevent an auto-optimization locally.
+ * How to use it:
+ * Imagify_Auto_Optimization::prevent_optimization( $attachment_id );
+ * wp_update_attachment_metadata( $attachment_id );
+ * Imagify_Auto_Optimization::allow_optimization( $attachment_id );
+ *
+ * @since 1.8.4
+ * @since 1.9.8 Prevents/Allows can stack.
+ *
+ * @param int $attachment_id Current attachment ID.
+ */
+ public static function prevent_optimization( $attachment_id ) {
+ if ( ! isset( self::$prevented[ $attachment_id ] ) ) {
+ self::$prevented[ $attachment_id ] = 1;
+ } else {
+ ++self::$prevented[ $attachment_id ];
+ }
+ }
+
+ /**
+ * Allow an auto-optimization locally.
+ * How to use it:
+ * Imagify_Auto_Optimization::prevent_optimization( $attachment_id );
+ * wp_update_attachment_metadata( $attachment_id );
+ * Imagify_Auto_Optimization::allow_optimization( $attachment_id );
+ *
+ * @since 1.8.4
+ * @since 1.9.8 Prevents/Allows can stack.
+ *
+ * @param int $attachment_id Current attachment ID.
+ */
+ public static function allow_optimization( $attachment_id ) {
+ if ( ! isset( self::$prevented[ $attachment_id ] ) ) {
+ return;
+ }
+ --self::$prevented[ $attachment_id ];
+
+ if ( self::$prevented[ $attachment_id ] <= 0 ) {
+ unset( self::$prevented[ $attachment_id ] );
+ }
+ }
+
+ /**
+ * Tell if an auto-optimization is prevented locally.
+ *
+ * @since 1.8.4
+ *
+ * @param int $attachment_id Current attachment ID.
+ * @return bool
+ */
+ public static function is_optimization_prevented( $attachment_id ) {
+ return ! empty( self::$prevented[ $attachment_id ] ) || ! empty( self::$prevented_internally[ $attachment_id ] );
+ }
+
+ /**
+ * Prevent an auto-optimization internally.
+ *
+ * @since 1.9.8
+ *
+ * @param int $attachment_id Current attachment ID.
+ */
+ protected static function prevent_optimization_internally( $attachment_id ) {
+ self::$prevented_internally[ $attachment_id ] = 1;
+ }
+
+ /**
+ * Allow an auto-optimization internally.
+ *
+ * @since 1.9.8
+ *
+ * @param int $attachment_id Current attachment ID.
+ */
+ protected static function allow_optimization_internally( $attachment_id ) {
+ unset( self::$prevented_internally[ $attachment_id ] );
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/inc/classes/class-imagify-cron-library-size.php b/wp/wp-content/plugins/imagify/inc/classes/class-imagify-cron-library-size.php
new file mode 100644
index 00000000..ee7918ed
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/classes/class-imagify-cron-library-size.php
@@ -0,0 +1,91 @@
+ 'imagify_update_estimate_sizes',
+ '_ajax_nonce' => wp_create_nonce( 'update_estimate_sizes' ),
+ ) );
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/inc/classes/class-imagify-cron-rating.php b/wp/wp-content/plugins/imagify/inc/classes/class-imagify-cron-rating.php
new file mode 100644
index 00000000..1da80cd2
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/classes/class-imagify-cron-rating.php
@@ -0,0 +1,110 @@
+get_event_name() ) && ! get_site_transient( 'do_imagify_rating_cron' ) ) {
+ wp_schedule_event( $this->get_event_timestamp(), $this->get_event_recurrence(), $this->get_event_name() );
+ }
+ }
+
+ /**
+ * The event action.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ */
+ public function do_event() {
+ // Stop the process if the plugin isn't installed for 3 days.
+ if ( get_site_transient( 'imagify_seen_rating_notice' ) ) {
+ return;
+ }
+
+ $user = get_imagify_user();
+
+ if ( ! is_wp_error( $user ) && isset( $user->image_count ) && (int) $user->image_count > 100 ) {
+ set_site_transient( 'imagify_user_images_count', $user->image_count );
+ }
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/inc/classes/class-imagify-cron-sync-files.php b/wp/wp-content/plugins/imagify/inc/classes/class-imagify-cron-sync-files.php
new file mode 100644
index 00000000..00dee480
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/classes/class-imagify-cron-sync-files.php
@@ -0,0 +1,100 @@
+can_operate() || ! $files_db->can_operate() ) {
+ return;
+ }
+
+ if ( ! Imagify_Requirements::is_api_key_valid() ) {
+ return;
+ }
+
+ if ( Imagify_Requirements::is_over_quota() ) {
+ return;
+ }
+
+ $this->set_no_time_limit();
+
+ /**
+ * Get the folders from DB.
+ */
+ $folders = Imagify_Custom_Folders::get_folders();
+
+ if ( ! $folders ) {
+ return;
+ }
+
+ Imagify_Custom_Folders::synchronize_files_from_folders( $folders );
+ }
+
+ /**
+ * Attempts to set no limit to the PHP timeout for time intensive processes.
+ *
+ * @return void
+ */
+ protected function set_no_time_limit() {
+ if (
+ function_exists( 'set_time_limit' )
+ &&
+ false === strpos( ini_get( 'disable_functions' ), 'set_time_limit' )
+ && ! ini_get( 'safe_mode' ) // phpcs:ignore PHPCompatibility.IniDirectives.RemovedIniDirectives.safe_modeDeprecatedRemoved
+ ) {
+ @set_time_limit( 0 ); // phpcs:ignore WordPress.PHP.NoSilencedErrors.Discouraged
+ }
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/inc/classes/class-imagify-custom-folders.php b/wp/wp-content/plugins/imagify/inc/classes/class-imagify-custom-folders.php
new file mode 100644
index 00000000..6a33bcd8
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/classes/class-imagify-custom-folders.php
@@ -0,0 +1,1316 @@
+get_site_root() . 'imagify-backup/';
+
+ /**
+ * Filter the backup directory path (custom folders).
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ *
+ * @param string $backup_dir The backup directory path.
+ */
+ $backup_dir = apply_filters( 'imagify_files_backup_directory', $backup_dir );
+ $backup_dir = $filesystem->normalize_dir_path( $backup_dir );
+
+ return $backup_dir;
+ }
+
+ /**
+ * Tell if the folder containing the backups is writable (custom folders).
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return bool
+ */
+ public static function backup_dir_is_writable() {
+ return imagify_get_filesystem()->make_dir( self::get_backup_dir_path() );
+ }
+
+ /**
+ * Get the backup path of a specific file (custom folders).
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param string $file_path The file path.
+ * @return string|bool The backup path. False on failure.
+ */
+ public static function get_file_backup_path( $file_path ) {
+ $file_path = wp_normalize_path( (string) $file_path );
+ $site_root = imagify_get_filesystem()->get_site_root();
+ $backup_dir = self::get_backup_dir_path();
+
+ if ( ! $file_path ) {
+ return false;
+ }
+
+ return preg_replace( '@^' . preg_quote( $site_root, '@' ) . '@', $backup_dir, $file_path );
+ }
+
+ /**
+ * Add index.php files recursively to a given directory and all its subdirectories.
+ *
+ * @since 1.9.11
+ *
+ * @param string $backup_dir (optional) Path to the directory where we will start adding indexes.
+ * Defaults to custom-folders backup dir.
+ *
+ * @return void
+ */
+ public static function add_indexes( $backup_dir = '' ) {
+ $filesystem = Imagify_Filesystem::get_instance();
+
+ if ( empty( $backup_dir ) ) {
+ $backup_dir = self::get_backup_dir_path();
+ }
+
+ if ( ! $filesystem->is_writable( $backup_dir ) ) {
+ return;
+ }
+
+ try {
+ $directory = new RecursiveDirectoryIterator( $backup_dir );
+ $iterator = new RecursiveIteratorIterator( $directory );
+
+ foreach ( $iterator as $fileinfo ) {
+
+ if ( '.' !== $fileinfo->getFilename() ) {
+ continue;
+ }
+
+ $path = trailingslashit( $fileinfo->getRealPath() );
+
+ if ( ! $filesystem->is_file( $path . 'index.html' )
+ && ! $filesystem->is_file( $path . 'index.php' )
+ ) {
+ $filesystem->touch( $path . 'index.php' );
+ }
+ }
+ } catch ( Exception $e ) {
+ return;
+ }
+ }
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** SINGLE FILE ============================================================================= */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Insert a file into the DB.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param array $args An array of arguments to pass to Imagify_Files_DB::insert(). Required values are 'folder_id' and ( 'path' or 'file_path').
+ * @return int The file ID on success. 0 on failure.
+ */
+ public static function insert_file( $args = array() ) {
+ if ( empty( $args['folder_id'] ) ) {
+ return 0;
+ }
+
+ if ( empty( $args['path'] ) ) {
+ if ( empty( $args['file_path'] ) ) {
+ return 0;
+ }
+
+ $args['path'] = Imagify_Files_Scan::add_placeholder( $args['file_path'] );
+ }
+
+ if ( empty( $args['file_path'] ) ) {
+ $args['file_path'] = Imagify_Files_Scan::remove_placeholder( $args['path'] );
+ }
+
+ $filesystem = imagify_get_filesystem();
+
+ if ( ! $filesystem->is_readable( $args['file_path'] ) ) {
+ return 0;
+ }
+
+ if ( empty( $args['file_date'] ) || '0000-00-00 00:00:00' === $args['file_date'] ) {
+ $args['file_date'] = $filesystem->get_date( $args['file_path'] );
+ }
+
+ if ( empty( $args['mime_type'] ) ) {
+ $args['mime_type'] = $filesystem->get_mime_type( $args['file_path'] );
+ }
+
+ if ( ( empty( $args['width'] ) || empty( $args['height'] ) ) && strpos( $args['mime_type'], 'image/' ) === 0 ) {
+ $file_size = $filesystem->get_image_size( $args['file_path'] );
+ $args['width'] = $file_size ? $file_size['width'] : 0;
+ $args['height'] = $file_size ? $file_size['height'] : 0;
+ }
+
+ if ( empty( $args['hash'] ) ) {
+ $args['hash'] = md5_file( $args['file_path'] );
+ }
+
+ if ( empty( $args['original_size'] ) ) {
+ $args['original_size'] = (int) $filesystem->size( $args['file_path'] );
+ }
+
+ $files_db = Imagify_Files_DB::get_instance();
+ $primary_key = $files_db->get_primary_key();
+ unset( $args[ $primary_key ] );
+
+ return $files_db->insert( $args );
+ }
+
+ /**
+ * Delete a custom file.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param array $args An array of arguments.
+ * At least: 'file_id'. At best: 'file_id', 'file_path' (or 'path' for the placeholder), and 'backup_path'.
+ */
+ public static function delete_file( $args = [] ) {
+ $args = array_merge( [
+ 'file_id' => 0,
+ 'file_path' => '',
+ 'path' => '',
+ 'backup_path' => '',
+ 'process' => false,
+ ], $args );
+
+ $filesystem = imagify_get_filesystem();
+
+ // Fill the blanks.
+ if ( $args['process'] && $args['process'] instanceof \Imagify\Optimization\Process\ProcessInterface ) {
+ $process = $args['process'];
+ } else {
+ $process = imagify_get_optimization_process( $args['file_id'], 'custom-folders' );
+ }
+
+ if ( ! $process->is_valid() ) {
+ // You fucked up!
+ return;
+ }
+
+ if ( ! $args['file_path'] && $args['path'] ) {
+ $args['file_path'] = Imagify_Files_Scan::remove_placeholder( $args['path'] );
+ }
+
+ if ( ! $args['file_path'] && $args['file_id'] ) {
+ $args['file_path'] = $process->get_media()->get_fullsize_path();
+ }
+
+ if ( ! $args['backup_path'] && $args['file_path'] ) {
+ $args['backup_path'] = self::get_file_backup_path( $args['file_path'] );
+ }
+
+ if ( ! $args['backup_path'] && $args['file_id'] ) {
+ $args['backup_path'] = $process->get_media()->get_raw_backup_path();
+ }
+
+ // Trigger a common hook.
+ imagify_trigger_delete_media_hook( $process );
+
+ // The file.
+ if ( $args['file_path'] && $filesystem->exists( $args['file_path'] ) ) {
+ $filesystem->delete( $args['file_path'] );
+ }
+
+ // The backup file.
+ if ( $args['backup_path'] && $filesystem->exists( $args['backup_path'] ) ) {
+ $filesystem->delete( $args['backup_path'] );
+ }
+
+ // WebP.
+ $mime_type = $filesystem->get_mime_type( $args['file_path'] );
+ $is_image = $mime_type && strpos( $mime_type, 'image/' ) === 0;
+ $webp_path = $is_image ? imagify_path_to_webp( $args['file_path'] ) : false;
+
+ if ( $webp_path && $filesystem->is_writable( $webp_path ) ) {
+ $filesystem->delete( $webp_path );
+ }
+
+ // In the database.
+ $process->get_media()->delete_row();
+ }
+
+ /**
+ * Check if a file has been modified, and update the database accordingly.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param ProcessInterface $process A \Imagify\Optimization\Process\ProcessInterface object.
+ * @param bool $is_folder_active Tell if the folder is active.
+ * @return int|bool|object The file ID if modified. False if not modified. A WP_Error object if the entry has been removed from the database.
+ * The entry is removed from the database if:
+ * - The file doesn't exist anymore.
+ * - Or if its folder is not active and: the file has been modified, or the file is not optimized by Imagify, or the file is orphan (its folder is not in the database anymore).
+ */
+ public static function refresh_file( $process, $is_folder_active = null ) {
+ global $wpdb;
+
+ if ( ! $process->is_valid() ) {
+ return new \WP_Error( 'invalid_media', __( 'This media is not valid.', 'imagify' ) );
+ }
+
+ $filesystem = imagify_get_filesystem();
+ $media = $process->get_media();
+ $file_path = $media->get_fullsize_path();
+ $mime_type = $filesystem->get_mime_type( $file_path );
+ $is_image = $mime_type && strpos( $mime_type, 'image/' ) === 0;
+ $webp_path = $is_image ? imagify_path_to_webp( $file_path ) : false;
+ $has_webp = $webp_path && $filesystem->is_writable( $webp_path );
+ $modified = false;
+
+ if ( ! $file_path || ! $filesystem->exists( $file_path ) ) {
+ /**
+ * The file doesn't exist anymore.
+ */
+ // Delete the backup file.
+ $process->delete_backup();
+
+ // Get the folder ID before removing the row.
+ $folder_id = $media->get_row();
+ $folder_id = $folder_id['folder_id'];
+
+ // Remove the entry from the database.
+ $media->delete_row();
+
+ // Remove the corresponding folder if inactive and have no files left.
+ self::remove_empty_inactive_folders( $folder_id );
+
+ // Delete the WebP version.
+ if ( $has_webp ) {
+ $filesystem->delete( $webp_path );
+ }
+
+ return new WP_Error( 'no-file', __( 'The file was missing or its path could not be retrieved from the database. The entry has been deleted from the database.', 'imagify' ) );
+ }
+
+ /**
+ * The file still exists.
+ */
+ $old_data = $media->get_row();
+ $new_data = [];
+
+ // Folder ID.
+ if ( $old_data['folder_id'] ) {
+ $folder = wp_cache_get( 'custom_folder_' . $old_data['folder_id'], 'imagify' );
+
+ if ( false === $folder ) {
+ // The folder is not in the cache.
+ $folder = Imagify_Folders_DB::get_instance()->get( $old_data['folder_id'] );
+ $folder = $folder ? $folder : 0;
+ }
+
+ if ( ! $folder ) {
+ // The folder is not in the database anymore.
+ $old_data['folder_id'] = 0;
+ $new_data['folder_id'] = 0;
+ }
+ } else {
+ $folder = 0;
+ }
+
+ // Hash + modified.
+ $current_hash = md5_file( $file_path );
+
+ if ( ! $old_data['hash'] ) {
+ $new_data['modified'] = 0;
+ } else {
+ $new_data['modified'] = (int) ! hash_equals( $old_data['hash'], $current_hash );
+ }
+
+ // The file is modified or is not optimized.
+ if ( $new_data['modified'] || ! $process->get_data()->is_optimized() ) {
+ if ( ! isset( $is_folder_active ) ) {
+ $is_folder_active = $folder && $folder['active'];
+ }
+
+ // Its folder is not active: remove the entry from the database and delete the backup.
+ if ( ! $is_folder_active ) {
+ // Delete the backup file.
+ $process->delete_backup();
+
+ // Remove the entry from the database.
+ $media->delete_row();
+
+ // Remove the corresponding folder if inactive and have no files left.
+ if ( $old_data['folder_id'] ) {
+ self::remove_empty_inactive_folders( $old_data['folder_id'] );
+ }
+
+ // Delete the WebP version.
+ if ( $has_webp ) {
+ $filesystem->delete( $webp_path );
+ }
+
+ return new WP_Error( 'folder-not-active', __( 'The file has been modified or was not optimized: its folder not being selected in the settings, the entry has been deleted from the database.', 'imagify' ) );
+ }
+ }
+
+ $new_data['hash'] = $current_hash;
+
+ // The file is modified.
+ if ( $new_data['modified'] ) {
+ // Delete all optimization data and update file data.
+ $modified = true;
+ $mime_type = ! empty( $old_data['mime_type'] ) ? $old_data['mime_type'] : $filesystem->get_mime_type( $file_path );
+
+ if ( $is_image ) {
+ $size = $filesystem->get_image_size( $file_path );
+
+ // Delete the WebP version.
+ if ( $has_webp ) {
+ $filesystem->delete( $webp_path );
+ }
+ } else {
+ $size = false;
+ }
+
+ $new_data = array_merge( $new_data, [
+ 'file_date' => $filesystem->get_date( $file_path ),
+ 'width' => $size ? $size['width'] : 0,
+ 'height' => $size ? $size['height'] : 0,
+ 'original_size' => $filesystem->size( $file_path ),
+ 'optimized_size' => null,
+ 'percent' => null,
+ 'optimization_level' => null,
+ 'status' => null,
+ 'error' => null,
+ 'data' => [],
+ ] );
+
+ // Delete the backup of the previous file.
+ $process->delete_backup();
+ } else {
+ // Update file data to make sure nothing is missing.
+ $backup_path = $media->get_backup_path();
+ $path = $backup_path ? $backup_path : $file_path;
+ $mime_type = ! empty( $old_data['mime_type'] ) ? $old_data['mime_type'] : $filesystem->get_mime_type( $path );
+ $file_date = ! empty( $old_data['file_date'] ) && '0000-00-00 00:00:00' !== $old_data['file_date'] ? $old_data['file_date'] : $filesystem->get_date( $path );
+
+ if ( $is_image ) {
+ $size = $filesystem->get_image_size( $path );
+ } else {
+ $size = false;
+ }
+
+ $new_data = array_merge( $new_data, [
+ 'file_date' => $file_date,
+ 'width' => $size ? $size['width'] : 0,
+ 'height' => $size ? $size['height'] : 0,
+ 'original_size' => $filesystem->size( $path ),
+ ] );
+
+ // WebP.
+ $webp_size = 'full' . $process::WEBP_SUFFIX;
+
+ if ( $has_webp && empty( $old_data['data'][ $webp_size ]['success'] ) ) {
+ $webp_file_size = $filesystem->size( $webp_path );
+
+ $old_data['data'][ $webp_size ] = [
+ 'success' => true,
+ 'original_size' => $new_data['original_size'],
+ 'optimized_size' => $webp_file_size,
+ 'percent' => round( ( ( $new_data['original_size'] - $webp_file_size ) / $new_data['original_size'] ) * 100, 2 ),
+ ];
+ }
+ }
+
+ // Save the new data.
+ $old_data = array_intersect_key( $old_data, $new_data );
+ ksort( $old_data );
+ ksort( $new_data );
+
+ if ( $old_data !== $new_data ) {
+ $media->update_row( $new_data );
+ }
+
+ return $modified ? $media->get_id() : false;
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** FOLDERS AND FILES ======================================================================= */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Get folders from the DB.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param array $args A list of arguments to tell more precisely what to fetch:
+ * - bool $active True to fetch only "active" folders (checked in the settings). False to fetch only folders that are not "active".
+ * @return array An array of arrays containing the following values:
+ * - int $folder_id The folder ID.
+ * - string $path The folder path, with placeholder.
+ * - int $active 1 if the folder should be optimized. 0 otherwize.
+ * - string $folder_path The real absolute folder path.
+ * Example:
+ * Array(
+ * [7] => Array(
+ * [folder_id] => 7
+ * [path] => {{ROOT}}/custom-path/
+ * [active] => 1
+ * [folder_path] => /absolute/path/to/custom-path/
+ * )
+ * [13] => Array(
+ * [folder_id] => 13
+ * [path] => {{CONTENT}}/another-custom-path/
+ * [active] => 1
+ * [folder_path] => /absolute/path/to/wp-content/another-custom-path/
+ * )
+ * )
+ */
+ public static function get_folders( $args = array() ) {
+ global $wpdb;
+
+ $folders_db = Imagify_Folders_DB::get_instance();
+ $folders_table = $folders_db->get_table_name();
+ $primary_key = $folders_db->get_primary_key();
+ $where_active = '';
+
+ if ( isset( $args['active'] ) ) {
+ if ( $args['active'] ) {
+ $args['active'] = true;
+ $where_active = 'WHERE active = 1';
+ } else {
+ $args['active'] = false;
+ $where_active = 'WHERE active = 0';
+ }
+ }
+
+ // Get the folders from the DB.
+ $results = $wpdb->get_results( "SELECT * FROM $folders_table $where_active;", ARRAY_A ); // WPCS: unprepared SQL ok.
+
+ if ( ! $results || ! is_array( $results ) ) {
+ return array();
+ }
+
+ // Cast results, add absolute paths.
+ $folders = array();
+
+ foreach ( $results as $row_fields ) {
+ // Cast the row.
+ $row_fields = $folders_db->cast_row( $row_fields );
+
+ // Add the absolute path.
+ $row_fields['folder_path'] = Imagify_Files_Scan::remove_placeholder( $row_fields['path'] );
+
+ // Add the row to the list.
+ $folders[ $row_fields[ $primary_key ] ] = $row_fields;
+ }
+
+ return $folders;
+ }
+
+ /**
+ * Get files belonging to the given folders.
+ * Files are scanned from the folders, then:
+ * - If a file doesn't exist in the DB, it is added (maybe, depending on arguments provided).
+ * - If a file is in the DB, but with a wrong folder_id, it is fixed.
+ * - If a file doesn't exist, it is removed from the database and its backup is deleted.
+ *
+ * @since 1.7
+ * @access public
+ * @see Imagify_Custom_Folders::get_folders()
+ * @author Grégory Viguier
+ *
+ * @param array $folders An array of arrays containing at least the keys 'folder_path' and 'active'. See Imagify_Custom_Folders::get_folders() for the format.
+ * @param array $args A list of arguments to tell more precisely what to fetch:
+ * - int $optimization_level If set with an integer, only files that needs to be optimized to this level will be returned (the status is also checked).
+ * - bool $return_only_old_files True to return only files that have not been newly inserted.
+ * - bool $add_inactive_folder_files When true: if a file is not in the database and its folder is not "active", it is added to the DB. Default false: new files are not added to the database if the folder is not active.
+ * @return array A list of files in the following format:
+ * Array(
+ * [_2] => Array(
+ * [file_id] => 2
+ * [folder_id] => 7
+ * [path] => {{ROOT}}/custom-path/image-1.jpg
+ * [optimization_level] => null
+ * [status] => null
+ * [file_path] => /absolute/path/to/custom-path/image-1.jpg
+ * ),
+ * [_3] => Array(
+ * [file_id] => 3
+ * [folder_id] => 7
+ * [path] => {{ROOT}}/custom-path/image-2.jpg
+ * [optimization_level] => 2
+ * [status] => success
+ * [file_path] => /absolute/path/to/custom-path/image-2.jpg
+ * ),
+ * [_6] => Array(
+ * [file_id] => 6
+ * [folder_id] => 13
+ * [path] => {{CONTENT}}/another-custom-path/image-1.jpg
+ * [optimization_level] => 0
+ * [status] => error
+ * [file_path] => /absolute/path/to/wp-content/another-custom-path/image-1.jpg
+ * ),
+ * )
+ * The fields 'optimization_level' and 'status' are set only if the argument 'optimization_level' was set.
+ */
+ public static function get_files_from_folders( $folders, $args = array() ) {
+ global $wpdb;
+
+ if ( ! $folders ) {
+ return array();
+ }
+
+ $filesystem = imagify_get_filesystem();
+ $files_db = Imagify_Files_DB::get_instance();
+ $files_table = $files_db->get_table_name();
+ $files_key = $files_db->get_primary_key();
+ $files_key_esc = esc_sql( $files_key );
+
+ $optimization = isset( $args['optimization_level'] ) && is_numeric( $args['optimization_level'] );
+ $no_new_files = ! empty( $args['return_only_old_files'] );
+ $add_inactive_folder_files = ! empty( $args['add_inactive_folder_files'] );
+
+ /**
+ * Scan folders for files. $files_from_scan will be in the following format:
+ * Array(
+ * [7] => Array(
+ * [/absolute/path/to/custom-path/image-1.jpg] => 0
+ * [/absolute/path/to/custom-path/image-2.jpg] => 1
+ * )
+ * [13] => Array(
+ * [/absolute/path/to/wp-content/another-custom-path/image-1.jpg] => 0
+ * [/absolute/path/to/wp-content/another-custom-path/image-2.jpg] => 1
+ * [/absolute/path/to/wp-content/another-custom-path/image-3.jpg] => 2
+ * )
+ * )
+ */
+ $files_from_scan = array();
+
+ foreach ( $folders as $folder_id => $folder ) {
+ $files_from_scan[ $folder_id ] = Imagify_Files_Scan::get_files_from_folder( $folder['folder_path'] );
+
+ if ( is_wp_error( $files_from_scan[ $folder_id ] ) ) {
+ unset( $files_from_scan[ $folder_id ] );
+ }
+ }
+
+ $files_from_scan = array_map( 'array_flip', $files_from_scan );
+
+ /**
+ * Get the files from DB. $files_from_db will be in the same format as the function output.
+ */
+ $already_optimized = array();
+ $folder_ids = array_keys( $folders );
+ $files_from_db = array_fill_keys( $folder_ids, array() );
+ $folder_ids = Imagify_DB::prepare_values_list( $folder_ids );
+ $select_fields = "$files_key_esc, folder_id, path" . ( $optimization ? ', optimization_level, status' : '' );
+
+ if ( $optimization ) {
+ $orderby = "
+ CASE status
+ WHEN 'already_optimized' THEN 3
+ WHEN 'error' THEN 2
+ ELSE 1
+ END ASC,
+ $files_key_esc DESC";
+ } else {
+ $orderby = "folder_id, $files_key_esc";
+ }
+
+ $results = $wpdb->get_results( "SELECT $select_fields FROM $files_table WHERE folder_id IN ( $folder_ids ) ORDER BY $orderby;", ARRAY_A ); // WPCS: unprepared SQL ok.
+
+ if ( $results ) {
+ $wpdb->flush();
+
+ foreach ( $results as $i => $row_fields ) {
+ // Cast the row.
+ $row_fields = $files_db->cast_row( $row_fields );
+
+ // Add the absolute path.
+ $row_fields['file_path'] = Imagify_Files_Scan::remove_placeholder( $row_fields['path'] );
+
+ // Remove the file from the scan.
+ unset( $files_from_scan[ $row_fields['folder_id'] ][ $row_fields['file_path'] ] );
+
+ if ( $optimization ) {
+ if ( 'error' !== $row_fields['status'] && $row_fields['optimization_level'] === $args['optimization_level'] ) {
+ // Try the same level only if the status is an error.
+ continue;
+ }
+
+ if ( 'already_optimized' === $row_fields['status'] && $row_fields['optimization_level'] >= $args['optimization_level'] ) {
+ // If the image is already compressed, optimize only if the requested level is higher.
+ continue;
+ }
+
+ if ( 'success' === $row_fields['status'] && $args['optimization_level'] !== $row_fields['optimization_level'] ) {
+ $file_backup_path = self::get_file_backup_path( $row_fields['file_path'] );
+
+ if ( ! $file_backup_path || ! $filesystem->exists( $file_backup_path ) ) {
+ // Don't try to re-optimize if there is no backup file.
+ continue;
+ }
+ }
+ }
+
+ if ( ! $filesystem->exists( $row_fields['file_path'] ) ) {
+ // If the file doesn't exist: remove all traces of it and bail out.
+ self::delete_file( array(
+ 'file_id' => $row_fields[ $files_key ],
+ 'file_path' => $row_fields['file_path'],
+ ) );
+ continue;
+ }
+
+ if ( $optimization && 'already_optimized' === $row_fields['status'] ) {
+ $already_optimized[ '_' . $row_fields[ $files_key ] ] = 1;
+ }
+
+ // Add the row to the list.
+ $files_from_db[ $row_fields['folder_id'] ][ '_' . $row_fields[ $files_key ] ] = $row_fields;
+ }
+ }
+
+ unset( $results );
+ $files_from_scan = array_filter( $files_from_scan );
+
+ // Make sure files from the scan are not already in the DB with another folder (shouldn't be possible, but, you know...).
+ if ( $files_from_scan ) {
+ $folders_by_placeholder = array();
+
+ foreach ( $files_from_scan as $folder_id => $folder_files ) {
+ foreach ( $folder_files as $file_path => $i ) {
+ $placeholder = Imagify_Files_Scan::add_placeholder( $file_path );
+
+ $folders_by_placeholder[ $placeholder ] = $folder_id;
+ $files_from_scan[ $folder_id ][ $file_path ] = $placeholder;
+ }
+ }
+
+ $placeholders = Imagify_DB::prepare_values_list( array_keys( $folders_by_placeholder ) );
+ $select_fields = "$files_key_esc, folder_id, path" . ( $optimization ? ', optimization_level, status' : '' );
+
+ $results = $wpdb->get_results( "SELECT $select_fields FROM $files_table WHERE path IN ( $placeholders ) ORDER BY folder_id, $files_key_esc;", ARRAY_A ); // WPCS: unprepared SQL ok.
+
+ if ( $results ) {
+ // Damn...
+ $wpdb->flush();
+
+ foreach ( $results as $i => $row_fields ) {
+ // Cast the row.
+ $row_fields = $files_db->cast_row( $row_fields );
+ $old_folder_id = $row_fields['folder_id'];
+
+ // Add the absolute path.
+ $row_fields['file_path'] = Imagify_Files_Scan::remove_placeholder( $row_fields['path'] );
+
+ // Set the new folder ID.
+ $row_fields['folder_id'] = $folders_by_placeholder[ $row_fields['path'] ];
+
+ // Remove the file from everywhere.
+ unset(
+ $files_from_db[ $old_folder_id ][ '_' . $row_fields[ $files_key ] ],
+ $files_from_scan[ $old_folder_id ][ $row_fields['file_path'] ],
+ $files_from_scan[ $row_fields['folder_id'] ][ $row_fields['file_path'] ]
+ );
+
+ if ( $optimization ) {
+ if ( 'error' !== $row_fields['status'] && $row_fields['optimization_level'] === $args['optimization_level'] ) {
+ // Try the same level only if the status is an error.
+ continue;
+ }
+
+ if ( 'already_optimized' === $row_fields['status'] && $row_fields['optimization_level'] >= $args['optimization_level'] ) {
+ // If the image is already compressed, optimize only if the requested level is higher.
+ continue;
+ }
+
+ if ( 'success' === $row_fields['status'] && $args['optimization_level'] !== $row_fields['optimization_level'] ) {
+ $file_backup_path = self::get_file_backup_path( $row_fields['file_path'] );
+
+ if ( ! $file_backup_path || ! $filesystem->exists( $file_backup_path ) ) {
+ // Don't try to re-optimize if there is no backup file.
+ continue;
+ }
+ }
+ }
+
+ if ( ! $filesystem->exists( $row_fields['file_path'] ) ) {
+ // If the file doesn't exist: remove all traces of it and bail out.
+ self::delete_file( array(
+ 'file_id' => $row_fields[ $files_key ],
+ 'file_path' => $row_fields['file_path'],
+ ) );
+ continue;
+ }
+
+ // Set the correct folder ID in the DB.
+ $success = $files_db->update( $row_fields[ $files_key ], array(
+ 'folder_id' => $row_fields['folder_id'],
+ ) );
+
+ if ( $success ) {
+ if ( $optimization && 'already_optimized' === $row_fields['status'] ) {
+ $already_optimized[ '_' . $row_fields[ $files_key ] ] = 1;
+ }
+
+ $files_from_db[ $row_fields['folder_id'] ][ '_' . $row_fields[ $files_key ] ] = $row_fields;
+ }
+ }
+ }
+
+ unset( $results, $folders_by_placeholder );
+ }
+
+ $files_from_scan = array_filter( $files_from_scan );
+
+ // Insert the remaining files into the DB.
+ if ( $files_from_scan ) {
+ foreach ( $files_from_scan as $folder_id => $placeholders ) {
+ // Don't add the file to the DB if its folder is not "active".
+ if ( ! $add_inactive_folder_files && empty( $folders[ $folder_id ]['active'] ) ) {
+ unset( $files_from_scan[ $folder_id ] );
+ continue;
+ }
+
+ foreach ( $placeholders as $file_path => $placeholder ) {
+ $file_id = self::insert_file( array(
+ 'folder_id' => $folder_id,
+ 'path' => $placeholder,
+ 'file_path' => $file_path,
+ ) );
+
+ if ( $file_id && ! $no_new_files ) {
+ $files_from_db[ $folder_id ][ '_' . $file_id ] = array(
+ 'file_id' => $file_id,
+ 'folder_id' => $folder_id,
+ 'path' => $placeholder,
+ 'optimization_level' => null,
+ 'status' => null,
+ 'file_path' => $file_path,
+ );
+ }
+ }
+
+ unset( $files_from_scan[ $folder_id ] );
+ }
+ }
+
+ $files_from_db = array_filter( $files_from_db );
+
+ if ( ! $files_from_db ) {
+ return array();
+ }
+
+ $files_from_db = call_user_func_array( 'array_merge', array_values( $files_from_db ) );
+
+ if ( $already_optimized ) {
+ // Put the files already optimized at the end of the list.
+ $already_optimized = array_intersect_key( $files_from_db, $already_optimized );
+ $files_from_db = array_diff_key( $files_from_db, $already_optimized );
+ $files_from_db = array_merge( $files_from_db, $already_optimized );
+ }
+
+ return $files_from_db;
+ }
+
+ /**
+ * Check if files inside the given folders have been modified, and update the database accordingly.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param array $folders A list of folders. See Imagify_Custom_Folders::get_folders() for the format.
+ */
+ public static function synchronize_files_from_folders( $folders ) {
+ global $wpdb;
+ /**
+ * Get the files from DB, and from the folder.
+ */
+ $files = self::get_files_from_folders( $folders, array(
+ 'return_only_old_files' => true,
+ ) );
+
+ if ( ! $files ) {
+ // This folder doesn't have (new) images.
+ return;
+ }
+
+ $files_db = Imagify_Files_DB::get_instance();
+ $files_table = $files_db->get_table_name();
+ $files_key = $files_db->get_primary_key();
+ $files_key_esc = esc_sql( $files_key );
+ $file_ids = wp_list_pluck( $files, $files_key );
+ $file_ids = Imagify_DB::prepare_values_list( $file_ids );
+ $results = $wpdb->get_results( "SELECT * FROM $files_table WHERE $files_key IN ( $file_ids ) ORDER BY $files_key_esc;", ARRAY_A ); // WPCS: unprepared SQL ok.
+
+ if ( ! $results ) {
+ // WAT?!
+ return;
+ }
+
+ // Caching the folders will prevent unecessary SQL queries in Imagify_Custom_Folders::refresh_file().
+ foreach ( $folders as $folder_id => $folder ) {
+ wp_cache_set( 'custom_folder_' . $folder_id, $folder, 'imagify' );
+ }
+
+ // Finally, refresh the files data.
+ foreach ( $results as $file ) {
+ $file = $files_db->cast_row( $file );
+ $folder_id = $file['folder_id'];
+ $process = imagify_get_optimization_process( $file, 'custom-folders' );
+
+ self::refresh_file( $process, $folders[ $folder_id ]['active'] );
+ }
+
+ foreach ( $folders as $folder_id => $folder ) {
+ wp_cache_delete( 'custom_folder_' . $folder_id, 'imagify' );
+ }
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** WHEN SAVING SELECTED FOLDERS ============================================================ */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Dectivate all active folders.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ */
+ public static function deactivate_all_folders() {
+ self::deactivate_not_selected_folders();
+ }
+
+ /**
+ * Dectivate folders that are not selected.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param array|object|string $selected_paths A list of "placeholdered" paths corresponding to the selected folders.
+ */
+ public static function deactivate_not_selected_folders( $selected_paths = array() ) {
+ global $wpdb;
+
+ $folders_table = Imagify_Folders_DB::get_instance()->get_table_name();
+
+ if ( $selected_paths ) {
+ if ( is_array( $selected_paths ) || is_object( $selected_paths ) ) {
+ $selected_paths = Imagify_DB::prepare_values_list( $selected_paths );
+ }
+
+ $selected_paths_clause = "AND path NOT IN ( $selected_paths )";
+ } else {
+ $selected_paths_clause = '';
+ }
+
+ // Remove the active status from the folders that are not selected.
+ $wpdb->query( "UPDATE $folders_table SET active = 0 WHERE active != 0 $selected_paths_clause" ); // WPCS: unprepared SQL ok.
+ }
+
+ /**
+ * Activate folders that are selected.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param array|object $selected_paths A list of "placeholdered" paths corresponding to the selected folders.
+ * @return array An array of paths of folders that are not in the DB.
+ */
+ public static function activate_selected_folders( $selected_paths ) {
+ global $wpdb;
+
+ if ( ! $selected_paths ) {
+ return $selected_paths;
+ }
+
+ $folders_db = Imagify_Folders_DB::get_instance();
+ $folders_table = $folders_db->get_table_name();
+ $folders_key = $folders_db->get_primary_key();
+
+ $selected_paths = (array) $selected_paths;
+ $selected_in = Imagify_DB::prepare_values_list( $selected_paths );
+
+ // Get folders that already are in the DB.
+ $folders = $wpdb->get_results( "SELECT * FROM $folders_table WHERE path IN ( $selected_in );", ARRAY_A ); // WPCS: unprepared SQL ok.
+
+ if ( ! $folders ) {
+ return $selected_paths;
+ }
+
+ $selected_paths = array_flip( $selected_paths );
+
+ foreach ( $folders as $folder ) {
+ $folder = $folders_db->cast_row( $folder );
+
+ if ( Imagify_Files_Scan::placeholder_path_exists( $folder['path'] ) ) {
+ if ( ! $folder['active'] ) {
+ // Add the active status only if not already set and if the folder exists.
+ $folders_db->update( $folder[ $folders_key ], array(
+ 'active' => 1,
+ ) );
+ }
+ } else {
+ // Remove the active status if the folder does not exist.
+ $folders_db->update( $folder[ $folders_key ], array(
+ 'active' => 0,
+ ) );
+ }
+
+ // Remove the path from the selected list, so the remaining will be created.
+ unset( $selected_paths[ $folder['path'] ] );
+ }
+
+ // Paths of folders that are not in the DB.
+ return array_flip( $selected_paths );
+ }
+
+ /**
+ * Insert folders into the database.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param array $folders An array of "placeholdered" paths.
+ * @return array An array of folder IDs.
+ */
+ public static function insert_folders( $folders ) {
+ if ( ! $folders ) {
+ return array();
+ }
+
+ $folder_ids = array();
+ $filesystem = imagify_get_filesystem();
+ $folders_db = Imagify_Folders_DB::get_instance();
+
+ foreach ( $folders as $placeholder ) {
+ $full_path = Imagify_Files_Scan::remove_placeholder( $placeholder );
+ $full_path = realpath( $full_path );
+
+ if ( ! $full_path || ! $filesystem->is_readable( $full_path ) || ! $filesystem->is_dir( $full_path ) ) {
+ continue;
+ }
+
+ if ( Imagify_Files_Scan::is_path_forbidden( trailingslashit( $full_path ) ) ) {
+ continue;
+ }
+
+ $folder_ids[] = $folders_db->insert( array(
+ 'path' => $placeholder,
+ 'active' => 1,
+ ) );
+ }
+
+ return array_filter( $folder_ids );
+ }
+
+ /**
+ * Remove files that are in inactive folders and are not optimized.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ */
+ public static function remove_unoptimized_files_from_inactive_folders() {
+ global $wpdb;
+
+ $folders_db = Imagify_Folders_DB::get_instance();
+ $folders_key = $folders_db->get_primary_key();
+ $files_table = Imagify_Files_DB::get_instance()->get_table_name();
+ $folder_ids = $folders_db->get_active_folders_column( $folders_key );
+
+ if ( $folder_ids ) {
+ $folder_ids = Imagify_DB::prepare_values_list( $folder_ids );
+
+ $wpdb->query( "DELETE FROM $files_table WHERE folder_id NOT IN ( $folder_ids ) AND ( status != 'success' OR status IS NULL )" ); // WPCS: unprepared SQL ok.
+ } else {
+ $wpdb->query( "DELETE FROM $files_table WHERE status != 'success' OR status IS NULL" ); // WPCS: unprepared SQL ok.
+ }
+ }
+
+ /**
+ * Reassign inactive files to active folders.
+ * Example:
+ * - Consider the file "/a/b/c/d/file.png".
+ * - The folder "/a/b/c/", previously active, becomes inactive.
+ * - The folder "/a/b/", previously inactive, becomes active.
+ * - The file is reassigned to the folder "/a/b/".
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ */
+ public static function reassign_inactive_files() {
+ global $wpdb;
+
+ $folders_db = Imagify_Folders_DB::get_instance();
+ $folders_table = $folders_db->get_table_name();
+ $folders_key = $folders_db->get_primary_key();
+ $folders_key_esc = esc_sql( $folders_key );
+
+ $files_db = Imagify_Files_DB::get_instance();
+ $files_table = $files_db->get_table_name();
+ $files_key = $files_db->get_primary_key();
+ $files_key_esc = esc_sql( $files_key );
+
+ // All active folders.
+ $active_folders = $wpdb->get_results( "SELECT $folders_key_esc, path FROM $folders_table WHERE active = 1;", ARRAY_A ); // WPCS: unprepared SQL ok.
+
+ if ( ! $active_folders ) {
+ return;
+ }
+
+ $active_folder_ids = array();
+ $has_site_root = false;
+
+ foreach ( $active_folders as $i => $active_folder ) {
+ $active_folders[ $i ] = $folders_db->cast_row( $active_folder );
+ $active_folder_ids[] = $active_folders[ $i ][ $folders_key ];
+
+ if ( '{{ROOT}}/' === $active_folders[ $i ]['path'] ) {
+ $has_site_root = true;
+ break;
+ }
+ }
+
+ // Files not in active folders.
+ $active_folder_ids = Imagify_DB::prepare_values_list( $active_folder_ids );
+ $inactive_files = $wpdb->get_results( "SELECT $files_key_esc, path FROM $files_table WHERE folder_id NOT IN ( $active_folder_ids )", ARRAY_A ); // WPCS: unprepared SQL ok.
+
+ if ( ! $inactive_files ) {
+ return;
+ }
+
+ $filesystem = imagify_get_filesystem();
+ $file_ids_by_folder = array();
+ $active_folders = self::sort_folders( $active_folders, true );
+
+ foreach ( $inactive_files as $inactive_file ) {
+ $inactive_file = $files_db->cast_row( $inactive_file );
+ $inactive_file['full_path'] = Imagify_Files_Scan::remove_placeholder( $inactive_file['path'] );
+
+ if ( $has_site_root ) {
+ $inactive_file['dirname'] = $filesystem->dir_path( $inactive_file['full_path'] );
+ }
+
+ foreach ( $active_folders as $active_folder ) {
+ $folder_id = $active_folder[ $folders_key ];
+
+ if ( strpos( $inactive_file['full_path'], $active_folder['full_path'] ) !== 0 ) {
+ // The file is not in this folder.
+ continue;
+ }
+
+ if ( ! isset( $file_ids_by_folder[ $folder_id ] ) ) {
+ $file_ids_by_folder[ $folder_id ] = array();
+ }
+
+ if ( '{{ROOT}}/' === $active_folder['path'] ) {
+ // For the site's root: only direct childs.
+ if ( $inactive_file['dirname'] === $active_folder['full_path'] ) {
+ // This file is in the site's root folder.
+ $file_ids_by_folder[ $folder_id ][] = $inactive_file[ $files_key ];
+ }
+ break;
+ }
+
+ // This file is not in the site's root, but still a grand-child of this folder.
+ $file_ids_by_folder[ $folder_id ][] = $inactive_file[ $files_key ];
+ break;
+ }
+ }
+
+ $file_ids_by_folder = array_filter( $file_ids_by_folder );
+
+ if ( ! $file_ids_by_folder ) {
+ return;
+ }
+
+ // Set the new folder ID.
+ foreach ( $file_ids_by_folder as $folder_id => $file_ids ) {
+ $file_ids = Imagify_DB::prepare_values_list( $file_ids );
+
+ $wpdb->query( "UPDATE $files_table SET folder_id = $folder_id WHERE $files_key_esc IN ( $file_ids )" ); // WPCS: unprepared SQL ok.
+ }
+ }
+
+ /**
+ * Remove the given folders from the DB if they are inactive and have no files.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param array $folder_ids An array of folder IDs.
+ * @return int Number of removed folders.
+ */
+ public static function remove_empty_inactive_folders( $folder_ids = null ) {
+ global $wpdb;
+
+ $folders_db = Imagify_Folders_DB::get_instance();
+ $folders_table = $folders_db->get_table_name();
+ $folders_key = $folders_db->get_primary_key();
+ $folders_key_esc = esc_sql( $folders_key );
+ $files_table = Imagify_Files_DB::get_instance()->get_table_name();
+
+ $folder_ids = array_filter( (array) $folder_ids );
+
+ if ( $folder_ids ) {
+ $folder_ids = $folders_db->cast_col( $folder_ids, $folders_key );
+ $folder_ids = Imagify_DB::prepare_values_list( $folder_ids );
+ $in_clause = "folders.$folders_key_esc IN ( $folder_ids )";
+ } else {
+ $in_clause = '1=1';
+ }
+
+ // Within the range of given folder IDs, filter the ones that are inactive and have no files.
+ $results = $wpdb->get_col( // WPCS: unprepared SQL ok.
+ "
+ SELECT folders.$folders_key_esc FROM $folders_table AS folders
+ LEFT JOIN $files_table AS files ON folders.$folders_key_esc = files.folder_id
+ WHERE $in_clause
+ AND folders.active != 1
+ AND files.folder_id IS NULL"
+ );
+
+ if ( ! $results ) {
+ return 0;
+ }
+
+ $results = $folders_db->cast_col( $results, $folders_key );
+ $results = Imagify_DB::prepare_values_list( $results );
+
+ // Remove inactive folders with no files.
+ $wpdb->query( "DELETE FROM $folders_table WHERE $folders_key_esc IN ( $results )" ); // WPCS: unprepared SQL ok.
+
+ return (int) $wpdb->rows_affected;
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** TOOLS =================================================================================== */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Sort folders by full path.
+ * The row "full_path" is added to each folder.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param array $folders An array of folders with at least a "path" row.
+ * @param bool $reverse Reverse the order.
+ * @return array
+ */
+ public static function sort_folders( $folders, $reverse = false ) {
+ if ( ! $folders ) {
+ return array();
+ }
+
+ $keyed_folders = array();
+ $keyed_paths = array();
+
+ foreach ( $folders as $folder ) {
+ $folder = (array) $folder;
+ $folder['full_path'] = Imagify_Files_Scan::remove_placeholder( $folder['path'] );
+
+ $keyed_folders[ $folder['path'] ] = $folder;
+ $keyed_paths[ $folder['path'] ] = $folder['full_path'];
+ }
+
+ natcasesort( $keyed_paths );
+
+ if ( $reverse ) {
+ $keyed_paths = array_reverse( $keyed_paths, true );
+ }
+
+ $keyed_folders = array_merge( $keyed_paths, $keyed_folders );
+
+ return array_values( $keyed_folders );
+ }
+
+ /**
+ * Remove sub-paths: if 'a/b/' and 'a/b/c/' are in the array, we keep only the "parent" 'a/b/'.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param array $placeholders A list of "placeholdered" paths.
+ * @return array
+ */
+ public static function remove_sub_paths( $placeholders ) {
+ sort( $placeholders );
+
+ foreach ( $placeholders as $i => $placeholder_path ) {
+ if ( '{{ROOT}}/' === $placeholder_path ) {
+ continue;
+ }
+
+ if ( ! isset( $prev_path ) ) {
+ $prev_path = strtolower( Imagify_Files_Scan::remove_placeholder( $placeholder_path ) );
+ continue;
+ }
+
+ $placeholder_path = strtolower( Imagify_Files_Scan::remove_placeholder( $placeholder_path ) );
+
+ if ( strpos( $placeholder_path, $prev_path ) === 0 ) {
+ unset( $placeholders[ $i ] );
+ } else {
+ $prev_path = $placeholder_path;
+ }
+ }
+
+ return $placeholders;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/inc/classes/class-imagify-data.php b/wp/wp-content/plugins/imagify/inc/classes/class-imagify-data.php
new file mode 100644
index 00000000..0290fb36
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/classes/class-imagify-data.php
@@ -0,0 +1,103 @@
+ 0.0,
+ 'average_size_images_per_month' => 0.0,
+ 'previous_quota_percent' => 0.0,
+ );
+
+ /**
+ * The single instance of the class.
+ *
+ * @var object
+ * @since 1.7
+ * @access protected
+ */
+ protected static $_instance;
+
+ /**
+ * Get the main Instance.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ * @access public
+ *
+ * @return object Main instance.
+ */
+ public static function get_instance() {
+ if ( ! isset( self::$_instance ) ) {
+ self::$_instance = new self();
+ }
+
+ return self::$_instance;
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** SANITIZATION, VALIDATION ================================================================ */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Sanitize and validate an option value. Basic casts have been made.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ * @access public
+ *
+ * @param string $key The option key.
+ * @param mixed $value The value.
+ * @param mixed $default The default value.
+ * @return mixed
+ */
+ public function sanitize_and_validate_value( $key, $value, $default ) {
+ switch ( $key ) {
+ case 'total_size_images_library':
+ case 'average_size_images_per_month':
+ if ( $value <= 0 ) {
+ // Invalid.
+ return 0.0;
+ }
+ return $value;
+
+ case 'previous_quota_percent':
+ $value = round( $value, 1 );
+ return min( max( 0, $value ), 100 );
+ }
+
+ return false;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/inc/classes/class-imagify-db.php b/wp/wp-content/plugins/imagify/inc/classes/class-imagify-db.php
new file mode 100644
index 00000000..b457c214
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/classes/class-imagify-db.php
@@ -0,0 +1,580 @@
+query( $query ); // WPCS: unprepared SQL ok.
+ }
+ }
+
+ /**
+ * Change an array of values into a comma separated list, ready to be used in a `IN ()` clause.
+ *
+ * @since 1.6.13
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param array $values An array of values.
+ * @return string A comma separated list of values.
+ */
+ public static function prepare_values_list( $values ) {
+ $values = esc_sql( (array) $values );
+ $values = array_map( array( __CLASS__, 'quote_string' ), $values );
+ return implode( ',', $values );
+ }
+
+ /**
+ * Wrap a value in quotes, unless it's an integer.
+ *
+ * @since 1.6.13
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param int|string $value A value.
+ * @return int|string
+ */
+ public static function quote_string( $value ) {
+ return is_numeric( $value ) ? $value : "'" . addcslashes( $value, "'" ) . "'";
+ }
+
+ /**
+ * First half of escaping for LIKE special characters % and _ before preparing for MySQL.
+ * Use this only before wpdb::prepare() or esc_sql(). Reversing the order is very bad for security.
+ *
+ * Example Prepared Statement:
+ * $wild = '%';
+ * $find = 'only 43% of planets';
+ * $like = $wild . $wpdb->esc_like( $find ) . $wild;
+ * $sql = $wpdb->prepare( "SELECT * FROM $wpdb->posts WHERE post_content LIKE %s", $like );
+ *
+ * Example Escape Chain:
+ * $sql = esc_sql( $wpdb->esc_like( $input ) );
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param string $text The raw text to be escaped. The input typed by the user should have no extra or deleted slashes.
+ * @return string Text in the form of a LIKE phrase. The output is not SQL safe. Call $wpdb::prepare() or real_escape next.
+ */
+ public static function esc_like( $text ) {
+ global $wpdb;
+
+ if ( method_exists( $wpdb, 'esc_like' ) ) {
+ // Introduced in WP 4.0.0.
+ return $wpdb->esc_like( $text );
+ }
+
+ return addcslashes( $text, '_%\\' );
+ }
+
+ /**
+ * Get Imagify mime types, ready to be used in a `IN ()` clause.
+ *
+ * @since 1.6.13
+ * @since 1.9 Added $type parameter.
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param string $type One of 'image', 'not-image'. Any other value will return all mime types.
+ * @return string A comma separated list of mime types.
+ */
+ public static function get_mime_types( $type = null ) {
+ static $mime_types = [];
+
+ if ( empty( $type ) ) {
+ $type = 'all';
+ }
+
+ if ( ! isset( $mime_types[ $type ] ) ) {
+ $mime_types[ $type ] = self::prepare_values_list( imagify_get_mime_types( $type ) );
+ }
+
+ return $mime_types[ $type ];
+ }
+
+ /**
+ * Get post statuses related to attachments, ready to be used in a `IN ()` clause.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return string A comma separated list of post statuses.
+ */
+ public static function get_post_statuses() {
+ static $statuses;
+
+ if ( ! isset( $statuses ) ) {
+ $statuses = self::prepare_values_list( imagify_get_post_statuses() );
+ }
+
+ return $statuses;
+ }
+
+ /**
+ * Get the SQL JOIN clause to use to get only attachments that have the required WP metadata.
+ * It returns an empty string if the database has no attachments without the required metadada.
+ * It also triggers Imagify_DB::unlimit_joins().
+ *
+ * @param string $id_field An ID field to match the metadata ID against in the JOIN clause.
+ * Default is the posts table `ID` field, using the `p` alias: `p.ID`.
+ * In case of "false" value or PEBKAC, fallback to the same field without alias.
+ * @param bool $matching Set to false to get a query to fetch metas NOT matching the file extensions.
+ * @param bool $test Test if the site has attachments without required metadata before returning the query. False to bypass the test and get the query anyway.
+ * @param string $special_join_conditions Special conditions to apply on the join.
+ *
+ * @return string
+ * @author Grégory Viguier
+ *
+ * @since 1.7
+ * @access public
+ */
+ public static function get_required_wp_metadata_join_clause( $id_field = 'p.ID', $matching = true, $test = true, $special_join_conditions = '' ) {
+ global $wpdb;
+
+ if ( $test && ! imagify_has_attachments_without_required_metadata() ) {
+ return '';
+ }
+
+ self::unlimit_joins();
+ $clause = '';
+
+ if ( ! $id_field || ! is_string( $id_field ) ) {
+ $id_field = "$wpdb->posts.ID";
+ }
+
+ $join = $matching ? 'INNER' : 'LEFT';
+
+ $first = true;
+
+ foreach ( self::get_required_wp_metadata_aliases() as $meta_name => $alias ) {
+ if ( $first ) {
+ $first = false;
+ $clause .= "
+ $join JOIN $wpdb->postmeta AS $alias
+ ON ( $id_field = $alias.post_id AND $alias.meta_key = '$meta_name' $special_join_conditions )";
+ continue;
+ }
+ $clause .= "
+ $join JOIN $wpdb->postmeta AS $alias
+ ON ( $id_field = $alias.post_id AND $alias.meta_key = '$meta_name' )";
+ }
+
+ return $clause;
+ }
+
+ /**
+ * Get the SQL part to be used in a WHERE clause, to get only attachments that have (in)valid '_wp_attached_file' and '_wp_attachment_metadata' metadatas.
+ * It returns an empty string if the database has no attachments without the required metadada.
+ *
+ * @since 1.7
+ * @since 1.7.1.2 Use a single $arg parameter instead of 3. New $prepared parameter.
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param array $args {
+ * Optional. An array of arguments.
+ *
+ * string $aliases The aliases to use for the meta values.
+ * bool $matching Set to false to get a query to fetch invalid metas.
+ * bool $test Test if the site has attachments without required metadata before returning the query. False to bypass the test and get the query anyway.
+ * bool $prepared Set to true if the query will be prepared with using $wpdb->prepare().
+ * }.
+ * @return string A query.
+ */
+ public static function get_required_wp_metadata_where_clause( $args = array() ) {
+ static $query = array();
+
+ $args = imagify_merge_intersect( $args, array(
+ 'aliases' => array(),
+ 'matching' => true,
+ 'test' => true,
+ 'prepared' => false,
+ ) );
+
+ list( $aliases, $matching, $test, $prepared ) = array_values( $args );
+
+ if ( $test && ! imagify_has_attachments_without_required_metadata() ) {
+ return '';
+ }
+
+ if ( $aliases && is_string( $aliases ) ) {
+ $aliases = array(
+ '_wp_attached_file' => $aliases,
+ );
+ } elseif ( ! is_array( $aliases ) ) {
+ $aliases = array();
+ }
+
+ $aliases = imagify_merge_intersect( $aliases, self::get_required_wp_metadata_aliases() );
+ $key = implode( '|', $aliases ) . '|' . (int) $matching;
+
+ if ( isset( $query[ $key ] ) ) {
+ return $prepared ? str_replace( '%', '%%', $query[ $key ] ) : $query[ $key ];
+ }
+
+ unset( $args['prepared'] );
+ $alias_1 = $aliases['_wp_attached_file'];
+ $alias_2 = $aliases['_wp_attachment_metadata'];
+ $extensions = self::get_extensions_where_clause( $args );
+
+ if ( $matching ) {
+ $query[ $key ] = "AND $alias_1.meta_value NOT LIKE '%://%' AND $alias_1.meta_value NOT LIKE '_:\\\\\%' $extensions";
+ } else {
+ $query[ $key ] = "AND ( $alias_2.meta_value IS NULL OR $alias_1.meta_value IS NULL OR $alias_1.meta_value LIKE '%://%' OR $alias_1.meta_value LIKE '_:\\\\\%' $extensions )";
+ }
+
+ return $prepared ? str_replace( '%', '%%', $query[ $key ] ) : $query[ $key ];
+ }
+
+ /**
+ * Get the SQL part to be used in a WHERE clause, to get only attachments that have a valid file extensions.
+ * It returns an empty string if the database has no attachments without the required metadada.
+ *
+ * @since 1.7
+ * @since 1.7.1.2 Use a single $arg parameter instead of 3. New $prepared parameter.
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param array $args {
+ * Optional. An array of arguments.
+ *
+ * string $alias The alias to use for the meta value.
+ * bool $matching Set to false to get a query to fetch metas NOT matching the file extensions.
+ * bool $test Test if the site has attachments without required metadata before returning the query. False to bypass the test and get the query anyway.
+ * bool $prepared Set to true if the query will be prepared with using $wpdb->prepare().
+ * }.
+ * @return string A query.
+ */
+ public static function get_extensions_where_clause( $args = false ) {
+ static $extensions;
+ static $query = array();
+
+ $args = imagify_merge_intersect( $args, array(
+ 'alias' => array(),
+ 'matching' => true,
+ 'test' => true,
+ 'prepared' => false,
+ ) );
+
+ list( $alias, $matching, $test, $prepared ) = array_values( $args );
+
+ if ( $test && ! imagify_has_attachments_without_required_metadata() ) {
+ return '';
+ }
+
+ if ( ! isset( $extensions ) ) {
+ $extensions = array_keys( imagify_get_mime_types() );
+ $extensions = implode( '|', $extensions );
+ $extensions = explode( '|', $extensions );
+ $extensions = array_map(function ( $ex ) {
+ return strrev( $ex );
+ }, $extensions);
+ }
+
+ if ( ! $alias ) {
+ $alias = self::get_required_wp_metadata_aliases();
+ $alias = $alias['_wp_attached_file'];
+ }
+
+ $key = $alias . '|' . (int) $matching;
+
+ if ( isset( $query[ $key ] ) ) {
+ return $prepared ? str_replace( '%', '%%', $query[ $key ] ) : $query[ $key ];
+ }
+
+ $regex = '^' . implode( '\..*|^', $extensions ) . '\..*';
+
+ if ( $matching ) {
+ $query[ $key ] = "AND REVERSE (LOWER( $alias.meta_value )) REGEXP '$regex'";
+ } else {
+ $query[ $key ] = "AND REVERSE (LOWER( $alias.meta_value )) NOT REGEXP '$regex'";
+ }
+
+ return $prepared ? str_replace( '%', '%%', $query[ $key ] ) : $query[ $key ];
+ }
+
+ /**
+ * Get the aliases used for the metas in self::get_required_wp_metadata_join_clause(), self::get_required_wp_metadata_where_clause(), and self::get_extensions_where_clause().
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return array An array with the meta name as key and its alias as value.
+ */
+ public static function get_required_wp_metadata_aliases() {
+ return array(
+ '_wp_attached_file' => 'imrwpmt1',
+ '_wp_attachment_metadata' => 'imrwpmt2',
+ );
+ }
+
+ /**
+ * Combine two arrays with some specific keys.
+ * We use this function to combine the result of 2 SQL queries.
+ *
+ * @since 1.6.13
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param array $keys An array of keys.
+ * @param array $values An array of arrays like array( 'id' => id, 'value' => value ).
+ * @param int $keep_keys_order Set to true to return an array ordered like $keys instead of $values.
+ * @return array The combined arrays.
+ */
+ public static function combine_query_results( $keys, $values, $keep_keys_order = false ) {
+ if ( ! $keys || ! $values ) {
+ return array();
+ }
+
+ $result = array();
+ $keys = array_flip( $keys );
+
+ foreach ( $values as $v ) {
+ if ( isset( $keys[ $v['id'] ] ) ) {
+ $result[ $v['id'] ] = $v['value'];
+ }
+ }
+
+ if ( $keep_keys_order ) {
+ $keys = array_intersect_key( $keys, $result );
+ return array_replace( $keys, $result );
+ }
+
+ return $result;
+ }
+
+ /**
+ * A helper to retrieve all values from one or several post metas, given a list of post IDs.
+ * The $wpdb cache is flushed to save memory.
+ *
+ * @since 1.6.13
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param array $metas An array of meta names like:
+ * array(
+ * 'key1' => 'meta_name_1',
+ * 'key2' => 'meta_name_2',
+ * 'key3' => 'meta_name_3',
+ * )
+ * If a key contains 'data', the results will be unserialized.
+ * @param array $ids An array of post IDs.
+ * @return array An array of arrays of results like:
+ * array(
+ * 'key1' => array( post_id_1 => 'result_1', post_id_2 => 'result_2', post_id_3 => 'result_3' ),
+ * 'key2' => array( post_id_1 => 'result_4', post_id_3 => 'result_5' ),
+ * 'key3' => array( post_id_1 => 'result_6', post_id_2 => 'result_7' ),
+ * )
+ */
+ public static function get_metas( $metas, $ids ) {
+ global $wpdb;
+
+ if ( ! $ids ) {
+ return array_fill_keys( array_keys( $metas ), array() );
+ }
+
+ $sql_ids = implode( ',', $ids );
+
+ foreach ( $metas as $result_name => $meta_name ) {
+ $metas[ $result_name ] = $wpdb->get_results( // WPCS: unprepared SQL ok.
+ "SELECT pm.post_id as id, pm.meta_value as value
+ FROM $wpdb->postmeta as pm
+ WHERE pm.meta_key = '$meta_name'
+ AND pm.post_id IN ( $sql_ids )
+ ORDER BY pm.post_id DESC",
+ ARRAY_A
+ );
+
+ $wpdb->flush();
+ $metas[ $result_name ] = self::combine_query_results( $ids, $metas[ $result_name ], true );
+
+ if ( strpos( $result_name, 'data' ) !== false ) {
+ $metas[ $result_name ] = array_map( 'maybe_unserialize', $metas[ $result_name ] );
+ }
+ }
+
+ return $metas;
+ }
+
+ /**
+ * Create/Upgrade the table in the database.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param string $table_name The (prefixed) table name.
+ * @param string $schema_query Query representing the table schema.
+ * @return bool True on success. False otherwise.
+ */
+ public static function create_table( $table_name, $schema_query ) {
+ global $wpdb;
+
+ require_once ABSPATH . 'wp-admin/includes/upgrade.php';
+
+ $wpdb->hide_errors();
+
+ $schema_query = trim( $schema_query );
+ $charset_collate = $wpdb->get_charset_collate();
+
+ dbDelta( "CREATE TABLE $table_name ($schema_query) $charset_collate;" );
+
+ return empty( $wpdb->last_error ) && self::table_exists( $table_name );
+ }
+
+ /**
+ * Tell if the given table exists.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param string $table_name Full name of the table (with DB prefix).
+ * @return bool
+ */
+ public static function table_exists( $table_name ) {
+ global $wpdb;
+
+ $escaped_table = self::esc_like( $table_name );
+ $result = $wpdb->get_var( $wpdb->prepare( 'SHOW TABLES LIKE %s', $escaped_table ) );
+
+ return $result === $table_name;
+ }
+
+ /**
+ * Cache transients used for optimization process locks.
+ *
+ * @since 1.9
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param string $context The context.
+ * @param array $media_ids The media IDs.
+ */
+ public static function cache_process_locks( $context, $media_ids ) {
+ global $wpdb;
+
+ if ( ! $context || ! $media_ids || wp_using_ext_object_cache() ) {
+ return;
+ }
+
+ // Sanitize the IDs.
+ $media_ids = array_filter( $media_ids );
+ $media_ids = array_unique( $media_ids );
+
+ if ( ! $media_ids ) {
+ return;
+ }
+
+ $context_instance = imagify_get_context( $context );
+ $context = $context_instance->get_name();
+ $process_class_name = imagify_get_optimization_process_class_name( $context );
+ $transient_name = sprintf( $process_class_name::LOCK_NAME, $context, '%' );
+ $is_network_wide = $context_instance->is_network_wide();
+
+ // Do 1 DB query per context (and cache results) before doing 1 get_transient() (2 DB queries) per media ID.
+ $prefix = $is_network_wide ? '_site_transient_' : '_transient_';
+
+ if ( $is_network_wide && is_multisite() ) {
+ $network_id = function_exists( 'get_current_network_id' ) ? get_current_network_id() : (int) $wpdb->siteid;
+ $cache_prefix = "$network_id:";
+ $notoptions_key = "$network_id:notoptions";
+ $cache_group = 'site-options';
+ $results = $wpdb->get_results(
+ $wpdb->prepare(
+ "SELECT meta_key as name, meta_value as value FROM $wpdb->sitemeta WHERE ( meta_key LIKE %s OR meta_key LIKE %s ) AND site_id = %d",
+ $prefix . $transient_name,
+ $prefix . 'timeout_' . $transient_name,
+ $network_id
+ ),
+ OBJECT_K
+ ); // WPCS: unprepared SQL ok.
+ } else {
+ $cache_prefix = '';
+ $notoptions_key = 'notoptions';
+ $cache_group = 'options';
+ $results = $wpdb->get_results(
+ $wpdb->prepare(
+ "SELECT option_name as name, option_value as value FROM $wpdb->options WHERE ( option_name LIKE %s OR option_name LIKE %s )",
+ $prefix . $transient_name,
+ $prefix . 'timeout_' . $transient_name
+ ),
+ OBJECT_K
+ ); // WPCS: unprepared SQL ok.
+ }
+
+ $not_exist = [];
+
+ foreach ( [ '', 'timeout_' ] as $maybe_timeout ) {
+ foreach ( $media_ids as $id ) {
+ $option_name = $prefix . $maybe_timeout . str_replace( '%', $id, $transient_name );
+
+ if ( isset( $results[ $option_name ] ) ) {
+ // Cache the value.
+ $value = $results[ $option_name ]->value;
+ $value = maybe_unserialize( $value );
+ wp_cache_set( "$cache_prefix$option_name", $value, $cache_group );
+ } else {
+ // No value.
+ $not_exist[ $option_name ] = true;
+ }
+ }
+ }
+
+ if ( ! $not_exist ) {
+ return;
+ }
+
+ // Cache the options that don't exist in the DB.
+ $notoptions = wp_cache_get( $notoptions_key, $cache_group );
+ $notoptions = is_array( $notoptions ) ? $notoptions : [];
+ $notoptions = array_merge( $notoptions, $not_exist );
+
+ wp_cache_set( $notoptions_key, $notoptions, $cache_group );
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/inc/classes/class-imagify-files-db.php b/wp/wp-content/plugins/imagify/inc/classes/class-imagify-files-db.php
new file mode 100644
index 00000000..9da11a72
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/classes/class-imagify-files-db.php
@@ -0,0 +1,177 @@
+ '%d',
+ 'folder_id' => '%d',
+ 'file_date' => '%s',
+ 'path' => '%s',
+ 'hash' => '%s',
+ 'mime_type' => '%s',
+ 'modified' => '%d',
+ 'width' => '%d',
+ 'height' => '%d',
+ 'original_size' => '%d',
+ 'optimized_size' => '%d',
+ 'percent' => '%d',
+ 'optimization_level' => '%d',
+ 'status' => '%s',
+ 'error' => '%s',
+ 'data' => '%s',
+ );
+ }
+
+ /**
+ * Default column values.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return array
+ */
+ public function get_column_defaults() {
+ return array(
+ 'file_id' => 0,
+ 'folder_id' => 0,
+ 'file_date' => '0000-00-00 00:00:00',
+ 'path' => '',
+ 'hash' => '',
+ 'mime_type' => '',
+ 'modified' => 0,
+ 'width' => 0,
+ 'height' => 0,
+ 'original_size' => 0,
+ 'optimized_size' => null,
+ 'percent' => null,
+ 'optimization_level' => null,
+ 'status' => null,
+ 'error' => null,
+ 'data' => [],
+ );
+ }
+
+ /**
+ * Get the query to create the table fields.
+ *
+ * For with and height: `smallint(2) unsigned` means 65,535px max.
+ *
+ * @since 1.7
+ * @access protected
+ * @author Grégory Viguier
+ *
+ * @return string
+ */
+ protected function get_table_schema() {
+ return "
+ file_id bigint(20) unsigned NOT NULL auto_increment,
+ folder_id bigint(20) unsigned NOT NULL default 0,
+ file_date datetime NOT NULL default '0000-00-00 00:00:00',
+ path varchar(191) NOT NULL default '',
+ hash varchar(32) NOT NULL default '',
+ mime_type varchar(100) NOT NULL default '',
+ modified tinyint(1) unsigned NOT NULL default 0,
+ width smallint(2) unsigned NOT NULL default 0,
+ height smallint(2) unsigned NOT NULL default 0,
+ original_size int(4) unsigned NOT NULL default 0,
+ optimized_size int(4) unsigned default NULL,
+ percent smallint(2) unsigned default NULL,
+ optimization_level tinyint(1) unsigned default NULL,
+ status varchar(20) default NULL,
+ error varchar(255) default NULL,
+ data longtext default NULL,
+ PRIMARY KEY (file_id),
+ UNIQUE KEY path (path),
+ KEY folder_id (folder_id),
+ KEY optimization_level (optimization_level),
+ KEY status (status),
+ KEY modified (modified)";
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/inc/classes/class-imagify-files-iterator.php b/wp/wp-content/plugins/imagify/inc/classes/class-imagify-files-iterator.php
new file mode 100644
index 00000000..9e6c2dec
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/classes/class-imagify-files-iterator.php
@@ -0,0 +1,117 @@
+include_folders = (bool) $include_folders;
+ $this->filesystem = Imagify_Filesystem::get_instance();
+ }
+
+ /**
+ * Check whether the current element of the iterator is acceptable.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return bool Returns whether the current element of the iterator is acceptable through this filter.
+ */
+ public function accept(): bool {
+ static $extensions, $has_extension_method;
+
+ $file_path = $this->current()->getPathname();
+
+ // Prevent triggering an open_basedir restriction error.
+ $file_name = $this->filesystem->file_name( $file_path );
+
+ if ( '.' === $file_name || '..' === $file_name ) {
+ return false;
+ }
+
+ // Forbidden file/folder paths and names.
+ $is_dir = $this->isDir();
+
+ if ( $is_dir ) {
+ $file_path = trailingslashit( $file_path );
+ }
+
+ if ( Imagify_Files_Scan::is_path_forbidden( $file_path ) ) {
+ return false;
+ }
+
+ // OK for folders.
+ if ( $this->include_folders && $is_dir ) {
+ return true;
+ }
+
+ // Only files.
+ if ( ! $this->current()->isFile() ) {
+ return false;
+ }
+
+ // Only files with the required extension.
+ if ( ! isset( $extensions ) ) {
+ $extensions = array_keys( imagify_get_mime_types() );
+ $extensions = implode( '|', $extensions );
+ }
+
+ if ( ! isset( $has_extension_method ) ) {
+ // This method was introduced in php 5.3.6.
+ $has_extension_method = method_exists( $this->current(), 'getExtension' );
+ }
+
+ if ( $has_extension_method ) {
+ $file_extension = strtolower( $this->current()->getExtension() );
+ } else {
+ $file_extension = strtolower( $this->filesystem->path_info( $file_path, 'extension' ) );
+ }
+
+ return preg_match( '@^' . $extensions . '$@', $file_extension );
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/inc/classes/class-imagify-files-list-table.php b/wp/wp-content/plugins/imagify/inc/classes/class-imagify-files-list-table.php
new file mode 100644
index 00000000..ae332d90
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/classes/class-imagify-files-list-table.php
@@ -0,0 +1,1043 @@
+ 'imagify-files',
+ 'screen' => isset( $args['screen'] ) ? convert_to_screen( $args['screen'] ) : null,
+ ) );
+
+ $this->modes = array(
+ 'list' => __( 'List View', 'imagify' ),
+ );
+
+ $this->filesystem = Imagify_Filesystem::get_instance();
+ $this->views = Imagify_Views::get_instance();
+ }
+
+ /**
+ * Prepares the list of items for displaying.
+ *
+ * @since 1.7
+ */
+ public function prepare_items() {
+ global $wpdb;
+
+ add_screen_option( 'per_page', array(
+ 'label' => __( 'Number of files per page', 'imagify' ),
+ 'default' => 20,
+ 'option' => self::PER_PAGE_OPTION,
+ ) );
+
+ $files_db = Imagify_Files_DB::get_instance();
+ $files_table = $files_db->get_table_name();
+ $files_key = $files_db->get_primary_key();
+ $files_key_esc = esc_sql( $files_key );
+ $per_page = $this->get_items_per_page( self::PER_PAGE_OPTION );
+
+ // Prepare the query to get items.
+ $page = $this->get_pagenum();
+ $offset = ( $page - 1 ) * $per_page;
+ $orderbys = $this->get_sortable_columns();
+ $orderby = 'path';
+ $order = 'ASC';
+ $folders = array();
+ $file_ids = array();
+ $where = '';
+
+ $sent_orderby = isset( $_GET['orderby'] ) ? htmlspecialchars( wp_unslash( $_GET['orderby'] ) ) : ''; // phpcs:ignore WordPress.Security.NonceVerification.Missing, WordPress.Security.NonceVerification.Recommended
+ $sent_order = isset( $_GET['order'] ) ? htmlspecialchars( wp_unslash( $_GET['order'] ) ) : ''; // phpcs:ignore WordPress.Security.NonceVerification.Missing, WordPress.Security.NonceVerification.Recommended
+ $folder_filter = self::get_folder_filter();
+ $status_filter = self::get_status_filter();
+
+ if ( ! empty( $sent_orderby ) && isset( $orderbys[ $sent_orderby ] ) ) {
+ $orderby = $sent_orderby;
+ $order = is_array( $orderbys[ $orderby ] ) ? 'DESC' : 'ASC';
+
+ if ( 'optimization' === $orderby ) {
+ $orderby = 'percent';
+ }
+ }
+
+ if ( $sent_order ) {
+ $order = 'ASC' === strtoupper( $sent_order ) ? 'ASC' : 'DESC';
+ }
+
+ if ( $folder_filter ) {
+ // Display only files from a specific custom folder.
+ $where = "WHERE folder_id = $folder_filter";
+ }
+
+ if ( $status_filter ) {
+ // Display files optimized, not optimized, or with error.
+ $where .= $where ? ' AND ' : 'WHERE ';
+
+ switch ( $status_filter ) {
+ case 'optimized':
+ $where .= "( status = 'success' OR status = 'already_optimized' )";
+ break;
+ case 'unoptimized':
+ $where .= 'status IS NULL';
+ break;
+ case 'errors':
+ $where .= "status = 'error'";
+ break;
+ }
+ }
+
+ // Pagination.
+ $this->set_pagination_args( array(
+ 'total_items' => (int) $wpdb->get_var( "SELECT COUNT($files_key_esc) FROM $files_table $where" ), // WPCS: unprepared SQL ok.
+ 'per_page' => $per_page,
+ ) );
+
+ // Get items.
+ $this->items = $wpdb->get_results( $wpdb->prepare( "SELECT * FROM $files_table $where ORDER BY $orderby $order LIMIT %d, %d", $offset, $per_page ) ); // WPCS: unprepared SQL ok.
+
+ if ( ! $this->items ) {
+ return;
+ }
+
+ // Prepare items.
+ foreach ( $this->items as $i => $item ) {
+ // Cast values.
+ $item = $files_db->cast_row( $item );
+
+ // Store the folders used by the items to get their data later in 1 query.
+ $folders[ $item->folder_id ] = $item->folder_id;
+
+ // Store the item IDs to store transients later in 1 query.
+ $file_ids[ $item->$files_key ] = $item->$files_key;
+
+ // Use Imagify objects + add related folder ID and path (set later).
+ $this->items[ $i ] = (object) [
+ 'process' => imagify_get_optimization_process( $item, 'custom-folders' ),
+ 'folder_id' => $item->folder_id,
+ 'folder_path' => false,
+ 'is_folder_active' => true,
+ ];
+
+ if ( ! $this->items[ $i ]->process->is_valid() ) {
+ unset( $this->items[ $i ] );
+ }
+ }
+
+ $folders = array_filter( $folders );
+
+ // Cache transient values.
+ Imagify_DB::cache_process_locks( 'custom-folders', $file_ids );
+
+ if ( ! $folders ) {
+ return;
+ }
+
+ // Get folders data.
+ $folders_db = Imagify_Folders_DB::get_instance();
+ $folders_table = $folders_db->get_table_name();
+ $folders_key_esc = esc_sql( $folders_db->get_primary_key() );
+ $folders = Imagify_DB::prepare_values_list( $folders );
+ $folders = $wpdb->get_results( "SELECT * FROM $folders_table WHERE $folders_key_esc IN ( $folders )" ); // WPCS: unprepared SQL ok.
+
+ if ( ! $folders ) {
+ return;
+ }
+
+ // Cast folders data and store data into a property.
+ foreach ( $folders as $folder ) {
+ $folder = $folders_db->cast_row( $folder );
+
+ $this->folders[ $folder->folder_id ] = $folder;
+ }
+
+ // Set folders path to each item.
+ foreach ( $this->items as $i => $item ) {
+ if ( $item->folder_id && isset( $this->folders[ $item->folder_id ] ) ) {
+ $item->folder_path = $this->folders[ $item->folder_id ]->path;
+ $item->is_folder_active = (bool) $this->folders[ $item->folder_id ]->active;
+ }
+ }
+
+ // Button templates.
+ Imagify_Views::get_instance()->print_js_template_in_footer( 'button/processing' );
+ }
+
+ /**
+ * Message to be displayed when there are no items.
+ *
+ * @since 1.7
+ */
+ public function no_items() {
+ if ( self::get_status_filter() ) {
+ // Filter by status.
+ switch ( self::get_status_filter() ) {
+ case 'optimized':
+ /* translators: 1 is a link tag start, 2 is the link tag end. */
+ printf( esc_html__( 'No optimized files. Have you tried the %1$sbulk optimization%2$s yet?', 'imagify' ), '', ' ' );
+ return;
+
+ case 'unoptimized':
+ esc_html_e( 'No unoptimized files, hurray!', 'imagify' );
+ return;
+
+ case 'errors':
+ esc_html_e( 'No errors, hurray!', 'imagify' );
+ return;
+ }
+ }
+
+ $args = array(
+ 'action' => 'imagify_scan_custom_folders',
+ '_wpnonce' => wp_create_nonce( 'imagify_scan_custom_folders' ),
+ '_wp_http_referer' => get_imagify_admin_url( 'files-list' ),
+ );
+
+ if ( self::get_folder_filter() ) {
+ // A specific custom folder (selected or not).
+ $args['folder'] = self::get_folder_filter();
+ $args['_wp_http_referer'] = rawurlencode( add_query_arg( 'folder-filter', self::get_folder_filter(), $args['_wp_http_referer'] ) );
+
+ printf(
+ /* translators: 1 and 2 are link tag starts, 3 is a link tag end. */
+ esc_html__( 'No files yet. Do you want to %1$sscan this folder%3$s for new files or launch a %2$sbulk optimization%3$s directly?', 'imagify' ),
+ '',
+ ' ',
+ ' '
+ );
+ return;
+ }
+
+ if ( Imagify_Folders_DB::get_instance()->has_active_folders() ) {
+ // All selected custom folders.
+ $args['_wp_http_referer'] = rawurlencode( $args['_wp_http_referer'] );
+ printf(
+ /* translators: 1 and 2 are link tag starts, 3 is a link tag end. */
+ esc_html__( 'No files yet. Do you want to %1$sscan your selected folders%3$s for new files or launch a %2$sbulk optimization%3$s directly?', 'imagify' ),
+ '',
+ ' ',
+ ' '
+ );
+ return;
+ }
+
+ // Nothing selected in the settings.
+ printf(
+ /* translators: 1 is a link tag start, 2 is the link tag end. */
+ esc_html__( 'To see things appear here, you must select folders in the settings page first :)', 'imagify' ),
+ '',
+ ' '
+ );
+ }
+
+ /**
+ * Display views.
+ *
+ * @since 1.7
+ */
+ public function views() {
+ global $wpdb;
+
+ // Get all folders.
+ $folders_table = Imagify_Folders_DB::get_instance()->get_table_name();
+ $folders = $wpdb->get_results( "SELECT folder_id, path FROM $folders_table" ); // WPCS: unprepared SQL ok.
+
+ if ( ! $folders ) {
+ return;
+ }
+
+ $files_db = Imagify_Files_DB::get_instance();
+ $files_table = $files_db->get_table_name();
+ $files_key_esc = esc_sql( $files_db->get_primary_key() );
+
+ // Filter files by folder.
+ $folder_filters = array();
+ $root_id = 0;
+ $counts = $wpdb->get_results( "SELECT folder_id, COUNT( $files_key_esc ) AS count FROM $files_table GROUP BY folder_id", OBJECT_K ); // WPCS: unprepared SQL ok.
+
+ foreach ( $folders as $folder ) {
+ if ( '{{ROOT}}/' === $folder->path ) {
+ $root_id = $folder->folder_id;
+ $folder_filters[ $folder->folder_id ] = '/';
+ } else {
+ $folder_filters[ $folder->folder_id ] = '/' . trim( $this->filesystem->make_path_relative( Imagify_Files_Scan::remove_placeholder( $folder->path ) ), '/' );
+ }
+ }
+
+ natcasesort( $folder_filters );
+
+ if ( $root_id ) {
+ $folder_filters[ $root_id ] = __( 'Site\'s root', 'imagify' );
+ }
+
+ foreach ( $folder_filters as $folder_id => $label ) {
+ $folder_filters[ $folder_id ] .= ' (' . ( isset( $counts[ $folder_id ] ) ? (int) $counts[ $folder_id ]->count : 0 ) . ')';
+ }
+
+ // Filter files by status.
+ $counts = $wpdb->get_results( "SELECT status, COUNT( $files_key_esc ) AS count FROM $files_table GROUP BY status", OBJECT_K ); // WPCS: unprepared SQL ok.
+ $status_filters = array(
+ 'optimized' => 0,
+ 'unoptimized' => 0,
+ 'errors' => 0,
+ );
+
+ if ( isset( $counts['success'] ) ) {
+ $status_filters['optimized'] += $counts['success']->count;
+ }
+
+ if ( isset( $counts['already_optimized'] ) ) {
+ $status_filters['optimized'] += $counts['already_optimized']->count;
+ }
+
+ if ( isset( $counts[''] ) ) {
+ $status_filters['unoptimized'] += $counts['']->count;
+ }
+
+ if ( isset( $counts['error'] ) ) {
+ $status_filters['errors'] += $counts['error']->count;
+ }
+
+ $status_filters = array(
+ '' => __( 'All Media Files', 'imagify' ),
+ 'optimized' => _x( 'Optimized', 'Media Files', 'imagify' ) . ' (' . $status_filters['optimized'] . ')',
+ 'unoptimized' => _x( 'Unoptimized', 'Media Files', 'imagify' ) . ' (' . $status_filters['unoptimized'] . ')',
+ 'errors' => _x( 'Errors', 'Media Files', 'imagify' ) . ' (' . $status_filters['errors'] . ')',
+ );
+
+ // Get submitted values.
+ $folder_filter = self::get_folder_filter();
+ $status_filter = self::get_status_filter();
+
+ // Display the filters.
+ if ( method_exists( $this->screen, 'render_screen_reader_content' ) ) {
+ // Introduced in WP 4.4.
+ $this->screen->render_screen_reader_content( 'heading_views' );
+ }
+ ?>
+
+
+
+
+
+ %s', '', selected( $folder_filter, 0, false ), esc_html__( 'All Folders', 'imagify' ) );
+
+ foreach ( $folder_filters as $folder_id => $label ) {
+ printf( '%s ', $folder_id, selected( $folder_filter, $folder_id, false ), esc_html( $label ) );
+ }
+ ?>
+
+
+
+
+ $label ) {
+ printf( '%s ', $status, selected( $status_filter, $status, false ), esc_html( $label ) );
+ }
+ ?>
+
+
+ 'folders-query-submit' ) ); ?>
+
+ extra_tablenav( 'bar' ); ?>
+
+
+ option_title ) with the list of bulk actions available on this table.
+ *
+ * @since 1.7
+ *
+ * @return array
+ */
+ public function get_bulk_actions() {
+ return array(
+ 'imagify-bulk-refresh-status' => __( 'Refresh status', 'imagify' ),
+ );
+ }
+
+ /**
+ * Get a list of columns. The format is:
+ * 'internal-name' => 'Title'
+ *
+ * @since 1.7
+ *
+ * @return array
+ */
+ public function get_columns() {
+ return array(
+ 'cb' => ' ',
+ 'title' => __( 'File', 'imagify' ),
+ 'folder' => __( 'Folder', 'imagify' ),
+ 'optimization' => __( 'Optimization', 'imagify' ),
+ 'status' => __( 'Status', 'imagify' ),
+ 'optimization_level' => __( 'Optimization Level', 'imagify' ),
+ 'actions' => __( 'Actions', 'imagify' ),
+ );
+ }
+
+ /**
+ * Get a list of sortable columns. The format is:
+ * 'internal-name' => 'orderby'
+ * or
+ * 'internal-name' => array( 'orderby', true )
+ *
+ * The second format will make the initial sorting order be descending.
+ *
+ * @since 1.7
+ *
+ * @return array
+ */
+ public function get_sortable_columns() {
+ return array(
+ 'folder' => 'folder',
+ 'optimization' => array( 'optimization', true ),
+ 'status' => 'status',
+ 'optimization_level' => array( 'optimization_level', true ),
+ );
+ }
+
+ /**
+ * Get a column contents.
+ *
+ * @since 1.7
+ *
+ * @param string $column The column "name": "cb", "title", "optimization_level", etc.
+ * @param object $item The current item. It must contain at least a $process property.
+ * @return string HTML contents,
+ */
+ public function get_column( $column, $item ) {
+ if ( ! method_exists( $this, 'column_' . $column ) ) {
+ return '';
+ }
+
+ ob_start();
+ call_user_func( array( $this, 'column_' . $column ), $item );
+ return ob_get_clean();
+ }
+
+ /**
+ * Handles the checkbox column output.
+ *
+ * @since 1.7
+ *
+ * @param object $item The current item. It must contain at least a $process property.
+ */
+ public function column_cb( $item ) {
+ $media_id = $item->process->get_media()->get_id();
+ ?>
+
+
+ maybe_set_item_folder( $item );
+ $media = $item->process->get_media();
+ $url = $media->get_fullsize_url();
+ $base = ! empty( $item->folder_path ) ? Imagify_Files_Scan::remove_placeholder( $item->folder_path ) : '';
+ $title = $this->filesystem->make_path_relative( $media->get_fullsize_path(), $base );
+
+ list( $mime ) = explode( '/', $media->get_mime_type() );
+
+ if ( $media->is_image() ) {
+ $dimensions = $media->get_dimensions();
+ $orientation = $dimensions['width'] > $dimensions['height'] ? ' landscape' : ' portrait';
+ $orientation = $dimensions['width'] && $dimensions['height'] ? $orientation : '';
+
+ if ( ! wp_doing_ajax() && $item->process->get_data()->get_optimized_size( false, 0, false ) > 100000 ) {
+ // LazyLoad.
+ $image_tag = ' ';
+ $image_tag .= ' ';
+ } else {
+ $image_tag = ' ';
+ }
+ } else {
+ $orientation = '';
+ $image_tag = ' ';
+ }
+ ?>
+
+
+
+
+
+
+
+
+
+
+
+ comparison_tool_button( $item ); ?>
+
+ maybe_set_item_folder( $item );
+
+ if ( empty( $item->folder_path ) ) {
+ return;
+ }
+
+ $format = '%s';
+ $filter = self::get_folder_filter();
+
+ if ( $filter !== $item->folder_id ) {
+ $format = '%s ';
+ }
+
+ if ( '{{ROOT}}/' === $item->folder_path ) {
+ // It's the site's root.
+ printf( $format, __( 'Site\'s root', 'imagify' ) );
+ } else {
+ printf( $format, '/' . trim( $this->filesystem->make_path_relative( Imagify_Files_Scan::remove_placeholder( $item->folder_path ) ), '/' ) . '' );
+ }
+
+ if ( ! $item->is_folder_active ) {
+ echo ' ';
+ _e( 'This folder is not selected for bulk optimization.', 'imagify' );
+ }
+ }
+
+ /**
+ * Handles the optimization data column output.
+ *
+ * @since 1.7
+ *
+ * @param object $item The current item. It must contain at least a $process property.
+ */
+ public function column_optimization( $item ) {
+ $data = $item->process->get_data();
+ $media_id = $item->process->get_media()->get_id();
+ ?>
+
+
+
+ get_original_size() ); ?>
+
+ is_optimized() ) { ?>
+
+
+ get_optimized_size() ); ?>
+
+
+
+
+
+
+
+
+
+
+
+
+ get_saving_percent(); ?> %
+
+
+ process->get_media()->is_image() ) {
+ $has_nextgen = $item->process->has_next_gen() ? __( 'Yes', 'imagify' ) : __( 'No', 'imagify' );
+ ?>
+
+
+
+
+
+
+ process->get_data();
+ $row = $data->get_row();
+ $status = $data->get_optimization_status();
+ $messages = [];
+
+ if ( ! $status ) {
+ // File is not optimized.
+ $messages[] = '' . esc_html_x( 'Not optimized', 'Media File', 'imagify' ) . ' ';
+ } elseif ( ! empty( $row['error'] ) ) {
+ // Error or already optimized.
+ $messages[] = '' . esc_html( imagify_translate_api_message( $row['error'] ) ) . ' ';
+ }
+
+ if ( empty( $row['modified'] ) && ! $messages ) {
+ // No need to display this if we already have another message to display.
+ $messages[] = '' . esc_html__( 'No changes found', 'imagify' ) . ' ';
+ } elseif ( ! empty( $row['modified'] ) ) {
+ // The file has changed or is missing.
+ $messages[] = '' . esc_html__( 'The file has changed', 'imagify' ) . ' ';
+ }
+
+ echo implode( ' ', $messages );
+
+ $this->refresh_status_button( $item );
+ }
+
+ /**
+ * Handles the optimization level column output.
+ *
+ * @since 1.7
+ *
+ * @param object $item The current item. It must contain at least a $process property.
+ */
+ public function column_optimization_level( $item ) {
+ $data = $item->process->get_data();
+
+ if ( ! $data->is_error() ) {
+ echo imagify_get_optimization_level_label( $data->get_optimization_level(), '%ICON% %s' );
+ }
+ }
+
+ /**
+ * Handles the actions column output.
+ *
+ * @since 1.7
+ *
+ * @param object $item The current item. It must contain at least a $process property.
+ */
+ public function column_actions( $item ) {
+ static $done = false;
+
+ if ( ! Imagify_Requirements::is_api_key_valid() ) {
+ // Stop the process if the API key isn't valid.
+ if ( ! $done ) {
+ // No need to display this on every row.
+ $done = true;
+ esc_html_e( 'Invalid API key', 'imagify' );
+ echo '' . __( 'Check your Settings', 'imagify' ) . ' ';
+ }
+ return;
+ }
+
+ if ( $item->process->is_locked() ) {
+ Imagify_Views::get_instance()->print_template( 'button-processing', [
+ 'label' => __( 'Optimizing...', 'imagify' ),
+ ] );
+ return;
+ }
+
+ $this->optimize_button( $item );
+ $this->retry_button( $item );
+ $this->reoptimize_buttons( $item );
+ $this->generate_nextgen_versions_button( $item );
+ $this->delete_nextgen_versions_button( $item );
+ $this->restore_button( $item );
+ }
+
+ /**
+ * Prints a button to optimize the file.
+ *
+ * @since 1.7
+ *
+ * @param object $item The current item. It must contain at least a $process property.
+ */
+ protected function optimize_button( $item ) {
+ if ( $item->process->get_data()->get_optimization_status() ) {
+ // Already optimized.
+ return;
+ }
+
+ $media = $item->process->get_media();
+ $class = $media->has_backup() ? ' file-has-backup' : '';
+ $url = get_imagify_admin_url( 'optimize-file', [
+ 'attachment_id' => $media->get_id(),
+ ] );
+
+ echo $this->views->get_template( 'button/optimize', [
+ 'url' => $url,
+ 'atts' => [
+ 'class' => 'button-primary button-imagify-optimize' . $class,
+ ],
+ ] );
+ }
+
+ /**
+ * Prints a button to retry to optimize the file.
+ *
+ * @since 1.7
+ *
+ * @param object $item The current item. It must contain at least a $process property.
+ */
+ protected function retry_button( $item ) {
+ $data = $item->process->get_data();
+
+ if ( ! $data->is_already_optimized() && ! $data->is_error() ) {
+ // Not optimized or successfully optimized.
+ return;
+ }
+
+ $media = $item->process->get_media();
+ $class = $media->has_backup() ? ' file-has-backup' : '';
+ $url = get_imagify_admin_url( 'optimize-file', [
+ 'attachment_id' => $media->get_id(),
+ ] );
+
+ echo $this->views->get_template( 'button/retry-optimize', [
+ 'url' => $url,
+ 'atts' => [
+ 'class' => 'button button-imagify-optimize' . $class,
+ ],
+ ] );
+ echo ' ';
+ }
+
+ /**
+ * Prints buttons to re-optimize the file to other levels.
+ *
+ * @since 1.7
+ *
+ * @param object $item The current item. It must contain at least a $process property.
+ */
+ protected function reoptimize_buttons( $item ) {
+ $data = $item->process->get_data();
+
+ if ( ! $data->get_optimization_status() ) {
+ // Not optimized yet.
+ return;
+ }
+
+ $is_already_optimized = $data->is_already_optimized();
+ $media = $item->process->get_media();
+ $can_reoptimize = $is_already_optimized || $media->has_backup();
+
+ // Don't display anything if there is no backup or the image has been optimized.
+ if ( ! $can_reoptimize ) {
+ return;
+ }
+
+ $media_level = $data->get_optimization_level();
+ $data = [];
+ $url_args = [ 'attachment_id' => $media->get_id() ];
+
+ if ( $media_level < 1 ) {
+ $url_args['optimization_level'] = 2;
+ $data['optimization_level'] = 2;
+ $data['url'] = get_imagify_admin_url( 'reoptimize-file', $url_args );
+
+ echo $this->views->get_template( 'button/re-optimize', $data );
+ } elseif ( $media_level > 0 ) {
+ $url_args['optimization_level'] = 0;
+ $data['optimization_level'] = 0;
+ $data['url'] = get_imagify_admin_url( 'reoptimize-file', $url_args );
+
+ echo $this->views->get_template( 'button/re-optimize', $data );
+ }
+ }
+
+ /**
+ * Prints a button to generate Next gen versions if they are missing.
+ *
+ * @since 1.7
+ *
+ * @param object $item The current item. It must contain at least a $process property.
+ */
+ protected function generate_nextgen_versions_button( $item ) {
+ $button = get_imagify_attachment_generate_nextgen_versions_link( $item->process );
+
+ if ( $button ) {
+ echo $button . ' ';
+ }
+ }
+
+ /**
+ * Prints a button to delete next-gen versions when the status is "already_optimized".
+ *
+ * @since 1.9.6
+ *
+ * @param object $item The current item. It must contain at least a $process property.
+ */
+ protected function delete_nextgen_versions_button( $item ) {
+ $button = get_imagify_attachment_delete_nextgen_versions_link( $item->process );
+
+ if ( $button ) {
+ echo $button . ' ';
+ }
+ }
+
+ /**
+ * Prints a button to restore the file.
+ *
+ * @since 1.7
+ *
+ * @param object $item The current item. It must contain at least a $process property.
+ */
+ protected function restore_button( $item ) {
+ $data = $item->process->get_data();
+ $media = $item->process->get_media();
+
+ if ( ! $data->is_optimized() || ! $media->has_backup() ) {
+ return;
+ }
+
+ $url = get_imagify_admin_url( 'restore-file', array(
+ 'attachment_id' => $media->get_id(),
+ ) );
+
+ echo $this->views->get_template( 'button/restore', [ 'url' => $url ] );
+ }
+
+ /**
+ * Prints a button to check if the file has been modified or not.
+ *
+ * @since 1.7
+ *
+ * @param object $item The current item. It must contain at least a $process property.
+ */
+ protected function refresh_status_button( $item ) {
+ $url = get_imagify_admin_url( 'refresh-file-modified', array(
+ 'attachment_id' => $item->process->get_media()->get_id(),
+ ) );
+
+ echo ' ';
+ echo $this->views->get_template( 'button/refresh-status', [ 'url' => $url ] );
+ }
+
+ /**
+ * Prints a button for the comparison tool (before / after optimization).
+ *
+ * @since 1.7
+ *
+ * @param object $item The current item. It must contain at least a $process property.
+ */
+ protected function comparison_tool_button( $item ) {
+ $data = $item->process->get_data();
+ $media = $item->process->get_media();
+
+ if ( ! $data->is_optimized() || ! $media->has_backup() || ! $media->is_image() ) {
+ return;
+ }
+
+ $file_path = $media->get_fullsize_path();
+
+ if ( ! $file_path ) {
+ return;
+ }
+
+ $dimensions = $media->get_dimensions();
+
+ if ( $dimensions['width'] < 360 ) {
+ return;
+ }
+
+ $backup_url = $media->get_backup_url();
+
+ echo $this->views->get_template( 'button/compare-images', [
+ 'url' => $backup_url,
+ 'backup_url' => $backup_url,
+ 'original_url' => $media->get_fullsize_url(),
+ 'media_id' => $media->get_id(),
+ 'width' => $dimensions['width'],
+ 'height' => $dimensions['height'],
+ ] );
+
+ if ( wp_doing_ajax() ) {
+ ?>
+
+ folder_path ) ) {
+ return $item;
+ }
+
+ $item->folder_id = 0;
+ $item->folder_path = false;
+
+ $row = $item->process->get_data()->get_row();
+
+ if ( empty( $row['folder_id'] ) ) {
+ return $item;
+ }
+
+ $folder = Imagify_Folders_DB::get_instance()->get( $row['folder_id'] );
+
+ if ( ! $folder ) {
+ return $item;
+ }
+
+ $item->folder_id = $folder['folder_id'];
+ $item->folder_path = $folder['path'];
+ $item->is_folder_active = (bool) $folder['active'];
+
+ return $item;
+ }
+
+ /**
+ * Get the name of the default primary column.
+ *
+ * @since 1.7
+ *
+ * @return string Name of the default primary column, in this case, 'title'.
+ */
+ protected function get_default_primary_column_name() {
+ return 'title';
+ }
+
+ /**
+ * Get a list of CSS classes for the WP_List_Table table tag.
+ *
+ * @since 1.7
+ *
+ * @return array List of CSS classes for the table tag.
+ */
+ protected function get_table_classes() {
+ return array( 'widefat', 'fixed', 'striped', 'media', $this->_args['plural'] );
+ }
+
+ /**
+ * Allow to save the screen options when submitted by the user.
+ *
+ * @since 1.7
+ *
+ * @param bool|int $status Screen option value. Default false to skip.
+ * @param string $option The option name.
+ * @param int $value The number of rows to use.
+ * @return int|bool
+ */
+ public static function save_screen_options( $status, $option, $value ) {
+ if ( self::PER_PAGE_OPTION === $option ) {
+ return (int) $value;
+ }
+
+ return $status;
+ }
+
+ /**
+ * Get the requested folder filter.
+ *
+ * @since 1.7
+ *
+ * @return string
+ */
+ public static function get_folder_filter() {
+ static $filter;
+
+ if ( ! isset( $filter ) ) {
+ $filter = filter_input( INPUT_GET, 'folder-filter', FILTER_VALIDATE_INT );
+ $filter = max( 0, $filter );
+ }
+
+ return $filter;
+ }
+
+ /**
+ * Get the requested status filter.
+ *
+ * @since 1.7
+ *
+ * @return string
+ */
+ public static function get_status_filter() {
+ static $filter;
+
+ if ( isset( $filter ) ) {
+ return $filter;
+ }
+
+ $values = array(
+ 'optimized' => 1,
+ 'unoptimized' => 1,
+ 'errors' => 1,
+ );
+ $filter = isset( $_GET['status-filter'] ) ? trim( htmlspecialchars( wp_unslash( $_GET['status-filter'] ) ) ) : ''; // phpcs:ignore WordPress.Security.NonceVerification.Missing, WordPress.Security.NonceVerification.Recommended
+ $filter = isset( $values[ $filter ] ) ? $filter : '';
+
+ return $filter;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/inc/classes/class-imagify-files-recursive-iterator.php b/wp/wp-content/plugins/imagify/inc/classes/class-imagify-files-recursive-iterator.php
new file mode 100644
index 00000000..9246218d
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/classes/class-imagify-files-recursive-iterator.php
@@ -0,0 +1,104 @@
+filesystem = Imagify_Filesystem::get_instance();
+ }
+
+ /**
+ * Check whether the current element of the iterator is acceptable.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return bool Returns whether the current element of the iterator is acceptable through this filter.
+ */
+ public function accept(): bool {
+ static $extensions, $has_extension_method;
+
+ $file_path = $this->current()->getPathname();
+
+ // Prevent triggering an open_basedir restriction error.
+ $file_name = $this->filesystem->file_name( $file_path );
+
+ if ( '.' === $file_name || '..' === $file_name ) {
+ return false;
+ }
+
+ if ( $this->current()->isDir() ) {
+ $file_path = trailingslashit( $file_path );
+ }
+
+ if ( Imagify_Files_Scan::is_path_forbidden( $file_path ) ) {
+ return false;
+ }
+
+ // OK for folders.
+ if ( $this->hasChildren() ) {
+ return true;
+ }
+
+ // Only files.
+ if ( ! $this->current()->isFile() ) {
+ return false;
+ }
+
+ // Only files with the required extension.
+ if ( ! isset( $extensions ) ) {
+ $extensions = array_keys( imagify_get_mime_types() );
+ $extensions = implode( '|', $extensions );
+ }
+
+ if ( ! isset( $has_extension_method ) ) {
+ // This method was introduced in php 5.3.6.
+ $has_extension_method = method_exists( $this->current(), 'getExtension' );
+ }
+
+ if ( $has_extension_method ) {
+ $file_extension = strtolower( $this->current()->getExtension() );
+ } else {
+ $file_extension = strtolower( $this->filesystem->path_info( $file_path, 'extension' ) );
+ }
+
+ return preg_match( '@^' . $extensions . '$@', $file_extension );
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/inc/classes/class-imagify-files-scan.php b/wp/wp-content/plugins/imagify/inc/classes/class-imagify-files-scan.php
new file mode 100644
index 00000000..be8487b1
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/classes/class-imagify-files-scan.php
@@ -0,0 +1,717 @@
+is_dir( $folder ) ) {
+ return new WP_Error( 'not_a_folder', __( 'This file is not a folder.', 'imagify' ) );
+ }
+
+ if ( self::is_path_forbidden( trailingslashit( $folder ) ) ) {
+ return new WP_Error( 'folder_forbidden', __( 'This folder is not allowed.', 'imagify' ) );
+ }
+
+ // Finally we made all our validations.
+ if ( $filesystem->is_site_root( $folder ) ) {
+ // For the site's root, we don't look in sub-folders.
+ $dir = new DirectoryIterator( $folder );
+ $dir = new Imagify_Files_Iterator( $dir, false );
+ $images = array();
+
+ foreach ( new IteratorIterator( $dir ) as $file ) {
+ $images[] = $file->getPathname();
+ }
+
+ return $images;
+ }
+
+ /**
+ * 4096 stands for FilesystemIterator::SKIP_DOTS, which was introduced in php 5.3.0.
+ * 8192 stands for FilesystemIterator::UNIX_PATHS, which was introduced in php 5.3.0.
+ */
+ $dir = new RecursiveDirectoryIterator( $folder, 4096 | 8192 );
+ $dir = new Imagify_Files_Recursive_Iterator( $dir );
+ $images = new RecursiveIteratorIterator( $dir );
+ $images = array_keys( iterator_to_array( $images ) );
+
+ return $images;
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** FORBIDDEN FOLDERS AND FILES ============================================================= */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Tell if a path is autorized.
+ * When testing a folder, the path MUST have a trailing slash.
+ *
+ * @since 1.7.1
+ * @since 1.8 The path must have a trailing slash if for a folder.
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param string $file_path A file or folder absolute path.
+ * @return bool
+ */
+ public static function is_path_autorized( $file_path ) {
+ return ! self::is_path_forbidden( $file_path );
+ }
+
+ /**
+ * Tell if a path is forbidden.
+ * When testing a folder, the path MUST have a trailing slash.
+ *
+ * @since 1.7
+ * @since 1.8 The path must have a trailing slash if for a folder.
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param string $file_path A file or folder absolute path.
+ * @return bool
+ */
+ public static function is_path_forbidden( $file_path ) {
+ static $folders;
+
+ $filesystem = imagify_get_filesystem();
+
+ if ( self::is_filename_forbidden( $filesystem->file_name( $file_path ) ) ) {
+ return true;
+ }
+
+ if ( $filesystem->is_symlinked( $file_path ) ) {
+ // Files outside the site's folder are forbidden.
+ return true;
+ }
+
+ if ( ! isset( $folders ) ) {
+ $folders = self::get_forbidden_folders();
+ $folders = array_map( 'strtolower', $folders );
+ $folders = array_flip( $folders );
+ }
+
+ $file_path = self::normalize_path_for_comparison( $file_path );
+
+ if ( isset( $folders[ $file_path ] ) ) {
+ return true;
+ }
+
+ $delim = Imagify_Filesystem::PATTERN_DELIMITER;
+
+ foreach ( self::get_forbidden_folder_patterns() as $pattern ) {
+ if ( preg_match( $delim . '^' . $pattern . $delim, $file_path ) ) {
+ return true;
+ }
+ }
+
+ foreach ( $folders as $folder => $i ) {
+ if ( strpos( $file_path, $folder ) === 0 ) {
+ return true;
+ }
+ }
+
+ return false;
+ }
+
+ /**
+ * Get the list of folders where Imagify won't look for files to optimize.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return array A list of absolute paths.
+ */
+ public static function get_forbidden_folders() {
+ static $folders;
+
+ if ( isset( $folders ) ) {
+ return $folders;
+ }
+
+ $filesystem = imagify_get_filesystem();
+ $site_root = $filesystem->get_site_root();
+ $abspath = $filesystem->get_abspath();
+ $folders = array(
+ // Server.
+ $site_root . 'cgi-bin', // `cgi-bin`
+ // WordPress.
+ $abspath . 'wp-admin', // `wp-admin`
+ $abspath . WPINC, // `wp-includes`
+ WP_CONTENT_DIR . '/mu-plugins', // MU plugins.
+ WP_CONTENT_DIR . '/upgrade', // Upgrade.
+ // Plugins.
+ WP_CONTENT_DIR . '/bps-backup', // BulletProof Security.
+ self::get_ewww_tools_path(), // EWWW: /wp-content/ewww.
+ WP_CONTENT_DIR . '/ngg', // NextGen Gallery.
+ WP_CONTENT_DIR . '/ngg_styles', // NextGen Gallery.
+ WP_CONTENT_DIR . '/w3tc-config', // W3 Total Cache.
+ WP_CONTENT_DIR . '/wfcache', // WP Fastest Cache.
+ WP_CONTENT_DIR . '/wp-rocket-config', // WP Rocket.
+ Imagify_Custom_Folders::get_backup_dir_path(), // Imagify "Custom folders" backup: /imagify-backup.
+ IMAGIFY_PATH, // Imagify plugin: /wp-content/plugins/imagify.
+ self::get_shortpixel_path(), // ShortPixel: /wp-content/uploads/ShortpixelBackups.
+ );
+
+ if ( ! is_multisite() ) {
+ $uploads_dir = $filesystem->get_upload_basedir( true );
+ $ngg_galleries = self::get_ngg_galleries_path();
+
+ if ( $ngg_galleries ) {
+ $folders[] = $ngg_galleries; // NextGen Gallery: /wp-content/gallery.
+ }
+
+ $folders[] = $uploads_dir . 'formidable'; // Formidable Forms: /wp-content/uploads/formidable.
+ $folders[] = get_imagify_backup_dir_path( true ); // Imagify Media Library backup: /wp-content/uploads/backup.
+ $folders[] = self::get_wc_logs_path(); // WooCommerce Logs: /wp-content/uploads/wc-logs.
+ $folders[] = $uploads_dir . 'woocommerce_uploads'; // WooCommerce uploads: /wp-content/uploads/woocommerce_uploads.
+ }
+
+ $folders = array_map( array( $filesystem, 'normalize_dir_path' ), $folders );
+
+ /**
+ * Add folders to the list of forbidden ones.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ *
+ * @param array $added_folders List of absolute paths.
+ * @param array $folders List of folders already forbidden.
+ */
+ $added_folders = apply_filters( 'imagify_add_forbidden_folders', array(), $folders );
+ $added_folders = array_filter( (array) $added_folders );
+ $added_folders = array_filter( $added_folders, 'is_string' );
+
+ if ( ! $added_folders ) {
+ return $folders;
+ }
+
+ $added_folders = array_map( array( $filesystem, 'normalize_dir_path' ), $added_folders );
+
+ $folders = array_merge( $folders, $added_folders );
+ $folders = array_flip( array_flip( $folders ) );
+
+ return $folders;
+ }
+
+ /**
+ * Get the list of folder patterns where Imagify won't look for files to optimize. This is meant for paths that are dynamic.
+ * `^` will be prepended to each pattern (aka, the pattern must match an absolute path).
+ * Pattern delimiter is `Imagify_Filesystem::PATTERN_DELIMITER`.
+ * Paths tested against these patterns are lower-cased.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return array A list of regex patterns.
+ */
+ public static function get_forbidden_folder_patterns() {
+ static $folders;
+
+ if ( isset( $folders ) ) {
+ return $folders;
+ }
+
+ $folders = array();
+
+ // Media Library: /wp\-content/uploads/(sites/\d+/)?\d{4}/\d{2}/.
+ $folders[] = self::get_media_library_pattern();
+
+ if ( is_multisite() ) {
+ /**
+ * On multisite we can't exclude Imagify's library backup folders, or any other folder located in the uploads folders (created by other plugins): there are too many ways it can fail.
+ * Only exception we're aware of so far is NextGen Gallery, because it provides a clear pattern to use.
+ */
+ $ngg_galleries = self::get_ngg_galleries_multisite_pattern();
+
+ if ( $ngg_galleries ) {
+ // NextGen Gallery: /wp\-content/uploads/sites/\d+/nggallery/.
+ $folders[] = $ngg_galleries;
+ }
+ }
+
+ /**
+ * Add folder patterns to the list of forbidden ones.
+ * Don't forget to use `Imagify_Files_Scan::normalize_path_for_regex( $path )`!
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ *
+ * @param array $added_folders List of patterns.
+ * @param array $folders List of patterns already forbidden.
+ */
+ $added_folders = apply_filters( 'imagify_add_forbidden_folder_patterns', array(), $folders );
+ $added_folders = array_filter( (array) $added_folders );
+ $added_folders = array_filter( $added_folders, 'is_string' );
+
+ if ( ! $added_folders ) {
+ return $folders;
+ }
+
+ $folders = array_merge( $folders, $added_folders );
+ $folders = array_flip( array_flip( $folders ) );
+
+ return $folders;
+ }
+
+ /**
+ * Tell if a file/folder name is forbidden.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param string $file_name A file or folder name.
+ * @return bool
+ */
+ public static function is_filename_forbidden( $file_name ) {
+ static $file_names;
+
+ if ( ! isset( $file_names ) ) {
+ $file_names = array_flip( self::get_forbidden_file_names() );
+ }
+
+ return isset( $file_names[ strtolower( $file_name ) ] );
+ }
+
+ /**
+ * Get the list of file names that Imagify won't optimize.
+ * It can contain folder names. Names are case-lowered.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return array A list of file names
+ */
+ public static function get_forbidden_file_names() {
+ static $file_names;
+
+ if ( isset( $file_names ) ) {
+ return $file_names;
+ }
+
+ $file_names = array(
+ '.',
+ '..',
+ '.DS_Store',
+ '.git',
+ '.svn',
+ 'backup',
+ 'backups',
+ 'cache',
+ 'lang',
+ 'langs',
+ 'languages',
+ 'node_modules',
+ 'Thumbs.db',
+ );
+ $file_names = array_map( 'strtolower', $file_names );
+
+ /**
+ * Add file names to the list of forbidden ones.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ *
+ * @param array $added_file_names List of file names.
+ * @param array $file_names List of file names already forbidden.
+ */
+ $added_file_names = apply_filters( 'imagify_add_forbidden_file_names', array(), $file_names );
+
+ if ( ! $added_file_names || ! is_array( $added_file_names ) ) {
+ return $file_names;
+ }
+
+ $added_file_names = array_filter( $added_file_names, 'is_string' );
+ $added_file_names = array_map( 'strtolower', $added_file_names );
+
+ $file_names = array_merge( $file_names, $added_file_names );
+ $file_names = array_flip( array_flip( $file_names ) );
+
+ return $file_names;
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** PLACEHOLDERS ============================================================================ */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Add a placeholder to a path.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param string $file_path An absolute path.
+ * @return string A "placeholdered" path.
+ */
+ public static function add_placeholder( $file_path ) {
+ $file_path = wp_normalize_path( $file_path );
+ $locations = self::get_placeholder_paths();
+
+ foreach ( $locations as $placeholder => $location_path ) {
+ if ( strpos( $file_path, $location_path ) === 0 ) {
+ return preg_replace( '@^' . preg_quote( $location_path, '@' ) . '@', $placeholder, $file_path );
+ }
+ }
+
+ // Should not happen.
+ return $file_path;
+ }
+
+ /**
+ * Change a path with a placeholder into a real path or URL.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param string $file_path A path with a placeholder.
+ * @param string $type What to return: 'path' or 'url'.
+ * @return string An absolute path or a URL.
+ */
+ public static function remove_placeholder( $file_path, $type = 'path' ) {
+ if ( 'path' === $type ) {
+ $locations = self::get_placeholder_paths();
+ } else {
+ $locations = self::get_placeholder_urls();
+ }
+
+ foreach ( $locations as $placeholder => $location_path ) {
+ if ( strpos( $file_path, $placeholder ) === 0 ) {
+ return preg_replace( '@^' . preg_quote( $placeholder, '@' ) . '@', $location_path, $file_path );
+ }
+ }
+
+ // Should not happen.
+ return $file_path;
+ }
+
+ /**
+ * Get array of pairs of placeholder => corresponding path.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return array
+ */
+ public static function get_placeholder_paths() {
+ static $replacements;
+
+ if ( isset( $replacements ) ) {
+ return $replacements;
+ }
+
+ $filesystem = imagify_get_filesystem();
+ $replacements = array(
+ '{{PLUGINS}}/' => WP_PLUGIN_DIR,
+ '{{MU_PLUGINS}}/' => WPMU_PLUGIN_DIR,
+ '{{THEMES}}/' => WP_CONTENT_DIR . '/themes',
+ '{{UPLOADS}}/' => $filesystem->get_main_upload_basedir(),
+ '{{CONTENT}}/' => WP_CONTENT_DIR,
+ '{{ROOT}}/' => $filesystem->get_site_root(),
+ );
+ $replacements = array_map( array( $filesystem, 'normalize_dir_path' ), $replacements );
+
+ return $replacements;
+ }
+
+ /**
+ * Get array of pairs of placeholder => corresponding URL.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return array
+ */
+ public static function get_placeholder_urls() {
+ static $replacements;
+
+ if ( isset( $replacements ) ) {
+ return $replacements;
+ }
+
+ $filesystem = imagify_get_filesystem();
+ $replacements = array(
+ '{{PLUGINS}}/' => plugins_url( '/' ),
+ '{{MU_PLUGINS}}/' => plugins_url( '/', WPMU_PLUGIN_DIR . '/.' ),
+ '{{THEMES}}/' => content_url( 'themes/' ),
+ '{{UPLOADS}}/' => $filesystem->get_main_upload_baseurl(),
+ '{{CONTENT}}/' => content_url( '/' ),
+ '{{ROOT}}/' => $filesystem->get_site_root_url(),
+ );
+
+ return $replacements;
+ }
+
+ /**
+ * A file_exists() for paths with a placeholder.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param string $file_path The file path.
+ * @return bool
+ */
+ public static function placeholder_path_exists( $file_path ) {
+ return imagify_get_filesystem()->is_readable( self::remove_placeholder( $file_path ) );
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** PATHS =================================================================================== */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Get the path to NextGen galleries on monosites.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return string|bool An absolute path. False if it can't be retrieved.
+ */
+ public static function get_ngg_galleries_path() {
+ $galleries_path = get_site_option( 'ngg_options' );
+
+ if ( empty( $galleries_path['gallerypath'] ) ) {
+ return false;
+ }
+
+ $filesystem = imagify_get_filesystem();
+ $galleries_path = $filesystem->normalize_dir_path( $galleries_path['gallerypath'] );
+ $galleries_path = trim( $galleries_path, '/' ); // Something like `wp-content/gallery`.
+
+ $ngg_root = defined( 'NGG_GALLERY_ROOT_TYPE' ) ? NGG_GALLERY_ROOT_TYPE : 'site';
+
+ if ( $galleries_path && 'content' === $ngg_root ) {
+ $ngg_root = $filesystem->normalize_dir_path( WP_CONTENT_DIR );
+ $ngg_root = trim( $ngg_root, '/' ); // Something like `abs-path/to/wp-content`.
+
+ $exploded_root = explode( '/', $ngg_root );
+ $exploded_galleries = explode( '/', $galleries_path );
+ $first_gallery_dirname = reset( $exploded_galleries );
+ $last_root_dirname = end( $exploded_root );
+
+ if ( $last_root_dirname === $first_gallery_dirname ) {
+ array_shift( $exploded_galleries );
+ $galleries_path = implode( '/', $exploded_galleries );
+ }
+ }
+
+ if ( 'content' === $ngg_root ) {
+ $ngg_root = $filesystem->normalize_dir_path( WP_CONTENT_DIR );
+ } else {
+ $ngg_root = $filesystem->get_abspath();
+ }
+
+ if ( strpos( $galleries_path, $ngg_root ) !== 0 ) {
+ $galleries_path = $ngg_root . $galleries_path;
+ }
+
+ return $galleries_path . '/';
+ }
+
+ /**
+ * Get the path to WooCommerce logs on monosites.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return string An absolute path.
+ */
+ public static function get_wc_logs_path() {
+ if ( defined( 'WC_LOG_DIR' ) ) {
+ return WC_LOG_DIR;
+ }
+
+ return imagify_get_filesystem()->get_upload_basedir( true ) . 'wc-logs/';
+ }
+
+ /**
+ * Get the path to EWWW optimization tools.
+ * It is the same for all sites on multisite.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return string An absolute path.
+ */
+ public static function get_ewww_tools_path() {
+ if ( defined( 'EWWW_IMAGE_OPTIMIZER_TOOL_PATH' ) ) {
+ return EWWW_IMAGE_OPTIMIZER_TOOL_PATH;
+ }
+
+ return WP_CONTENT_DIR . '/ewww/';
+ }
+
+ /**
+ * Get the path to ShortPixel backup folder.
+ * It is the same for all sites on multisite (and yes, you'll get a surprise if your upload base dir -aka uploads/sites/12/- is not 2 folders deeper than theuploads folder).
+ *
+ * @since 1.8
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return string An absolute path.
+ */
+ public static function get_shortpixel_path() {
+ if ( defined( 'SHORTPIXEL_BACKUP_FOLDER' ) ) {
+ return trailingslashit( SHORTPIXEL_BACKUP_FOLDER );
+ }
+
+ $filesystem = imagify_get_filesystem();
+ $path = $filesystem->get_upload_basedir( true );
+ $path = is_main_site() ? $path : $filesystem->dir_path( $filesystem->dir_path( $path ) );
+
+ return $path . 'ShortpixelBackups/';
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** REGEX PATTERNS ========================================================================== */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Get the regex pattern used to match the paths to the media library.
+ * Pattern delimiter is `Imagify_Filesystem::PATTERN_DELIMITER`.
+ * Paths tested against these patterns are lower-cased.
+ *
+ * @since 1.8
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return string Something like `/wp\-content/uploads/(sites/\d+/)?\d{4}/\d{2}/`.
+ */
+ public static function get_media_library_pattern() {
+ $filesystem = imagify_get_filesystem();
+ $uploads_dir = self::normalize_path_for_regex( $filesystem->get_main_upload_basedir() );
+
+ if ( ! is_multisite() ) {
+ if ( get_option( 'uploads_use_yearmonth_folders' ) ) {
+ // In year/month folders.
+ return $uploads_dir . '\d{4}/\d{2}/';
+ }
+
+ // Not in year/month folders.
+ return $uploads_dir . '[^/]+$';
+ }
+
+ $pattern = $filesystem->get_multisite_uploads_subdir_pattern();
+
+ if ( get_option( 'uploads_use_yearmonth_folders' ) ) {
+ // In year/month folders.
+ return $uploads_dir . '(' . $pattern . ')?\d{4}/\d{2}/';
+ }
+
+ // Not in year/month folders.
+ return $uploads_dir . '(' . $pattern . ')?[^/]+$';
+ }
+
+ /**
+ * Get the regex pattern used to match the paths to NextGen galleries on multisite.
+ * Pattern delimiter is `Imagify_Filesystem::PATTERN_DELIMITER`.
+ * Paths tested against these patterns are lower-cased.
+ *
+ * @since 1.8
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return string|bool Something like `/wp-content/uploads/sites/\d+/nggallery/`. False if it can't be retrieved.
+ */
+ public static function get_ngg_galleries_multisite_pattern() {
+ $galleries_path = self::get_ngg_galleries_path(); // Something like `wp-content/uploads/sites/%BLOG_ID%/nggallery/`.
+
+ if ( ! $galleries_path ) {
+ return false;
+ }
+
+ $galleries_path = self::normalize_path_for_regex( $galleries_path );
+ $galleries_path = str_replace( array( '%blog_name%', '%blog_id%' ), array( '.+', '\d+' ), $galleries_path );
+
+ return $galleries_path;
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** NORMALIZATION TOOLS ===================================================================== */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Normalize a file path, aiming for path comparison.
+ * The path is normalized and case-lowered.
+ *
+ * @since 1.7
+ * @since 1.8 No trailing slash anymore, because it can be used for files.
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param string $file_path The file path.
+ * @return string The normalized file path.
+ */
+ public static function normalize_path_for_comparison( $file_path ) {
+ return strtolower( wp_normalize_path( $file_path ) );
+ }
+
+ /**
+ * Normalize a file path, aiming for use in a regex pattern.
+ * The path is normalized, case-lowered, and escaped.
+ *
+ * @since 1.8
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param string $file_path The file path.
+ * @return string The normalized file path.
+ */
+ public static function normalize_path_for_regex( $file_path ) {
+ return preg_quote( imagify_get_filesystem()->normalize_path_for_comparison( $file_path ), Imagify_Filesystem::PATTERN_DELIMITER );
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/inc/classes/class-imagify-files-stats.php b/wp/wp-content/plugins/imagify/inc/classes/class-imagify-files-stats.php
new file mode 100644
index 00000000..8cc15554
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/classes/class-imagify-files-stats.php
@@ -0,0 +1,474 @@
+can_operate() ) {
+ $count[ $status ] = 0;
+ return $count[ $status ];
+ }
+
+ switch ( $status ) {
+ case 'all':
+ $status = '';
+ break;
+
+ case 'none':
+ $status = 'status IS NULL';
+ break;
+
+ case 'optimized':
+ $status = "status IN ('success','already_optimized')";
+ break;
+
+ case 'unoptimized':
+ $status = "( status = 'error' OR status IS NULL )";
+ break;
+
+ default:
+ // "success", "already_optimized", "error".
+ $status = "status = '$status'";
+ }
+
+ $table_name = $files_db->get_table_name();
+ $status = $status ? "WHERE $status" : '';
+
+ $count[ $status ] = (int) $wpdb->get_var( // WPCS: unprepared SQL ok.
+ "SELECT COUNT( file_id ) FROM $table_name $status"
+ );
+
+ return $count[ $status ];
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** PERCENTS ================================================================================ */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Count percent of optimized images in custom folders.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return int The percent of optimized images.
+ */
+ public static function percent_optimized_files() {
+ /**
+ * Filter the percent of optimized images in custom folders.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ *
+ * @param int|bool $percent Default is false. Provide an integer.
+ */
+ $percent = apply_filters( 'imagify_percent_optimized_files', false );
+
+ if ( false !== $percent ) {
+ return (int) $percent;
+ }
+
+ $total_files = self::count_all_files();
+ $total_optimized_files = self::count_optimized_files();
+
+ if ( ! $total_files || ! $total_optimized_files ) {
+ return 0;
+ }
+
+ return min( round( 100 * $total_optimized_files / $total_files ), 100 );
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** GET FILE SIZES ========================================================================== */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Sum up all optimized sizes of all successfully optimized files.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return int The sizes sum in bytes.
+ */
+ public static function get_optimized_size() {
+ /**
+ * Filter the optimized sizes of all successfully optimized files.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ *
+ * @param int|bool $pre_size Default is false. Provide an integer.
+ */
+ $pre_size = apply_filters( 'imagify_get_optimized_files_size', false );
+
+ if ( false !== $pre_size ) {
+ return (int) $pre_size;
+ }
+
+ return self::get_size( 'optimized' );
+ }
+
+ /**
+ * Sum up all original sizes of all successfully optimized files.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return int The sizes sum in bytes.
+ */
+ public static function get_original_size() {
+ /**
+ * Filter the original sizes of all successfully optimized files.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ *
+ * @param int|bool $pre_size Default is false. Provide an integer.
+ */
+ $pre_size = apply_filters( 'imagify_get_original_files_size', false );
+
+ if ( false !== $pre_size ) {
+ return (int) $pre_size;
+ }
+
+ return self::get_size( 'original' );
+ }
+
+ /**
+ * Sum up all (optimized|original) sizes of all successfully optimized files.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param string $type "optimized" or "original".
+ * @return int The sizes sum in bytes.
+ */
+ public static function get_size( $type = null ) {
+ global $wpdb;
+ static $sizes = array();
+
+ $type = 'optimized' === $type ? 'optimized_size' : 'original_size';
+
+ if ( isset( $sizes[ $type ] ) ) {
+ return $sizes[ $type ];
+ }
+
+ $files_db = Imagify_Files_DB::get_instance();
+
+ if ( ! $files_db->can_operate() ) {
+ $sizes[ $type ] = 0;
+ return $sizes[ $type ];
+ }
+
+ $table_name = $files_db->get_table_name();
+ $sizes[ $type ] = (int) $wpdb->get_var( // WPCS: unprepared SQL ok.
+ "SELECT SUM( $type ) FROM $table_name WHERE status = 'success'"
+ );
+
+ return $sizes[ $type ];
+ }
+
+ /**
+ * Sum up all original sizes.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return int The sizes sum in bytes.
+ */
+ public static function get_overall_original_size() {
+ global $wpdb;
+ static $size;
+
+ if ( isset( $size ) ) {
+ return $size;
+ }
+
+ $files_db = Imagify_Files_DB::get_instance();
+
+ if ( ! $files_db->can_operate() ) {
+ $size = 0;
+ return $size;
+ }
+
+ $table_name = $files_db->get_table_name();
+ $size = round( $wpdb->get_var( "SELECT SUM( original_size ) FROM $table_name" ) ); // WPCS: unprepared SQL ok.
+
+ return $size;
+ }
+
+ /**
+ * Calculate the average size of the images uploaded per month.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return int The current average size of images uploaded per month in bytes.
+ */
+ public static function calculate_average_size_per_month() {
+ global $wpdb;
+ static $average;
+
+ if ( isset( $average ) ) {
+ return $average;
+ }
+
+ $files_db = Imagify_Files_DB::get_instance();
+
+ if ( ! $files_db->can_operate() ) {
+ $average = 0;
+ return $average;
+ }
+
+ $table_name = $files_db->get_table_name();
+ $average = round( $wpdb->get_var( "SELECT AVG( size ) AS average_size_per_month FROM ( SELECT SUM( original_size ) AS size FROM $table_name GROUP BY YEAR( file_date ), MONTH( file_date ) ) AS size_per_month" ) ); // WPCS: unprepared SQL ok.
+
+ return $average;
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** TOOLS =================================================================================== */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Validate a status.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param string $status The status of these folders: all, success, already_optimized, optimized, error, none, unoptimized.
+ * "none" if for files without status.
+ * "optimized" regroups "success" and "already_optimized".
+ * "unoptimized" regroups "error" and "none".
+ * @return string Fallback to 'all' if the status is not valid.
+ */
+ public static function validate_status( $status = 'all' ) {
+ $statuses = array(
+ 'all' => 1,
+ 'success' => 1,
+ 'already_optimized' => 1,
+ 'error' => 1,
+ 'none' => 1,
+ 'optimized' => 1,
+ 'unoptimized' => 1,
+ );
+
+ return isset( $statuses[ $status ] ) ? $status : 'all';
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/inc/classes/class-imagify-filesystem.php b/wp/wp-content/plugins/imagify/inc/classes/class-imagify-filesystem.php
new file mode 100644
index 00000000..8bd0f075
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/classes/class-imagify-filesystem.php
@@ -0,0 +1,1127 @@
+is_root( $file_path ) ? $this->get_root() : trailingslashit( $file_path );
+ }
+
+ /**
+ * Get information about a file path.
+ * Replacement for pathinfo().
+ *
+ * @since 1.7.1
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param string $file_path Path to the file.
+ * @param string $option If present, specifies a specific element to be returned; one of 'dir_path', 'file_name', 'extension' or 'file_base'.
+ * If option is not specified, returns all available elements.
+ * @return array|string|null If the option parameter is not passed, an associative array containing the following elements is returned: 'dir_path' (with trailing slash), 'file_name' (with extension), 'extension' (if any), and 'file_base' (without extension).
+ */
+ public function path_info( $file_path, $option = null ) {
+ if ( ! $file_path ) {
+ if ( isset( $option ) ) {
+ return '';
+ }
+
+ return array(
+ 'dir_path' => '',
+ 'file_name' => '',
+ 'extension' => null,
+ 'file_base' => '',
+ );
+ }
+
+ if ( isset( $option ) ) {
+ $options = array(
+ 'dir_path' => PATHINFO_DIRNAME,
+ 'file_name' => PATHINFO_BASENAME,
+ 'extension' => PATHINFO_EXTENSION,
+ 'file_base' => PATHINFO_FILENAME,
+ );
+
+ if ( ! isset( $options[ $option ] ) ) {
+ return '';
+ }
+
+ $output = pathinfo( $file_path, $options[ $option ] );
+
+ if ( 'dir_path' !== $option ) {
+ return $output;
+ }
+
+ return $this->is_root( $output ) ? $this->get_root() : trailingslashit( $output );
+ }
+
+ $output = pathinfo( $file_path );
+
+ $output['dirname'] = $this->is_root( $output['dirname'] ) ? $this->get_root() : trailingslashit( $output['dirname'] );
+ $output['extension'] = isset( $output['extension'] ) ? $output['extension'] : null;
+
+ // '/www/htdocs/inc/lib.inc.php'
+ return array(
+ 'dir_path' => $output['dirname'], // '/www/htdocs/inc/'
+ 'file_name' => $output['basename'], // 'lib.inc.php'
+ 'extension' => $output['extension'], // 'php'
+ 'file_base' => $output['filename'], // 'lib.inc'
+ );
+ }
+
+ /**
+ * Recursive directory creation based on full path. Will attempt to set permissions on folders.
+ * Replacement for recursive mkdir().
+ *
+ * @since 1.7.1
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param string $path Full path to attempt to create.
+ * @return bool Whether the path was created. True if path already exists.
+ */
+ public function make_dir( $path ) {
+ /*
+ * Safe mode fails with a trailing slash under certain PHP versions.
+ */
+ $path = untrailingslashit( wp_normalize_path( $path ) );
+
+ if ( $this->is_root( $path ) ) {
+ return $this->is_dir( $this->get_root() ) && $this->is_writable( $this->get_root() );
+ }
+
+ if ( $this->exists( $path ) ) {
+ return $this->is_dir( $path ) && $this->is_writable( $path );
+ }
+
+ $site_root = $this->get_site_root();
+
+ if ( strpos( $path, $site_root ) !== 0 ) {
+ return false;
+ }
+
+ $bits = preg_replace( '@^' . preg_quote( $site_root, '@' ) . '@i', '', $path );
+ $bits = explode( '/', trim( $bits, '/' ) );
+ $path = untrailingslashit( $site_root );
+
+ foreach ( $bits as $bit ) {
+ $parent_path = $path;
+ $path .= '/' . $bit;
+
+ if ( $this->exists( $path ) ) {
+ if ( ! $this->is_dir( $path ) ) {
+ return false;
+ }
+
+ continue;
+ }
+
+ if ( ! $this->is_writable( $parent_path ) ) {
+ $this->chmod_dir( $parent_path );
+
+ if ( ! $this->is_writable( $parent_path ) ) {
+ return false;
+ }
+ }
+
+ $this->mkdir( $path );
+
+ if ( ! $this->exists( $path ) ) {
+ return false;
+ }
+
+ $this->touch( trailingslashit( $path ) . 'index.php' );
+ }
+
+ return true;
+ }
+
+ /**
+ * Set a file permissions using FS_CHMOD_FILE.
+ *
+ * @since 1.7.1
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param string $file_path Path to the file.
+ * @return bool True on success, false on failure.
+ */
+ public function chmod_file( $file_path ) {
+ if ( ! $file_path ) {
+ return false;
+ }
+
+ return $this->chmod( $file_path, FS_CHMOD_FILE );
+ }
+
+ /**
+ * Set a directory permissions using FS_CHMOD_DIR.
+ *
+ * @since 1.7.1
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param string $file_path Path to the directory.
+ * @return bool True on success, false on failure.
+ */
+ public function chmod_dir( $file_path ) {
+ if ( ! $file_path ) {
+ return false;
+ }
+
+ return $this->chmod( $file_path, FS_CHMOD_DIR );
+ }
+
+ /**
+ * Get a file mime type.
+ *
+ * @since 1.7.1
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param string $file_path A file path (prefered) or a filename.
+ * @return string|bool A mime type. False on failure: the test is limited to mime types supported by Imagify.
+ */
+ public function get_mime_type( $file_path ) {
+ if ( ! $file_path ) {
+ return false;
+ }
+
+ $file_type = wp_check_filetype( $file_path, imagify_get_mime_types() );
+
+ return $file_type['type'];
+ }
+
+ /**
+ * Get a file modification date, formated as "mysql". Fallback to current date.
+ *
+ * @since 1.7.1
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param string $file_path Path to the file.
+ * @return string The date.
+ */
+ public function get_date( $file_path ) {
+ static $offset;
+
+ if ( ! $file_path ) {
+ return current_time( 'mysql' );
+ }
+
+ $date = $this->mtime( $file_path );
+
+ if ( ! $date ) {
+ return current_time( 'mysql' );
+ }
+
+ if ( ! isset( $offset ) ) {
+ $offset = get_option( 'gmt_offset' ) * HOUR_IN_SECONDS;
+ }
+
+ return gmdate( 'Y-m-d H:i:s', $date + $offset );
+ }
+
+ /**
+ * Tell if a file is symlinked.
+ *
+ * @since 1.7.1
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param string $file_path An absolute path.
+ * @return bool
+ */
+ public function is_symlinked( $file_path ) {
+ static $site_root;
+ static $plugin_paths = array();
+ global $wp_plugin_paths;
+
+ if ( ! $file_path ) {
+ return false;
+ }
+
+ $real_path = realpath( $file_path );
+
+ if ( ! $real_path ) {
+ return false;
+ }
+
+ if ( ! isset( $site_root ) ) {
+ $site_root = $this->normalize_path_for_comparison( $this->get_site_root() );
+ }
+
+ $lower_file_path = $this->normalize_path_for_comparison( $real_path );
+
+ if ( strpos( $lower_file_path, $site_root ) !== 0 ) {
+ return true;
+ }
+
+ if ( $wp_plugin_paths && is_array( $wp_plugin_paths ) ) {
+ if ( ! $plugin_paths ) {
+ foreach ( $wp_plugin_paths as $dir => $real_dir ) {
+ $dir = $this->normalize_path_for_comparison( $dir );
+ $plugin_paths[ $dir ] = $this->normalize_path_for_comparison( $real_dir );
+ }
+ }
+
+ $lower_file_path = $this->normalize_path_for_comparison( $file_path );
+
+ foreach ( $plugin_paths as $dir => $real_dir ) {
+ if ( strpos( $lower_file_path, $dir ) === 0 ) {
+ return true;
+ }
+ }
+ }
+
+ return false;
+ }
+
+ /**
+ * Tell if a file is a pdf.
+ *
+ * @since 1.8
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param string $file_path Path to the file.
+ * @return bool
+ */
+ public function is_pdf( $file_path ) {
+ if ( function_exists( 'finfo_fopen' ) ) {
+ $finfo = finfo_open( FILEINFO_MIME );
+
+ if ( $finfo ) {
+ $mimetype = finfo_file( $finfo, $file_path );
+
+ if ( false !== $mimetype ) {
+ return 'application/pdf' === $mimetype;
+ }
+ }
+ }
+
+ if ( function_exists( 'mime_content_type' ) ) {
+ $mimetype = mime_content_type( $file_path );
+ return 'application/pdf' === $mimetype;
+ }
+
+ return false;
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** CLASS OVERWRITES ======================================================================== */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Move a file and apply chmod.
+ * If the file failed to be moved once, a 2nd attempt is made after applying chmod.
+ *
+ * @since 1.8
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param string $source Path to the file to move.
+ * @param string $destination Path to the destination.
+ * @param bool $overwrite Allow to overwrite existing file at destination.
+ * @return bool True on success, false on failure.
+ */
+ public function move( $source, $destination, $overwrite = false ) {
+ if ( parent::move( $source, $destination, $overwrite ) ) {
+ return $this->chmod_file( $destination );
+ }
+
+ if ( ! $this->chmod_file( $destination ) ) {
+ return false;
+ }
+
+ if ( parent::move( $source, $destination, $overwrite ) ) {
+ return $this->chmod_file( $destination );
+ }
+
+ return false;
+ }
+
+ /**
+ * Determine if a file or directory is writable.
+ * This function is used to work around certain ACL issues in PHP primarily affecting Windows Servers.
+ * Replacement for is_writable().
+ *
+ * @since 1.7.1
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param string $file_path Path to the file.
+ * @return bool
+ */
+ public function is_writable( $file_path ) {
+ if ( ! $file_path ) {
+ return false;
+ }
+
+ return wp_is_writable( $file_path );
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** WORK WITH IMAGES ======================================================================== */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Tell if a file is an image.
+ *
+ * @since 1.8
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param string $file_path Path to the file.
+ * @return bool
+ */
+ public function is_image( $file_path ) {
+ if ( function_exists( 'finfo_fopen' ) ) {
+ $finfo = finfo_open( FILEINFO_MIME );
+
+ if ( $finfo ) {
+ $mimetype = finfo_file( $finfo, $file_path );
+
+ if ( false !== $mimetype ) {
+ return strpos( $mimetype, 'image/' ) === 0;
+ }
+ }
+ }
+
+ if ( function_exists( 'exif_imagetype' ) ) {
+ $mimetype = exif_imagetype( $file_path );
+ return (bool) $mimetype;
+ }
+
+ if ( function_exists( 'mime_content_type' ) ) {
+ $mimetype = mime_content_type( $file_path );
+ return strpos( $mimetype, 'image/' ) === 0;
+ }
+
+ return false;
+ }
+
+ /**
+ * Get an image data.
+ * Replacement for getimagesize().
+ *
+ * @since 1.7.1
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param string $file_path Path to the file.
+ * @return array The image data. An empty array on failure.
+ */
+ public function get_image_size( $file_path ) {
+ if ( ! $file_path ) {
+ return array();
+ }
+
+ $size = @getimagesize( $file_path );
+
+ if ( ! $size || ! isset( $size[0], $size[1] ) ) {
+ return array();
+ }
+
+ return array(
+ 0 => (int) $size[0],
+ 1 => (int) $size[1],
+ 'width' => (int) $size[0],
+ 'height' => (int) $size[1],
+ 'type' => (int) $size[2],
+ 'attr' => $size[3],
+ 'channels' => isset( $size['channels'] ) ? (int) $size['channels'] : null,
+ 'bits' => isset( $size['bits'] ) ? (int) $size['bits'] : null,
+ 'mime' => $size['mime'],
+ );
+ }
+
+ /**
+ * Tell if exif_read_data() is available.
+ *
+ * @since 1.7.1
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return bool
+ */
+ public function can_get_exif() {
+ static $callable;
+
+ if ( ! isset( $callable ) ) {
+ $callable = is_callable( 'exif_read_data' );
+ }
+
+ return $callable;
+ }
+
+ /**
+ * Get the EXIF headers from an image file.
+ * Replacement for exif_read_data().
+ *
+ * @since 1.7.1
+ * @access public
+ * @author Grégory Viguier
+ * @see https://secure.php.net/manual/en/function.exif-read-data.php
+ *
+ * @param string $file_path Path to the file.
+ * @param string $sections A comma separated list of sections that need to be present in file to produce a result array. See exif_read_data() documentation for values: FILE, COMPUTED, ANY_TAG, IFD0, THUMBNAIL, COMMENT, EXIF.
+ * @param bool $arrays Specifies whether or not each section becomes an array. The sections COMPUTED, THUMBNAIL, and COMMENT always become arrays as they may contain values whose names conflict with other sections.
+ * @param bool $thumbnail When set to TRUE the thumbnail itself is read. Otherwise, only the tagged data is read.
+ * @return array The EXIF headers. An empty array on failure.
+ */
+ public function get_image_exif( $file_path, $sections = null, $arrays = false, $thumbnail = false ) {
+ if ( ! $file_path || ! $this->can_get_exif() ) {
+ return array();
+ }
+
+ $exif = @exif_read_data( $file_path, $sections, $arrays, $thumbnail );
+
+ return is_array( $exif ) ? $exif : array();
+ }
+
+ /**
+ * Tell if a file is an animated gif.
+ *
+ * @since 1.9.5
+ * @access public
+ * @source https://www.php.net/manual/en/function.imagecreatefromgif.php#104473
+ * @author Grégory Viguier
+ *
+ * @param string $file_path Path to the file.
+ * @return bool|null Null if the file cannot be read.
+ */
+ public function is_animated_gif( $file_path ) {
+ if ( $this->path_info( $file_path, 'extension' ) !== 'gif' ) {
+ // Not a gif file.
+ return false;
+ }
+
+ $fh = @fopen( $file_path, 'rb' ); // phpcs:ignore WordPress.WP.AlternativeFunctions.file_system_read_fopen
+
+ if ( ! $fh ) {
+ // Could not open the file.
+ return null;
+ }
+
+ /**
+ * An animated gif contains multiple "frames", with each frame having a header made up of:
+ * - a static 4-byte sequence (\x00\x21\xF9\x04),
+ * - 4 variable bytes,
+ * - a static 2-byte sequence (\x00\x2C) (some variants may use \x00\x21 ?).
+ */
+ $count = 0;
+
+ // We read through the file til we reach the end of the file, or we've found at least 2 frame headers.
+ while ( ! feof( $fh ) && $count < 2 ) {
+ // Read 100kb at a time.
+ $chunk = fread( $fh, 1024 * 100 ); // phpcs:ignore WordPress.WP.AlternativeFunctions.file_system_read_fread
+ $count += preg_match_all( '#\x00\x21\xF9\x04.{4}\x00(\x2C|\x21)#s', $chunk, $matches );
+ }
+
+ fclose( $fh ); // phpcs:ignore WordPress.WP.AlternativeFunctions.file_system_read_fclose
+
+ return $count > 1;
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** WORK WITH PATHS ========================================================================= */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Make an absolute path relative to WordPress' root folder.
+ * Also works for files from registered symlinked plugins.
+ *
+ * @since 1.7.1
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param string $file_path An absolute path.
+ * @param string $base A base path to use instead of ABSPATH.
+ * @return string|bool A relative path. Can return the absolute path or false in case of a failure.
+ */
+ public function make_path_relative( $file_path, $base = '' ) {
+ global $wp_plugin_paths;
+
+ if ( ! $file_path ) {
+ return false;
+ }
+
+ $file_path = wp_normalize_path( $file_path );
+ $base = $base ? $this->normalize_dir_path( $base ) : $this->get_site_root();
+ $pos = strpos( $file_path, $base );
+
+ if ( false === $pos && $wp_plugin_paths && is_array( $wp_plugin_paths ) ) {
+ // The file is probably part of a symlinked plugin.
+ arsort( $wp_plugin_paths );
+
+ foreach ( $wp_plugin_paths as $dir => $real_dir ) {
+ if ( strpos( $file_path, $real_dir ) === 0 ) {
+ $file_path = wp_normalize_path( $dir . substr( $file_path, strlen( $real_dir ) ) );
+ }
+ }
+
+ $pos = strpos( $file_path, $base );
+ }
+
+ if ( false === $pos ) {
+ // We're in trouble.
+ return $file_path;
+ }
+
+ return substr_replace( $file_path, '', 0, $pos + strlen( $base ) );
+ }
+
+ /**
+ * Normalize a directory path.
+ * The path is normalized and a trailing slash is added.
+ *
+ * @since 1.7.1
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param string $file_path The file path.
+ * @return string The normalized dir path.
+ */
+ public function normalize_dir_path( $file_path ) {
+ return wp_normalize_path( trailingslashit( $file_path ) );
+ }
+
+ /**
+ * Normalize a file path, aiming for path comparison.
+ * The path is normalized, case-lowered, and a trailing slash is added.
+ *
+ * @since 1.7.1
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param string $file_path The file path.
+ * @return string The normalized file path.
+ */
+ public function normalize_path_for_comparison( $file_path ) {
+ return strtolower( $this->normalize_dir_path( $file_path ) );
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** SOME WELL KNOWN PATHS AND URLS ========================================================== */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Tell if WordPress is installed in its own directory: aka WP's path !== site's path.
+ *
+ * @since 1.8.1
+ * @access public
+ * @see https://codex.wordpress.org/Giving_WordPress_Its_Own_Directory
+ * @author Grégory Viguier
+ *
+ * @return string
+ */
+ public function has_wp_its_own_directory() {
+ return $this->get_abspath() !== $this->get_site_root();
+ }
+
+ /**
+ * The path to the server's root is not always '/', it can also be '//' or 'C://'.
+ * I am get_root.
+ *
+ * @since 1.7.1
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return string The path to the server's root.
+ */
+ public function get_root() {
+ static $groot;
+
+ if ( isset( $groot ) ) {
+ return $groot;
+ }
+
+ $groot = preg_replace( '@^((?:.:)?/+).*@', '$1', $this->get_site_root() );
+
+ return $groot;
+ }
+
+ /**
+ * Tell if a path is the server's root.
+ *
+ * @since 1.7.1
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param string $path The path.
+ * @return bool
+ */
+ public function is_root( $path ) {
+ $path = rtrim( $path, '/\\' );
+ return '.' === $path || '' === $path || preg_match( '@^.:$@', $path );
+ }
+
+ /**
+ * Get the path to the site's root.
+ * This is an improved version of get_home_path() that *should* work in almost every cases.
+ * Because creating a constant like ABSPATH was too simple.
+ *
+ * @since 1.8.1
+ * @access public
+ * @see get_home_path()
+ * @author Grégory Viguier
+ *
+ * @return string
+ */
+ public function get_site_root() {
+ static $root_path;
+
+ if ( isset( $root_path ) ) {
+ return $root_path;
+ }
+
+ /**
+ * Filter the path to the site's root.
+ *
+ * @since 1.8.1
+ * @author Grégory Viguier
+ *
+ * @param string $root_path Path to the site's root. Default is null.
+ */
+ $root_path = apply_filters( 'imagify_site_root', null );
+
+ if ( is_string( $root_path ) ) {
+ $root_path = trailingslashit( wp_normalize_path( $root_path ) );
+
+ return $root_path;
+ }
+
+ $home = set_url_scheme( untrailingslashit( get_option( 'home' ) ), 'http' );
+ $siteurl = set_url_scheme( untrailingslashit( get_option( 'siteurl' ) ), 'http' );
+
+ if ( ! empty( $home ) && 0 !== strcasecmp( $home, $siteurl ) ) {
+ $wp_path_rel_to_home = str_ireplace( $home, '', $siteurl ); /* $siteurl - $home */
+ $pos = strripos( str_replace( '\\', '/', ABSPATH ), trailingslashit( $wp_path_rel_to_home ) );
+ $root_path = substr( ABSPATH, 0, $pos );
+ $root_path = trailingslashit( wp_normalize_path( $root_path ) );
+ return $root_path;
+ }
+
+ if ( ! defined( 'PATH_CURRENT_SITE' ) || ! is_multisite() || is_main_site() ) {
+ $root_path = $this->get_abspath();
+ return $root_path;
+ }
+
+ /**
+ * For a multisite in its own directory, get_home_path() returns the expected path only for the main site.
+ *
+ * Friend, each time an attempt is made to improve this method, and especially this part, please increment the following counter.
+ * Improvement attempts: 3.
+ */
+ $document_root = realpath( wp_unslash( $_SERVER['DOCUMENT_ROOT'] ) ); // `realpath()` is needed for those cases where $_SERVER['DOCUMENT_ROOT'] is totally different from ABSPATH.
+ $document_root = trailingslashit( str_replace( '\\', '/', $document_root ) );
+ $path_current_site = trim( str_replace( '\\', '/', PATH_CURRENT_SITE ), '/' );
+ $root_path = trailingslashit( wp_normalize_path( $document_root . $path_current_site ) );
+
+ return $root_path;
+ }
+
+ /**
+ * Get the URL of the site's root. It corresponds to the main site's home page URL.
+ *
+ * @since 1.8.1
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return string
+ */
+ public function get_site_root_url() {
+ static $root_url;
+
+ if ( isset( $root_url ) ) {
+ return $root_url;
+ }
+
+ if ( ! is_multisite() || is_main_site() ) {
+ $root_url = home_url( '/' );
+ return $root_url;
+ }
+
+ $current_network = false;
+
+ if ( function_exists( 'get_network' ) ) {
+ $current_network = get_network();
+ } elseif ( function_exists( 'get_current_site' ) ) {
+ $current_network = get_current_site();
+ }
+
+ if ( ! $current_network ) {
+ $root_url = home_url( '/' );
+ return $root_url;
+ }
+
+ $root_url = is_ssl() ? 'https' : 'http';
+ $root_url = set_url_scheme( 'http://' . $current_network->domain . $current_network->path, $root_url );
+ $root_url = trailingslashit( $root_url );
+
+ return $root_url;
+ }
+
+ /**
+ * Tell if a path is the site's root.
+ *
+ * @since 1.8.1
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param string $path The path.
+ * @return bool
+ */
+ public function is_site_root( $path ) {
+ return $this->normalize_dir_path( $path ) === $this->get_site_root();
+ }
+
+ /**
+ * Get a clean value of ABSPATH.
+ *
+ * @since 1.7.1
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return string The path to WordPress' root folder.
+ */
+ public function get_abspath() {
+ static $abspath;
+
+ if ( isset( $abspath ) ) {
+ return $abspath;
+ }
+
+ $abspath = wp_normalize_path( ABSPATH );
+
+ // Make sure ABSPATH is not messed up: it could be defined as a relative path for example (yeah, I know, but we've seen it).
+ $test_file = wp_normalize_path( IMAGIFY_FILE );
+ $pos = strpos( $test_file, $abspath );
+
+ if ( $pos > 0 ) {
+ // ABSPATH has a wrong value.
+ $abspath = substr( $test_file, 0, $pos ) . $abspath;
+
+ } elseif ( false === $pos && class_exists( 'ReflectionClass' ) ) {
+ // Imagify is symlinked (dude, you look for trouble).
+ $reflector = new ReflectionClass( 'WP' );
+ $test_file = $reflector->getFileName();
+ $pos = strpos( $test_file, $abspath );
+
+ if ( 0 < $pos ) {
+ // ABSPATH has a wrong value.
+ $abspath = substr( $test_file, 0, $pos ) . $abspath;
+ }
+ }
+
+ $abspath = trailingslashit( $abspath );
+
+ if ( '/' !== substr( $abspath, 0, 1 ) && ':' !== substr( $abspath, 1, 1 ) ) {
+ $abspath = '/' . $abspath;
+ }
+
+ return $abspath;
+ }
+
+ /**
+ * Tell if a path is WP's root (ABSPATH).
+ *
+ * @since 1.7.1
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param string $path The path.
+ * @return bool
+ */
+ public function is_abspath( $path ) {
+ return $this->normalize_dir_path( $path ) === $this->get_abspath();
+ }
+
+ /**
+ * Get the upload basedir.
+ *
+ * @since 1.7.1
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param bool $bypass_error True to return the path even if there is an error. This is used when we want to display this path in a message for example.
+ * @return string|bool The path. False on failure.
+ */
+ public function get_upload_basedir( $bypass_error = false ) {
+ static $upload_basedir;
+ static $upload_basedir_or_error;
+
+ if ( isset( $upload_basedir ) ) {
+ return $bypass_error ? $upload_basedir : $upload_basedir_or_error;
+ }
+
+ $uploads = wp_upload_dir();
+ $upload_basedir = $this->normalize_dir_path( $uploads['basedir'] );
+
+ if ( false !== $uploads['error'] ) {
+ $upload_basedir_or_error = false;
+ } else {
+ $upload_basedir_or_error = $upload_basedir;
+ }
+
+ return $bypass_error ? $upload_basedir : $upload_basedir_or_error;
+ }
+
+ /**
+ * Get the upload baseurl.
+ *
+ * @since 1.7.1
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return string|bool The URL. False on failure.
+ */
+ public function get_upload_baseurl() {
+ static $upload_baseurl;
+
+ if ( isset( $upload_baseurl ) ) {
+ return $upload_baseurl;
+ }
+
+ $uploads = wp_upload_dir();
+
+ if ( false !== $uploads['error'] ) {
+ $upload_baseurl = false;
+ return $upload_baseurl;
+ }
+
+ $upload_baseurl = trailingslashit( $uploads['baseurl'] );
+
+ return $upload_baseurl;
+ }
+
+ /**
+ * Get the path to the uploads base directory of the main site.
+ *
+ * @since 1.8
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return string
+ */
+ public function get_main_upload_basedir() {
+ static $basedir;
+
+ if ( isset( $basedir ) ) {
+ return $basedir;
+ }
+
+ $basedir = get_imagify_upload_basedir( true );
+
+ if ( is_multisite() ) {
+ $pattern = '/' . $this->get_multisite_uploads_subdir_pattern() . '$';
+ $basedir = preg_replace( self::PATTERN_DELIMITER . $pattern . self::PATTERN_DELIMITER, '/', $basedir );
+ }
+
+ return $basedir;
+ }
+
+ /**
+ * Get the URL of the uploads base directory of the main site.
+ *
+ * @since 1.8
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return string
+ */
+ public function get_main_upload_baseurl() {
+ static $baseurl;
+
+ if ( isset( $baseurl ) ) {
+ return $baseurl;
+ }
+
+ $baseurl = get_imagify_upload_baseurl( true );
+
+ if ( is_multisite() ) {
+ $pattern = '/' . $this->get_multisite_uploads_subdir_pattern() . '$';
+ $baseurl = preg_replace( self::PATTERN_DELIMITER . $pattern . self::PATTERN_DELIMITER, '/', $baseurl );
+ }
+
+ return $baseurl;
+ }
+
+ /**
+ * Get the regex pattern used to match the uploads subdir on multisite in a file path.
+ * Pattern delimiter is `Imagify_Filesystem::PATTERN_DELIMITER`.
+ * Paths tested against these patterns are lower-cased.
+ *
+ * @since 1.8
+ * @access public
+ * @see _wp_upload_dir()
+ * @author Grégory Viguier
+ *
+ * @return string
+ */
+ public function get_multisite_uploads_subdir_pattern() {
+ static $pattern;
+
+ if ( isset( $pattern ) ) {
+ return $pattern;
+ }
+
+ $pattern = '';
+
+ if ( ! is_multisite() ) {
+ return $pattern;
+ }
+
+ if ( ! get_site_option( 'ms_files_rewriting' ) ) {
+ if ( defined( 'MULTISITE' ) ) {
+ $pattern = 'sites/\d+/';
+ } else {
+ $pattern = '\d+/';
+ }
+ } elseif ( defined( 'UPLOADS' ) ) {
+ $site_id = (string) get_current_blog_id();
+ $path = $this->get_upload_basedir( true ); // Something like `/absolute/path/to/wp-content/blogs.dir/3/files/`, also for site 1.
+ $path = strrev( $path );
+
+ if ( preg_match( self::PATTERN_DELIMITER . '^.*' . strrev( $site_id ) . '[^/]*/' . self::PATTERN_DELIMITER . 'U', $path, $matches ) ) {
+ $pattern = end( $matches );
+ $pattern = ltrim( strtolower( strrev( $pattern ) ), '/' );
+ $pattern = str_replace( $site_id, '\d+', $pattern );
+ }
+ }
+
+ /**
+ * Filter the regex pattern used to match the uploads subdir on multisite in a file path.
+ * Pattern delimiter is `Imagify_Filesystem::PATTERN_DELIMITER`.
+ * Important: lowercase, no heading slash, mandatory trailing slash.
+ *
+ * @since 1.8
+ * @author Grégory Viguier
+ *
+ * @param string $pattern The regex pattern.
+ */
+ $pattern = apply_filters( 'imagify_multisite_uploads_subdir_pattern', $pattern );
+
+ return $pattern;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/inc/classes/class-imagify-folders-db.php b/wp/wp-content/plugins/imagify/inc/classes/class-imagify-folders-db.php
new file mode 100644
index 00000000..cc3f269f
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/classes/class-imagify-folders-db.php
@@ -0,0 +1,238 @@
+ '%d',
+ 'path' => '%s',
+ 'active' => '%d',
+ );
+ }
+
+ /**
+ * Default column values.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return array
+ */
+ public function get_column_defaults() {
+ return array(
+ 'folder_id' => 0,
+ 'path' => '',
+ 'active' => 0,
+ );
+ }
+
+ /**
+ * Get the query to create the table fields.
+ *
+ * @since 1.7
+ * @access protected
+ * @author Grégory Viguier
+ *
+ * @return string
+ */
+ protected function get_table_schema() {
+ return "
+ folder_id bigint(20) unsigned NOT NULL auto_increment,
+ path varchar(191) NOT NULL default '',
+ active tinyint(1) unsigned NOT NULL default 0,
+ PRIMARY KEY (folder_id),
+ UNIQUE KEY path (path),
+ KEY active (active)";
+ }
+
+ /**
+ * Tell if folders are selected in the plugin settings.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return bool
+ */
+ public function has_active_folders() {
+ global $wpdb;
+
+ $column = esc_sql( $this->get_primary_key() );
+
+ return (bool) $wpdb->get_var( "SELECT $column FROM $this->table_name WHERE active = 1 LIMIT 1;" ); // WPCS: unprepared SQL ok.
+ }
+
+ /**
+ * Retrieve active folders (checked in the settings).
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param string $column_select A column name.
+ * @return array
+ */
+ public function get_active_folders_column( $column_select ) {
+ global $wpdb;
+
+ $column = esc_sql( $column_select );
+
+ $result = $wpdb->get_col( "SELECT $column FROM $this->table_name WHERE active = 1;" ); // WPCS: unprepared SQL ok.
+
+ return $this->cast_col( $result, $column_select );
+ }
+
+ /**
+ * Retrieve active folders (checked in the settings) by the specified column / values.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param string $column_select A column name.
+ * @param string $column_where A column name.
+ * @param array $column_values An array of values.
+ * @return array
+ */
+ public function get_active_folders_column_in( $column_select, $column_where, $column_values ) {
+ global $wpdb;
+
+ $column = esc_sql( $column_select );
+ $column_where = esc_sql( $column_where );
+ $column_values = Imagify_DB::prepare_values_list( $column_values );
+
+ $result = $wpdb->get_col( "SELECT $column FROM $this->table_name WHERE $column_where IN ( $column_values ) AND active = 1;" ); // WPCS: unprepared SQL ok.
+
+ return $this->cast_col( $result, $column_select );
+ }
+
+ /**
+ * Retrieve active folders (checked in the settings) by the specified column / values.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param string $column_select A column name.
+ * @param string $column_where A column name.
+ * @param array $column_values An array of values.
+ * @return array
+ */
+ public function get_active_folders_column_not_in( $column_select, $column_where, $column_values ) {
+ global $wpdb;
+
+ $column = esc_sql( $column_select );
+ $column_where = esc_sql( $column_where );
+ $column_values = Imagify_DB::prepare_values_list( $column_values );
+
+ $result = $wpdb->get_col( "SELECT $column FROM $this->table_name WHERE $column_where NOT IN ( $column_values ) AND active = 1;" ); // WPCS: unprepared SQL ok.
+
+ return $this->cast_col( $result, $column_select );
+ }
+
+ /**
+ * Retrieve not active folders (not checked in the settings).
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param string $column_select A column name.
+ * @return array
+ */
+ public function get_inactive_folders_column( $column_select ) {
+ global $wpdb;
+
+ $column = esc_sql( $column_select );
+
+ $result = $wpdb->get_col( "SELECT $column FROM $this->table_name WHERE active != 1;" ); // WPCS: unprepared SQL ok.
+
+ return $this->cast_col( $result, $column_select );
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/inc/classes/class-imagify-options.php b/wp/wp-content/plugins/imagify/inc/classes/class-imagify-options.php
new file mode 100644
index 00000000..a60450cd
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/classes/class-imagify-options.php
@@ -0,0 +1,215 @@
+ '',
+ 'optimization_level' => 2,
+ 'lossless' => 0,
+ 'auto_optimize' => 0,
+ 'backup' => 0,
+ 'resize_larger' => 0,
+ 'resize_larger_w' => 0,
+ 'display_nextgen' => 0,
+ 'display_nextgen_method' => 'picture',
+ 'display_webp' => 0,
+ 'display_webp_method' => 'picture',
+ 'cdn_url' => '',
+ 'disallowed-sizes' => [],
+ 'admin_bar_menu' => 0,
+ 'partner_links' => 0,
+ 'convert_to_avif' => 0,
+ 'convert_to_webp' => 0,
+ 'optimization_format' => 'webp',
+ ];
+
+ /**
+ * The Imagify main option values used when they are set the first time or reset.
+ * Values identical to default values are not listed.
+ *
+ * @var array
+ * @since 1.7
+ */
+ protected $reset_values = [
+ 'optimization_level' => 2,
+ 'auto_optimize' => 1,
+ 'backup' => 1,
+ 'admin_bar_menu' => 1,
+ 'partner_links' => 1,
+ ];
+
+ /**
+ * The constructor.
+ * Side note: $this->hook_identifier value is "option".
+ *
+ * @since 1.7
+ */
+ protected function __construct() {
+ if ( defined( 'IMAGIFY_API_KEY' ) && IMAGIFY_API_KEY ) {
+ $this->default_values['api_key'] = (string) IMAGIFY_API_KEY;
+ }
+
+ if ( function_exists( 'wp_get_original_image_path' ) ) {
+ $this->reset_values['resize_larger'] = 1;
+
+ $filter_cb = [ imagify_get_context( 'wp' ), 'get_resizing_threshold' ];
+ $filtered = has_filter( 'big_image_size_threshold', $filter_cb );
+
+ if ( $filtered ) {
+ remove_filter( 'big_image_size_threshold', $filter_cb, IMAGIFY_INT_MAX );
+ }
+
+ /** This filter is documented in wp-admin/includes/image.php */
+ $this->reset_values['resize_larger_w'] = (int) apply_filters( 'big_image_size_threshold', 2560, [ 0, 0 ], '', 0 );
+ $this->reset_values['resize_larger_w'] = $this->sanitize_and_validate_value( 'resize_larger_w', $this->reset_values['resize_larger_w'], $this->default_values['resize_larger_w'] );
+
+ if ( $filtered ) {
+ add_filter( 'big_image_size_threshold', $filter_cb, IMAGIFY_INT_MAX );
+ }
+ }
+
+ $this->network_option = imagify_is_active_for_network();
+
+ parent::__construct();
+ }
+
+ /**
+ * Sanitize and validate an option value. Basic casts have been made.
+ *
+ * @since 1.7
+ *
+ * @param string $key The option key.
+ * @param mixed $value The value.
+ * @param mixed $default The default value.
+ * @return mixed
+ */
+ public function sanitize_and_validate_value( $key, $value, $default ) {
+ static $max_sizes;
+
+ switch ( $key ) {
+ case 'api_key':
+ if ( defined( 'IMAGIFY_API_KEY' ) && IMAGIFY_API_KEY ) {
+ return (string) IMAGIFY_API_KEY;
+ }
+ return $value ? sanitize_key( $value ) : '';
+
+ case 'optimization_level':
+ if ( $value < 0 || $value > 2 ) {
+ // For an invalid value, return the "reset" value.
+ $reset_values = $this->get_reset_values();
+ return $reset_values[ $key ];
+ }
+ return $value;
+ case 'optimization_format':
+ if ( ! in_array( $value, [ 'off', 'webp', 'avif' ], true ) ) {
+ // For an invalid value, return the "reset" value.
+ $reset_values = $this->get_reset_values();
+ return $reset_values[ $key ];
+ }
+ return $value;
+ case 'auto_optimize':
+ case 'backup':
+ case 'lossless':
+ case 'resize_larger':
+ case 'convert_to_webp':
+ case 'display_nextgen':
+ case 'display_webp':
+ case 'admin_bar_menu':
+ case 'partner_links':
+ case 'convert_to_avif':
+ return empty( $value ) ? 0 : 1;
+
+ case 'resize_larger_w':
+ if ( $value <= 0 ) {
+ // Invalid.
+ return $default;
+ }
+ if ( ! isset( $max_sizes ) ) {
+ $max_sizes = get_imagify_max_intermediate_image_size();
+ }
+ if ( $value < $max_sizes['width'] ) {
+ // Invalid.
+ return $max_sizes['width'];
+ }
+ return $value;
+
+ case 'disallowed-sizes':
+ if ( ! $value ) {
+ return $default;
+ }
+
+ $value = array_keys( $value );
+ $value = array_map( 'sanitize_text_field', $value );
+ return array_fill_keys( $value, 1 );
+
+ case 'display_nextgen_method':
+ case 'display_webp_method':
+ $values = [
+ 'picture' => 1,
+ 'rewrite' => 1,
+ ];
+ if ( isset( $values[ $value ] ) ) {
+ return $value;
+ }
+ // For an invalid value, return the "reset" value.
+ $reset_values = $this->get_reset_values();
+ return $reset_values[ $key ];
+
+ case 'cdn_url':
+ $cdn_source = apply_filters( 'imagify_cdn_source_url', $value );
+
+ if ( 'option' !== $cdn_source['source'] ) {
+ /**
+ * If the URL is defined via constant or filter, unset the option.
+ * This is useful when the CDN is disabled: there is no need to do anything then.
+ */
+ return '';
+ }
+
+ return $cdn_source['url'];
+ }
+
+ return false;
+ }
+
+ /**
+ * Validate Imagify's options before storing them. Basic sanitization and validation have been made, row by row.
+ *
+ * @since 1.7
+ *
+ * @param string $values The option value.
+ * @return array
+ */
+ public function validate_values_on_update( $values ) {
+ // The max width for the "Resize larger images" option can't be 0.
+ if ( empty( $values['resize_larger_w'] ) ) {
+ unset( $values['resize_larger'], $values['resize_larger_w'] );
+ }
+
+ return $values;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/inc/classes/class-imagify-requirements-check.php b/wp/wp-content/plugins/imagify/inc/classes/class-imagify-requirements-check.php
new file mode 100644
index 00000000..e580b5b9
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/classes/class-imagify-requirements-check.php
@@ -0,0 +1,343 @@
+$setting = $args[ $setting ];
+ }
+ }
+
+ if ( empty( $this->wp_last_version ) ) {
+ $this->wp_last_version = '1.6.14.2';
+ }
+
+ if ( empty( $this->php_last_version ) ) {
+ $this->php_last_version = '1.8.4.1';
+ }
+ }
+
+ /**
+ * Check if all requirements are ok, if not, display a notice and the rollback.
+ *
+ * @since 1.9
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return bool
+ */
+ public function check() {
+ if ( ! $this->php_passes() || ! $this->wp_passes() ) {
+ add_action( 'admin_notices', array( $this, 'print_notice' ) );
+ add_action( 'admin_post_imagify_rollback', array( $this, 'rollback' ) );
+
+ return false;
+ }
+
+ return true;
+ }
+
+ /**
+ * Check if the current PHP version is equal or superior to the required PHP version.
+ *
+ * @since 1.9
+ * @access private
+ * @author Grégory Viguier
+ *
+ * @return bool
+ */
+ private function php_passes() {
+ return version_compare( PHP_VERSION, $this->php_version ) >= 0;
+ }
+
+ /**
+ * Check if the current WordPress version is equal or superior to the required PHP version.
+ *
+ * @since 1.9
+ * @access private
+ * @author Grégory Viguier
+ *
+ * @return bool
+ */
+ private function wp_passes() {
+ global $wp_version;
+
+ return version_compare( $wp_version, $this->wp_version ) >= 0;
+ }
+
+ /**
+ * Get the last version of the plugin that can run with the current WP and PHP versions.
+ *
+ * @since 1.9
+ * @access private
+ * @author Grégory Viguier
+ *
+ * @return string
+ */
+ private function get_last_version() {
+ $last_version = '';
+
+ if ( ! $this->php_passes() ) {
+ $last_version = $this->php_last_version;
+ }
+
+ if ( ! $this->wp_passes() ) {
+ $last_version = ! $last_version || version_compare( $last_version, $this->wp_last_version ) > 0 ? $this->wp_last_version : $last_version;
+ }
+
+ return $last_version;
+ }
+
+ /**
+ * Tell if the current user can rollback.
+ *
+ * @since 1.9
+ * @access private
+ * @author Grégory Viguier
+ *
+ * @return bool
+ */
+ private function current_user_can() {
+ $describer = 'manage';
+ $capacity = $this->is_active_for_network() ? 'manage_network_options' : 'manage_options';
+ // This filter is documented in classes/Context/AbstractContext.php.
+ $capacity = (string) apply_filters( 'imagify_capacity', $capacity, $describer, 'wp' );
+
+ $user_can = current_user_can( $capacity );
+ // This filter is documented in classes/Context/AbstractContext.php.
+ $user_can = (bool) apply_filters( 'imagify_current_user_can', $user_can, $capacity, $describer, null, 'wp' );
+
+ return $user_can;
+ }
+
+ /**
+ * Tell if Imagify is activated on the network.
+ *
+ * @since 1.9
+ * @access private
+ * @author Grégory Viguier
+ *
+ * return bool True if Imagify is activated on the network.
+ */
+ private function is_active_for_network() {
+ if ( ! is_multisite() ) {
+ return false;
+ }
+
+ if ( ! function_exists( 'is_plugin_active_for_network' ) ) {
+ require_once ABSPATH . 'wp-admin/includes/plugin.php';
+ }
+
+ return is_plugin_active_for_network( plugin_basename( $this->plugin_file ) );
+ }
+
+ /**
+ * Warn if PHP version is less than 5.4 and offers to rollback.
+ *
+ * @since 1.9
+ * @access public
+ * @author Grégory Viguier
+ */
+ public function print_notice() {
+ if ( ! $this->current_user_can() ) {
+ return;
+ }
+
+ imagify_load_translations();
+
+ $message = array();
+ $required = array();
+ $rollback_url = wp_nonce_url( admin_url( 'admin-post.php?action=imagify_rollback' ), 'imagify_rollback' );
+
+ if ( ! $this->php_passes() ) {
+ /* translators: %1$s = Plugin name, %2$s = PHP version required. */
+ $message[] = sprintf( esc_html__( 'To use this %1$s version, please ask your web host how to upgrade your server to PHP %2$s or higher.', 'imagify' ), $this->plugin_name, $this->php_version );
+ $required[] = 'PHP ' . $this->php_version;
+ }
+
+ if ( ! $this->wp_passes() ) {
+ /* translators: %1$s = Plugin name, %2$s = WordPress version required. */
+ $message[] = sprintf( esc_html__( 'To use this %1$s version, please upgrade WordPress to version %2$s or higher.', 'imagify' ), $this->plugin_name, $this->wp_version );
+ $required[] = 'WordPress ' . $this->wp_version;
+ }
+
+ $message = '' . implode( ' ', $message ) . "
\n";
+ $required = wp_sprintf_l( '%l', $required );
+
+ /* translators: %1$s = Plugin name, %2$s = Plugin version, $3$s is something like "PHP 5.4" or "PHP 5.4 and WordPress 4.0". */
+ $message = '' . sprintf( esc_html__( 'To function properly, %1$s %2$s requires at least %3$s.', 'imagify' ), '' . $this->plugin_name . ' ', $this->plugin_version, $required ) . "
\n" . $message;
+
+ $message .= '' . esc_html__( 'If you are not able to upgrade, you can rollback to the previous version by using the button below.', 'imagify' ) . "
\n";
+ /* translators: %s = Previous plugin version. */
+ $message .= '' . sprintf( __( 'Re-install version %s', 'imagify' ), $this->get_last_version() ) . '
';
+
+ echo '' . $message . '
';
+ }
+
+ /**
+ * Do the rollback.
+ *
+ * @since 1.9
+ * @access public
+ * @author Grégory Viguier
+ */
+ public function rollback() {
+ check_ajax_referer( 'imagify_rollback' );
+
+ if ( ! $this->current_user_can() ) {
+ wp_die();
+ }
+
+ imagify_load_translations();
+
+ $plugin_transient = get_site_transient( 'update_plugins' );
+ $plugin_basename = plugin_basename( $this->plugin_file );
+ $plugin_folder = dirname( $plugin_basename );
+ $last_version = $this->get_last_version();
+ $package_filename = $plugin_folder . '.' . $last_version . '.zip';
+
+ $plugin_transient->checked[ $plugin_basename ] = $last_version;
+
+ if ( ! empty( $plugin_transient->response[ $plugin_basename ] ) ) {
+ $tmp_obj = $plugin_transient->response[ $plugin_basename ];
+ } elseif ( ! empty( $plugin_transient->no_update[ $plugin_basename ] ) ) {
+ $tmp_obj = $plugin_transient->no_update[ $plugin_basename ];
+ } else {
+ $tmp_obj = (object) array(
+ 'id' => 'w.org/plugins/' . $plugin_folder,
+ 'slug' => $plugin_folder,
+ 'plugin' => $plugin_basename,
+ 'new_version' => $last_version,
+ 'url' => 'https://wordpress.org/plugins/' . $plugin_folder . '/',
+ 'package' => 'https://downloads.wordpress.org/plugin/' . $package_filename,
+ 'icons' => array(),
+ 'banners' => array(),
+ 'banners_rtl' => array(),
+ );
+ }
+
+ $tmp_obj->new_version = $last_version;
+ $tmp_obj->package = preg_replace( '@/[^/]+$@', '/' . $package_filename, $tmp_obj->package );
+
+ $plugin_transient->response[ $plugin_basename ] = $tmp_obj;
+ unset( $plugin_transient->no_update[ $plugin_basename ] );
+
+ set_site_transient( 'update_plugins', $plugin_transient );
+
+ require_once ABSPATH . 'wp-admin/includes/class-wp-upgrader.php';
+
+ /* translators: %s is the plugin name. */
+ $title = sprintf( __( '%s Update Rollback', 'imagify' ), $this->plugin_name );
+ $nonce = 'upgrade-plugin_' . $plugin_basename;
+ $url = 'update.php?action=upgrade-plugin&plugin=' . rawurlencode( $plugin_basename );
+ $upgrader_skin = new Plugin_Upgrader_Skin( compact( 'title', 'nonce', 'url', 'plugin' ) );
+ $upgrader = new Plugin_Upgrader( $upgrader_skin );
+
+ $upgrader->upgrade( $plugin_basename );
+
+ wp_die(
+ '',
+ /* translators: %s is the plugin name. */
+ sprintf( __( '%s Update Rollback', 'imagify' ), $this->plugin_name ),
+ array( 'response' => 200 )
+ );
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/inc/classes/class-imagify-requirements.php b/wp/wp-content/plugins/imagify/inc/classes/class-imagify-requirements.php
new file mode 100644
index 00000000..6632e6cb
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/classes/class-imagify-requirements.php
@@ -0,0 +1,342 @@
+ IMAGIFY_PATH . 'assets/images/imagify-logo.png',
+ 'mime_types' => imagify_get_mime_types( 'image' ),
+ 'methods' => Imagify_Attachment::get_editor_methods(),
+ );
+
+ /** This filter is documented in /wp-includes/media.php. */
+ $implementations = apply_filters( 'wp_image_editors', array( 'WP_Image_Editor_Imagick', 'WP_Image_Editor_GD' ) );
+
+ foreach ( $implementations as $implementation ) {
+ if ( ! call_user_func( array( $implementation, 'test' ), $args ) ) {
+ continue;
+ }
+
+ foreach ( $args['mime_types'] as $mime_type ) {
+ if ( ! call_user_func( array( $implementation, 'supports_mime_type' ), $mime_type ) ) {
+ continue 2;
+ }
+ }
+
+ if ( array_diff( $args['methods'], get_class_methods( $implementation ) ) ) {
+ continue;
+ }
+
+ self::$supports['image_editor'] = true;
+ break;
+ }
+
+ return self::$supports['image_editor'];
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** WORDPRESS =============================================================================== */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Test for the uploads directory.
+ *
+ * @since 1.7.1
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param bool $reset_cache True to get a fresh value.
+ * @return bool
+ */
+ public static function supports_uploads( $reset_cache = false ) {
+ if ( ! $reset_cache && isset( self::$supports['uploads'] ) ) {
+ return self::$supports['uploads'];
+ }
+
+ self::$supports['uploads'] = Imagify_Filesystem::get_instance()->get_upload_basedir();
+
+ if ( self::$supports['uploads'] ) {
+ self::$supports['uploads'] = Imagify_Filesystem::get_instance()->is_writable( self::$supports['uploads'] );
+ }
+
+ return self::$supports['uploads'];
+ }
+
+ /**
+ * Test if external requests are blocked for Imagify.
+ *
+ * @since 1.7.1
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param bool $reset_cache True to get a fresh value.
+ * @return bool
+ */
+ public static function is_imagify_blocked( $reset_cache = false ) {
+ if ( ! $reset_cache && isset( self::$supports['imagify_blocked'] ) ) {
+ return self::$supports['imagify_blocked'];
+ }
+
+ if ( ! defined( 'WP_HTTP_BLOCK_EXTERNAL' ) || ! WP_HTTP_BLOCK_EXTERNAL ) {
+ self::$supports['imagify_blocked'] = false;
+ return self::$supports['imagify_blocked'];
+ }
+
+ if ( ! defined( 'WP_ACCESSIBLE_HOSTS' ) ) {
+ self::$supports['imagify_blocked'] = true;
+ return self::$supports['imagify_blocked'];
+ }
+
+ $accessible_hosts = explode( ',', WP_ACCESSIBLE_HOSTS );
+ $accessible_hosts = array_map( 'trim', $accessible_hosts );
+ $accessible_hosts = array_flip( $accessible_hosts );
+
+ if ( isset( $accessible_hosts['*.imagify.io'] ) ) {
+ self::$supports['imagify_blocked'] = false;
+ return self::$supports['imagify_blocked'];
+ }
+
+ if ( isset( $accessible_hosts['imagify.io'], $accessible_hosts['app.imagify.io'], $accessible_hosts['storage.imagify.io'] ) ) {
+ self::$supports['imagify_blocked'] = false;
+ return self::$supports['imagify_blocked'];
+ }
+
+ self::$supports['imagify_blocked'] = true;
+ return self::$supports['imagify_blocked'];
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** IMAGIFY BACKUP DIRECTORIES ============================================================== */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Test for the attachments backup directory.
+ *
+ * @since 1.7.1
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param bool $reset_cache True to get a fresh value.
+ * @return bool
+ */
+ public static function attachments_backup_dir_is_writable( $reset_cache = false ) {
+ if ( $reset_cache || ! isset( self::$supports['attachment_backups'] ) ) {
+ self::$supports['attachment_backups'] = imagify_backup_dir_is_writable();
+ }
+
+ return self::$supports['attachment_backups'];
+ }
+
+ /**
+ * Test for the custom folders backup directory.
+ *
+ * @since 1.7.1
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param bool $reset_cache True to get a fresh value.
+ * @return bool
+ */
+ public static function custom_folders_backup_dir_is_writable( $reset_cache = false ) {
+ if ( $reset_cache || ! isset( self::$supports['custom_folder_backups'] ) ) {
+ self::$supports['custom_folder_backups'] = Imagify_Custom_Folders::backup_dir_is_writable();
+ }
+
+ return self::$supports['custom_folder_backups'];
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** IMAGIFY API ============================================================================= */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Determine if the Imagify API is available by checking the API version.
+ * The result is cached for 3 minutes.
+ *
+ * @since 1.7.1
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param bool $reset_cache True to get a fresh value.
+ * @return bool
+ */
+ public static function is_api_up( $reset_cache = false ) {
+ if ( ! $reset_cache && isset( self::$supports['api_up'] ) ) {
+ return self::$supports['api_up'];
+ }
+
+ $transient_name = 'imagify_check_api_version';
+ $transient_expiration = 3 * MINUTE_IN_SECONDS;
+ $transient_value = $reset_cache ? false : get_site_transient( $transient_name );
+
+ if ( false !== $transient_value ) {
+ self::$supports['api_up'] = (bool) $transient_value;
+ return self::$supports['api_up'];
+ }
+
+ self::$supports['api_up'] = ! is_wp_error( get_imagify_api_version() );
+ $transient_value = (int) self::$supports['api_up'];
+
+ set_site_transient( $transient_name, $transient_value, $transient_expiration );
+
+ return self::$supports['api_up'];
+ }
+
+ /**
+ * Test for the Imagify API key validity.
+ * A positive result is cached for 1 year.
+ *
+ * @since 1.7.1
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param bool $reset_cache True to get a fresh value.
+ * @return bool
+ */
+ public static function is_api_key_valid( $reset_cache = false ) {
+ if ( $reset_cache ) {
+ self::reset_cache( 'api_key_valid' );
+ }
+
+ if ( isset( self::$supports['api_key_valid'] ) ) {
+ return self::$supports['api_key_valid'];
+ }
+
+ if ( ! Imagify_Options::get_instance()->get( 'api_key' ) ) {
+ self::$supports['api_key_valid'] = false;
+ return self::$supports['api_key_valid'];
+ }
+
+ if ( get_site_transient( 'imagify_check_licence_1' ) ) {
+ self::$supports['api_key_valid'] = true;
+ return self::$supports['api_key_valid'];
+ }
+
+ if ( is_wp_error( get_imagify_user() ) ) {
+ self::$supports['api_key_valid'] = false;
+ return self::$supports['api_key_valid'];
+ }
+
+ self::$supports['api_key_valid'] = true;
+ set_site_transient( 'imagify_check_licence_1', 1, YEAR_IN_SECONDS );
+
+ return self::$supports['api_key_valid'];
+ }
+
+ /**
+ * Test for the Imagify account quota.
+ *
+ * @since 1.7.1
+ * @since 1.9.9 Return false when the API cannot be reached.
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param bool $reset_cache True to get a fresh value.
+ * @return bool True when over quota. False otherwise, even when the API cannot be reached.
+ */
+ public static function is_over_quota( $reset_cache = false ) {
+ if ( ! $reset_cache && isset( self::$supports['over_quota'] ) ) {
+ return self::$supports['over_quota'];
+ }
+
+ $user = new User();
+
+ self::$supports['over_quota'] = $user->get_error() ? false : $user->is_over_quota();
+
+ return self::$supports['over_quota'];
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** CLASS CACHE ============================================================================= */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Reset a test cache.
+ *
+ * @since 1.7.1
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param string $cache_key Cache key.
+ */
+ public static function reset_cache( $cache_key ) {
+ unset( self::$supports[ $cache_key ] );
+
+ $transients = array(
+ 'api_up' => 'imagify_check_api_version',
+ 'api_key_valid' => 'imagify_check_licence_1',
+ );
+
+ if ( isset( $transients[ $cache_key ] ) && get_site_transient( $transients[ $cache_key ] ) ) {
+ delete_site_transient( $transients[ $cache_key ] );
+ }
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/inc/classes/class-imagify-settings.php b/wp/wp-content/plugins/imagify/inc/classes/class-imagify-settings.php
new file mode 100644
index 00000000..abfca2df
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/classes/class-imagify-settings.php
@@ -0,0 +1,994 @@
+options = Imagify_Options::get_instance();
+ $this->option_name = $this->options->get_option_name();
+ $this->settings_group = IMAGIFY_SLUG;
+ }
+
+ /**
+ * Get the main Instance.
+ *
+ * @since 1.7
+ * @return object Main instance.
+ */
+ public static function get_instance() {
+ if ( ! isset( self::$_instance ) ) {
+ self::$_instance = new self();
+ }
+
+ return self::$_instance;
+ }
+
+ /**
+ * Launch the hooks.
+ *
+ * @since 1.7
+ */
+ public function init() {
+ add_filter( 'sanitize_option_' . $this->option_name, [ $this, 'populate_values_on_save' ], 5 );
+ add_action( 'admin_init', [ $this, 'register' ] );
+ add_filter( 'option_page_capability_' . $this->settings_group, [ $this, 'get_capability' ] );
+
+ if ( imagify_is_active_for_network() ) {
+ add_filter( 'pre_update_site_option_' . $this->option_name, [
+ $this,
+ 'maybe_set_redirection',
+ ], 10, 2 );
+ add_action( 'update_site_option_' . $this->option_name, [
+ $this,
+ 'after_save_network_options',
+ ], 10, 3 );
+ add_action( 'admin_post_update', [ $this, 'update_site_option_on_network' ] );
+ } else {
+ add_filter( 'pre_update_option_' . $this->option_name, [ $this, 'maybe_set_redirection' ], 10, 2 );
+ add_action( 'update_option_' . $this->option_name, [ $this, 'after_save_options' ], 10, 2 );
+ }
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** VARIOUS HELPERS ========================================================================= */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Get the name of the settings group.
+ *
+ * @since 1.7
+ * @return string
+ */
+ public function get_settings_group() {
+ return $this->settings_group;
+ }
+
+ /**
+ * Get the URL to use as form action.
+ *
+ * @since 1.7
+ * @return string
+ */
+ public function get_form_action() {
+ return imagify_is_active_for_network() ? admin_url( 'admin-post.php' ) : admin_url( 'options.php' );
+ }
+
+ /**
+ * Tell if we're submitting the settings form.
+ *
+ * @since 1.7
+ * @return bool
+ */
+ public function is_form_submit() {
+ if ( ! isset( $_POST['option_page'], $_POST['action'] ) ) { // phpcs:ignore WordPress.Security.NonceVerification.Missing
+ return false;
+ }
+
+ return htmlspecialchars( wp_unslash( $_POST['option_page'] ) ) === $this->settings_group && htmlspecialchars( wp_unslash( $_POST['action'] ) ) === 'update'; // phpcs:ignore WordPress.Security.NonceVerification.Missing
+ }
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** ON FORM SUBMIT ========================================================================== */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * On form submit, handle some specific values.
+ * This must be hooked before Imagify_Options::sanitize_and_validate_on_update().
+ *
+ * @since 1.7
+ *
+ * @param array $values The option values.
+ *
+ * @return array
+ */
+ public function populate_values_on_save( $values ) {
+ if ( ! $this->is_form_submit() ) {
+ return $values;
+ }
+
+ $values = is_array( $values ) ? $values : [];
+
+ /**
+ * Disabled thumbnail sizes.
+ */
+ $values = $this->populate_disallowed_sizes( $values );
+
+ /**
+ * Custom folders.
+ */
+ $values = $this->populate_custom_folders( $values );
+
+ /**
+ * Filter settings when saved via the settings page.
+ *
+ * @since 1.9
+ *
+ * @param array $values The option values.
+ */
+ $values = apply_filters( 'imagify_settings_on_save', $values );
+
+ return (array) $values;
+ }
+
+ /**
+ * On form submit, handle disallowed thumbnail sizes.
+ *
+ * @since 1.7
+ *
+ * @param array $values The option values.
+ *
+ * @return array
+ */
+ protected function populate_disallowed_sizes( $values ) {
+ $values['disallowed-sizes'] = [];
+
+ if ( isset( $values['disallowed-sizes-reversed'] ) && is_array( $values['disallowed-sizes-reversed'] ) ) {
+ $checked = ! empty( $values['disallowed-sizes-checked'] ) && is_array( $values['disallowed-sizes-checked'] ) ? array_flip( $values['disallowed-sizes-checked'] ) : [];
+
+ if ( ! empty( $values['disallowed-sizes-reversed'] ) ) {
+ foreach ( $values['disallowed-sizes-reversed'] as $size_key ) {
+ if ( ! isset( $checked[ $size_key ] ) ) {
+ // The checkbox is not checked: the size is disabled.
+ $values['disallowed-sizes'][ $size_key ] = 1;
+ }
+ }
+ }
+ }
+
+ unset( $values['disallowed-sizes-reversed'], $values['disallowed-sizes-checked'] );
+
+ return $values;
+ }
+
+ /**
+ * On form submit, handle the custom folders.
+ *
+ * @since 1.7
+ *
+ * @param array $values The option values.
+ *
+ * @return array
+ */
+ protected function populate_custom_folders( $values ) {
+ if ( ! imagify_can_optimize_custom_folders() ) {
+ // The databases are not ready or the user has not the permission.
+ unset( $values['custom_folders'] );
+
+ return $values;
+ }
+
+ if ( ! isset( $values['custom_folders'] ) ) {
+ // No selected folders: set them all inactive.
+ Imagify_Custom_Folders::deactivate_all_folders();
+ // Remove files that are in inactive folders and are not optimized.
+ Imagify_Custom_Folders::remove_unoptimized_files_from_inactive_folders();
+ // Remove empty inactive folders.
+ Imagify_Custom_Folders::remove_empty_inactive_folders();
+
+ return $values;
+ }
+
+ if ( ! is_array( $values['custom_folders'] ) ) {
+ // Invalid value.
+ unset( $values['custom_folders'] );
+
+ return $values;
+ }
+
+ $selected = array_filter( $values['custom_folders'] );
+ unset( $values['custom_folders'] );
+
+ if ( ! $selected ) {
+ // No selected folders: set them all inactive.
+ Imagify_Custom_Folders::deactivate_all_folders();
+ // Remove files that are in inactive folders and are not optimized.
+ Imagify_Custom_Folders::remove_unoptimized_files_from_inactive_folders();
+ // Remove empty inactive folders.
+ Imagify_Custom_Folders::remove_empty_inactive_folders();
+
+ return $values;
+ }
+
+ // Normalize the paths, remove duplicates, and remove sub-paths.
+ $selected = array_map( 'sanitize_text_field', $selected );
+ $selected = array_map( 'wp_normalize_path', $selected );
+ $selected = array_map( 'trailingslashit', $selected );
+ $selected = array_flip( array_flip( $selected ) );
+ $selected = Imagify_Custom_Folders::remove_sub_paths( $selected );
+
+ // Remove the active status from the folders that are not selected.
+ Imagify_Custom_Folders::deactivate_not_selected_folders( $selected );
+
+ // Add the active status to the folders that are selected (and already in the DB).
+ $selected = Imagify_Custom_Folders::activate_selected_folders( $selected );
+
+ // If we still have paths here, they need to be added to the DB with an active status.
+ Imagify_Custom_Folders::insert_folders( $selected );
+
+ // Remove files that are in inactive folders and are not optimized.
+ Imagify_Custom_Folders::remove_unoptimized_files_from_inactive_folders();
+
+ // Reassign files to active folders.
+ Imagify_Custom_Folders::reassign_inactive_files();
+
+ // Remove empty inactive folders.
+ Imagify_Custom_Folders::remove_empty_inactive_folders();
+
+ return $values;
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** SETTINGS API ============================================================================ */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Add Imagify' settings to the settings API whitelist.
+ *
+ * @since 1.7
+ */
+ public function register() {
+ register_setting( $this->settings_group, $this->option_name );
+ }
+
+ /**
+ * Set the user capacity needed to save Imagify's main options from the settings page.
+ *
+ * @since 1.7
+ */
+ public function get_capability() {
+ return imagify_get_context( 'wp' )->get_capacity( 'manage' );
+ }
+
+ /**
+ * If the user clicked the "Save & Go to Bulk Optimizer" button, set a redirection to the bulk optimizer.
+ * We use this hook because it can be triggered even if the option value hasn't changed.
+ *
+ * @since 1.7
+ *
+ * @param mixed $value The new, unserialized option value.
+ * @param mixed $old_value The old option value.
+ *
+ * @return mixed The option value.
+ */
+ public function maybe_set_redirection( $value, $old_value ) {
+ if ( isset( $_POST['submit-goto-bulk'] ) ) { // WPCS: CSRF ok.
+ $_REQUEST['_wp_http_referer'] = esc_url_raw( get_admin_url( get_current_blog_id(), 'upload.php?page=imagify-bulk-optimization' ) );
+ }
+
+ return $value;
+ }
+
+ /**
+ * Used to launch some actions after saving the network options.
+ *
+ * @since 1.7
+ *
+ * @param string $option Name of the network option.
+ * @param mixed $value Current value of the network option.
+ * @param mixed $old_value Old value of the network option.
+ */
+ public function after_save_network_options( $option, $value, $old_value ) {
+ $this->after_save_options( $old_value, $value );
+ }
+
+ /**
+ * Used to launch some actions after saving the options.
+ *
+ * @since 1.7
+ *
+ * @param mixed $old_value The old option value.
+ * @param mixed $value The new option value.
+ */
+ public function after_save_options( $old_value, $value ) {
+ $old_key = isset( $old_value['api_key'] ) ? $old_value['api_key'] : '';
+ $new_key = isset( $value['api_key'] ) ? $value['api_key'] : '';
+
+ if ( $old_key === $new_key ) {
+ return;
+ }
+
+ // Handle API key validation cache and notices.
+ if ( Imagify_Requirements::is_api_key_valid( true ) ) {
+ Notices::dismiss_notice( 'wrong-api-key' );
+ } else {
+ Notices::renew_notice( 'wrong-api-key' );
+ }
+ }
+
+ /**
+ * `options.php` does not handle network options. Let's use `admin-post.php` for multisite installations.
+ *
+ * @since 1.9.11 deprecate 'whitelist_options' filter.
+ * @since 1.7
+ *
+ * @return void
+ */
+ public function update_site_option_on_network() {
+ global $wp_version;
+
+ if ( empty( $_POST['option_page'] ) || $_POST['option_page'] !== $this->settings_group ) { // WPCS: CSRF ok.
+ return;
+ }
+
+ /** This filter is documented in /wp-admin/options.php. */
+ $capability = apply_filters( 'option_page_capability_' . $this->settings_group, 'manage_network_options' );
+
+ if ( ! current_user_can( $capability ) ) {
+ imagify_die();
+
+ return;
+ }
+
+ if ( ! imagify_check_nonce( $this->settings_group . '-options' ) ) {
+ return;
+ }
+
+ if ( version_compare( $wp_version, '5.5', '>=' ) ) {
+ $allowed_options = apply_filters_deprecated(
+ 'whitelist_options',
+ [ [] ],
+ '5.5.0',
+ 'allowed_options',
+ __( 'Please consider writing more inclusive code.' )
+ );
+ } else {
+ $allowed_options = apply_filters( 'whitelist_options', [] );
+ }
+
+ $allowed_options = apply_filters( 'allowed_options', $allowed_options );
+
+ if ( ! isset( $allowed_options[ $this->settings_group ] ) ) {
+ imagify_die( __( 'ERROR : options page not found.' ) );
+
+ return;
+ }
+
+ $options = $allowed_options[ $this->settings_group ];
+
+ if ( $options ) {
+ foreach ( $options as $option ) {
+ $option = trim( $option );
+ $value = null;
+
+ if ( isset( $_POST[ $option ] ) ) {
+ $value = wp_unslash( $_POST[ $option ] );
+ if ( ! is_array( $value ) ) {
+ $value = trim( $value );
+ }
+ $value = wp_unslash( $value );
+ }
+
+ update_site_option( $option, $value );
+ }
+ }
+
+ /**
+ * Redirect back to the settings page that was submitted.
+ */
+ imagify_maybe_redirect( false, [ 'settings-updated' => 'true' ] );
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** FIELDS ================================================================================== */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Display a single checkbox.
+ *
+ * @since 1.7
+ *
+ * @param array $args Arguments:
+ * {option_name} string The option name. E.g. 'disallowed-sizes'. Mandatory.
+ * {label} string The label to use.
+ * {info} string Text to display in an "Info box" after the field. A 'aria-describedby' attribute will automatically be created.
+ * {attributes} array A list of HTML attributes, as 'attribute' => 'value'.
+ * {current_value} int|bool USE ONLY WHEN DEALING WITH DATA THAT IS NOT SAVED IN THE PLUGIN OPTIONS. If not provided, the field will automatically get the value from the options.
+ */
+ public function field_checkbox( $args ) {
+ $args = array_merge( [
+ 'option_name' => '',
+ 'label' => '',
+ 'info' => '',
+ 'attributes' => [],
+ // To not use the plugin settings: use an integer.
+ 'current_value' => null,
+ ], $args );
+
+ if ( ! $args['option_name'] || ! $args['label'] ) {
+ return;
+ }
+
+ if ( is_numeric( $args['current_value'] ) || is_bool( $args['current_value'] ) ) {
+ // We don't use the plugin settings.
+ $current_value = (int) (bool) $args['current_value'];
+ } else {
+ // This is a normal plugin setting.
+ $current_value = $this->options->get( $args['option_name'] );
+ }
+
+ $option_name_class = sanitize_html_class( $args['option_name'] );
+ $attributes = [
+ 'name' => $this->option_name . '[' . $args['option_name'] . ']',
+ 'id' => 'imagify_' . $option_name_class,
+ ];
+
+ if ( $args['info'] && empty( $attributes['aria-describedby'] ) ) {
+ $attributes['aria-describedby'] = 'describe-' . $option_name_class;
+ }
+
+ $attributes = array_merge( $attributes, $args['attributes'] );
+ $args['attributes'] = self::build_attributes( $attributes );
+ ?>
+ />
+
+
+
+
+
+
+
+ tag.
+ * {values} array List of values to display, in the form of 'value' => 'Label'. Mandatory.
+ * {disabled_values} array Values to be disabled. Values are the array keys.
+ * {reverse_check} bool If true, the values that will be stored in the option are the ones that are unchecked. It requires special treatment when saving (detect what values are unchecked).
+ * {attributes} array A list of HTML attributes, as 'attribute' => 'value'.
+ * {current_values} array USE ONLY WHEN DEALING WITH DATA THAT IS NOT SAVED IN THE PLUGIN OPTIONS. If not provided, the field will automatically get the value from the options.
+ */
+ public function field_checkbox_list( $args ) {
+ $args = array_merge( [
+ 'option_name' => '',
+ 'legend' => '',
+ 'values' => [],
+ 'disabled_values' => [],
+ 'reverse_check' => false,
+ 'attributes' => [],
+ // To not use the plugin settings: use an array.
+ 'current_values' => false,
+ ], $args );
+
+ if ( ! $args['option_name'] || ! $args['values'] ) {
+ return;
+ }
+
+ if ( is_array( $args['current_values'] ) ) {
+ // We don't use the plugin settings.
+ $current_values = $args['current_values'];
+ } else {
+ // This is a normal plugin setting.
+ $current_values = $this->options->get( $args['option_name'] );
+ }
+
+ $option_name_class = sanitize_html_class( $args['option_name'] );
+ $attributes = array_merge( [
+ 'name' => $this->option_name . '[' . $args['option_name'] . ( $args['reverse_check'] ? '-checked' : '' ) . '][]',
+ 'id' => 'imagify_' . $option_name_class . '_%s',
+ 'class' => 'imagify-row-check',
+ ], $args['attributes'] );
+
+ $id_attribute = $attributes['id'];
+ unset( $attributes['id'] );
+ $args['attributes'] = self::build_attributes( $attributes );
+
+ $current_values = array_diff_key( $current_values, $args['disabled_values'] );
+ $nb_of_values = count( $args['values'] );
+ $display_check_all = $nb_of_values > 3;
+ $nb_of_checked = 0;
+ ?>
+
+
+
+ $label ) {
+ $input_id = sprintf( $id_attribute, sanitize_html_class( $value ) );
+ $disabled = isset( $args['disabled_values'][ $value ] );
+
+ if ( $args['reverse_check'] ) {
+ $checked = ! $disabled && ! isset( $current_values[ $value ] );
+ } else {
+ $checked = ! $disabled && isset( $current_values[ $value ] );
+ }
+
+ $nb_of_checked = $checked ? $nb_of_checked + 1 : $nb_of_checked;
+
+ if ( $args['reverse_check'] ) {
+ echo ' ';
+ }
+ ?>
+
+ />
+
+
+
+
+
+
+
+
+
+
+
+
+ tag.
+ * @type string $info Text to display in an "Info box" after the field. A 'aria-describedby' attribute will automatically be created.
+ * @type array $values List of values to display, in the form of 'value' => 'Label'. Mandatory.
+ * @type array $attributes A list of HTML attributes, as 'attribute' => 'value'.
+ * @type array $current_value USE ONLY WHEN DEALING WITH DATA THAT IS NOT SAVED IN THE PLUGIN OPTIONS. If not provided, the field will automatically get the value from the options.
+ * }
+ */
+ public function field_radio_list( $args ) {
+ $args = array_merge( [
+ 'option_name' => '',
+ 'legend' => '',
+ 'info' => '',
+ 'values' => [],
+ 'attributes' => [],
+ // To not use the plugin settings: use an array.
+ 'current_value' => false,
+ ], $args );
+
+ if ( ! $args['option_name'] || ! $args['values'] ) {
+ return;
+ }
+
+ if ( is_array( $args['current_value'] ) ) {
+ // We don't use the plugin settings.
+ $current_value = $args['current_value'];
+ } else {
+ // This is a normal plugin setting.
+ $current_value = $this->options->get( $args['option_name'] );
+ }
+
+ $option_name_class = sanitize_html_class( $args['option_name'] );
+ $attributes = array_merge( [
+ 'name' => $this->option_name . '[' . $args['option_name'] . ']',
+ 'id' => 'imagify_' . $option_name_class . '_%s',
+ 'class' => 'imagify-row-radio',
+ ], $args['attributes'] );
+
+ $id_attribute = $attributes['id'];
+ unset( $attributes['id'] );
+ $args['attributes'] = self::build_attributes( $attributes );
+ ?>
+
+
+
+ $label ) {
+ $input_id = sprintf( $id_attribute, sanitize_html_class( $value ) );
+ ?>
+ />
+
+
+
+
+
+
+
+
+
+ 'Label'. Mandatory.
+ * {attributes} array A list of HTML attributes, as 'attribute' => 'value'.
+ * {current_value} int|bool USE ONLY WHEN DEALING WITH DATA THAT IS NOT SAVED IN THE PLUGIN OPTIONS. If not provided, the field will automatically get the value from the options.
+ *
+ * @return void
+ */
+ public function field_inline_radio_list( $args ) {
+ $args = array_merge(
+ [
+ 'option_name' => '',
+ 'values' => [],
+ 'info' => '',
+ 'attributes' => [],
+ 'current_value' => false,
+ ],
+ $args
+ );
+
+ if ( ! $args['option_name'] || ! $args['values'] ) {
+ return;
+ }
+
+ if ( is_numeric( $args['current_value'] ) || is_string( $args['current_value'] ) ) {
+ $current_value = $args['current_value'];
+ } else {
+ $current_value = $this->options->get( $args['option_name'] );
+ }
+
+ $option_name_class = sanitize_html_class( $args['option_name'] );
+ $attributes = array_merge( [
+ 'name' => $this->option_name . '[' . $args['option_name'] . ']',
+ 'id' => 'imagify_' . $option_name_class . '_%s',
+ 'class' => 'imagify-row-radio',
+ ], $args['attributes'] );
+
+ $id_attribute = $attributes['id'];
+ unset( $attributes['id'] );
+ $args['attributes'] = self::build_attributes( $attributes );
+ ?>
+
+
+ $label ) {
+ $input_id = sprintf( $id_attribute, sanitize_html_class( $value ) );
+ ?>
+ />
+
+
+
+
+
+
+
+
+ 'value'.
+ * {current_value} int|bool USE ONLY WHEN DEALING WITH DATA THAT IS NOT SAVED IN THE PLUGIN OPTIONS. If not provided, the field will automatically get the value from the options.
+ */
+ public function field_text_box( $args ) {
+ $args = array_merge( [
+ 'option_name' => '',
+ 'label' => '',
+ 'info' => '',
+ 'attributes' => [],
+ // To not use the plugin settings.
+ 'current_value' => null,
+ ], $args );
+
+ if ( ! $args['option_name'] || ! $args['label'] ) {
+ return;
+ }
+
+ if ( is_numeric( $args['current_value'] ) || is_string( $args['current_value'] ) ) {
+ // We don't use the plugin settings.
+ $current_value = $args['current_value'];
+ } else {
+ // This is a normal plugin setting.
+ $current_value = $this->options->get( $args['option_name'] );
+ }
+
+ $option_name_class = sanitize_html_class( $args['option_name'] );
+ $attributes = [
+ 'name' => $this->option_name . '[' . $args['option_name'] . ']',
+ 'id' => 'imagify_' . $option_name_class,
+ ];
+
+ if ( $args['info'] && empty( $attributes['aria-describedby'] ) ) {
+ $attributes['aria-describedby'] = 'describe-' . $option_name_class;
+ }
+
+ $attributes = array_merge( $attributes, $args['attributes'] );
+ $args['attributes'] = self::build_attributes( $attributes );
+ ?>
+
+
+ />
+
+
+
+
+
+ 'value'.
+ * {current_value} int|bool USE ONLY WHEN DEALING WITH DATA THAT IS NOT SAVED IN THE PLUGIN OPTIONS. If not provided, the field will automatically get the value from the options.
+ */
+ public function field_hidden( $args ) {
+ $args = array_merge( [
+ 'option_name' => '',
+ 'attributes' => [],
+ // To not use the plugin settings.
+ 'current_value' => null,
+ ], $args );
+
+ if ( ! $args['option_name'] ) {
+ return;
+ }
+
+ if ( is_numeric( $args['current_value'] ) || is_string( $args['current_value'] ) ) {
+ // We don't use the plugin settings.
+ $current_value = $args['current_value'];
+ } else {
+ // This is a normal plugin setting.
+ $current_value = $this->options->get( $args['option_name'] );
+ }
+
+ $option_name_class = sanitize_html_class( $args['option_name'] );
+ $attributes = [
+ 'name' => $this->option_name . '[' . $args['option_name'] . ']',
+ 'id' => 'imagify_' . $option_name_class,
+ ];
+
+ $attributes = array_merge( $attributes, $args['attributes'] );
+ $args['attributes'] = self::build_attributes( $attributes );
+ ?>
+ />
+ 'medium - 300 Ă— 300'.
+ */
+ public static function get_thumbnail_sizes() {
+ static $sizes;
+
+ if ( isset( $sizes ) ) {
+ return $sizes;
+ }
+
+ $sizes = get_imagify_thumbnail_sizes();
+
+ foreach ( $sizes as $size_key => $size_data ) {
+ $sizes[ $size_key ] = sprintf( '%s - %d × %d', esc_html( stripslashes( $size_data['name'] ) ), $size_data['width'], $size_data['height'] );
+ }
+
+ return $sizes;
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** TOOLS =================================================================================== */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Create HTML attributes from an array.
+ *
+ * @since 1.7
+ *
+ * @param array $attributes A list of attribute pairs.
+ *
+ * @return string HTML attributes.
+ */
+ public static function build_attributes( $attributes ) {
+ if ( ! $attributes || ! is_array( $attributes ) ) {
+ return '';
+ }
+
+ $out = '';
+
+ foreach ( $attributes as $attribute => $value ) {
+ $out .= ' ' . $attribute . '="' . esc_attr( $value ) . '"';
+ }
+
+ return $out;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/inc/classes/class-imagify-views.php b/wp/wp-content/plugins/imagify/inc/classes/class-imagify-views.php
new file mode 100644
index 00000000..72664102
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/classes/class-imagify-views.php
@@ -0,0 +1,684 @@
+slug_settings = IMAGIFY_SLUG;
+ $this->slug_bulk = IMAGIFY_SLUG . '-bulk-optimization';
+ $this->slug_files = IMAGIFY_SLUG . '-files';
+ $this->filesystem = Imagify_Filesystem::get_instance();
+ }
+
+ /**
+ * Get the main Instance.
+ *
+ * @since 1.7
+ *
+ * @return object Main instance.
+ */
+ public static function get_instance() {
+ if ( ! isset( self::$_instance ) ) {
+ self::$_instance = new self();
+ }
+
+ return self::$_instance;
+ }
+
+ /**
+ * Launch the hooks.
+ *
+ * @since 1.7
+ */
+ public function init() {
+ // Menu items.
+ add_action( 'admin_menu', [ $this, 'add_site_menus' ] );
+
+ if ( imagify_is_active_for_network() ) {
+ add_action( 'network_admin_menu', [ $this, 'add_network_menus' ] );
+ }
+
+ // Action links in plugins list.
+ $basename = plugin_basename( IMAGIFY_FILE );
+ add_filter( 'plugin_action_links_' . $basename, [ $this, 'plugin_action_links' ] );
+ add_filter( 'network_admin_plugin_action_links_' . $basename, [ $this, 'plugin_action_links' ] );
+
+ // Save the "per page" option value from the files list screen.
+ add_filter( 'set-screen-option', [ 'Imagify_Files_List_Table', 'save_screen_options' ], 10, 3 );
+
+ // JS templates in footer.
+ add_action( 'admin_print_footer_scripts', [ $this, 'print_js_templates' ] );
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** MENU ITEMS ============================================================================== */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Add sub-menus for all sites.
+ *
+ * @since 1.7
+ */
+ public function add_site_menus() {
+ $wp_context = imagify_get_context( 'wp' );
+
+ // Sub-menu item: bulk optimization.
+ add_media_page( __( 'Bulk Optimization', 'imagify' ), __( 'Bulk Optimization', 'imagify' ), $wp_context->get_capacity( 'bulk-optimize' ), $this->get_bulk_page_slug(), [ $this, 'display_bulk_page' ] );
+
+ if ( imagify_is_active_for_network() ) {
+ return;
+ }
+
+ /**
+ * Plugin is not network activated.
+ */
+ if ( imagify_can_optimize_custom_folders() ) {
+ // Sub-menu item: custom folders list.
+ $cf_context = imagify_get_context( 'custom-folders' );
+ $screen_id = add_media_page( __( 'Other Media optimized by Imagify', 'imagify' ), __( 'Other Media', 'imagify' ), $cf_context->get_capacity( 'optimize' ), $this->get_files_page_slug(), [ $this, 'display_files_list' ] );
+
+ if ( $screen_id ) {
+ // Load the data for this page.
+ add_action( 'load-' . $screen_id, [ $this, 'load_files_list' ] );
+ }
+ }
+
+ // Sub-menu item: settings.
+ add_options_page( 'Imagify', 'Imagify', $wp_context->get_capacity( 'manage' ), $this->get_settings_page_slug(), [ $this, 'display_settings_page' ] );
+ }
+
+ /**
+ * Add menu and sub-menus in the network admin when Imagify is network-activated.
+ *
+ * @since 1.7
+ */
+ public function add_network_menus() {
+ global $submenu;
+
+ $wp_context = imagify_get_context( 'wp' );
+
+ if ( ! imagify_can_optimize_custom_folders() ) {
+ // Main item: settings (edge case).
+ add_menu_page( 'Imagify', 'Imagify', $wp_context->get_capacity( 'manage' ), $this->get_settings_page_slug(), array( $this, 'display_settings_page' ) );
+ return;
+ }
+
+ $cf_context = imagify_get_context( 'custom-folders' );
+
+ // Main item: bulk optimization (custom folders).
+ add_menu_page( __( 'Bulk Optimization', 'imagify' ), 'Imagify', $cf_context->current_user_can( 'bulk-optimize' ), $this->get_bulk_page_slug(), array( $this, 'display_bulk_page' ) );
+
+ // Sub-menu item: custom folders list.
+ $screen_id = add_submenu_page( $this->get_bulk_page_slug(), __( 'Other Media optimized by Imagify', 'imagify' ), __( 'Other Media', 'imagify' ), $cf_context->current_user_can( 'bulk-optimize' ), $this->get_files_page_slug(), array( $this, 'display_files_list' ) );
+
+ // Sub-menu item: settings.
+ add_submenu_page( $this->get_bulk_page_slug(), 'Imagify', __( 'Settings', 'imagify' ), $wp_context->get_capacity( 'manage' ), $this->get_settings_page_slug(), array( $this, 'display_settings_page' ) );
+
+ // Change the sub-menu label.
+ if ( ! empty( $submenu[ $this->get_bulk_page_slug() ] ) ) {
+ $submenu[ $this->get_bulk_page_slug() ][0][0] = __( 'Bulk Optimization', 'imagify' ); // WPCS: override ok.
+ }
+
+ if ( $screen_id ) {
+ // On the "Other Media optimized by Imagify" page, load the data.
+ add_action( 'load-' . $screen_id, array( $this, 'load_files_list' ) );
+ }
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** PLUGIN ACTION LINKS ===================================================================== */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Add links to the plugin row in the plugins list.
+ *
+ * @since 1.7
+ *
+ * @param array $actions An array of action links.
+ * @return array
+ */
+ public function plugin_action_links( $actions ) {
+ array_unshift( $actions, sprintf( '%s ', esc_url( imagify_get_external_url( 'documentation' ) ), __( 'Documentation', 'imagify' ) ) );
+ array_unshift( $actions, sprintf( '%s ', esc_url( get_imagify_admin_url( 'bulk-optimization' ) ), __( 'Bulk Optimization', 'imagify' ) ) );
+ array_unshift( $actions, sprintf( '%s ', esc_url( get_imagify_admin_url() ), __( 'Settings', 'imagify' ) ) );
+ return $actions;
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** MAIN PAGE TEMPLATES ===================================================================== */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * The main settings page.
+ *
+ * @since 1.7
+ */
+ public function display_settings_page() {
+ $this->print_template( 'page-settings' );
+ }
+
+ /**
+ * The bulk optimization page.
+ *
+ * @since 1.7
+ */
+ public function display_bulk_page() {
+ $types = array();
+ $data = array(
+ // Limits.
+ 'unoptimized_attachment_limit' => 0,
+ // What to optimize.
+ 'icon' => 'images-alt2',
+ 'title' => __( 'Optimize your media files', 'imagify' ),
+ 'groups' => array(),
+ );
+
+ if ( imagify_is_screen( 'bulk' ) ) {
+ if ( ! is_network_admin() ) {
+ /**
+ * Library: in each site.
+ */
+ $types['library|wp'] = 1;
+ }
+
+ if ( imagify_can_optimize_custom_folders() && ( imagify_is_active_for_network() && is_network_admin() || ! imagify_is_active_for_network() ) ) {
+ /**
+ * Custom folders: in network admin only if network activated, in each site otherwise.
+ */
+ $types['custom-folders|custom-folders'] = 1;
+ }
+ }
+
+ /**
+ * Filter the types to display in the bulk optimization page.
+ *
+ * @since 1.7.1
+ * @author Grégory Viguier
+ *
+ * @param array $types The folder types displayed on the page. If a folder type is "library", the context should be suffixed after a pipe character. They are passed as array keys.
+ */
+ $types = apply_filters( 'imagify_bulk_page_types', $types );
+ $types = array_filter( (array) $types );
+
+ if ( isset( $types['library|wp'] ) ) {
+ // Limits.
+ $data['unoptimized_attachment_limit'] += imagify_get_unoptimized_attachment_limit();
+ // Group.
+ $data['groups']['library'] = array(
+ /**
+ * The group_id corresponds to the file names like 'part-bulk-optimization-results-row-{$group_id}'.
+ * It is also used in get_imagify_localize_script_translations().
+ */
+ 'group_id' => 'library',
+ 'context' => 'wp',
+ 'title' => __( 'Media Library', 'imagify' ),
+ /* translators: 1 is the opening of a link, 2 is the closing of this link. */
+ 'footer' => sprintf( __( 'You can also re-optimize your media files from your %1$sMedia Library%2$s screen.', 'imagify' ), '', ' ' ),
+ );
+ }
+
+ if ( isset( $types['custom-folders|custom-folders'] ) ) {
+ if ( ! Imagify_Folders_DB::get_instance()->has_items() ) {
+ // New Feature!
+ $data['no-custom-folders'] = true;
+ } elseif ( Imagify_Folders_DB::get_instance()->has_active_folders() ) {
+ // Group.
+ $data['groups']['custom-folders'] = array(
+ 'group_id' => 'custom-folders',
+ 'context' => 'custom-folders',
+ 'title' => __( 'Custom folders', 'imagify' ),
+ /* translators: 1 is the opening of a link, 2 is the closing of this link. */
+ 'footer' => sprintf( __( 'You can re-optimize your media files more finely directly in the %1$smedia management%2$s.', 'imagify' ), '', ' ' ),
+ );
+ }
+ }
+
+ // Add generic stats.
+ $data = array_merge( $data, imagify_get_bulk_stats( $types, array(
+ 'fullset' => true,
+ ) ) );
+
+ /**
+ * Filter the data to use on the bulk optimization page.
+ *
+ * @since 1.7
+ * @since 1.7.1 Added the $types parameter.
+ * @author Grégory Viguier
+ *
+ * @param array $data The data to use.
+ * @param array $types The folder types displayed on the page. They are passed as array keys.
+ */
+ $data = apply_filters( 'imagify_bulk_page_data', $data, $types );
+
+ $this->print_template( 'page-bulk', $data );
+ }
+
+ /**
+ * The page displaying the "custom folders" files.
+ *
+ * @since 1.7
+ */
+ public function display_files_list() {
+ $this->print_template( 'page-files-list' );
+ }
+
+ /**
+ * Initiate the "custom folders" list table data.
+ *
+ * @since 1.7
+ */
+ public function load_files_list() {
+ // Instantiate the list.
+ $this->list_table = new Imagify_Files_List_Table( array(
+ 'screen' => 'imagify-files',
+ ) );
+
+ // Query the Items.
+ $this->list_table->prepare_items();
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** GETTERS ================================================================================= */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Get the settings page slug.
+ *
+ * @since 1.7
+ *
+ * @return string
+ */
+ public function get_settings_page_slug() {
+ return $this->slug_settings;
+ }
+
+ /**
+ * Get the bulk optimization page slug.
+ *
+ * @since 1.7
+ *
+ * @return string
+ */
+ public function get_bulk_page_slug() {
+ return $this->slug_bulk;
+ }
+
+ /**
+ * Get the "custom folders" files page slug.
+ *
+ * @since 1.7
+ *
+ * @return string
+ */
+ public function get_files_page_slug() {
+ return $this->slug_files;
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** PAGE TESTS ============================================================================== */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Tell if we’re displaying the settings page.
+ *
+ * @since 1.9
+ *
+ * @return bool
+ */
+ public function is_settings_page() {
+ global $pagenow;
+
+ $page = htmlspecialchars( wp_unslash( $_GET['page'] ) ); // phpcs:ignore WordPress.Security.NonceVerification.Missing, WordPress.Security.NonceVerification.Recommended
+
+ if ( $this->get_settings_page_slug() !== $page ) {
+ return false;
+ }
+
+ if ( imagify_is_active_for_network() ) {
+ return 'admin.php' === $pagenow;
+ }
+
+ return 'options-general.php' === $pagenow;
+ }
+
+ /**
+ * Tell if we’re displaying the bulk optimization page.
+ *
+ * @since 1.9
+ *
+ * @return bool
+ */
+ public function is_bulk_page() {
+ global $pagenow;
+
+ $page = htmlspecialchars( wp_unslash( $_GET['page'] ) ); // phpcs:ignore WordPress.Security.NonceVerification.Missing, WordPress.Security.NonceVerification.Recommended
+
+ return 'upload.php' === $pagenow && $this->get_bulk_page_slug() === $page;
+ }
+
+ /**
+ * Tell if we’re displaying the custom files list page.
+ *
+ * @since 1.9
+ *
+ * @return bool
+ */
+ public function is_files_page() {
+ global $pagenow;
+
+ $page = htmlspecialchars( wp_unslash( $_GET['page'] ) ); // phpcs:ignore WordPress.Security.NonceVerification.Missing, WordPress.Security.NonceVerification.Recommended
+
+ return 'upload.php' === $pagenow && $this->get_files_page_slug() === $page;
+ }
+
+ /**
+ * Tell if we’re displaying the WP media library page.
+ *
+ * @since 1.9
+ *
+ * @return bool
+ */
+ public function is_wp_library_page() {
+ global $pagenow;
+
+ return 'upload.php' === $pagenow && ! isset( $_GET['page'] ); // phpcs:ignore WordPress.Security.NonceVerification.Recommended
+ }
+
+ /**
+ * Tell if we’re displaying a media page.
+ *
+ * @since 1.9
+ *
+ * @return bool
+ */
+ public function is_media_page() {
+ global $pagenow, $typenow;
+
+ return 'post.php' === $pagenow && 'attachment' === $typenow;
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** QUOTA =================================================================================== */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Get the remaining quota in percent.
+ *
+ * @since 1.8.1
+ *
+ * @return int
+ */
+ public function get_quota_percent() {
+ static $quota;
+
+ if ( isset( $quota ) ) {
+ return $quota;
+ }
+
+ $user = new User();
+ $quota = $user->get_percent_unconsumed_quota();
+
+ return $quota;
+ }
+
+ /**
+ * Get the HTML class used for the quota (to change the color when out of quota for example).
+ *
+ * @since 1.8.1
+ *
+ * @return string
+ */
+ public function get_quota_class() {
+ static $class;
+
+ if ( isset( $class ) ) {
+ return $class;
+ }
+
+ $quota = $this->get_quota_percent();
+ $class = 'imagify-bar-';
+
+ if ( $quota <= 20 ) {
+ $class .= 'negative';
+ } elseif ( $quota <= 50 ) {
+ $class .= 'neutral';
+ } else {
+ $class .= 'positive';
+ }
+
+ return $class;
+ }
+
+ /**
+ * Get the HTML tag used for the quota (the weather-like icon).
+ *
+ * @since 1.8.1
+ *
+ * @return string
+ */
+ public function get_quota_icon() {
+ static $icon;
+
+ if ( isset( $icon ) ) {
+ return $icon;
+ }
+
+ $quota = $this->get_quota_percent();
+
+ if ( $quota <= 20 ) {
+ $icon = ' ';
+ } elseif ( $quota <= 50 ) {
+ $icon = ' ';
+ } else {
+ $icon = ' ';
+ }
+
+ return $icon;
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** GENERIC TEMPLATE TOOLS ================================================================== */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Get a template contents.
+ *
+ * @since 1.7
+ *
+ * @param string $template The template name.
+ * @param mixed $data Some data to pass to the template.
+ * @return string|bool The page contents. False if the template doesn't exist.
+ */
+ public function get_template( $template, $data = array() ) {
+ $path = str_replace( '_', '-', $template );
+ $path = IMAGIFY_PATH . 'views/' . $template . '.php';
+
+ if ( ! $this->filesystem->exists( $path ) ) {
+ return false;
+ }
+
+ ob_start();
+ include $path;
+ $contents = ob_get_clean();
+
+ return trim( (string) $contents );
+ }
+
+ /**
+ * Print a template.
+ *
+ * @since 1.7
+ *
+ * @param string $template The template name.
+ * @param mixed $data Some data to pass to the template.
+ */
+ public function print_template( $template, $data = array() ) {
+ echo $this->get_template( $template, $data );
+ }
+
+ /**
+ * Add a template to the list of JS templates to print at the end of the page.
+ *
+ * @since 1.7
+ *
+ * @param string $template The template name.
+ */
+ public function print_js_template_in_footer( $template ) {
+ if ( isset( $this->templates_in_footer[ $template ] ) ) {
+ return;
+ }
+
+ if ( defined( 'DOING_AJAX' ) && DOING_AJAX ) {
+ return;
+ }
+
+ switch ( $template ) {
+ case 'button/processing':
+ $data = [ 'label' => '{{ data.label }}' ];
+ break;
+ default:
+ $data = [];
+ }
+
+ $this->templates_in_footer[ $template ] = $data;
+ }
+
+ /**
+ * Print the JS templates that have been added to the "queue".
+ *
+ * @since 1.9
+ */
+ public function print_js_templates() {
+ if ( ! $this->templates_in_footer ) {
+ return;
+ }
+
+ foreach ( $this->templates_in_footer as $template => $data ) {
+ $template_id = str_replace( [ '/', '_' ], '-', $template );
+
+ echo '';
+ }
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** TOOLS =================================================================================== */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Create HTML attributes from an array.
+ *
+ * @since 1.9
+ *
+ * @param array $attributes A list of attribute pairs.
+ * @return string HTML attributes.
+ */
+ public function build_attributes( $attributes ) {
+ if ( ! $attributes || ! is_array( $attributes ) ) {
+ return '';
+ }
+
+ $out = '';
+
+ foreach ( $attributes as $attribute => $value ) {
+ if ( '' === $value ) {
+ continue;
+ }
+
+ $out .= ' ' . $attribute . '="' . esc_attr( $value ) . '"';
+ }
+
+ return $out;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/inc/classes/class-imagify.php b/wp/wp-content/plugins/imagify/inc/classes/class-imagify.php
new file mode 100644
index 00000000..b7d7669d
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/classes/class-imagify.php
@@ -0,0 +1,657 @@
+api_key = get_imagify_option( 'api_key' );
+ $this->secure_key = $this->generate_secure_key();
+ $this->filesystem = Imagify_Filesystem::get_instance();
+
+ $this->all_headers['Accept'] = 'Accept: application/json';
+ $this->all_headers['Content-Type'] = 'Content-Type: application/json';
+ $this->all_headers['Authorization'] = 'Authorization: token ' . $this->api_key;
+ }
+
+ /**
+ * Get your Imagify account infos.
+ *
+ * @since 1.6.5
+ *
+ * @return object
+ */
+ public function get_user() {
+ global $wp_current_filter;
+
+ if ( isset( static::$user ) ) {
+ return static::$user;
+ }
+
+ if ( in_array( 'upgrader_post_install', (array) $wp_current_filter, true ) ) {
+ // Dirty patch used when updating from 1.7.
+ static::$user = new WP_Error();
+ return static::$user;
+ }
+
+ $this->headers = $this->all_headers;
+ static::$user = $this->http_call( 'users/me/', [ 'timeout' => 10 ] );
+
+ if ( is_wp_error( static::$user ) ) {
+ return static::$user;
+ }
+
+ $maybe_missing = [
+ 'account_type' => 'free',
+ 'quota' => 0,
+ 'extra_quota' => 0,
+ 'extra_quota_consumed' => 0,
+ 'consumed_current_month_quota' => 0,
+ ];
+
+ foreach ( $maybe_missing as $name => $value ) {
+ if ( ! isset( static::$user->$name ) ) {
+ static::$user->$name = $value;
+ }
+ }
+
+ return static::$user;
+ }
+
+ /**
+ * Create a user on your Imagify account.
+ *
+ * @since 1.6.5
+ *
+ * @param array $data All user data.
+ * @return object
+ */
+ public function create_user( $data ) {
+ $this->headers = [];
+ $data = array_merge(
+ $data,
+ [
+ 'from_plugin' => true,
+ 'partner' => imagify_get_partner(),
+ ]
+ );
+
+ if ( ! $data['partner'] ) {
+ unset( $data['partner'] );
+ }
+
+ $response = $this->http_call(
+ 'users/',
+ [
+ 'method' => 'POST',
+ 'post_data' => $data,
+ ]
+ );
+
+ if ( ! is_wp_error( $response ) ) {
+ imagify_delete_partner();
+ }
+
+ return $response;
+ }
+
+ /**
+ * Update an existing user on your Imagify account.
+ *
+ * @since 1.6.5
+ *
+ * @param string $data All user data.
+ * @return object
+ */
+ public function update_user( $data ) {
+ $this->headers = $this->all_headers;
+
+ return $this->http_call(
+ 'users/me/',
+ [
+ 'method' => 'PUT',
+ 'post_data' => $data,
+ 'timeout' => 10,
+ ]
+ );
+ }
+
+ /**
+ * Check your Imagify API key status.
+ *
+ * @since 1.6.5
+ *
+ * @param string $data The license key.
+ * @return object
+ */
+ public function get_status( $data ) {
+ static $status = [];
+
+ if ( isset( $status[ $data ] ) ) {
+ return $status[ $data ];
+ }
+
+ $this->headers = [
+ 'Authorization' => 'Authorization: token ' . $data,
+ ];
+
+ $uri = 'status/';
+ $partner = imagify_get_partner();
+
+ if ( $partner ) {
+ $uri .= '?partner=' . $partner;
+ }
+
+ $status[ $data ] = $this->http_call( $uri, [ 'timeout' => 10 ] );
+
+ return $status[ $data ];
+ }
+
+ /**
+ * Get the Imagify API version.
+ *
+ * @since 1.6.5
+ *
+ * @return object
+ */
+ public function get_api_version() {
+ static $api_version;
+
+ if ( ! isset( $api_version ) ) {
+ $this->headers = [
+ 'Authorization' => $this->all_headers['Authorization'],
+ ];
+
+ $api_version = $this->http_call( 'version/', [ 'timeout' => 5 ] );
+ }
+
+ return $api_version;
+ }
+
+ /**
+ * Get Public Info.
+ *
+ * @since 1.6.5
+ *
+ * @return object
+ */
+ public function get_public_info() {
+ $this->headers = $this->all_headers;
+
+ return $this->http_call( 'public-info' );
+ }
+
+ /**
+ * Optimize an image from its binary content.
+ *
+ * @since 1.6.5
+ * @since 1.6.7 $data['image'] can contain the file path (prefered) or the result of `curl_file_create()`.
+ *
+ * @param string $data All options.
+ * @return object
+ */
+ public function upload_image( $data ) {
+ $this->headers = [
+ 'Authorization' => $this->all_headers['Authorization'],
+ ];
+
+ return $this->http_call(
+ 'upload/',
+ [
+ 'method' => 'POST',
+ 'post_data' => $data,
+ ]
+ );
+ }
+
+ /**
+ * Optimize an image from its URL.
+ *
+ * @since 1.6.5
+ *
+ * @param string $data All options. Details here: --.
+ * @return object
+ */
+ public function fetch_image( $data ) {
+ $this->headers = $this->all_headers;
+
+ return $this->http_call(
+ 'fetch/',
+ [
+ 'method' => 'POST',
+ 'post_data' => wp_json_encode( $data ),
+ ]
+ );
+ }
+
+ /**
+ * Get prices for plans.
+ *
+ * @since 1.6.5
+ *
+ * @return object
+ */
+ public function get_plans_prices() {
+ $this->headers = $this->all_headers;
+
+ return $this->http_call( 'pricing/plan/' );
+ }
+
+ /**
+ * Get all prices (Plans included).
+ *
+ * @since 1.6.5
+ *
+ * @return object
+ */
+ public function get_all_prices() {
+ $this->headers = $this->all_headers;
+
+ return $this->http_call( 'pricing/all/' );
+ }
+
+ /**
+ * Get coupon code data.
+ *
+ * @since 1.6.5
+ *
+ * @param string $coupon A coupon code.
+ * @return object
+ */
+ public function check_coupon_code( $coupon ) {
+ $this->headers = $this->all_headers;
+
+ return $this->http_call( 'coupons/' . $coupon . '/' );
+ }
+
+ /**
+ * Get information about current discount.
+ *
+ * @since 1.6.5
+ *
+ * @return object
+ */
+ public function check_discount() {
+ $this->headers = $this->all_headers;
+
+ return $this->http_call( 'pricing/discount/' );
+ }
+
+ /**
+ * Make an HTTP call using curl.
+ *
+ * @since 1.6.5
+ * @since 1.6.7 Use `wp_remote_request()` when possible (when we don't need to send an image).
+ *
+ * @param string $url The URL to call.
+ * @param array $args The request args.
+ * @return object
+ */
+ private function http_call( $url, $args = [] ) {
+ $args = array_merge(
+ [
+ 'method' => 'GET',
+ 'post_data' => null,
+ 'timeout' => 45,
+ ],
+ $args
+ );
+
+ $endpoint = trim( $url, '/' );
+ /**
+ * Filter the timeout value for any request to the API.
+ *
+ * @since 1.6.7
+ * @author Grégory Viguier
+ *
+ * @param int $timeout Timeout value in seconds.
+ * @param string $endpoint The targetted endpoint. It's basically URI without heading nor trailing slash.
+ */
+ $args['timeout'] = apply_filters( 'imagify_api_http_request_timeout', $args['timeout'], $endpoint );
+
+ // We need to send an image: we must use cURL directly.
+ if ( isset( $args['post_data']['image'] ) ) {
+ return $this->curl_http_call( $url, $args );
+ }
+
+ $args = array_merge(
+ [
+ 'headers' => [],
+ 'body' => $args['post_data'],
+ 'sslverify' => apply_filters( 'https_ssl_verify', false ),
+ ],
+ $args
+ );
+
+ unset( $args['post_data'] );
+
+ if ( $this->headers ) {
+ foreach ( $this->headers as $name => $value ) {
+ $value = explode( ':', $value, 2 );
+ $value = end( $value );
+
+ $args['headers'][ $name ] = trim( $value );
+ }
+ }
+
+ if ( ! empty( $args['headers']['Authorization'] ) ) {
+ // Make sure our API has not overwritten by some other plugin.
+ $args[ $this->secure_key ] = preg_replace( '/^token /', '', $args['headers']['Authorization'] );
+
+ if ( ! has_filter( 'http_request_args', [ $this, 'force_api_key_header' ] ) ) {
+ add_filter( 'http_request_args', [ $this, 'force_api_key_header' ], IMAGIFY_INT_MAX + 25, 2 );
+ }
+ }
+
+ $response = wp_remote_request( self::API_ENDPOINT . $url, $args );
+
+ if ( is_wp_error( $response ) ) {
+ return $response;
+ }
+
+ $http_code = wp_remote_retrieve_response_code( $response );
+ $response = wp_remote_retrieve_body( $response );
+
+ return $this->handle_response( $response, $http_code );
+ }
+
+ /**
+ * Make an HTTP call using curl.
+ *
+ * @since 1.6.7
+ * @throws Exception When curl_init() fails.
+ * @author Grégory Viguier
+ *
+ * @param string $url The URL to call.
+ * @param array $args The request arguments.
+ * @return object
+ */
+ private function curl_http_call( $url, $args = [] ) {
+ // Check if curl is available.
+ if ( ! Imagify_Requirements::supports_curl() ) {
+ return new WP_Error( 'curl', 'cURL isn\'t installed on the server.' );
+ }
+
+ /**
+ * Allows to mock Imagify calls to the API.
+ *
+ * @param stdClass|null $response Response from the call.
+ * @param string $url URL from the call.
+ * @param array $args Arguments from the call.
+ */
+ $response = apply_filters( 'pre_imagify_request', null, $url, $args );
+
+ if ( $response ) {
+ return $response;
+ }
+
+ try {
+ $url = self::API_ENDPOINT . $url;
+ $ch = curl_init();
+
+ if ( false === $ch ) {
+ throw new Exception( 'Could not initialize a new cURL handle' );
+ }
+
+ if ( isset( $args['post_data']['image'] ) && is_string( $args['post_data']['image'] ) && $this->filesystem->exists( $args['post_data']['image'] ) ) {
+ $args['post_data']['image'] = curl_file_create( $args['post_data']['image'] );
+ }
+
+ // Handle proxies.
+ $proxy = new WP_HTTP_Proxy();
+
+ if ( $proxy->is_enabled() && $proxy->send_through_proxy( $url ) ) {
+ curl_setopt( $ch, CURLOPT_PROXYTYPE, CURLPROXY_HTTP );
+ curl_setopt( $ch, CURLOPT_PROXY, $proxy->host() );
+ curl_setopt( $ch, CURLOPT_PROXYPORT, $proxy->port() );
+
+ if ( $proxy->use_authentication() ) {
+ curl_setopt( $ch, CURLOPT_PROXYAUTH, CURLAUTH_ANY );
+ curl_setopt( $ch, CURLOPT_PROXYUSERPWD, $proxy->authentication() );
+ }
+ }
+
+ if ( 'POST' === $args['method'] ) {
+ curl_setopt( $ch, CURLOPT_POST, true );
+ curl_setopt( $ch, CURLOPT_POSTFIELDS, $args['post_data'] );
+ } elseif ( 'PUT' === $args['method'] ) {
+ curl_setopt( $ch, CURLOPT_CUSTOMREQUEST, 'PUT' );
+ curl_setopt( $ch, CURLOPT_POSTFIELDS, $args['post_data'] );
+ }
+
+ if ( defined( 'CURLOPT_PROTOCOLS' ) ) {
+ curl_setopt( $ch, CURLOPT_PROTOCOLS, CURLPROTO_HTTP | CURLPROTO_HTTPS );
+ }
+
+ $user_agent = apply_filters( 'http_headers_useragent', 'WordPress/' . get_bloginfo( 'version' ) . '; ' . get_bloginfo( 'url' ), $url );
+
+ curl_setopt( $ch, CURLOPT_URL, $url );
+ curl_setopt( $ch, CURLOPT_RETURNTRANSFER, true );
+ curl_setopt( $ch, CURLOPT_HEADER, false );
+ curl_setopt( $ch, CURLOPT_HTTPHEADER, $this->headers );
+ curl_setopt( $ch, CURLOPT_TIMEOUT, $args['timeout'] );
+ curl_setopt( $ch, CURLOPT_CONNECTTIMEOUT, $args['timeout'] );
+ curl_setopt( $ch, CURLOPT_USERAGENT, $user_agent );
+ @curl_setopt( $ch, CURLOPT_FOLLOWLOCATION, false );
+ curl_setopt( $ch, CURLOPT_SSL_VERIFYHOST, false );
+ curl_setopt( $ch, CURLOPT_SSL_VERIFYPEER, false );
+
+ /**
+ * Tell which http version to use with cURL during image optimization.
+ *
+ * @since 1.8.4.1
+ * @since 1.9.9 Default value is `false`.
+ * @author Grégory Viguier
+ *
+ * @param $use_version_1_0 bool True to use version 1.0. False for 1.1. Default is false.
+ */
+ if ( apply_filters( 'imagify_curl_http_version_1_0', false ) ) {
+ curl_setopt( $ch, CURLOPT_HTTP_VERSION, CURL_HTTP_VERSION_1_0 );
+ } else {
+ curl_setopt( $ch, CURLOPT_HTTP_VERSION, CURL_HTTP_VERSION_1_1 );
+ }
+
+ $response = curl_exec( $ch );
+ $error = curl_error( $ch );
+ $http_code = (int) curl_getinfo( $ch, CURLINFO_HTTP_CODE );
+
+ if ( is_resource( $ch ) ) {
+ curl_close( $ch );
+ } else {
+ unset( $ch );
+ }
+ } catch ( Exception $e ) {
+ $args['headers'] = $this->headers;
+ /**
+ * Fires after a failed curl request.
+ *
+ * @since 1.6.9
+ * @author Grégory Viguier
+ *
+ * @param string $url The requested URL.
+ * @param array $args The request arguments.
+ * @param object $e The raised Exception.
+ */
+ do_action( 'imagify_curl_http_response', $url, $args, $e );
+
+ return new WP_Error( 'curl', 'An error occurred (' . $e->getMessage() . ')' );
+ } // End try().
+
+ $args['headers'] = $this->headers;
+
+ /**
+ * Fires after a successful curl request.
+ *
+ * @since 1.6.9
+ * @author Grégory Viguier
+ *
+ * @param string $url The requested URL.
+ * @param array $args The request arguments.
+ * @param string $response The request response.
+ * @param int $http_code The request HTTP code.
+ * @param string $error An error message.
+ */
+ do_action( 'imagify_curl_http_response', $url, $args, $response, $http_code, $error );
+
+ return $this->handle_response( $response, $http_code, $error );
+ }
+
+ /**
+ * Handle the request response and maybe trigger an error.
+ *
+ * @since 1.6.7
+ * @author Grégory Viguier
+ *
+ * @param string $response The request response.
+ * @param int $http_code The request HTTP code.
+ * @param string $error An error message.
+ * @return object
+ */
+ private function handle_response( $response, $http_code, $error = '' ) {
+ $response = json_decode( $response );
+
+ if ( 401 === $http_code ) {
+ // Reset the API validity cache if the API key is not valid.
+ Imagify_Requirements::reset_cache( 'api_key_valid' );
+ }
+
+ if ( 200 !== $http_code && ! empty( $response->code ) ) {
+ if ( ! empty( $response->detail ) ) {
+ return new WP_Error( 'error ' . $http_code, $response->detail );
+ }
+ if ( ! empty( $response->image ) ) {
+ $error = (array) $response->image;
+ $error = reset( $error );
+ return new WP_Error( 'error ' . $http_code, $error );
+ }
+ }
+
+ if ( 413 === $http_code ) {
+ return new WP_Error( 'error ' . $http_code, 'Your image is too big to be uploaded on our server.' );
+ }
+
+ if ( 200 !== $http_code ) {
+ $error = trim( (string) $error );
+ $error = '' !== $error ? ' - ' . htmlentities( $error ) : '';
+ return new WP_Error( 'error ' . $http_code, "Our server returned an error ({$http_code}{$error})" );
+ }
+
+ if ( ! is_object( $response ) ) {
+ return new WP_Error( 'invalid response', 'Our server returned an invalid response.', $response );
+ }
+
+ return $response;
+ }
+
+ /**
+ * Generate a random key.
+ * Similar to wp_generate_password() but without filter.
+ *
+ * @since 1.8.4
+ * @see wp_generate_password()
+ * @author Grégory Viguier
+ *
+ * @return string
+ */
+ private function generate_secure_key() {
+ $length = wp_rand( 12, 20 );
+ $chars = 'abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789!@#$%^&*()-_ []{}<>~`+=,.;:/?|';
+ $password = '';
+
+ for ( $i = 0; $i < $length; $i++ ) {
+ $password .= substr( $chars, wp_rand( 0, strlen( $chars ) - 1 ), 1 );
+ }
+
+ return $password;
+ }
+
+ /**
+ * Filter the arguments used in an HTTP request, to make sure our API key has not been overwritten by some other plugin.
+ *
+ * @since 1.8.4
+ * @author Grégory Viguier
+ *
+ * @param array $args An array of HTTP request arguments.
+ * @param string $url The request URL.
+ * @return array
+ */
+ public function force_api_key_header( $args, $url ) {
+ if ( strpos( $url, self::API_ENDPOINT ) === false ) {
+ return $args;
+ }
+
+ if ( ! empty( $args['headers']['Authorization'] ) || ! empty( $args[ $this->secure_key ] ) ) {
+ if ( ! empty( $args[ $this->secure_key ] ) ) {
+ $args['headers']['Authorization'] = 'token ' . $args[ $this->secure_key ];
+ } else {
+ $args['headers']['Authorization'] = 'token ' . $this->api_key;
+ }
+ }
+
+ return $args;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/inc/common/admin-bar.php b/wp/wp-content/plugins/imagify/inc/common/admin-bar.php
new file mode 100644
index 00000000..af89ec43
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/common/admin-bar.php
@@ -0,0 +1,79 @@
+current_user_can( 'manage' ) ) {
+ return;
+ }
+
+ if ( ! get_imagify_option( 'admin_bar_menu' ) ) {
+ return;
+ }
+
+ // Parent.
+ $wp_admin_bar->add_menu( array(
+ 'id' => 'imagify',
+ 'title' => 'Imagify',
+ 'href' => get_imagify_admin_url(),
+ ) );
+
+ // Settings.
+ $wp_admin_bar->add_menu(array(
+ 'parent' => 'imagify',
+ 'id' => 'imagify-settings',
+ 'title' => __( 'Settings' ),
+ 'href' => get_imagify_admin_url(),
+ ) );
+
+ // Bulk Optimization.
+ if ( ! is_network_admin() ) {
+ $wp_admin_bar->add_menu(array(
+ 'parent' => 'imagify',
+ 'id' => 'imagify-bulk-optimization',
+ 'title' => __( 'Bulk Optimization', 'imagify' ),
+ 'href' => get_imagify_admin_url( 'bulk-optimization' ),
+ ) );
+ }
+
+ // Documentation.
+ $wp_admin_bar->add_menu(array(
+ 'parent' => 'imagify',
+ 'id' => 'imagify-documentation',
+ 'title' => __( 'Documentation', 'imagify' ),
+ 'href' => imagify_get_external_url( 'documentation' ),
+ 'meta' => array(
+ 'target' => '_blank',
+ ),
+ ) );
+
+ // Rate it.
+ $wp_admin_bar->add_menu(array(
+ 'parent' => 'imagify',
+ 'id' => 'imagify-rate-it',
+ /* translators: %s is WordPress.org. */
+ 'title' => sprintf( __( 'Rate Imagify on %s', 'imagify' ), 'WordPress.org' ),
+ 'href' => imagify_get_external_url( 'rate' ),
+ 'meta' => array(
+ 'target' => '_blank',
+ ),
+ ) );
+
+ // Quota & Profile informations.
+ if ( defined( 'IMAGIFY_HIDDEN_ACCOUNT' ) && IMAGIFY_HIDDEN_ACCOUNT || ! get_imagify_option( 'api_key' ) ) {
+ return;
+ }
+
+ $wp_admin_bar->add_menu( array(
+ 'parent' => 'imagify',
+ 'id' => 'imagify-profile',
+ 'title' => wp_nonce_field( 'imagify-get-admin-bar-profile', 'imagifygetadminbarprofilenonce', false, false ) . '' . __( 'Loading...', 'imagify' ) . '
',
+ ) );
+}
diff --git a/wp/wp-content/plugins/imagify/inc/common/attachments.php b/wp/wp-content/plugins/imagify/inc/common/attachments.php
new file mode 100644
index 00000000..17939c5a
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/common/attachments.php
@@ -0,0 +1,101 @@
+is_valid() ) {
+ return;
+ }
+
+ imagify_trigger_delete_media_hook( $process );
+}
+
+add_action( 'imagify_delete_media', 'imagify_cleanup_after_media_deletion' );
+/**
+ * Delete the backup file and the next-gen files when an attachement is deleted.
+ *
+ * @since 1.9
+ * @author Grégory Viguier
+ *
+ * @param ProcessInterface $process An optimization process.
+ */
+function imagify_cleanup_after_media_deletion( $process ) {
+ if ( 'wp' !== $process->get_media()->get_context() ) {
+ return;
+ }
+
+ /**
+ * The optimization data will be automatically deleted by WP (post metas).
+ * Delete the Nextgen versions and the backup file.
+ */
+ $process->delete_nextgen_files( false, true );
+
+ $process->delete_backup();
+}
+
+add_filter( 'ext2type', 'imagify_add_avif_type' );
+/**
+ * Add the AVIF extension to wp_get_ext_types().
+ *
+ * @since 1.9
+ * @author Grégory Viguier
+ *
+ * @param array $ext2type Multi-dimensional array with extensions for a default set of file types.
+ * @return array
+ */
+function imagify_add_avif_type( $ext2type ) {
+ if ( ! in_array( 'avif', $ext2type['image'], true ) ) {
+ $ext2type['image'][] = 'avif';
+ }
+ return $ext2type;
+}
+
+/**
+ * Set WP’s "big images threshold" to Imagify’s resizing value.
+ *
+ * @since 1.9.8
+ * @since WP 5.3
+ * @author Grégory Viguier
+ */
+add_filter( 'big_image_size_threshold', [ imagify_get_context( 'wp' ), 'get_resizing_threshold' ], IMAGIFY_INT_MAX );
+
+/**
+ * Add filters to manage images formats that will be generated
+ *
+ * @return array
+ */
+function imagify_nextgen_images_formats() {
+ $value = get_imagify_option( 'optimization_format' );
+ $formats = [];
+
+ if ( 'off' !== $value ) {
+ $formats[ $value ] = $value;
+ }
+
+ $default = $formats;
+
+ /**
+ * Filters the array of next gen formats to generate with Imagify
+ *
+ * @since 2.2
+ *
+ * @param array $formats Array of image formats
+ */
+ $formats = apply_filters( 'imagify_nextgen_images_formats', $formats );
+
+ if ( ! is_array( $formats ) ) {
+ $formats = $default;
+ }
+
+ return $formats;
+}
diff --git a/wp/wp-content/plugins/imagify/inc/common/partners.php b/wp/wp-content/plugins/imagify/inc/common/partners.php
new file mode 100644
index 00000000..6040b1cd
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/common/partners.php
@@ -0,0 +1,33 @@
+get_option_name(), 'imagify_maybe_delete_partner_on_option_update', 10, 2 );
+/**
+ * After the first API key has been successfully added, make sure the partner ID is deleted.
+ *
+ * @since 1.6.14
+ * @author Grégory Viguier
+ *
+ * @param mixed $old_value The old option value.
+ * @param mixed $new_value The new option value.
+ */
+function imagify_maybe_delete_partner_on_option_update( $old_value, $new_value ) {
+ if ( empty( $old_value['api_key'] ) && ! empty( $new_value['api_key'] ) ) {
+ imagify_delete_partner();
+ }
+}
+
+add_action( 'update_site_option_' . Imagify_Options::get_instance()->get_option_name(), 'imagify_maybe_delete_partner_on_network_option_update', 10, 3 );
+/**
+ * After the first API key has been successfully added to the network option, make sure the partner ID is deleted.
+ *
+ * @since 1.6.14
+ * @author Grégory Viguier
+ *
+ * @param string $option Name of the network option.
+ * @param mixed $new_value The new network option value.
+ * @param mixed $old_value The old network option value.
+ */
+function imagify_maybe_delete_partner_on_network_option_update( $option, $new_value, $old_value ) {
+ imagify_maybe_delete_partner_on_option_update( $old_value, $new_value );
+}
diff --git a/wp/wp-content/plugins/imagify/inc/deprecated/3rd-party.php b/wp/wp-content/plugins/imagify/inc/deprecated/3rd-party.php
new file mode 100644
index 00000000..79820f73
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/deprecated/3rd-party.php
@@ -0,0 +1,334 @@
+maybe_upgrade_table()' );
+
+ \Imagify\ThirdParty\NGG\DB::get_instance()->maybe_upgrade_table();
+ }
+
+ /**
+ * Update all Imagify stats for NGG Bulk Optimization.
+ *
+ * @since 1.5
+ * @since 1.7 Deprecated.
+ * @author Jonathan Buttigieg
+ * @deprecated
+ */
+ function _imagify_ngg_update_bulk_stats() {
+ _deprecated_function( __FUNCTION__ . '()', '1.7', 'imagify_ngg_bulk_page_data()' );
+
+ if ( empty( $_GET['page'] ) || imagify_get_ngg_bulk_screen_slug() !== $_GET['page'] ) { // WPCS: CSRF ok.
+ return;
+ }
+
+ add_filter( 'imagify_count_attachments' , 'imagify_ngg_count_attachments' );
+ add_filter( 'imagify_count_optimized_attachments' , 'imagify_ngg_count_optimized_attachments' );
+ add_filter( 'imagify_count_error_attachments' , 'imagify_ngg_count_error_attachments' );
+ add_filter( 'imagify_count_unoptimized_attachments' , 'imagify_ngg_count_unoptimized_attachments' );
+ add_filter( 'imagify_percent_optimized_attachments' , 'imagify_ngg_percent_optimized_attachments' );
+ add_filter( 'imagify_count_saving_data' , 'imagify_ngg_count_saving_data', 8 );
+ }
+
+ /**
+ * Prepare the data that goes back with the Heartbeat API.
+ *
+ * @since 1.5
+ * @since 1.7.1 Deprecated.
+ * @deprecated
+ *
+ * @param array $response The Heartbeat response.
+ * @param array $data The $_POST data sent.
+ * @return array
+ */
+ function _imagify_ngg_heartbeat_received( $response, $data ) {
+ _deprecated_function( __FUNCTION__ . '()', '1.7.1' );
+
+ if ( ! isset( $data['imagify_heartbeat'] ) || 'update_ngg_bulk_data' !== $data['imagify_heartbeat'] ) {
+ return $response;
+ }
+
+ add_filter( 'imagify_count_saving_data', 'imagify_ngg_count_saving_data', 8 );
+ $saving_data = imagify_count_saving_data();
+ $user = new User();
+
+ $response['imagify_bulk_data'] = array(
+ // User account.
+ 'unconsumed_quota' => is_wp_error( $user ) ? 0 : $user->get_percent_unconsumed_quota(),
+ // Global chart.
+ 'optimized_attachments_percent' => imagify_ngg_percent_optimized_attachments(),
+ 'unoptimized_attachments' => imagify_ngg_count_unoptimized_attachments(),
+ 'optimized_attachments' => imagify_ngg_count_optimized_attachments(),
+ 'errors_attachments' => imagify_ngg_count_error_attachments(),
+ // Stats block.
+ 'already_optimized_attachments' => number_format_i18n( $saving_data['count'] ),
+ 'original_human' => imagify_size_format( $saving_data['original_size'], 1 ),
+ 'optimized_human' => imagify_size_format( $saving_data['optimized_size'], 1 ),
+ 'optimized_percent' => $saving_data['percent'],
+ );
+
+ return $response;
+ }
+
+ /**
+ * Filter the current user capability to operate Imagify.
+ *
+ * @since 1.6.11
+ * @since 1.9 Deprecated.
+ * @see imagify_get_capacity()
+ * @author Grégory Viguier
+ * @deprecated
+ *
+ * @param bool $user_can Tell if the current user has the required capacity to operate Imagify.
+ * @param string $capacity The user capacity.
+ * @param string $describer Capacity describer. See imagify_get_capacity() for possible values. Can also be a "real" user capacity.
+ * @param int $post_id A post ID (a gallery ID for NGG).
+ * @return bool
+ */
+ function imagify_ngg_current_user_can( $user_can, $capacity, $describer, $post_id ) {
+ static $user_can_per_gallery = array();
+
+ _deprecated_function( __FUNCTION__ . '()', '1.9' );
+
+ if ( ! $user_can || ! $post_id || 'NextGEN Manage gallery' !== $capacity ) {
+ return $user_can;
+ }
+
+ $image = nggdb::find_image( $post_id );
+
+ if ( isset( $user_can_per_gallery[ $image->galleryid ] ) ) {
+ return $user_can_per_gallery[ $image->galleryid ];
+ }
+
+ $gallery_mapper = C_Gallery_Mapper::get_instance();
+ $gallery = $gallery_mapper->find( $image->galleryid, false );
+
+ if ( get_current_user_id() === $gallery->author || current_user_can( 'NextGEN Manage others gallery' ) ) {
+ // The user created this gallery or can edit others galleries.
+ $user_can_per_gallery[ $image->galleryid ] = true;
+ return $user_can_per_gallery[ $image->galleryid ];
+ }
+
+ // The user can't edit this gallery.
+ $user_can_per_gallery[ $image->galleryid ] = false;
+ return $user_can_per_gallery[ $image->galleryid ];
+ }
+
+ /**
+ * Get user capacity to operate Imagify within NGG galleries.
+ * It is meant to be used to filter 'imagify_capacity'.
+ *
+ * @since 1.6.11
+ * @since 1.9 Deprecated.
+ * @see imagify_get_capacity()
+ * @author Grégory Viguier
+ * @deprecated
+ *
+ * @param string $capacity The user capacity.
+ * @param string $describer Capacity describer. See imagify_get_capacity() for possible values. Can also be a "real" user capacity.
+ * @return string
+ */
+ function imagify_get_ngg_capacity( $capacity = 'edit_post', $describer = 'manual-optimize' ) {
+ if ( 'manual-optimize' === $describer ) {
+ return 'NextGEN Manage gallery';
+ }
+
+ return $capacity;
+ }
+
+ /**
+ * Dispatch the optimization process.
+ *
+ * @since 1.8
+ * @since 1.9 Deprecated.
+ * @author Grégory Viguier
+ * @deprecated
+ */
+ function imagify_ngg_dispatch_dynamic_thumbnail_background_process() {
+ _deprecated_function( __FUNCTION__ . '()', '1.9' );
+
+ Imagify_NGG_Dynamic_Thumbnails_Background_Process::get_instance()->save()->dispatch();
+ }
+
+ /**
+ * On manual optimization, manual re-optimization, and manual restoration, filter the user capacity to operate Imagify within NGG.
+ *
+ * @since 1.6.11
+ * @since 1.9 Deprecated.
+ * @author Grégory Viguier
+ * @deprecated
+ */
+ function _do_admin_post_imagify_ngg_user_capacity() {
+ _deprecated_function( __FUNCTION__ . '()', '1.9' );
+
+ if ( ! empty( $_GET['context'] ) && 'NGG' === $_GET['context'] ) { // WPCS: CSRF ok.
+ add_filter( 'imagify_capacity', 'imagify_get_ngg_capacity', 10, 2 );
+ }
+ }
+
+ /**
+ * Get all unoptimized attachment ids.
+ *
+ * @since 1.0
+ * @since 1.9 Deprecated
+ * @author Jonathan Buttigieg
+ * @deprecated
+ */
+ function _do_wp_ajax_imagify_ngg_get_unoptimized_attachment_ids() {
+ _deprecated_function( __FUNCTION__ . '()', '1.9', '\\Imagify\\ThirdParty\\NGG\\AdminAjaxPost::get_instance()->get_media_ids()' );
+
+ \Imagify\ThirdParty\NGG\AdminAjaxPost::get_instance()->get_media_ids();
+ }
+
+ /**
+ * Provide custom folder type data.
+ *
+ * @since 1.7
+ * @since 1.9 Deprecated
+ * @author Grégory Viguier
+ * @deprecated
+ *
+ * @param array $data An array with keys corresponding to cell classes, and values formatted with HTML.
+ * @param string $context A context.
+ * @return array
+ */
+ function imagify_ngg_get_folder_type_data( $data, $context ) {
+ _deprecated_function( __FUNCTION__ . '()', '1.9' );
+
+ if ( 'ngg' !== $context ) {
+ return $data;
+ }
+
+ // Already filtered in imagify_ngg_bulk_page_data().
+ $total_saving_data = imagify_count_saving_data();
+
+ return [
+ 'images-optimized' => imagify_ngg_count_optimized_attachments(),
+ 'errors' => imagify_ngg_count_error_attachments(),
+ 'optimized' => $total_saving_data['optimized_size'],
+ 'original' => $total_saving_data['original_size'],
+ 'errors_url' => admin_url( 'admin.php?page=nggallery-manage-gallery' ),
+ ];
+ }
+
+endif;
+
+if ( function_exists( 'wr2x_delete_attachment' ) ) :
+
+ /**
+ * Remove all retina versions if they exist.
+ *
+ * @since 1.0
+ * @since 1.8 Deprecated.
+ * @deprecated
+ *
+ * @param int $attachment_id An attachment ID.
+ */
+ function _imagify_wr2x_delete_attachment_on_restore( $attachment_id ) {
+ _deprecated_function( __FUNCTION__ . '()', '1.8' );
+
+ wr2x_delete_attachment( $attachment_id );
+ }
+
+ /**
+ * Regenerate all retina versions.
+ *
+ * @since 1.0
+ * @since 1.8 Deprecated.
+ * @deprecated
+ *
+ * @param int $attachment_id An attachment ID.
+ */
+ function _imagify_wr2x_generate_images_on_restore( $attachment_id ) {
+ _deprecated_function( __FUNCTION__ . '()', '1.8' );
+
+ wr2x_delete_attachment( $attachment_id );
+ wr2x_generate_images( wp_get_attachment_metadata( $attachment_id ) );
+ }
+
+ /**
+ * Filter the optimization data of each thumbnail.
+ *
+ * @since 1.0
+ * @since 1.8 Deprecated.
+ * @deprecated
+ *
+ * @param array $data The statistics data.
+ * @param object $response The API response.
+ * @param int $id The attachment ID.
+ * @param string $path The attachment path.
+ * @param string $url The attachment URL.
+ * @param string $size_key The attachment size key.
+ * @param bool $optimization_level The optimization level.
+ * @return array $data The new optimization data.
+ */
+ function _imagify_optimize_wr2x( $data, $response, $id, $path, $url, $size_key, $optimization_level ) {
+ _deprecated_function( __FUNCTION__ . '()', '1.8', 'Imagify_WP_Retina_2x::optimize_retina_version()' );
+
+ /**
+ * Allow to optimize the retina version generated by WP Retina x2.
+ *
+ * @since 1.0
+ *
+ * @param bool $do_retina True will force the optimization.
+ */
+ $do_retina = apply_filters( 'do_imagify_optimize_retina', true );
+ $retina_path = wr2x_get_retina( $path );
+
+ if ( empty( $retina_path ) || ! $do_retina ) {
+ return $data;
+ }
+
+ $response = do_imagify( $retina_path, array(
+ 'backup' => false,
+ 'optimization_level' => $optimization_level,
+ 'context' => 'wp-retina',
+ ) );
+ $attachment = get_imagify_attachment( 'wp', $id, 'imagify_fill_thumbnail_data' );
+
+ return $attachment->fill_data( $data, $response, $size_key . '@2x' );
+ }
+
+endif;
+
+if ( defined( 'WP_ROCKET_VERSION' ) ) :
+
+ /**
+ * Don't load Imagify CSS & JS files on WP Rocket options screen to avoid conflict with older version of SweetAlert.
+ * Since 1.6.10 they should be enqueued only if one of our notices displays here.
+ *
+ * @since 1.6.9.1
+ * @since 1.6.10 Use the new class Imagify_Assets.
+ * @since 1.9.3 Deprecated.
+ * @author Jonathan Buttigieg
+ * @author Grégory Viguier
+ * @deprecated
+ */
+ function imagify_dequeue_sweetalert_wprocket() {
+ _deprecated_function( __FUNCTION__ . '()', '1.9.3', '\\Imagify\\ThirdParty\\WPRocket\\Main::dequeue_sweetalert()' );
+
+ if ( ! defined( 'WP_ROCKET_PLUGIN_SLUG' ) ) {
+ return;
+ }
+
+ if ( ! imagify_is_screen( 'settings_page_' . WP_ROCKET_PLUGIN_SLUG ) && ! imagify_is_screen( 'settings_page_' . WP_ROCKET_PLUGIN_SLUG . '-network' ) ) {
+ return;
+ }
+
+ Imagify_Assets::get_instance()->dequeue_script( array( 'sweetalert-core', 'sweetalert', 'notices' ) );
+ }
+
+endif;
diff --git a/wp/wp-content/plugins/imagify/inc/deprecated/Traits/Media/CustomFoldersDeprecatedTrait.php b/wp/wp-content/plugins/imagify/inc/deprecated/Traits/Media/CustomFoldersDeprecatedTrait.php
new file mode 100644
index 00000000..d4c8e4c2
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/deprecated/Traits/Media/CustomFoldersDeprecatedTrait.php
@@ -0,0 +1,44 @@
+get_fullsize_url()' );
+
+ if ( ! $this->is_valid() ) {
+ return false;
+ }
+
+ if ( $this->get_cdn() ) {
+ return $this->get_cdn()->get_file_url();
+ }
+
+ $row = $this->get_row();
+
+ if ( ! $row || empty( $row['path'] ) ) {
+ return false;
+ }
+
+ return \Imagify_Files_Scan::remove_placeholder( $row['path'], 'url' );
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/inc/deprecated/Traits/Media/NGGDeprecatedTrait.php b/wp/wp-content/plugins/imagify/inc/deprecated/Traits/Media/NGGDeprecatedTrait.php
new file mode 100644
index 00000000..6eee3965
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/deprecated/Traits/Media/NGGDeprecatedTrait.php
@@ -0,0 +1,38 @@
+get_fullsize_url()' );
+
+ if ( ! $this->is_valid() ) {
+ return false;
+ }
+
+ if ( $this->get_cdn() ) {
+ return $this->get_cdn()->get_file_url();
+ }
+
+ return ! empty( $this->image->imageURL ) ? $this->image->imageURL : false;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/inc/deprecated/Traits/Media/NoopDeprecatedTrait.php b/wp/wp-content/plugins/imagify/inc/deprecated/Traits/Media/NoopDeprecatedTrait.php
new file mode 100644
index 00000000..2bef3bba
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/deprecated/Traits/Media/NoopDeprecatedTrait.php
@@ -0,0 +1,30 @@
+get_fullsize_url()' );
+
+ return false;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/inc/deprecated/Traits/Media/WPDeprecatedTrait.php b/wp/wp-content/plugins/imagify/inc/deprecated/Traits/Media/WPDeprecatedTrait.php
new file mode 100644
index 00000000..0c89bc5d
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/deprecated/Traits/Media/WPDeprecatedTrait.php
@@ -0,0 +1,40 @@
+get_fullsize_url()' );
+
+ if ( ! $this->is_valid() ) {
+ return false;
+ }
+
+ if ( $this->get_cdn() ) {
+ return $this->get_cdn()->get_file_url();
+ }
+
+ $url = wp_get_attachment_url( $this->id );
+
+ return $url ? $url : false;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/inc/deprecated/Traits/Optimization/Process/AbstractProcessDeprecatedTrait.php b/wp/wp-content/plugins/imagify/inc/deprecated/Traits/Optimization/Process/AbstractProcessDeprecatedTrait.php
new file mode 100644
index 00000000..679a4898
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/deprecated/Traits/Optimization/Process/AbstractProcessDeprecatedTrait.php
@@ -0,0 +1,44 @@
+get_fullsize_file()' );
+
+ if ( isset( $this->file ) ) {
+ return $this->file;
+ }
+
+ $this->file = false;
+
+ if ( $this->get_media() ) {
+ $this->file = new File( $this->get_media()->get_raw_fullsize_path() );
+ }
+
+ return $this->file;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/inc/deprecated/classes/class-imagify-abstract-attachment.php b/wp/wp-content/plugins/imagify/inc/deprecated/classes/class-imagify-abstract-attachment.php
new file mode 100644
index 00000000..0e9565cb
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/deprecated/classes/class-imagify-abstract-attachment.php
@@ -0,0 +1,1237 @@
+is_image()
+ */
+ protected $is_image;
+
+ /**
+ * Tell if the file is a pdf.
+ *
+ * @var bool
+ * @since 1.8
+ * @access protected
+ * @see $this->is_pdf()
+ */
+ protected $is_pdf;
+
+ /**
+ * Stores the file extension (even if the extension is not supported by Imagify).
+ *
+ * @var string|null
+ * @since 1.8
+ * @access protected
+ * @see $this->get_extension()
+ */
+ protected $extension = false;
+
+ /**
+ * Stores the file mime type + file extension (if the file is supported).
+ *
+ * @var array
+ * @since 1.8
+ * @access protected
+ * @see $this->get_file_type()
+ */
+ protected $file_type;
+
+ /**
+ * Filesystem object.
+ *
+ * @var object Imagify_Filesystem
+ * @since 1.7.1
+ * @access protected
+ * @author Grégory Viguier
+ */
+ protected $filesystem;
+
+ /**
+ * The editor instances used to resize files.
+ *
+ * @var array An array of image editor objects (WP_Image_Editor_Imagick, WP_Image_Editor_GD).
+ * @since 1.7.1
+ * @access protected
+ * @author Grégory Viguier
+ */
+ protected $editors = array();
+
+ /**
+ * The name of the transient that tells if optimization is processing.
+ *
+ * @var string
+ * @since 1.7.1
+ * @access protected
+ * @author Grégory Viguier
+ */
+ protected $optimization_state_transient;
+
+ /**
+ * Tell if the optimization status is network-wide.
+ *
+ * @var bool
+ * @since 1.7.1
+ * @access protected
+ * @author Grégory Viguier
+ */
+ protected $optimization_state_network_wide = false;
+
+ /**
+ * The constructor.
+ *
+ * @since 1.0
+ * @access public
+ *
+ * @param int|object $id The attachment ID or the attachment itself.
+ * If an integer, make sure the attachment exists.
+ */
+ public function __construct( $id = 0 ) {
+ global $post;
+
+ if ( $id ) {
+ if ( $id instanceof WP_Post ) {
+ $this->id = $id->ID;
+ } elseif ( is_numeric( $id ) ) {
+ $this->id = $id;
+ }
+ } elseif ( $post && $id instanceof WP_Post ) {
+ $this->id = $post->ID;
+ }
+
+ $this->id = (int) $this->id;
+ $this->filesystem = Imagify_Filesystem::get_instance();
+ $this->optimization_state_transient = 'wp' !== $this->get_context() ? strtolower( $this->get_context() ) . '-' : '';
+ $this->optimization_state_transient = 'imagify-' . $this->optimization_state_transient . 'async-in-progress-' . $this->id;
+ }
+
+ /**
+ * Get the attachment context.
+ *
+ * @since 1.7.1
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return string
+ */
+ public function get_context() {
+ if ( $this->context ) {
+ return $this->context;
+ }
+
+ $this->context = str_replace( array( 'Imagify_', 'Attachment' ), '', get_class( $this ) );
+ $this->context = trim( $this->context, '_' );
+ $this->context = $this->context ? $this->context : 'wp';
+
+ return $this->context;
+ }
+
+ /**
+ * Tell if the current attachment is valid.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ * @access public
+ *
+ * @return bool
+ */
+ public function is_valid() {
+ return $this->id > 0;
+ }
+
+ /**
+ * Get the attachment ID.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ * @access public
+ *
+ * @return int
+ */
+ public function get_id() {
+ return $this->id;
+ }
+
+ /**
+ * Get the original attachment path.
+ *
+ * @since 1.0
+ * @access public
+ *
+ * @return string
+ */
+ abstract public function get_original_path();
+
+ /**
+ * Get the original attachment URL.
+ *
+ * @since 1.0
+ * @access public
+ *
+ * @return string
+ */
+ abstract public function get_original_url();
+
+ /**
+ * Get the attachment backup file path, even if the file doesn't exist.
+ *
+ * @since 1.6.13
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return string|bool The file path. False on failure.
+ */
+ abstract public function get_raw_backup_path();
+
+ /**
+ * Get the attachment backup file path.
+ *
+ * @since 1.0
+ * @access public
+ *
+ * @return string|false The file path. False if it doesn't exist.
+ */
+ public function get_backup_path() {
+ if ( ! $this->is_valid() ) {
+ return false;
+ }
+
+ $backup_path = $this->get_raw_backup_path();
+
+ if ( $backup_path && $this->filesystem->exists( $backup_path ) ) {
+ return $backup_path;
+ }
+
+ return false;
+ }
+
+ /**
+ * Get the attachment backup URL.
+ *
+ * @since 1.4
+ * @access public
+ *
+ * @return string|false
+ */
+ public function get_backup_url() {
+ if ( ! $this->is_valid() ) {
+ return false;
+ }
+
+ return get_imagify_attachment_url( $this->get_raw_backup_path() );
+ }
+
+ /**
+ * Get the attachment optimization data.
+ *
+ * @since 1.0
+ * @access public
+ *
+ * @return array
+ */
+ abstract public function get_data();
+
+ /**
+ * Get the attachment optimization level.
+ *
+ * @since 1.0
+ * @access public
+ *
+ * @return int
+ */
+ abstract public function get_optimization_level();
+
+ /**
+ * Get the attachment optimization status (success or error).
+ *
+ * @since 1.0
+ * @access public
+ *
+ * @return string
+ */
+ abstract public function get_status();
+
+ /**
+ * Get the attachment error if there is one.
+ *
+ * @since 1.1.5
+ * @access public
+ *
+ * @return string The message error
+ */
+ public function get_optimized_error() {
+ $error = $this->get_size_data( 'full', 'error' );
+
+ if ( is_string( $error ) ) {
+ return trim( $error );
+ }
+
+ return '';
+ }
+
+ /**
+ * Count number of optimized sizes.
+ *
+ * @since 1.0
+ * @access public
+ *
+ * @return int
+ */
+ public function get_optimized_sizes_count() {
+ $data = $this->get_data();
+ $sizes = ! empty( $data['sizes'] ) && is_array( $data['sizes'] ) ? $data['sizes'] : array();
+ $count = 0;
+
+ unset( $sizes['full'] );
+
+ if ( ! $sizes ) {
+ return 0;
+ }
+
+ foreach ( $sizes as $size ) {
+ if ( ! empty( $size['success'] ) ) {
+ $count++;
+ }
+ }
+
+ return $count;
+ }
+
+ /**
+ * Delete the 3 metas used by Imagify.
+ *
+ * @since 1.6.6
+ * @access public
+ * @author Grégory Viguier
+ */
+ public function delete_imagify_data() {
+ if ( ! $this->is_valid() ) {
+ return;
+ }
+
+ delete_post_meta( $this->id, '_imagify_data' );
+ delete_post_meta( $this->id, '_imagify_status' );
+ delete_post_meta( $this->id, '_imagify_optimization_level' );
+ }
+
+ /**
+ * Get width and height of the original image.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ * @access public
+ *
+ * @return array
+ */
+ public function get_dimensions() {
+ return array(
+ 'width' => 0,
+ 'height' => 0,
+ );
+ }
+
+ /**
+ * Tell if the current item refers to an image, based on file extension.
+ *
+ * @since 1.8
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return bool Returns false in case it's an image but not in a supported format (bmp for example).
+ */
+ public function is_image() {
+ if ( isset( $this->is_image ) ) {
+ return $this->is_image;
+ }
+
+ $this->is_image = strpos( (string) $this->get_mime_type(), 'image/' ) === 0;
+
+ return $this->is_image;
+ }
+
+ /**
+ * Tell if the current item refers to a pdf, based on file extension.
+ *
+ * @since 1.8
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return bool
+ */
+ public function is_pdf() {
+ if ( isset( $this->is_pdf ) ) {
+ return $this->is_pdf;
+ }
+
+ $this->is_pdf = 'application/pdf' === $this->get_mime_type();
+
+ return $this->is_pdf;
+ }
+
+ /**
+ * Get the file mime type.
+ *
+ * @since 1.8
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return bool
+ */
+ public function get_mime_type() {
+ return $this->get_file_type()->type;
+ }
+
+ /**
+ * Get the file mime type + file extension (if the file is supported).
+ *
+ * @since 1.8
+ * @access public
+ * @see wp_check_filetype()
+ * @author Grégory Viguier
+ *
+ * @return object
+ */
+ public function get_file_type() {
+ if ( isset( $this->file_type ) ) {
+ return $this->file_type;
+ }
+
+ if ( ! $this->is_valid() ) {
+ $this->file_type = (object) array(
+ 'ext' => '',
+ 'type' => '',
+ );
+ return $this->file_type;
+ }
+
+ $path = $this->get_original_path();
+
+ if ( ! $path ) {
+ $this->file_type = (object) array(
+ 'ext' => '',
+ 'type' => '',
+ );
+ return $this->file_type;
+ }
+
+ $this->file_type = (object) wp_check_filetype( $path, imagify_get_mime_types() );
+
+ return $this->file_type;
+ }
+
+ /**
+ * Get the attachment extension.
+ *
+ * @since 1.0
+ * @access public
+ *
+ * @return string|null
+ */
+ public function get_extension() {
+ if ( false !== $this->extension ) {
+ return $this->extension;
+ }
+
+ if ( ! $this->is_valid() ) {
+ $this->extension = null;
+ return $this->extension;
+ }
+
+ $this->extension = $this->filesystem->path_info( $this->get_original_path(), 'extension' );
+
+ return $this->extension;
+ }
+
+ /**
+ * Tell if the current file extension is supported.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return bool
+ */
+ public function is_extension_supported() {
+ return (bool) $this->get_file_type()->ext;
+ }
+
+ /**
+ * Tell if the current file mime type is supported.
+ *
+ * @since 1.6.9
+ * @since 1.8 Does the same has this->is_extension_supported().
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return bool
+ */
+ public function is_mime_type_supported() {
+ return (bool) $this->get_mime_type();
+ }
+
+ /**
+ * Tell if the current attachment has the required WP metadata.
+ *
+ * @since 1.6.12
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return bool
+ */
+ public function has_required_metadata() {
+ if ( ! $this->is_valid() ) {
+ return false;
+ }
+
+ return imagify_attachment_has_required_metadata( $this->id );
+ }
+
+ /**
+ * Get the attachment optimization level label.
+ *
+ * @since 1.2
+ * @since 1.7 Added $format parameter.
+ * @access public
+ *
+ * @param string $format Format to display the label. Use %ICON% for the icon and %s for the label.
+ * @return string
+ */
+ public function get_optimization_level_label( $format = '%s' ) {
+ return imagify_get_optimization_level_label( $this->get_optimization_level(), $format );
+ }
+
+ /**
+ * Get the original attachment size.
+ *
+ * @since 1.0
+ * @access public
+ *
+ * @param bool $human_format True to display the image human format size (1Mb).
+ * @param int $decimals Precision of number of decimal places.
+ * @return string|int
+ */
+ public function get_original_size( $human_format = true, $decimals = 2 ) {
+ if ( ! $this->is_valid() ) {
+ return $human_format ? imagify_size_format( 0, $decimals ) : 0;
+ }
+
+ $size = $this->get_size_data( 'full', 'original_size' );
+
+ if ( ! $size ) {
+ // Check for the backup file first.
+ $filepath = $this->get_backup_path();
+
+ if ( ! $filepath ) {
+ $filepath = $this->get_original_path();
+ $filepath = $filepath && $this->filesystem->exists( $filepath ) ? $filepath : false;
+ }
+
+ $size = $filepath ? $this->filesystem->size( $filepath ) : 0;
+ }
+
+ if ( $human_format ) {
+ return imagify_size_format( (int) $size, $decimals );
+ }
+
+ return (int) $size;
+ }
+
+ /**
+ * Get the optimized attachment size.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param bool $human_format True to display the image human format size (1Mb).
+ * @param int $decimals Precision of number of decimal places.
+ * @return string|int
+ */
+ public function get_optimized_size( $human_format = true, $decimals = 2 ) {
+ if ( ! $this->is_valid() ) {
+ return $human_format ? imagify_size_format( 0, $decimals ) : 0;
+ }
+
+ $size = $this->get_size_data( 'full', 'optimized_size' );
+
+ if ( ! $size ) {
+ $filepath = $this->get_original_path();
+ $filepath = $filepath && $this->filesystem->exists( $filepath ) ? $filepath : false;
+ $size = $filepath ? $this->filesystem->size( $filepath ) : 0;
+ }
+
+ if ( $human_format ) {
+ return imagify_size_format( (int) $size, $decimals );
+ }
+
+ return (int) $size;
+ }
+
+ /**
+ * Get the optimized attachment size.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return float A 2-decimals float.
+ */
+ public function get_saving_percent() {
+ if ( ! $this->is_valid() ) {
+ return round( (float) 0, 2 );
+ }
+
+ $percent = $this->get_size_data( 'full', 'percent' );
+ $percent = $percent ? $percent : (float) 0;
+
+ return round( $percent, 2 );
+ }
+
+ /**
+ * Get the overall optimized size (all thumbnails).
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return float A 2-decimals float.
+ */
+ public function get_overall_saving_percent() {
+ if ( ! $this->is_valid() ) {
+ return round( (float) 0, 2 );
+ }
+
+ $percent = $this->get_data();
+ $percent = ! empty( $percent['stats']['percent'] ) ? $percent['stats']['percent'] : (float) 0;
+
+ return round( $percent, 2 );
+ }
+
+ /**
+ * Get the statistics of a specific size.
+ *
+ * @since 1.0
+ * @access public
+ *
+ * @param string $size The thumbnail slug.
+ * @param string $key The specific data slug.
+ * @return array|string
+ */
+ public function get_size_data( $size = 'full', $key = '' ) {
+ $data = $this->get_data();
+ $stats = array();
+
+ if ( isset( $data['sizes'][ $size ] ) ) {
+ $stats = $data['sizes'][ $size ];
+ }
+
+ if ( isset( $stats[ $key ] ) ) {
+ $stats = $stats[ $key ];
+ }
+
+ return $stats;
+ }
+
+ /**
+ * Get the global statistics data or a specific one.
+ *
+ * @since 1.0
+ * @access public
+ *
+ * @param string $key The specific data slug.
+ * @return array|string
+ */
+ public function get_stats_data( $key = '' ) {
+ $data = $this->get_data();
+ $stats = '';
+
+ if ( isset( $data['stats'] ) ) {
+ $stats = $data['stats'];
+ }
+
+ if ( isset( $stats[ $key ] ) ) {
+ $stats = $stats[ $key ];
+ }
+
+ return $stats;
+ }
+
+ /**
+ * Check if the attachment is already optimized (before Imagify).
+ *
+ * @since 1.1.6
+ * @access public
+ *
+ * @return bool True if the attachment is optimized.
+ */
+ public function is_already_optimized() {
+ return 'already_optimized' === $this->get_status();
+ }
+
+ /**
+ * Check if the attachment is optimized.
+ *
+ * @since 1.0
+ * @access public
+ *
+ * @return bool True if the attachment is optimized.
+ */
+ public function is_optimized() {
+ return 'success' === $this->get_status();
+ }
+
+ /**
+ * Check if the attachment exceeding the limit size (> 5mo).
+ *
+ * @since 1.0
+ * @access public
+ *
+ * @return bool True if the attachment is skipped.
+ */
+ public function is_exceeded() {
+ $filepath = $this->get_original_path();
+ $size = 0;
+
+ if ( $filepath && $this->filesystem->exists( $filepath ) ) {
+ $size = $this->filesystem->size( $filepath );
+ }
+
+ return $size > IMAGIFY_MAX_BYTES;
+ }
+
+ /**
+ * Check if the attachment has a backup of the original size.
+ *
+ * @since 1.0
+ * @access public
+ *
+ * @return bool True if the attachment has a backup.
+ */
+ public function has_backup() {
+ return (bool) $this->get_backup_path();
+ }
+
+ /**
+ * Check if the attachment has an error.
+ *
+ * @since 1.0
+ * @access public
+ *
+ * @return bool True if the attachment has an error.
+ */
+ public function has_error() {
+ return 'error' === $this->get_status();
+ }
+
+ /**
+ * Get an image editor instance (WP_Image_Editor_Imagick, WP_Image_Editor_GD).
+ *
+ * @since 1.7.1
+ * @access protected
+ * @author Grégory Viguier
+ *
+ * @param string $path A file path.
+ * @return object An image editor instance (WP_Image_Editor_Imagick, WP_Image_Editor_GD). A WP_Error object on error.
+ */
+ protected function get_editor( $path ) {
+ if ( isset( $this->editors[ $path ] ) ) {
+ return $this->editors[ $path ];
+ }
+
+ $this->editors[ $path ] = wp_get_image_editor( $path, array(
+ 'methods' => self::get_editor_methods(),
+ ) );
+
+ return $this->editors[ $path ];
+ }
+
+ /**
+ * Get the image editor methods we will use.
+ *
+ * @since 1.7.1
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return array
+ */
+ public static function get_editor_methods() {
+ static $methods;
+
+ if ( isset( $methods ) ) {
+ return $methods;
+ }
+
+ $methods = array(
+ 'resize',
+ 'multi_resize',
+ 'generate_filename',
+ 'save',
+ );
+
+ if ( Imagify_Filesystem::get_instance()->can_get_exif() ) {
+ $methods[] = 'rotate';
+ }
+
+ return $methods;
+ }
+
+ /**
+ * Update the metadata size of the attachment
+ *
+ * @since 1.2
+ * @access public
+ *
+ * @return void
+ */
+ abstract public function update_metadata_size();
+
+ /**
+ * Delete the backup file.
+ *
+ * @since 1.0
+ * @access public
+ *
+ * @return void
+ */
+ public function delete_backup() {
+ $backup_path = $this->get_backup_path();
+
+ if ( $backup_path ) {
+ $this->filesystem->delete( $backup_path );
+ }
+ }
+
+ /**
+ * Get the registered sizes.
+ *
+ * @since 1.6.10
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return array Data for the registered thumbnail sizes.
+ */
+ public static function get_registered_sizes() {
+ static $registered_sizes;
+
+ if ( ! isset( $registered_sizes ) ) {
+ $registered_sizes = get_imagify_thumbnail_sizes();
+ }
+
+ return $registered_sizes;
+ }
+
+ /**
+ * Get the unoptimized sizes for a specific attachment.
+ *
+ * @since 1.6.10
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return array Data for the unoptimized thumbnail sizes.
+ * Each size data has a "file" key containing the name the thumbnail "should" have.
+ */
+ public function get_unoptimized_sizes() {
+ // The attachment must have been optimized once and have a backup.
+ if ( ! $this->is_valid() || ! $this->is_optimized() || ! $this->has_backup() || ! $this->is_image() ) {
+ return array();
+ }
+
+ $registered_sizes = self::get_registered_sizes();
+ $attachment_sizes = $this->get_data();
+ $attachment_sizes = ! empty( $attachment_sizes['sizes'] ) ? $attachment_sizes['sizes'] : array();
+ $missing_sizes = array_diff_key( $registered_sizes, $attachment_sizes );
+
+ if ( ! $missing_sizes ) {
+ // We have everything we need.
+ return array();
+ }
+
+ // Get full size dimensions.
+ $orig = wp_get_attachment_metadata( $this->id );
+ $orig_f = ! empty( $orig['file'] ) ? $orig['file'] : '';
+ $orig_w = ! empty( $orig['width'] ) ? (int) $orig['width'] : 0;
+ $orig_h = ! empty( $orig['height'] ) ? (int) $orig['height'] : 0;
+
+ if ( ! $orig_f || ! $orig_w || ! $orig_h ) {
+ return array();
+ }
+
+ $orig_f = $this->filesystem->path_info( $orig_f );
+ $orig_f = $orig_f['file_base'] . '-{%suffix%}.' . $orig_f['extension'];
+
+ // Test if the missing sizes are needed.
+ $disallowed_sizes = get_imagify_option( 'disallowed-sizes' );
+ $is_active_for_network = imagify_is_active_for_network();
+
+ foreach ( $missing_sizes as $size_name => $size_data ) {
+ $duplicate = ( $orig_w === $size_data['width'] ) && ( $orig_h === $size_data['height'] );
+
+ if ( $duplicate ) {
+ // Same dimensions as the full size.
+ unset( $missing_sizes[ $size_name ] );
+ continue;
+ }
+
+ if ( ! $is_active_for_network && isset( $disallowed_sizes[ $size_name ] ) ) {
+ // This size must be optimized.
+ unset( $missing_sizes[ $size_name ] );
+ continue;
+ }
+
+ $resize_result = image_resize_dimensions( $orig_w, $orig_h, $size_data['width'], $size_data['height'], $size_data['crop'] );
+
+ if ( ! $resize_result ) {
+ // This size is not needed.
+ unset( $missing_sizes[ $size_name ] );
+ continue;
+ }
+
+ // Provide what should be the file name.
+ list( , , , , $dst_w, $dst_h ) = $resize_result;
+ $missing_sizes[ $size_name ]['file'] = str_replace( '{%suffix%}', "{$dst_w}x{$dst_h}", $orig_f );
+ }
+
+ return $missing_sizes;
+ }
+
+ /**
+ * Fills statistics data with values from $data array.
+ *
+ * @since 1.0
+ * @since 1.6.5 Not static anymore.
+ * @since 1.6.6 Removed the attachment ID parameter.
+ * @since 1.7 Removed the image URL parameter.
+ * @access public
+ *
+ * @param array $data The statistics data.
+ * @param object $response The API response.
+ * @param string $size The attachment size key.
+ * @return bool|array False if the original size has an error or an array contains the data for other result.
+ */
+ abstract public function fill_data( $data, $response, $size = 'full' );
+
+ /**
+ * Optimize all sizes with Imagify.
+ *
+ * @since 1.0
+ * @access public
+ *
+ * @param int $optimization_level The optimization level (2=ultra, 1=aggressive, 0=normal).
+ * @param array $metadata The attachment meta data.
+ * @return array $optimized_data The optimization data.
+ */
+ abstract public function optimize( $optimization_level = null, $metadata = array() );
+
+ /**
+ * Optimize missing sizes with Imagify.
+ *
+ * @since 1.6.10
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param int $optimization_level The optimization level (2=ultra, 1=aggressive, 0=normal).
+ * @return array|object An array of thumbnail data, size by size. A WP_Error object on failure.
+ */
+ abstract public function optimize_missing_thumbnails( $optimization_level = null );
+
+ /**
+ * Re-optimize the given thumbnail sizes to the same level.
+ * Before doing this, the given sizes must be restored.
+ *
+ * @since 1.7.1
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param array $sizes The sizes to optimize.
+ * @return array|void A WP_Error object on failure.
+ */
+ abstract public function reoptimize_thumbnails( $sizes );
+
+ /**
+ * Process an attachment restoration from the backup file.
+ *
+ * @since 1.0
+ * @access public
+ *
+ * @return void
+ */
+ abstract public function restore();
+
+ /**
+ * Resize an image if bigger than the maximum width defined in the settings.
+ *
+ * @since 1.5.7
+ * @since 1.7.1 Keys for width and height in $attachment_sizes are now 'width' and 'height' instead of 0 and 1.
+ * @access public
+ * @author Remy Perona
+ *
+ * @param string $attachment_path Path to the image.
+ * @param array $attachment_sizes Array of original image dimensions.
+ * @param int $max_width Maximum width defined in the settings.
+ * @return string Path the the resized image or the original image if the resize failed.
+ */
+ public function resize( $attachment_path, $attachment_sizes, $max_width ) {
+ if ( ! $this->is_valid() || ! $this->is_image() ) {
+ return '';
+ }
+
+ $editor = $this->get_editor( $attachment_path );
+
+ if ( is_wp_error( $editor ) ) {
+ return $editor;
+ }
+
+ $new_sizes = wp_constrain_dimensions( $attachment_sizes['width'], $attachment_sizes['height'], $max_width );
+ $image_type = strtolower( (string) $this->filesystem->path_info( $attachment_path, 'extension' ) );
+
+ // Try to correct for auto-rotation if the info is available.
+ if ( $this->filesystem->can_get_exif() && ( 'jpg' === $image_type || 'jpe' === $image_type || 'jpeg' === $image_type ) ) {
+ $exif = $this->filesystem->get_image_exif( $attachment_path );
+ $orientation = isset( $exif['Orientation'] ) ? (int) $exif['Orientation'] : 1;
+
+ switch ( $orientation ) {
+ case 3:
+ $editor->rotate( 180 );
+ break;
+ case 6:
+ $editor->rotate( -90 );
+ break;
+ case 8:
+ $editor->rotate( 90 );
+ }
+ }
+
+ // Prevent removal of the exif data when resizing (only works with Imagick).
+ add_filter( 'image_strip_meta', '__return_false', 789 );
+
+ $resized = $editor->resize( $new_sizes[0], $new_sizes[1], false );
+
+ // Remove the filter when we're done to prevent any conflict.
+ remove_filter( 'image_strip_meta', '__return_false', 789 );
+
+ if ( is_wp_error( $resized ) ) {
+ return $resized;
+ }
+
+ $resized_image_path = $editor->generate_filename( 'imagifyresized' );
+ $resized_image_saved = $editor->save( $resized_image_path );
+
+ if ( is_wp_error( $resized_image_saved ) ) {
+ return $resized_image_saved;
+ }
+
+ return $resized_image_path;
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** WORKING STATUS ========================================================================== */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Tell if the file is currently being optimized (or restored, etc).
+ *
+ * @since 1.7.1
+ * @author Grégory Viguier
+ * @access public
+ *
+ * @return bool
+ */
+ public function is_running() {
+ $callback = $this->optimization_state_network_wide ? 'get_site_transient' : 'get_transient';
+
+ return false !== call_user_func( $callback, $this->optimization_state_transient );
+ }
+
+ /**
+ * Set the running status to "running" for 10 minutes.
+ *
+ * @since 1.7.1
+ * @author Grégory Viguier
+ * @access public
+ */
+ public function set_running_status() {
+ $callback = $this->optimization_state_network_wide ? 'set_site_transient' : 'set_transient';
+
+ call_user_func( $callback, $this->optimization_state_transient, true, 10 * MINUTE_IN_SECONDS );
+ }
+
+ /**
+ * Unset the running status.
+ *
+ * @since 1.7.1
+ * @author Grégory Viguier
+ * @access public
+ */
+ public function delete_running_status() {
+ $callback = $this->optimization_state_network_wide ? 'delete_site_transient' : 'delete_transient';
+
+ call_user_func( $callback, $this->optimization_state_transient );
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** DB ROW ================================================================================== */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Get the data row.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ * @access public
+ *
+ * @return array
+ */
+ public function get_row() {
+ if ( isset( $this->row ) ) {
+ return $this->row;
+ }
+
+ if ( ! $this->db_class_name || ! $this->is_valid() ) {
+ return $this->invalidate_row();
+ }
+
+ $this->row = $this->get_row_db_instance()->get( $this->id );
+
+ if ( ! $this->row ) {
+ return $this->invalidate_row();
+ }
+
+ return $this->row;
+ }
+
+ /**
+ * Update the data row.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ * @access public
+ *
+ * @param array $data The data to update.
+ */
+ public function update_row( $data ) {
+ if ( ! $this->db_class_name || ! $this->is_valid() ) {
+ return;
+ }
+
+ $this->get_row_db_instance()->update( $this->id, $data );
+
+ $this->reset_row_cache();
+ }
+
+ /**
+ * Delete the data row.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ * @access public
+ */
+ public function delete_row() {
+ if ( ! $this->db_class_name || ! $this->is_valid() ) {
+ return;
+ }
+
+ $this->get_row_db_instance()->delete( $this->id );
+
+ $this->invalidate_row();
+ }
+
+ /**
+ * Shorthand to get the DB table instance.
+ *
+ * @since 1.7.1
+ * @author Grégory Viguier
+ * @access public
+ *
+ * @return object The DB table instance.
+ */
+ public function get_row_db_instance() {
+ return call_user_func( array( $this->db_class_name, 'get_instance' ) );
+ }
+
+ /**
+ * Invalidate the row.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ * @access public
+ *
+ * @return array The row
+ */
+ public function invalidate_row() {
+ $this->row = array();
+ return $this->row;
+ }
+
+ /**
+ * Reset the row cache.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ * @access public
+ *
+ * @return null The row.
+ */
+ public function reset_row_cache() {
+ $this->row = null;
+ return $this->row;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/inc/deprecated/classes/class-imagify-abstract-db-deprecated.php b/wp/wp-content/plugins/imagify/inc/deprecated/classes/class-imagify-abstract-db-deprecated.php
new file mode 100644
index 00000000..9ee4a61e
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/deprecated/classes/class-imagify-abstract-db-deprecated.php
@@ -0,0 +1,48 @@
+imagify_auto_optimize_callback()' );
+
+ if ( empty( $_POST['_ajax_nonce'] ) || empty( $_POST['attachment_id'] ) || empty( $_POST['metadata'] ) || empty( $_POST['context'] ) ) { // WPCS: CSRF ok.
+ return;
+ }
+
+ $context = imagify_sanitize_context( $_POST['context'] );
+ $attachment_id = absint( $_POST['attachment_id'] );
+
+ imagify_check_nonce( 'new_media-' . $attachment_id );
+ imagify_check_user_capacity( 'auto-optimize' );
+
+ $attachment = get_imagify_attachment( $context, $attachment_id, 'imagify_async_optimize_upload_new_media' );
+
+ // Optimize it!!!!!
+ $attachment->optimize( null, $_POST['metadata'] );
+ die( 1 );
+ }
+
+ /**
+ * Optimize image on picture editing (resize, crop...) with async request.
+ *
+ * @since 1.6.11
+ * @since 1.8.4 Deprecated
+ * @access public
+ * @author Julio Potier
+ * @deprecated
+ */
+ public function imagify_async_optimize_save_image_editor_file_callback() {
+ _deprecated_function( get_class( $this ) . '::' . __FUNCTION__ . '()', '1.8.4', 'Imagify_Admin_Ajax_Post::get_instance()->imagify_auto_optimize_callback()' );
+
+ $attachment_id = ! empty( $_POST['postid'] ) ? absint( $_POST['postid'] ) : 0;
+
+ if ( ! $attachment_id || empty( $_POST['do'] ) ) {
+ return;
+ }
+
+ imagify_check_nonce( 'image_editor-' . $attachment_id );
+ imagify_check_user_capacity( 'edit_post', $attachment_id );
+
+ $attachment = get_imagify_attachment( 'wp', $attachment_id, 'wp_ajax_imagify_async_optimize_save_image_editor_file' );
+
+ if ( ! $attachment->get_data() ) {
+ return;
+ }
+
+ $optimization_level = $attachment->get_optimization_level();
+ $metadata = wp_get_attachment_metadata( $attachment_id );
+
+ // Remove old optimization data.
+ $attachment->delete_imagify_data();
+
+ if ( 'restore' === $_POST['do'] ) {
+ // Restore the backup file.
+ $attachment->restore();
+
+ // Get old metadata to regenerate all thumbnails.
+ $metadata = array( 'sizes' => array() );
+ $backup_sizes = (array) get_post_meta( $attachment_id, '_wp_attachment_backup_sizes', true );
+
+ foreach ( $backup_sizes as $size_key => $size_data ) {
+ $size_key = str_replace( '-origin', '' , $size_key );
+ $metadata['sizes'][ $size_key ] = $size_data;
+ }
+ }
+
+ // Optimize it!!!!!
+ $attachment->optimize( $optimization_level, $metadata );
+ die( 1 );
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** CUSTOM FOLDERS CALLBACKS ================================================================ */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Optimize a file.
+ *
+ * @since 1.7
+ * @since 1.9 Deprecated
+ * @access public
+ * @author Grégory Viguier
+ * @deprecated
+ */
+ public function imagify_bulk_optimize_file_callback() {
+ _deprecated_function( get_class( $this ) . '::' . __FUNCTION__ . '()', '1.9', '$this->imagify_bulk_optimize_callback()' );
+
+ imagify_check_nonce( 'imagify-bulk-upload' );
+ imagify_check_user_capacity( 'optimize-file' );
+
+ $file_id = filter_input( INPUT_POST, 'image', FILTER_VALIDATE_INT );
+ $context = imagify_sanitize_context( filter_input( INPUT_POST, 'context', FILTER_SANITIZE_STRING ) );
+ $context = ! $context || 'wp' === strtolower( $context ) ? 'File' : $context;
+
+ if ( ! $file_id ) {
+ imagify_die( __( 'Invalid request', 'imagify' ) );
+ }
+
+ $file = get_imagify_attachment( $context, $file_id, 'imagify_bulk_optimize_file' );
+
+ if ( ! $file->is_valid() ) {
+ imagify_die( __( 'Invalid file ID', 'imagify' ) );
+ }
+
+ // Restore before re-optimizing.
+ if ( false !== $file->get_optimization_level() ) {
+ $file->restore();
+ }
+
+ // Optimize it.
+ $result = $file->optimize( $this->get_optimization_level() );
+
+ // Return the optimization statistics.
+ if ( ! $file->is_optimized() ) {
+ $data = array(
+ 'success' => false,
+ 'error_code' => '',
+ 'error' => (string) $file->get_optimized_error(),
+ );
+
+ if ( ! $file->has_error() ) {
+ $data['error_code'] = 'already-optimized';
+ } else {
+ $message = 'You\'ve consumed all your data. You have to upgrade your account to continue';
+
+ if ( $data['error'] === $message ) {
+ $data['error_code'] = 'over-quota';
+ }
+ }
+
+ $data['error'] = imagify_translate_api_message( $data['error'] );
+
+ imagify_die( $data );
+ }
+
+ $data = $file->get_size_data();
+
+ wp_send_json_success( array(
+ 'success' => true,
+ 'original_size_human' => imagify_size_format( $data['original_size'], 2 ),
+ 'new_size_human' => imagify_size_format( $data['optimized_size'], 2 ),
+ 'overall_saving' => $data['original_size'] - $data['optimized_size'],
+ 'overall_saving_human' => imagify_size_format( $data['original_size'] - $data['optimized_size'], 2 ),
+ 'original_overall_size' => $data['original_size'],
+ 'original_overall_size_human' => imagify_size_format( $data['original_size'], 2 ),
+ 'new_overall_size' => $data['optimized_size'],
+ 'percent_human' => $data['percent'] . '%',
+ 'thumbnails' => $file->get_optimized_sizes_count(),
+ ) );
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** AUTOMATIC OPTIMIZATION ================================================================== */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Auto-optimize files.
+ *
+ * @since 1.8.4
+ * @since 1.9 Deprecated
+ * @access public
+ * @author Grégory Viguier
+ * @see Imagify_Auto_Optimization->do_auto_optimization()
+ * @deprecated
+ */
+ public function imagify_auto_optimize_callback() {
+ _deprecated_function( get_class( $this ) . '::' . __FUNCTION__ . '()', '1.9' );
+
+ if ( empty( $_POST['_ajax_nonce'] ) || empty( $_POST['attachment_id'] ) || empty( $_POST['context'] ) ) { // WPCS: CSRF ok.
+ imagify_die( __( 'Invalid request', 'imagify' ) );
+ }
+
+ $media_id = $this->get_media_id( 'POST' );
+
+ imagify_check_nonce( 'imagify_auto_optimize-' . $media_id );
+
+ if ( ! get_transient( 'imagify-auto-optimize-' . $media_id ) ) {
+ imagify_die();
+ }
+
+ delete_transient( 'imagify-auto-optimize-' . $media_id );
+
+ $context = $this->get_context( 'POST' );
+ $process = imagify_get_optimization_process( $media_id, $context );
+
+ if ( ! $process->is_valid() ) {
+ imagify_die( __( 'This media is not valid.', 'imagify' ) );
+ }
+
+ if ( ! $process->get_media()->is_supported() ) {
+ imagify_die( __( 'This type of file is not supported.', 'imagify' ) );
+ }
+
+ $this->check_can_optimize();
+
+ /**
+ * Let's start.
+ */
+ $is_new_upload = ! empty( $_POST['is_new_upload'] );
+
+ /**
+ * Triggered before a media is auto-optimized.
+ *
+ * @since 1.8.4
+ * @author Grégory Viguier
+ *
+ * @param int $media_id The media ID.
+ * @param bool $is_new_upload True if it's a new upload. False otherwize.
+ */
+ do_action( 'imagify_before_auto_optimization', $media_id, $is_new_upload );
+
+ if ( $is_new_upload ) {
+ /**
+ * It's a new upload.
+ */
+ // Optimize.
+ $process->optimize();
+ } else {
+ /**
+ * The media has already been optimized (or at least it has been tried).
+ */
+ $data = $process->get_data();
+
+ // Get the optimization level before deleting the optimization data.
+ $optimization_level = $data->get_optimization_level();
+
+ // Remove old optimization data.
+ $data->delete_imagify_data();
+
+ // Some specifics for the image editor.
+ if ( ! empty( $_POST['data']['do'] ) && 'restore' === $_POST['data']['do'] ) {
+ // Restore the backup file.
+ $process->restore();
+ }
+
+ // Optimize.
+ $process->optimize( $optimization_level );
+ }
+
+ /**
+ * Triggered after a media is auto-optimized.
+ *
+ * @since 1.8.4
+ * @author Grégory Viguier
+ *
+ * @param int $media_id The media ID.
+ * @param bool $is_new_upload True if it's a new upload. False otherwize.
+ */
+ do_action( 'imagify_after_auto_optimization', $media_id, $is_new_upload );
+ die( 1 );
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** VARIOUS FOR OPTIMIZATION ================================================================ */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Get all unoptimized attachment ids.
+ *
+ * @since 1.6.11
+ * @since 1.9 Deprecated
+ * @access public
+ * @author Jonathan Buttigieg
+ * @deprecated
+ */
+ public function imagify_get_unoptimized_attachment_ids_callback() {
+ global $wpdb;
+
+ _deprecated_function( get_class( $this ) . '::' . __FUNCTION__ . '()', '1.9', '$this->imagify_get_media_ids_callback()' );
+
+ imagify_check_nonce( 'imagify-bulk-upload' );
+ imagify_check_user_capacity( 'bulk-optimize' );
+ $this->check_can_optimize();
+
+ @set_time_limit( 0 );
+
+ // Get (ordered) IDs.
+ $optimization_level = $this->get_optimization_level();
+
+ $mime_types = Imagify_DB::get_mime_types();
+ $statuses = Imagify_DB::get_post_statuses();
+ $nodata_join = Imagify_DB::get_required_wp_metadata_join_clause();
+ $nodata_where = Imagify_DB::get_required_wp_metadata_where_clause( array(
+ 'prepared' => true,
+ ) );
+ $ids = $wpdb->get_col( $wpdb->prepare( // WPCS: unprepared SQL ok.
+ "
+ SELECT p.ID
+ FROM $wpdb->posts AS p
+ $nodata_join
+ LEFT JOIN $wpdb->postmeta AS mt1
+ ON ( p.ID = mt1.post_id AND mt1.meta_key = '_imagify_status' )
+ LEFT JOIN $wpdb->postmeta AS mt2
+ ON ( p.ID = mt2.post_id AND mt2.meta_key = '_imagify_optimization_level' )
+ WHERE
+ p.post_mime_type IN ( $mime_types )
+ AND (
+ mt1.meta_value = 'error'
+ OR
+ mt2.meta_value != %d
+ OR
+ mt2.post_id IS NULL
+ )
+ AND p.post_type = 'attachment'
+ AND p.post_status IN ( $statuses )
+ $nodata_where
+ GROUP BY p.ID
+ ORDER BY
+ CASE mt1.meta_value
+ WHEN 'already_optimized' THEN 2
+ ELSE 1
+ END ASC,
+ p.ID DESC
+ LIMIT 0, %d",
+ $optimization_level,
+ imagify_get_unoptimized_attachment_limit()
+ ) );
+
+ $wpdb->flush();
+ unset( $mime_types );
+ $ids = array_filter( array_map( 'absint', $ids ) );
+
+ if ( ! $ids ) {
+ wp_send_json_success( array() );
+ }
+
+ $results = Imagify_DB::get_metas( array(
+ // Get attachments filename.
+ 'filenames' => '_wp_attached_file',
+ // Get attachments data.
+ 'data' => '_imagify_data',
+ // Get attachments optimization level.
+ 'optimization_levels' => '_imagify_optimization_level',
+ // Get attachments status.
+ 'statuses' => '_imagify_status',
+ ), $ids );
+
+ // First run.
+ foreach ( $ids as $i => $id ) {
+ $attachment_status = isset( $results['statuses'][ $id ] ) ? $results['statuses'][ $id ] : false;
+ $attachment_optimization_level = isset( $results['optimization_levels'][ $id ] ) ? $results['optimization_levels'][ $id ] : false;
+ $attachment_error = '';
+
+ if ( isset( $results['data'][ $id ]['sizes']['full']['error'] ) ) {
+ $attachment_error = $results['data'][ $id ]['sizes']['full']['error'];
+ }
+
+ // Don't try to re-optimize if the optimization level is still the same.
+ if ( $optimization_level === $attachment_optimization_level && is_string( $attachment_error ) ) {
+ unset( $ids[ $i ] );
+ continue;
+ }
+
+ // Don't try to re-optimize images already compressed.
+ if ( 'already_optimized' === $attachment_status && $attachment_optimization_level >= $optimization_level ) {
+ unset( $ids[ $i ] );
+ continue;
+ }
+
+ $attachment_error = trim( $attachment_error );
+
+ // Don't try to re-optimize images with an empty error message.
+ if ( 'error' === $attachment_status && empty( $attachment_error ) ) {
+ unset( $ids[ $i ] );
+ }
+ }
+
+ if ( ! $ids ) {
+ wp_send_json_success( array() );
+ }
+
+ $ids = array_values( $ids );
+
+ /**
+ * Triggered before testing for file existence.
+ *
+ * @since 1.6.7
+ * @author Grégory Viguier
+ *
+ * @param array $ids An array of attachment IDs.
+ * @param array $results An array of the data fetched from the database.
+ * @param int $optimization_level The optimization level that will be used for the optimization.
+ */
+ do_action( 'imagify_bulk_optimize_before_file_existence_tests', $ids, $results, $optimization_level );
+
+ $data = array();
+
+ foreach ( $ids as $i => $id ) {
+ if ( empty( $results['filenames'][ $id ] ) ) {
+ // Problem.
+ continue;
+ }
+
+ $file_path = get_imagify_attached_file( $results['filenames'][ $id ] );
+
+ /** This filter is documented in inc/deprecated/deprecated.php. */
+ $file_path = apply_filters( 'imagify_file_path', $file_path );
+
+ if ( ! $file_path || ! $this->filesystem->exists( $file_path ) ) {
+ continue;
+ }
+
+ $attachment_backup_path = get_imagify_attachment_backup_path( $file_path );
+ $attachment_status = isset( $results['statuses'][ $id ] ) ? $results['statuses'][ $id ] : false;
+ $attachment_optimization_level = isset( $results['optimization_levels'][ $id ] ) ? $results['optimization_levels'][ $id ] : false;
+
+ // Don't try to re-optimize if there is no backup file.
+ if ( 'success' === $attachment_status && $optimization_level !== $attachment_optimization_level && ! $this->filesystem->exists( $attachment_backup_path ) ) {
+ continue;
+ }
+
+ $data[ '_' . $id ] = get_imagify_attachment_url( $results['filenames'][ $id ] );
+ } // End foreach().
+
+ if ( ! $data ) {
+ wp_send_json_success( array() );
+ }
+
+ wp_send_json_success( $data );
+ }
+
+ /**
+ * Get all unoptimized file ids.
+ *
+ * @since 1.7
+ * @since 1.9 Deprecated
+ * @access public
+ * @author Grégory Viguier
+ * @deprecated
+ */
+ public function imagify_get_unoptimized_file_ids_callback() {
+ _deprecated_function( get_class( $this ) . '::' . __FUNCTION__ . '()', '1.9', '$this->imagify_get_media_ids_callback()' );
+
+ imagify_check_nonce( 'imagify-bulk-upload' );
+ imagify_check_user_capacity( 'optimize-file' );
+
+ $this->check_can_optimize();
+
+ @set_time_limit( 0 );
+
+ $optimization_level = $this->get_optimization_level();
+
+ /**
+ * Get the folders from DB.
+ */
+ $folders = Imagify_Custom_Folders::get_folders( array(
+ 'active' => true,
+ ) );
+
+ if ( ! $folders ) {
+ wp_send_json_success( array() );
+ }
+
+ /**
+ * Triggered before getting file IDs.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ *
+ * @param array $folders An array of folders data.
+ * @param int $optimization_level The optimization level that will be used for the optimization.
+ */
+ do_action( 'imagify_bulk_optimize_files_before_get_files', $folders, $optimization_level );
+
+ /**
+ * Get the files from DB, and from the folders.
+ */
+ $files = Imagify_Custom_Folders::get_files_from_folders( $folders, array(
+ 'optimization_level' => $optimization_level,
+ ) );
+
+ if ( ! $files ) {
+ wp_send_json_success( array() );
+ }
+
+ // We need to output file URLs.
+ foreach ( $files as $k => $file ) {
+ $files[ $k ] = Imagify_Files_Scan::remove_placeholder( $file['path'], 'url' );
+ }
+
+ wp_send_json_success( $files );
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/inc/deprecated/classes/class-imagify-as3cf-attachment.php b/wp/wp-content/plugins/imagify/inc/deprecated/classes/class-imagify-as3cf-attachment.php
new file mode 100644
index 00000000..5bd60182
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/deprecated/classes/class-imagify-as3cf-attachment.php
@@ -0,0 +1,990 @@
+get_thumbnail_path();
+ }
+
+ /**
+ * Get a thumbnail path.
+ *
+ * @since 1.6.6
+ * @author Grégory Viguier
+ *
+ * @param string $size_file The basename of the file. If not provided, the path to the main file is returned.
+ * @return string|bool Path to the file if it exists or has been successfully retrieved from S3. False on failure.
+ */
+ public function get_thumbnail_path( $size_file = false ) {
+ if ( ! $this->is_valid() ) {
+ return '';
+ }
+
+ $file_path = get_attached_file( $this->id, true );
+
+ if ( $size_file ) {
+ // It's not the full size.
+ $file_path = $this->filesystem->dir_path( $file_path ) . $size_file;
+ }
+
+ return $file_path;
+ }
+
+ /**
+ * Get the original attachment URL.
+ *
+ * @since 1.6.6
+ * @author Grégory Viguier
+ *
+ * @return string|bool The main file URL. False on failure.
+ */
+ public function get_original_url() {
+ return $this->get_thumbnail_url();
+ }
+
+ /**
+ * Get a thumbnail URL.
+ *
+ * @since 1.6.6
+ * @author Grégory Viguier
+ *
+ * @param string $size_file The basename of the file. If not provided, the main file's URL is returned.
+ * @return string|bool The file URL. False on failure.
+ */
+ public function get_thumbnail_url( $size_file = false ) {
+ if ( ! $this->is_extension_supported() ) {
+ return false;
+ }
+
+ $file_url = wp_get_attachment_url( $this->id );
+
+ if ( $size_file ) {
+ // It's not the full size.
+ $file_url = $this->filesystem->dir_path( $file_url ) . $size_file;
+ }
+
+ return $file_url;
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** THE PUBLIC STUFF ======================================================================== */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Optimize all sizes with Imagify.
+ *
+ * @since 1.6.6
+ * @author Grégory Viguier
+ *
+ * @param int $optimization_level The optimization level (2 = ultra, 1 = aggressive, 0 = normal).
+ * @param array $metadata The attachment meta data, containing the sizes. Provide only for a new attachment.
+ * @return array|bool The optimization data. False on failure.
+ */
+ public function optimize( $optimization_level = null, $metadata = array() ) {
+ $metadata_changed = false;
+
+ /**
+ * Make some sanity tests first.
+ */
+
+ // Check if the attachment extension is allowed.
+ if ( ! $this->is_extension_supported() ) {
+ return false;
+ }
+
+ // To avoid issue with "original_size" at 0 in "_imagify_data".
+ if ( 0 === (int) $this->get_stats_data( 'original_size' ) ) {
+ $this->delete_imagify_data();
+ }
+
+ $optimization_level = isset( $optimization_level ) ? (int) $optimization_level : get_imagify_option( 'optimization_level' );
+
+ // Check if the full size is already optimized with this level.
+ if ( $this->is_optimized() && $this->get_optimization_level() === $optimization_level ) {
+ return false;
+ }
+
+ // Get file path of the full size.
+ $attachment_path = $this->get_original_path();
+ $attachment_url = $this->get_original_url();
+
+ if ( ! $attachment_path ) {
+ // We're in deep sh**.
+ return false;
+ }
+
+ if ( ! $this->filesystem->exists( $attachment_path ) && ! $this->get_file_from_s3( $attachment_path ) ) {
+ // The file doesn't exist and couldn't be retrieved from S3.
+ return false;
+ }
+
+ /**
+ * Start the process.
+ */
+ $this->set_running_status();
+
+ /** This hook is documented in /inc/classes/class-imagify-attachment.php. */
+ do_action( 'before_imagify_optimize_attachment', $this->id );
+
+ $metadata = $this->set_deletion_status( $metadata );
+
+ // Store the paths of the files that may be deleted once optimized and sent to S3.
+ $to_delete = array();
+ $filesize_total = 0;
+
+ // Maybe resize (and backup) the image.
+ $resized = $this->is_image() && $this->maybe_resize( $attachment_path );
+
+ if ( $resized ) {
+ $size = $this->filesystem->get_image_size( $attachment_path );
+
+ if ( $size ) {
+ $metadata['width'] = $size['width'];
+ $metadata['height'] = $size['height'];
+ $metadata_changed = true;
+ }
+ }
+
+ // Optimize the full size.
+ $response = do_imagify( $attachment_path, array(
+ 'optimization_level' => $optimization_level,
+ 'context' => 'wp',
+ 'resized' => $resized,
+ 'original_size' => $this->get_original_size( false ),
+ ) );
+
+ $data = $this->fill_data( null, $response );
+
+ if ( $this->delete_files ) {
+ $to_delete[] = $attachment_path;
+ // This is used by AS3CF.
+ $bytes = $this->filesystem->size( $attachment_path );
+
+ if ( false !== $bytes ) {
+ $metadata_changed = true;
+ $filesize_total += $bytes;
+ $metadata['filesize'] = $bytes;
+ } else {
+ $metadata['filesize'] = 0;
+ }
+ }
+
+ /** This filter is documented in /inc/classes/class-imagify-attachment.php. */
+ $data = apply_filters( 'imagify_fill_full_size_data', $data, $response, $this->id, $attachment_path, $attachment_url, 'full', $optimization_level, $metadata );
+
+ // Save the optimization level.
+ update_post_meta( $this->id, '_imagify_optimization_level', $optimization_level );
+
+ if ( ! $data ) {
+ // The optimization failed.
+ $metadata = $metadata_changed ? $metadata : false;
+ $this->cleanup( $metadata, $to_delete );
+ return false;
+ }
+
+ // Optimize all thumbnails.
+ if ( ! empty( $metadata['sizes'] ) ) {
+ $disallowed_sizes = get_imagify_option( 'disallowed-sizes' );
+ $is_active_for_network = imagify_is_active_for_network();
+
+ foreach ( $metadata['sizes'] as $size_key => $size_data ) {
+ $thumbnail_path = $this->get_thumbnail_path( $size_data['file'] );
+ $thumbnail_url = $this->get_thumbnail_url( $size_data['file'] );
+
+ if ( $this->delete_files ) {
+ $to_delete[] = $thumbnail_path;
+
+ // Even if this size must not be optimized ($disallowed_sizes), we must fetch the file from S3 to get its size, and not to trigger a `WP_Error` in `upload_attachment_to_s3()`.
+ if ( ! $this->filesystem->exists( $thumbnail_path ) && ! $this->get_file_from_s3( $thumbnail_path ) ) {
+ // Doesn't exist and couldn't be retrieved from S3.
+ $data['sizes'][ $size_key ] = array(
+ 'success' => false,
+ 'error' => __( 'This size could not be retrieved from Amazon S3.', 'imagify' ),
+ );
+ continue;
+ }
+
+ // This is used by AS3CF.
+ $bytes = $this->filesystem->size( $thumbnail_path );
+
+ if ( false !== $bytes ) {
+ $filesize_total += $bytes;
+ }
+ }
+
+ // Check if this size has to be optimized.
+ if ( ! $is_active_for_network && isset( $disallowed_sizes[ $size_key ] ) && $this->is_image() ) {
+ $data['sizes'][ $size_key ] = array(
+ 'success' => false,
+ 'error' => __( 'This size is not authorized to be optimized. Update your Imagify settings if you want to optimize it.', 'imagify' ),
+ );
+
+ /** This filter is documented in /inc/classes/class-imagify-attachment.php. */
+ $data = apply_filters( 'imagify_fill_unauthorized_thumbnail_data', $data, $this->id, $thumbnail_path, $thumbnail_url, $size_key, $optimization_level, $metadata );
+ continue;
+ }
+
+ if ( ! $this->delete_files && ! $this->filesystem->exists( $thumbnail_path ) && ! $this->get_file_from_s3( $thumbnail_path ) ) {
+ // Doesn't exist and couldn't be retrieved from S3.
+ $data['sizes'][ $size_key ] = array(
+ 'success' => false,
+ 'error' => __( 'This size could not be retrieved from Amazon S3.', 'imagify' ),
+ );
+ continue;
+ }
+
+ if ( ! $this->is_image() ) {
+ continue;
+ }
+
+ // Optimize the thumbnail size.
+ $response = do_imagify( $thumbnail_path, array(
+ 'backup' => false,
+ 'optimization_level' => $optimization_level,
+ 'context' => 'wp',
+ ) );
+
+ $data = $this->fill_data( $data, $response, $size_key );
+
+ /** This filter is documented in /inc/classes/class-imagify-attachment.php. */
+ $data = apply_filters( 'imagify_fill_thumbnail_data', $data, $response, $this->id, $thumbnail_path, $thumbnail_url, $size_key, $optimization_level, $metadata );
+ } // End foreach().
+ } // End if().
+
+ $data['stats']['percent'] = round( ( ( $data['stats']['original_size'] - $data['stats']['optimized_size'] ) / $data['stats']['original_size'] ) * 100, 2 );
+
+ update_post_meta( $this->id, '_imagify_data', $data );
+ update_post_meta( $this->id, '_imagify_status', 'success' );
+
+ if ( $this->delete_files && $filesize_total ) {
+ // Add the total file size for all image sizes. This is a meta used by AS3CF.
+ update_post_meta( $this->id, 'wpos3_filesize_total', $filesize_total );
+ }
+
+ $optimized_data = $this->get_data();
+
+ /** This hook is documented in /inc/classes/class-imagify-attachment.php. */
+ do_action( 'after_imagify_optimize_attachment', $this->id, $optimized_data );
+
+ $sent = $this->maybe_send_attachment_to_s3( $metadata, $attachment_path );
+ // Update metadata only if they changed.
+ $metadata = $metadata_changed ? $metadata : false;
+ // Delete files only if they have been uploaded to S3.
+ $to_delete = $sent ? $to_delete : array();
+
+ $this->cleanup( $metadata, $to_delete );
+
+ return $optimized_data;
+ }
+
+ /**
+ * Optimize missing thumbnail sizes with Imagify.
+ *
+ * @since 1.6.10
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param int $optimization_level The optimization level (2=ultra, 1=aggressive, 0=normal).
+ * @return array|object An array of thumbnail data, size by size. A WP_Error object on failure.
+ */
+ public function optimize_missing_thumbnails( $optimization_level = null ) {
+ // Check if the attachment extension is allowed.
+ if ( ! $this->is_extension_supported() || ! $this->is_image() ) {
+ return new WP_Error( 'mime_type_not_supported', __( 'This type of file is not supported.', 'imagify' ) );
+ }
+
+ /**
+ * Create missing thumbnails and optimize them.
+ */
+ $result = parent::optimize_missing_thumbnails( $optimization_level );
+ $result_sizes = array();
+
+ $this->set_running_status();
+
+ if ( is_array( $result ) ) {
+ // All good.
+ $result_sizes = $result;
+ } elseif ( is_wp_error( $result ) ) {
+ // Some thumbnails could not be created. Lets see if some were.
+ $result_sizes = $result->get_error_data( 'image_resize_error' );
+ $result_sizes = ! empty( $result_sizes['sizes_succeeded'] ) ? $result_sizes['sizes_succeeded'] : array();
+ }
+
+ if ( ! $result_sizes ) {
+ // No thumbnails created.
+ $this->delete_running_status();
+ return $result;
+ }
+
+ /**
+ * Fetch all images from S3 if they're not on the server.
+ * S3 Offload needs ALL images (so it can update its metas), we can't just send some of them without entering Hell -_-'.
+ */
+ $metadata = $this->set_deletion_status();
+
+ if ( ! $this->can_send_to_s3() ) {
+ // The other thumbnails are not on S3, so we don't need to send the new ones.
+ $this->delete_running_status();
+ return $result;
+ }
+
+ /**
+ * The main file.
+ */
+ $attachment_path = $this->get_original_path();
+ $to_delete = array();
+ $to_skip = array();
+ $filesize_total = 0;
+ $metadata_changed = false;
+
+ if ( ! $attachment_path ) {
+ // WAT?!
+ if ( ! is_wp_error( $result ) ) {
+ $result = new WP_Error( 'no_attachment_path', __( 'Files could not be sent to Amazon S3.', 'imagify' ), array(
+ 'sizes_succeeded' => $result_sizes,
+ ) );
+ } else {
+ $result->add( 'no_attachment_path', __( 'Files could not be sent to Amazon S3.', 'imagify' ) );
+ }
+
+ $this->delete_running_status();
+ return $result;
+ }
+
+ if ( ! $this->filesystem->exists( $attachment_path ) && ! $this->get_file_from_s3( $attachment_path ) ) {
+ // The file doesn't exist and couldn't be retrieved from S3.
+ if ( ! is_wp_error( $result ) ) {
+ $result = new WP_Error( 'main_file_not_on_s3', __( 'The main image could not be retrieved from Amazon S3.', 'imagify' ), array(
+ 'sizes_succeeded' => $result_sizes,
+ ) );
+ } else {
+ $result->add( 'main_file_not_on_s3', __( 'The main image could not be retrieved from Amazon S3.', 'imagify' ) );
+ }
+
+ $this->delete_running_status();
+ return $result;
+ }
+
+ // Files that must not be retrieved from S3.
+ foreach ( $result_sizes as $size_key => $size_data ) {
+ $to_skip[] = $this->get_thumbnail_path( $size_data['file'] );
+ }
+
+ // Store the paths of the files that may be deleted once sent to S3.
+ if ( $this->delete_files ) {
+ $to_delete[] = $attachment_path;
+ $to_delete = array_merge( $to_delete, $to_skip );
+
+ // This is used by AS3CF.
+ $bytes = $this->filesystem->size( $attachment_path );
+
+ if ( false !== $bytes ) {
+ $metadata_changed = true;
+ $filesize_total += $bytes;
+ $metadata['filesize'] = $bytes;
+ } elseif ( ! isset( $metadata['filesize'] ) ) {
+ $metadata_changed = true;
+ $metadata['filesize'] = 0;
+ }
+ }
+
+ /**
+ * The thumbnails.
+ */
+ if ( ! empty( $metadata['sizes'] ) ) {
+ $to_skip = array_flip( $to_skip );
+
+ foreach ( $metadata['sizes'] as $size_key => $size_data ) {
+ $thumbnail_path = $this->get_thumbnail_path( $size_data['file'] );
+
+ if ( isset( $to_skip[ $thumbnail_path ] ) ) {
+ continue;
+ }
+
+ if ( ! $this->filesystem->exists( $thumbnail_path ) && ! $this->get_file_from_s3( $thumbnail_path ) ) {
+ // The file doesn't exist and couldn't be retrieved from S3.
+ if ( ! is_wp_error( $result ) ) {
+ $result = new WP_Error( 'thumbnail_not_on_s3', __( 'This size could not be retrieved from Amazon S3.', 'imagify' ), array(
+ 'sizes_succeeded' => $result_sizes,
+ 'size' => $size_key,
+ ) );
+ } else {
+ $result->add( 'thumbnail_not_on_s3', __( 'This size could not be retrieved from Amazon S3.', 'imagify' ), array(
+ 'size' => $size_key,
+ ) );
+ }
+
+ $this->delete_running_status();
+ return $result;
+ }
+
+ if ( $this->delete_files ) {
+ $to_delete[] = $thumbnail_path;
+
+ // This is used by AS3CF.
+ $bytes = $this->filesystem->size( $thumbnail_path );
+
+ if ( false !== $bytes ) {
+ $filesize_total += $bytes;
+ }
+ }
+ } // End foreach().
+ } // End if().
+
+ if ( $this->delete_files && $filesize_total ) {
+ // Add the total file size for all image sizes. This is a meta used by AS3CF.
+ update_post_meta( $this->id, 'wpos3_filesize_total', $filesize_total );
+ }
+
+ $sent = $this->maybe_send_attachment_to_s3( $metadata, $attachment_path );
+ // Update metadata only if they changed.
+ $metadata = $metadata_changed ? $metadata : false;
+ // Delete files only if they have been uploaded to S3.
+ $to_delete = $sent ? $to_delete : array();
+
+ $this->cleanup( $metadata, $to_delete );
+
+ return $result;
+ }
+
+ /**
+ * Re-optimize the given thumbnail sizes to the same level.
+ * Not supported yet in this context.
+ *
+ * @since 1.7.1
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param array $sizes The sizes to optimize.
+ * @return array|void A WP_Error object on failure.
+ */
+ public function reoptimize_thumbnails( $sizes ) {}
+
+ /**
+ * Process an attachment restoration from the backup file.
+ *
+ * @since 1.6.6
+ * @author Grégory Viguier
+ *
+ * @return array A list of files sent to S3.
+ */
+ public function restore() {
+ // Check if the attachment extension is allowed.
+ if ( ! $this->is_extension_supported() ) {
+ return false;
+ }
+
+ // Stop the process if there is no backup file to restore.
+ if ( ! $this->has_backup() ) {
+ return false;
+ }
+
+ /** This hook is documented in /inc/classes/class-imagify-attachment.php. */
+ do_action( 'before_imagify_restore_attachment', $this->id );
+
+ $backup_path = $this->get_backup_path();
+ $attachment_path = $this->get_original_path();
+
+ if ( ! $attachment_path ) {
+ return false;
+ }
+
+ // Create the original image from the backup.
+ $this->filesystem->copy( $backup_path, $attachment_path, true );
+ $this->filesystem->chmod_file( $attachment_path );
+
+ if ( ! $this->filesystem->exists( $attachment_path ) ) {
+ return false;
+ }
+
+ $this->set_deletion_status();
+
+ // Remove old optimization data.
+ $this->delete_imagify_data();
+
+ if ( ! $this->is_image() ) {
+ // We need to delete the thumbnails for pdf, or new ones will be generated with new unique file names.
+ $metadata = wp_get_attachment_metadata( $this->id );
+
+ if ( ! empty( $metadata['sizes'] ) && is_array( $metadata['sizes'] ) ) {
+ foreach ( $metadata['sizes'] as $size_key => $size_data ) {
+ $thumbnail_path = $this->get_thumbnail_path( $size_data['file'] );
+
+ if ( $this->filesystem->exists( $thumbnail_path ) ) {
+ $this->filesystem->delete( $thumbnail_path );
+ }
+ }
+ }
+ }
+
+ if ( ! function_exists( 'wp_generate_attachment_metadata' ) ) {
+ require_once ABSPATH . 'wp-admin/includes/image.php';
+ }
+
+ // Generate new thumbnails and new metadata.
+ $metadata = wp_generate_attachment_metadata( $this->id, $attachment_path );
+
+ // Send to S3.
+ $sent = $this->maybe_send_attachment_to_s3( $metadata, $attachment_path );
+ // Files restored (and maybe to delete).
+ $files = array();
+ // If the files must be deleted, we need to store the file sizes.
+ $filesize_total = 0;
+
+ if ( $sent ) {
+ $files[] = $attachment_path;
+ }
+
+ if ( $this->delete_files ) {
+ // This is used by AS3CF.
+ $bytes = $this->filesystem->size( $attachment_path );
+
+ if ( false !== $bytes ) {
+ $filesize_total += $bytes;
+ $metadata['filesize'] = $bytes;
+ } else {
+ $metadata['filesize'] = 0;
+ }
+ }
+
+ if ( ! empty( $metadata['sizes'] ) && ( $sent || $this->delete_files ) ) {
+ foreach ( $metadata['sizes'] as $size_key => $size_data ) {
+ $thumbnail_path = $this->get_thumbnail_path( $size_data['file'] );
+
+ if ( $sent ) {
+ $files[] = $thumbnail_path;
+ }
+
+ if ( $this->delete_files ) {
+ // This is used by AS3CF.
+ $bytes = $this->filesystem->size( $thumbnail_path );
+
+ if ( false !== $bytes ) {
+ $filesize_total += $bytes;
+ }
+ }
+ }
+ }
+
+ if ( $this->delete_files && $filesize_total ) {
+ // Add the total file size for all image sizes. This is a meta used by AS3CF.
+ update_post_meta( $this->id, 'wpos3_filesize_total', $filesize_total );
+ }
+
+ /** This hook is documented in /inc/classes/class-imagify-attachment.php. */
+ do_action( 'after_imagify_restore_attachment', $this->id );
+
+ $to_delete = $this->delete_files ? $files : array();
+
+ $this->cleanup( $metadata, $to_delete );
+
+ return $files;
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** INTERNAL UTILITIES ====================================================================== */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Cleanup after optimization or a restore:
+ * - Maybe update metadata.
+ * - Maybe delete local files.
+ * - Delete the "optimization status" transient.
+ *
+ * @since 1.6.6
+ * @author Grégory Viguier
+ *
+ * @param array $new_metadata New attachment metadata to be stored.
+ * @param array $files_to_remove Files to delete.
+ */
+ protected function cleanup( $new_metadata, $files_to_remove ) {
+ if ( $new_metadata ) {
+ /**
+ * Filter the metadata stored after optimization or a restore.
+ *
+ * @since 1.6.6
+ * @author Grégory Viguier
+ *
+ * @param array $new_metadata New attachment metadata to be stored.
+ * @param int $id The attachment ID.
+ */
+ $new_metadata = apply_filters( 'imagify_as3cf_attachment_cleanup_metadata', $new_metadata, $this->id );
+ /**
+ * Update the attachment meta that contains the file sizes.
+ * Here we don't use wp_update_attachment_metadata() to prevent triggering unwanted hooks.
+ */
+ update_post_meta( $this->id, '_wp_attachment_metadata', $new_metadata );
+ }
+
+ if ( $files_to_remove ) {
+ $attachment_path = $this->get_original_path();
+ /** This filter is documented in /amazon-s3-and-cloudfront/classes/amazon-s3-and-cloudfront.php. */
+ $files_to_remove = (array) apply_filters( 'as3cf_upload_attachment_local_files_to_remove', $files_to_remove, $this->id, $attachment_path );
+ $files_to_remove = array_filter( $files_to_remove );
+
+ if ( $files_to_remove ) {
+ $files_to_remove = array_unique( $files_to_remove );
+ /**
+ * Delete the local files.
+ */
+ array_map( array( $this, 'maybe_delete_file' ), $files_to_remove );
+ }
+ }
+
+ /**
+ * Delete the "optimization status" transient.
+ */
+ $this->delete_running_status();
+ }
+
+ /**
+ * Maybe resize (and backup) an image.
+ *
+ * @since 1.6.6
+ * @author Grégory Viguier
+ *
+ * @param string $attachment_path The file path.
+ * @return bool True on success. False on failure.
+ */
+ protected function maybe_resize( $attachment_path ) {
+ if ( ! $this->is_image() ) {
+ return false;
+ }
+
+ $do_resize = get_imagify_option( 'resize_larger' );
+ $resize_width = get_imagify_option( 'resize_larger_w' );
+ $attachment_size = $this->filesystem->get_image_size( $attachment_path );
+
+ if ( ! $do_resize || ! $attachment_size || $resize_width >= $attachment_size['width'] ) {
+ return false;
+ }
+
+ $resized_attachment_path = $this->resize( $attachment_path, $attachment_size, $resize_width );
+
+ if ( is_wp_error( $resized_attachment_path ) ) {
+ return false;
+ }
+
+ $backuped = imagify_backup_file( $attachment_path );
+
+ if ( is_wp_error( $backuped ) ) {
+ return false;
+ }
+
+ return $this->filesystem->move( $resized_attachment_path, $attachment_path, true );
+ }
+
+ /**
+ * Tell if the files must be deleted after being optimized or restored.
+ * It sets the 2 properties $this->use_s3_settings and $this->delete_files.
+ *
+ * @since 1.6.6
+ * @author Grégory Viguier
+ *
+ * @param array $metadata Attachment metadata. Provide, only if it comes from a 'wp_generate_attachment_metadata' or 'wp_update_attachment_metadata' hook.
+ * @return array Attachment metadata. If not provided as argument, new values are fetched.
+ */
+ protected function set_deletion_status( $metadata = false ) {
+ global $as3cf;
+
+ if ( $metadata ) {
+ /**
+ * Metadata is provided: we were in a 'wp_generate_attachment_metadata' or 'wp_update_attachment_metadata' hook.
+ * This means we'll follow AS3CF settings to know if the local files must be sent to S3 and/or deleted.
+ */
+ $this->use_s3_settings = true;
+ $this->delete_files = $as3cf && $as3cf->get_setting( 'remove-local-file' ) && $this->can_send_to_s3();
+
+ return $metadata;
+ }
+
+ /**
+ * Metadata is not provided: we were not in a 'wp_generate_attachment_metadata' or 'wp_update_attachment_metadata' hook.
+ * So, we fetch the current meta value.
+ * This also means we won't follow AS3CF settings to know if the local files must be sent to S3 and/or deleted.
+ * In that case we'll send the files to S3 if they already are there, and delete them if they is a 'filesize' entry in the metadata.
+ */
+ $metadata = wp_get_attachment_metadata( $this->id, true );
+ $this->use_s3_settings = false;
+ $this->delete_files = isset( $metadata['filesize'] ) && $this->can_send_to_s3();
+
+ return $metadata;
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** S3 UTILITIES ============================================================================ */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Tell if AS3CF is set up.
+ *
+ * @since 1.6.6
+ * @author Grégory Viguier
+ *
+ * @return bool
+ */
+ public function is_s3_setup() {
+ global $as3cf;
+ static $is;
+
+ if ( ! isset( $is ) ) {
+ $is = $as3cf && $as3cf->is_plugin_setup();
+ }
+
+ return $is;
+ }
+
+ /**
+ * Tell if an attachment is stored on S3.
+ *
+ * @since 1.6.6
+ * @author Grégory Viguier
+ *
+ * @return array|bool The S3 info on success. False if the attachment is not on S3.
+ */
+ public function get_s3_info() {
+ global $as3cf;
+
+ if ( ! $as3cf ) {
+ return false;
+ }
+
+ if ( method_exists( $as3cf, 'get_attachment_s3_info' ) ) {
+ return $as3cf->get_attachment_s3_info( $this->id );
+ }
+
+ return $as3cf->get_attachment_provider_info( $this->id );
+ }
+
+ /**
+ * Get a file from S3.
+ *
+ * @since 1.6.6
+ * @author Grégory Viguier
+ *
+ * @param string $file_path The file path.
+ * @return string|bool The file path on success, false on failure.
+ */
+ protected function get_file_from_s3( $file_path ) {
+ global $as3cf;
+
+ if ( ! $this->is_extension_supported() ) {
+ return false;
+ }
+
+ if ( ! $this->is_s3_setup() ) {
+ return false;
+ }
+
+ $s3_object = $this->get_s3_info();
+
+ if ( ! $s3_object ) {
+ // The attachment is not on S3.
+ return false;
+ }
+
+ $directory = $this->filesystem->dir_path( $s3_object['key'] );
+ $directory = $this->filesystem->is_root( $directory ) ? '' : $directory;
+ $s3_object['key'] = $directory . $this->filesystem->file_name( $file_path );
+
+ // Retrieve file from S3.
+ if ( method_exists( $as3cf->plugin_compat, 'copy_s3_file_to_server' ) ) {
+ $as3cf->plugin_compat->copy_s3_file_to_server( $s3_object, $file_path );
+ } else {
+ $as3cf->plugin_compat->copy_provider_file_to_server( $s3_object, $file_path );
+ }
+
+ return $this->filesystem->exists( $file_path ) ? $file_path : false;
+ }
+
+ /**
+ * Maybe send the attachment to S3.
+ *
+ * @since 1.6.6
+ * @author Grégory Viguier
+ *
+ * @param array $metadata The attachment metadata.
+ * @param string $attachment_path The attachment path.
+ * @param bool $remove_local_files True to let AS3CF delete the local files (if set in the settings). We usually don't want that, we do it by ourselves.
+ * @return bool True on success. False otherwize.
+ */
+ protected function maybe_send_attachment_to_s3( $metadata = null, $attachment_path = null, $remove_local_files = false ) {
+ global $as3cf;
+
+ if ( ! $this->can_send_to_s3() ) {
+ return false;
+ }
+
+ $s3_object = $this->get_s3_info();
+
+ if ( ! $s3_object ) {
+ return false;
+ }
+
+ $full_file_path = $this->get_original_path();
+
+ if ( ! $full_file_path ) {
+ // This is bad.
+ return false;
+ }
+
+ if ( method_exists( $as3cf, 'upload_attachment_to_s3' ) ) {
+ $s3_data = $as3cf->upload_attachment_to_s3( $this->id, $metadata, $attachment_path, false, $remove_local_files );
+ } else {
+ $s3_data = $as3cf->upload_attachment( $this->id, $metadata, $attachment_path, false, $remove_local_files );
+ }
+
+ return ! is_wp_error( $s3_data );
+ }
+
+ /**
+ * Tell if an attachment can be sent to S3.
+ *
+ * @since 1.6.6
+ * @author Grégory Viguier
+ *
+ * @return bool
+ */
+ protected function can_send_to_s3() {
+ global $as3cf;
+ static $can = array();
+ static $copy_to_s3;
+
+ if ( isset( $can[ $this->id ] ) ) {
+ return $can[ $this->id ];
+ }
+
+ if ( ! isset( $copy_to_s3 ) ) {
+ $copy_to_s3 = $as3cf && $as3cf->get_setting( 'copy-to-s3' );
+ }
+
+ $is_s3_setup = $this->is_s3_setup();
+ $s3_object = $this->get_s3_info();
+ // S3 is set up and the attachment is on S3.
+ $can[ $this->id ] = $is_s3_setup && $s3_object;
+
+ if ( $can[ $this->id ] && ! empty( $this->use_s3_settings ) ) {
+ // Use AS3CF setting to tell if we're allowed to send the files.
+ $can[ $this->id ] = $copy_to_s3;
+ }
+
+ /**
+ * Filter the result of Imagify_AS3CF_Attachment::can_send_to_s3().
+ *
+ * @since 1.6.6
+ * @author Grégory Viguier
+ *
+ * @param bool $can True if the attachment can be sent. False otherwize.
+ * @param int $id The attachment ID.
+ * @param array $s3_object The S3 infos.
+ * @param bool $is_s3_setup AS3CF is set up or not.
+ * @param bool $copy_to_s3 AS3CF setting that tells if a "new" attachment can be sent.
+ * @param bool $use_s3_settings Tell if we must use AS3CF setting in this case.
+ */
+ $can[ $this->id ] = (bool) apply_filters( 'imagify_can_send_to_s3', $can[ $this->id ], $this->id, $s3_object, $is_s3_setup, $copy_to_s3, $this->use_s3_settings );
+
+ return $can[ $this->id ];
+ }
+
+ /**
+ * Maybe delete the local file.
+ *
+ * @since 1.6.6
+ * @author Grégory Viguier
+ *
+ * @param string $file_path The file path.
+ * @return bool True if deleted or doesn't exist. False on failure or if the file is not supposed to be deleted.
+ */
+ protected function maybe_delete_file( $file_path ) {
+ if ( ! $this->file_should_be_deleted( $file_path ) ) {
+ return false;
+ }
+
+ if ( ! $this->filesystem->exists( $file_path ) ) {
+ return true;
+ }
+
+ return $this->filesystem->delete( $file_path, false, 'f' );
+ }
+
+ /**
+ * Tell if a file should be deleted.
+ *
+ * @since 1.6.6
+ * @author Grégory Viguier
+ *
+ * @param string $file_path The file path.
+ * @return bool True to delete, false to keep.
+ */
+ protected function file_should_be_deleted( $file_path ) {
+ if ( ! $file_path || ! $this->delete_files ) {
+ // We keep the file.
+ return false;
+ }
+
+ /** This hook is documented in /amazon-s3-and-cloudfront/classes/amazon-s3-and-cloudfront.php. */
+ $preserve = apply_filters( 'as3cf_preserve_file_from_local_removal', false, $file_path );
+
+ return false === $preserve;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/inc/deprecated/classes/class-imagify-as3cf-deprecated.php b/wp/wp-content/plugins/imagify/inc/deprecated/classes/class-imagify-as3cf-deprecated.php
new file mode 100644
index 00000000..ed813426
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/deprecated/classes/class-imagify-as3cf-deprecated.php
@@ -0,0 +1,313 @@
+is_plugin_setup() ) {
+ return;
+ }
+
+ // Remove from the list files that exist.
+ $ids = array_flip( $ids );
+
+ foreach ( $ids as $id => $i ) {
+ if ( empty( $results['filenames'][ $id ] ) ) {
+ // Problem.
+ unset( $ids[ $id ] );
+ continue;
+ }
+
+ $file_path = get_imagify_attached_file( $results['filenames'][ $id ] );
+
+ /** This filter is documented in inc/deprecated/deprecated.php. */
+ $file_path = apply_filters( 'imagify_file_path', $file_path, $id, 'as3cf_maybe_copy_files_from_s3' );
+
+ if ( ! $file_path || $this->filesystem->exists( $file_path ) ) {
+ // The file exists, no need to retrieve it from S3.
+ unset( $ids[ $id ] );
+ } else {
+ $ids[ $id ] = $file_path;
+ }
+ }
+
+ if ( ! $ids ) {
+ // All files are already on the server.
+ return;
+ }
+
+ // Determine which files are on S3.
+ $ids = array_flip( $ids );
+ $sql_ids = implode( ',', $ids );
+
+ $s3_data = $wpdb->get_results( // WPCS: unprepared SQL ok.
+ "SELECT pm.post_id as id, pm.meta_value as value
+ FROM $wpdb->postmeta as pm
+ WHERE pm.meta_key = 'amazonS3_info'
+ AND pm.post_id IN ( $sql_ids )
+ ORDER BY pm.post_id DESC",
+ ARRAY_A
+ );
+
+ $wpdb->flush();
+
+ if ( ! $s3_data ) {
+ return;
+ }
+
+ unset( $sql_ids );
+ $s3_data = Imagify_DB::combine_query_results( $ids, $s3_data, true );
+
+ // Retrieve the missing files from S3.
+ $ids = array_flip( $ids );
+
+ foreach ( $s3_data as $id => $s3_object ) {
+ $s3_object = maybe_unserialize( $s3_object );
+ $file_path = $ids[ $id ];
+
+ $attachment_backup_path = get_imagify_attachment_backup_path( $file_path );
+ $attachment_status = isset( $results['statuses'][ $id ] ) ? $results['statuses'][ $id ] : false;
+ $attachment_optimization_level = isset( $results['optimization_levels'][ $id ] ) ? $results['optimization_levels'][ $id ] : false;
+
+ // Don't try to re-optimize if there is no backup file.
+ if ( 'success' === $attachment_status && $optimization_level !== $attachment_optimization_level && ! $this->filesystem->exists( $attachment_backup_path ) ) {
+ unset( $s3_data[ $id ], $ids[ $id ] );
+ continue;
+ }
+
+ $directory = $this->filesystem->dir_path( $s3_object['key'] );
+ $directory = $this->filesystem->is_root( $directory ) ? '' : $directory;
+ $s3_object['key'] = $directory . $this->filesystem->file_name( $file_path );
+
+ // Retrieve file from S3.
+ if ( method_exists( $as3cf->plugin_compat, 'copy_s3_file_to_server' ) ) {
+ $as3cf->plugin_compat->copy_s3_file_to_server( $s3_object, $file_path );
+ } else {
+ $as3cf->plugin_compat->copy_provider_file_to_server( $s3_object, $file_path );
+ }
+
+ unset( $s3_data[ $id ], $ids[ $id ] );
+ }
+ }
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** AUTOMATIC OPTIMIZATION: OPTIMIZE AFTER S3 HAS DONE ITS WORK ============================= */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Filter the generated attachment meta data.
+ * This is used when a new attachment has just been uploaded (or not, when wp_generate_attachment_metadata() is used).
+ * We use it to tell the difference later in wp_update_attachment_metadata().
+ *
+ * @since 1.6.6
+ * @since 1.8.4 Deprecated
+ * @author Grégory Viguier
+ * @see $this->do_async_job()
+ * @deprecated
+ *
+ * @param array $metadata An array of attachment meta data.
+ * @param int $attachment_id Current attachment ID.
+ * @return array
+ */
+ public function store_upload_ids( $metadata, $attachment_id ) {
+ _deprecated_function( get_class( $this ) . '::' . __FUNCTION__ . '()', '1.8.4' );
+
+ if ( imagify_is_attachment_mime_type_supported( $attachment_id ) ) {
+ $this->uploads[ $attachment_id ] = 1;
+ }
+
+ return $metadata;
+ }
+
+ /**
+ * After an image (maybe) being sent to S3, launch an async optimization.
+ *
+ * @since 1.6.6
+ * @since 1.8.4 Deprecated
+ * @author Grégory Viguier
+ * @see $this->store_upload_ids()
+ * @deprecated
+ *
+ * @param array $metadata An array of attachment meta data.
+ * @param int $attachment_id Current attachment ID.
+ * @return array
+ */
+ public function do_async_job( $metadata, $attachment_id ) {
+ static $auto_optimize;
+
+ _deprecated_function( get_class( $this ) . '::' . __FUNCTION__ . '()', '1.8.4' );
+
+ $is_new_upload = ! empty( $this->uploads[ $attachment_id ] );
+ unset( $this->uploads[ $attachment_id ] );
+
+ if ( ! $metadata || ! imagify_is_attachment_mime_type_supported( $attachment_id ) ) {
+ return $metadata;
+ }
+
+ if ( ! isset( $auto_optimize ) ) {
+ $auto_optimize = Imagify_Requirements::is_api_key_valid() && get_imagify_option( 'auto_optimize' );
+ }
+
+ if ( $is_new_upload ) {
+ // It's a new upload.
+ if ( ! $auto_optimize ) {
+ // Auto-optimization is disabled.
+ return $metadata;
+ }
+
+ /** This filter is documented in inc/common/attachments.php. */
+ $optimize = apply_filters( 'imagify_auto_optimize_attachment', true, $attachment_id, $metadata );
+
+ if ( ! $optimize ) {
+ return $metadata;
+ }
+ }
+
+ if ( ! $is_new_upload ) {
+ $attachment = get_imagify_attachment( self::CONTEXT, $attachment_id, 'as3cf_async_job' );
+
+ if ( ! $attachment->get_data() ) {
+ // It's not a new upload and the attachment is not optimized yet.
+ return $metadata;
+ }
+ }
+
+ $data = array();
+
+ // Some specifics for the image editor.
+ if ( isset( $_POST['action'], $_POST['do'], $_POST['postid'] ) && 'image-editor' === $_POST['action'] && (int) $_POST['postid'] === $attachment_id ) { // WPCS: CSRF ok.
+ check_ajax_referer( 'image_editor-' . $_POST['postid'] );
+ $data = $_POST;
+ }
+
+ imagify_do_async_job( array(
+ 'action' => 'imagify_async_optimize_as3cf',
+ '_ajax_nonce' => wp_create_nonce( 'imagify_async_optimize_as3cf' ),
+ 'post_id' => $attachment_id,
+ 'metadata' => $metadata,
+ 'data' => $data,
+ ) );
+
+ return $metadata;
+ }
+
+ /**
+ * Once an image has been sent to S3, optimize it and send it again.
+ *
+ * @since 1.6.6
+ * @since 1.8.4 Deprecated
+ * @author Grégory Viguier
+ * @deprecated
+ */
+ public function optimize() {
+ _deprecated_function( get_class( $this ) . '::' . __FUNCTION__ . '()', '1.8.4' );
+
+ check_ajax_referer( 'imagify_async_optimize_as3cf' );
+
+ if ( empty( $_POST['post_id'] ) || ! imagify_current_user_can( 'auto-optimize' ) ) {
+ die();
+ }
+
+ $attachment_id = absint( $_POST['post_id'] );
+
+ if ( ! $attachment_id || empty( $_POST['metadata'] ) || ! is_array( $_POST['metadata'] ) || empty( $_POST['metadata']['sizes'] ) ) {
+ die();
+ }
+
+ if ( ! imagify_is_attachment_mime_type_supported( $attachment_id ) ) {
+ die();
+ }
+
+ $optimization_level = null;
+ $attachment = get_imagify_attachment( self::CONTEXT, $attachment_id, 'as3cf_optimize' );
+
+ // Some specifics for the image editor.
+ if ( ! empty( $_POST['data']['do'] ) ) {
+ $optimization_level = $attachment->get_optimization_level();
+
+ // Remove old optimization data.
+ $attachment->delete_imagify_data();
+
+ if ( 'restore' === $_POST['data']['do'] ) {
+ // Restore the backup file.
+ $attachment->restore();
+ }
+ }
+
+ // Optimize it.
+ $attachment->optimize( $optimization_level, $_POST['metadata'] );
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/inc/deprecated/classes/class-imagify-assets-deprecated.php b/wp/wp-content/plugins/imagify/inc/deprecated/classes/class-imagify-assets-deprecated.php
new file mode 100644
index 00000000..ed1e5670
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/deprecated/classes/class-imagify-assets-deprecated.php
@@ -0,0 +1,104 @@
+is_intercom ) || empty( $user->display_support ) ) {
+ return;
+ }
+ ?>
+
+ scripts[ $handle ] ) ) {
+ // If we registered it, it's one of our scripts.
+ $handle = self::JS_PREFIX . $handle;
+ }
+
+ $wp_scripts = wp_scripts();
+ $dependencies = $wp_scripts->query( $handle );
+
+ if ( ! $dependencies || ! $dependencies->deps ) {
+ return;
+ }
+
+ $dependencies = array_flip( $dependencies->deps );
+
+ if ( ! isset( $dependencies['heartbeat'] ) ) {
+ return;
+ }
+
+ $suffix = SCRIPT_DEBUG ? '' : '.min';
+ $depts = [ 'jquery' ];
+
+ if ( version_compare( $wp_version, '5.0.0' ) >= 0 ) {
+ $depts[] = 'wp-hooks';
+ }
+
+ wp_register_script( 'heartbeat', "/wp-includes/js/heartbeat$suffix.js", $depts, false, true ); // phpcs:ignore WordPress.WP.EnqueuedResourceParameters.NoExplicitVersion
+
+ if ( $wp_scripts->get_data( 'heartbeat', 'data' ) ) {
+ return;
+ }
+
+ /** This filter is documented in /wp-includes/script-loader.php */
+ $data = apply_filters( 'heartbeat_settings', [] );
+
+ if ( empty( $data['nonce'] ) ) {
+ $data = wp_heartbeat_settings( $data );
+ }
+
+ wp_localize_script( 'heartbeat', 'heartbeatSettings', $data );
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/inc/deprecated/classes/class-imagify-attachment.php b/wp/wp-content/plugins/imagify/inc/deprecated/classes/class-imagify-attachment.php
new file mode 100644
index 00000000..34315bad
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/deprecated/classes/class-imagify-attachment.php
@@ -0,0 +1,850 @@
+get_original_path() );
+ }
+
+ /**
+ * Get the attachment optimization data.
+ *
+ * @since 1.0
+ * @access public
+ *
+ * @return array
+ */
+ public function get_data() {
+ $data = get_post_meta( $this->id, '_imagify_data', true );
+ return is_array( $data ) ? $data : array();
+ }
+
+ /**
+ * Get the attachment optimization level.
+ *
+ * @since 1.0
+ * @access public
+ *
+ * @return int
+ */
+ public function get_optimization_level() {
+ $level = get_post_meta( $this->id, '_imagify_optimization_level', true );
+ return false !== $level ? (int) $level : false;
+ }
+
+ /**
+ * Get the attachment optimization status (success or error).
+ *
+ * @since 1.0
+ * @access public
+ *
+ * @return string
+ */
+ public function get_status() {
+ $status = get_post_meta( $this->id, '_imagify_status', true );
+ return is_string( $status ) ? $status : '';
+ }
+
+ /**
+ * Get the original attachment path.
+ *
+ * @since 1.0
+ * @access public
+ *
+ * @return string
+ */
+ public function get_original_path() {
+ return get_attached_file( $this->id );
+ }
+
+ /**
+ * Get the original attachment URL.
+ *
+ * @since 1.0
+ * @access public
+ *
+ * @return string
+ */
+ public function get_original_url() {
+ return wp_get_attachment_url( $this->id );
+ }
+
+ /**
+ * Get width and height of the original image.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ * @access public
+ *
+ * @return array
+ */
+ public function get_dimensions() {
+ if ( ! $this->is_image() ) {
+ return parent::get_dimensions();
+ }
+
+ $values = wp_get_attachment_image_src( $this->id, 'full' );
+
+ return array(
+ 'width' => $values[1],
+ 'height' => $values[2],
+ );
+ }
+
+ /**
+ * Update the metadata size of the attachment.
+ *
+ * @since 1.2
+ * @access public
+ *
+ * @return bool
+ */
+ public function update_metadata_size() {
+ // Check if the attachment extension is allowed.
+ if ( ! $this->is_extension_supported() || ! $this->is_image() ) {
+ return false;
+ }
+
+ $size = $this->filesystem->get_image_size( $this->get_original_path() );
+
+ if ( ! $size ) {
+ return false;
+ }
+
+ /**
+ * Triggered before updating an image width and height into its metadata.
+ *
+ * @since 1.8.4
+ * @see Imagify_Filesystem->get_image_size()
+ * @author Grégory Viguier
+ *
+ * @param int $attachment_id The attachment ID.
+ * @param array $size {
+ * An array with, among other data:
+ *
+ * @type int $width The image width.
+ * @type int $height The image height.
+ * }
+ */
+ do_action( 'before_imagify_update_metadata_size', $this->id, $size );
+
+ $metadata = wp_get_attachment_metadata( $this->id );
+ $metadata['width'] = $size['width'];
+ $metadata['height'] = $size['height'];
+
+ wp_update_attachment_metadata( $this->id, $metadata );
+
+ /**
+ * Triggered after updating an image width and height into its metadata.
+ *
+ * @since 1.8.4
+ * @see Imagify_Filesystem->get_image_size()
+ * @author Grégory Viguier
+ *
+ * @param int $attachment_id The attachment ID.
+ * @param array $size {
+ * An array with, among other data:
+ *
+ * @type int $width The image width.
+ * @type int $height The image height.
+ * }
+ */
+ do_action( 'after_imagify_update_metadata_size', $this->id, $size );
+
+ return true;
+ }
+
+ /**
+ * Fills statistics data with values from $data array.
+ *
+ * @since 1.0
+ * @since 1.6.5 Not static anymore.
+ * @since 1.6.6 Removed the attachment ID parameter.
+ * @since 1.7 Removed the image URL parameter.
+ * @access public
+ *
+ * @param array $data The statistics data.
+ * @param object $response The API response.
+ * @param string $size The attachment size key.
+ * @return bool|array False if the original size has an error or an array contains the data for other result.
+ */
+ public function fill_data( $data, $response, $size = 'full' ) {
+ $data = is_array( $data ) ? $data : array();
+ $data['sizes'] = ! empty( $data['sizes'] ) && is_array( $data['sizes'] ) ? $data['sizes'] : array();
+
+ if ( empty( $data['stats'] ) ) {
+ $data['stats'] = array(
+ 'original_size' => 0,
+ 'optimized_size' => 0,
+ 'percent' => 0,
+ );
+ }
+
+ if ( is_wp_error( $response ) ) {
+ $error = $response->get_error_message();
+ $error_status = 'error';
+
+ $data['sizes'][ $size ] = array(
+ 'success' => false,
+ 'error' => $error,
+ );
+
+ // Update the error status for the original size.
+ if ( 'full' === $size ) {
+ update_post_meta( $this->id, '_imagify_data', $data );
+
+ if ( false !== strpos( $error, 'This image is already compressed' ) ) {
+ $error_status = 'already_optimized';
+ }
+
+ update_post_meta( $this->id, '_imagify_status', $error_status );
+
+ return false;
+ }
+ } else {
+ $response = (object) array_merge( array(
+ 'original_size' => 0,
+ 'new_size' => 0,
+ 'percent' => 0,
+ ), (array) $response );
+
+ $data['sizes'][ $size ] = array(
+ 'success' => true,
+ 'original_size' => $response->original_size,
+ 'optimized_size' => $response->new_size,
+ 'percent' => $response->percent,
+ );
+
+ $data['stats']['original_size'] += $response->original_size;
+ $data['stats']['optimized_size'] += $response->new_size;
+ } // End if().
+
+ return $data;
+ }
+
+ /**
+ * Create a thumbnail if it doesn't exist.
+ *
+ * @since 1.6.10
+ * @access protected
+ * @author Grégory Viguier
+ *
+ * @param array $thumbnail_data The thumbnail data (width, height, crop, name, file).
+ * @return bool|array|object True if the file exists. An array of thumbnail data if the file has just been created (width, height, crop, file). A WP_Error object on error.
+ */
+ protected function create_thumbnail( $thumbnail_data ) {
+ $thumbnail_size = $thumbnail_data['name'];
+ $metadata = wp_get_attachment_metadata( $this->id );
+ $metadata_sizes = ! empty( $metadata['sizes'] ) && is_array( $metadata['sizes'] ) ? $metadata['sizes'] : array();
+
+ $original_dirname = $this->filesystem->dir_path( $this->get_original_path() );
+ $thumbnail_path = $original_dirname . $thumbnail_data['file'];
+
+ if ( ! empty( $metadata_sizes[ $thumbnail_size ] ) && $this->filesystem->exists( $thumbnail_path ) ) {
+ $this->filesystem->chmod_file( $thumbnail_path );
+ return true;
+ }
+
+ // Get the editor.
+ $editor = $this->get_editor( $this->get_backup_path() );
+
+ if ( is_wp_error( $editor ) ) {
+ return $editor;
+ }
+
+ // Create the file.
+ $result = $editor->multi_resize( array( $thumbnail_size => $thumbnail_data ) );
+
+ if ( ! $result ) {
+ return new WP_Error( 'image_resize_error' );
+ }
+
+ // The file name can change from what we expected (1px wider, etc).
+ $backup_dirname = $this->filesystem->dir_path( $this->get_backup_path() );
+ $backup_thumb_path = $backup_dirname . $result[ $thumbnail_size ]['file'];
+ $thumbnail_path = $original_dirname . $result[ $thumbnail_size ]['file'];
+
+ // Since we used the backup image as source, the new image is still in the backup folder, we need to move it.
+ $moved = $this->filesystem->move( $backup_thumb_path, $thumbnail_path, true );
+
+ if ( ! $moved ) {
+ return new WP_Error( 'image_resize_error' );
+ }
+
+ return reset( $result );
+ }
+
+ /**
+ * Create all missing thumbnails if they don't exist and update the attachment metadata.
+ *
+ * @since 1.6.10
+ * @access protected
+ * @author Grégory Viguier
+ *
+ * @param array $missing_sizes An array of thumbnail data (width, height, crop, name, file) for each thumbnail size.
+ * @return array An array of thumbnail data (width, height, crop, file).
+ */
+ protected function create_missing_thumbnails( $missing_sizes ) {
+ if ( ! $missing_sizes || ! $this->is_image() ) {
+ return array();
+ }
+
+ $metadata = wp_get_attachment_metadata( $this->id );
+ $metadata['sizes'] = ! empty( $metadata['sizes'] ) && is_array( $metadata['sizes'] ) ? $metadata['sizes'] : array();
+ $thumbnail_new_datas = array();
+ $thumbnail_metadatas = array();
+
+ // Create the missing thumbnails.
+ foreach ( $missing_sizes as $size_name => $thumbnail_data ) {
+ $result = $this->create_thumbnail( $thumbnail_data );
+
+ if ( is_array( $result ) ) {
+ // New file.
+ $thumbnail_new_datas[ $size_name ] = $result;
+ unset( $thumbnail_new_datas[ $size_name ]['name'] );
+ } elseif ( true === $result ) {
+ // The file already exists.
+ $thumbnail_metadatas[ $size_name ] = $metadata['sizes'][ $size_name ];
+ }
+ }
+
+ // Save the new data into the attachment metadata.
+ if ( $thumbnail_new_datas ) {
+ $metadata['sizes'] = array_merge( $metadata['sizes'], $thumbnail_new_datas );
+
+ /**
+ * Here we don't use wp_update_attachment_metadata() to prevent triggering unwanted hooks.
+ */
+ update_post_meta( $this->id, '_wp_attachment_metadata', $metadata );
+ }
+
+ return array_merge( $thumbnail_metadatas, $thumbnail_new_datas );
+ }
+
+ /**
+ * Optimize all sizes with Imagify.
+ *
+ * @since 1.0
+ * @access public
+ *
+ * @param int $optimization_level The optimization level (2=ultra, 1=aggressive, 0=normal).
+ * @param array $metadata The attachment meta data.
+ * @return array $optimized_data The optimization data.
+ */
+ public function optimize( $optimization_level = null, $metadata = array() ) {
+ // Check if the attachment extension is allowed.
+ if ( ! $this->is_extension_supported() ) {
+ return;
+ }
+
+ $optimization_level = isset( $optimization_level ) ? (int) $optimization_level : get_imagify_option( 'optimization_level' );
+ $metadata = $metadata ? $metadata : wp_get_attachment_metadata( $this->id );
+ $sizes = ! empty( $metadata['sizes'] ) && is_array( $metadata['sizes'] ) && $this->is_image() ? $metadata['sizes'] : array();
+
+ // To avoid issue with "original_size" at 0 in "_imagify_data".
+ if ( 0 === (int) $this->get_stats_data( 'original_size' ) ) {
+ $this->delete_imagify_data();
+ }
+
+ // Check if the full size is already optimized.
+ if ( $this->is_optimized() && $this->get_optimization_level() === $optimization_level ) {
+ return;
+ }
+
+ // Get file path & URL for original image.
+ $attachment_path = $this->get_original_path();
+ $attachment_url = $this->get_original_url();
+ $attachment_original_size = $this->get_original_size( false );
+
+ /**
+ * Fires before optimizing an attachment.
+ *
+ * @since 1.0
+ *
+ * @param int $id The attachment ID.
+ */
+ do_action( 'before_imagify_optimize_attachment', $this->id );
+
+ $this->set_running_status();
+
+ // Get the resize values for the original size.
+ $resized = false;
+ $do_resize = $this->is_image() && get_imagify_option( 'resize_larger' );
+
+ if ( $do_resize ) {
+ $resize_width = get_imagify_option( 'resize_larger_w' );
+ $attachment_size = $this->filesystem->get_image_size( $attachment_path );
+
+ if ( $attachment_size && $resize_width < $attachment_size['width'] ) {
+ $resized_attachment_path = $this->resize( $attachment_path, $attachment_size, $resize_width );
+
+ if ( ! is_wp_error( $resized_attachment_path ) ) {
+ // TODO (@Greg): Send an error message if the backup fails.
+ imagify_backup_file( $attachment_path );
+
+ $this->filesystem->move( $resized_attachment_path, $attachment_path, true );
+
+ $resized = true;
+ }
+ }
+ }
+
+ // Optimize the original size.
+ $response = do_imagify( $attachment_path, array(
+ 'optimization_level' => $optimization_level,
+ 'context' => $this->get_context(),
+ 'resized' => $resized,
+ 'original_size' => $attachment_original_size,
+ ) );
+
+ $data = $this->fill_data( null, $response );
+
+ /**
+ * Filter the optimization data of the full size.
+ *
+ * @since 1.8
+ * @author Grégory Viguier
+ *
+ * @param array $data The statistics data.
+ * @param object $response The API response.
+ * @param int $id The attachment ID.
+ * @param string $attachment_path The attachment path.
+ * @param string $attachment_url The attachment URL.
+ * @param string $size_key The attachment size key. The value is obviously 'full' but it's kept for concistancy with other filters.
+ * @param int $optimization_level The optimization level.
+ * @param array $metadata WP metadata.
+ */
+ $data = apply_filters( 'imagify_fill_full_size_data', $data, $response, $this->id, $attachment_path, $attachment_url, 'full', $optimization_level, $metadata );
+
+ // Save the optimization level.
+ update_post_meta( $this->id, '_imagify_optimization_level', $optimization_level );
+
+ // If we resized the original with success, we have to update the attachment metadata.
+ // If not, WordPress keeps the old attachment size.
+ if ( $resized ) {
+ $this->update_metadata_size();
+ }
+
+ if ( ! $data ) {
+ $this->delete_running_status();
+ return;
+ }
+
+ // Optimize all thumbnails.
+ if ( $sizes ) {
+ $disallowed_sizes = get_imagify_option( 'disallowed-sizes' );
+ $is_active_for_network = imagify_is_active_for_network();
+ $attachment_path_dirname = $this->filesystem->dir_path( $attachment_path );
+ $attachment_url_dirname = $this->filesystem->dir_path( $attachment_url );
+
+ foreach ( $sizes as $size_key => $size_data ) {
+ $thumbnail_path = $attachment_path_dirname . $size_data['file'];
+ $thumbnail_url = $attachment_url_dirname . $size_data['file'];
+
+ // Check if this size has to be optimized.
+ if ( ! $is_active_for_network && isset( $disallowed_sizes[ $size_key ] ) ) {
+ $data['sizes'][ $size_key ] = array(
+ 'success' => false,
+ 'error' => __( 'This size is not authorized to be optimized. Update your Imagify settings if you want to optimize it.', 'imagify' ),
+ );
+
+ /**
+ * Filter the optimization data of an unauthorized thumbnail.
+ *
+ * @since 1.8
+ * @author Grégory Viguier
+ *
+ * @param array $data The statistics data.
+ * @param int $id The attachment ID.
+ * @param string $thumbnail_path The thumbnail path.
+ * @param string $thumbnail_url The thumbnail URL.
+ * @param string $size_key The thumbnail size key.
+ * @param int $optimization_level The optimization level.
+ * @param array $metadata WP metadata.
+ */
+ $data = apply_filters( 'imagify_fill_unauthorized_thumbnail_data', $data, $this->id, $thumbnail_path, $thumbnail_url, $size_key, $optimization_level, $metadata );
+ continue;
+ }
+
+ // Optimize the thumbnail size.
+ $response = do_imagify( $thumbnail_path, array(
+ 'backup' => false,
+ 'optimization_level' => $optimization_level,
+ 'context' => $this->get_context(),
+ ) );
+
+ $data = $this->fill_data( $data, $response, $size_key );
+
+ /**
+ * Filter the optimization data of a specific thumbnail.
+ *
+ * @since 1.0
+ * @since 1.8 Added $metadata.
+ *
+ * @param array $data The statistics data.
+ * @param object $response The API response.
+ * @param int $id The attachment ID.
+ * @param string $thumbnail_path The thumbnail path.
+ * @param string $thumbnail_url The thumbnail URL.
+ * @param string $size_key The thumbnail size key.
+ * @param int $optimization_level The optimization level.
+ * @param array $metadata WP metadata.
+ */
+ $data = apply_filters( 'imagify_fill_thumbnail_data', $data, $response, $this->id, $thumbnail_path, $thumbnail_url, $size_key, $optimization_level, $metadata );
+ } // End foreach().
+ } // End if().
+
+ $data['stats']['percent'] = round( ( ( $data['stats']['original_size'] - $data['stats']['optimized_size'] ) / $data['stats']['original_size'] ) * 100, 2 );
+
+ update_post_meta( $this->id, '_imagify_data', $data );
+ update_post_meta( $this->id, '_imagify_status', 'success' );
+
+ $optimized_data = $this->get_data();
+
+ /**
+ * Fires after optimizing an attachment.
+ *
+ * @since 1.0
+ *
+ * @param int $id The attachment ID.
+ * @param array $optimized_data The optimization data.
+ */
+ do_action( 'after_imagify_optimize_attachment', $this->id, $optimized_data );
+
+ $this->delete_running_status();
+
+ return $optimized_data;
+ }
+
+ /**
+ * Optimize missing thumbnail sizes with Imagify.
+ *
+ * @since 1.6.10
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param int $optimization_level The optimization level (2=ultra, 1=aggressive, 0=normal).
+ * @return array|object An array of thumbnail data, size by size. A WP_Error object on failure.
+ */
+ public function optimize_missing_thumbnails( $optimization_level = null ) {
+ // Check if the attachment extension is allowed.
+ if ( ! $this->is_extension_supported() || ! $this->is_image() ) {
+ return new WP_Error( 'mime_type_not_supported', __( 'This type of file is not supported.', 'imagify' ) );
+ }
+
+ $optimization_level = isset( $optimization_level ) ? (int) $optimization_level : get_imagify_option( 'optimization_level' );
+ $missing_sizes = $this->get_unoptimized_sizes();
+
+ if ( ! $missing_sizes ) {
+ // We have everything we need.
+ return array();
+ }
+
+ // Stop the process if there is no backup file to use.
+ if ( ! $this->has_backup() ) {
+ return new WP_Error( 'no_backup', __( 'This file has no backup file.', 'imagify' ) );
+ }
+
+ /**
+ * Fires before optimizing the missing thumbnails.
+ *
+ * @since 1.6.10
+ * @author Grégory Viguier
+ * @see $this->get_unoptimized_sizes()
+ *
+ * @param int $id The attachment ID.
+ * @param array $missing_sizes An array of the missing sizes.
+ */
+ do_action( 'before_imagify_optimize_missing_thumbnails', $this->id, $missing_sizes );
+
+ $this->set_running_status();
+
+ $errors = new WP_Error();
+
+ // Create the missing thumbnails.
+ $result_sizes = $this->create_missing_thumbnails( $missing_sizes );
+ $failed_sizes = array_diff_key( $missing_sizes, $result_sizes );
+
+ if ( $failed_sizes ) {
+ $failed_count = count( $failed_sizes );
+ /* translators: %d is a number of thumbnails. */
+ $error_message = _n( '%d thumbnail failed to be created', '%d thumbnails failed to be created', $failed_count, 'imagify' );
+ $error_message = sprintf( $error_message, $failed_count );
+
+ $errors->add( 'image_resize_error', $error_message, array(
+ 'nbr_failed' => $failed_count,
+ 'sizes_failed' => $failed_sizes,
+ 'sizes_succeeded' => $result_sizes,
+ ) );
+ }
+
+ if ( ! $result_sizes ) {
+ $this->delete_running_status();
+ return $errors;
+ }
+
+ // Optimize.
+ $imagify_data = $this->get_data();
+ $original_dirname = $this->filesystem->dir_path( $this->get_original_path() );
+ $orig_url_dirname = $this->filesystem->dir_path( $this->get_original_url() );
+
+ foreach ( $result_sizes as $size_name => $thumbnail_data ) {
+ $thumbnail_path = $original_dirname . $thumbnail_data['file'];
+ $thumbnail_url = $orig_url_dirname . $thumbnail_data['file'];
+
+ // Optimize the thumbnail size.
+ $response = do_imagify( $thumbnail_path, array(
+ 'backup' => false,
+ 'optimization_level' => $optimization_level,
+ 'context' => $this->get_context(),
+ ) );
+
+ $imagify_data = $this->fill_data( $imagify_data, $response, $size_name );
+ $metadata = wp_get_attachment_metadata( $this->id );
+
+ /** This filter is documented in inc/classes/class-imagify-attachment.php. */
+ $imagify_data = apply_filters( 'imagify_fill_thumbnail_data', $imagify_data, $response, $this->id, $thumbnail_path, $thumbnail_url, $size_name, $optimization_level, $metadata );
+ }
+
+ // Save Imagify data.
+ $imagify_data['stats']['percent'] = round( ( ( $imagify_data['stats']['original_size'] - $imagify_data['stats']['optimized_size'] ) / $imagify_data['stats']['original_size'] ) * 100, 2 );
+
+ update_post_meta( $this->id, '_imagify_data', $imagify_data );
+
+ /**
+ * Fires after optimizing the missing thumbnails.
+ *
+ * @since 1.6.10
+ * @author Grégory Viguier
+ * @see $this->create_missing_thumbnails()
+ *
+ * @param int $id The attachment ID.
+ * @param array $result_sizes An array of created thumbnails.
+ * @param object $errors A WP_Error object that stores thumbnail creation failures.
+ */
+ do_action( 'after_imagify_optimize_missing_thumbnails', $this->id, $result_sizes, $errors );
+
+ $this->delete_running_status();
+
+ // Return the result.
+ if ( $errors->get_error_codes() ) {
+ return $errors;
+ }
+
+ return $result_sizes;
+ }
+
+ /**
+ * Re-optimize the given thumbnail sizes to the same level.
+ * Before doing this, the given sizes must be restored.
+ *
+ * @since 1.7.1
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param array $sizes The sizes to optimize.
+ * @return array|void A WP_Error object on failure.
+ */
+ public function reoptimize_thumbnails( $sizes ) {
+ // Check if the attachment extension is allowed.
+ if ( ! $this->is_extension_supported() || ! $this->is_image() ) {
+ return new WP_Error( 'mime_type_not_supported', __( 'This type of file is not supported.', 'imagify' ) );
+ }
+
+ if ( ! $sizes || ! is_array( $sizes ) ) {
+ return;
+ }
+
+ /**
+ * Fires before re-optimizing some thumbnails of an attachment.
+ *
+ * @since 1.7.1
+ * @author Grégory Viguier
+ *
+ * @param int $id The attachment ID.
+ * @param array $sizes The sizes to optimize.
+ */
+ do_action( 'before_imagify_reoptimize_attachment_thumbnails', $this->id, $sizes );
+
+ $this->set_running_status();
+
+ $data = $this->get_data();
+
+ $data['sizes'] = ! empty( $data['sizes'] ) && is_array( $data['sizes'] ) ? $data['sizes'] : array();
+
+ foreach ( $sizes as $size_key => $size_data ) {
+ // In case it's a disallowed size, fill in the new data. If it's not, it will be overwritten by $this->fill_data() later.
+ $data['sizes'][ $size_key ] = array(
+ 'success' => false,
+ 'error' => __( 'This size is not authorized to be optimized. Update your Imagify settings if you want to optimize it.', 'imagify' ),
+ );
+ }
+
+ // Update global attachment stats.
+ $data['stats'] = array(
+ 'original_size' => 0,
+ 'optimized_size' => 0,
+ 'percent' => 0,
+ );
+
+ foreach ( $data['sizes'] as $size_data ) {
+ if ( ! empty( $size_data['original_size'] ) ) {
+ $data['stats']['original_size'] += $size_data['original_size'];
+ }
+ if ( ! empty( $size_data['optimized_size'] ) ) {
+ $data['stats']['optimized_size'] += $size_data['optimized_size'];
+ }
+ }
+
+ // Remove disallowed sizes.
+ if ( ! imagify_is_active_for_network() ) {
+ $sizes = array_diff_key( $sizes, get_imagify_option( 'disallowed-sizes' ) );
+ }
+
+ if ( ! $sizes ) {
+ $data['stats']['percent'] = $data['stats']['original_size'] ? round( ( ( $data['stats']['original_size'] - $data['stats']['optimized_size'] ) / $data['stats']['original_size'] ) * 100, 2 ) : 0;
+ update_post_meta( $this->id, '_imagify_data', $data );
+ $this->delete_running_status();
+ return;
+ }
+
+ $optimization_level = $this->get_optimization_level();
+ $thumbnail_path = $this->get_original_path();
+ $thumbnail_url = $this->get_original_url();
+ $attachment_path_dirname = $this->filesystem->dir_path( $thumbnail_path );
+ $attachment_url_dirname = $this->filesystem->dir_path( $thumbnail_url );
+
+ foreach ( $sizes as $size_key => $size_data ) {
+ $thumbnail_path = $attachment_path_dirname . $size_data['file'];
+ $thumbnail_url = $attachment_url_dirname . $size_data['file'];
+
+ // Optimize the thumbnail size.
+ $response = do_imagify( $thumbnail_path, array(
+ 'backup' => false,
+ 'optimization_level' => $optimization_level,
+ 'context' => $this->get_context(),
+ ) );
+
+ $data = $this->fill_data( $data, $response, $size_key );
+
+ /** This filter is documented in /inc/classes/class-imagify-attachment.php. */
+ $data = apply_filters( 'imagify_fill_thumbnail_data', $data, $response, $this->id, $thumbnail_path, $thumbnail_url, $size_key, $optimization_level );
+ } // End foreach().
+
+ $data['stats']['percent'] = round( ( ( $data['stats']['original_size'] - $data['stats']['optimized_size'] ) / $data['stats']['original_size'] ) * 100, 2 );
+
+ update_post_meta( $this->id, '_imagify_data', $data );
+
+ /**
+ * Fires after re-optimizing some thumbnails of an attachment.
+ *
+ * @since 1.7.1
+ * @author Grégory Viguier
+ *
+ * @param int $id The attachment ID.
+ * @param array $sizes The sizes to optimize.
+ */
+ do_action( 'after_imagify_reoptimize_attachment_thumbnails', $this->id, $sizes );
+
+ $this->delete_running_status();
+ }
+
+ /**
+ * Process an attachment restoration from the backup file.
+ *
+ * @since 1.0
+ * @access public
+ *
+ * @return void
+ */
+ public function restore() {
+ // Check if the attachment extension is allowed.
+ if ( ! $this->is_extension_supported() ) {
+ return;
+ }
+
+ // Stop the process if there is no backup file to restore.
+ if ( ! $this->has_backup() ) {
+ return;
+ }
+
+ $backup_path = $this->get_backup_path();
+ $attachment_path = $this->get_original_path();
+
+ /**
+ * Fires before restoring an attachment.
+ *
+ * @since 1.0
+ *
+ * @param int $id The attachment ID
+ */
+ do_action( 'before_imagify_restore_attachment', $this->id );
+
+ // Create the original image from the backup.
+ $this->filesystem->copy( $backup_path, $attachment_path, true );
+ $this->filesystem->chmod_file( $attachment_path );
+
+ if ( $this->is_image() ) {
+ if ( ! function_exists( 'wp_generate_attachment_metadata' ) ) {
+ require_once ABSPATH . 'wp-admin/includes/image.php';
+ }
+
+ wp_generate_attachment_metadata( $this->id, $attachment_path );
+
+ // Restore the original size in the metadata.
+ $this->update_metadata_size();
+ }
+
+ // Remove old optimization data.
+ $this->delete_imagify_data();
+
+ /**
+ * Fires after restoring an attachment.
+ *
+ * @since 1.0
+ *
+ * @param int $id The attachment ID
+ */
+ do_action( 'after_imagify_restore_attachment', $this->id );
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/inc/deprecated/classes/class-imagify-auto-optimization-deprecated.php b/wp/wp-content/plugins/imagify/inc/deprecated/classes/class-imagify-auto-optimization-deprecated.php
new file mode 100644
index 00000000..cb9260d0
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/deprecated/classes/class-imagify-auto-optimization-deprecated.php
@@ -0,0 +1,55 @@
+prevent_auto_optimization_when_generating_thumbnails()
+ *
+ * @param array $metadata An array of attachment meta data.
+ * @param int $attachment_id Current attachment ID.
+ * @param string $context Additional context. Can be 'create' when metadata was initially created for new attachment or 'update' when the metadata was updated.
+ * @return array An array of attachment meta data.
+ */
+ public function allow_auto_optimization_when_generating_thumbnails( $metadata, $attachment_id, $context = null ) {
+ _deprecated_function( get_class( $this ) . '::' . __FUNCTION__ . '()', '1.9.10' );
+
+ if ( ! empty( $context ) && 'create' !== $context ) {
+ return $metadata;
+ }
+
+ // Fired from wp_generate_attachment_metadata(): $context is empty (WP < 5.3) or equal to 'create' (>P >= 5.3).
+ static::allow_optimization_internally( $attachment_id );
+ return $metadata;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/inc/deprecated/classes/class-imagify-enable-media-replace-deprecated.php b/wp/wp-content/plugins/imagify/inc/deprecated/classes/class-imagify-enable-media-replace-deprecated.php
new file mode 100644
index 00000000..8cc1e24e
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/deprecated/classes/class-imagify-enable-media-replace-deprecated.php
@@ -0,0 +1,181 @@
+store_old_backup_path()
+ * @deprecated
+ *
+ * @param string $return_url The URL the user will be redirected to.
+ * @return string The same URL.
+ */
+ public function optimize( $return_url ) {
+ _deprecated_function( get_class( $this ) . '::' . __FUNCTION__ . '()', '1.8.4' );
+
+ $attachment = $this->get_attachment();
+
+ if ( $attachment->get_data() ) {
+ /**
+ * The old images have been optimized in the past.
+ */
+ // Use the same otimization level for the new ones.
+ $optimization_level = $attachment->get_optimization_level();
+
+ // Remove old optimization data.
+ $attachment->delete_imagify_data();
+
+ // Optimize and overwrite the previous backup file if exists and needed.
+ add_filter( 'imagify_backup_overwrite_backup', '__return_true', 42 );
+ $attachment->optimize( $optimization_level );
+ remove_filter( 'imagify_backup_overwrite_backup', '__return_true', 42 );
+ }
+
+ $filesystem = Imagify_Filesystem::get_instance();
+
+ /**
+ * Delete the old backup file.
+ */
+ if ( ! $this->old_backup_path || ! $filesystem->exists( $this->old_backup_path ) ) {
+ // The user didn't choose to rename the files, or there is no old backup.
+ $this->old_backup_path = null;
+ return $return_url;
+ }
+
+ $new_backup_path = $attachment->get_raw_backup_path();
+
+ if ( $new_backup_path === $this->old_backup_path ) {
+ // We don't want to delete the new backup.
+ $this->old_backup_path = null;
+ return $return_url;
+ }
+
+ // Finally, delete the old backup file.
+ $filesystem->delete( $this->old_backup_path );
+
+ $this->old_backup_path = null;
+ return $return_url;
+ }
+
+ /**
+ * When the user chooses to change the file name, store the old backup file path. This path will be used later to delete the file.
+ *
+ * @since 1.6.9
+ * @since 1.9.10 Deprecated.
+ * @deprecated
+ *
+ * @param string $new_filename The new file name.
+ * @param string $current_path The current file path.
+ * @param int $post_id The attachment ID.
+ * @return string The same file name.
+ */
+ public function store_old_backup_path( $new_filename, $current_path, $post_id ) {
+ _deprecated_function( get_class( $this ) . '::' . __FUNCTION__ . '()', '1.9.10' );
+
+ if ( ! $this->media_id || $post_id !== $this->media_id ) {
+ return $new_filename;
+ }
+
+ $this->get_process();
+
+ if ( ! $this->process ) {
+ $this->media_id = 0;
+ return $new_filename;
+ }
+
+ $media = $this->process->get_media();
+ $backup_path = $media->get_backup_path();
+
+ if ( $backup_path ) {
+ $this->old_backup_path = $backup_path;
+
+ // Keep track of existing WebP files.
+ $media_files = $media->get_media_files();
+
+ if ( $media_files ) {
+ foreach ( $media_files as $media_file ) {
+ $this->old_webp_paths[] = imagify_path_to_webp( $media_file['path'] );
+ }
+ }
+ } else {
+ $this->media_id = 0;
+ $this->old_backup_path = false;
+ $this->old_webp_paths = [];
+ }
+
+ return $new_filename;
+ }
+
+ /**
+ * Get the attachment.
+ *
+ * @since 1.6.9
+ * @since 1.9 Deprecated.
+ * @deprecated
+ *
+ * @return object A Imagify_Attachment object (or any class extending it).
+ */
+ protected function get_attachment() {
+ if ( $this->attachment ) {
+ return $this->attachment;
+ }
+
+ _deprecated_function( get_class( $this ) . '::' . __FUNCTION__ . '()', '1.9', '\\Imagify\\ThirdParty\\EnableMediaReplace\\Main::get_instance()->get_process()' );
+
+ $this->attachment = get_imagify_attachment( 'wp', $this->attachment_id, 'enable_media_replace' );
+
+ return $this->attachment;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/inc/deprecated/classes/class-imagify-file-attachment.php b/wp/wp-content/plugins/imagify/inc/deprecated/classes/class-imagify-file-attachment.php
new file mode 100644
index 00000000..87a9d83f
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/deprecated/classes/class-imagify-file-attachment.php
@@ -0,0 +1,760 @@
+id = (int) $id;
+ $this->get_row();
+ } elseif ( is_array( $id ) || is_object( $id ) ) {
+ $prim_key = $this->get_row_db_instance()->get_primary_key();
+ $this->row = (array) $id;
+ $this->id = $this->row[ $prim_key ];
+ } else {
+ $this->invalidate_row();
+ }
+
+ $this->filesystem = Imagify_Filesystem::get_instance();
+ $this->optimization_state_transient = 'imagify-file-async-in-progress-' . $this->id;
+ }
+
+ /**
+ * Get the original file path.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return string
+ */
+ public function get_original_path() {
+ $row = $this->get_row();
+
+ if ( ! $row || empty( $row['path'] ) ) {
+ return '';
+ }
+
+ return Imagify_Files_Scan::remove_placeholder( $row['path'] );
+ }
+
+ /**
+ * Get the original file URL.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return string
+ */
+ public function get_original_url() {
+ $row = $this->get_row();
+
+ if ( ! $row || empty( $row['path'] ) ) {
+ return '';
+ }
+
+ return Imagify_Files_Scan::remove_placeholder( $row['path'], 'url' );
+ }
+
+ /**
+ * Get the backup file path, even if the file doesn't exist.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return string|bool The file path. False on failure.
+ */
+ public function get_raw_backup_path() {
+ if ( ! $this->is_valid() ) {
+ return false;
+ }
+
+ return Imagify_Custom_Folders::get_file_backup_path( $this->get_original_path() );
+ }
+
+ /**
+ * Get the backup URL.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return string|bool The file URL. False on failure.
+ */
+ public function get_backup_url() {
+ if ( ! $this->is_valid() ) {
+ return false;
+ }
+
+ return site_url( '/' ) . $this->filesystem->make_path_relative( $this->get_raw_backup_path() );
+ }
+
+ /**
+ * Get the optimization data.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return array
+ */
+ public function get_data() {
+ if ( ! $this->is_valid() ) {
+ return array();
+ }
+
+ $data = array_merge( $this->get_row_db_instance()->get_column_defaults(), $this->get_row() );
+
+ unset( $data['file_id'] );
+ return $data;
+ }
+
+ /**
+ * Get the optimization level.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return int|bool
+ */
+ public function get_optimization_level() {
+ $row = $this->get_row();
+ return isset( $row['optimization_level'] ) && is_int( $row['optimization_level'] ) ? $row['optimization_level'] : false;
+ }
+
+ /**
+ * Get the file optimization status (success, already_optimized, or error).
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return string
+ */
+ public function get_status() {
+ $row = $this->get_row();
+ return ! empty( $row['status'] ) ? $row['status'] : '';
+ }
+
+ /**
+ * Get width and height of the original image.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return array
+ */
+ public function get_dimensions() {
+ $row = $this->get_row();
+
+ return array(
+ 'width' => ! empty( $row['width'] ) ? $row['width'] : 0,
+ 'height' => ! empty( $row['height'] ) ? $row['height'] : 0,
+ );
+ }
+
+ /**
+ * Get the attachment error if there is one.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return string The message error
+ */
+ public function get_optimized_error() {
+ $row = $this->get_row();
+ return ! empty( $row['error'] ) && is_string( $row['error'] ) ? trim( $row['error'] ) : '';
+ }
+
+ /**
+ * Count number of optimized sizes.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return int
+ */
+ public function get_optimized_sizes_count() {
+ return $this->get_status() === 'success' ? 1 : 0;
+ }
+
+ /**
+ * Delete the data related to optimization.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ */
+ public function delete_imagify_data() {
+ if ( ! $this->is_valid() ) {
+ return;
+ }
+
+ $this->update_row( $this->get_reset_imagify_data() );
+ }
+
+ /**
+ * Tell if the current file extension is supported.
+ * If it's in the DB, it's supported.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return bool
+ */
+ public function is_extension_supported() {
+ return $this->is_valid();
+ }
+
+ /**
+ * Tell if the current file mime type is supported.
+ * If it's in the DB, it's supported.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return bool
+ */
+ public function is_mime_type_supported() {
+ return $this->is_valid();
+ }
+
+ /**
+ * Tell if the current attachment has the required WP metadata.
+ * Well, these are not attachments, so...
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return bool
+ */
+ public function has_required_metadata() {
+ return $this->is_valid();
+ }
+
+ /**
+ * Get the original file size.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param bool $human_format True to display the image human format size (1Mb).
+ * @param int $decimals Precision of number of decimal places.
+ * @return string|int
+ */
+ public function get_original_size( $human_format = true, $decimals = 2 ) {
+ if ( ! $this->is_valid() ) {
+ return $human_format ? imagify_size_format( 0, $decimals ) : 0;
+ }
+
+ $row = $this->get_row();
+
+ if ( ! empty( $row['original_size'] ) ) {
+ $size = $row['original_size'];
+ } else {
+ // Check for the backup file first.
+ $file_path = $this->get_backup_path();
+
+ if ( ! $file_path ) {
+ $file_path = $this->get_original_path();
+ $file_path = $file_path && $this->filesystem->exists( $file_path ) ? $file_path : false;
+ }
+
+ $size = $file_path ? $this->filesystem->size( $file_path ) : 0;
+ }
+
+ if ( $human_format ) {
+ return imagify_size_format( (int) $size, $decimals );
+ }
+
+ return (int) $size;
+ }
+
+ /**
+ * Get the optimized file size.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param bool $human_format True to display the image human format size (1Mb).
+ * @param int $decimals Precision of number of decimal places.
+ * @return string|int
+ */
+ public function get_optimized_size( $human_format = true, $decimals = 2 ) {
+ if ( ! $this->is_valid() ) {
+ return $human_format ? imagify_size_format( 0, $decimals ) : 0;
+ }
+
+ $row = $this->get_row();
+
+ if ( ! empty( $row['optimized_size'] ) ) {
+ $size = $row['optimized_size'];
+ } else {
+ $file_path = $this->get_original_path();
+ $file_path = $file_path && $this->filesystem->exists( $file_path ) ? $file_path : false;
+ $size = $file_path ? $this->filesystem->size( $file_path ) : 0;
+ }
+
+ if ( $human_format ) {
+ return imagify_size_format( (int) $size, $decimals );
+ }
+
+ return (int) $size;
+ }
+
+ /**
+ * Get the optimized attachment size.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return float A 2-decimals float.
+ */
+ public function get_saving_percent() {
+ if ( ! $this->is_valid() ) {
+ return round( (float) 0, 2 );
+ }
+
+ $row = $this->get_row();
+
+ if ( ! empty( $row['percent'] ) ) {
+ return $row['percent'] / 100;
+ }
+
+ $original_size = $this->get_original_size( false );
+
+ if ( ! $original_size ) {
+ return round( (float) 0, 2 );
+ }
+
+ $optimized_size = $this->get_optimized_size( false );
+
+ if ( ! $optimized_size ) {
+ return round( (float) 0, 2 );
+ }
+
+ return round( ( $original_size - $optimized_size ) / $original_size * 100, 2 );
+ }
+
+ /**
+ * Get the overall optimized size (all thumbnails).
+ * And since we don't have thumbnails...
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return float A 2-decimals float.
+ */
+ public function get_overall_saving_percent() {
+ return $this->get_saving_percent();
+ }
+
+ /**
+ * Get the statistics of the file.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param string $size The thumbnail slug. Not used here.
+ * @param string $key The specific data slug.
+ * @return array|string
+ */
+ public function get_size_data( $size = null, $key = null ) {
+ if ( ! isset( $key ) ) {
+ $key = $size;
+ }
+
+ if ( ! $this->is_valid() ) {
+ return isset( $key ) ? '' : array();
+ }
+
+ $data = imagify_merge_intersect( $this->get_row(), array(
+ 'original_size' => 0,
+ 'optimized_size' => false,
+ 'percent' => 0,
+ 'status' => false,
+ 'error' => false,
+ ) );
+
+ $data['success'] = 'success' === $data['status'];
+
+ if ( $data['status'] ) {
+ unset( $data['status'], $data['error'] );
+
+ if ( empty( $data['percent'] ) && $data['original_size'] && $data['optimized_size'] ) {
+ $data['percent'] = round( ( $data['original_size'] - $data['optimized_size'] ) / $data['original_size'] * 100, 2 );
+ } elseif ( ! empty( $data['percent'] ) ) {
+ $data['percent'] = $data['percent'] / 100;
+ }
+ } else {
+ unset( $data['status'], $data['original_size'], $data['optimized_size'], $data['percent'] );
+ }
+
+ if ( isset( $key ) ) {
+ return isset( $data[ $key ] ) ? $data[ $key ] : '';
+ }
+
+ return $data;
+ }
+
+ /**
+ * Get the global statistics data or a specific one.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param string $key The specific data slug.
+ * @return array|string
+ */
+ public function get_stats_data( $key = null ) {
+ if ( ! $this->is_valid() ) {
+ return isset( $key ) ? '' : array();
+ }
+
+ $stats = $this->get_size_data( $key );
+ $default = array(
+ 'original_size' => 0,
+ 'optimized_size' => 0,
+ 'percent' => 0,
+ );
+
+ return imagify_merge_intersect( $stats, $default );
+ }
+
+ /**
+ * Since these files are not resized, this method is not needed.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return bool
+ */
+ public function update_metadata_size() {
+ return false;
+ }
+
+ /**
+ * Get the unoptimized sizes for a specific attachment.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return array
+ */
+ public function get_unoptimized_sizes() {
+ return array();
+ }
+
+ /**
+ * Get default values used to reset Imagify data.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ */
+ public function get_reset_imagify_data() {
+ static $column_defaults;
+
+ if ( ! isset( $column_defaults ) ) {
+ $column_defaults = $this->get_row_db_instance()->get_column_defaults();
+
+ // All DB columns that have `null` as default value, are Imagify data.
+ foreach ( $column_defaults as $column_name => $value ) {
+ if ( 'hash' === $column_name || 'modified' === $column_name ) {
+ continue;
+ }
+
+ if ( isset( $value ) ) {
+ unset( $column_defaults[ $column_name ] );
+ }
+ }
+ }
+
+ $imagify_columns = $column_defaults;
+
+ // Also set the new file hash.
+ $file_path = $this->get_original_path();
+
+ if ( $file_path && $this->filesystem->exists( $file_path ) ) {
+ $imagify_columns['hash'] = md5_file( $file_path );
+ }
+
+ return $imagify_columns;
+ }
+
+ /**
+ * Fills statistics data with values from $data array.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param array $data The statistics data.
+ * @param object $response The API response.
+ * @param string $size The attachment size key. Not used here.
+ * @return bool|array False if the original size has an error or an array contains the data for other result.
+ */
+ public function fill_data( $data, $response, $size = null ) {
+ $data = is_array( $data ) ? $data : array();
+ $data = imagify_merge_intersect( $data, $this->get_reset_imagify_data() );
+
+ if ( is_wp_error( $response ) ) {
+ // Error or already optimized.
+ $data['error'] = $response->get_error_message();
+
+ if ( false !== strpos( $data['error'], 'This image is already compressed' ) ) {
+ $data['status'] = 'already_optimized';
+ } else {
+ $data['status'] = 'error';
+ }
+
+ return $data;
+ }
+
+ // Success.
+ $old_data = $this->get_data();
+ $original_size = $old_data['original_size'];
+ $data['percent'] = 0;
+ $data['status'] = 'success';
+
+ if ( ! empty( $response->original_size ) && ! $original_size ) {
+ $data['original_size'] = (int) $response->original_size;
+ $original_size = $data['original_size'];
+ }
+
+ if ( ! empty( $response->new_size ) ) {
+ $data['optimized_size'] = (int) $response->new_size;
+ } else {
+ $file_path = $this->get_original_path();
+ $file_path = $file_path && $this->filesystem->exists( $file_path ) ? $file_path : false;
+
+ $data['optimized_size'] = $file_path ? $this->filesystem->size( $file_path ) : 0;
+ }
+
+ if ( $original_size && $data['optimized_size'] ) {
+ $data['percent'] = round( ( $original_size - $data['optimized_size'] ) / $original_size * 10000 );
+ }
+
+ return $data;
+ }
+
+ /**
+ * Optimize the file with Imagify.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param int $optimization_level The optimization level (2=ultra, 1=aggressive, 0=normal).
+ * @param array $metadata The attachment meta data. Not used here.
+ * @return bool|object True on success (status success or already_optimized). A WP_Error object on failure.
+ */
+ public function optimize( $optimization_level = null, $metadata = null ) {
+ // Check if the file extension is allowed.
+ if ( ! $this->is_extension_supported() ) {
+ return new WP_Error( 'mime_type_not_supported', __( 'This type of file is not supported.', 'imagify' ) );
+ }
+
+ $optimization_level = is_numeric( $optimization_level ) ? (int) $optimization_level : get_imagify_option( 'optimization_level' );
+
+ // Check if the image is already optimized.
+ if ( $this->is_optimized() && ( $this->get_optimization_level() === $optimization_level ) ) {
+ return new WP_Error( 'same_optimization_level', __( 'This file is already optimized with this level.', 'imagify' ) );
+ }
+
+ /**
+ * Fires before optimizing a file.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ *
+ * @param int $id The file ID.
+ */
+ do_action( 'before_imagify_optimize_file', $this->id );
+
+ $this->set_running_status();
+
+ // Optimize the image.
+ $response = do_imagify( $this->get_original_path(), array(
+ 'optimization_level' => $optimization_level,
+ 'context' => 'File',
+ 'original_size' => $this->get_original_size( false ),
+ 'backup_path' => $this->get_raw_backup_path(),
+ ) );
+
+ // Fill the data.
+ $data = $this->fill_data( array(
+ 'optimization_level' => $optimization_level,
+ ), $response );
+
+ // Save the data.
+ $this->update_row( $data );
+
+ if ( is_wp_error( $response ) ) {
+ $this->delete_running_status();
+
+ if ( 'error' === $data['status'] ) {
+ return $response;
+ }
+
+ // Already optimized.
+ return true;
+ }
+
+ /**
+ * Fires after optimizing an attachment.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ *
+ * @param int $id The attachment ID.
+ * @param array $optimized_data The optimization data.
+ */
+ do_action( 'after_imagify_optimize_file', $this->id, $this->get_data() );
+
+ $this->delete_running_status();
+
+ return true;
+ }
+
+ /**
+ * Process an attachment restoration from the backup file.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return bool|object True on success (status success or already_optimized). A WP_Error object on failure.
+ */
+ public function restore() {
+ // Check if the file extension is allowed.
+ if ( ! $this->is_extension_supported() ) {
+ return new WP_Error( 'mime_type_not_supported', __( 'This type of file is not supported.', 'imagify' ) );
+ }
+
+ $backup_path = $this->get_backup_path();
+
+ // Stop the process if there is no backup file to restore.
+ if ( ! $backup_path ) {
+ return new WP_Error( 'source_doesnt_exist', __( 'The backup file does not exist.', 'imagify' ) );
+ }
+
+ $file_path = $this->get_original_path();
+
+ if ( ! $file_path ) {
+ return new WP_Error( 'empty_path', __( 'The file path is empty.', 'imagify' ) );
+ }
+
+ /**
+ * Fires before restoring a file.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ *
+ * @param int $id The file ID.
+ */
+ do_action( 'before_imagify_restore_file', $this->id );
+
+ // Create the original image from the backup.
+ $this->filesystem->copy( $backup_path, $file_path, true );
+ $this->filesystem->chmod_file( $file_path );
+
+ // Remove old optimization data.
+ $this->delete_imagify_data();
+
+ /**
+ * Fires after restoring a file.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ *
+ * @param int $id The file ID.
+ */
+ do_action( 'after_imagify_restore_file', $this->id );
+ }
+
+
+ /** ----------------------------------------------------------------------------------------- */
+ /** DB ROW ================================================================================== */
+ /** ----------------------------------------------------------------------------------------- */
+
+ /**
+ * Invalidate the row.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ * @access public
+ *
+ * @return array The row
+ */
+ public function invalidate_row() {
+ // Since the ID doesn't exist in any other table (not a Post ID, not a NGG gallery ID), it must be reset.
+ $this->id = 0;
+ $this->row = array();
+ return $this->row;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/inc/deprecated/classes/class-imagify-ngg-attachment.php b/wp/wp-content/plugins/imagify/inc/deprecated/classes/class-imagify-ngg-attachment.php
new file mode 100644
index 00000000..24c82012
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/deprecated/classes/class-imagify-ngg-attachment.php
@@ -0,0 +1,1011 @@
+is_mime_type_supported()
+ */
+ protected $is_mime_type_supported;
+
+ /**
+ * The constructor.
+ *
+ * @since 1.5
+ * @author Jonathan Buttigieg
+ *
+ * @param int|object $id An image attachment ID or a NGG object.
+ */
+ public function __construct( $id ) {
+ imagify_deprecated_class( get_class( $this ), '1.9', '\\Imagify\\ThirdParty\\NGG\\Optimization\\Process\\NGG( $id )' );
+
+ if ( is_object( $id ) ) {
+ if ( $id instanceof nggImage ) {
+ $this->image = $id;
+ $this->id = (int) $id->pid;
+ } else {
+ $this->image = nggdb::find_image( (int) $id->pid );
+ $this->id = ! empty( $this->image->pid ) ? (int) $this->image->pid : 0;
+ }
+ } else {
+ $this->image = nggdb::find_image( absint( $id ) );
+ $this->id = ! empty( $this->image->pid ) ? (int) $this->image->pid : 0;
+ }
+
+ $this->get_row();
+
+ if ( ! empty( $this->image->_ngiw ) ) {
+ $this->storage = $this->image->_ngiw->get_storage()->object;
+ } else {
+ $this->storage = C_Gallery_Storage::get_instance()->object;
+ }
+
+ $this->filesystem = Imagify_Filesystem::get_instance();
+ $this->optimization_state_transient = 'imagify-ngg-async-in-progress-' . $this->id;
+
+ // Load nggAdmin class.
+ $ngg_admin_functions_path = WP_PLUGIN_DIR . '/' . NGGFOLDER . '/products/photocrati_nextgen/modules/ngglegacy/admin/functions.php';
+
+ if ( ! class_exists( 'nggAdmin' ) && $this->filesystem->exists( $ngg_admin_functions_path ) ) {
+ require_once $ngg_admin_functions_path;
+ }
+ }
+
+ /**
+ * Get the original attachment path.
+ *
+ * @since 1.5
+ * @author Jonathan Buttigieg
+ *
+ * @access public
+ * @return string
+ */
+ public function get_original_path() {
+ if ( ! $this->is_valid() ) {
+ return '';
+ }
+
+ return $this->image->imagePath;
+ }
+
+ /**
+ * Get the original attachment URL.
+ *
+ * @since 1.5
+ * @author Jonathan Buttigieg
+ *
+ * @access public
+ * @return string
+ */
+ public function get_original_url() {
+ if ( ! $this->is_valid() ) {
+ return '';
+ }
+
+ return $this->image->imageURL;
+ }
+
+ /**
+ * Get the attachment backup file path, even if the file doesn't exist.
+ *
+ * @since 1.6.13
+ * @author Grégory Viguier
+ * @access public
+ *
+ * @return string|bool The file path. False on failure.
+ */
+ public function get_raw_backup_path() {
+ if ( ! $this->is_valid() ) {
+ return false;
+ }
+
+ return get_imagify_ngg_attachment_backup_path( $this->get_original_path() );
+ }
+
+ /**
+ * Get the attachment backup URL.
+ *
+ * @since 1.6.8
+ * @author Grégory Viguier
+ *
+ * @return string|false
+ */
+ public function get_backup_url() {
+ if ( ! $this->is_valid() ) {
+ return false;
+ }
+
+ return site_url( '/' ) . $this->filesystem->make_path_relative( $this->get_raw_backup_path() );
+ }
+
+ /**
+ * Get the attachment optimization data.
+ *
+ * @since 1.5
+ * @author Jonathan Buttigieg
+ *
+ * @access public
+ * @return array
+ */
+ public function get_data() {
+ $row = $this->get_row();
+ return isset( $row['data'] ) ? $row['data'] : array();
+ }
+
+ /**
+ * Get the attachment optimization level.
+ *
+ * @since 1.5
+ * @author Jonathan Buttigieg
+ *
+ * @access public
+ * @return int|bool
+ */
+ public function get_optimization_level() {
+ $row = $this->get_row();
+ return isset( $row['optimization_level'] ) ? (int) $row['optimization_level'] : false;
+ }
+
+ /**
+ * Get the attachment optimization status (success or error).
+ *
+ * @since 1.5
+ * @author Jonathan Buttigieg
+ *
+ * @access public
+ * @return string|bool
+ */
+ public function get_status() {
+ $row = $this->get_row();
+ return isset( $row['status'] ) ? $row['status'] : false;
+ }
+
+ /**
+ * Delete the data related to optimization.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ */
+ public function delete_imagify_data() {
+ if ( ! $this->get_row() ) {
+ return;
+ }
+
+ $this->delete_row();
+ }
+
+ /**
+ * Get width and height of the original image.
+ *
+ * @since 1.7
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return array
+ */
+ public function get_dimensions() {
+ return array(
+ 'width' => ! empty( $this->image->meta_data['width'] ) ? (int) $this->image->meta_data['width'] : 0,
+ 'height' => ! empty( $this->image->meta_data['height'] ) ? (int) $this->image->meta_data['height'] : 0,
+ );
+ }
+
+ /**
+ * Get the file mime type + file extension (if the file is supported).
+ *
+ * @since 1.8
+ * @access public
+ * @see wp_check_filetype()
+ * @author Grégory Viguier
+ *
+ * @return object
+ */
+ public function get_file_type() {
+ if ( isset( $this->file_type ) ) {
+ return $this->file_type;
+ }
+
+ if ( ! $this->is_valid() ) {
+ $this->file_type = (object) array(
+ 'ext' => '',
+ 'type' => '',
+ );
+ return $this->file_type;
+ }
+
+ $this->file_type = (object) wp_check_filetype( $this->get_original_path(), imagify_get_mime_types( 'image' ) );
+
+ return $this->file_type;
+ }
+
+ /**
+ * Tell if the current attachment has the required WP metadata.
+ *
+ * @since 1.6.12
+ * @author Grégory Viguier
+ *
+ * @return bool
+ */
+ public function has_required_metadata() {
+ static $sizes;
+
+ if ( ! isset( $sizes ) ) {
+ $sizes = $this->get_image_sizes();
+ }
+
+ return $sizes && $this->get_original_path();
+ }
+
+ /**
+ * Update the metadata size of the attachment.
+ *
+ * @since 1.5
+ *
+ * @access public
+ * @return void
+ */
+ public function update_metadata_size() {
+ $size = $this->filesystem->get_image_size( $this->get_original_path() );
+
+ if ( ! $size ) {
+ return;
+ }
+
+ $this->image->meta_data['width'] = $size['width'];
+ $this->image->meta_data['height'] = $size['height'];
+ $this->image->meta_data['full']['width'] = $size['width'];
+ $this->image->meta_data['full']['height'] = $size['height'];
+
+ nggdb::update_image_meta( $this->id, $this->image->meta_data );
+ }
+
+ /**
+ * Fills statistics data with values from $data array.
+ *
+ * @since 1.5
+ * @since 1.6.5 Not static anymore.
+ * @since 1.6.6 Removed the attachment ID parameter.
+ * @since 1.7 Removed the image URL parameter.
+ * @author Jonathan Buttigieg
+ * @access public
+ *
+ * @param array $data The statistics data.
+ * @param object $response The API response.
+ * @param string $size The attachment size key.
+ * @return bool|array False if the original size has an error or an array contains the data for other result.
+ */
+ public function fill_data( $data, $response, $size = 'full' ) {
+ $data = is_array( $data ) ? $data : array();
+ $data['sizes'] = ! empty( $data['sizes'] ) && is_array( $data['sizes'] ) ? $data['sizes'] : array();
+
+ if ( empty( $data['stats'] ) ) {
+ $data['stats'] = array(
+ 'original_size' => 0,
+ 'optimized_size' => 0,
+ 'percent' => 0,
+ );
+ }
+
+ if ( is_wp_error( $response ) ) {
+ // Error or already optimized.
+ $error = $response->get_error_message();
+ $error_status = 'error';
+
+ $data['sizes'][ $size ] = array(
+ 'success' => false,
+ 'error' => $error,
+ );
+
+ // Update the error status for the original size.
+ if ( 'full' === $size ) {
+ if ( false !== strpos( $error, 'This image is already compressed' ) ) {
+ $error_status = 'already_optimized';
+ }
+
+ $this->update_row( array(
+ // The pid column is needed in case the row doesn't exist yet.
+ 'pid' => $this->id,
+ 'status' => $error_status,
+ 'data' => $data,
+ ) );
+
+ return false;
+ }
+
+ return $data;
+ }
+
+ // Success.
+ $old_data = $this->get_data();
+ $original_size = ! empty( $old_data['sizes'][ $size ]['original_size'] ) ? (int) $old_data['sizes'][ $size ]['original_size'] : 0;
+
+ $response = (object) array_merge( array(
+ 'original_size' => 0,
+ 'new_size' => 0,
+ 'percent' => 0,
+ ), (array) $response );
+
+ if ( ! empty( $response->original_size ) && ! $original_size ) {
+ $original_size = (int) $response->original_size;
+ }
+
+ if ( ! empty( $response->new_size ) ) {
+ $optimized_size = (int) $response->new_size;
+ } else {
+ $file_path = $this->get_original_path();
+ $file_path = $file_path && $this->filesystem->exists( $file_path ) ? $file_path : false;
+ $optimized_size = $file_path ? $this->filesystem->size( $file_path ) : 0;
+ }
+
+ if ( $original_size && $optimized_size ) {
+ $percent = round( ( $original_size - $optimized_size ) / $original_size * 100, 2 );
+ } elseif ( ! empty( $response->percent ) ) {
+ $percent = round( $response->percent, 2 );
+ } else {
+ $percent = 0;
+ }
+
+ $data['sizes'][ $size ] = array(
+ 'success' => true,
+ 'original_size' => $original_size,
+ 'optimized_size' => $optimized_size,
+ 'percent' => $percent,
+ );
+
+ $data['stats']['original_size'] += $original_size;
+ $data['stats']['optimized_size'] += $optimized_size;
+ $data['stats']['percent'] = round( ( ( $data['stats']['original_size'] - $data['stats']['optimized_size'] ) / $data['stats']['original_size'] ) * 100, 2 );
+
+ return $data;
+ }
+
+ /**
+ * Optimize all sizes with Imagify.
+ *
+ * @since 1.5
+ * @author Jonathan Buttigieg
+ *
+ * @access public
+ * @param int $optimization_level The optimization level (2=ultra, 1=aggressive, 0=normal).
+ * @param array $metadata The attachment meta data (not used here).
+ * @return array $data The optimization data.
+ */
+ public function optimize( $optimization_level = null, $metadata = array() ) {
+ // Check if the attachment extension is allowed.
+ if ( ! $this->is_extension_supported() ) {
+ return;
+ }
+
+ $optimization_level = isset( $optimization_level ) ? (int) $optimization_level : get_imagify_option( 'optimization_level' );
+
+ // To avoid issue with "original_size" at 0 in "_imagify_data".
+ if ( 0 === (int) $this->get_stats_data( 'original_size' ) ) {
+ $this->delete_imagify_data();
+ }
+
+ // Check if the full size is already optimized.
+ if ( $this->is_optimized() && $this->get_optimization_level() === $optimization_level ) {
+ return;
+ }
+
+ // Get file path for original image.
+ $attachment_path = $this->get_original_path();
+ $attachment_url = $this->get_original_url();
+
+ /**
+ * Fires before optimizing an attachment.
+ *
+ * @since 1.5
+ * @author Jonathan Buttigieg
+ *
+ * @param int $id The image ID
+ */
+ do_action( 'before_imagify_ngg_optimize_attachment', $this->id );
+
+ $this->set_running_status();
+
+ // Optimize the original size.
+ $response = do_imagify( $attachment_path, array(
+ 'optimization_level' => $optimization_level,
+ 'context' => 'NGG',
+ 'keep_exif' => true,
+ 'original_size' => $this->get_original_size( false ),
+ 'backup_path' => $this->get_raw_backup_path(),
+ ) );
+
+ $data = $this->fill_data( null, $response );
+
+ /**
+ * Filter the optimization data of the full size.
+ *
+ * @since 1.8
+ * @author Grégory Viguier
+ *
+ * @param array $data The statistics data.
+ * @param object $response The API response.
+ * @param int $id The attachment ID.
+ * @param string $attachment_path The attachment path.
+ * @param string $attachment_url The attachment URL.
+ * @param string $size_key The attachment size key. The value is obviously 'full' but it's kept for concistancy with other filters.
+ * @param int $optimization_level The optimization level.
+ */
+ $data = apply_filters( 'imagify_fill_ngg_full_size_data', $data, $response, $this->id, $attachment_path, $attachment_url, 'full', $optimization_level );
+
+ // Save the optimization level.
+ $this->update_row( array(
+ // The pid column is needed in case the row doesn't exist yet.
+ 'pid' => $this->id,
+ 'optimization_level' => $optimization_level,
+ ) );
+
+ if ( ! $data ) {
+ // Error or already optimized.
+ $this->delete_running_status();
+ return;
+ }
+
+ // Optimize thumbnails.
+ $data = $this->optimize_thumbnails( $optimization_level, $data );
+
+ // Save the status to success.
+ $this->update_row( array(
+ 'status' => 'success',
+ ) );
+
+ /**
+ * Update NGG meta data.
+ */
+ $image_data = $this->storage->_image_mapper->find( $this->id );
+
+ if ( ! $image_data ) {
+ $this->delete_running_status();
+ return $data;
+ }
+
+ $dimensions = $this->filesystem->get_image_size( $attachment_path );
+ $md5 = md5_file( $attachment_path );
+
+ if ( ( $dimensions || $md5 ) && ( empty( $image_data->meta_data['full'] ) || ! is_array( $image_data->meta_data['full'] ) ) ) {
+ $image_data->meta_data['full'] = array(
+ 'width' => 0,
+ 'height' => 0,
+ 'md5' => '',
+ );
+ }
+
+ if ( $dimensions ) {
+ $image_data->meta_data['width'] = $dimensions['width'];
+ $image_data->meta_data['height'] = $dimensions['height'];
+ $image_data->meta_data['full']['width'] = $dimensions['width'];
+ $image_data->meta_data['full']['height'] = $dimensions['height'];
+ }
+
+ if ( $md5 ) {
+ $image_data->meta_data['md5'] = $md5;
+ $image_data->meta_data['full']['md5'] = $md5;
+ }
+
+ /**
+ * Fires after optimizing an attachment.
+ *
+ * @since 1.5
+ *
+ * @param int $id The attachment ID.
+ * @param array $data The optimization data.
+ */
+ do_action( 'after_imagify_ngg_optimize_attachment', $this->id, $data );
+
+ $this->delete_running_status();
+
+ return $data;
+ }
+
+ /**
+ * Optimize all thumbnails of an image.
+ *
+ * @since 1.5
+ * @author Jonathan Buttigieg
+ *
+ * @access public
+ * @param int $optimization_level The optimization level (2=ultra, 1=aggressive, 0=normal).
+ * @param array $data The optimization data.
+ * @return array $data The optimization data.
+ */
+ public function optimize_thumbnails( $optimization_level = null, $data = array() ) {
+ $sizes = $this->get_image_sizes();
+ $data = $data ? $data : $this->get_data();
+
+ // Stop if the original image has an error.
+ if ( $this->has_error() ) {
+ return $data;
+ }
+
+ $optimization_level = isset( $optimization_level ) ? (int) $optimization_level : get_imagify_option( 'optimization_level' );
+
+ /**
+ * Fires before optimizing all thumbnails.
+ *
+ * @since 1.5
+ * @author Jonathan Buttigieg
+ *
+ * @param int $id The image ID.
+ */
+ do_action( 'before_imagify_ngg_optimize_thumbnails', $this->id );
+
+ if ( $sizes ) {
+ $image_data = $this->storage->_image_mapper->find( $this->id );
+
+ foreach ( $sizes as $size_key ) {
+ if ( 'full' === $size_key || isset( $data['sizes'][ $size_key ]['success'] ) ) {
+ continue;
+ }
+
+ $thumbnail_path = $this->storage->get_image_abspath( $image_data, $size_key );
+ $thumbnail_url = $this->storage->get_image_url( $image_data, $size_key );
+
+ // Optimize the thumbnail size.
+ $response = do_imagify( $thumbnail_path, array(
+ 'optimization_level' => $optimization_level,
+ 'context' => 'NGG',
+ 'keep_exif' => true,
+ 'backup' => false,
+ ) );
+
+ $data = $this->fill_data( $data, $response, $size_key );
+
+ /**
+ * Filter the optimization data of a specific thumbnail.
+ *
+ * @since 1.5
+ * @author Jonathan Buttigieg
+ *
+ * @param array $data The statistics data.
+ * @param object $response The API response.
+ * @param int $id The image ID.
+ * @param string $thumbnail_path The image path.
+ * @param string $thumbnail_url The image URL.
+ * @param string $size_key The image size key.
+ * @param bool $is_aggressive The optimization level.
+ * @return array $data The new optimization data.
+ */
+ $data = apply_filters( 'imagify_fill_ngg_thumbnail_data', $data, $response, $this->id, $thumbnail_path, $thumbnail_url, $size_key, $optimization_level );
+ }
+
+ $this->update_row( array(
+ 'data' => $data,
+ ) );
+ } // End if().
+
+ /**
+ * Fires after optimizing all thumbnails.
+ *
+ * @since 1.5
+ * @author Jonathan Buttigieg
+ *
+ * @param int $id The image ID.
+ * @param array $data The optimization data.
+ */
+ do_action( 'after_imagify_ngg_optimize_thumbnails', $this->id, $data );
+
+ return $data;
+ }
+
+ /**
+ * Optimize one size.
+ *
+ * @since 1.8
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param string $size The thumbnail size.
+ */
+ public function optimize_new_thumbnail( $size ) {
+ // Check if the attachment extension is allowed.
+ if ( ! $this->is_extension_supported() ) {
+ return;
+ }
+
+ if ( ! $this->is_optimized() ) {
+ // The main image is not optimized.
+ return;
+ }
+
+ $data = $this->get_data();
+
+ if ( isset( $data['sizes'][ $size ]['success'] ) ) {
+ // This thumbnail has already been processed.
+ return;
+ }
+
+ $sizes = $this->get_image_sizes();
+ $sizes = array_flip( $sizes );
+
+ if ( ! isset( $sizes[ $size ] ) ) {
+ // This size doesn't exist.
+ return;
+ }
+
+ /**
+ * Fires before optimizing a thumbnail.
+ *
+ * @since 1.8
+ * @author Grégory Viguier
+ *
+ * @param int $id The image ID.
+ */
+ do_action( 'before_imagify_ngg_optimize_new_thumbnail', $this->id );
+
+ $this->set_running_status();
+
+ $image_data = $this->storage->_image_mapper->find( $this->id );
+ $thumbnail_path = $this->storage->get_image_abspath( $image_data, $size );
+ $thumbnail_url = $this->storage->get_image_url( $image_data, $size );
+ $optimization_level = $this->get_optimization_level();
+
+ // Optimize the thumbnail size.
+ $response = do_imagify( $thumbnail_path, array(
+ 'optimization_level' => $optimization_level,
+ 'context' => 'NGG',
+ 'keep_exif' => true,
+ 'backup' => false,
+ ) );
+
+ $data = $this->fill_data( $data, $response, $size );
+
+ /** This filter is documented in inc/3rd-party/nextgen-gallery/inc/classes/class-imagify-ngg-attachment.php. */
+ $data = apply_filters( 'imagify_fill_ngg_thumbnail_data', $data, $response, $this->id, $thumbnail_path, $thumbnail_url, $size, $optimization_level );
+
+ $this->update_row( array(
+ 'data' => $data,
+ ) );
+
+ /**
+ * Fires after optimizing a thumbnail.
+ *
+ * @since 1.8
+ * @author Grégory Viguier
+ *
+ * @param int $id The image ID.
+ * @param array $data The optimization data.
+ */
+ do_action( 'after_imagify_ngg_optimize_new_thumbnail', $this->id, $data );
+
+ $this->delete_running_status();
+ }
+
+ /**
+ * Re-optimize the given thumbnail sizes to the same level.
+ * This is not used in this context.
+ *
+ * @since 1.7.1
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param array $sizes The sizes to optimize.
+ * @return array|void A WP_Error object on failure.
+ */
+ public function reoptimize_thumbnails( $sizes ) {}
+
+ /**
+ * Process an attachment restoration from the backup file.
+ *
+ * @since 1.5
+ * @since 1.6.9 Doesn't use NGG's recover_image() anymore, these are fundamentally not the same things. This also prevents alt text, description, and tags deletion.
+ * @since 1.6.9 Return true or a WP_Error object.
+ * @author Jonathan Buttigieg
+ *
+ * @access public
+ * @return bool|object True on success, a WP_Error object on error.
+ */
+ public function restore() {
+ // Check if the attachment extension is allowed.
+ if ( ! $this->is_extension_supported() ) {
+ return new WP_Error( 'mime_not_type_supported', __( 'Mime type not supported.', 'imagify' ) );
+ }
+
+ // Stop the process if there is no backup file to restore.
+ if ( ! $this->has_backup() ) {
+ return new WP_Error( 'no_backup', __( 'Backup image not found.', 'imagify' ) );
+ }
+
+ $image_data = $this->storage->_image_mapper->find( $this->id );
+
+ if ( ! $image_data ) {
+ return new WP_Error( 'no_image', __( 'Image not found in NextGen Gallery data.', 'imagify' ) );
+ }
+
+ /**
+ * Make some more tests before restoring the backup.
+ */
+ $full_abspath = $this->storage->get_image_abspath( $image_data );
+ $backup_abspath = $this->storage->get_image_abspath( $image_data, 'backup' );
+
+ if ( $backup_abspath === $full_abspath ) {
+ return new WP_Error( 'same_path', __( 'Image path and backup path are identical.', 'imagify' ) );
+ }
+
+ if ( ! $this->filesystem->is_writable( $full_abspath ) || ! $this->filesystem->is_writable( $this->filesystem->dir_path( $full_abspath ) ) ) {
+ return new WP_Error( 'destination_not_writable', __( 'The image to replace is not writable.', 'imagify' ) );
+ }
+
+ /**
+ * Fires before restoring an attachment.
+ *
+ * @since 1.5
+ * @author Jonathan Buttigieg
+ *
+ * @param int $id The attachment ID.
+ */
+ do_action( 'before_imagify_ngg_restore_attachment', $this->id );
+
+ if ( ! $this->filesystem->copy( $backup_abspath, $full_abspath, true, FS_CHMOD_FILE ) ) {
+ return new WP_Error( 'copy_failed', __( 'Restoration failed.', 'imagify' ) );
+ }
+
+ /**
+ * Remove Imagify data.
+ */
+ $this->delete_row();
+
+ /**
+ * Fill in the NGG meta data.
+ */
+ // 1- Meta data for the backup file.
+ $dimensions = $this->filesystem->get_image_size( $backup_abspath );
+ $backup_data = array(
+ 'backup' => array(
+ 'filename' => $this->filesystem->file_name( $full_abspath ), // Yes, $full_abspath.
+ 'width' => 0,
+ 'height' => 0,
+ 'generated' => microtime(),
+ ),
+ );
+
+ if ( $dimensions ) {
+ $backup_data['backup']['width'] = $dimensions['width'];
+ $backup_data['backup']['height'] = $dimensions['height'];
+ }
+
+ // 2- Meta data for the full sized image.
+ $full_data = array(
+ 'width' => 0,
+ 'height' => 0,
+ 'md5' => '',
+ 'full' => array(
+ 'width' => 0,
+ 'height' => 0,
+ 'md5' => '',
+ ),
+ );
+
+ $dimensions = $this->filesystem->get_image_size( $full_abspath );
+
+ if ( $dimensions ) {
+ $full_data['width'] = $dimensions['width'];
+ $full_data['height'] = $dimensions['height'];
+ $full_data['full']['width'] = $dimensions['width'];
+ $full_data['full']['height'] = $dimensions['height'];
+ }
+
+ $md5 = md5_file( $full_abspath );
+
+ if ( $md5 ) {
+ $full_data['md5'] = $md5;
+ $full_data['full']['md5'] = $md5;
+ }
+
+ // 3- Thumbnails meta data.
+ $thumbnails_data = array();
+
+ // 4- Common meta data.
+ require_once NGGALLERY_ABSPATH . '/lib/meta.php';
+ $meta_obj = new nggMeta( $image_data );
+ $common_data = $meta_obj->get_common_meta();
+
+ if ( $common_data ) {
+ unset( $common_data['width'], $common_data['height'] );
+ } else {
+ $common_data = array(
+ 'aperture' => 0,
+ 'credit' => '',
+ 'camera' => '',
+ 'caption' => '',
+ 'created_timestamp' => 0,
+ 'copyright' => '',
+ 'focal_length' => 0,
+ 'iso' => 0,
+ 'shutter_speed' => 0,
+ 'flash' => 0,
+ 'title' => '',
+ 'keywords' => '',
+ );
+
+ if ( ! empty( $image_data->meta_data ) && is_array( $image_data->meta_data ) ) {
+ $image_data->meta_data = array_merge( $common_data, $image_data->meta_data );
+ $common_data = array_intersect_key( $image_data->meta_data, $common_data );
+ }
+ }
+
+ $common_data['saved'] = true;
+
+ /**
+ * Re-create non-fullsize image sizes and add related data.
+ */
+ $failed = array();
+
+ foreach ( $this->get_image_sizes() as $named_size ) {
+ if ( 'full' === $named_size ) {
+ continue;
+ }
+
+ $params = $this->storage->get_image_size_params( $image_data, $named_size );
+ $thumbnail = $this->storage->generate_image_clone(
+ $backup_abspath,
+ $this->storage->get_image_abspath( $image_data, $named_size ),
+ $params
+ );
+
+ if ( ! $thumbnail ) {
+ // Failed.
+ $failed[] = $named_size;
+ continue;
+ }
+
+ $size_meta = array(
+ 'width' => 0,
+ 'height' => 0,
+ 'filename' => M_I18n::mb_basename( $thumbnail->fileName ),
+ 'generated' => microtime(),
+ );
+
+ $dimensions = $this->filesystem->get_image_size( $thumbnail->fileName );
+
+ if ( $dimensions ) {
+ $size_meta['width'] = $dimensions['width'];
+ $size_meta['height'] = $dimensions['height'];
+ }
+
+ if ( isset( $params['crop_frame'] ) ) {
+ $size_meta['crop_frame'] = $params['crop_frame'];
+ }
+
+ $thumbnails_data[ $named_size ] = $size_meta;
+ } // End foreach().
+
+ do_action( 'ngg_recovered_image', $image_data );
+
+ /**
+ * Save the meta data.
+ */
+ $image_data->meta_data = array_merge( $backup_data, $full_data, $thumbnails_data, $common_data );
+
+ // Keep our property up to date.
+ $this->image->_ngiw->_cache['meta_data'] = $image_data->meta_data;
+ $this->image->_ngiw->_orig_image = $image_data;
+
+ $post_id = $this->storage->_image_mapper->save( $image_data );
+
+ if ( ! $post_id ) {
+ return new WP_Error( 'meta_data_not_saved', __( 'Related data could not be saved.', 'imagify' ) );
+ }
+
+ if ( $failed ) {
+ return new WP_Error(
+ 'thumbnail_restore_failed',
+ sprintf( _n( '%n thumbnail could not be restored.', '%n thumbnails could not be restored.', count( $failed ), 'imagify' ), count( $failed ) ),
+ array( 'failed_thumbnails' => $failed )
+ );
+ }
+
+ /**
+ * Fires after restoring an attachment.
+ *
+ * @since 1.5
+ * @author Jonathan Buttigieg
+ *
+ * @param int $id The attachment ID.
+ */
+ do_action( 'after_imagify_ngg_restore_attachment', $this->id );
+
+ return true;
+ }
+
+ /**
+ * Get the image sizes.
+ *
+ * @since 1.8
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return array
+ */
+ public function get_image_sizes() {
+ $sizes = array(
+ 'full',
+ );
+
+ // Remove common values (that have no value for us here, lol).
+ $image_data = array_diff_key( $this->image->meta_data, array(
+ 'backup' => 1,
+ 'width' => 1,
+ 'height' => 1,
+ 'md5' => 1,
+ 'full' => 1,
+ 'aperture' => 1,
+ 'credit' => 1,
+ 'camera' => 1,
+ 'caption' => 1,
+ 'created_timestamp' => 1,
+ 'copyright' => 1,
+ 'focal_length' => 1,
+ 'iso' => 1,
+ 'shutter_speed' => 1,
+ 'flash' => 1,
+ 'title' => 1,
+ 'keywords' => 1,
+ 'saved' => 1,
+ ) );
+
+ if ( ! $image_data ) {
+ return $sizes;
+ }
+
+ foreach ( $image_data as $size_name => $size_data ) {
+ if ( isset( $size_data['width'], $size_data['height'], $size_data['filename'], $size_data['generated'] ) ) {
+ $sizes[] = $size_name;
+ }
+ }
+
+ return $sizes;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/inc/deprecated/classes/class-imagify-ngg-dynamic-thumbnails-background-process.php b/wp/wp-content/plugins/imagify/inc/deprecated/classes/class-imagify-ngg-dynamic-thumbnails-background-process.php
new file mode 100644
index 00000000..2b872112
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/deprecated/classes/class-imagify-ngg-dynamic-thumbnails-background-process.php
@@ -0,0 +1,167 @@
+data[ $key ] = $data;
+
+ return $this;
+ }
+
+ /**
+ * Dispatch.
+ *
+ * @since 1.8
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @return array|WP_Error
+ */
+ public function dispatch() {
+ if ( ! empty( $this->data ) ) {
+ return parent::dispatch();
+ }
+ }
+
+ /**
+ * Tell if a task is already in the queue.
+ *
+ * @since 1.8
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param array $data {
+ * The data to test against the queue.
+ *
+ * @type int $id The image ID. Required.
+ * @type string $size The thumbnail size. Required.
+ * }
+ * @return bool
+ */
+ public function is_in_queue( $data ) {
+ $key = $data['id'] . '|' . $data['size'];
+
+ return isset( $this->data[ $key ] );
+ }
+
+ /**
+ * Task: optimize the thumbnail.
+ *
+ * @since 1.8
+ * @access public
+ * @author Grégory Viguier
+ *
+ * @param array $item {
+ * The data to test against the queue.
+ *
+ * @type int $id The image ID. Required.
+ * @type string $size The thumbnail size. Required.
+ * }
+ * @return bool False to remove the item from the queue.
+ */
+ protected function task( $item ) {
+ $attachment_id = absint( $item['id'] );
+ $size = sanitize_text_field( $item['size'] );
+
+ if ( ! $attachment_id || ! $size ) {
+ return false;
+ }
+
+ $attachment = get_imagify_attachment( 'NGG', $attachment_id, 'ngg_optimize_dynamic_thumbnail' );
+
+ $attachment->optimize_new_thumbnail( $size );
+
+ return false;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/inc/deprecated/classes/class-imagify-notices-deprecated.php b/wp/wp-content/plugins/imagify/inc/deprecated/classes/class-imagify-notices-deprecated.php
new file mode 100644
index 00000000..edb50d5b
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/deprecated/classes/class-imagify-notices-deprecated.php
@@ -0,0 +1,29 @@
+print_template( \'notice-\' . $view, $data )' );
+
+ Imagify_Views::get_instance()->print_template( 'notice-' . $view, $data );
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/inc/deprecated/classes/class-imagify-regenerate-thumbnails-deprecated.php b/wp/wp-content/plugins/imagify/inc/deprecated/classes/class-imagify-regenerate-thumbnails-deprecated.php
new file mode 100644
index 00000000..198a0fca
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/deprecated/classes/class-imagify-regenerate-thumbnails-deprecated.php
@@ -0,0 +1,160 @@
+is_valid() || ! $attachment->is_image() ) {
+ wp_send_json_error();
+ }
+
+ // Optimize.
+ $attachment->reoptimize_thumbnails( wp_unslash( $_POST['sizes'] ) );
+
+ // Put the optimized original file back.
+ $this->put_optimized_file_back( $attachment_id );
+
+ wp_send_json_success();
+ }
+
+ /**
+ * Set the Imagify attachment.
+ *
+ * @since 1.7.1
+ * @since 1.9 Deprecated.
+ * @access protected
+ * @author Grégory Viguier
+ * @deprecated
+ *
+ * @param int $attachment_id Attachment ID.
+ * @return object|false An Imagify attachment object. False on failure.
+ */
+ protected function set_attachment( $attachment_id ) {
+ _deprecated_function( get_class( $this ) . '::' . __FUNCTION__ . '()', '1.9', '\\Imagify\\ThirdParty\\RegenerateThumbnails\\Main::get_instance()->set_process()' );
+
+ if ( ! $attachment_id || ! Imagify_Requirements::is_api_key_valid() ) {
+ return false;
+ }
+
+ $attachment = get_imagify_attachment( 'wp', $attachment_id, 'regenerate_thumbnails' );
+
+ if ( ! $attachment->is_valid() || ! $attachment->is_image() || ! $attachment->is_optimized() ) {
+ return false;
+ }
+
+ // This attachment can be optimized.
+ $this->attachments[ $attachment_id ] = $attachment;
+ return $this->attachments[ $attachment_id ];
+ }
+
+ /**
+ * Unset the Imagify attachment.
+ *
+ * @since 1.7.1
+ * @since 1.9 Deprecated.
+ * @access protected
+ * @author Grégory Viguier
+ * @deprecated
+ *
+ * @param int $attachment_id Attachment ID.
+ */
+ protected function unset_attachment( $attachment_id ) {
+ _deprecated_function( get_class( $this ) . '::' . __FUNCTION__ . '()', '1.9', '\\Imagify\\ThirdParty\\RegenerateThumbnails\\Main::get_instance()->unset_process()' );
+
+ unset( $this->attachments[ $attachment_id ] );
+ }
+
+ /**
+ * Get the Imagify attachment.
+ *
+ * @since 1.7.1
+ * @since 1.9 Deprecated.
+ * @access protected
+ * @author Grégory Viguier
+ * @deprecated
+ *
+ * @param int $attachment_id Attachment ID.
+ * @return object|false An Imagify attachment object. False on failure.
+ */
+ protected function get_attachment( $attachment_id ) {
+ _deprecated_function( get_class( $this ) . '::' . __FUNCTION__ . '()', '1.9', '\\Imagify\\ThirdParty\\RegenerateThumbnails\\Main::get_instance()->get_process()' );
+
+ return ! empty( $this->attachments[ $attachment_id ] ) ? $this->attachments[ $attachment_id ] : false;
+ }
+
+ /**
+ * Get the name of the nonce used for the ajax callback.
+ *
+ * @since 1.7.1
+ * @since 1.9 Deprecated.
+ * @access public
+ * @author Grégory Viguier
+ * @deprecated
+ *
+ * @param int $media_id The media ID.
+ * @param string $context The context.
+ * @return string
+ */
+ public static function get_nonce_name( $media_id, $context ) {
+ _deprecated_function( get_called_class() . '::' . __FUNCTION__ . '()', '1.9' );
+
+ return static::ACTION . '-' . $media_id . '-' . $context;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/inc/deprecated/classes/class-imagify-user.php b/wp/wp-content/plugins/imagify/inc/deprecated/classes/class-imagify-user.php
new file mode 100644
index 00000000..64a0a50a
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/deprecated/classes/class-imagify-user.php
@@ -0,0 +1,265 @@
+error = $user;
+ return;
+ }
+
+ $this->id = $user->id;
+ $this->email = $user->email;
+ $this->plan_id = (int) $user->plan_id;
+ $this->plan_label = ucfirst( $user->plan_label );
+ $this->quota = $user->quota;
+ $this->extra_quota = $user->extra_quota;
+ $this->extra_quota_consumed = $user->extra_quota_consumed;
+ $this->consumed_current_month_quota = $user->consumed_current_month_quota;
+ $this->next_date_update = $user->next_date_update;
+ $this->is_active = $user->is_active;
+ $this->error = false;
+ }
+
+ /**
+ * Get the possible error returned when fetching user data.
+ *
+ * @since 1.9.9
+ *
+ * @return bool|\WP_Error A \WP_Error object if the request to fetch the user data failed. False overwise.
+ */
+ public function get_error() {
+ return $this->error;
+ }
+
+ /**
+ * Percentage of consumed quota, including extra quota.
+ *
+ * @since 1.0
+ *
+ * @return float|int
+ */
+ public function get_percent_consumed_quota() {
+ static $done = false;
+ if ( $this->get_error() ) {
+ return 0;
+ }
+
+ $quota = $this->quota;
+ $consumed_quota = $this->consumed_current_month_quota;
+
+ if ( imagify_round_half_five( $this->extra_quota_consumed ) < $this->extra_quota ) {
+ $quota += $this->extra_quota;
+ $consumed_quota += $this->extra_quota_consumed;
+ }
+
+ if ( ! $quota || ! $consumed_quota ) {
+ $percent = 0;
+ } else {
+ $percent = 100 * $consumed_quota / $quota;
+ $percent = round( $percent, 1 );
+ $percent = min( max( 0, $percent ), 100 );
+ }
+
+ $percent = (float) $percent;
+
+ $percent = 100;
+
+ if ( $done ) {
+ return $percent;
+ }
+
+ $previous_percent = Imagify_Data::get_instance()->get( 'previous_quota_percent' );
+
+
+ // Percent is not 100% anymore.
+ if ( 100.0 === (float) $previous_percent && $percent < 100 ) {
+ /**
+ * Triggered when the consumed quota percent decreases below 100%.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ *
+ * @param float|int $percent The current percentage of consumed quota.
+ */
+ do_action( 'imagify_not_over_quota_anymore', $percent );
+ }
+
+ // Percent is not >= 80% anymore.
+ if ( (float) $previous_percent >= 80.0 && $percent < 80 ) {
+ /**
+ * Triggered when the consumed quota percent decreases below 80%.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ *
+ * @param float|int $percent The current percentage of consumed quota.
+ * @param float|int $previous_percent The previous percentage of consumed quota.
+ */
+ do_action( 'imagify_not_almost_over_quota_anymore', $percent, $previous_percent );
+ }
+
+ if ( (float) $previous_percent !== (float) $percent ) {
+ Imagify_Data::get_instance()->set( 'previous_quota_percent', $percent );
+ }
+
+ $done = true;
+
+ return $percent;
+ }
+
+ /**
+ * Count percent of unconsumed quota.
+ *
+ * @since 1.0
+ *
+ * @return float|int
+ */
+ public function get_percent_unconsumed_quota() {
+ return 100 - $this->get_percent_consumed_quota();
+ }
+
+ /**
+ * Check if the user has a free account.
+ *
+ * @since 1.1.1
+ *
+ * @return bool
+ */
+ public function is_free() {
+ return 1 === $this->plan_id;
+ }
+
+ /**
+ * Check if the user has consumed all his/her quota.
+ *
+ * @since 1.1.1
+ * @since 1.9.9 Return false if the request to fetch the user data failed.
+ *
+ * @return bool
+ */
+ public function is_over_quota() {
+ if ( $this->get_error() ) {
+ return false;
+ }
+
+ return (
+ $this->is_free()
+ &&
+ floatval( 100 ) === round( $this->get_percent_consumed_quota() )
+ );
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/inc/deprecated/deprecated.php b/wp/wp-content/plugins/imagify/inc/deprecated/deprecated.php
new file mode 100644
index 00000000..aef5cada
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/deprecated/deprecated.php
@@ -0,0 +1,1754 @@
+schedule_event()' );
+
+ Imagify_Cron_Rating::get_instance()->schedule_event();
+}
+
+/**
+ * Save the user images count to display it later in a notice message to ask him to rate Imagify on WordPress.org.
+ *
+ * @since 1.4.2
+ * @since 1.7 Deprecated.
+ * @deprecated
+ */
+function _do_imagify_rating_cron() {
+ _deprecated_function( __FUNCTION__ . '()', '1.7', 'Imagify_Cron_Rating::get_instance()->do_event()' );
+
+ Imagify_Cron_Rating::get_instance()->do_event();
+}
+
+/**
+ * Adds weekly interval for cron jobs.
+ *
+ * @since 1.6
+ * @since 1.7 Deprecated.
+ * @author Remy Perona
+ * @deprecated
+ *
+ * @param Array $schedules An array of intervals used by cron jobs.
+ * @return Array Updated array of intervals.
+ */
+function imagify_purge_cron_schedule( $schedules ) {
+ _deprecated_function( __FUNCTION__ . '()', '1.7', 'Imagify_Cron_Library_Size::get_instance()->maybe_add_recurrence( $schedules )' );
+
+ return Imagify_Cron_Library_Size::get_instance()->do_event( $schedules );
+}
+
+/**
+ * Planning cron task to update weekly the size of the images and the size of images uploaded by month.
+ * If the task is not programmed, it is automatically triggered.
+ *
+ * @since 1.6
+ * @since 1.7 Deprecated.
+ * @author Remy Perona
+ * @deprecated
+ */
+function _imagify_update_library_size_calculations_scheduled() {
+ _deprecated_function( __FUNCTION__ . '()', '1.7', 'Imagify_Cron_Library_Size::get_instance()->schedule_event()' );
+
+ Imagify_Cron_Library_Size::get_instance()->schedule_event();
+}
+
+/**
+ * Cron task to update weekly the size of the images and the size of images uploaded by month.
+ *
+ * @since 1.6
+ * @since 1.7 Deprecated.
+ * @author Remy Perona
+ * @deprecated
+ */
+function _do_imagify_update_library_size_calculations() {
+ _deprecated_function( __FUNCTION__ . '()', '1.7', 'Imagify_Cron_Library_Size::get_instance()->do_event()' );
+
+ Imagify_Cron_Library_Size::get_instance()->do_event();
+}
+
+/**
+ * Set a file permissions using FS_CHMOD_FILE.
+ *
+ * @since 1.2
+ * @since 1.6.5 Use WP Filesystem.
+ * @since 1.7.1 Deprecated.
+ * @deprecated
+ *
+ * @param string $file_path Path to the file.
+ * @return bool True on success, false on failure.
+ */
+function imagify_chmod_file( $file_path ) {
+ _deprecated_function( __FUNCTION__ . '()', '1.7.1', 'imagify_get_filesystem()->chmod_file( $file_path )' );
+
+ return imagify_get_filesystem()->chmod_file( $file_path );
+}
+
+/**
+ * Get a file mime type.
+ *
+ * @since 1.6.9
+ * @since 1.7 Doesn't use exif_imagetype() nor getimagesize() anymore.
+ * @since 1.7.1 Deprecated.
+ * @author Grégory Viguier
+ * @deprecated
+ *
+ * @param string $file_path A file path (prefered) or a filename.
+ * @return string|bool A mime type. False on failure: the test is limited to mime types supported by Imagify.
+ */
+function imagify_get_mime_type_from_file( $file_path ) {
+ _deprecated_function( __FUNCTION__ . '()', '1.7.1', 'imagify_get_filesystem()->get_mime_type( $file_path )' );
+
+ return imagify_get_filesystem()->get_mime_type( $file_path );
+}
+
+/**
+ * Get a file modification date, formated as "mysql". Fallback to current date.
+ *
+ * @since 1.7
+ * @since 1.7.1 Deprecated.
+ * @author Grégory Viguier
+ * @deprecated
+ *
+ * @param string $file_path The file path.
+ * @return string The date.
+ */
+function imagify_get_file_date( $file_path ) {
+ _deprecated_function( __FUNCTION__ . '()', '1.7.1', 'imagify_get_filesystem()->get_date( $file_path )' );
+
+ return imagify_get_filesystem()->get_date( $file_path );
+}
+
+/**
+ * Get a clean value of ABSPATH that can be used in string replacements.
+ *
+ * @since 1.6.8
+ * @since 1.7.1 Deprecated.
+ * @author Grégory Viguier
+ * @deprecated
+ *
+ * @return string The path to WordPress' root folder.
+ */
+function imagify_get_abspath() {
+ _deprecated_function( __FUNCTION__ . '()', '1.7.1', 'imagify_get_filesystem()->get_abspath()' );
+
+ return imagify_get_filesystem()->get_abspath();
+}
+
+/**
+ * Make an absolute path relative to WordPress' root folder.
+ * Also works for files from registered symlinked plugins.
+ *
+ * @since 1.6.10
+ * @since 1.7 The parameter $base is added.
+ * @since 1.7.1 Deprecated.
+ * @author Grégory Viguier
+ * @deprecated
+ *
+ * @param string $file_path An absolute path.
+ * @param string $base A base path to use instead of ABSPATH.
+ * @return string|bool A relative path. Can return the absolute path or false in case of a failure.
+ */
+function imagify_make_file_path_relative( $file_path, $base = '' ) {
+ _deprecated_function( __FUNCTION__ . '()', '1.7.1', 'imagify_get_filesystem()->make_path_relative( $file_path, $base )' );
+
+ return imagify_get_filesystem()->make_path_relative( $file_path, $base );
+}
+
+/**
+ * Tell if a file is symlinked.
+ *
+ * @since 1.7
+ * @since 1.7.1 Deprecated.
+ * @author Grégory Viguier
+ * @deprecated
+ *
+ * @param string $file_path An absolute path.
+ * @return bool
+ */
+function imagify_file_is_symlinked( $file_path ) {
+ _deprecated_function( __FUNCTION__ . '()', '1.7.1', 'imagify_get_filesystem()->is_symlinked( $file_path )' );
+
+ return imagify_get_filesystem()->is_symlinked( $file_path );
+}
+
+/**
+ * Determine if the Imagify API key is valid.
+ *
+ * @since 1.0
+ * @since 1.7.1 Deprecated.
+ * @deprecated
+ *
+ * @return bool True if the API key is valid.
+ */
+function imagify_valid_key() {
+ _deprecated_function( __FUNCTION__ . '()', '1.7.1', 'Imagify_Requirements::is_api_key_valid()' );
+
+ return Imagify_Requirements::is_api_key_valid();
+}
+
+/**
+ * Check if external requests are blocked for Imagify.
+ *
+ * @since 1.0
+ * @since 1.7.1 Deprecated.
+ * @deprecated
+ *
+ * @return bool True if Imagify API can't be called.
+ */
+function is_imagify_blocked() {
+ _deprecated_function( __FUNCTION__ . '()', '1.7.1', 'Imagify_Requirements::is_imagify_blocked()' );
+
+ return Imagify_Requirements::is_imagify_blocked();
+}
+
+/**
+ * Determine if the Imagify API is available by checking the API version.
+ *
+ * @since 1.0
+ * @since 1.7.1 Deprecated.
+ * @deprecated
+ *
+ * @return bool True if the Imagify API is available.
+ */
+function is_imagify_servers_up() {
+ _deprecated_function( __FUNCTION__ . '()', '1.7.1', 'Imagify_Requirements::is_api_up()' );
+
+ return Imagify_Requirements::is_api_up();
+}
+
+/**
+ * Auto-optimize when a new attachment is generated.
+ *
+ * @since 1.0
+ * @since 1.5 Async job.
+ * @since 1.8.4 Deprecated
+ * @see Imagify_Admin_Ajax_Post_Deprecated::imagify_async_optimize_upload_new_media_callback()
+ * @deprecated
+ *
+ * @param array $metadata An array of attachment meta data.
+ * @param int $attachment_id Current attachment ID.
+ * @return array
+ */
+function _imagify_optimize_attachment( $metadata, $attachment_id ) {
+ _deprecated_function( __FUNCTION__ . '()', '1.8.4', 'Imagify_Auto_Optimization::get_instance()->store_upload_ids()' );
+
+ if ( ! Imagify_Requirements::is_api_key_valid() || ! get_imagify_option( 'auto_optimize' ) ) {
+ return $metadata;
+ }
+
+ /**
+ * Allow to prevent automatic optimization for a specific attachment.
+ *
+ * @since 1.6.12
+ * @author Grégory Viguier
+ *
+ * @param bool $optimize True to optimize, false otherwise.
+ * @param int $attachment_id Attachment ID.
+ * @param array $metadata An array of attachment meta data.
+ */
+ $optimize = apply_filters( 'imagify_auto_optimize_attachment', true, $attachment_id, $metadata );
+
+ if ( ! $optimize ) {
+ return $metadata;
+ }
+
+ $context = 'wp';
+ $action = 'imagify_async_optimize_upload_new_media';
+ $_ajax_nonce = wp_create_nonce( 'new_media-' . $attachment_id );
+
+ imagify_do_async_job( compact( 'action', '_ajax_nonce', 'metadata', 'attachment_id', 'context' ) );
+
+ return $metadata;
+}
+
+/**
+ * Optimize an attachment after being resized.
+ *
+ * @since 1.3.6
+ * @since 1.4 Async job.
+ * @since 1.8.4 Deprecated
+ * @deprecated
+ */
+function _imagify_optimize_save_image_editor_file() {
+ _deprecated_function( __FUNCTION__ . '()', '1.8.4' );
+
+ if ( ! isset( $_POST['action'], $_POST['do'], $_POST['postid'] ) || 'image-editor' !== $_POST['action'] || 'open' === $_POST['do'] ) { // WPCS: CSRF ok.
+ return;
+ }
+
+ $attachment_id = absint( $_POST['postid'] );
+
+ if ( ! $attachment_id || ! Imagify_Requirements::is_api_key_valid() ) {
+ return;
+ }
+
+ check_ajax_referer( 'image_editor-' . $attachment_id );
+
+ $attachment = get_imagify_attachment( 'wp', $attachment_id, 'save_image_editor_file' );
+
+ if ( ! $attachment->get_data() ) {
+ return;
+ }
+
+ $body = $_POST;
+ $body['action'] = 'imagify_async_optimize_save_image_editor_file';
+
+ imagify_do_async_job( $body );
+}
+
+
+/**
+ * Display an admin notice informing that the current WP version is lower than the required one.
+ *
+ * @since 1.8.1
+ * @since 1.9 Deprecated
+ * @author Grégory Viguier
+ * @deprecated
+ */
+function imagify_wp_version_notice() {
+ global $wp_version;
+
+ _deprecated_function( __FUNCTION__ . '()', '1.9', 'Imagify_Requirements_Check->print_notice()' );
+
+ if ( is_multisite() ) {
+ if ( ! function_exists( 'is_plugin_active_for_network' ) ) {
+ require_once ABSPATH . 'wp-admin/includes/plugin.php';
+ }
+
+ $is_active = is_plugin_active_for_network( plugin_basename( IMAGIFY_FILE ) );
+ $capacity = $is_active ? 'manage_network_options' : 'manage_options';
+ } else {
+ $capacity = 'manage_options';
+ }
+
+ if ( ! current_user_can( $capacity ) ) {
+ return;
+ }
+
+ echo '';
+ echo '' . __( 'Notice:', 'imagify' ) . ' ';
+ /* translators: 1 is this plugin name, 2 is the required WP version, 3 is the current WP version. */
+ printf( __( '%1$s requires WordPress %2$s minimum, your website is actually running version %3$s.', 'imagify' ), 'Imagify ', '' . IMAGIFY_WP_MIN . '', '' . $wp_version . '' );
+ echo '
';
+}
+
+/**
+ * Delete the backup file when an attachement is deleted.
+ *
+ * @since 1.0
+ * @since 1.9 Deprecated
+ * @deprecated
+ *
+ * @param int $post_id Attachment ID.
+ */
+function _imagify_delete_backup_file( $post_id ) {
+ _deprecated_function( __FUNCTION__ . '()', '1.9', 'imagify_cleanup_after_media_deletion( $post_id )' );
+
+ get_imagify_attachment( 'wp', $post_id, 'delete_attachment' )->delete_backup();
+}
+
+/**
+ * Classes autoloader.
+ *
+ * @since 1.6.12
+ * @since 1.9 Deprecated
+ * @author Grégory Viguier
+ * @deprecated
+ *
+ * @param string $class Name of the class to include.
+ */
+function imagify_autoload( $class ) {
+ static $strtolower;
+
+ _deprecated_function( __FUNCTION__ . '()', '1.9' );
+
+ if ( ! isset( $strtolower ) ) {
+ $strtolower = function_exists( 'mb_strtolower' ) ? 'mb_strtolower' : 'strtolower';
+ }
+
+ // Generic classes.
+ $classes = array(
+ 'Imagify_Abstract_Attachment' => 1,
+ 'Imagify_Abstract_Background_Process' => 1,
+ 'Imagify_Abstract_Cron' => 1,
+ 'Imagify_Abstract_DB' => 1,
+ 'Imagify_Abstract_Options' => 1,
+ 'Imagify_Admin_Ajax_Post' => 1,
+ 'Imagify_Assets' => 1,
+ 'Imagify_Attachment' => 1,
+ 'Imagify_Auto_Optimization' => 1,
+ 'Imagify_Cron_Library_Size' => 1,
+ 'Imagify_Cron_Rating' => 1,
+ 'Imagify_Cron_Sync_Files' => 1,
+ 'Imagify_Custom_Folders' => 1,
+ 'Imagify_Data' => 1,
+ 'Imagify_DB' => 1,
+ 'Imagify_File_Attachment' => 1,
+ 'Imagify_Files_DB' => 1,
+ 'Imagify_Files_Iterator' => 1,
+ 'Imagify_Files_List_Table' => 1,
+ 'Imagify_Files_Recursive_Iterator' => 1,
+ 'Imagify_Files_Scan' => 1,
+ 'Imagify_Files_Stats' => 1,
+ 'Imagify_Filesystem' => 1,
+ 'Imagify_Folders_DB' => 1,
+ 'Imagify_Notices' => 1,
+ 'Imagify_Options' => 1,
+ 'Imagify_Requirements' => 1,
+ 'Imagify_Settings' => 1,
+ 'Imagify_User' => 1,
+ 'Imagify_Views' => 1,
+ 'Imagify' => 1,
+ );
+
+ if ( isset( $classes[ $class ] ) ) {
+ $class = str_replace( '_', '-', call_user_func( $strtolower, $class ) );
+ include IMAGIFY_PATH . 'inc/classes/class-' . $class . '.php';
+ return;
+ }
+
+ // Third party classes.
+ $classes = array(
+ 'Imagify_AS3CF_Attachment' => 'amazon-s3-and-cloudfront',
+ 'Imagify_AS3CF' => 'amazon-s3-and-cloudfront',
+ 'Imagify_Enable_Media_Replace' => 'enable-media-replace',
+ 'Imagify_Formidable_Pro' => 'formidable-pro',
+ 'Imagify_NGG_Attachment' => 'nextgen-gallery',
+ 'Imagify_NGG_DB' => 'nextgen-gallery',
+ 'Imagify_NGG_Dynamic_Thumbnails_Background_Process' => 'nextgen-gallery',
+ 'Imagify_NGG_Storage' => 'nextgen-gallery',
+ 'Imagify_NGG' => 'nextgen-gallery',
+ 'Imagify_Regenerate_Thumbnails' => 'regenerate-thumbnails',
+ 'Imagify_WP_Retina_2x' => 'wp-retina-2x',
+ 'Imagify_WP_Retina_2x_Core' => 'wp-retina-2x',
+ 'Imagify_WP_Time_Capsule' => 'wp-time-capsule',
+ );
+
+ if ( isset( $classes[ $class ] ) ) {
+ $folder = $classes[ $class ];
+ $class = str_replace( '_', '-', call_user_func( $strtolower, $class ) );
+ include IMAGIFY_PATH . 'inc/3rd-party/' . $folder . '/inc/classes/class-' . $class . '.php';
+ }
+}
+
+/**
+ * Tell if the attachment has the required WP metadata.
+ *
+ * @since 1.6.12
+ * @since 1.7 Also checks that the '_wp_attached_file' meta is valid (not a URL or anything funny).
+ * @since 1.9 Deprecated
+ * @author Grégory Viguier
+ * @deprecated
+ *
+ * @param int $attachment_id The attachment ID.
+ * @return bool
+ */
+function imagify_attachment_has_required_metadata( $attachment_id ) {
+ _deprecated_function( __FUNCTION__ . '()', '1.9', '( new Imagify\\Media\\WP( $attachment_id ) )->has_required_media_data() )' );
+
+ $file = get_post_meta( $attachment_id, '_wp_attached_file', true );
+
+ if ( ! $file || preg_match( '@://@', $file ) || preg_match( '@^.:\\\@', $file ) ) {
+ return false;
+ }
+
+ return (bool) wp_get_attachment_metadata( $attachment_id, true );
+}
+
+/**
+ * Get the default Bulk Optimization buffer size.
+ *
+ * @since 1.5.10
+ * @since 1.7 Added $sizes parameter.
+ * @since 1.9 Deprecated
+ * @author Jonathan Buttigieg
+ * @deprecated
+ *
+ * @param int $sizes Number of image sizes per item (attachment).
+ * @return int The buffer size.
+ */
+function get_imagify_bulk_buffer_size( $sizes = false ) {
+ _deprecated_function( __FUNCTION__ . '()', '1.9' );
+
+ if ( ! $sizes ) {
+ $sizes = count( get_imagify_thumbnail_sizes() );
+ }
+
+ switch ( true ) {
+ case ( $sizes >= 10 ):
+ return 1;
+
+ case ( $sizes >= 8 ):
+ return 2;
+
+ case ( $sizes >= 6 ):
+ return 3;
+
+ default:
+ return 4;
+ }
+}
+
+/**
+ * Get the Imagify attachment class name depending to a context.
+ *
+ * @since 1.5
+ * @since 1.6.6 $attachment_id and $identifier have been added.
+ * @since 1.9 Deprecated
+ * @author Jonathan Buttigieg
+ * @deprecated
+ *
+ * @param string $context The context to determine the class name.
+ * @param int $attachment_id The attachment ID.
+ * @param string $identifier An identifier.
+ * @return string The Imagify attachment class name.
+ */
+function get_imagify_attachment_class_name( $context, $attachment_id, $identifier ) {
+ _deprecated_function( __FUNCTION__ . '()', '1.9', 'imagify_get_optimization_process_class_name( $context )' );
+
+ $context = $context ? $context : 'wp';
+
+ if ( 'wp' !== $context && 'wp' === strtolower( $context ) ) {
+ $context = 'wp';
+ }
+
+ /**
+ * Filter the context used for the optimization.
+ *
+ * @since 1.6.6
+ * @author Grégory Viguier
+ *
+ * @param string $context The context.
+ * @param int $attachment_id The attachment ID.
+ * @param string $identifier An identifier.
+ */
+ $context = apply_filters( 'imagify_optimize_attachment_context', $context, $attachment_id, $identifier );
+
+ return 'Imagify_' . ( 'wp' !== $context ? $context . '_' : '' ) . 'Attachment';
+}
+
+/**
+ * Get the Imagify attachment instance depending to a context.
+ *
+ * @since 1.6.13
+ * @since 1.9 Deprecated
+ * @author Grégory Viguier
+ * @deprecated
+ *
+ * @param string $context The context to determine the class name.
+ * @param int $attachment_id The attachment ID.
+ * @param string $identifier An identifier.
+ * @return object The Imagify attachment instance.
+ */
+function get_imagify_attachment( $context, $attachment_id, $identifier ) {
+ _deprecated_function( __FUNCTION__ . '()', '1.9', 'imagify_get_optimization_process( $media_id, $context )' );
+
+ $class_name = get_imagify_attachment_class_name( $context, $attachment_id, $identifier );
+ return new $class_name( $attachment_id );
+}
+
+/**
+ * Optimize a file with Imagify.
+ *
+ * @since 1.0
+ * @since 1.9 Deprecated
+ * @deprecated
+ *
+ * @param string $file_path Absolute path to the file.
+ * @param array $args {
+ * Optional. An array of arguments.
+ *
+ * @type bool $backup Force a backup of the original file.
+ * @type int $optimization_level The optimization level (2=ultra, 1=aggressive, 0=normal).
+ * @type bool $keep_exif To keep exif data or not.
+ * }
+ * @return array|WP_Error Optimized image data. A WP_Error object on error.
+ */
+function do_imagify( $file_path, $args = array() ) {
+ _deprecated_function( __FUNCTION__ . '()', '1.9', '(new Imagify\\Optimization\\File( $file_path ))->optimize( $args )' );
+
+ $args = array_merge( array(
+ 'backup' => get_imagify_option( 'backup' ),
+ 'optimization_level' => get_imagify_option( 'optimization_level' ),
+ 'keep_exif' => get_imagify_option( 'exif' ),
+ 'context' => 'wp',
+ 'resized' => false,
+ 'original_size' => 0,
+ 'backup_path' => null,
+ ), $args );
+
+ /**
+ * Filter the attachment path.
+ *
+ * @since 1.2
+ *
+ * @param string $file_path The attachment path.
+ */
+ $file_path = apply_filters( 'imagify_file_path', $file_path );
+
+ // Check that file path isn't empty.
+ if ( ! $file_path ) {
+ return new WP_Error( 'empty_path', __( 'File path is empty.', 'imagify' ) );
+ }
+
+ // Check if curl is available.
+ if ( ! Imagify_Requirements::supports_curl() ) {
+ return new WP_Error( 'curl', __( 'cURL is not available on the server.', 'imagify' ) );
+ }
+
+ $filesystem = imagify_get_filesystem();
+
+ // Check if imageMagick or GD is available.
+ if ( $filesystem->is_image( $file_path ) && ! Imagify_Requirements::supports_image_editor() ) {
+ return new WP_Error( 'image_editor', sprintf(
+ /* translators: %s is a "More info?" link. */
+ __( 'No php extensions are available to edit images on the server. ImageMagick or GD is required. %s', 'imagify' ),
+ '' . __( 'More info?', 'imagify' ) . ' '
+ ) );
+ }
+
+ // Check if external HTTP requests are blocked.
+ if ( Imagify_Requirements::is_imagify_blocked() ) {
+ return new WP_Error( 'http_block_external', __( 'External HTTP requests are blocked.', 'imagify' ) );
+ }
+
+ // Check if the Imagify servers & the API are accessible.
+ if ( ! Imagify_Requirements::is_api_up() ) {
+ return new WP_Error( 'api_server_down', __( 'Sorry, our servers are temporarily unavailable. Please, try again in a couple of minutes.', 'imagify' ) );
+ }
+
+ // Check that the file exists.
+ if ( ! $filesystem->is_writable( $file_path ) || ! $filesystem->is_file( $file_path ) ) {
+ /* translators: %s is a file path. */
+ return new WP_Error( 'file_not_found', sprintf( __( 'Could not find %s.', 'imagify' ), $filesystem->make_path_relative( $file_path ) ) );
+ }
+
+ // Check that the file directory is writable.
+ if ( ! $filesystem->is_writable( $filesystem->dir_path( $file_path ) ) ) {
+ /* translators: %s is a file path. */
+ return new WP_Error( 'not_writable', sprintf( __( '%s is not writable.', 'imagify' ), $filesystem->make_path_relative( $filesystem->dir_path( $file_path ) ) ) );
+ }
+
+ /**
+ * Fires before to optimize the Image with Imagify.
+ *
+ * @since 1.0
+ *
+ * @param string $file_path Absolute path to the image file.
+ * @param bool $backup Force a backup of the original file.
+ */
+ do_action( 'before_do_imagify', $file_path, $args['backup'] );
+
+ // Create a backup file before sending to optimization (to make sure we can backup the file).
+ $do_backup = $args['backup'] && ! $args['resized'];
+
+ if ( $do_backup ) {
+ $backup_result = imagify_backup_file( $file_path, $args['backup_path'] );
+
+ if ( is_wp_error( $backup_result ) ) {
+ // Stop the process if we can't backup the file.
+ return $backup_result;
+ }
+ }
+
+ // Send image for optimization and fetch the response.
+ $response = upload_imagify_image( array(
+ 'image' => $file_path,
+ 'data' => wp_json_encode( array(
+ 'aggressive' => ( 1 === (int) $args['optimization_level'] ),
+ 'ultra' => ( 2 === (int) $args['optimization_level'] ),
+ 'keep_exif' => $args['keep_exif'],
+ 'context' => $args['context'],
+ 'original_size' => $args['original_size'],
+ ) ),
+ ) );
+
+ // Check status code.
+ if ( is_wp_error( $response ) ) {
+ return new WP_Error( 'api_error', $response->get_error_message() );
+ }
+
+ if ( ! function_exists( 'download_url' ) ) {
+ require_once ABSPATH . 'wp-admin/includes/file.php';
+ }
+
+ $temp_file = download_url( $response->image );
+
+ if ( is_wp_error( $temp_file ) ) {
+ return new WP_Error( 'temp_file_not_found', $temp_file->get_error_message() );
+ }
+
+ $filesystem->move( $temp_file, $file_path, true );
+
+ /**
+ * Fires after to optimize the Image with Imagify.
+ *
+ * @since 1.0
+ *
+ * @param string $file_path Absolute path to the image file.
+ * @param bool $backup Force a backup of the original file.
+ */
+ do_action( 'after_do_imagify', $file_path, $args['backup'] );
+
+ return $response;
+}
+
+/**
+ * Backup a file.
+ *
+ * @since 1.6.8
+ * @since 1.9 Deprecated
+ * @author Grégory Viguier
+ * @deprecated
+ *
+ * @param string $file_path The file path.
+ * @param string $backup_path The backup path. This is useful for NGG for example, who doesn't store the backups in our backup folder.
+ * @return bool|object True on success. False if the backup option is not enabled. A WP_Error object on failure.
+ */
+function imagify_backup_file( $file_path, $backup_path = null ) {
+ _deprecated_function( __FUNCTION__ . '()', '1.9', '(new Imagify\\Optimization\\File( $file_path ))->backup( $backup_path )' );
+
+ if ( ! get_imagify_option( 'backup' ) ) {
+ return false;
+ }
+
+ // Make sure the source path is not empty.
+ if ( ! $file_path ) {
+ return new WP_Error( 'empty_path', __( 'The file path is empty.', 'imagify' ) );
+ }
+
+ $filesystem = imagify_get_filesystem();
+
+ // Make sure the filesystem has no errors.
+ if ( ! empty( $filesystem->errors->errors ) ) {
+ return new WP_Error( 'filesystem_error', __( 'Filesystem error.', 'imagify' ), $filesystem->errors );
+ }
+
+ // Make sure the source file exists.
+ if ( ! $filesystem->exists( $file_path ) ) {
+ return new WP_Error( 'source_doesnt_exist', __( 'The file to backup does not exist.', 'imagify' ), array(
+ 'file_path' => $filesystem->make_path_relative( $file_path ),
+ ) );
+ }
+
+ if ( ! isset( $backup_path ) ) {
+ // Make sure the backup directory is writable.
+ if ( ! Imagify_Requirements::attachments_backup_dir_is_writable() ) {
+ return new WP_Error( 'backup_dir_not_writable', __( 'The backup directory is not writable.', 'imagify' ) );
+ }
+
+ $backup_path = get_imagify_attachment_backup_path( $file_path );
+ }
+
+ // Make sure the uploads directory has no errors.
+ if ( ! $backup_path ) {
+ return new WP_Error( 'wp_upload_error', __( 'Error while retrieving the uploads directory path.', 'imagify' ) );
+ }
+
+ // Create sub-directories.
+ $filesystem->make_dir( $filesystem->dir_path( $backup_path ) );
+
+ /**
+ * Allow to overwrite the backup file if it already exists.
+ *
+ * @since 1.6.9
+ * @author Grégory Viguier
+ *
+ * @param bool $overwrite Whether to overwrite the backup file.
+ * @param string $file_path The file path.
+ * @param string $backup_path The backup path.
+ */
+ $overwrite = apply_filters( 'imagify_backup_overwrite_backup', false, $file_path, $backup_path );
+
+ // Copy the file.
+ $filesystem->copy( $file_path, $backup_path, $overwrite, FS_CHMOD_FILE );
+
+ // Make sure the backup copy exists.
+ if ( ! $filesystem->exists( $backup_path ) ) {
+ return new WP_Error( 'backup_doesnt_exist', __( 'The file could not be saved.', 'imagify' ), array(
+ 'file_path' => $filesystem->make_path_relative( $file_path ),
+ 'backup_path' => $filesystem->make_path_relative( $backup_path ),
+ ) );
+ }
+
+ return true;
+}
+
+if ( is_admin() ) :
+
+ /**
+ * Fix the capability for our capacity filter hook
+ *
+ * @since 1.0
+ * @since 1.7 Deprecated.
+ * @author Jonathan
+ * @deprecated
+ */
+ function _imagify_correct_capability_for_options_page() {
+ _deprecated_function( __FUNCTION__ . '()', '1.7', 'Imagify_Settings::get_instance()->get_capability()' );
+
+ return Imagify_Settings::get_instance()->get_capability();
+ }
+
+ /**
+ * Tell to WordPress to be confident with our setting, we are clean!
+ *
+ * @since 1.0
+ * @since 1.7 Deprecated.
+ * @author Jonathan
+ * @deprecated
+ */
+ function _imagify_register_setting() {
+ _deprecated_function( __FUNCTION__ . '()', '1.7', 'Imagify_Settings::get_instance()->register()' );
+
+ Imagify_Settings::get_instance()->register();
+ }
+
+ /**
+ * Filter specific options before its value is (maybe) serialized and updated.
+ *
+ * @since 1.0
+ * @since 1.7 Deprecated.
+ * @author Jonathan
+ * @deprecated
+ *
+ * @param mixed $value The new option value.
+ * @param mixed $old_value The old option value.
+ * @return array The new option value.
+ */
+ function _imagify_pre_update_option( $value, $old_value ) {
+ _deprecated_function( __FUNCTION__ . '()', '1.7', 'Imagify_Settings::get_instance()->sanitize_and_validate( $value )' );
+
+ return Imagify_Settings::get_instance()->sanitize_and_validate( $value );
+ }
+
+ /**
+ * If the user clicked the "Save & Go to Bulk Optimizer" button, set a redirection to the bulk optimizer.
+ * We use this hook because it can be triggered even if the option value hasn't changed.
+ *
+ * @since 1.6.8
+ * @since 1.7 Deprecated.
+ * @author Grégory Viguier
+ * @deprecated
+ *
+ * @param mixed $value The new, unserialized option value.
+ * @param mixed $old_value The old option value.
+ * @return mixed The option value.
+ */
+ function _imagify_maybe_set_redirection_before_save_options( $value, $old_value ) {
+ _deprecated_function( __FUNCTION__ . '()', '1.7', 'Imagify_Settings::get_instance()->maybe_set_redirection( $value, $old_value )' );
+
+ return Imagify_Settings::get_instance()->maybe_set_redirection( $value, $old_value );
+ }
+
+ /**
+ * Used to launch some actions after saving the network options.
+ *
+ * @since 1.6.5
+ * @since 1.7 Deprecated.
+ * @author Grégory Viguier
+ * @deprecated
+ *
+ * @param string $option Name of the network option.
+ * @param mixed $value Current value of the network option.
+ * @param mixed $old_value Old value of the network option.
+ */
+ function _imagify_after_save_network_options( $option, $value, $old_value ) {
+ _deprecated_function( __FUNCTION__ . '()', '1.7', 'Imagify_Settings::get_instance()->after_save_network_options( $option, $value, $old_value )' );
+
+ Imagify_Settings::get_instance()->after_save_network_options( $option, $value, $old_value );
+ }
+
+ /**
+ * Used to launch some actions after saving the options.
+ *
+ * @since 1.0
+ * @since 1.5 Used to redirect user to Bulk Optimizer (if requested).
+ * @since 1.6.8 Not used to redirect user to Bulk Optimizer anymore: see _imagify_maybe_set_redirection_before_save_options().
+ * @since 1.7 Deprecated.
+ * @author Jonathan
+ * @deprecated
+ *
+ * @param mixed $old_value The old option value.
+ * @param mixed $value The new option value.
+ */
+ function _imagify_after_save_options( $old_value, $value ) {
+ _deprecated_function( __FUNCTION__ . '()', '1.7', 'Imagify_Settings::get_instance()->after_save_options( $old_value, $value )' );
+
+ Imagify_Settings::get_instance()->after_save_options( $old_value, $value );
+ }
+
+ /**
+ * `options.php` do not handle site options. Let's use `admin-post.php` for multisite installations.
+ *
+ * @since 1.0
+ * @since 1.7 Deprecated.
+ * @deprecated
+ */
+ function _imagify_update_site_option_on_network() {
+ _deprecated_function( __FUNCTION__ . '()', '1.7', 'Imagify_Settings::get_instance()->update_site_option_on_network()' );
+
+ Imagify_Settings::get_instance()->update_site_option_on_network();
+ }
+
+ /**
+ * Display the plan chooser section.
+ *
+ * @since 1.6
+ * @since 1.7 Deprecated.
+ * @author Geoffrey
+ * @deprecated
+ *
+ * @return string HTML.
+ */
+ function get_imagify_new_to_imagify() {
+ _deprecated_function( __FUNCTION__ . '()', '1.7', 'imagify_get_template( \'part-new-to-imagify\' )' );
+
+ return imagify_get_template( 'part-new-to-imagify' );
+ }
+
+ /**
+ * Get the payment modal HTML.
+ *
+ * @since 1.6
+ * @since 1.6.3 Include discount banners.
+ * @since 1.7 Deprecated.
+ * @author Geoffrey
+ * @deprecated
+ */
+ function imagify_payment_modal() {
+ _deprecated_function( __FUNCTION__ . '()', '1.7', 'Imagify_Views::get_instance()->print_template( \'modal-payment\' )' );
+
+ Imagify_Views::get_instance()->print_template( 'modal-payment' );
+ }
+
+ /**
+ * Print the discount banner used inside Payment Modal.
+ *
+ * @since 1.6.3
+ * @since 1.7 Deprecated.
+ * @author Geoffrey Crofte
+ * @deprecated
+ */
+ function imagify_print_discount_banner() {
+ _deprecated_function( __FUNCTION__ . '()', '1.7', 'Imagify_Views::get_instance()->print_template( \'part-discount-banner\' )' );
+
+ Imagify_Views::get_instance()->print_template( 'part-discount-banner' );
+ }
+
+ /**
+ * Return the formatted price present in pricing tables.
+ *
+ * @since 1.6
+ * @since 1.7 Deprecated.
+ * @author Geoffrey
+ * @deprecated
+ *
+ * @param float $value The price value.
+ * @return string The markuped price.
+ */
+ function get_imagify_price_table_format( $value ) {
+ _deprecated_function( __FUNCTION__ . '()', '1.7' );
+
+ $v = explode( '.', (string) $value );
+
+ return '' . $v[0] . ' .' . ( strlen( $v[1] ) === 1 ? $v[1] . '0' : $v[1] ) . ' ';
+ }
+
+ /**
+ * Add submenu in menu "Settings".
+ *
+ * @since 1.0
+ * @since 1.7 Deprecated.
+ * @deprecated
+ */
+ function _imagify_settings_menu() {
+ _deprecated_function( __FUNCTION__ . '()', '1.7', 'Imagify_Views::get_instance()->add_network_menus()' );
+
+ Imagify_Views::get_instance()->add_network_menus();
+ }
+
+ /**
+ * Add submenu in menu "Media".
+ *
+ * @since 1.0
+ * @since 1.7 Deprecated.
+ * @deprecated
+ */
+ function _imagify_bulk_optimization_menu() {
+ _deprecated_function( __FUNCTION__ . '()', '1.7', 'Imagify_Views::get_instance()->add_site_menus()' );
+
+ Imagify_Views::get_instance()->add_site_menus();
+ }
+
+ /**
+ * The main settings page.
+ *
+ * @since 1.0
+ * @since 1.7 Deprecated.
+ * @deprecated
+ */
+ function _imagify_display_options_page() {
+ _deprecated_function( __FUNCTION__ . '()', '1.7', 'Imagify_Views::get_instance()->display_settings_page()' );
+
+ Imagify_Views::get_instance()->display_settings_page();
+ }
+
+ /**
+ * The bulk optimization page.
+ *
+ * @since 1.0
+ * @since 1.7 Deprecated.
+ * @deprecated
+ */
+ function _imagify_display_bulk_page() {
+ _deprecated_function( __FUNCTION__ . '()', '1.7', 'Imagify_Views::get_instance()->display_bulk_page()' );
+
+ Imagify_Views::get_instance()->display_bulk_page();
+ }
+
+ /**
+ * Add link to the plugin configuration pages.
+ *
+ * @since 1.0
+ * @since 1.7 Deprecated.
+ *
+ * @param array $actions An array of action links.
+ * @return array
+ */
+ function _imagify_plugin_action_links( $actions ) {
+ _deprecated_function( __FUNCTION__ . '()', '1.7', 'Imagify_Views::get_instance()->plugin_action_links( $actions )' );
+
+ return Imagify_Views::get_instance()->plugin_action_links( $actions );
+ }
+
+ /**
+ * Get stats data for a specific folder type.
+ *
+ * @since 1.7
+ * @since 1.9 Deprecated
+ * @author Grégory Viguier
+ * @deprecated
+ *
+ * @param string $context A context.
+ * @return array
+ */
+ function imagify_get_folder_type_data( $context ) {
+ _deprecated_function( __FUNCTION__ . '()', '1.9', 'Imagify_Admin_Ajax_Post::get_instance()->get_bulk_instance( $context )->get_context_data()' );
+
+ /**
+ * Get the data.
+ */
+ switch ( $context ) {
+ case 'wp':
+ $total_saving_data = imagify_count_saving_data();
+ $data = array(
+ 'images-optimized' => imagify_count_optimized_attachments(),
+ 'errors' => imagify_count_error_attachments(),
+ 'optimized' => $total_saving_data['optimized_size'],
+ 'original' => $total_saving_data['original_size'],
+ 'errors_url' => get_imagify_admin_url( 'folder-errors', $context ),
+ );
+ break;
+
+ case 'custom-folders':
+ $data = array(
+ 'images-optimized' => Imagify_Files_Stats::count_optimized_files(),
+ 'errors' => Imagify_Files_Stats::count_error_files(),
+ 'optimized' => Imagify_Files_Stats::get_optimized_size(),
+ 'original' => Imagify_Files_Stats::get_original_size(),
+ 'errors_url' => get_imagify_admin_url( 'folder-errors', $context ),
+ );
+ break;
+
+ default:
+ /**
+ * Provide custom folder type data.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ *
+ * @param array $data An array with keys corresponding to cell classes, and values formatted with HTML.
+ * @param string $context A context.
+ */
+ $data = apply_filters( 'imagify_get_folder_type_data', [], $context );
+
+ if ( ! $data || ! is_array( $data ) ) {
+ return [];
+ }
+ }
+
+ /**
+ * Format the data.
+ */
+ /* translators: %s is a formatted number, dont use %d. */
+ $data['images-optimized'] = sprintf( _n( '%s Media File Optimized', '%s Media Files Optimized', $data['images-optimized'], 'imagify' ), '' . number_format_i18n( $data['images-optimized'] ) . ' ' );
+
+ if ( $data['errors'] ) {
+ /* translators: %s is a formatted number, dont use %d. */
+ $data['errors'] = sprintf( _n( '%s Error', '%s Errors', $data['errors'], 'imagify' ), '' . number_format_i18n( $data['errors'] ) . ' ' );
+ $data['errors'] .= ' ' . __( 'View Errors', 'imagify' ) . ' ';
+ } else {
+ $data['errors'] = '';
+ }
+
+ if ( $data['optimized'] ) {
+ $data['optimized'] = '' . __( 'Optimized Filesize', 'imagify' ) . ' ' . imagify_size_format( $data['optimized'], 2 );
+ } else {
+ $data['optimized'] = '';
+ }
+
+ if ( $data['original'] ) {
+ $data['original'] = '' . __( 'Original Filesize', 'imagify' ) . ' ' . imagify_size_format( $data['original'], 2 );
+ } else {
+ $data['original'] = '';
+ }
+
+ unset( $data['errors_url'] );
+
+ return $data;
+ }
+
+ /**
+ * Tell if the current user has the required ability to operate Imagify.
+ *
+ * @since 1.6.11
+ * @since 1.9
+ * @see imagify_get_capacity()
+ * @author Grégory Viguier
+ * @deprecated
+ *
+ * @param string $describer Capacity describer. See imagify_get_capacity() for possible values. Can also be a "real" user capacity.
+ * @param int $post_id A post ID.
+ * @return bool
+ */
+ function imagify_current_user_can( $describer = 'manage', $post_id = null ) {
+ static $can_upload;
+
+ _deprecated_function( __FUNCTION__ . '()', '1.9', 'imagify_get_context( $context )->current_user_can( $describer, $media_id )' );
+
+ $post_id = $post_id ? $post_id : null;
+ $capacity = imagify_get_capacity( $describer );
+ $user_can = false;
+
+ if ( 'manage' !== $describer && 'bulk-optimize' !== $describer && 'optimize-file' !== $describer ) {
+ // Describers that are not 'manage', 'bulk-optimize', and 'optimize-file' need an additional test for 'upload_files'.
+ if ( ! isset( $can_upload ) ) {
+ $can_upload = current_user_can( 'upload_files' );
+ }
+
+ if ( $can_upload ) {
+ if ( 'upload_files' === $capacity ) {
+ // We already know it's true.
+ $user_can = true;
+ } else {
+ $user_can = current_user_can( $capacity, $post_id );
+ }
+ }
+ } else {
+ $user_can = current_user_can( $capacity );
+ }
+
+ /**
+ * Filter the current user ability to operate Imagify.
+ *
+ * @since 1.6.11
+ *
+ * @param bool $user_can Tell if the current user has the required ability to operate Imagify.
+ * @param string $capacity The user capacity.
+ * @param string $describer Capacity describer. See imagify_get_capacity() for possible values. Can also be a "real" user capacity.
+ * @param int $post_id A post ID (a gallery ID for NGG).
+ */
+ return apply_filters( 'imagify_current_user_can', $user_can, $capacity, $describer, $post_id );
+ }
+
+ /**
+ * Get user capacity to operate Imagify.
+ *
+ * @since 1.6.5
+ * @since 1.6.11 Uses a string as describer for the first argument.
+ * @since 1.9 Deprecated.
+ * @author Grégory Viguier
+ * @deprecated
+ *
+ * @param string $describer Capacity describer. Possible values are 'manage', 'bulk-optimize', 'manual-optimize', 'auto-optimize', and 'optimize-file'.
+ * @return string
+ */
+ function imagify_get_capacity( $describer = 'manage' ) {
+ static $edit_attachment_cap;
+
+ _deprecated_function( __FUNCTION__ . '()', '1.9', 'imagify_get_context( $context )->get_capacity( $describer )' );
+
+ // Back compat.
+ if ( ! is_string( $describer ) ) {
+ if ( $describer || ! is_multisite() ) {
+ $describer = 'bulk-optimize';
+ } else {
+ $describer = 'manage';
+ }
+ }
+
+ switch ( $describer ) {
+ case 'manage':
+ $capacity = imagify_is_active_for_network() ? 'manage_network_options' : 'manage_options';
+ break;
+
+ case 'optimize-file':
+ $capacity = is_multisite() ? 'manage_network_options' : 'manage_options';
+ break;
+
+ case 'bulk-optimize':
+ $capacity = 'manage_options';
+ break;
+
+ case 'optimize':
+ case 'restore':
+ // This is a generic capacity: don't use it unless you have no other choices!
+ if ( ! isset( $edit_attachment_cap ) ) {
+ $edit_attachment_cap = get_post_type_object( 'attachment' );
+ $edit_attachment_cap = $edit_attachment_cap ? $edit_attachment_cap->cap->edit_posts : 'edit_posts';
+ }
+
+ $capacity = $edit_attachment_cap;
+ break;
+
+ case 'manual-optimize':
+ case 'manual-restore':
+ // Must be used with an Attachment ID.
+ $capacity = 'edit_post';
+ break;
+
+ case 'auto-optimize':
+ $capacity = 'upload_files';
+ break;
+
+ default:
+ $capacity = $describer;
+ }
+
+ /**
+ * Filter the user capacity used to operate Imagify.
+ *
+ * @since 1.0
+ * @since 1.6.5 Added $force_mono parameter.
+ * @since 1.6.11 Replaced $force_mono by $describer.
+ *
+ * @param string $capacity The user capacity.
+ * @param string $describer Capacity describer. Possible values are 'manage', 'bulk-optimize', 'manual-optimize', 'auto-optimize', and 'optimize-file'.
+ */
+ return apply_filters( 'imagify_capacity', $capacity, $describer );
+ }
+
+ /**
+ * Check for user capacity.
+ *
+ * @since 1.6.10
+ * @since 1.6.11 Uses a capacity describer instead of a capacity itself.
+ * @since 1.9 Deprecated.
+ * @see imagify_get_capacity()
+ * @author Grégory Viguier
+ * @deprecated
+ *
+ * @param string $describer Capacity describer. See imagify_get_capacity() for possible values. Can also be a "real" user capacity.
+ * @param int $post_id A post ID.
+ */
+ function imagify_check_user_capacity( $describer = 'manage', $post_id = null ) {
+ _deprecated_function( __FUNCTION__ . '()', '1.9' );
+
+ if ( ! imagify_current_user_can( $describer, $post_id ) ) {
+ imagify_die();
+ }
+ }
+
+ /**
+ * Update the Heartbeat API settings.
+ *
+ * @since 1.4.5
+ * @since 1.9.3 Deprecated.
+ * @deprecated
+ *
+ * @param array $settings Heartbeat API settings.
+ * @return array
+ */
+ function _imagify_heartbeat_settings( $settings ) {
+ _deprecated_function( __FUNCTION__ . '()', '1.9.3' );
+
+ $settings['interval'] = 30;
+ return $settings;
+ }
+
+ /**
+ * Prepare the data that goes back with the Imagifybeat API.
+ *
+ * @since 1.4.5
+ * @since 1.9.3 Deprecated.
+ * @deprecated
+ *
+ * @param array $response The Imagifybeat response.
+ * @param array $data The $_POST data sent.
+ * @return array
+ */
+ function _imagify_heartbeat_received( $response, $data ) {
+ _deprecated_function( __FUNCTION__ . '()', '1.9.3', '\\Imagify\\Imagifybeat\\Actions::get_instance()->add_bulk_optimization_stats_to_response()' );
+
+ $heartbeat_id = 'imagify_bulk_data';
+
+ if ( empty( $data[ $heartbeat_id ] ) ) {
+ return $response;
+ }
+
+ $folder_types = array_flip( array_filter( $data[ $heartbeat_id ] ) );
+
+ $response[ $heartbeat_id ] = imagify_get_bulk_stats( $folder_types, array(
+ 'fullset' => true,
+ ) );
+
+ return $response;
+ }
+
+ /**
+ * Prepare the data that goes back with the Imagifybeat API.
+ *
+ * @since 1.7.1
+ * @since 1.9.3 Deprecated.
+ * @author Grégory Viguier
+ * @deprecated
+ *
+ * @param array $response The Imagifybeat response.
+ * @param array $data The $_POST data sent.
+ * @return array
+ */
+ function imagify_heartbeat_requirements_received( $response, $data ) {
+ _deprecated_function( __FUNCTION__ . '()', '1.9.3', '\\Imagify\\Imagifybeat\\Actions::get_instance()->add_requirements_to_response()' );
+
+ $heartbeat_id = 'imagify_bulk_requirements';
+
+ if ( empty( $data[ $heartbeat_id ] ) ) {
+ return $response;
+ }
+
+ $response[ $heartbeat_id ] = array(
+ 'curl_missing' => ! Imagify_Requirements::supports_curl(),
+ 'editor_missing' => ! Imagify_Requirements::supports_image_editor(),
+ 'external_http_blocked' => Imagify_Requirements::is_imagify_blocked(),
+ 'api_down' => Imagify_Requirements::is_imagify_blocked() || ! Imagify_Requirements::is_api_up(),
+ 'key_is_valid' => ! Imagify_Requirements::is_imagify_blocked() && Imagify_Requirements::is_api_up() && Imagify_Requirements::is_api_key_valid(),
+ 'is_over_quota' => ! Imagify_Requirements::is_imagify_blocked() && Imagify_Requirements::is_api_up() && Imagify_Requirements::is_api_key_valid() && Imagify_Requirements::is_over_quota(),
+ );
+
+ return $response;
+ }
+
+ /**
+ * Look for media where status has changed, compared to what Imagifybeat sends.
+ * This is used in the bulk optimization page.
+ *
+ * @since 1.9
+ * @since 1.9.3 Deprecated.
+ * @author Grégory Viguier
+ * @deprecated
+ *
+ * @param array $response The Imagifybeat response.
+ * @param array $data The $_POST data sent.
+ * @return array
+ */
+ function imagify_heartbeat_bulk_optimization_status_received( $response, $data ) {
+ _deprecated_function( __FUNCTION__ . '()', '1.9.3', '\\Imagify\\Imagifybeat\\Actions::get_instance()->add_bulk_optimization_status_to_response()' );
+
+ $heartbeat_id = 'imagify_bulk_queue';
+
+ if ( empty( $data[ $heartbeat_id ] ) || ! is_array( $data[ $heartbeat_id ] ) ) {
+ return $response;
+ }
+
+ $statuses = [];
+
+ foreach ( $data[ $heartbeat_id ] as $item ) {
+ if ( empty( $statuses[ $item['context'] ] ) ) {
+ $statuses[ $item['context'] ] = [];
+ }
+
+ $statuses[ $item['context'] ][ '_' . $item['mediaID'] ] = 1;
+ }
+
+ $results = imagify_get_modified_optimization_statusses( $statuses );
+
+ if ( ! $results ) {
+ return $response;
+ }
+
+ $response[ $heartbeat_id ] = [];
+
+ // Sanitize received data and grab some other info.
+ foreach ( $results as $context_id => $media_atts ) {
+ $process = imagify_get_optimization_process( $media_atts['media_id'], $media_atts['context'] );
+ $optim_data = $process->get_data();
+
+ if ( $optim_data->is_optimized() ) {
+ // Successfully optimized.
+ $full_size_data = $optim_data->get_size_data();
+ $response[ $heartbeat_id ][] = [
+ 'mediaID' => $media_atts['media_id'],
+ 'context' => $media_atts['context'],
+ 'success' => true,
+ 'status' => 'optimized',
+ // Raw data.
+ 'originalOverallSize' => $full_size_data['original_size'],
+ 'newOverallSize' => $full_size_data['optimized_size'],
+ 'overallSaving' => $full_size_data['original_size'] - $full_size_data['optimized_size'],
+ 'thumbnailsCount' => $optim_data->get_optimized_sizes_count(),
+ // Human readable data.
+ 'originalSizeHuman' => imagify_size_format( $full_size_data['original_size'], 2 ),
+ 'newSizeHuman' => imagify_size_format( $full_size_data['optimized_size'], 2 ),
+ 'overallSavingHuman' => imagify_size_format( $full_size_data['original_size'] - $full_size_data['optimized_size'], 2 ),
+ 'originalOverallSizeHuman' => imagify_size_format( $full_size_data['original_size'], 2 ),
+ 'percentHuman' => $full_size_data['percent'] . '%',
+ ];
+ } elseif ( $optim_data->is_already_optimized() ) {
+ // Already optimized.
+ $response[ $heartbeat_id ][] = [
+ 'mediaID' => $media_atts['media_id'],
+ 'context' => $media_atts['context'],
+ 'success' => true,
+ 'status' => 'already-optimized',
+ ];
+ } else {
+ // Error.
+ $full_size_data = $optim_data->get_size_data();
+ $message = ! empty( $full_size_data['error'] ) ? $full_size_data['error'] : '';
+ $status = 'error';
+
+ if ( 'You\'ve consumed all your data. You have to upgrade your account to continue' === $message ) {
+ $status = 'over-quota';
+ }
+
+ $response[ $heartbeat_id ][] = [
+ 'mediaID' => $media_atts['media_id'],
+ 'context' => $media_atts['context'],
+ 'success' => false,
+ 'status' => $status,
+ 'error' => imagify_translate_api_message( $message ),
+ ];
+ }
+ }
+
+ return $response;
+ }
+
+ /**
+ * Look for media where status has changed, compared to what Imagifybeat sends.
+ * This is used in the settings page.
+ *
+ * @since 1.9
+ * @since 1.9.3 Deprecated.
+ * @author Grégory Viguier
+ * @deprecated
+ *
+ * @param array $response The Imagifybeat response.
+ * @param array $data The $_POST data sent.
+ * @return array
+ */
+ function imagify_heartbeat_options_bulk_optimization_status_received( $response, $data ) {
+ _deprecated_function( __FUNCTION__ . '()', '1.9.3', '\\Imagify\\Imagifybeat\\Actions::get_instance()->add_options_optimization_status_to_response()' );
+
+ $heartbeat_id = 'imagify_options_bulk_queue';
+
+ if ( empty( $data[ $heartbeat_id ] ) || ! is_array( $data[ $heartbeat_id ] ) ) {
+ return $response;
+ }
+
+ $statuses = [];
+
+ foreach ( $data[ $heartbeat_id ] as $item ) {
+ if ( empty( $statuses[ $item['context'] ] ) ) {
+ $statuses[ $item['context'] ] = [];
+ }
+
+ $statuses[ $item['context'] ][ '_' . $item['mediaID'] ] = 1;
+ }
+
+ $results = imagify_get_modified_optimization_statusses( $statuses );
+
+ if ( ! $results ) {
+ return $response;
+ }
+
+ $response[ $heartbeat_id ] = [];
+
+ foreach ( $results as $result ) {
+ $response[ $heartbeat_id ][] = [
+ 'mediaID' => $result['media_id'],
+ 'context' => $result['context'],
+ ];
+ }
+
+ return $response;
+ }
+
+ /**
+ * Look for media where status has changed, compared to what Imagifybeat sends.
+ * This is used in the WP Media Library.
+ *
+ * @since 1.9
+ * @since 1.9.3 Deprecated.
+ * @author Grégory Viguier
+ * @deprecated
+ *
+ * @param array $response The Imagifybeat response.
+ * @param array $data The $_POST data sent.
+ * @return array
+ */
+ function imagify_heartbeat_optimization_status_received( $response, $data ) {
+ _deprecated_function( __FUNCTION__ . '()', '1.9.3', '\\Imagify\\Imagifybeat\\Actions::get_instance()->add_library_optimization_status_to_response()' );
+
+ $heartbeat_id = get_imagify_localize_script_translations( 'media-modal' );
+ $heartbeat_id = $heartbeat_id['heartbeatId'];
+
+ if ( empty( $data[ $heartbeat_id ] ) || ! is_array( $data[ $heartbeat_id ] ) ) {
+ return $response;
+ }
+
+ $response[ $heartbeat_id ] = imagify_get_modified_optimization_statusses( $data[ $heartbeat_id ] );
+
+ if ( ! $response[ $heartbeat_id ] ) {
+ return $response;
+ }
+
+ // Sanitize received data and grab some other info.
+ foreach ( $response[ $heartbeat_id ] as $context_id => $media_atts ) {
+ $process = imagify_get_optimization_process( $media_atts['media_id'], $media_atts['context'] );
+
+ $response[ $heartbeat_id ][ $context_id ] = get_imagify_media_column_content( $process, false );
+ }
+
+ return $response;
+ }
+
+ /**
+ * Look for media where status has changed, compared to what Imagifybeat sends.
+ * This is used in the custom folders list (the "Other Media" page).
+ *
+ * @since 1.9
+ * @since 1.9.3 Deprecated.
+ * @author Grégory Viguier
+ * @deprecated
+ *
+ * @param array $response The Imagifybeat response.
+ * @param array $data The $_POST data sent.
+ * @return array
+ */
+ function imagify_heartbeat_custom_folders_optimization_status_received( $response, $data ) {
+ _deprecated_function( __FUNCTION__ . '()', '1.9.3', '\\Imagify\\Imagifybeat\\Actions::get_instance()->add_custom_folders_optimization_status_to_response()' );
+
+ $heartbeat_id = get_imagify_localize_script_translations( 'files-list' );
+ $heartbeat_id = $heartbeat_id['heartbeatId'];
+
+ if ( empty( $data[ $heartbeat_id ] ) || ! is_array( $data[ $heartbeat_id ] ) ) {
+ return $response;
+ }
+
+ $response[ $heartbeat_id ] = imagify_get_modified_optimization_statusses( $data[ $heartbeat_id ] );
+
+ if ( ! $response[ $heartbeat_id ] ) {
+ return $response;
+ }
+
+ $admin_ajax_post = Imagify_Admin_Ajax_Post::get_instance();
+ $list_table = new Imagify_Files_List_Table( [
+ 'screen' => 'imagify-files',
+ ] );
+
+ // Sanitize received data and grab some other info.
+ foreach ( $response[ $heartbeat_id ] as $context_id => $media_atts ) {
+ $process = imagify_get_optimization_process( $media_atts['media_id'], $media_atts['context'] );
+
+ $response[ $heartbeat_id ][ $context_id ] = $admin_ajax_post->get_media_columns( $process, $list_table );
+ }
+
+ return $response;
+ }
+
+ /**
+ * Look for media where status has changed, compared to what Imagifybeat sends.
+ *
+ * @since 1.9
+ * @since 1.9.3 Deprecated.
+ * @author Grégory Viguier
+ * @deprecated
+ *
+ * @param array $data The data received.
+ * @return array
+ */
+ function imagify_get_modified_optimization_statusses( $data ) {
+ _deprecated_function( __FUNCTION__ . '()', '1.9.3', '\\Imagify\\Imagifybeat\\Actions::get_instance()->get_modified_optimization_statuses()' );
+
+ if ( ! $data ) {
+ return [];
+ }
+
+ $output = [];
+
+ // Sanitize received data and grab some other info.
+ foreach ( $data as $context => $media_statuses ) {
+ if ( ! $context || ! $media_statuses || ! is_array( $media_statuses ) ) {
+ continue;
+ }
+
+ // Sanitize the IDs: IDs come as strings, prefixed with an undescore character (to prevent JavaScript from screwing everything).
+ $media_ids = array_keys( $media_statuses );
+ $media_ids = array_map( function( $media_id ) {
+ return (int) substr( $media_id, 1 );
+ }, $media_ids );
+ $media_ids = array_filter( $media_ids );
+
+ if ( ! $media_ids ) {
+ continue;
+ }
+
+ // Sanitize the context.
+ $context_instance = imagify_get_context( $context );
+ $context = $context_instance->get_name();
+ $process_class_name = imagify_get_optimization_process_class_name( $context );
+ $transient_name = sprintf( $process_class_name::LOCK_NAME, $context, '%' );
+ $is_network_wide = $context_instance->is_network_wide();
+
+ Imagify_DB::cache_process_locks( $context, $media_ids );
+
+ // Now that everything is cached for this context, we can get the transients without hitting the DB.
+ foreach ( $media_ids as $id ) {
+ $is_locked = (bool) $media_statuses[ '_' . $id ];
+ $option_name = str_replace( '%', $id, $transient_name );
+
+ if ( $is_network_wide ) {
+ $in_db = (bool) get_site_transient( $option_name );
+ } else {
+ $in_db = (bool) get_transient( $option_name );
+ }
+
+ if ( $is_locked === $in_db ) {
+ continue;
+ }
+
+ $output[ $context . '_' . $id ] = [
+ 'media_id' => $id,
+ 'context' => $context,
+ ];
+ }
+ }
+
+ return $output;
+ }
+
+endif;
+
+/**
+ * Maybe reset opcache after Imagify update.
+ *
+ * @since 1.7.1.2
+ * @since 2.0
+ * @author Grégory Viguier
+ *
+ * @param object $wp_upgrader Plugin_Upgrader instance.
+ * @param array $hook_extra {
+ * Array of bulk item update data.
+ *
+ * @type string $action Type of action. Default 'update'.
+ * @type string $type Type of update process. Accepts 'plugin', 'theme', 'translation', or 'core'.
+ * @type bool $bulk Whether the update process is a bulk update. Default true.
+ * @type array $plugins Array of the basename paths of the plugins' main files.
+ * }
+ */
+function imagify_maybe_reset_opcache( $wp_upgrader, $hook_extra ) {
+ _deprecated_function( __FUNCTION__ . '()', '2.0' );
+
+ static $imagify_path;
+
+ if ( ! isset( $hook_extra['action'], $hook_extra['type'], $hook_extra['plugins'] ) ) {
+ return;
+ }
+
+ if ( 'update' !== $hook_extra['action'] || 'plugin' !== $hook_extra['type'] || ! is_array( $hook_extra['plugins'] ) ) {
+ return;
+ }
+
+ $plugins = array_flip( $hook_extra['plugins'] );
+
+ if ( ! isset( $imagify_path ) ) {
+ $imagify_path = plugin_basename( IMAGIFY_FILE );
+ }
+
+ if ( ! isset( $plugins[ $imagify_path ] ) ) {
+ return;
+ }
+
+ imagify_reset_opcache();
+}
+
+/**
+ * Reset PHP opcache.
+ *
+ * @since 1.8.1
+ * @since 1.9.9 Added $reset_function_cache parameter and return boolean.
+ * @since 2.0 deprecated
+ * @author Grégory Viguier
+ *
+ * @param bool $reset_function_cache Set to true to bypass the cache.
+ * @return bool Return true if the opcode cache was reset (or reset in a previous call), or false if the opcode cache is disabled.
+ */
+function imagify_reset_opcache( $reset_function_cache = false ) {
+ _deprecated_function( __FUNCTION__ . '()', '2.0' );
+
+ static $can_reset;
+
+ if ( $reset_function_cache || ! isset( $can_reset ) ) {
+ if ( ! function_exists( 'opcache_reset' ) ) {
+ $can_reset = false;
+ return false;
+ }
+
+ $opcache_enabled = filter_var( ini_get( 'opcache.enable' ), FILTER_VALIDATE_BOOLEAN ); // phpcs:ignore PHPCompatibility.IniDirectives.NewIniDirectives.opcache_enableFound
+
+ if ( ! $opcache_enabled ) {
+ $can_reset = false;
+ return false;
+ }
+
+ $restrict_api = ini_get( 'opcache.restrict_api' ); // phpcs:ignore PHPCompatibility.IniDirectives.NewIniDirectives.opcache_restrict_apiFound
+
+ if ( $restrict_api && strpos( __FILE__, $restrict_api ) !== 0 ) {
+ $can_reset = false;
+ return false;
+ }
+
+ $can_reset = true;
+ }
+
+ if ( ! $can_reset ) {
+ return false;
+ }
+
+ return opcache_reset(); // phpcs:ignore PHPCompatibility.FunctionUse.NewFunctions.opcache_resetFound
+}
diff --git a/wp/wp-content/plugins/imagify/inc/functions/admin-stats.php b/wp/wp-content/plugins/imagify/inc/functions/admin-stats.php
new file mode 100644
index 00000000..84d534de
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/functions/admin-stats.php
@@ -0,0 +1,795 @@
+get_var( // WPCS: unprepared SQL ok.
+ "
+ SELECT COUNT( p.ID )
+ FROM $wpdb->posts AS p
+ $nodata_join
+ WHERE p.post_mime_type IN ( $mime_types )
+ AND p.post_type = 'attachment'
+ AND p.post_status IN ( $statuses )
+ $nodata_where"
+ );
+
+ if ( $count > imagify_get_unoptimized_attachment_limit() ) {
+ set_transient( 'imagify_large_library', 1 );
+ } elseif ( get_transient( 'imagify_large_library' ) ) {
+ // In case the number is decreasing under our limit.
+ delete_transient( 'imagify_large_library' );
+ }
+
+ return $count;
+}
+
+/**
+ * Count number of optimized attachments with an error.
+ *
+ * @since 1.0
+ * @author Jonathan Buttigieg
+ *
+ * @return int The number of attachments.
+ */
+function imagify_count_error_attachments() {
+ global $wpdb;
+ static $count;
+
+ /**
+ * Filter the number of optimized attachments with an error.
+ * 3rd party will be able to override the result.
+ *
+ * @since 1.5
+ *
+ * @param int|bool $pre_count Default is false. Provide an integer.
+ */
+ $pre_count = apply_filters( 'imagify_count_error_attachments', false );
+
+ if ( false !== $pre_count ) {
+ return (int) $pre_count;
+ }
+
+ if ( isset( $count ) ) {
+ return $count;
+ }
+
+ $mime_types = Imagify_DB::get_mime_types();
+ $statuses = Imagify_DB::get_post_statuses();
+ $nodata_join = Imagify_DB::get_required_wp_metadata_join_clause();
+ $nodata_where = Imagify_DB::get_required_wp_metadata_where_clause();
+ $count = (int) $wpdb->get_var( // WPCS: unprepared SQL ok.
+ "
+ SELECT COUNT( DISTINCT p.ID )
+ FROM $wpdb->posts AS p
+ $nodata_join
+ INNER JOIN $wpdb->postmeta AS mt1
+ ON ( p.ID = mt1.post_id AND mt1.meta_key = '_imagify_status' )
+ WHERE p.post_mime_type IN ( $mime_types )
+ AND p.post_type = 'attachment'
+ AND p.post_status IN ( $statuses )
+ AND mt1.meta_value = 'error'
+ $nodata_where"
+ );
+
+ return $count;
+}
+
+/**
+ * Count number of optimized attachments (by Imagify or an other tool before).
+ *
+ * @since 1.0
+ * @author Jonathan Buttigieg
+ *
+ * @return int The number of attachments.
+ */
+function imagify_count_optimized_attachments() {
+ global $wpdb;
+ static $count;
+
+ /**
+ * Filter the number of optimized attachments.
+ * 3rd party will be able to override the result.
+ *
+ * @since 1.5
+ *
+ * @param int|bool $pre_count Default is false. Provide an integer.
+ */
+ $pre_count = apply_filters( 'imagify_count_optimized_attachments', false );
+
+ if ( false !== $pre_count ) {
+ return (int) $pre_count;
+ }
+
+ if ( isset( $count ) ) {
+ return $count;
+ }
+
+ $mime_types = Imagify_DB::get_mime_types();
+ $statuses = Imagify_DB::get_post_statuses();
+ $nodata_join = Imagify_DB::get_required_wp_metadata_join_clause();
+ $nodata_where = Imagify_DB::get_required_wp_metadata_where_clause();
+ $count = (int) $wpdb->get_var( // WPCS: unprepared SQL ok.
+ "
+ SELECT COUNT( DISTINCT p.ID )
+ FROM $wpdb->posts AS p
+ $nodata_join
+ INNER JOIN $wpdb->postmeta AS mt1
+ ON ( p.ID = mt1.post_id AND mt1.meta_key = '_imagify_status' )
+ WHERE p.post_mime_type IN ( $mime_types )
+ AND p.post_type = 'attachment'
+ AND p.post_status IN ( $statuses )
+ AND mt1.meta_value IN ( 'success', 'already_optimized' )
+ $nodata_where"
+ );
+
+ return $count;
+}
+
+/**
+ * Count number of unoptimized attachments.
+ *
+ * @since 1.0
+ * @author Jonathan Buttigieg
+ *
+ * @return int The number of attachments.
+ */
+function imagify_count_unoptimized_attachments() {
+ /**
+ * Filter the number of unoptimized attachments.
+ * 3rd party will be able to override the result.
+ *
+ * @since 1.5
+ *
+ * @param int|bool $pre_count Default is false. Provide an integer.
+ */
+ $pre_count = apply_filters( 'imagify_count_unoptimized_attachments', false );
+
+ if ( false !== $pre_count ) {
+ return (int) $pre_count;
+ }
+
+ return imagify_count_attachments() - imagify_count_optimized_attachments() - imagify_count_error_attachments();
+}
+
+/**
+ * Count percent of optimized attachments.
+ *
+ * @since 1.0
+ * @author Jonathan Buttigieg
+ *
+ * @return int The percent of optimized attachments.
+ */
+function imagify_percent_optimized_attachments() {
+ /**
+ * Filter the percent of optimized attachments.
+ * 3rd party will be able to override the result.
+ *
+ * @since 1.5
+ *
+ * @param int|bool $percent Default is false. Provide an integer.
+ */
+ $percent = apply_filters( 'imagify_percent_optimized_attachments', false );
+
+ if ( false !== $percent ) {
+ return (int) $percent;
+ }
+
+ $total_attachments = imagify_count_attachments();
+ $total_optimized_attachments = imagify_count_optimized_attachments();
+
+ if ( ! $total_attachments || ! $total_optimized_attachments ) {
+ return 0;
+ }
+
+ return min( round( 100 * $total_optimized_attachments / $total_attachments ), 100 );
+}
+
+/**
+ * Count percent, original & optimized size of all images optimized by Imagify.
+ *
+ * @since 1.0
+ * @since 1.6.7 Revamped to handle huge libraries.
+ * @author Jonathan Buttigieg
+ *
+ * @param string $key What data to return. Choices are between 'count', 'original_size', 'optimized_size', and 'percent'. If left empty, the whole array is returned.
+ * @return array|int An array containing the optimization data. A single data if $key is provided.
+ */
+function imagify_count_saving_data( $key = '' ) {
+ global $wpdb;
+
+ /**
+ * Filter the query to get all optimized attachments.
+ * 3rd party will be able to override the result.
+ *
+ * @since 1.5
+ * @since 1.6.7 This filter should return an array containing the following keys: 'count', 'original_size', and 'optimized_size'.
+ *
+ * @param bool|array $attachments An array containing the keys ('count', 'original_size', and 'optimized_size'), or an array of attachments (back compat', deprecated), or false.
+ */
+ $attachments = apply_filters( 'imagify_count_saving_data', false );
+
+ $original_size = 0;
+ $optimized_size = 0;
+ $count = 0;
+
+ if ( is_array( $attachments ) ) {
+ /**
+ * Bypass.
+ */
+ if ( isset( $attachments['count'], $attachments['original_size'], $attachments['optimized_size'] ) ) {
+ /**
+ * We have the results we need.
+ */
+ $attachments['percent'] = $attachments['optimized_size'] && $attachments['original_size'] ? ceil( ( ( $attachments['original_size'] - $attachments['optimized_size'] ) / $attachments['original_size'] ) * 100 ) : 0;
+
+ return $attachments;
+ }
+
+ /**
+ * Back compat'.
+ * The following shouldn't be used. Sites with a huge library won't like it.
+ */
+ $attachments = array_map( 'maybe_unserialize', (array) $attachments );
+
+ if ( $attachments ) {
+ foreach ( $attachments as $attachment_data ) {
+ if ( ! $attachment_data ) {
+ continue;
+ }
+
+ ++$count;
+ $original_data = $attachment_data['sizes']['full'];
+
+ // Increment the original sizes.
+ $original_size += $original_data['original_size'] ? $original_data['original_size'] : 0;
+ $optimized_size += $original_data['optimized_size'] ? $original_data['optimized_size'] : 0;
+
+ unset( $attachment_data['sizes']['full'] );
+
+ // Increment the thumbnails sizes.
+ if ( $attachment_data['sizes'] ) {
+ foreach ( $attachment_data['sizes'] as $size_data ) {
+ if ( ! empty( $size_data['success'] ) ) {
+ $original_size += $size_data['original_size'] ? $size_data['original_size'] : 0;
+ $optimized_size += $size_data['optimized_size'] ? $size_data['optimized_size'] : 0;
+ }
+ }
+ }
+ }
+ }
+ } else {
+ /**
+ * Filter the chunk size of the requests fetching the data.
+ * 15,000 seems to be a good balance between memory used, speed, and number of DB hits.
+ *
+ * @param int $limit The maximum number of elements per chunk.
+ */
+ $limit = apply_filters( 'imagify_count_saving_data_limit', 15000 );
+ $limit = absint( $limit );
+
+ $mime_types = Imagify_DB::get_mime_types();
+ $statuses = Imagify_DB::get_post_statuses();
+ $nodata_join = Imagify_DB::get_required_wp_metadata_join_clause();
+ $nodata_where = Imagify_DB::get_required_wp_metadata_where_clause();
+ $attachment_ids = $wpdb->get_col( // WPCS: unprepared SQL ok.
+ "
+ SELECT p.ID
+ FROM $wpdb->posts AS p
+ $nodata_join
+ INNER JOIN $wpdb->postmeta AS mt1
+ ON ( p.ID = mt1.post_id AND mt1.meta_key = '_imagify_status' )
+ WHERE p.post_mime_type IN ( $mime_types )
+ AND p.post_type = 'attachment'
+ AND p.post_status IN ( $statuses )
+ AND mt1.meta_value = 'success'
+ $nodata_where
+ ORDER BY CAST( p.ID AS UNSIGNED )"
+ );
+ $wpdb->flush();
+
+ $attachment_ids = array_map( 'absint', array_unique( $attachment_ids ) );
+ $attachment_ids = array_chunk( $attachment_ids, $limit );
+
+ while ( $attachment_ids ) {
+ $limit_ids = array_shift( $attachment_ids );
+ $limit_ids = implode( ',', $limit_ids );
+
+ $attachments = $wpdb->get_col( // WPCS: unprepared SQL ok.
+ "
+ SELECT meta_value
+ FROM $wpdb->postmeta
+ WHERE post_id IN ( $limit_ids )
+ AND meta_key = '_imagify_data'"
+ );
+ $wpdb->flush();
+
+ unset( $limit_ids );
+
+ if ( ! $attachments ) {
+ // Uh?!
+ continue;
+ }
+
+ $attachments = array_map( 'maybe_unserialize', $attachments );
+
+ foreach ( $attachments as $attachment_data ) {
+ if ( ! $attachment_data ) {
+ continue;
+ }
+
+ if ( empty( $attachment_data['sizes']['full']['success'] ) ) {
+ /**
+ * - Case where this attachment has multiple '_imagify_status' metas, and is fetched (in the above query) as a "success" while the '_imagify_data' says otherwise.
+ * - Case where this meta has no "full" entry.
+ * Don't ask how it's possible, I don't know ¯\(°_o)/¯
+ */
+ continue;
+ }
+
+ $original_data = $attachment_data['sizes']['full'];
+
+ ++$count;
+
+ // Increment the original sizes.
+ $original_size += ! empty( $original_data['original_size'] ) ? $original_data['original_size'] : 0;
+ $optimized_size += ! empty( $original_data['optimized_size'] ) ? $original_data['optimized_size'] : 0;
+
+ unset( $attachment_data['sizes']['full'], $original_data );
+
+ // Increment the thumbnails sizes.
+ if ( $attachment_data['sizes'] ) {
+ foreach ( $attachment_data['sizes'] as $size_data ) {
+ if ( ! empty( $size_data['success'] ) ) {
+ $original_size += ! empty( $size_data['original_size'] ) ? $size_data['original_size'] : 0;
+ $optimized_size += ! empty( $size_data['optimized_size'] ) ? $size_data['optimized_size'] : 0;
+ }
+ }
+ }
+
+ unset( $size_data );
+ }
+
+ unset( $attachments, $attachment_data );
+ } // End while().
+ } // End if().
+
+ $data = array(
+ 'count' => $count,
+ 'original_size' => $original_size,
+ 'optimized_size' => $optimized_size,
+ 'percent' => $original_size && $optimized_size ? ceil( ( ( $original_size - $optimized_size ) / $original_size ) * 100 ) : 0,
+ );
+
+ if ( ! empty( $key ) ) {
+ return isset( $data[ $key ] ) ? $data[ $key ] : 0;
+ }
+
+ return $data;
+}
+
+/**
+ * Returns the estimated total size of the images not optimized.
+ *
+ * We estimate the total size of the images in the library by getting the latest 250 images and their thumbnails
+ * add up their filesizes, and doing some maths to get the total size.
+ *
+ * @since 1.6
+ * @author Remy Perona
+ *
+ * @return int The current estimated total size of images not optimized.
+ */
+function imagify_calculate_total_size_images_library() {
+ global $wpdb;
+
+ $mime_types = Imagify_DB::get_mime_types();
+ $statuses = Imagify_DB::get_post_statuses();
+ $nodata_join = Imagify_DB::get_required_wp_metadata_join_clause();
+ $nodata_where = Imagify_DB::get_required_wp_metadata_where_clause();
+ $image_ids = $wpdb->get_col( // WPCS: unprepared SQL ok.
+ "
+ SELECT p.ID
+ FROM $wpdb->posts AS p
+ $nodata_join
+ WHERE p.post_mime_type IN ( $mime_types )
+ AND p.post_type = 'attachment'
+ AND p.post_status IN ( $statuses )
+ $nodata_where
+ LIMIT 250
+ " );
+
+ if ( ! $image_ids ) {
+ return 0;
+ }
+
+ $count_latest_images = count( $image_ids );
+ $count_total_images = imagify_count_attachments();
+
+ return imagify_calculate_total_image_size( $image_ids, $count_latest_images, $count_total_images );
+}
+
+/**
+ * Returns the estimated average size of the images uploaded per month.
+ *
+ * We estimate the average size of the images uploaded in the library per month by getting the latest 250 images and their thumbnails
+ * for the 3 latest months, add up their filesizes, and doing some maths to get the total average size.
+ *
+ * @since 1.6
+ * @since 1.7 Use wpdb instead of WP_Query.
+ * @author Remy Perona
+ *
+ * @return int The current estimated average size of images uploaded per month.
+ */
+function imagify_calculate_average_size_images_per_month() {
+ global $wpdb;
+
+ $mime_types = Imagify_DB::get_mime_types();
+ $statuses = Imagify_DB::get_post_statuses();
+ $nodata_join = Imagify_DB::get_required_wp_metadata_join_clause( "$wpdb->posts.ID" );
+ $nodata_where = Imagify_DB::get_required_wp_metadata_where_clause();
+ $limit = ' LIMIT 0, 250';
+ $query = "
+ SELECT $wpdb->posts.ID
+ FROM $wpdb->posts
+ $nodata_join
+ WHERE $wpdb->posts.post_mime_type IN ( $mime_types )
+ AND $wpdb->posts.post_type = 'attachment'
+ AND $wpdb->posts.post_status IN ( $statuses )
+ $nodata_where
+ %date_query%";
+
+ // Queries per month.
+ $date_query = new WP_Date_Query( array(
+ array(
+ 'before' => 'now',
+ 'after' => '1 month ago',
+ ),
+ ) );
+
+ $partial_images_uploaded_last_month = $wpdb->get_col( str_replace( '%date_query%', $date_query->get_sql(), $query . $limit ) ); // WPCS: unprepared SQL ok.
+
+ $date_query = new WP_Date_Query( array(
+ array(
+ 'before' => '1 month ago',
+ 'after' => '2 months ago',
+ ),
+ ) );
+
+ $partial_images_uploaded_two_months_ago = $wpdb->get_col( str_replace( '%date_query%', $date_query->get_sql(), $query . $limit ) ); // WPCS: unprepared SQL ok.
+
+ $date_query = new WP_Date_Query( array(
+ array(
+ 'before' => '2 month ago',
+ 'after' => '3 months ago',
+ ),
+ ) );
+
+ $partial_images_uploaded_three_months_ago = $wpdb->get_col( str_replace( '%date_query%', $date_query->get_sql(), $query . $limit ) ); // WPCS: unprepared SQL ok.
+
+ // Total for the 3 months.
+ $partial_images_uploaded_id = array_merge( $partial_images_uploaded_last_month, $partial_images_uploaded_two_months_ago, $partial_images_uploaded_three_months_ago );
+
+ if ( ! $partial_images_uploaded_id ) {
+ return 0;
+ }
+
+ // Total for the 3 months, without the "250" limit.
+ $date_query = new WP_Date_Query( array(
+ array(
+ 'before' => 'now',
+ 'after' => '3 month ago',
+ ),
+ ) );
+
+ $images_uploaded_id = $wpdb->get_col( str_replace( '%date_query%', $date_query->get_sql(), $query ) ); // WPCS: unprepared SQL ok.
+
+ if ( ! $images_uploaded_id ) {
+ return 0;
+ }
+
+ // Number of image attachments uploaded for the 3 latest months, limited to 250 per month.
+ $partial_total_images_uploaded = count( $partial_images_uploaded_id );
+ // Total number of image attachments uploaded for the 3 latest months.
+ $total_images_uploaded = count( $images_uploaded_id );
+
+ return imagify_calculate_total_image_size( $partial_images_uploaded_id, $partial_total_images_uploaded, $total_images_uploaded ) / 3;
+}
+
+/**
+ * Returns the estimated total size of images.
+ *
+ * @since 1.6
+ * @author Remy Perona
+ *
+ * @param array $image_ids Array of image IDs.
+ * @param int $partial_total_images The number of image attachments we're doing the calculation with.
+ * @param int $total_images The total number of image attachments.
+ * @return int The estimated total size of images.
+ */
+function imagify_calculate_total_image_size( $image_ids, $partial_total_images, $total_images ) {
+ global $wpdb;
+
+ $image_ids = array_filter( array_map( 'absint', $image_ids ) );
+
+ if ( ! $image_ids ) {
+ return 0;
+ }
+
+ $results = Imagify_DB::get_metas( array(
+ // Get attachments filename.
+ 'filenames' => '_wp_attached_file',
+ // Get attachments data.
+ 'data' => '_wp_attachment_metadata',
+ // Get Imagify data.
+ 'imagify_data' => '_imagify_data',
+ // Get attachments status.
+ 'statuses' => '_imagify_status',
+ ), $image_ids );
+
+ // Number of image attachments we're doing the calculation with. In case array_filter() removed results.
+ $partial_total_images = count( $image_ids );
+ // Total size of unoptimized size.
+ $partial_size_images = 0;
+ // Total number of thumbnails.
+ $partial_total_intermediate_images = 0;
+
+ $filesystem = imagify_get_filesystem();
+ $is_active_for_network = imagify_is_active_for_network();
+ $disallowed_sizes = get_imagify_option( 'disallowed-sizes' );
+
+ foreach ( $image_ids as $i => $image_id ) {
+ $attachment_status = isset( $results['statuses'][ $image_id ] ) ? $results['statuses'][ $image_id ] : false;
+
+ if ( 'success' === $attachment_status ) {
+ /**
+ * The image files have been optimized.
+ */
+ // Original size.
+ $partial_size_images += isset( $results['imagify_data'][ $image_id ]['stats']['original_size'] ) ? $results['imagify_data'][ $image_id ]['stats']['original_size'] : 0;
+ // Number of thumbnails.
+ $partial_total_intermediate_images += count( $results['imagify_data'][ $image_id ]['sizes'] );
+ unset(
+ $image_ids[ $i ],
+ $results['filenames'][ $image_id ],
+ $results['data'][ $image_id ],
+ $results['imagify_data'][ $image_id ],
+ $results['statuses'][ $image_id ]
+ );
+ continue;
+ }
+
+ /**
+ * The image files are not optimized.
+ */
+ // Create an array containing all this attachment files.
+ $files = array(
+ 'full' => get_imagify_attached_file( $results['filenames'][ $image_id ] ),
+ );
+
+ $sizes = isset( $results['data'][ $image_id ]['sizes'] ) ? $results['data'][ $image_id ]['sizes'] : array();
+
+ if ( $sizes && is_array( $sizes ) ) {
+ if ( ! $is_active_for_network ) {
+ $sizes = array_diff_key( $sizes, $disallowed_sizes );
+ }
+
+ if ( $sizes ) {
+ $full_dirname = $filesystem->dir_path( $files['full'] );
+
+ foreach ( $sizes as $size_key => $size_data ) {
+ $files[ $size_key ] = $full_dirname . '/' . $size_data['file'];
+ }
+ }
+ }
+
+ /**
+ * Allow to provide all files size and the number of thumbnails.
+ *
+ * @since 1.6.7
+ * @author Grégory Viguier
+ *
+ * @param bool $size_and_count False by default.
+ * @param int $image_id The attachment ID.
+ * @param array $files An array of file paths with thumbnail sizes as keys.
+ * @param array $image_ids An array of all attachment IDs.
+ * @return bool|array False by default. Provide an array with the keys 'filesize' (containing the total filesize) and 'thumbnails' (containing the number of thumbnails).
+ */
+ $size_and_count = apply_filters( 'imagify_total_attachment_filesize', false, $image_id, $files, $image_ids );
+
+ if ( is_array( $size_and_count ) ) {
+ $partial_size_images += $size_and_count['filesize'];
+ $partial_total_intermediate_images += $size_and_count['thumbnails'];
+ } else {
+ foreach ( $files as $file ) {
+ if ( $filesystem->exists( $file ) ) {
+ $partial_size_images += $filesystem->size( $file );
+ }
+ }
+
+ unset( $files['full'] );
+ $partial_total_intermediate_images += count( $files );
+ }
+
+ unset(
+ $image_ids[ $i ],
+ $results['filenames'][ $image_id ],
+ $results['data'][ $image_id ],
+ $results['imagify_data'][ $image_id ],
+ $results['statuses'][ $image_id ]
+ );
+ } // End foreach().
+
+ // Number of thumbnails per attachment = Number of thumbnails / Number of attachments.
+ $intermediate_images_per_image = $partial_total_intermediate_images / $partial_total_images;
+ /**
+ * Note: Number of attachments ($partial_total_images) === Number of full sizes.
+ * Average image size = Size of the images / ( Number of full sizes + Number of thumbnails ).
+ * Average image size = Size of the images / Number of images.
+ */
+ $average_size_images = $partial_size_images / ( $partial_total_images + $partial_total_intermediate_images );
+ /**
+ * Note: Total number of attachments ($total_images) === Total number of full sizes.
+ * Total images size = Average image size * ( Total number of full sizes + ( Number of thumbnails per attachment * Total number of attachments ) ).
+ * Total images size = Average image size * ( Total number of full sizes + Total number of thumbnails ).
+ */
+ $total_size_images = $average_size_images * ( $total_images + ( $intermediate_images_per_image * $total_images ) );
+
+ return $total_size_images;
+}
+
+/**
+ * Get all generic stats to be used in the bulk optimization page.
+ *
+ * @since 1.7.1
+ * @author Grégory Viguier
+ *
+ * @param array $types The folder types. If a folder type is "library", the context should be suffixed after a pipe character. They are passed as array keys.
+ * @param array $args {
+ * Optional. An array of arguments.
+ *
+ * @type bool $fullset True to return the full set of data. False to return only the main data.
+ * @type bool $formatting Some of the data is returned formatted.
+ * }
+ * @return array
+ */
+function imagify_get_bulk_stats( $types, $args = array() ) {
+ $types = $types && is_array( $types ) ? $types : array();
+ $args = array_merge( array(
+ 'fullset' => false,
+ 'formatting' => true,
+ ), (array) $args );
+
+ $data = array(
+ // Global chart.
+ 'total_attachments' => 0,
+ 'unoptimized_attachments' => 0,
+ 'optimized_attachments' => 0,
+ 'errors_attachments' => 0,
+ // Stats block.
+ 'already_optimized_attachments' => 0,
+ 'original_human' => 0,
+ 'optimized_human' => 0,
+ );
+
+ if ( isset( $types['library|wp'] ) ) {
+ /**
+ * Library.
+ */
+ $saving_data = imagify_count_saving_data();
+
+ // Global chart.
+ $data['total_attachments'] += imagify_count_attachments();
+ $data['unoptimized_attachments'] += imagify_count_unoptimized_attachments();
+ $data['optimized_attachments'] += imagify_count_optimized_attachments();
+ $data['errors_attachments'] += imagify_count_error_attachments();
+ // Stats block.
+ $data['already_optimized_attachments'] += $saving_data['count'];
+ $data['original_human'] += $saving_data['original_size'];
+ $data['optimized_human'] += $saving_data['optimized_size'];
+ }
+
+ if ( isset( $types['custom-folders|custom-folders'] ) ) {
+ /**
+ * Custom folders.
+ */
+ // Global chart.
+ $data['total_attachments'] += Imagify_Files_Stats::count_all_files();
+ $data['unoptimized_attachments'] += Imagify_Files_Stats::count_no_status_files();
+ $data['optimized_attachments'] += Imagify_Files_Stats::count_optimized_files();
+ $data['errors_attachments'] += Imagify_Files_Stats::count_error_files();
+ // Stats block.
+ $data['already_optimized_attachments'] += Imagify_Files_Stats::count_success_files();
+ $data['original_human'] += Imagify_Files_Stats::get_original_size();
+ $data['optimized_human'] += Imagify_Files_Stats::get_optimized_size();
+ }
+
+ /**
+ * Full set of data.
+ */
+ if ( $args['fullset'] ) {
+ // User account.
+ $views = Imagify_Views::get_instance();
+
+ $data['unconsumed_quota'] = $views->get_quota_percent();
+ $data['quota_class'] = $views->get_quota_class();
+ $data['quota_icon'] = $views->get_quota_icon();
+ }
+
+ /**
+ * Filter the generic stats used in the bulk optimization page.
+ *
+ * @since 1.7.1
+ * @author Grégory Viguier
+ *
+ * @param array $data The data.
+ * @param array $types The folder types. They are passed as array keys.
+ * @param array $args {
+ * Optional. An array of arguments.
+ *
+ * @type bool $fullset True to return the full set of data. False to return only the main data.
+ * @type bool $formatting Some of the data is returned formatted.
+ * }
+ */
+ $data = apply_filters( 'imagify_bulk_stats', $data, $types, $args );
+
+ /**
+ * Percentages.
+ */
+ if ( $data['total_attachments'] && $data['optimized_attachments'] ) {
+ $data['optimized_attachments_percent'] = round( 100 * $data['optimized_attachments'] / $data['total_attachments'] );
+ } else {
+ $data['optimized_attachments_percent'] = 0;
+ }
+
+ if ( $data['original_human'] && $data['optimized_human'] ) {
+ $data['optimized_percent'] = ceil( 100 - ( 100 * $data['optimized_human'] / $data['original_human'] ) );
+ } else {
+ $data['optimized_percent'] = 0;
+ }
+
+ /**
+ * Formating.
+ */
+ if ( $args['formatting'] ) {
+ $data['already_optimized_attachments'] = number_format_i18n( $data['already_optimized_attachments'] );
+ $data['original_human'] = imagify_size_format( $data['original_human'], 1 );
+ $data['optimized_human'] = imagify_size_format( $data['optimized_human'], 1 );
+ }
+
+ return $data;
+}
diff --git a/wp/wp-content/plugins/imagify/inc/functions/admin-ui.php b/wp/wp-content/plugins/imagify/inc/functions/admin-ui.php
new file mode 100644
index 00000000..5a501b4b
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/functions/admin-ui.php
@@ -0,0 +1,541 @@
+is_valid() ) {
+ return '';
+ }
+
+ $is_media_page = Imagify_Views::get_instance()->is_media_page();
+ $is_library_page = Imagify_Views::get_instance()->is_wp_library_page();
+ $output = $is_media_page ? '' : '';
+ $output .= '';
+ $output .= '';
+ $output .= '' . __( 'View details', 'imagify' ) . ' ';
+ $output .= ' ';
+ $output .= ' ';
+ $output .= '
';
+ $output .= '';
+
+ // Not in metabox.
+ $output .= $output_before . '' . __( 'Original Filesize:', 'imagify' ) . ' ' . $data->get_original_size() . ' ' . $output_after;
+ }
+
+ $output .= $output_before . '' . __( 'Level:', 'imagify' ) . ' ' . $optimization_level . ' ' . $output_after;
+
+ if ( $media->is_image() ) {
+ $has_nextgen = $process->has_next_gen() ? __( 'Yes', 'imagify' ) : __( 'No', 'imagify' );
+
+ if ( $process->has_next_gen() ) {
+ $has_nextgen = $process->is_full_next_gen() ? __( 'Yes', 'imagify' ) : __( 'Partially', 'imagify' );
+ }
+ $output .= $output_before . '' . __( 'Next-Gen generated:', 'imagify' ) . ' ' . esc_html( $has_nextgen ) . ' ' . $output_after;
+
+ $total_optimized_thumbnails = $data->get_optimized_sizes_count();
+
+ if ( $total_optimized_thumbnails ) {
+ $output .= $output_before . '' . __( 'Thumbnails Optimized:', 'imagify' ) . ' ' . $total_optimized_thumbnails . ' ' . $output_after;
+ $output .= $output_before . '' . __( 'Overall Saving:', 'imagify' ) . ' ' . $data->get_overall_saving_percent() . '% ' . $output_after;
+ }
+ }
+
+ // End of list.
+ $output .= $is_media_page ? '' : ' ';
+
+ // Actions section.
+ $output .= $is_media_page ? $output_before : '';
+ $output .= $reoptimize_output_before;
+ $output .= $reoptimize_output;
+
+ if ( $media->has_backup() ) {
+ $url = get_imagify_admin_url( 'restore', [
+ 'attachment_id' => $attachment_id,
+ 'context' => $media->get_context(),
+ ] );
+
+ $output .= Imagify_Views::get_instance()->get_template( 'button/restore', [
+ 'url' => $url,
+ 'atts' => [
+ 'class' => $is_media_page ? '' : null,
+ ],
+ ] );
+
+ if ( ! $is_library_page ) {
+ $output .= ' ';
+ $output .= ' ';
+ $output .= ' ';
+
+ if ( $media->is_image() ) {
+ $dimensions = $media->get_dimensions();
+
+ $output .= ' ';
+ $output .= ' ';
+ }
+ }
+ }
+
+ $output .= $reoptimize_output_after;
+
+ return $output;
+}
+
+/**
+ * Get the error message for a specific attachment.
+ *
+ * @since 1.0
+ * @since 1.9 Function signature changed.
+ * @author Jonathan Buttigieg
+ *
+ * @param ProcessInterface $process The optimization process object.
+ * @return string The output to print.
+ */
+function get_imagify_attachment_error_text( $process ) {
+ if ( ! $process->is_valid() ) {
+ return '';
+ }
+
+ $data = $process->get_data()->get_optimization_data();
+
+ if ( ! isset( $data['sizes']['full']['success'] ) || $data['sizes']['full']['success'] ) {
+ return '';
+ }
+
+ $class = 'button';
+ $media = $process->get_media();
+ $url = get_imagify_admin_url( 'optimize', [
+ 'attachment_id' => $media->get_id(),
+ 'context' => $media->get_context(),
+ ] );
+
+ if ( ! Imagify_Views::get_instance()->is_media_page() ) {
+ $class .= ' button-imagify-optimize';
+ }
+
+ return Imagify_Views::get_instance()->get_template( 'button/retry-optimize', [
+ 'url' => $url,
+ 'error' => $data['sizes']['full']['error'],
+ 'atts' => [
+ 'class' => $class,
+ ],
+ ] );
+}
+
+/**
+ * Get the re-optimize link for a specific attachment.
+ *
+ * @since 1.0
+ * @since 1.9 Function signature changed.
+ * @author Jonathan Buttigieg
+ *
+ * @param ProcessInterface $process The optimization process object.
+ * @return string The output to print.
+ */
+function get_imagify_attachment_reoptimize_link( $process ) {
+ if ( ! $process->is_valid() ) {
+ return '';
+ }
+
+ $data = $process->get_data();
+
+ if ( ! $data->get_optimization_status() ) {
+ // Not optimized yet.
+ return '';
+ }
+
+ // Stop the process if the API key isn't valid.
+ if ( ! Imagify_Requirements::is_api_key_valid() ) {
+ return '';
+ }
+
+ $is_already_optimized = $data->is_already_optimized();
+ $media = $process->get_media();
+ $can_reoptimize = $is_already_optimized || $media->has_backup();
+
+ // Don't display anything if there is no backup or the image has been optimized.
+ if ( ! $can_reoptimize ) {
+ return '';
+ }
+
+ $output = '';
+ $views = Imagify_Views::get_instance();
+ $media_level = $data->get_optimization_level();
+ $data = [];
+ $url_args = [
+ 'attachment_id' => $media->get_id(),
+ 'context' => $media->get_context(),
+ ];
+
+ if ( Imagify_Views::get_instance()->is_media_page() ) {
+ $data['atts'] = [
+ 'class' => '',
+ ];
+ }
+
+ if ( $media_level < 1 ) {
+ $url_args['optimization_level'] = 2;
+ $data['optimization_level'] = 2;
+ $data['url'] = get_imagify_admin_url( 'manual-reoptimize', $url_args );
+
+ $output .= $views->get_template( 'button/re-optimize', $data );
+ } elseif ( $media_level > 0 ) {
+ $url_args['optimization_level'] = 0;
+ $data['optimization_level'] = 0;
+ $data['url'] = get_imagify_admin_url( 'manual-reoptimize', $url_args );
+
+ $output .= $views->get_template( 'button/re-optimize', $data );
+ }
+
+ return $output;
+}
+
+/**
+ * Get the link to optimize missing thumbnail sizes for a specific attachment.
+ *
+ * @since 1.6.10
+ * @since 1.9 Function signature changed.
+ * @author Grégory Viguier
+ *
+ * @param ProcessInterface $process The optimization process object.
+ * @return string The output to print.
+ */
+function get_imagify_attachment_optimize_missing_thumbnails_link( $process ) {
+ if ( ! $process->is_valid() ) {
+ return '';
+ }
+
+ $media = $process->get_media();
+
+ if ( ! $media->is_image() || ! Imagify_Requirements::is_api_key_valid() || ! $media->has_backup() ) {
+ return '';
+ }
+
+ $context = $media->get_context();
+
+ /**
+ * Allow to not display the "Optimize missing thumbnails" link.
+ *
+ * @since 1.6.10
+ * @since 1.9 The $attachment object is replaced by a $process object.
+ * @author Grégory Viguier
+ *
+ * @param bool $display True to display the link. False to not display it.
+ * @param ProcessInterface $process The optimization process object.
+ * @param string $context The context.
+ */
+ $display = apply_filters( 'imagify_display_missing_thumbnails_link', true, $process, $context );
+
+ // Stop the process if the filter is false.
+ if ( ! $display ) {
+ return '';
+ }
+
+ $missing_sizes = $process->get_missing_sizes();
+
+ if ( ! $missing_sizes || is_wp_error( $missing_sizes ) ) {
+ return '';
+ }
+
+ $url = get_imagify_admin_url( 'optimize-missing-sizes', [
+ 'attachment_id' => $media->get_id(),
+ 'context' => $context,
+ ] );
+
+ return Imagify_Views::get_instance()->get_template( 'button/optimize-missing-sizes', [
+ 'url' => $url,
+ 'count' => count( $missing_sizes ),
+ ] );
+}
+
+/**
+ * Get the link to generate next-gen versions if they are missing.
+ *
+ * @since 1.9
+ *
+ * @param ProcessInterface $process The optimization process object.
+ *
+ * @return string The output to print.
+ */
+function get_imagify_attachment_generate_nextgen_versions_link( $process ) {
+ if ( ! $process->is_valid() ) {
+ return '';
+ }
+
+ $formats = imagify_nextgen_images_formats();
+
+ if ( empty( $formats ) ) {
+ return '';
+ }
+
+ $media = $process->get_media();
+
+ if ( ! $media->is_image() || ! Imagify_Requirements::is_api_key_valid() || ! $media->has_backup() ) {
+ return '';
+ }
+
+ $format = get_imagify_option( 'optimization_format' );
+
+ if (
+ 'avif' === $format
+ &&
+ 'image/avif' === $media->get_mime_type()
+ ) {
+ return '';
+ } elseif ( 'image/webp' === $media->get_mime_type() ) {
+ return '';
+ }
+
+ $data = $process->get_data();
+
+ if ( ! $data->is_optimized() && ! $data->is_already_optimized() ) {
+ return '';
+ }
+
+ if ( $process->has_next_gen() ) {
+ return '';
+ }
+
+ $context = $media->get_context();
+
+ $display = apply_filters_deprecated( 'imagify_display_generate_webp_versions_link', array( true, $process, $context ), '2.2', 'imagify_display_generate_next_gen_versions_link' );
+
+ /**
+ * Allow to not display the "Generate next-gen versions" link.
+ *
+ * @since 1.9
+ * @author Grégory Viguier
+ *
+ * @param bool $display True to display the link. False to not display it.
+ * @param ProcessInterface $process The optimization process object.
+ * @param string $context The context.
+ */
+ $display = apply_filters( 'imagify_display_generate_next_gen_versions_link', $display, $process, $context );
+
+ // Stop the process if the filter is false.
+ if ( ! $display ) {
+ return '';
+ }
+
+ $url = get_imagify_admin_url( 'generate-nextgen-versions', [
+ 'attachment_id' => $media->get_id(),
+ 'context' => $context,
+ ] );
+
+ $output = Imagify_Views::get_instance()->get_template( 'button/generate-webp', [
+ 'url' => $url,
+ ] );
+
+ return $output . ' ';
+}
+
+/**
+ * Get the link to delete next-gen versions when the status is "already_optimized".
+ *
+ * @since 1.9.6
+ * @author Grégory Viguier
+ *
+ * @param ProcessInterface $process The optimization process object.
+ * @return string The output to print.
+ */
+function get_imagify_attachment_delete_nextgen_versions_link( $process ) {
+ if ( ! $process->is_valid() ) {
+ return '';
+ }
+
+ $media = $process->get_media();
+ $context = $media->get_context();
+ $media_id = $media->get_id();
+
+ if ( ! imagify_get_context( $context )->current_user_can( 'manual-restore', $media_id ) ) {
+ imagify_die();
+ }
+
+ $data = $process->get_data();
+
+ if ( ! $data->is_already_optimized() || ! $process->has_next_gen() ) {
+ return '';
+ }
+
+ $class = '';
+ $url = get_imagify_admin_url( 'delete-nextgen-versions', [
+ 'attachment_id' => $media_id,
+ 'context' => $context,
+ ] );
+
+ if ( ! Imagify_Views::get_instance()->is_media_page() ) {
+ $class .= 'button-imagify-delete-webp';
+ }
+
+ return Imagify_Views::get_instance()->get_template( 'button/delete-webp', [
+ 'url' => $url,
+ 'atts' => [
+ 'class' => $class,
+ ],
+ ] );
+}
+
+/**
+ * Get all data to diplay for a specific media.
+ *
+ * @since 1.2
+ * @since 1.9 Function signature changed.
+ * @author Jonathan Buttigieg
+ *
+ * @param ProcessInterface $process The optimization process object.
+ * @param bool $with_container Set to false to not return the HTML container.
+ * @return string The output to print.
+ */
+function get_imagify_media_column_content( $process, $with_container = true ) {
+ if ( ! $process->is_valid() ) {
+ return __( 'This media is not valid.', 'imagify' );
+ }
+
+ if ( ! $process->current_user_can( 'manual-optimize' ) ) {
+ return __( 'You are not allowed to optimize this file.', 'imagify' );
+ }
+
+ $media = $process->get_media();
+
+ // Check if the media is supported.
+ if ( ! $media->is_supported() ) {
+ return __( 'This media is not supported.', 'imagify' );
+ }
+
+ // Check if the media has the required WP data.
+ if ( ! $media->has_required_media_data() ) {
+ return __( 'This media lacks the required metadata and cannot be optimized.', 'imagify' );
+ }
+
+ $data = $process->get_data();
+
+ // Check if the API key is valid.
+ if ( ! Imagify_Requirements::is_api_key_valid() && ! $data->is_optimized() ) {
+ $output = __( 'Invalid API key', 'imagify' );
+ $output .= ' ';
+ $output .= '' . __( 'Check your Settings', 'imagify' ) . ' ';
+ return $output;
+ }
+
+ $media_id = $media->get_id();
+ $context = $media->get_context();
+ $views = Imagify_Views::get_instance();
+ $is_locked = $process->is_locked();
+
+ if ( $is_locked ) {
+ switch ( $is_locked ) {
+ case 'optimizing':
+ $lock_label = __( 'Optimizing...', 'imagify' );
+ break;
+ case 'restoring':
+ $lock_label = __( 'Restoring...', 'imagify' );
+ break;
+ default:
+ $lock_label = __( 'Processing...', 'imagify' );
+ }
+
+ if ( ! $with_container ) {
+ return $views->get_template( 'button/processing', [ 'label' => $lock_label ] );
+ }
+
+ return $views->get_template( 'container/data-actions', [
+ 'media_id' => $media_id,
+ 'context' => $context,
+ 'content' => $views->get_template( 'button/processing', [ 'label' => $lock_label ] ),
+ ] );
+ }
+
+ // Check if the image was optimized.
+ if ( ! $data->get_optimization_status() ) {
+ $output = Imagify_Views::get_instance()->get_template( 'button/optimize', [
+ 'url' => get_imagify_admin_url( 'manual-optimize', [
+ 'attachment_id' => $media_id,
+ 'context' => $context,
+ ] ),
+ ] );
+
+ if ( $media->has_backup() ) {
+ $output .= ' ';
+ }
+ } else {
+ $output = get_imagify_attachment_optimization_text( $process );
+ }
+
+ if ( ! $with_container ) {
+ return $output;
+ }
+
+ return $views->get_template( 'container/data-actions', [
+ 'media_id' => $media_id,
+ 'context' => $context,
+ 'content' => $output,
+ ] );
+}
diff --git a/wp/wp-content/plugins/imagify/inc/functions/admin.php b/wp/wp-content/plugins/imagify/inc/functions/admin.php
new file mode 100644
index 00000000..efe7c935
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/functions/admin.php
@@ -0,0 +1,437 @@
+in_admin() ) {
+ return false;
+ }
+
+ switch ( $identifier ) {
+ case 'imagify-settings':
+ // Imagify Settings or Imagify Network Settings.
+ $slug = Imagify_Views::get_instance()->get_settings_page_slug();
+ return 'settings_page_' . $slug === $current_screen->id || $slug . '_page_' . $slug . '-network' === $current_screen->id || 'toplevel_page_' . $slug . '-network' === $current_screen->id;
+
+ case 'imagify-network-settings':
+ // Imagify Network Settings.
+ $slug = Imagify_Views::get_instance()->get_settings_page_slug();
+ return $slug . '_page_' . $slug . '-network' === $current_screen->id || 'toplevel_page_' . $slug . '-network' === $current_screen->id;
+
+ case 'library':
+ // Media Library.
+ return 'upload' === $current_screen->id;
+
+ case 'upload':
+ // Upload New Media.
+ return 'media' === $current_screen->id;
+
+ case 'post':
+ // Edit Post, Page, Attachment, etc.
+ return 'post' === $current_screen->base;
+
+ case 'attachment':
+ case 'post-attachment':
+ // Edit Attachment.
+ return 'post' === $current_screen->base && 'attachment' === $current_screen->id && $post_id && imagify_is_attachment_mime_type_supported( $post_id );
+
+ case 'bulk':
+ case 'bulk-optimization':
+ // Bulk Optimization (any).
+ $slug = Imagify_Views::get_instance()->get_bulk_page_slug();
+ return 'toplevel_page_' . $slug . '-network' === $current_screen->id || 'media_page_' . $slug === $current_screen->id;
+
+ case 'files-bulk-optimization':
+ // Bulk Optimization (custom folders).
+ $slug = Imagify_Views::get_instance()->get_bulk_page_slug();
+ return 'toplevel_page_' . $slug . '-network' === $current_screen->id || 'media_page_' . $slug === $current_screen->id;
+
+ case 'files':
+ case 'files-list':
+ // "Custom folders" files list.
+ $slug = Imagify_Views::get_instance()->get_files_page_slug();
+ return 'imagify_page_' . $slug . '-network' === $current_screen->id || 'media_page_' . $slug === $current_screen->id;
+
+ case 'media-modal':
+ // Media modal.
+ return did_action( 'wp_enqueue_media' ) || doing_filter( 'wp_enqueue_media' );
+
+ default:
+ return $identifier === $current_screen->id;
+ }
+}
+
+/**
+ * Get the URL related to specific admin page or action.
+ *
+ * @since 1.0
+ *
+ * @param string $action An action.
+ * @param array|string $arg An array of arguments. It can contain an attachment ID and/or a context.
+ * @return string The URL of the specific admin page or action.
+ */
+function get_imagify_admin_url( $action = 'settings', $arg = [] ) {
+ if ( is_array( $arg ) ) {
+ $id = isset( $arg['attachment_id'] ) ? $arg['attachment_id'] : 0;
+ $context = isset( $arg['context'] ) ? $arg['context'] : 'wp';
+ $level = isset( $arg['optimization_level'] ) ? $arg['optimization_level'] : '';
+ }
+
+ switch ( $action ) {
+ case 'manual-reoptimize':
+ case 'manual-override-upload': // Deprecated.
+ return wp_nonce_url( admin_url( 'admin-post.php?action=imagify_manual_reoptimize&attachment_id=' . $id . '&optimization_level=' . $level . '&context=' . $context ), 'imagify-manual-reoptimize-' . $id . '-' . $context );
+
+ case 'optimize-missing-sizes':
+ return wp_nonce_url( admin_url( 'admin-post.php?action=imagify_optimize_missing_sizes&attachment_id=' . $id . '&context=' . $context ), 'imagify-optimize-missing-sizes-' . $id . '-' . $context );
+
+ case 'generate-nextgen-versions':
+ return wp_nonce_url( admin_url( 'admin-post.php?action=imagify_generate_nextgen_versions&attachment_id=' . $id . '&context=' . $context ), 'imagify-generate-nextgen-versions-' . $id . '-' . $context );
+
+ case 'delete-nextgen-versions':
+ return wp_nonce_url( admin_url( 'admin-post.php?action=imagify_delete_nextgen_versions&attachment_id=' . $id . '&context=' . $context ), 'imagify-delete-nextgen-versions-' . $id . '-' . $context );
+
+ case 'optimize':
+ case 'manual-upload': // Deprecated.
+ case 'manual-optimize':
+ return wp_nonce_url( admin_url( 'admin-post.php?action=imagify_manual_optimize&attachment_id=' . $id . '&context=' . $context ), 'imagify-optimize-' . $id . '-' . $context );
+
+ case 'restore':
+ case 'restore-upload': // Deprecated.
+ return wp_nonce_url( admin_url( 'admin-post.php?action=imagify_restore&attachment_id=' . $id . '&context=' . $context ), 'imagify-restore-' . $id . '-' . $context );
+
+ case 'optimize-file':
+ case 'restore-file':
+ case 'refresh-file-modified':
+ $action = 'imagify_' . str_replace( '-', '_', $action );
+ return wp_nonce_url( admin_url( 'admin-post.php?action=' . $action . '&id=' . $id ), $action );
+
+ case 'reoptimize-file':
+ $action = 'imagify_' . str_replace( '-', '_', $action );
+ return wp_nonce_url( admin_url( 'admin-post.php?action=' . $action . '&id=' . $id . '&level=' . $level ), $action );
+
+ case 'get-files-tree':
+ return wp_nonce_url( admin_url( 'admin-ajax.php?action=imagify_get_files_tree' ), 'get-files-tree' );
+
+ case 'bulk-optimization':
+ return admin_url( 'upload.php?page=' . Imagify_Views::get_instance()->get_bulk_page_slug() );
+
+ case 'files-bulk-optimization':
+ $page = '?page=' . Imagify_Views::get_instance()->get_bulk_page_slug();
+ return imagify_is_active_for_network() ? network_admin_url( 'admin.php' . $page ) : admin_url( 'upload.php' . $page );
+
+ case 'files-list':
+ $page = '?page=' . Imagify_Views::get_instance()->get_files_page_slug();
+ return imagify_is_active_for_network() ? network_admin_url( 'admin.php' . $page ) : admin_url( 'upload.php' . $page );
+
+ case 'folder-errors':
+ switch ( $arg ) {
+ case 'wp':
+ return add_query_arg( array(
+ 'mode' => 'list',
+ 'imagify-status' => 'errors',
+ ), admin_url( 'upload.php' ) );
+
+ case 'custom-folders':
+ return add_query_arg( array(
+ 'status-filter' => 'errors',
+ ), get_imagify_admin_url( 'files-list' ) );
+ }
+ /**
+ * Provide a URL to a page displaying optimization errors for the given context.
+ *
+ * @since 1.9
+ *
+ * @param string $url The URL.
+ * @param string $arg The context.
+ */
+ return apply_filters( 'imagify_optimization_errors_url', '', $arg );
+
+ case 'dismiss-notice':
+ return wp_nonce_url( admin_url( 'admin-post.php?action=imagify_dismiss_notice¬ice=' . $arg ), Notices::DISMISS_NONCE_ACTION );
+
+ default:
+ $page = '?page=' . Imagify_Views::get_instance()->get_settings_page_slug();
+ return imagify_is_active_for_network() ? network_admin_url( 'admin.php' . $page ) : admin_url( 'options-general.php' . $page );
+ }
+}
+
+/**
+ * Get maximal width and height from all thumbnails.
+ *
+ * @since 1.1
+ *
+ * @return array An array containing the max width and height.
+ */
+function get_imagify_max_intermediate_image_size() {
+ $width = 0;
+ $height = 0;
+ $limit = 9999;
+
+ foreach ( get_imagify_thumbnail_sizes() as $_size ) {
+ if ( $_size['width'] > $width && $_size['width'] < $limit ) {
+ $width = $_size['width'];
+ }
+
+ if ( $_size['height'] > $height && $_size['height'] < $limit ) {
+ $height = $_size['height'];
+ }
+ }
+
+ return array(
+ 'width' => $width,
+ 'height' => $height,
+ );
+}
+
+/**
+ * Simple helper to get the WP Rocket's site URL.
+ * The URL is localized and contains some utm_*** parameters.
+ *
+ * @since 1.6.8
+ * @since 1.6.9 Added $path and $query parameters.
+ *
+ * @param string $path A path to add to the URL (URI). Not in use yet.
+ * @param array $query An array of query arguments (utm_*).
+ * @return string The URL.
+ */
+function imagify_get_wp_rocket_url( $path = false, $query = array() ) {
+ $wprocket_url = 'https://wp-rocket.me/';
+
+ // Current lang.
+ $lang = imagify_get_current_lang_in( array( 'de', 'es', 'fr', 'it' ) );
+
+ if ( 'en' !== $lang ) {
+ $wprocket_url .= $lang . '/';
+ }
+
+ // URI.
+ $paths = array(
+ 'pricing' => array(
+ 'de' => 'preise',
+ 'en' => 'pricing',
+ 'es' => 'precios',
+ 'fr' => 'offres',
+ 'it' => 'offerte',
+ ),
+ );
+
+ if ( $path ) {
+ $path = trim( $path, '/' );
+
+ if ( isset( $paths[ $path ] ) ) {
+ $wprocket_url .= $paths[ $path ][ $lang ] . '/';
+ } else {
+ $wprocket_url .= $path . '/';
+ }
+ }
+
+ // Query args.
+ $query = array_merge( array(
+ 'utm_source' => 'imagify-coupon',
+ 'utm_medium' => 'plugin',
+ 'utm_campaign' => 'imagify',
+ ), $query );
+
+ return add_query_arg( $query, $wprocket_url );
+}
+
+/**
+ * Check for nonce.
+ *
+ * @since 1.9.11 Return true when nonce is good.
+ * @since 1.6.10
+ *
+ * @param string $action Action nonce.
+ * @param string|bool $query_arg Optional. Key to check for the nonce in `$_REQUEST`. If false, `$_REQUEST` values will be evaluated for '_ajax_nonce', and '_wpnonce' (in that order). Default false.
+ *
+ * @return bool True if the nonce is good; otherwise terminates.
+ */
+function imagify_check_nonce( $action, $query_arg = false ) {
+ if ( ! check_ajax_referer( $action, $query_arg, false ) ) {
+ imagify_die();
+ return false;
+ }
+
+ return true;
+}
+
+/**
+ * Die Today.
+ *
+ * @since 1.6.10
+ *
+ * @param string $message A message to display.
+ */
+function imagify_die( $message = null ) {
+ if ( ! isset( $message ) ) {
+ /* translators: This sentense already exists in WordPress. */
+ $message = __( 'Sorry, you are not allowed to do that.', 'imagify' );
+ } elseif ( is_wp_error( $message ) ) {
+ $message = imagify_translate_api_message( $message->get_error_message() );
+ }
+
+ if ( is_array( $message ) ) {
+ if ( ! empty( $message['error'] ) ) {
+ $message['error'] = imagify_translate_api_message( $message['error'] );
+ } elseif ( ! empty( $message['detail'] ) ) {
+ $message['detail'] = imagify_translate_api_message( $message['detail'] );
+ }
+ }
+
+ if ( wp_doing_ajax() ) {
+ wp_send_json_error( $message );
+ }
+
+ if ( is_array( $message ) ) {
+ if ( ! empty( $message['error'] ) ) {
+ $message = $message['error'];
+ } elseif ( ! empty( $message['detail'] ) ) {
+ $message = $message['detail'];
+ } else {
+ $message = reset( $message );
+ }
+ }
+
+ if ( wp_get_referer() ) {
+ $message .= '';
+ $message .= sprintf( '%s ',
+ esc_url( remove_query_arg( 'updated', wp_get_referer() ) ),
+ /* translators: This sentense already exists in WordPress. */
+ __( 'Go back', 'imagify' )
+ );
+ }
+
+ /* translators: %s is the plugin name. */
+ wp_die( $message, sprintf( __( '%s Failure Notice', 'imagify' ), 'Imagify' ), 403 );
+}
+
+/**
+ * Redirect if not an ajax request.
+ *
+ * @since 1.6.10
+ *
+ * @param string $message A message to display in an admin notice once redirected.
+ * @param array|string $args_or_url An array of query args to add to the redirection URL. If a string, the complete URL.
+ */
+function imagify_maybe_redirect( $message = false, $args_or_url = array() ) {
+ if ( wp_doing_ajax() ) {
+ return;
+ }
+
+ if ( $args_or_url && is_array( $args_or_url ) ) {
+ $redirect = add_query_arg( $args_or_url, wp_get_referer() );
+ } elseif ( $args_or_url && is_string( $args_or_url ) ) {
+ $redirect = $args_or_url;
+ } else {
+ $redirect = wp_get_referer();
+ }
+
+ /**
+ * Filter the URL to redirect to.
+ *
+ * @since 1.6.10
+ *
+ * @param string $redirect The URL to redirect to.
+ */
+ $redirect = apply_filters( 'imagify_redirect_to', $redirect );
+
+ if ( $message ) {
+ if ( is_multisite() && strpos( $redirect, network_admin_url( '/' ) ) === 0 ) {
+ Notices::get_instance()->add_network_temporary_notice( $message );
+ } else {
+ Notices::get_instance()->add_site_temporary_notice( $message );
+ }
+ }
+
+ wp_safe_redirect( esc_url_raw( $redirect ) );
+ die();
+}
+
+/**
+ * Get cached Imagify user data.
+ * This is usefull to prevent triggering an HTTP request to our server on every page load, but it can be used only where the data doesn't need to be in real time.
+ *
+ * @since 1.7
+ *
+ * @return object|bool An object on success. False otherwise.
+ */
+function imagify_get_cached_user() {
+ if ( ! Imagify_Requirements::is_api_key_valid() ) {
+ return false;
+ }
+
+ if ( imagify_is_active_for_network() ) {
+ $user = get_site_transient( 'imagify_user' );
+ } else {
+ $user = get_transient( 'imagify_user' );
+ }
+
+ return is_object( $user ) ? $user : false;
+}
+
+/**
+ * Cache Imagify user data for 5 minutes.
+ * Runs every methods to store the results. Also stores formatted data like the quota and the next update date.
+ *
+ * @since 1.7
+ *
+ * @return object|bool An object on success. False otherwise.
+ */
+function imagify_cache_user() {
+ if ( ! Imagify_Requirements::is_api_key_valid() ) {
+ return false;
+ }
+
+ $user = new User();
+ $data = (object) get_object_vars( $user );
+ $methods = get_class_methods( $user );
+
+ foreach ( $methods as $method ) {
+ if ( '__construct' !== $method ) {
+ $data->$method = $user->$method();
+ }
+ }
+
+ $data->quota_formatted = imagify_size_format( $user->quota * pow( 1024, 2 ) );
+ $data->next_date_update_formatted = date_i18n( get_option( 'date_format' ), strtotime( $user->next_date_update ) );
+
+ if ( imagify_is_active_for_network() ) {
+ set_site_transient( 'imagify_user', $data, 5 * MINUTE_IN_SECONDS );
+ } else {
+ set_transient( 'imagify_user', $data, 5 * MINUTE_IN_SECONDS );
+ }
+
+ return $data;
+}
+
+/**
+ * Delete cached Imagify user data.
+ *
+ * @since 1.9.5
+ */
+function imagify_delete_cached_user() {
+ if ( imagify_is_active_for_network() ) {
+ delete_site_transient( 'imagify_user' );
+ } else {
+ delete_transient( 'imagify_user' );
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/inc/functions/api.php b/wp/wp-content/plugins/imagify/inc/functions/api.php
new file mode 100644
index 00000000..2168dd70
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/functions/api.php
@@ -0,0 +1,315 @@
+create_user( $data );
+}
+
+/**
+ * Update your Imagify account.
+ *
+ * @param string $data All user data.
+ * @return object
+ */
+function update_imagify_user( $data ) {
+ return imagify()->update_user( $data );
+}
+
+/**
+ * Get your Imagify account infos.
+ *
+ * @return object
+ */
+function get_imagify_user() {
+ return imagify()->get_user();
+}
+
+/**
+ * Get the Imagify API version.
+ *
+ * @return object
+ */
+function get_imagify_api_version() {
+ return imagify()->get_api_version();
+}
+
+/**
+ * Check your Imagify API key status.
+ *
+ * @param string $data An API key.
+ * @return bool
+ */
+function get_imagify_status( $data ) {
+ return imagify()->get_status( $data );
+}
+
+/**
+ * Optimize an image by uploading it on Imagify.
+ *
+ * @param array $data All image data.
+ * @return object
+ */
+function fetch_imagify_image( $data ) {
+ return imagify()->fetch_image( $data );
+}
+
+/**
+ * Optimize an image by sharing its URL on Imagify.
+ *
+ * @since 1.6.7 $data['image'] can contain the file path (prefered) or the result of `curl_file_create()`.
+ *
+ * @param array $data All image data.
+ * @return object
+ */
+function upload_imagify_image( $data ) {
+ return imagify()->upload_image( $data );
+}
+
+/**
+ * Get Imagify Plans Prices.
+ *
+ * @since 1.5
+ *
+ * @return object
+ */
+function get_imagify_plans_prices() {
+ return imagify()->get_plans_prices();
+}
+
+/**
+ * Get Imagify All Prices (plans).
+ *
+ * @since 1.5.4
+ *
+ * @return object
+ */
+function get_imagify_all_prices() {
+ return imagify()->get_all_prices();
+}
+
+/**
+ * Check if Coupon Code exists.
+ *
+ * @since 1.6
+ *
+ * @param string $coupon the coupon code to check.
+ * @return object
+ */
+function check_imagify_coupon_code( $coupon ) {
+ return imagify()->check_coupon_code( $coupon );
+}
+
+/**
+ * Check if Discount/Promotion is available.
+ *
+ * @since 1.6.3
+ *
+ * @return object
+ */
+function check_imagify_discount() {
+ return imagify()->check_discount();
+}
+
+/**
+ * Get Maximum image size for free plan.
+ *
+ * @since 1.5.6
+ *
+ * @return string
+ */
+function get_imagify_max_image_size() {
+ $max_image_size = get_transient( 'imagify_max_image_size' );
+
+ if ( false === $max_image_size ) {
+ $max_image_size = imagify()->get_public_info();
+
+ if ( ! is_wp_error( $max_image_size ) ) {
+ $max_image_size = $max_image_size->max_image_size;
+ set_transient( 'imagify_max_image_size', $max_image_size, 6 * HOUR_IN_SECONDS );
+ }
+ }
+
+ return $max_image_size;
+}
+
+/**
+ * Translate a message from our servers.
+ *
+ * @since 1.6.10
+ *
+ * @see Imagify::curl_http_call()
+ * @see Imagify::handle_response()
+ *
+ * @param string $message The message from the server (in English).
+ * @return string If in our list, the translated message. The original message otherwise.
+ */
+function imagify_translate_api_message( $message ) {
+ if ( ! $message ) {
+ $message = 'Unknown error occurred';
+ }
+
+ if ( is_wp_error( $message ) ) {
+ if ( $message->errors ) {
+ foreach ( (array) $message->errors as $code => $messages ) {
+ if ( $messages ) {
+ $message->errors[ $code ] = array_map( 'imagify_translate_api_message', (array) $messages );
+ }
+ }
+ }
+
+ return $message;
+ }
+
+ if ( is_object( $message ) && ! empty( $message->detail ) ) {
+ $message->detail = imagify_translate_api_message( $message->detail );
+ }
+
+ if ( ! is_string( $message ) ) {
+ return $message;
+ }
+
+ $trim_message = trim( $message, '. ' );
+
+ $messages = [
+ // Local messages from Imagify::curl_http_call() and Imagify::handle_response().
+ 'Could not initialize a new cURL handle' => __( 'Could not initialize a new cURL handle.', 'imagify' ),
+ 'Unknown error occurred' => sprintf(
+ // translators: %1$s = opening link tag, %2$s = closing link tag.
+ __( 'An unknown error occurred: %1$sMore info and possible solutions%2$s', 'imagify' ),
+ '',
+ ' '
+ ),
+ 'Your image is too big to be uploaded on our server' => __( 'Your file is too big to be uploaded on our server.', 'imagify' ),
+ 'Webp is less performant than original' => __( 'WebP file is larger than the original image', 'imagify' ),
+ 'Our server returned an invalid response' => __( 'Our server returned an invalid response.', 'imagify' ),
+ 'cURL isn\'t installed on the server' => __( 'cURL is not available on the server.', 'imagify' ),
+ // API messages.
+ 'Authentification not provided' => __( 'Authentication not provided.', 'imagify' ),
+ 'Cannot create client token' => __( 'Cannot create client token.', 'imagify' ),
+ 'Confirm your account to continue optimizing image' => __( 'Confirm your account to continue optimizing files.', 'imagify' ),
+ 'Coupon doesn\'t exist' => __( 'Coupon does not exist.', 'imagify' ),
+ 'Email field shouldn\'t be empty' => __( 'Email field should not be empty.', 'imagify' ),
+ 'Email or Password field shouldn\'t be empty' => __( 'This account already exists.', 'imagify' ),
+ 'Error uploading to data Storage' => __( 'Error uploading to Data Storage.', 'imagify' ),
+ 'Not able to connect to Data Storage API to get the token' => __( 'Unable to connect to Data Storage API to get the token.', 'imagify' ),
+ 'Not able to connect to Data Storage API' => __( 'Unable to connect to Data Storage API.', 'imagify' ),
+ 'Not able to retrieve the token from DataStorage API' => __( 'Unable to retrieve the token from Data Storage API.', 'imagify' ),
+ 'This email is already registered, you should try another email' => __( 'This email is already registered, you should try another email.', 'imagify' ),
+ 'This user doesn\'t exit' => __( 'This user does not exist.', 'imagify' ),
+ 'Too many request, be patient' => __( 'Too many requests, please be patient.', 'imagify' ),
+ 'Unable to regenerate access token' => __( 'Unable to regenerate access token.', 'imagify' ),
+ 'User not valid' => __( 'User not valid.', 'imagify' ),
+ 'WELL DONE. This image is already compressed, no further compression required' => __( 'WELL DONE. This media file is already optimized, no further optimization is required.', 'imagify' ),
+ 'You are not authorized to perform this action' => __( 'You are not authorized to perform this action.', 'imagify' ),
+ 'You\'ve consumed all your data. You have to upgrade your account to continue' => __( 'You have consumed all your data. You have to upgrade your account to continue.', 'imagify' ),
+ 'Invalid token' => __( 'Invalid API key', 'imagify' ),
+ 'Upload a valid image. The file you uploaded was either not an image or a corrupted image' => __( 'Invalid or corrupted file.', 'imagify' ),
+ ];
+
+ if ( isset( $messages[ $trim_message ] ) ) {
+ return $messages[ $trim_message ];
+ }
+
+ // Local message.
+ if ( preg_match( '@^(?:Unknown|An) error occurred \((.+)\)$@', $trim_message, $matches ) ) {
+ /* translators: %s is an error message. */
+ return sprintf( __( 'An error occurred (%s).', 'imagify' ), esc_html( wp_strip_all_tags( $matches[1] ) ) );
+ }
+
+ // Local message.
+ if ( preg_match( '@^Our server returned an error \((.+)\)$@', $trim_message, $matches ) ) {
+ /* translators: %s is an error message. */
+ return sprintf( __( 'Our server returned an error (%s).', 'imagify' ), esc_html( wp_strip_all_tags( $matches[1] ) ) );
+ }
+
+ // API message.
+ if ( preg_match( '@^Custom one time plan starts from (\d+) MB$@', $trim_message, $matches ) ) {
+ /* translators: %s is a formatted number, dont use %d. */
+ return sprintf( __( 'Custom One Time plan starts from %s MB.', 'imagify' ), number_format_i18n( (int) $matches[1] ) );
+ }
+
+ // API message.
+ if ( preg_match( '@^(.*) is not a valid extension$@', $trim_message, $matches ) ) {
+ /* translators: %s is a file extension. */
+ return sprintf( __( '%s is not a valid extension.', 'imagify' ), sanitize_text_field( $matches[1] ) );
+ }
+
+ // API message.
+ if ( preg_match( '@^Request was throttled\. Expected available in ([\d.]+) second$@', $trim_message, $matches ) ) {
+ /* translators: %s is a float number. */
+ return sprintf( _n( 'Request was throttled. Expected available in %s second.', 'Request was throttled. Expected available in %s seconds.', (int) $matches[1], 'imagify' ), sanitize_text_field( $matches[1] ) );
+ }
+
+ return $message;
+}
+
+/**
+ * Runs the bulk optimization
+ *
+ * @param array $contexts An array of contexts (WP/Custom folders).
+ * @param int $optimization_level Optimization level to use.
+ *
+ * @return void
+ */
+function imagify_bulk_optimize( $contexts, $optimization_level ) {
+ foreach ( $contexts as $context ) {
+ Imagify\Bulk\Bulk::get_instance()->run_optimize( $context, $optimization_level );
+ }
+}
+
+/**
+ * Runs the next-gen generation
+ *
+ * @param array $contexts An array of contexts (WP/Custom folders).
+ *
+ * @return void
+ */
+function imagify_generate_nextgen( $contexts ) {
+ Imagify\Bulk\Bulk::get_instance()->run_generate_nextgen( $contexts );
+}
+
+/**
+ * Add command to WP CLI
+ *
+ * @param CommandInterface $command Command object.
+ *
+ * @return void
+ */
+function imagify_add_command( CommandInterface $command ) {
+ if ( ! defined( 'WP_CLI' ) || ! WP_CLI || ! class_exists( '\WP_CLI' ) ) {
+ return;
+ }
+
+ \WP_CLI::add_command( $command->get_name(), $command, [
+ 'shortdesc' => $command->get_description(),
+ 'synopsis' => $command->get_synopsis(),
+ ] );
+}
+
+/**
+ * Checks if the API key is valid
+ *
+ * @return bool
+ */
+function imagify_is_api_key_valid() {
+ return Imagify_Requirements::is_api_key_valid();
+}
diff --git a/wp/wp-content/plugins/imagify/inc/functions/attachments.php b/wp/wp-content/plugins/imagify/inc/functions/attachments.php
new file mode 100644
index 00000000..af361d74
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/functions/attachments.php
@@ -0,0 +1,379 @@
+ 'image/jpeg',
+ 'png' => 'image/png',
+ 'gif' => 'image/gif',
+ 'webp' => 'image/webp',
+ ];
+ }
+
+ if ( 'image' !== $type ) {
+ $mimes['pdf'] = 'application/pdf';
+ }
+
+ return $mimes;
+}
+
+/**
+ * Tell if an attachment has a supported mime type.
+ * Was previously Imagify_AS3CF::is_mime_type_supported() since 1.6.6.
+ *
+ * @since 1.6.8
+ * @author Grégory Viguier
+ *
+ * @param int $attachment_id The attachment ID.
+ * @return bool
+ */
+function imagify_is_attachment_mime_type_supported( $attachment_id ) {
+ static $is = array( false );
+
+ $attachment_id = absint( $attachment_id );
+
+ if ( isset( $is[ $attachment_id ] ) ) {
+ return $is[ $attachment_id ];
+ }
+
+ $mime_types = imagify_get_mime_types();
+ $mime_types = array_flip( $mime_types );
+ $mime_type = (string) get_post_mime_type( $attachment_id );
+
+ $is[ $attachment_id ] = isset( $mime_types[ $mime_type ] );
+
+ return $is[ $attachment_id ];
+}
+
+/**
+ * Get post statuses related to attachments.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ *
+ * @return array
+ */
+function imagify_get_post_statuses() {
+ static $statuses;
+
+ if ( isset( $statuses ) ) {
+ return $statuses;
+ }
+
+ $statuses = array(
+ 'inherit' => 'inherit',
+ 'private' => 'private',
+ );
+
+ $custom_statuses = get_post_stati( array( 'public' => true ) );
+ unset( $custom_statuses['publish'] );
+
+ if ( $custom_statuses ) {
+ $statuses = array_merge( $statuses, $custom_statuses );
+ }
+
+ /**
+ * Filter the post statuses Imagify is allowed to optimize.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ *
+ * @param array $statuses An array of post statuses. Kays and values are set.
+ */
+ $statuses = apply_filters( 'imagify_post_statuses', $statuses );
+
+ return $statuses;
+}
+
+/**
+ * Tell if the site has attachments (only the ones Imagify would optimize) without the required WP metadata.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ *
+ * @return bool
+ */
+function imagify_has_attachments_without_required_metadata() {
+ global $wpdb;
+ static $has;
+
+ if ( isset( $has ) ) {
+ return $has;
+ }
+
+ $mime_types = Imagify_DB::get_mime_types();
+ $statuses = Imagify_DB::get_post_statuses();
+ $nodata_join = Imagify_DB::get_required_wp_metadata_join_clause(
+ 'p.ID',
+ false,
+ false,
+ "AND p.post_mime_type IN ( $mime_types )
+ AND p.post_type = 'attachment'
+ AND p.post_status IN ( $statuses )"
+ );
+ $nodata_where = Imagify_DB::get_required_wp_metadata_where_clause( array(
+ 'matching' => false,
+ 'test' => false,
+ ) );
+ $has = (bool) $wpdb->get_var( // WPCS: unprepared SQL ok.
+ "
+ SELECT p.ID
+ FROM $wpdb->posts AS p
+ $nodata_join
+ WHERE p.post_mime_type IN ( $mime_types )
+ AND p.post_type = 'attachment'
+ AND p.post_status IN ( $statuses )
+ $nodata_where
+ LIMIT 1"
+ );
+
+ return $has;
+}
+
+/**
+ * Get the path to the backups directory.
+ *
+ * @since 1.6.8
+ * @author Grégory Viguier
+ *
+ * @param bool $bypass_error True to return the path even if there is an error. This is used when we want to display this path in a message for example.
+ * @return string|bool Path to the backups directory. False on failure.
+ */
+function get_imagify_backup_dir_path( $bypass_error = false ) {
+ static $backup_dir;
+
+ if ( isset( $backup_dir ) ) {
+ return $backup_dir;
+ }
+
+ $upload_basedir = get_imagify_upload_basedir( $bypass_error );
+
+ if ( ! $upload_basedir ) {
+ return false;
+ }
+
+ $backup_dir = $upload_basedir . 'backup/';
+
+ /**
+ * Filter the backup directory path.
+ *
+ * @since 1.0
+ *
+ * @param string $backup_dir The backup directory path.
+ */
+ $backup_dir = apply_filters( 'imagify_backup_directory', $backup_dir );
+ $backup_dir = imagify_get_filesystem()->normalize_dir_path( $backup_dir );
+
+ return $backup_dir;
+}
+
+/**
+ * Tell if the folder containing the backups is writable.
+ *
+ * @since 1.6.8
+ * @author Grégory Viguier
+ *
+ * @return bool
+ */
+function imagify_backup_dir_is_writable() {
+ return imagify_get_filesystem()->make_dir( get_imagify_backup_dir_path() );
+}
+
+/**
+ * Get the backup path of a specific attachement.
+ *
+ * @since 1.0
+ *
+ * @param string $file_path The file path.
+ * @return string|bool The backup path. False on failure.
+ */
+function get_imagify_attachment_backup_path( $file_path ) {
+ $file_path = wp_normalize_path( (string) $file_path );
+ $upload_basedir = get_imagify_upload_basedir();
+ $backup_dir = get_imagify_backup_dir_path();
+
+ if ( ! $file_path || ! $upload_basedir ) {
+ return false;
+ }
+
+ return preg_replace( '@^' . preg_quote( $upload_basedir, '@' ) . '@', $backup_dir, $file_path );
+}
+
+/**
+ * Retrieve file path for an attachment based on filename.
+ *
+ * @since 1.4.5
+ *
+ * @param int $file_path The file path.
+ * @return string|false The file path to where the attached file should be, false otherwise.
+ */
+function get_imagify_attached_file( $file_path ) {
+ $file_path = wp_normalize_path( (string) $file_path );
+ $upload_basedir = get_imagify_upload_basedir();
+
+ if ( ! $file_path || ! $upload_basedir ) {
+ return false;
+ }
+
+ // The file path is absolute.
+ if ( strpos( $file_path, '/' ) === 0 || preg_match( '|^.:\\\|', $file_path ) ) {
+ return false;
+ }
+
+ // Prepend upload dir.
+ return $upload_basedir . $file_path;
+}
+
+/**
+ * Retrieve the URL for an attachment based on file path.
+ *
+ * @since 1.4.5
+ *
+ * @param string $file_path A relative or absolute file path.
+ * @return string|bool File URL, otherwise false.
+ */
+function get_imagify_attachment_url( $file_path ) {
+ $file_path = wp_normalize_path( (string) $file_path );
+ $upload_basedir = get_imagify_upload_basedir();
+
+ if ( ! $file_path || ! $upload_basedir ) {
+ return false;
+ }
+
+ $upload_baseurl = get_imagify_upload_baseurl();
+
+ // Check that the upload base exists in the (absolute) file location.
+ if ( 0 === strpos( $file_path, $upload_basedir ) ) {
+ // Replace file location with url location.
+ return preg_replace( '@^' . preg_quote( $upload_basedir, '@' ) . '@', $upload_baseurl, $file_path );
+ }
+
+ if ( false !== strpos( '/' . $file_path, '/wp-content/uploads/' ) ) {
+ // Get the directory name relative to the basedir (back compat for pre-2.7 uploads).
+ return trailingslashit( $upload_baseurl . _wp_get_attachment_relative_path( $file_path ) ) . imagify_get_filesystem()->file_name( $file_path );
+ }
+
+ // It's a newly-uploaded file, therefore $file is relative to the basedir.
+ return $upload_baseurl . $file_path;
+}
+
+/**
+ * Get size information for all currently registered thumbnail sizes.
+ *
+ * @since 1.5.10
+ * @since 1.6.10 For consistency, revamped the function like WP does with wp_generate_attachment_metadata().
+ * Removed the filter, added crop value to each size.
+ * @author Grégory Viguier
+ *
+ * @return array {
+ * Data for the currently registered thumbnail sizes.
+ * Size names are used as array keys.
+ *
+ * @type int $width The image width.
+ * @type int $height The image height.
+ * @type bool $crop True to crop, false to resize.
+ * @type string $name The size name.
+ * }
+ */
+function get_imagify_thumbnail_sizes() {
+ // All image size names.
+ $intermediate_image_sizes = get_intermediate_image_sizes();
+ $intermediate_image_sizes = array_flip( $intermediate_image_sizes );
+ // Additional image size attributes.
+ $additional_image_sizes = wp_get_additional_image_sizes();
+
+ // Create the full array with sizes and crop info.
+ foreach ( $intermediate_image_sizes as $size_name => $s ) {
+ $intermediate_image_sizes[ $size_name ] = array(
+ 'width' => '',
+ 'height' => '',
+ 'crop' => false,
+ 'name' => $size_name,
+ );
+
+ if ( isset( $additional_image_sizes[ $size_name ]['width'] ) ) {
+ // For theme-added sizes.
+ $intermediate_image_sizes[ $size_name ]['width'] = (int) $additional_image_sizes[ $size_name ]['width'];
+ } else {
+ // For default sizes set in options.
+ $intermediate_image_sizes[ $size_name ]['width'] = (int) get_option( "{$size_name}_size_w" );
+ }
+
+ if ( isset( $additional_image_sizes[ $size_name ]['height'] ) ) {
+ // For theme-added sizes.
+ $intermediate_image_sizes[ $size_name ]['height'] = (int) $additional_image_sizes[ $size_name ]['height'];
+ } else {
+ // For default sizes set in options.
+ $intermediate_image_sizes[ $size_name ]['height'] = (int) get_option( "{$size_name}_size_h" );
+ }
+
+ if ( isset( $additional_image_sizes[ $size_name ]['crop'] ) ) {
+ // For theme-added sizes.
+ $intermediate_image_sizes[ $size_name ]['crop'] = (int) $additional_image_sizes[ $size_name ]['crop'];
+ } else {
+ // For default sizes set in options.
+ $intermediate_image_sizes[ $size_name ]['crop'] = (int) get_option( "{$size_name}_crop" );
+ }
+ }
+
+ return $intermediate_image_sizes;
+}
+
+/**
+ * A simple helper to get the upload basedir.
+ *
+ * @since 1.6.7
+ * @since 1.6.8 Added the $bypass_error parameter.
+ * @author Grégory Viguier
+ *
+ * @param bool $bypass_error True to return the path even if there is an error. This is used when we want to display this path in a message for example.
+ * @return string|bool The path. False on failure.
+ */
+function get_imagify_upload_basedir( $bypass_error = false ) {
+ return imagify_get_filesystem()->get_upload_basedir( $bypass_error );
+}
+
+/**
+ * A simple helper to get the upload baseurl.
+ *
+ * @since 1.6.7
+ * @author Grégory Viguier
+ *
+ * @return string|bool The URL. False on failure.
+ */
+function get_imagify_upload_baseurl() {
+ return imagify_get_filesystem()->get_upload_baseurl();
+}
+
+/**
+ * Get the maximal number of unoptimized attachments to fetch.
+ *
+ * @since 1.6.14
+ * @author Grégory Viguier
+ *
+ * @return int
+ */
+function imagify_get_unoptimized_attachment_limit() {
+ /**
+ * Filter the unoptimized attachments limit query.
+ *
+ * @since 1.4.4
+ *
+ * @param int $limit The limit (-1 for unlimited).
+ */
+ $limit = (int) apply_filters( 'imagify_unoptimized_attachment_limit', 10000 );
+
+ return -1 === $limit ? PHP_INT_MAX : abs( $limit );
+}
diff --git a/wp/wp-content/plugins/imagify/inc/functions/common.php b/wp/wp-content/plugins/imagify/inc/functions/common.php
new file mode 100644
index 00000000..ac4bffc3
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/functions/common.php
@@ -0,0 +1,646 @@
+can_operate() || ! Imagify_Files_DB::get_instance()->can_operate() ) {
+ $can = false;
+ return $can;
+ }
+
+ // Check for user capacity.
+ $can = imagify_get_context( 'custom-folders' )->current_user_can( 'optimize' );
+
+ return $can;
+}
+
+/**
+ * Simple helper to get some external URLs, like to the documentation.
+ *
+ * @since 1.6.12
+ * @author Grégory Viguier
+ *
+ * @param string $target What we want.
+ * @param array $query_args An array of query arguments.
+ * @return string The URL.
+ */
+function imagify_get_external_url( $target, $query_args = array() ) {
+ $site_url = IMAGIFY_SITE_DOMAIN . '/';
+ $app_url = IMAGIFY_APP_DOMAIN . '/#/';
+
+ switch ( $target ) {
+ case 'plugin':
+ /* translators: Plugin URI of the plugin/theme */
+ $url = __( 'https://wordpress.org/plugins/imagify/', 'imagify' );
+ break;
+
+ case 'rate':
+ $url = 'https://wordpress.org/support/view/plugin-reviews/imagify?rate=5#postform';
+ break;
+
+ case 'share-twitter':
+ $url = rawurlencode( imagify_get_external_url( 'plugin' ) );
+ $url = 'https://twitter.com/intent/tweet?source=webclient&original_referer=' . $url . '&url=' . $url . '&related=imagify&hastags=performance,web,wordpress';
+ break;
+
+ case 'share-facebook':
+ $url = rawurlencode( imagify_get_external_url( 'plugin' ) );
+ $url = 'https://www.facebook.com/sharer/sharer.php?u=' . $url;
+ break;
+
+ case 'contact':
+ $lang = imagify_get_current_lang_in( 'fr' );
+ $paths = array(
+ 'en' => 'contact',
+ 'fr' => 'fr/contact',
+ );
+
+ $url = $site_url . $paths[ $lang ] . '/';
+ break;
+
+ case 'documentation':
+ $url = $site_url . 'documentation/';
+ break;
+
+ case 'documentation-imagick-gd':
+ $url = $site_url . 'documentation/solve-imagemagick-gd-required/';
+ break;
+
+ case 'register':
+ $partner = imagify_get_partner();
+
+ if ( $partner ) {
+ $query_args['partner'] = $partner;
+ }
+
+ $url = $app_url . 'register';
+ break;
+
+ case 'subscription':
+ $url = $app_url . 'subscription';
+ break;
+
+ case 'get-api-key':
+ $url = $app_url . 'api';
+ break;
+
+ case 'payment':
+ // Don't remove the trailing slash.
+ $url = $app_url . 'plugin/';
+ break;
+
+ default:
+ return '';
+ }
+
+ if ( $query_args ) {
+ $url = add_query_arg( $query_args, $url );
+ }
+
+ return $url;
+}
+
+/**
+ * Get the current lang ('fr', 'en', 'de'...), limited to a given list.
+ *
+ * @since 1.6.14
+ * @author Grégory Viguier
+ *
+ * @param array $langs An array of langs, like array( 'de', 'es', 'fr', 'it' ).
+ * @return string The current lang. Default is 'en'.
+ */
+function imagify_get_current_lang_in( $langs ) {
+ static $locale;
+
+ if ( ! isset( $locale ) ) {
+ $locale = imagify_get_locale();
+ $locale = explode( '_', strtolower( $locale . '_' ) ); // Trailing underscore is to make sure $locale[1] is set.
+ }
+
+ foreach ( (array) $langs as $lang ) {
+ if ( $lang === $locale[0] || $lang === $locale[1] ) {
+ return $lang;
+ }
+ }
+
+ return 'en';
+}
+
+/**
+ * Get the current locale.
+ *
+ * @since 1.6.14
+ * @author Grégory Viguier
+ *
+ * @return string The current locale.
+ */
+function imagify_get_locale() {
+ $locale = function_exists( 'get_user_locale' ) ? get_user_locale() : get_locale();
+ /**
+ * Filter the locale used by Imagify.
+ *
+ * @since 1.6.14
+ * @author Grégory Viguier
+ *
+ * @param string $locale The current locale.
+ */
+ return apply_filters( 'imagify_locale', $locale );
+}
+
+/**
+ * Get the label corresponding to the given optimization label.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ *
+ * @param int|bool $level Optimization level (between 0 and 2). False if no level.
+ * @param string $format Format to display the label. Use %ICON% for the icon and %s for the label.
+ * @return string The label.
+ */
+function imagify_get_optimization_level_label( $level, $format = '%s' ) {
+ if ( ! is_numeric( $level ) ) {
+ return '';
+ }
+
+ if ( strpos( $format, '%ICON%' ) !== false ) {
+ $icon = '';
+
+ switch ( $level ) {
+ case 2:
+ case 1:
+ $icon .= ' ';
+ break;
+ case 0:
+ $icon .= ' ';
+ }
+
+ $icon .= ' ';
+
+ $format = str_replace( '%ICON%', $icon, $format );
+ }
+
+ switch ( $level ) {
+ case 2:
+ case 1:
+ return sprintf( $format, __( 'Smart', 'imagify' ) );
+ case 0:
+ return sprintf( $format, __( 'Lossless', 'imagify' ) );
+ }
+
+ return '';
+}
+
+/**
+ * `array_merge()` + `array_intersect_key()`.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ *
+ * @param array $values The array we're interested in.
+ * @param array $default The array we use as boundaries.
+ * @return array
+ */
+function imagify_merge_intersect( $values, $default ) {
+ $values = array_merge( $default, (array) $values );
+ return array_intersect_key( $values, $default );
+}
+
+/**
+ * Returns true.
+ * Useful for returning true to filters easily.
+ * Similar to WP's __return_true() function, it allows to remove it from a filter without removing another one added by another plugin.
+ *
+ * @since 1.9
+ * @author Grégory Viguier
+ *
+ * @return bool True.
+ */
+function imagify_return_true() {
+ return true;
+}
+
+/**
+ * Returns false.
+ * Useful for returning false to filters easily.
+ * Similar to WP's __return_false() function, it allows to remove it from a filter without removing another one added by another plugin.
+ *
+ * @since 1.9
+ * @author Grégory Viguier
+ *
+ * @return bool False.
+ */
+function imagify_return_false() {
+ return false;
+}
+
+/**
+ * Marks a class as deprecated and informs when it has been used.
+ * Similar to _deprecated_constructor(), but with different strings.
+ * The current behavior is to trigger a user error if `WP_DEBUG` is true.
+ *
+ * @since 1.9
+ * @author Grégory Viguier
+ *
+ * @param string $class The class containing the deprecated constructor.
+ * @param string $version The version of WordPress that deprecated the function.
+ * @param string $replacement Optional. The function that should have been called. Default null.
+ * @param string $parent_class Optional. The parent class calling the deprecated constructor. Default empty string.
+ */
+function imagify_deprecated_class( $class, $version, $replacement = null, $parent_class = '' ) {
+
+ /**
+ * Fires when a deprecated class is called.
+ *
+ * @since 1.9
+ * @author Grégory Viguier
+ *
+ * @param string $class The class containing the deprecated constructor.
+ * @param string $version The version of WordPress that deprecated the function.
+ * @param string $replacement Optional. The function that should have been called.
+ * @param string $parent_class The parent class calling the deprecated constructor.
+ */
+ do_action( 'imagify_deprecated_class_run', $class, $version, $replacement, $parent_class );
+
+ if ( ! WP_DEBUG ) {
+ return;
+ }
+
+ /**
+ * Filters whether to trigger an error for deprecated classes.
+ *
+ * `WP_DEBUG` must be true in addition to the filter evaluating to true.
+ *
+ * @since 1.9
+ * @author Grégory Viguier
+ *
+ * @param bool $trigger Whether to trigger the error for deprecated classes. Default true.
+ */
+ if ( ! apply_filters( 'imagify_deprecated_class_trigger_error', true ) ) {
+ return;
+ }
+
+ if ( function_exists( '__' ) ) {
+ if ( ! empty( $parent_class ) ) {
+ /**
+ * With parent class.
+ */
+ if ( ! empty( $replacement ) ) {
+ /**
+ * With replacement.
+ */
+ call_user_func(
+ 'trigger_error',
+ sprintf(
+ /* translators: 1: PHP class name, 2: PHP parent class name, 3: version number, 4: replacement class name. */
+ __( 'The called class %1$s extending %2$s is deprecated since version %3$s! Use %4$s instead.', 'imagify' ),
+ '' . $class . '',
+ '' . $parent_class . '',
+ '' . $version . ' ',
+ '' . $replacement . ''
+ )
+ );
+ return;
+ }
+
+ /**
+ * Without replacement.
+ */
+ call_user_func(
+ 'trigger_error',
+ sprintf(
+ /* translators: 1: PHP class name, 2: PHP parent class name, 3: version number. */
+ __( 'The called class %1$s extending %2$s is deprecated since version %3$s!', 'imagify' ),
+ '' . $class . '',
+ '' . $parent_class . '',
+ '' . $version . ' '
+ )
+ );
+ return;
+ }
+
+ /**
+ * Without parent class.
+ */
+ if ( ! empty( $replacement ) ) {
+ /**
+ * With replacement.
+ */
+ call_user_func(
+ 'trigger_error',
+ sprintf(
+ /* translators: 1: PHP class name, 2: version number, 3: replacement class name. */
+ __( 'The called class %1$s is deprecated since version %2$s! Use %3$s instead.', 'imagify' ),
+ '' . $class . '',
+ '' . $version . ' ',
+ '' . $replacement . ''
+ )
+ );
+ return;
+ }
+
+ /**
+ * Without replacement.
+ */
+ call_user_func(
+ 'trigger_error',
+ sprintf(
+ /* translators: 1: PHP class name, 2: version number. */
+ __( 'The called class %1$s is deprecated since version %2$s!', 'imagify' ),
+ '' . $class . '',
+ '' . $version . ' '
+ )
+ );
+ return;
+ }
+
+ if ( ! empty( $parent_class ) ) {
+ /**
+ * With parent class.
+ */
+ if ( ! empty( $replacement ) ) {
+ /**
+ * With replacement.
+ */
+ call_user_func(
+ 'trigger_error',
+ sprintf(
+ 'The called class %1$s extending %2$s is deprecated since version %3$s! Use %4$s instead.',
+ '' . $class . '',
+ '' . $parent_class . '',
+ '' . $version . ' ',
+ '' . $replacement . ''
+ )
+ );
+ return;
+ }
+
+ /**
+ * Without replacement.
+ */
+ call_user_func(
+ 'trigger_error',
+ sprintf(
+ 'The called class %1$s extending %2$s is deprecated since version %3$s!',
+ '' . $class . '',
+ '' . $parent_class . '',
+ '' . $version . ' '
+ )
+ );
+ return;
+ }
+
+ /**
+ * Without parent class.
+ */
+ if ( ! empty( $replacement ) ) {
+ /**
+ * With replacement.
+ */
+ call_user_func(
+ 'trigger_error',
+ sprintf(
+ 'The called class %1$s is deprecated since version %2$s! Use %3$s instead.',
+ '' . $class . '',
+ '' . $version . ' ',
+ '' . $replacement . ''
+ )
+ );
+ return;
+ }
+
+ /**
+ * Without replacement.
+ */
+ call_user_func(
+ 'trigger_error',
+ sprintf(
+ 'The called class %1$s is deprecated since version %2$s!',
+ '' . $class . '',
+ '' . $version . ' '
+ )
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/inc/functions/formatting.php b/wp/wp-content/plugins/imagify/inc/functions/formatting.php
new file mode 100644
index 00000000..9fb36c63
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/functions/formatting.php
@@ -0,0 +1,57 @@
+ 0 ) {
+ if ( $decimal <= 0.5 ) {
+ return floatval( $number[0] ) + 0.5;
+ }
+ if ( $decimal <= 0.99 ) {
+ return floatval( $number[0] ) + 1;
+ }
+ return 1;
+ }
+
+ return floatval( $number );
+}
+
+/**
+ * Convert number of bytes largest unit bytes will fit into.
+ * This is a clone of size_format(), but with a non-breaking space.
+ *
+ * @since 1.7
+ * @since 1.8.1 Automatic $decimals.
+ * @author Grégory Viguier
+ *
+ * @param int|string $bytes Number of bytes. Note max integer size for integers.
+ * @param int $decimals Optional. Precision of number of decimal places.
+ * If negative or not an integer, $decimals value is "automatic": 0 if $bytes <= 1GB, or 1 if > 1GB.
+ * @return string|false False on failure. Number string on success.
+ */
+function imagify_size_format( $bytes, $decimals = -1 ) {
+
+ if ( $decimals < 0 || ! is_int( $decimals ) ) {
+ $decimals = $bytes > pow( 1024, 3 ) ? 1 : 0;
+ }
+
+ $bytes = @size_format( $bytes, $decimals );
+ return str_replace( ' ', 'Â ', $bytes );
+}
diff --git a/wp/wp-content/plugins/imagify/inc/functions/i18n.php b/wp/wp-content/plugins/imagify/inc/functions/i18n.php
new file mode 100644
index 00000000..8edd3a29
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/functions/i18n.php
@@ -0,0 +1,333 @@
+ admin_url( 'admin-ajax.php' ),
+ ];
+
+ case 'notices':
+ return [
+ 'labels' => [
+ /* translators: Don't use escaped HTML entities here (like ). */
+ 'signupTitle' => __( 'Let\'s get you started!', 'imagify' ),
+ 'signupText' => __( 'Enter your email to get an API key:', 'imagify' ),
+ 'signupConfirmButtonText' => __( 'Sign Up', 'imagify' ),
+ 'signupErrorEmptyEmail' => __( 'You need to specify an email!', 'imagify' ),
+ /* translators: Don't use escaped HTML entities here (like ). */
+ 'signupSuccessTitle' => __( 'Congratulations!', 'imagify' ),
+ 'signupSuccessText' => __( 'Your account has been successfully created. Please check your mailbox, you are going to receive an email with API key.', 'imagify' ),
+ /* translators: Don't use escaped HTML entities here (like ). */
+ 'saveApiKeyTitle' => __( 'Connect to Imagify!', 'imagify' ),
+ 'saveApiKeyText' => __( 'Paste your API key below:', 'imagify' ),
+ 'saveApiKeyConfirmButtonText' => __( 'Connect me', 'imagify' ),
+ 'ApiKeyErrorEmpty' => __( 'You need to specify your API key!', 'imagify' ),
+ 'ApiKeyCheckSuccessTitle' => __( 'Congratulations!', 'imagify' ),
+ 'ApiKeyCheckSuccessText' => __( 'Your API key is valid. You can now configure the Imagify settings to optimize your images.', 'imagify' ),
+ ],
+ ];
+
+ case 'sweetalert':
+ return [
+ 'labels' => [
+ 'cancelButtonText' => __( 'Cancel' ),
+ ],
+ ];
+
+ case 'options':
+ $translations = [
+ 'getFilesTree' => imagify_can_optimize_custom_folders() ? get_imagify_admin_url( 'get-files-tree' ) : false,
+ 'labels' => [
+ 'ValidApiKeyText' => __( 'Your API key is valid.', 'imagify' ),
+ 'waitApiKeyCheckText' => __( 'Check in progress...', 'imagify' ),
+ 'ApiKeyCheckSuccessTitle' => __( 'Congratulations!', 'imagify' ),
+ 'ApiKeyCheckSuccessText' => __( 'Your API key is valid. You can now configure the Imagify settings to optimize your images.', 'imagify' ),
+ 'noBackupTitle' => __( 'Don\'t Need a Parachute?', 'imagify' ),
+ 'noBackupText' => __( 'If you keep this option deactivated, you won\'t be able to re-optimize your images to another compression level and restore your original images in case of need.', 'imagify' ),
+ 'removeFolder' => _x( 'Remove', 'custom folder', 'imagify' ),
+ 'filesTreeTitle' => __( 'Select Folders', 'imagify' ),
+ 'filesTreeSubTitle' => __( 'Select one or several folders to optimize.', 'imagify' ),
+ 'cleaningInfo' => __( 'Some folders that do not contain any images are hidden.', 'imagify' ),
+ 'confirmFilesTreeBtn' => __( 'Select Folders', 'imagify' ),
+ 'customFilesLegend' => __( 'Choose the folders to optimize', 'imagify' ),
+ 'error' => __( 'Error', 'imagify' ),
+ 'themesAdded' => __( 'Added! All Good!', 'imagify' ),
+ ],
+ ];
+
+ if ( OptimizedMediaWithoutNextGen::get_instance()->get_cached_stat() ) {
+ $contexts = imagify_get_context_names();
+ $translations['bulk'] = [
+ 'curlMissing' => ! Imagify_Requirements::supports_curl(),
+ 'editorMissing' => ! Imagify_Requirements::supports_image_editor(),
+ 'extHttpBlocked' => Imagify_Requirements::is_imagify_blocked(),
+ 'apiDown' => ! Imagify_Requirements::is_api_up(),
+ 'keyIsValid' => Imagify_Requirements::is_api_key_valid(),
+ 'isOverQuota' => Imagify_Requirements::is_over_quota(),
+ 'imagifybeatIDs' => [
+ 'progress' => $imagifybeat_actions->get_imagifybeat_id( 'options_optimization_status' ),
+ 'requirements' => $imagifybeat_actions->get_imagifybeat_id( 'requirements' ),
+ ],
+ 'ajaxActions' => [
+ 'MissingNextGen' => 'imagify_missing_nextgen_generation',
+ ],
+ 'ajaxNonce' => wp_create_nonce( 'imagify-bulk-optimize' ),
+ 'contexts' => $contexts,
+ 'progress_next_gen' => [
+ 'remaining' => OptimizedMediaWithoutNextGen::get_instance()->get_stat(),
+ 'total' => get_transient( 'imagify_missing_next_gen_total' ),
+ ],
+ 'labels' => [
+ 'curlMissing' => __( 'cURL is not available on the server.', 'imagify' ),
+ 'editorMissing' => sprintf(
+ // translators: %s is a "More info?" link.
+ __( 'No php extensions are available to edit images on the server. ImageMagick or GD is required. %s', 'imagify' ),
+ '' . __( 'More info?', 'imagify' ) . ' '
+ ),
+ 'extHttpBlocked' => __( 'External HTTP requests are blocked.', 'imagify' ),
+ 'apiDown' => __( 'Sorry, our servers are temporarily unavailable. Please, try again in a couple of minutes.', 'imagify' ),
+ 'invalidAPIKeyTitle' => __( 'Your API key is not valid!', 'imagify' ),
+ 'overQuotaTitle' => __( 'You have used all your credits!', 'imagify' ),
+ 'nothingToDoTitle' => __( 'Hold on!', 'imagify' ),
+ 'nothingToDoText' => __( 'All your optimized images already have a next-gen version. Congratulations!', 'imagify' ),
+ 'nothingToDoNoBackupText' => __( 'Because the selected images did not have a backup copy, Imagify was unable to create next-gen versions.', 'imagify' ),
+ 'error' => __( 'Error', 'imagify' ),
+ 'ajaxErrorText' => __( 'The operation failed.', 'imagify' ),
+ 'getUnoptimizedImagesErrorTitle' => __( 'Oops, There is something wrong!', 'imagify' ),
+ 'getUnoptimizedImagesErrorText' => __( 'An unknown error occurred when we tried to get all your unoptimized media files. Try again and if the issue still persists, please contact us!', 'imagify' ),
+ ],
+ ];
+
+ /**
+ * Filter the number of parallel queries generating WebP images by bulk method.
+ *
+ * @since 1.9
+ * @author Grégory Viguier
+ *
+ * @param int $bufferSize Number of parallel queries.
+ */
+ $translations['bulk']['bufferSize'] = apply_filters( 'imagify_bulk_generate_webp_buffer_size', 4 );
+ $translations['bulk']['bufferSize'] = max( 1, (int) $translations['bulk']['bufferSize'] );
+ }
+
+ return $translations;
+
+ case 'pricing-modal':
+ $translations = [
+ 'imagify_app_domain' => IMAGIFY_APP_DOMAIN,
+ 'labels' => [
+ 'errorCouponAPI' => __( 'Error with checking this coupon.', 'imagify' ),
+ /* translators: 1 is a percentage, 2 is a coupon code. */
+ 'successCouponAPI' => sprintf( _x( '%1$s off with %2$s', 'coupon validated', 'imagify' ), ' ', ' ' ),
+ 'errorPriceAPI' => __( 'Something went wrong with getting our updated offers. Please retry later.', 'imagify' ),
+ 'defaultCouponLabel' => __( 'If you have a coupon code use it here:', 'imagify' ),
+ 'errorCouponPlan' => __( 'This coupon is not valid with this plan.', 'imagify' ),
+ ],
+ ];
+
+ if ( Imagify_Requirements::is_api_key_valid() ) {
+ $translations['userDataCache'] = [
+ 'deleteAction' => 'imagify_delete_user_data_cache',
+ 'deleteNonce' => wp_create_nonce( 'imagify_delete_user_data_cache' ),
+ ];
+ }
+
+ return $translations;
+
+ case 'twentytwenty':
+ $image = [
+ 'src' => '',
+ 'width' => 0,
+ 'height' => 0,
+ ];
+
+ if ( imagify_is_screen( 'attachment' ) && wp_attachment_is_image( $post_id ) ) {
+ $process = imagify_get_optimization_process( $post_id, 'wp' );
+
+ if ( $process->is_valid() ) {
+ $media = $process->get_media();
+
+ if ( $media->is_image() ) {
+ $dimensions = $media->get_dimensions();
+ $image = [
+ 'src' => $media->get_fullsize_url(),
+ 'width' => $dimensions['width'],
+ 'height' => $dimensions['height'],
+ ];
+ }
+ }
+ }
+
+ return [
+ 'imageSrc' => $image['src'],
+ 'imageWidth' => $image['width'],
+ 'imageHeight' => $image['height'],
+ 'widthLimit' => 360, // See _imagify_add_actions_to_media_list_row().
+ 'labels' => [
+ 'filesize' => __( 'File Size:', 'imagify' ),
+ 'saving' => __( 'Original Saving:', 'imagify' ),
+ 'close' => __( 'Close', 'imagify' ),
+ 'originalL' => __( 'Original File', 'imagify' ),
+ 'optimizedL' => __( 'Optimized File', 'imagify' ),
+ 'compare' => __( 'Compare Original VS Optimized', 'imagify' ),
+ 'optimize' => __( 'Optimize', 'imagify' ),
+ ],
+ ];
+
+ case 'beat':
+ return Core::get_instance()->get_settings();
+
+ case 'media-modal':
+ return [
+ 'imagifybeatID' => $imagifybeat_actions->get_imagifybeat_id( 'library_optimization_status' ),
+ ];
+
+ case 'library':
+ return [
+ 'backupOption' => get_imagify_option( 'backup' ),
+ 'labels' => [
+ 'bulkActionsOptimize' => __( 'Optimize', 'imagify' ),
+ 'bulkActionsOptimizeMissingSizes' => __( 'Optimize Missing Sizes', 'imagify' ),
+ 'bulkActionsRestore' => __( 'Restore Original', 'imagify' ),
+ ],
+ ];
+
+ case 'bulk':
+ $translations = [
+ 'curlMissing' => ! Imagify_Requirements::supports_curl(),
+ 'editorMissing' => ! Imagify_Requirements::supports_image_editor(),
+ 'extHttpBlocked' => Imagify_Requirements::is_imagify_blocked(),
+ 'apiDown' => Imagify_Requirements::is_imagify_blocked() || ! Imagify_Requirements::is_api_up(),
+ 'keyIsValid' => ! Imagify_Requirements::is_imagify_blocked() && Imagify_Requirements::is_api_up() && Imagify_Requirements::is_api_key_valid(),
+ 'isOverQuota' => ! Imagify_Requirements::is_imagify_blocked() && Imagify_Requirements::is_api_up() && Imagify_Requirements::is_api_key_valid() && Imagify_Requirements::is_over_quota(),
+ 'imagifybeatIDs' => [
+ 'stats' => $imagifybeat_actions->get_imagifybeat_id( 'bulk_optimization_stats' ),
+ 'queue' => $imagifybeat_actions->get_imagifybeat_id( 'bulk_optimization_status' ),
+ 'requirements' => $imagifybeat_actions->get_imagifybeat_id( 'requirements' ),
+ ],
+ 'waitImageUrl' => IMAGIFY_ASSETS_IMG_URL . 'popin-loader.svg',
+ 'ajaxActions' => [
+ 'bulkProcess' => 'imagify_bulk_optimize',
+ 'getFolderData' => 'imagify_get_folder_type_data',
+ 'bulkInfoSeen' => 'imagify_bulk_info_seen',
+ ],
+ 'ajaxNonce' => wp_create_nonce( 'imagify-bulk-optimize' ),
+ 'bufferSizes' => [
+ 'wp' => 4,
+ 'custom-folders' => 4,
+ ],
+ 'optimizing' => get_transient( 'imagify_custom-folders_optimize_running' ) || get_transient( 'imagify_wp_optimize_running' ),
+ 'labels' => [
+ 'overviewChartLabels' => [
+ 'unoptimized' => __( 'Unoptimized', 'imagify' ),
+ 'optimized' => __( 'Optimized', 'imagify' ),
+ 'error' => __( 'Error', 'imagify' ),
+ ],
+ 'curlMissing' => __( 'cURL is not available on the server.', 'imagify' ),
+ 'editorMissing' => sprintf(
+ /* translators: %s is a "More info?" link. */
+ __( 'No php extensions are available to edit images on the server. ImageMagick or GD is required. %s', 'imagify' ),
+ '' . __( 'More info?', 'imagify' ) . ' '
+ ),
+ 'extHttpBlocked' => __( 'External HTTP requests are blocked.', 'imagify' ),
+ 'apiDown' => __( 'Sorry, our servers are temporarily unavailable. Please, try again in a couple of minutes.', 'imagify' ),
+ 'invalidAPIKeyTitle' => __( 'Your API key is not valid!', 'imagify' ),
+ 'overQuotaTitle' => __( 'You have used all your credits!', 'imagify' ),
+ 'waitTitle' => __( 'Please wait...', 'imagify' ),
+ 'waitText' => __( 'We are trying to get your unoptimized media files, it may take time depending on the number of files.', 'imagify' ),
+ 'nothingToDoTitle' => __( 'Hold on!', 'imagify' ),
+ 'nothingToDoText' => [
+ 'optimize' => __( 'All your media files have been optimized by Imagify. Congratulations!', 'imagify' ),
+ 'generate_webp' => __( 'All your optimized images already have a next-gen version. Congratulations!', 'imagify' ),
+ ],
+ 'optimizing' => __( 'Optimizing', 'imagify' ),
+ 'error' => __( 'Error', 'imagify' ),
+ 'ajaxErrorText' => __( 'The operation failed.', 'imagify' ),
+ 'complete' => _x( 'Complete', 'adjective', 'imagify' ),
+ 'alreadyOptimized' => _x( 'Already Optimized', 'file', 'imagify' ),
+ /* translators: %s is a number. Don't use %d. */
+ 'nbrFiles' => __( '%s file(s)', 'imagify' ),
+ 'notice' => _x( 'Notice', 'noun', 'imagify' ),
+ /* translators: %s is a number. Don't use %d. */
+ 'nbrErrors' => __( '%s error(s)', 'imagify' ),
+ 'getUnoptimizedImagesErrorTitle' => __( 'Oops, There is something wrong!', 'imagify' ),
+ 'getUnoptimizedImagesErrorText' => __( 'An unknown error occurred when we tried to get all your unoptimized media files. Try again and if the issue still persists, please contact us!', 'imagify' ),
+ 'waitingOtimizationsText' => __( 'Waiting other optimizations to finish.', 'imagify' ),
+ /* translators: %s is a formatted number, dont use %d. */
+ 'imagesOptimizedText' => __( '%s Media File(s) Optimized', 'imagify' ),
+ /* translators: %s is a formatted number, dont use %d. */
+ 'imagesErrorText' => __( '%s Error(s)', 'imagify' ),
+ 'bulkInfoTitle' => __( 'Information', 'imagify' ),
+ 'confirmBulk' => __( 'Start the optimization', 'imagify' ),
+ ],
+ ];
+
+ if ( get_transient( 'imagify_large_library' ) ) {
+ // On huge media libraries, don't use Imagifybeat, and fetch stats only when the process ends.
+ $translations['ajaxActions']['getStats'] = 'imagify_bulk_get_stats';
+ }
+
+ if ( isset( $translations['bufferSizes']['wp'] ) ) {
+ /**
+ * Filter the number of parallel queries during the Bulk Optimization (library).
+ *
+ * @since 1.5.4
+ * @since 1.7 Deprecated
+ * @deprecated
+ *
+ * @param int $buffer_size Number of parallel queries.
+ */
+ $translations['bufferSizes']['wp'] = apply_filters_deprecated( 'imagify_bulk_buffer_size', [ $translations['bufferSizes']['wp'] ], '1.7', 'imagify_bulk_buffer_sizes' );
+ }
+
+ /**
+ * Filter the number of parallel queries during the Bulk Optimization.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ *
+ * @param array $buffer_sizes An array of number of parallel queries, keyed by context.
+ */
+ $translations['bufferSizes'] = apply_filters( 'imagify_bulk_buffer_sizes', $translations['bufferSizes'] );
+
+ return $translations;
+
+ case 'files-list':
+ return [
+ 'backupOption' => get_imagify_option( 'backup' ),
+ 'context' => 'custom-folders',
+ 'imagifybeatID' => $imagifybeat_actions->get_imagifybeat_id( 'custom_folders_optimization_status' ),
+ 'labels' => [
+ 'bulkActionsOptimize' => __( 'Optimize', 'imagify' ),
+ 'bulkActionsRestore' => __( 'Restore Original', 'imagify' ),
+ ],
+ ];
+
+ default:
+ return [];
+ } // End switch().
+}
diff --git a/wp/wp-content/plugins/imagify/inc/functions/media.php b/wp/wp-content/plugins/imagify/inc/functions/media.php
new file mode 100644
index 00000000..e532ac8b
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/functions/media.php
@@ -0,0 +1,22 @@
+get( $key );
+}
+
+/**
+ * Update an Imagify option.
+ *
+ * @since 1.6
+ * @author Remy Perona
+ *
+ * @param string $key The option name.
+ * @param mixed $value The value of the option.
+ */
+function update_imagify_option( $key, $value ) {
+ Imagify_Options::get_instance()->set( $key, $value );
+}
+
+/**
+ * Autoload network options and put them in cache.
+ *
+ * @since 1.7
+ * @author Grégory Viguier
+ * @source SecuPress
+ *
+ * @param array $option_names A list of option names to cache.
+ * @param string|array $prefixes A prefix for the option names. Handy for transients for example (`_site_transient_` and `_site_transient_timeout_`).
+ */
+function imagify_load_network_options( $option_names, $prefixes = '' ) {
+ global $wpdb;
+
+ $prefixes = (array) $prefixes;
+
+ if ( ! $option_names || count( $option_names ) * count( $prefixes ) === 1 ) {
+ return;
+ }
+
+ // Get values.
+ $not_exist = array();
+ $option_names = array_flip( array_flip( $option_names ) );
+ $options = '';
+
+ foreach ( $prefixes as $prefix ) {
+ $options .= "'$prefix" . implode( "','$prefix", esc_sql( $option_names ) ) . "',";
+ }
+
+ $options = rtrim( $options, ',' );
+
+ if ( is_multisite() ) {
+ $network_id = function_exists( 'get_current_network_id' ) ? get_current_network_id() : (int) $wpdb->siteid;
+ $cache_prefix = "$network_id:";
+ $notoptions_key = "$network_id:notoptions";
+ $cache_group = 'site-options';
+ $results = $wpdb->get_results( $wpdb->prepare( "SELECT meta_key as name, meta_value as value FROM $wpdb->sitemeta WHERE meta_key IN ( $options ) AND site_id = %d", $network_id ), OBJECT_K ); // WPCS: unprepared SQL ok.
+ } else {
+ $cache_prefix = '';
+ $notoptions_key = 'notoptions';
+ $cache_group = 'options';
+ $results = $wpdb->get_results( "SELECT option_name as name, option_value as value FROM $wpdb->options WHERE option_name IN ( $options )", OBJECT_K ); // WPCS: unprepared SQL ok.
+ }
+
+ foreach ( $prefixes as $prefix ) {
+ foreach ( $option_names as $option_name ) {
+ $option_name = $prefix . $option_name;
+
+ if ( isset( $results[ $option_name ] ) ) {
+ // Cache the value.
+ $value = $results[ $option_name ]->value;
+ $value = maybe_unserialize( $value );
+ wp_cache_set( "$cache_prefix$option_name", $value, $cache_group );
+ } else {
+ // No value.
+ $not_exist[ $option_name ] = true;
+ }
+ }
+ }
+
+ if ( ! $not_exist ) {
+ return;
+ }
+
+ // Cache the options that don't exist in the DB.
+ $notoptions = wp_cache_get( $notoptions_key, $cache_group );
+ $notoptions = is_array( $notoptions ) ? $notoptions : array();
+ $notoptions = array_merge( $notoptions, $not_exist );
+
+ wp_cache_set( $notoptions_key, $notoptions, $cache_group );
+}
diff --git a/wp/wp-content/plugins/imagify/inc/functions/partners.php b/wp/wp-content/plugins/imagify/inc/functions/partners.php
new file mode 100644
index 00000000..449c3c21
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/functions/partners.php
@@ -0,0 +1,38 @@
+ 0.01,
+ 'blocking' => false,
+ 'body' => $body,
+ 'cookies' => isset( $_COOKIE ) && is_array( $_COOKIE ) ? $_COOKIE : [],
+ 'sslverify' => apply_filters( 'https_local_ssl_verify', false ),
+ ];
+
+ /**
+ * Filter the arguments used to launch an async job.
+ *
+ * @since 1.6.6
+ * @author Grégory Viguier
+ *
+ * @param array $args An array of arguments passed to wp_remote_post().
+ */
+ $args = apply_filters( 'imagify_do_async_job_args', $args );
+
+ /**
+ * It can be a XML-RPC request. The problem is that XML-RPC doesn't use cookies.
+ */
+ if ( defined( 'XMLRPC_REQUEST' ) && get_current_user_id() ) {
+ /**
+ * In old WP versions, the field "option_name" in the wp_options table was limited to 64 characters.
+ * From 64, remove 19 characters for "_transient_timeout_" = 45.
+ * Then remove 12 characters for "imagify_rpc_" (transient name) = 33.
+ * Luckily, a md5 is 32 characters long.
+ */
+ $rpc_id = md5( maybe_serialize( $body ) );
+
+ // Send the request to our RPC bridge instead.
+ $args['body']['imagify_rpc_action'] = $args['body']['action'];
+ $args['body']['action'] = 'imagify_rpc';
+ $args['body']['imagify_rpc_id'] = $rpc_id;
+ $args['body']['imagify_rpc_nonce'] = wp_create_nonce( 'imagify_rpc_' . $rpc_id );
+
+ // Since we can't send cookies to keep the user logged in, store the user ID in a transient.
+ set_transient( 'imagify_rpc_' . $rpc_id, get_current_user_id(), 30 );
+ }
+
+ $url = admin_url( 'admin-ajax.php' );
+
+ /**
+ * Filter the URL to use for async jobs.
+ *
+ * @since 1.9.5
+ * @author Grégory Viguier
+ *
+ * @param string $url An URL.
+ * @param array $args An array of arguments passed to wp_remote_post().
+ */
+ $url = apply_filters( 'imagify_async_job_url', $url, $args );
+
+ wp_remote_post( $url, $args );
+}
diff --git a/wp/wp-content/plugins/imagify/inc/main.php b/wp/wp-content/plugins/imagify/inc/main.php
new file mode 100644
index 00000000..eaad6169
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/inc/main.php
@@ -0,0 +1,35 @@
+ IMAGIFY_PATH,
+ )
+ );
+
+ $plugin->init( $providers );
+}
+add_action( 'plugins_loaded', 'imagify_init' );
diff --git a/wp/wp-content/plugins/imagify/readme.txt b/wp/wp-content/plugins/imagify/readme.txt
new file mode 100644
index 00000000..9bebd46a
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/readme.txt
@@ -0,0 +1,816 @@
+=== Imagify – Optimize Images & Convert WebP & AVIF | Compress Images Easily ===
+Contributors: wp_rocket, imagify
+Tags: optimize images, convert webp, webp converter, convert AVIF, webp to AVIF, AVIF plugin, AVIF converter, image optimization, compress images, image compressor, resize images, reduce image size, performance, image optimizer, core web vitals, best image optimization plugin
+Tested up to: 6.5
+Stable tag: 2.2.2
+Requires PHP: 7.3
+License: GPLv2 or later
+License URI: http://www.gnu.org/licenses/gpl-2.0.html
+
+Compress images & convert WebP and AVIF with the best WordPress image optimization plugin. Optimize images in 1-click & resize images with our image optimizer!
+
+== Description ==
+
+= The Best Image Optimization Plugin For WordPress =
+
+[Imagify](https://imagify.io/) is the most advanced image optimization plugin to help you resize and compress images. You can now use its power directly in WordPress to optimise images and reduce the weight of the photos you want to add to your site – all in just one click and without sacrificing their quality.
+
+Imagify is the best WordPress image optimizer. The plugin lets you optimize images in one go with its asynchronous bulk optimization option. You can resize your images on the fly – they will be automatically optimized at the best compression level. If needed, you can always restore your images to their original versions.
+
+On top of optimizing images, you’ll choose the best WebP plugin and AVIF plugin for WordPress. Imagify also converts your images to WebP and AVIF, the next-gen formats for lighter images that will speed up your WordPress site, improve user experience, and even SEO. Convert WebP and convert AVIF will make a difference in image optimization, you’ll see that from yourself.
+
+Lastly, it’s easy to use the best image compression plugin for better site performance. Speed up your WordPress site and improve Core Web Vitals thanks to Imagify’s state-of-the-art image optimization process.
+
+Our video explains why Imagify is the easiest image optimization plugin and shows how it makes your website faster thanks to lighter images.
+
+[youtube https://www.youtube.com/watch?v=ZgMwWvUZFu4&feature=youtu.be]
+
+
+= Resize and Compress Images Without Losing Quality =
+
+Imagify is a great image compressor and the ultimate solution to optimise images. You are able to resize and compress images from the most common image formats as well as PDF format. In case you have many images to optimize, you can also resize images in bulk thanks to our async bulk optimization option. In just one click, you will be able to compress multiple images super easily. Imagify compresses all your images in the background, so you can leave the page and not worry about anything.
+
+Many of your high-quality images may be in sizes that are much too large. To reduce image size and compress large images, Imagify has a setting that allows you to choose a maximum width for all of your images, and if you upload images that are larger than that size, it will resize large images for you during optimization. Imagify will resize images proportionally without cropping them.
+
+With such a great image optimizer like Imagify, you’ll get your images automatically optimized at the best compression level and quality – thanks to the Smart Compression Mode.
+
+When using our image compression tool, Imagify, you will enjoy smaller file sizes and faster loading times. But the best part is that you will optimise images and reduce their weight without losing quality: why should you have to choose between beauty and speed? If you want to compress images, it’s now easier than ever with Imagify!
+
+= Convert Images to the WebP and AVIF Formats =
+
+Thanks to Imagify, you can take a step further in your image optimization process. You can also convert all your images to next-gen image formats such as WebP and AVIF. WebP format, as well as the AVIF format, offers superior image compression and quality and is a way to optimise images and speed up their loading times on websites. To convert images to next-gen format, using the Imagify plugin will save you a precious amount of time.
+
+With Imagify, WebP compression and conversion are indeed super easy. Wondering how the convert WebP option works? Imagify will automatically enable WebP and convert your images to WebP. You can also easily convert WebP images to AVIF.
+
+If the "Create Next-gen formats versions" option is enabled, the AVIF version of optimized images will be created automatically. Simple as that! Thanks to the best WebP and AVIF plugin for WordPress, you’ll be able to take advantage of the automatic convert WebP feature in no time, plus you’ll always have the convert AVIF option.
+
+Imagify can also display the AVIF images directly on your front-end. But because some browser versions don’t support AVIF yet, Imagify lets you have both optimized versions of the original format images and the WebP versions ready. Imagify will serve the AVIF version if a visitor's browser supports it and the WebP format if not (if you have previously converted the images to WebP).
+
+WebP is definitively an excellent replacement for jpeg, png, and gif images, and the same goes for AVIF, which improves your image performance even further. Imagify offers WebP conversion for all image formats: you can convert gif to webP, jpeg to WebP, and even png to WebP. You can also benefit from AVIF conversion and convert gif to AVIF, jpg and jpeg to AVIF, ng to AVIF, and even WebP to AVIF!
+Whatever your favorite image format, let Imagify optimise your images!
+
+= Optimise Images to Make Your Site Faster and Improve Core Web Vitals =
+
+Did you know that image optimization and web performance go hand in hand? In fact, when it comes to web page speed, one of the first things you should do is optimize your images. Large and heavy image sizes will indeed slow down your website and provide a bad user experience to your visitors – and that’s why you should compress images. On the contrary, when you optimise images and improve image loading speed, you should see a direct improvement in your website speed and performance. With Imagify, it’s time to say goodbye to images taking too long to load.
+
+Images are one of the largest influencing factors in the Core Web Vitals. Image compression will ensure your images load faster and improve your overall website performance, including your Core Web Vitals metrics. If you’re looking to improve user experience and speed up your WordPress site, images are a good place to start.
+
+Even Google tells you to take care of your images! If you have ever run a performance audit on PageSpeed Insights, you might have seen the [“serve images in next-gen formats”](https://imagify.io/blog/serve-next-gen-formats-wordpress/) opportunity popping up. Another PageSpeed Insights recommendation related to images is to [“efficiently encode images”](https://imagify.io/blog/efficiently-encode-images-wordpress/). When you use Imagify, you will be able to address both recommendations and fix your images for a faster website.
+
+= What Do Our Users Think Of Imagify? =
+
+Here’s what our users have to say about us after optimizing their images with Imagify:
+
+>"Images and other media are the largest parts on your web pages (most likely). Therefore don't forget to optimise images for the web before adding to your site. For WordPress there are many optimisation plugins available. My favourite is Imagify" — [Mark Wilkinson](https://twitter.com/wpmark/status/1479128422395830273)
+>
+
+>”To give your images a slimming treatment, without altering them aesthetically, there is a great plugin on WordPress: Imagify. Simple, efficient and functional, it’s really worth a look.”— [WP Marmite](https://twitter.com/wpmarmite_en/status/1383072818649255937)
+>
+
+> "Imagify is an awesome tool that is powerful & easy to use. It's fast, rivals and surpasses other established plugins/software. Awesome!" — [Simon Harper](https://twitter.com/SRHDesign/status/663758140505235456)
+>
+
+> "If you want to "squeeze" your images as much as possible and "trim out" your website on the highest professional level... Imagify" — [Ivica Delic](https://twitter.com/Free_LanceTools/status/685503950909476865)
+>
+
+> "Clearly Imagify is the most awesome WordPress plugin to compress images on your website! A must try" — [Eric Walter](https://twitter.com/EricWaltR/status/679053496382038016)
+>
+
+= Is Imagify Free? =
+
+You can optimize for free 20MB of images (that’s about 200 images) every month. You can also convert to the next-gen WebP format for free.
+
+Need to compress more images? Have a look at our plans: [https://imagify.io/pricing](https://imagify.io/pricing)
+
+= Want Image Optimization Tips? =
+
+If you want to know more about using WebP images on WordPress, improving your PageSpeed score with Imagify, or compressing multiple images online, take a look at our blog: [https://imagify.io/blog/](https://imagify.io/blog/)
+
+It’s packed with advice on image compression and so much more!
+
+*[How to Convert Images to WebP on WordPress with Imagify](https://imagify.io/blog/how-to-convert-images-to-webp/)
+
+*[How to Optimize Images on WordPress for Performance and SEO](https://imagify.io/blog/image-optimization-manual-for-wordpress/)
+
+*[How to Reduce Image Size Without Losing Quality (and Save Space)](https://imagify.io/blog/reduce-image-size-without-losing-quality/)
+
+*[How to Resize and Compress Multiple Images Online (Easy Methods)](https://imagify.io/blog/how-to-resize-compress-multiple-images-online/)
+
+*[How to Make Photos Load Faster on WordPress: 6 Key Tactics](https://imagify.io/blog/how-to-make-photos-load-faster-wordpress/)
+
+*[How to Optimize Images for Page Speed (and Google)](https://imagify.io/blog/optimize-images-page-speed-google/)
+
+= Who Are We? =
+
+We are [WP Media](https://wp-media.me/), the company behind WP Rocket, the best caching plugin for WordPress.
+
+Our mission is to improve the web, we are making it faster with [WP Rocket](https://wp-rocket.me/) and lighter with Imagify.
+
+= Get In Touch! =
+
+* Website: [Imagify.io](https://imagify.io)
+* Contact Us: [https://imagify.io/contact](https://imagify.io/contact)
+* Twitter: [https://twitter.com/imagify](https://twitter.com/imagify)
+
+= Related Plugins =
+* [WP Rocket](https://wp-rocket.me/): Best caching plugin to speed-up your WordPress website.
+* [Lazy Load](https://wordpress.org/plugins/rocket-lazy-load/): Best Lazy Load script to reduce the number of HTTP requests and improve the website's loading time.
+
+License: GPLv2 or later
+License URI: http://www.gnu.org/licenses/gpl-2.0.html
+
+== Installation ==
+
+= WordPress Admin Method =
+1. Go to you administration area in WordPress `Plugins > Add`
+2. Look for `Imagify` (use search form)
+3. Click on Install and activate the plugin
+4. Optional: find the settings page through `Settings > Imagify`
+
+= FTP Method =
+1. Upload the complete `imagify` folder to the `/wp-content/plugins/` directory
+2. Activate the plugin through the 'Plugins' menu in WordPress
+3. Optional: find the settings page through `Settings > Imagify`
+
+== Frequently Asked Questions ==
+
+= How can I measure the impact of Imagify on speed score? =
+
+You can use GTMetrix and Google PageSpeed Insights to check the relevant suggestions. It is recommended to test the following metrics before and after the image optimization:
+
+* Total Page Size (GTMetrix)
+* Optimize images (GTMetrix)
+* Serve images in next-gen formats (PageSpeed Insights)
+* Efficiently encode images (PageSpeed Insights)
+
+= What makes Imagify better than other image optimizer tools? =
+
+Imagify is an extremely powerful image optimizer: our advanced compressing algorithm will compress images, reduce their weight without sacrificing their quality.
+
+Imagify is also super easy to use. Thanks to its intuitive design, you can easily get familiar with the interface and services without thinking about it.
+
+And our dedicated customer support will help you fix any issue with your image optimizing process. Support is available via contact form, either on our website, or directly on your Imagify plugin settings page.
+
+= How many websites can I optimize with Imagify? =
+
+You can use Imagify on as many websites as you wish. Your image optimization quota to compress images will be shared evenly across all of the websites.
+
+If you need more control over how your Imagify subscription is used, you should create sub-accounts to allocate a quota for each.
+
+= How does the WebP feature work on non-supported browsers? =
+
+Imagify will deliver images in the original format for browsers that don’t support the next-gen WebP format automatically, so there is nothing further to be done.
+
+= Is Imagify compatible with NextGEN? =
+
+Yes, Imagify is fully compatible with NextGEN Gallery, the most popular photo gallery plugin for WordPress. All Imagify optimization features related to NextGEN Gallery images are located and usable within the NextGEN Gallery menus and pages. So when you add images to your NextGEN galleries, you’ll be able to optimize them as well.
+
+= Which formats can be optimized? =
+
+Imagify can optimize JPG, PNG, WebP, PDF files and GIFs (whether animated or not).
+
+When you optimize JPG, PNG, and GIF files, Imagify will also create WebP versions of your original images and all your thumbnail sizes (if you have this option enabled).
+
+= How should I know which image compression level is best for me? =
+
+Don’t worry! Imagify comes with the Smart Compression Mode. It means that your images will be automatically optimized for the best possible compression ratio and quality. There’s nothing else to do – just enjoy your lighter and faster images.
+
+=How does the optimization process work?=
+
+The image optimization process is performed on our servers. Once done, Imagify returns the optimized image to your server. We do not edit images’ titles or any other information, so there is nothing further to be done on your end than to compress images. Your original images will be moved to a dedicated backup folder (just make sure to keep the Backup option active in Imagify settings).
+
+=How long are images stored by Imagify?=
+
+Once your images have been optimized via the WP plugin, the compressed images stay on your end forever (even if you delete the Imagify account).
+
+During the optimization process, compressed images sent via the API or WordPress plugin are stored for one hour on our server (they are already sent back to your site and stay there safely).
+
+Using the online application, compressed images are stored for 24 hours (with a free account) and for unlimited time if you have a paid subscription.
+
+=Can I restore images after compression?=
+
+Yes, as long as the Backup option is active in Imagify settings (it is active by default when you activate the WP Plugin).
+
+=If I remove Imagify, will my images stay compressed?=
+
+Yes, your images will stay compressed even after removing Imagify (and even after you delete your Imagify account).
+
+=If I use Imagify, do I need to continue optimizing and resizing my images with Photoshop?=
+
+Do not waste your time resizing and optimizing your images in Photoshop. Imagify takes care of everything to compress your images!
+
+=Is the EXIF data of images removed?=
+
+EXIF data is not removed.
+
+=I used Kraken, Optimus, EWWW or WP Smush, will Imagify further optimize my images?=
+
+Absolutely. Most of the time, Imagify will still be able to optimize your images even if you have already compressed them with another tool.
+
+= Will the original images be deleted? =
+
+No. Imagify automatically replaces the original images with an optimized image. The backup option allows you to keep the original images and restore them with one click.
+
+= Is it possible to re-optimize images with a different level? =
+
+Yes. By activating the backup option in the plugin, you can re-optimize each image to lossless compression with a single click.
+
+= What happens when the plugin is disabled? =
+
+When the plugin is disabled, your existing images remain optimized. Backups of the original images are still available if you have enabled the images backup option.
+
+= On which web hosts can the plugin be used? =
+
+The plugin can be used on all hosts including "managed hosting" providers like WP Engine.
+
+= Is Imagify compatible with Multi-Site? =
+
+Yes, Imagify is 100% compatible with multi-site.
+
+= Can we use Imagify on WordPress.com? =
+
+It is possible to use the Imagify plugin on WordPress.com if you have a Business account.
+
+=Do you offer support?=
+
+Yes, the Imagify team offers full email support for image optimization questions. You can contact us via [https://imagify.io/contact/](https://imagify.io/contact/).
+
+= When is support available? =
+
+Our support is currently available Monday-Friday 8AM-10PM CET. We answer every email so you can expect the answer from us within 24h max (unless during the weekends).
+
+=Is registration free?=
+
+Yes, and no credit card is required.
+
+= Do you offer a trial version? =
+
+No. However, you get 20MB of quota per month for free to optimize your images (around 200 images).
+
+= Where do I report security bugs found in this plugin? =
+
+You can report any security bugs found in the source code of the site-reviews plugin through the [Patchstack Vulnerability Disclosure Program](https://patchstack.com/database/vdp/imagify). The Patchstack team will assist you with verification, CVE assignment and take care of notifying the developers of this plugin.
+
+== Screenshots ==
+
+1. Bulk Optimization
+
+2. Settings Page
+
+3. Media Page
+
+4. Other Media Page
+
+== Changelog ==
+= 2.2.2 =
+- Enhancement: Allow to choose which Next-Gen images should be generated in UI
+- Enhancement: Guard against image size that’s not a string
+- Enhancement: Guard against file type that doesn’t match existing mime type
+- Bugfix: Fix a fatal error related to “WP_List_Table”
+
+= 2.2.1 =
+- Enhancement: Prevent updating .htaccess when switching between AVIF and WEBP generation features
+- Enhancement: Display the smallest size of the image in the Media Library image details section
+- Enhancement: Correctly delete all Next-Gen versions when restoring the Original Image
+- Enhancement: Bump minimum version to PHP7.3
+- Bugfix: Fix the problem with progress bar when disabling AVIF generation
+- Bugfix: Fix a bug when number of images in the Bulk Optimization section was not correct
+- Bugfix: Fix the original/optimized image comparision bug
+- 3rd-party compatibility: Update compatibility with Next-Gen Gallery to match AVIF images
+- 3rd-party compatibility: Update compatibility with AMP, Regenerate Thumbnails and WooCommerce to work correctly with AVIF images
+
+= 2.2.0.1 =
+- Bugfix: Preserve "Display images in webp format" configuration when updating.
+
+= 2.2 =
+- New Feature: Introduce AVIF generation feature
+
+= 2.1.3.1 =
+- Bugfix: missing styling on some banners when using minified versions of the CSS files (#765)
+
+= 2.1.3 =
+- Enhancement: Update chart.js (#742)
+- Enhancement: Improve messaging around WebP images when they are larger than the original (#751)
+- Enhancement: Update notices when out of quota (#727, #728)
+- Bugfix: Prevent PHP deprecated notice on PHP 8.1 (#734)
+- Bugfix: Improve database queries on large media libraries (#747)
+
+= 2.1.2 =
+- Bugfix: Prevent deprecation notice with PHP 8.1 & 8.2 (#721, #723)
+- Bugfix: Escape error message before display (#729)
+- Bugfix: Don't count WebP images in the generate missing WebP images versions (#713)
+- Bugfix: Improve information related to out of quota on bulk optimization (#714)
+- Bugfix: Fix optimization filter type working with file filters on media library (#670)
+
+= 2.1.1 =
+- Enhancement: Allow WebP images to be optimized by Imagify from the plugin (#611)
+- Enhancement: Improve error message displayed when an unknown error occured (#637)
+- Enhancement: Update Action Scheduler to v3.5.4 (#708)
+- Enhancement: Only display plan suggestion for users on free plan (#69)
+- Bugfix: Prevent optimization from getting stuck on websites with big images libraries (#707)
+- Bugfix: Prevent PHP8 ArgumentCountError (#682)
+
+
+= 2.1 =
+- Enhancement: Re-add lossless compression option (#686)
+- Enhancement: New async bulk optimization, allowing to run the bulk optimization without keeping the browser open. Also possible to run the bulk optimization from an API function or a WP CLI command (#674)
+- Bugfix: Correctly resize the WebP generated file to the maximum defined size from the settings (#521)
+- Bugfix: Prevent error related to set_time_limit() function on some environments (#671)
+
+= 2.0 =
+- Enhancement: Add compatibility with our new smart compression system (#663)
+- Enhancement: Optimize initialization of some of the code (#473)
+- Enhancement: Add new filter `imagify_process_webp_content` (#653)
+- Bugfix: Prevent PHP warning when displaying the pricing modal (#666)
+- 3rd party compatibility: Pass missing parameter to the `http_headers_useragent` filter (#612)
+- 3rd party compatibility: Prevent conflict with WP Cloudflare super page cache (#609)
+- Bugfix: Fix various UI issues (#604, #586, #592, #594)
+- i18n: Fix typos & improve strings (#621)
+
+= 1.10 - 2021/07/15 =
+* The plugin minimum compatible versions are now PHP 7.0 and WordPress 5.3
+* Enhancement: Correctly display WordPress cover blocks when WebP and picture tag replacement is enabled (#546)
+* Enhancement: Update our jQuery code to be compatible with the new jQuery version included in WordPress (#545)
+* 3rd party compatibility: Correctly display WooCommerce variable products images when WebP and picture tag replacement is enabled (#495)
+* Bugfix: Prevent nested picture tags when picture tag replacement is enabled (#537)
+* Bugfix: Prevent a fatal error related to get_current_screen() in some cases (#567)
+* Bugfix: Fixes some display issues related to the promotions in the checkout process (#556, #557)
+* Bugfix: Fixes some display issues on the settings & bulk optimization pages on mobile (#566)
+* Bugfix: Prevent PHP warning in some cases on the bulk optimization process (#565)
+* Bugfix: Prevent PHP notice in somes cases for the $images_count variable (#573)
+
+= 1.9.14 =
+* Fix: cURL not connecting to Imagify API when using PHP 8.
+* Fix: Display issue in Chrome on scrollable check groups on Imagify admin page.
+
+= 1.9.13 =
+* Improvement: Update readme with new quotas, FAQ and description info.
+
+= 1.9.12 - 2020/11/09 =
+* Improvement: Enable plugin to work with new app pricing API.
+
+= 1.9.11 - 2020/09/09 =
+* Fix: Fix settings error on multi-sites with WordPress 5.5
+* Fix: Write the correct conf file for use with WebP rewrites on nginx
+* Improvement: Namespace composer dependencies to avoid possible naming collisions.
+* Security: Add blank index.php to imagify-created backup folders to disable public access.
+
+= 1.9.10 - 2020/05/26 =
+* Fix: Correctly optimize thumbnails during auto-optimization of image upload
+* Fix: Fix broken compatibility with Enable Media Replace plugin after WordPress 5.3
+
+= 1.9.9 - 2020/02/13 =
+* Fix: do not warn that all the quota has been consumed when it is not the case.
+* Fix: fix a "chunky upload" error that some users experienced.
+* Fix: php notices that could happen when optimizing.
+
+= 1.9.8.1 - 2019/11/15 =
+* Fix: WebP image not showing when using the `` method and the original ` ` does not have a `srcset` attribute.
+* Fix: a fatal error with WP Offload Media 2.3.
+
+= 1.9.8 - 2019/11/11 =
+* Improvement: compatibility with WordPress 5.3!
+* New: among other things, WordPress 5.3 automatically resizes large images on upload, using a predefined threshold value that can be changed only by filter (no setting fields are provided). Imagify’s "Resize larger images" setting field is now used to tweak this threshold.
+* Caution: to be able to work on WordPress 5.3, some adjustments have been made to our compatibility with Enable Media Replace and Regenerate Thumbnails. However, these plugins must be updated to work with WordPress 5.3: do not use them until then.
+* Improvement: moved the `width` and `height` attributes from the `` tag to the ` ` tag to be valid HTML markup.
+* Fix: added a missing descriptor in `srcset` attribute when using `` tags to display WebP images. This should also fix an issue with LasyLoad.
+* Fix: fixed an issue with the user capacity used for "Other Media" menu item.
+* Fix: a php notice `stripos(): Non-string needles will be interpreted as strings in the future.`.
+
+= 1.9.7 - 2019/10/08 =
+* Improvement: prevent greedy antiviruses from crashing the website by renaming our highly dangerous php file with a ".suspected" suffix.
+* Improvement: on the settings page, display the "Save & Go to Bulk Optimizer" button only if the user has the ability to bulk optimize.
+* Fix: display the "Welcome" banner correctly when it is shown on the WP Rocket’s settings page.
+
+= 1.9.6 - 2019/07/22 =
+* Improvement: now images that are "already optimized" can also get WebP versions.
+* Fix: progress bar height in the admin bar for Chrome and Safari.
+
+= 1.9.5 - 2019/07/16 =
+* Improvement: Basic Authentication support. If it does not work automatically, you can still define the constants `IMAGIFY_AUTH_USER` and `IMAGIFY_AUTH_PASSWORD` in your `wp-config.php` file.
+* Improvement: WebP images are not created for animated gif images by default anymore. Use the filter `imagify_pre_can_create_next_gen_version` if you still want to create an unanimated WebP version of them.
+* Improvement: when creating WebP images from the settings page, we made more clear when all the images are missing a backup copy.
+* Improvement: clear the 5 minutes data cache when buying quota from the plugin.
+* Improvement: when displaying WebP images with the `` tag, allow to use relative URLs (starting with `/`).
+
+= 1.9.4 - 2019/07/10 =
+* Improvement: if a next-gen image is larger than its non-next-gen version, it is now possible to not keep it. This can be done by using the filter `imagify_keep_large_next_gen`.
+* Improvement: compatibility with Pressable.
+* Improvement: renamed a php class to prevent some hosts to wrongly flag it as "suspicious" and trigger a fatal error.
+* Improvement: better compatibility with WP Real Media Library plugin.
+* Fix: rewrite rules for WebP could not work on some servers.
+* Fix: when using `` tags for WebP, some attributes could disappear if they were written on multiple lines.
+* Fix: the bulk method would not work in the NextGen Gallery list.
+* Fix: php notice `Trying to get property "namespace" for a non object`.
+
+= 1.9.3.1 - 2019/07/03 =
+* Fix: conflict with plugins using an ancient version of Composer.
+
+= 1.9.3 - 2019/06/17 =
+* Improvement: better compatibility with CDNs when displaying WebP images with `` tags. There is now a new setting field to fill in the CDN URL in use.
+* Improvement: don’t use Heartbeat anymore. This speeds up the optimization process and prevents other plugins to break everything when they remove Heartbeat.
+* Fix: a fatal error upon plugin deactivation.
+* Fix: an occasional fatal error preventing the optimization process to work.
+* Fix: conflict with plugins using an ancient version of Composer.
+* Fix: php notices displayed on the bulk optimization page on rare cases.
+* Fix: a php notice about "Non-string needles" with php 7.3.
+* Fix: a php notice displayed when restoring a custom file.
+
+= 1.9.2 - 2019/05/16 =
+* Fix: don’t display support bubble anymore.
+
+= 1.9.1 - 2019/05/09 =
+* Improvement: prevent "Generating missing WebP versions" being stuck at 0% in the settings page by displaying a "done/total" label instead.
+* Improvement: improved our "re-registering" of the Heartbeat library, that some plugins may deactivate.
+
+= 1.9.0 - 2019/05/06 =
+* New: WebP support. For each image or thumbnail, Imagify can create a WebP version of it. But since creating these images without using them does not make really sense, Imagify can also display your WebP images on your site. All of this can be enabled in the settings. For the images that are already optimized, you get the possibility to create the WebP versions separately (one by one or in the settings page), but only if you kept a backup copy of the original images.
+* Improvement: the optimization process has been entirely rebuilt. This new process allows you to optimize as many thumbnail sizes that you want. It also implies that many classes, functions, and hooks have been deprecated.
+* Improvement: compatibility with Flywheel.
+* Improvement: some error messages are now more accurate.
+* Fix: made sure to stop the optimization process if the backup process fails. Since the optimization process has been rebuilt, some other bugs have been fixed along the way.
+* Fix: an issue preventing directory creation.
+* Fix: a fatal error when uploading an image in NextGen Gallery, due to a recent change in NGG.
+* Imagify now requires WordPress 4.0+ and php 5.4+.
+* Support for the plugin WP Retina 2x has been dropped (maybe temporarily).
+
+= 1.8.4.1 - 2018/12/18 =
+* Improvement: prevent "unknown error" messages that some users are getting since yesterday.
+
+= 1.8.4 - 2018/11/12 =
+* Improvement: automatic optimization is delayed further, it now happens after the image original data is stored in the database. This new process should be more reliable.
+* Improvement: compatibility with wordpress.com.
+* Improvement: some wording and typos in the plan suggestion tool.
+* Improvement: improved wording and added a link to a new documentation entry for the case when no php extension are available for image manipulation.
+* Improvement: prevent plugins from accidentally overwriting the header containing the API key when contacting our servers.
+* Bug Fix: the handle in the original/optimized image comparator was a bit shy, but after some personal work it should stick to the cursor hopefully.
+* Bug Fix: a php notice in the WP Retina 2x compatibility code.
+* Bug Fix: handle a specific error case when contacting our servers fails.
+
+= 1.8.3 - 2018/10/24 =
+* Improvement: compatibility with new version of WP Offload Media plugin.
+* Improvement: some wording about EXIF Data and the 2MB limit.
+* Bug Fix: the lock icon now displays correctly.
+* Bug Fix: a text encoding issue with some server configurations.
+
+= 1.8.2 - 2018/09/12 =
+* New: display partnership links (can be removed).
+* Improvement: display a small spinner when opening a folder in the custom folders selector.
+* Improvement: visual for the admin toolbar option has been updated and localized for some languages.
+* Bug Fix: two errors that prevented to create the backup folder (and other things).
+* Bug Fix: improved uninstall cleanup.
+
+= 1.8.1.1 - 2018/07/31 =
+* Bug Fix: an open_basedir error that prevented some users to use the custom folders browser.
+* Bug Fix: an error that prevented to create the backup folder (and other things) on multisite.
+
+= 1.8.1 - 2018/07/18 =
+* Imagify now requires WordPress 4.0 at least! This value may increase in the future, like required php version.
+* Bug Fix: improved support of sites having the "wp-content" folder outside WordPress folder.
+* Bug Fix: improved the plan recommendation tool: better choices, and pre-select only what is needed.
+* Bug fix: fixed a wrong color on a quota bar.
+* Lots of various small fixes and code improvements.
+
+= 1.8.0.1 - 2018/06/19 =
+* Bug Fix: issue on some sites displaying a "no php extension available".
+
+= 1.8 - 2018/06/19 =
+* New: you can now optimize pdf files.
+* Improvement: custom folders, you can now optimize files located in the *uploads* folder.
+* Improvement: support for thumbnails dynamically generated by NextGen Gallery plugin.
+* Bug Fix: revamped support for WP Retina 2x plugin.
+
+= 1.7.1.3 - 2018/04/12 =
+* Bug Fix: a fatal error with outdated versions of php.
+
+= 1.7.1.2 - 2018/04/12 =
+* Improvement: reset OPcache after Imagify being updated.
+* Bug Fix: a fatal error upon Imagify update.
+* Bug Fix: a case where the bulk optimizer wrongly says that all images are already optimized.
+
+= 1.7.1 - 2018/04/10 =
+* New: compatibility with Regenerate Thumbnails (v3) plugin.
+* Improvement: better performance of the bulk optimization on sites with huge media library. This is done by not updating the statistics display periodically, but only when the job is done.
+* Improvement: SiteGround cache testing is not blocked anymore.
+* Improvement: proxies are now handled.
+* Improvement: test for ImageMagick or GD availability.
+* Dev stuff: improved the way we use the filesystem. This should solve few edge cases.
+
+= 1.7 - 2018/03/13 =
+* New: you can now optimize the images from your themes and plugins, or from any other folder in your site!
+* Improvement: compatibility with old and new versions of WP Offload S3 plugins.
+* Improvement: don't start the bulk optimization process if cURL is not available.
+* Bug Fix: image dimensions not being stored sometimes after it is resized.
+* Bug Fix: the comparison tool could display multiple handles.
+* Bug Fix: issue with php 7.2.
+* Dev stuff: lots of internal changes, many things have been rewritten.
+* Dev stuff: the default options can now be filtered.
+
+= 1.6.14.2 - 2018/01/15 =
+* Improvement: force browsers not to use the old version of our script for the charts.
+
+= 1.6.14.1 - 2018/01/11 =
+* Bug Fix: no more conflicts between our script used for the charts and theme builders, or plugins that use an outdated version of this script.
+
+= 1.6.14 - 2018/01/10 =
+* New: added compatibility with partners' plugins.
+* Improvement: updated the script used for the charts, it will lower the risk of conflicts with other plugins (that are also up-to-date).
+* Improvement: the comparison tool button is now also inserted when clicking the next/previous buttons in the media modal.
+* Bug Fix: the comparison tool button should not be inserted several times anymore.
+* Bug Fix: the images wouldn't appear in the comparison tool sometimes.
+
+= 1.6.13.1 - 2017/11/08 =
+* Bug Fix: fixed a php error with php 5.2.
+
+= 1.6.13 - 2017/11/07 =
+* New: added links to the documentation in Imagify' settings and bulk optimization pages.
+* Improvement: better compatibility with NextGen Gallery plugin. Imagify no longer resizes NextGen images nor removes exif, to let NextGen Gallery do its job peacefully.
+* Improvement: better compatibility with WP Real Media Library plugin, our modal wasn't working correctly.
+* Improvement: better compatibility with plugins that use cookies, like Duo Two-Factor Authentication and Shield Security, to prevent being disconnected.
+* Improvement: better compatibility with SiteGround. A "security" measure was preventing Imagify to work correctly.
+* Improvement: better compatibility with hosts that limit some SQL queries, it prevented our bulk optimization to work.
+* Improvement: better compatibility with Heartbeat Control plugin, it prevented our bulk optimization to work.
+* Improvement: better compatibility with Formidable Forms Pro plugin, the bulk optimizer was never satisfied.
+* Bug Fix: fixed a few bugs when optimizing in NextGen Gallery.
+
+= 1.6.12 - 2017/10/18 =
+* New: added links to the documentation in the plugin's admin bar item and the plugin's row (plugins page). There is more to come.
+* Improvement: image attachments that don't have some mandatory WordPress metadata are not included in Imagify stats anymore.
+* Fix: the "Optimized size" progress bar in the bulk optimization page now behaves like the "Original size" one does.
+* Dev stuff: auto-optimization can be disabled on an attachment basis with the new filter `imagify_auto_optimize_attachment`. For example it can be used to disable auto-optimization for a specific file extension.
+* Dev stuff: classes are now auto-loaded. Some constants have been removed.
+
+= 1.6.11 - 2017/10/12 =
+* Improvement: Imagify now works with the iOS app, and with XML-RPC in general.
+* Improvement: we harmonized and improved how user roles are handled.
+* Improvement: prevent optimized image to be cached by the browser in the comparison tool.
+* Fix: sometimes the comparison tool's button wouldn't show on the attachment edition page.
+* Fix: the bulk optimization button works again.
+
+= 1.6.10 - 2017/10/05 =
+* New: if new thumbnail sizes appear after activating a new theme or plugin, you can now optimize only these missing sizes instead of restoring and re-optimizing all images.
+* Improvement: CSS and JS files have been split and are loaded only when needed.
+* Improvement: in each NextGen Galleries you now have "Optimize" and "Restore" bulk actions.
+* Improvement: better banner placements with languages with long sentences (looking at you, Germany).
+* Improvement: messages like the "WELL DONE" one can now be translated.
+* Bug Fix: the account infos in the admin bar now works properly on front-end.
+* Bug Fix: some thumbnail sizes with curious name were not listed in the settings page.
+* Bug Fix: improved library size calculation for "What plan do I need?". Some thumbnail sizes were missing, lowering the result.
+* Regression fix: the issue with Imagify's popup on WP Rocket options screen is now also solved when WP Rocket is white-labelled.
+* Lots of various small fixes and code improvements.
+
+= 1.6.9.1 - 2017/08/12 =
+* Regression fix: don't load Imagify's popup files on WP Rocket options screen to avoid conflicts.
+
+= 1.6.9 - 2017/08/11 =
+* Improvement: the bulk optimization now stops as soon as the quota is fully consumed, instead of trying to optimize more images and getting error messages one after the other.
+* Improvement: updated (almost) all JavaScript libraries we use. SweetAlert won't conflict with new versions anymore. Few code improvements.
+* Improvement: in the medias list, improved the Imagify column behavior on small screens.
+* Improvement: when optimizing in NextGen Gallery, update some NGG data.
+* Bug Fix: revamped the whole Enable Media Replace plugin compatibility. Optimization, restoration, and backup should work properly now.
+* Bug Fix: revamped the way to restore images in NextGen Gallery to prevent deletion of alt text, description, and tags.
+* Regression fix: fixed optimization and restoration not working in NextGen Gallery.
+* Regression fix: fixed the bulk optimization not working with PHP 5.2.
+
+= 1.6.8 - 2017/07/26 =
+* Improvement: don't display the restore bulk action in the medias list if there is nothing to restore.
+* Improvement: you can know select and unselect all image sizes at once in the settings page.
+* Improvement: detect when the backup directory is not writable. A warning is displayed dynamically under the backup setting, a notice is also displayed on some pages.
+* Improvement: some strings were still not translated in the bulk optimization page.
+* Bug Fix: the "Save & Go to Bulk Optimizer" button now redirects you even if no settings have been changed.
+* Lots of various small fixes and code improvements.
+
+= 1.6.7.1 - 2017/07/13 =
+* Bug Fix: Fixed the "Unknown error" during a bulk optimization.
+
+= 1.6.7 - 2017/07/12 =
+* Improvement: Compatibility with the plugin WP Offload S3 Pro, and fixed a few things for both Lite and Pro versions.
+* Improvement: Improved performance on the bulk optimization page for huge image libraries.
+* Improvement: When performing a bulk optimization, moved the attachments with the "WELL DONE" message at the end of the queue, it helps to speed up things.
+* Improvement: Use cURL directly only to optimize an image. It helps when cURL is not available: less things will break in that case.
+* Bug Fix: Fixed a bug with the plugin Screets Live Chat, prior to version 2.2.8.
+* Regression fix: Fixed the buffer size on the bulk optimization page.
+* Dev stuff: Added a hook allowing to filter arguments when doing a request to our API. It can be used to increase the timeout value for example.
+
+= 1.6.6 - 2017/06/27 =
+* New: Compatibility with the plugin WP Offload S3 Lite. Your images now will be sent to Amazon S3 after being optimized. Also works when you store your images only on S3, not locally.
+* Improvement: Added a filter to the asynchronous job arguments.
+* Bug fix: Compatibility with Internet Explorer 9 to 11.
+* Regression fix: The comparison tool stopped working in the medias list since the previous version.
+
+= 1.6.5 - 2017/06/22 =
+* Improvement: Code quality of the whole plugin has been improved to fit more WordPress coding standards.
+* Improvement: Lots of internationalization improvements. Now the plugin's internationalization fully rely on the repository system.
+* Bug Fix: Fixed an error with php 7.1: `Uncaught Error: [] operator not supported for strings in /wp-content/plugins/imagify/inc/functions/admin.php:134`.
+
+= 1.6.4 - 2017/04/06 =
+* Improvement: Provide a link to optimize in higher level when an image is already optimized.
+* Improvement: Add a dedicated message for 413 HTTP error when the image is too big to be uploaded on our servers.
+
+= 1.6.3 - 2016/12/16 =
+* Improvement: The discount is now automatically applied in when you buy from the plugin and a promotion is active
+
+= 1.6.2 - 2016/11/22 =
+* Bug Fix: Correctly display the modal when clicking on the plan suggestion button on bulk optimization page
+
+= 1.6.1 - 2016/11/22 =
+* Bug Fix: Better offer suggestion when your medias library is bigger than 3GB
+
+= 1.6 - 2016/11/21 =
+* New: Knowing how many MB/GB you need to optimize your existing and future images is complicated. We love to make things easier, so Imagify will do it and advise you the best plan.
+* New: You can now buy all the plans without leaving your WordPress administration
+* Improvement: Some styles fixed in the interface
+
+= 1.5.10 - 2016/10/05 =
+* Improvement: Set to 1 the Bulk buffer size when there are more than 10 thumbnails to avoid "Unknown error" on the Bulk Optimization
+
+= 1.5.9 - 2016/09/27 =
+* Bug Fix: Don't delete the thumbnail when the maximum file size is set to one of the thumbnail size
+* Bug Fix: Don't strip the image meta data if possible (only with Imagick)
+* Bug Fix: Fix persistent "WELL DONE" message because of "original_size" meta value was 0
+
+= 1.5.8 - 2016/08/24 =
+* Regression fix: Check if the backup option is active before doing a backup when an image is resized
+
+= 1.5.7 - 2016/08/23 =
+* Improvement: Resize images bigger than the maximum width defined in the settings using WP Image Editor instead of Imagify API
+
+= 1.5.6 - 2016/07/29 =
+* Improvement: Dynamically update from the API the maximum image size allowed in bulk optimization
+* Improvement: Updated SweetAlert to SweetAlert2
+
+= 1.5.5 =
+* Bug Fix: Fix issue with "original_size" at 0 in "_imagify_data" to be able to re-optimize an image with a "Forbidden" error.
+
+= 1.5.4 =
+* Improvement: Increase to 4 the number of parallel queries during a bulk optimization
+* Improvement: Don't display Intercom chat if the user turned off the option in the web app
+
+= 1.5.3 =
+* Regression Fix: Display the Original File size in "View Details" section
+
+= 1.5.2.1 =
+* Bug Fix: Fix JS error: Uncaught ReferenceError: imagify is not defined in /assets/options.min.js
+* Bug Fix: Don't show "Optimize" button during optimizing process in "Edit Media" screen
+
+= 1.5.1 =
+* Bug Fix: Thumbnail sizes in settings page aren't reset anymore on plugin update
+* Bug Fix: Fix PHP Warning: Cannot unset offset in a non-array variable in /inc/functions/admin-stats.php on line 23
+* Bug Fix: Fix PHP Warning: Invalid argument supplied for foreach() in /inc/functions/admin-stats.php on line 233
+
+= 1.5 =
+* New: NextGen Gallery compatibility - Optimize all your images uploaded with NextGen Gallery
+* New: Asynchronous Optimization - No more latency when you upload new images, Imagify will optimize them in background!
+* Improvement: Bulk Optimization: Interface improvements for a better experience
+
+= 1.4.7 =
+* Bug Fix: Fix issue between Bulk Optimization & WP Engine. The query to get unoptimized images is limited to 2500 images to be able to use the Bulk Optimization on this hosting.
+* Bug Fix: Fix SSL certificate problem: unable to get local issuer certificate
+
+= 1.4.6 =
+* Bug Fix: Fix the "All your images have been optimized by Imagify" issue when images still need to be optimized. This issue occurred only since 1.4.5 for some users. Sorry for the inconvenience!
+
+= 1.4.5 =
+* Improvement: Bulk Optimization: optimize all SQL queries and improve by 65% the process time \o/
+* Improvement: Chart.js library updated
+* Improvement: Media List JS notice removed
+
+= 1.4.4 =
+* Improvement: Visual fix: CSS prefixed in notices to avoid class conflicts
+* Improvement: Visual fix: improve Imagify Notices CSS to avoid issue with WP Engine CSS
+* Improvement: Medias: new "Compare Original VS Optimized" action link in grid view mode
+* Improvement: Settings: new sample images for visual comparison of compression levels (removes unused sample images)
+
+= 1.4.3 =
+* New: Medias: new "Compare Original VS Optimized" action link in list view
+* Improvement: Visual fix: CSS prefixed in notices to avoid class conflicts
+* Improvement: Medias: comparison are now available for image from 36Opx wide
+* Improvement: Settings: new sample images for visual comparison of compression levels
+
+= 1.4.2 =
+* New: Add German translation
+* New: You can define the `IMAGIFY_HIDDEN_ACCOUNT` constant in wp-config.php to hide all your Imagify account infos in the Admin Bar and Bulk Optimization
+* Bug Fix: Fix PHP Notice: Undefined index original_size in /inc/functions/admin-stats.php on line 185
+* Bug Fix: Fix PHP Notice: Undefined index optimized_size in /inc/functions/admin-stats.php on line 186
+
+= 1.4.1 =
+* Improvement: Medias: better comparison for big portrait images
+* Improvement: Medias: Don't display the "Compare Original VS Optimized" button for images without backup
+* Bug Fix: WPML: Fix AJAX error caused by WPML to avoid issue during the API key validation process
+* Bug Fix: Yoast: Remove JS error caused by Yoast SEO on the attachment edit screen to avoid issue with our "Compare Original VS Optimized"
+
+= 1.4 =
+* New: Medias: Click a button to open images comparison between Original and Optimized (available for big enough images)
+* Improvement: Add async method to optimize resized images
+
+= 1.3.6 =
+* Improvement: Optimize attachments resized with the WordPress editor tool
+* Improvement: Compatibility with the "Replace the file, use new file name and update all links" option from "Enable Media Replace" plugin
+* Improvement: Add a notice message during the Bulk Optimization if the quota is consumed
+* Improvement: Better styles for compression details next to your images
+* Bug Fix: No freeze anymore during the Bulk Optimization if an unknown error occurred with an image
+* Bug Fix: Add a notice message if we can't get all unoptimized images during the Bulk Optimization process
+* Bug Fix: Fix PHP Warning: set_time_limit(): Cannot set time limit in safe mode in ../inc/admin/ajax.php on line 137
+* Bug Fix: Details about compressed images in modal media box are now closed by default
+* Regression Fix: Get all attachments with the message "You've consumed all your data" during the Bulk Optimization process to be able to optimize them
+
+= 1.3.5.2 =
+* Regression Fix: Check mark displayed better on certain settings pages
+
+= 1.3.5 =
+* Bug Fix: Check box display issue fixed on Imagify settings page: SVG Icons cleaning
+
+= 1.3.4 =
+* New: Add Italian translation
+
+= 1.3.3 =
+* Bug Fix: Fixed behavior in multisite networks where Imagify options would not get saved when the plugin wasn't network-activated, but only activated for specific sites within the network.
+
+= 1.3.2 =
+* New: Add Spanish translation
+* Bug Fix: Avoid lack of performance in the WordPress administration if the Imagify's servers are down.
+
+= 1.3.1 =
+* Bug Fix: Remove a notice message which causes a lack of performance in the administration. (thanks Kevin Gauthier to warn us)
+
+= 1.3 =
+* New: Add GIF support
+* New: You can now decide to keep EXIF data on your images
+
+= 1.2.4 =
+* Bug Fix: Don't duplicate Imagify data in the attachment edit screen (wp-admin/post.php)
+
+= 1.2.3 =
+* Improvement: Use AJAX to display the quota in the admin bar to avoid a call to our API on each pages.
+
+= 1.2.2 =
+* Bug Fix: Bulk Optimization: Fix issue when the backup option isn't activated. The compression level applied was "Normal" instead the one saved in the settings.
+* Bug Fix: Bulk Optimization: Don't try to re-optimize an image already optimized which has the same compression level than the one saved in the settings.
+
+= 1.2.1 =
+* Regression fix: Fix the Bulk Optimization issue when you never optimized any images and avoid the message "All your images have been optimized by Imagify. Congratulations!".
+
+= 1.2 =
+* New: compression level: Ultra
+* New: You can now choose to display Admin Bar Imagify's menu, or not.
+* New: See the differences between Ultra, Aggressive and Normal option inside Imagify Options page.
+* Bug Fix: Admin Bar: Styles are now included in front-end too.
+* Bug Fix: Admin Bar: Better styles in certain cases.
+* Bug Fix: Deactivate a conflict plugin doesn't return a blank page anymore!
+* Bug Fix: Display the right original image size after a resize (meta data)
+* Regression Fix: Bulk Optimization: update in live the unconsumed credit during a bulk optimization.
+
+= 1.1.6 =
+* Improvement: Quick access to your profile informations (quota) in Admin Bar > Imagify
+* Improvement: More precise information about global size saved using Imagify (bulk optimization page)
+* Improvement: When your bulk optimization is over, success message isn't inside the table anymore
+* Improvement: To quit the bulk optimization processing you have to confirm your action
+* Bug Fix: JS: `console` undefined on some IE browsers
+* Bug Fix: PHP Warning: `Illegal string offset 'sizes' in ../inc/functions/admin-stats.php on line 180`
+* Bug Fix: Don't count GIF & SVG in the Imagify statistics
+
+= 1.1.5 =
+* Improvement: Display a default preview to avoid issues with 404 images and a security restriction on SSL websites on the Bulk Optimization page
+* Improvement: Don't count all exceeded images to avoid lack of speed on the Bulk Optimization page
+* Bug Fix: Don't try to re-optimize images with an empty error message or with an already optimized message on the Bulk Optimization
+* Bug Fix: Don't generate special chars in the password to avoid issue on the Imagify app log in
+
+= 1.1.4 =
+* Improvement: Don't add the WP Rocket ads if this plugin is activated
+* Bug Fix: Ignore thumbnails with infinite width like 9999 to avoid an issue with the "Resize larger images" option
+
+= 1.1.3 =
+* Bug Fix: Fix PHP Warning: `curl_setopt() [function.curl-setopt]: CURLOPT_FOLLOWLOCATION cannot be activated when safe_mode is enabled or an open_basedir is set in ../inc/api/imagify.php on line 218`
+
+= 1.1.2 =
+* Regression fix: Fix the "%undefined%" and the overview chart issues on the Bulk Optimization page
+* Regression fix: Fix PHP Warning: Illegal string offset 'sizes' in ../inc/classes/class-attachment.php on line 347
+* Regression fix: Fix PHP Notice: Uninitialized string offset: 0 in ../inc/classes/class-attachment.php on line 347
+* Regression fix: Fix PHP Warning: Illegal string offset 'file' in ../inc/classes/class-attachment.php on line 410
+
+= 1.1.1 =
+* New: Add a notice on the Bulk Optimization & Imagify Settings page when the monthly free quota is consumed
+* Bug Fix: Fix issue on Chrome & Opera on the Bulk Optimization: images are optimized from the newest to the oldest.
+
+= 1.1 =
+* New: Add new option "Resize larger Images"
+* Improvement: Bulk optimization: results table is not shrinkable to the infinite anymore (scrollable)
+* Improvement: Better visual in options page
+* Bug Fix: Check if an attachment exists to avoid an issue which is stopped the Bulk Optimization
+* Bug Fix: Really Fix PHP Notice: Undefined offset: 1 in imagify/inc/functions/formatting.php on line 17
+* Bug Fix: Double animation in Progress Bar
+
+= 1.0.3 =
+* Bug Fix: Fix PHP Notice: Undefined offset: 1 in ../inc/functions/formatting.php on line 16
+
+= 1.0.2 =
+* Improvement: Add error descriptions on the Bulk Optimization results
+* Improvement: Add a notice to switch to the list view in the media library page
+
+= 1.0.1 =
+* New: Add Intercom Live Chat on Imagify Settings and Bulk Optimization pages
+* Improvement: Better user informations
+* Bug Fix: PHP 5.2+ compatibility
+
+= 1.0 =
+* Initial release.
diff --git a/wp/wp-content/plugins/imagify/uninstall.php b/wp/wp-content/plugins/imagify/uninstall.php
new file mode 100644
index 00000000..82a9de69
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/uninstall.php
@@ -0,0 +1,50 @@
+prefix . 'ngg_imagify_data_db_version' );
+
+// Delete all transients.
+delete_site_transient( 'imagify_activation' );
+delete_site_transient( 'imagify_check_licence_1' );
+delete_site_transient( 'imagify_user' );
+delete_site_transient( 'imagify_themes_plugins_to_sync' );
+delete_site_transient( 'do_imagify_rating_cron' );
+delete_site_transient( 'imagify_seen_rating_notice' );
+delete_site_transient( 'imagify_user_images_count' );
+delete_transient( 'imagify_activation' );
+delete_transient( 'imagify_bulk_optimization_level' );
+delete_transient( 'imagify_bulk_optimization_infos' );
+delete_transient( 'imagify_large_library' );
+delete_transient( 'imagify_max_image_size' );
+delete_transient( 'imagify_user' );
+delete_transient( 'imagify_stat_without_next_gen' );
+
+// Delete transients.
+$transients = implode( '" OR option_name LIKE "', array(
+ '\_transient\_%imagify-auto-optimize-%',
+ '\_transient\_%imagify\_rpc\_%',
+ '\_transient\_imagify\_%\_process\_locked',
+ '\_site\_transient\_imagify\_%\_process\_lock%',
+) );
+$wpdb->query( "DELETE from $wpdb->options WHERE option_name LIKE \"$transients\"" ); // WPCS: unprepared SQL ok.
+
+// Clear scheduled hooks.
+wp_clear_scheduled_hook( 'imagify_rating_event' );
+wp_clear_scheduled_hook( 'imagify_update_library_size_calculations_event' );
+
+// Delete all user meta related to Imagify.
+delete_metadata( 'user', '', '_imagify_ignore_notices', '', true );
+
+// Drop the tables.
+$wpdb->query( 'DROP TABLE IF EXISTS ' . $wpdb->base_prefix . 'imagify_files' );
+$wpdb->query( 'DROP TABLE IF EXISTS ' . $wpdb->base_prefix . 'imagify_folders' );
+$wpdb->query( 'DROP TABLE IF EXISTS ' . $wpdb->prefix . 'ngg_imagify_data' );
diff --git a/wp/wp-content/plugins/imagify/vendor/autoload.php b/wp/wp-content/plugins/imagify/vendor/autoload.php
new file mode 100644
index 00000000..0567dacc
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/autoload.php
@@ -0,0 +1,25 @@
+
+ * Jordi Boggiano
+ *
+ * For the full copyright and license information, please view the LICENSE
+ * file that was distributed with this source code.
+ */
+
+namespace Composer\AutoloadWPMediaImagifyWordPressPlugin;
+
+/**
+ * ClassLoader implements a PSR-0, PSR-4 and classmap class loader.
+ *
+ * $loader = new \Composer\AutoloadWPMediaImagifyWordPressPlugin\ClassLoader();
+ *
+ * // register classes with namespaces
+ * $loader->add('Symfony\Component', __DIR__.'/component');
+ * $loader->add('Symfony', __DIR__.'/framework');
+ *
+ * // activate the autoloader
+ * $loader->register();
+ *
+ * // to enable searching the include path (eg. for PEAR packages)
+ * $loader->setUseIncludePath(true);
+ *
+ * In this example, if you try to use a class in the Symfony\Component
+ * namespace or one of its children (Symfony\Component\Console for instance),
+ * the autoloader will first look for the class under the component/
+ * directory, and it will then fallback to the framework/ directory if not
+ * found before giving up.
+ *
+ * This class is loosely based on the Symfony UniversalClassLoader.
+ *
+ * @author Fabien Potencier
+ * @author Jordi Boggiano
+ * @see https://www.php-fig.org/psr/psr-0/
+ * @see https://www.php-fig.org/psr/psr-4/
+ */
+class ClassLoader
+{
+ /** @var \Closure(string):void */
+ private static $includeFile;
+
+ /** @var string|null */
+ private $vendorDir;
+
+ // PSR-4
+ /**
+ * @var array>
+ */
+ private $prefixLengthsPsr4 = array();
+ /**
+ * @var array>
+ */
+ private $prefixDirsPsr4 = array();
+ /**
+ * @var list
+ */
+ private $fallbackDirsPsr4 = array();
+
+ // PSR-0
+ /**
+ * List of PSR-0 prefixes
+ *
+ * Structured as array('F (first letter)' => array('Foo\Bar (full prefix)' => array('path', 'path2')))
+ *
+ * @var array>>
+ */
+ private $prefixesPsr0 = array();
+ /**
+ * @var list
+ */
+ private $fallbackDirsPsr0 = array();
+
+ /** @var bool */
+ private $useIncludePath = false;
+
+ /**
+ * @var array
+ */
+ private $classMap = array();
+
+ /** @var bool */
+ private $classMapAuthoritative = false;
+
+ /**
+ * @var array
+ */
+ private $missingClasses = array();
+
+ /** @var string|null */
+ private $apcuPrefix;
+
+ /**
+ * @var array
+ */
+ private static $registeredLoaders = array();
+
+ /**
+ * @param string|null $vendorDir
+ */
+ public function __construct($vendorDir = null)
+ {
+ $this->vendorDir = $vendorDir;
+ self::initializeIncludeClosure();
+ }
+
+ /**
+ * @return array>
+ */
+ public function getPrefixes()
+ {
+ if (!empty($this->prefixesPsr0)) {
+ return call_user_func_array('array_merge', array_values($this->prefixesPsr0));
+ }
+
+ return array();
+ }
+
+ /**
+ * @return array>
+ */
+ public function getPrefixesPsr4()
+ {
+ return $this->prefixDirsPsr4;
+ }
+
+ /**
+ * @return list
+ */
+ public function getFallbackDirs()
+ {
+ return $this->fallbackDirsPsr0;
+ }
+
+ /**
+ * @return list
+ */
+ public function getFallbackDirsPsr4()
+ {
+ return $this->fallbackDirsPsr4;
+ }
+
+ /**
+ * @return array Array of classname => path
+ */
+ public function getClassMap()
+ {
+ return $this->classMap;
+ }
+
+ /**
+ * @param array $classMap Class to filename map
+ *
+ * @return void
+ */
+ public function addClassMap(array $classMap)
+ {
+ if ($this->classMap) {
+ $this->classMap = array_merge($this->classMap, $classMap);
+ } else {
+ $this->classMap = $classMap;
+ }
+ }
+
+ /**
+ * Registers a set of PSR-0 directories for a given prefix, either
+ * appending or prepending to the ones previously set for this prefix.
+ *
+ * @param string $prefix The prefix
+ * @param list|string $paths The PSR-0 root directories
+ * @param bool $prepend Whether to prepend the directories
+ *
+ * @return void
+ */
+ public function add($prefix, $paths, $prepend = false)
+ {
+ $paths = (array) $paths;
+ if (!$prefix) {
+ if ($prepend) {
+ $this->fallbackDirsPsr0 = array_merge(
+ $paths,
+ $this->fallbackDirsPsr0
+ );
+ } else {
+ $this->fallbackDirsPsr0 = array_merge(
+ $this->fallbackDirsPsr0,
+ $paths
+ );
+ }
+
+ return;
+ }
+
+ $first = $prefix[0];
+ if (!isset($this->prefixesPsr0[$first][$prefix])) {
+ $this->prefixesPsr0[$first][$prefix] = $paths;
+
+ return;
+ }
+ if ($prepend) {
+ $this->prefixesPsr0[$first][$prefix] = array_merge(
+ $paths,
+ $this->prefixesPsr0[$first][$prefix]
+ );
+ } else {
+ $this->prefixesPsr0[$first][$prefix] = array_merge(
+ $this->prefixesPsr0[$first][$prefix],
+ $paths
+ );
+ }
+ }
+
+ /**
+ * Registers a set of PSR-4 directories for a given namespace, either
+ * appending or prepending to the ones previously set for this namespace.
+ *
+ * @param string $prefix The prefix/namespace, with trailing '\\'
+ * @param list|string $paths The PSR-4 base directories
+ * @param bool $prepend Whether to prepend the directories
+ *
+ * @throws \InvalidArgumentException
+ *
+ * @return void
+ */
+ public function addPsr4($prefix, $paths, $prepend = false)
+ {
+ $paths = (array) $paths;
+ if (!$prefix) {
+ // Register directories for the root namespace.
+ if ($prepend) {
+ $this->fallbackDirsPsr4 = array_merge(
+ $paths,
+ $this->fallbackDirsPsr4
+ );
+ } else {
+ $this->fallbackDirsPsr4 = array_merge(
+ $this->fallbackDirsPsr4,
+ $paths
+ );
+ }
+ } elseif (!isset($this->prefixDirsPsr4[$prefix])) {
+ // Register directories for a new namespace.
+ $length = strlen($prefix);
+ if ('\\' !== $prefix[$length - 1]) {
+ throw new \InvalidArgumentException("A non-empty PSR-4 prefix must end with a namespace separator.");
+ }
+ $this->prefixLengthsPsr4[$prefix[0]][$prefix] = $length;
+ $this->prefixDirsPsr4[$prefix] = $paths;
+ } elseif ($prepend) {
+ // Prepend directories for an already registered namespace.
+ $this->prefixDirsPsr4[$prefix] = array_merge(
+ $paths,
+ $this->prefixDirsPsr4[$prefix]
+ );
+ } else {
+ // Append directories for an already registered namespace.
+ $this->prefixDirsPsr4[$prefix] = array_merge(
+ $this->prefixDirsPsr4[$prefix],
+ $paths
+ );
+ }
+ }
+
+ /**
+ * Registers a set of PSR-0 directories for a given prefix,
+ * replacing any others previously set for this prefix.
+ *
+ * @param string $prefix The prefix
+ * @param list|string $paths The PSR-0 base directories
+ *
+ * @return void
+ */
+ public function set($prefix, $paths)
+ {
+ if (!$prefix) {
+ $this->fallbackDirsPsr0 = (array) $paths;
+ } else {
+ $this->prefixesPsr0[$prefix[0]][$prefix] = (array) $paths;
+ }
+ }
+
+ /**
+ * Registers a set of PSR-4 directories for a given namespace,
+ * replacing any others previously set for this namespace.
+ *
+ * @param string $prefix The prefix/namespace, with trailing '\\'
+ * @param list|string $paths The PSR-4 base directories
+ *
+ * @throws \InvalidArgumentException
+ *
+ * @return void
+ */
+ public function setPsr4($prefix, $paths)
+ {
+ if (!$prefix) {
+ $this->fallbackDirsPsr4 = (array) $paths;
+ } else {
+ $length = strlen($prefix);
+ if ('\\' !== $prefix[$length - 1]) {
+ throw new \InvalidArgumentException("A non-empty PSR-4 prefix must end with a namespace separator.");
+ }
+ $this->prefixLengthsPsr4[$prefix[0]][$prefix] = $length;
+ $this->prefixDirsPsr4[$prefix] = (array) $paths;
+ }
+ }
+
+ /**
+ * Turns on searching the include path for class files.
+ *
+ * @param bool $useIncludePath
+ *
+ * @return void
+ */
+ public function setUseIncludePath($useIncludePath)
+ {
+ $this->useIncludePath = $useIncludePath;
+ }
+
+ /**
+ * Can be used to check if the autoloader uses the include path to check
+ * for classes.
+ *
+ * @return bool
+ */
+ public function getUseIncludePath()
+ {
+ return $this->useIncludePath;
+ }
+
+ /**
+ * Turns off searching the prefix and fallback directories for classes
+ * that have not been registered with the class map.
+ *
+ * @param bool $classMapAuthoritative
+ *
+ * @return void
+ */
+ public function setClassMapAuthoritative($classMapAuthoritative)
+ {
+ $this->classMapAuthoritative = $classMapAuthoritative;
+ }
+
+ /**
+ * Should class lookup fail if not found in the current class map?
+ *
+ * @return bool
+ */
+ public function isClassMapAuthoritative()
+ {
+ return $this->classMapAuthoritative;
+ }
+
+ /**
+ * APCu prefix to use to cache found/not-found classes, if the extension is enabled.
+ *
+ * @param string|null $apcuPrefix
+ *
+ * @return void
+ */
+ public function setApcuPrefix($apcuPrefix)
+ {
+ $this->apcuPrefix = function_exists('apcu_fetch') && filter_var(ini_get('apc.enabled'), FILTER_VALIDATE_BOOLEAN) ? $apcuPrefix : null;
+ }
+
+ /**
+ * The APCu prefix in use, or null if APCu caching is not enabled.
+ *
+ * @return string|null
+ */
+ public function getApcuPrefix()
+ {
+ return $this->apcuPrefix;
+ }
+
+ /**
+ * Registers this instance as an autoloader.
+ *
+ * @param bool $prepend Whether to prepend the autoloader or not
+ *
+ * @return void
+ */
+ public function register($prepend = false)
+ {
+ spl_autoload_register(array($this, 'loadClass'), true, $prepend);
+
+ if (null === $this->vendorDir) {
+ return;
+ }
+
+ if ($prepend) {
+ self::$registeredLoaders = array($this->vendorDir => $this) + self::$registeredLoaders;
+ } else {
+ unset(self::$registeredLoaders[$this->vendorDir]);
+ self::$registeredLoaders[$this->vendorDir] = $this;
+ }
+ }
+
+ /**
+ * Unregisters this instance as an autoloader.
+ *
+ * @return void
+ */
+ public function unregister()
+ {
+ spl_autoload_unregister(array($this, 'loadClass'));
+
+ if (null !== $this->vendorDir) {
+ unset(self::$registeredLoaders[$this->vendorDir]);
+ }
+ }
+
+ /**
+ * Loads the given class or interface.
+ *
+ * @param string $class The name of the class
+ * @return true|null True if loaded, null otherwise
+ */
+ public function loadClass($class)
+ {
+ if ($file = $this->findFile($class)) {
+ $includeFile = self::$includeFile;
+ $includeFile($file);
+
+ return true;
+ }
+
+ return null;
+ }
+
+ /**
+ * Finds the path to the file where the class is defined.
+ *
+ * @param string $class The name of the class
+ *
+ * @return string|false The path if found, false otherwise
+ */
+ public function findFile($class)
+ {
+ // class map lookup
+ if (isset($this->classMap[$class])) {
+ return $this->classMap[$class];
+ }
+ if ($this->classMapAuthoritative || isset($this->missingClasses[$class])) {
+ return false;
+ }
+ if (null !== $this->apcuPrefix) {
+ $file = apcu_fetch($this->apcuPrefix.$class, $hit);
+ if ($hit) {
+ return $file;
+ }
+ }
+
+ $file = $this->findFileWithExtension($class, '.php');
+
+ // Search for Hack files if we are running on HHVM
+ if (false === $file && defined('HHVM_VERSION')) {
+ $file = $this->findFileWithExtension($class, '.hh');
+ }
+
+ if (null !== $this->apcuPrefix) {
+ apcu_add($this->apcuPrefix.$class, $file);
+ }
+
+ if (false === $file) {
+ // Remember that this class does not exist.
+ $this->missingClasses[$class] = true;
+ }
+
+ return $file;
+ }
+
+ /**
+ * Returns the currently registered loaders keyed by their corresponding vendor directories.
+ *
+ * @return array
+ */
+ public static function getRegisteredLoaders()
+ {
+ return self::$registeredLoaders;
+ }
+
+ /**
+ * @param string $class
+ * @param string $ext
+ * @return string|false
+ */
+ private function findFileWithExtension($class, $ext)
+ {
+ // PSR-4 lookup
+ $logicalPathPsr4 = strtr($class, '\\', DIRECTORY_SEPARATOR) . $ext;
+
+ $first = $class[0];
+ if (isset($this->prefixLengthsPsr4[$first])) {
+ $subPath = $class;
+ while (false !== $lastPos = strrpos($subPath, '\\')) {
+ $subPath = substr($subPath, 0, $lastPos);
+ $search = $subPath . '\\';
+ if (isset($this->prefixDirsPsr4[$search])) {
+ $pathEnd = DIRECTORY_SEPARATOR . substr($logicalPathPsr4, $lastPos + 1);
+ foreach ($this->prefixDirsPsr4[$search] as $dir) {
+ if (file_exists($file = $dir . $pathEnd)) {
+ return $file;
+ }
+ }
+ }
+ }
+ }
+
+ // PSR-4 fallback dirs
+ foreach ($this->fallbackDirsPsr4 as $dir) {
+ if (file_exists($file = $dir . DIRECTORY_SEPARATOR . $logicalPathPsr4)) {
+ return $file;
+ }
+ }
+
+ // PSR-0 lookup
+ if (false !== $pos = strrpos($class, '\\')) {
+ // namespaced class name
+ $logicalPathPsr0 = substr($logicalPathPsr4, 0, $pos + 1)
+ . strtr(substr($logicalPathPsr4, $pos + 1), '_', DIRECTORY_SEPARATOR);
+ } else {
+ // PEAR-like class name
+ $logicalPathPsr0 = strtr($class, '_', DIRECTORY_SEPARATOR) . $ext;
+ }
+
+ if (isset($this->prefixesPsr0[$first])) {
+ foreach ($this->prefixesPsr0[$first] as $prefix => $dirs) {
+ if (0 === strpos($class, $prefix)) {
+ foreach ($dirs as $dir) {
+ if (file_exists($file = $dir . DIRECTORY_SEPARATOR . $logicalPathPsr0)) {
+ return $file;
+ }
+ }
+ }
+ }
+ }
+
+ // PSR-0 fallback dirs
+ foreach ($this->fallbackDirsPsr0 as $dir) {
+ if (file_exists($file = $dir . DIRECTORY_SEPARATOR . $logicalPathPsr0)) {
+ return $file;
+ }
+ }
+
+ // PSR-0 include paths.
+ if ($this->useIncludePath && $file = stream_resolve_include_path($logicalPathPsr0)) {
+ return $file;
+ }
+
+ return false;
+ }
+
+ /**
+ * @return void
+ */
+ private static function initializeIncludeClosure()
+ {
+ if (self::$includeFile !== null) {
+ return;
+ }
+
+ /**
+ * Scope isolated include.
+ *
+ * Prevents access to $this/self from included files.
+ *
+ * @param string $file
+ * @return void
+ */
+ self::$includeFile = \Closure::bind(static function($file) {
+ include $file;
+ }, null, null);
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/InstalledVersions.php b/wp/wp-content/plugins/imagify/vendor/composer/InstalledVersions.php
new file mode 100644
index 00000000..51e734a7
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/InstalledVersions.php
@@ -0,0 +1,359 @@
+
+ * Jordi Boggiano
+ *
+ * For the full copyright and license information, please view the LICENSE
+ * file that was distributed with this source code.
+ */
+
+namespace Composer;
+
+use Composer\Autoload\ClassLoader;
+use Composer\Semver\VersionParser;
+
+/**
+ * This class is copied in every Composer installed project and available to all
+ *
+ * See also https://getcomposer.org/doc/07-runtime.md#installed-versions
+ *
+ * To require its presence, you can require `composer-runtime-api ^2.0`
+ *
+ * @final
+ */
+class InstalledVersions
+{
+ /**
+ * @var mixed[]|null
+ * @psalm-var array{root: array{name: string, pretty_version: string, version: string, reference: string|null, type: string, install_path: string, aliases: string[], dev: bool}, versions: array}|array{}|null
+ */
+ private static $installed;
+
+ /**
+ * @var bool|null
+ */
+ private static $canGetVendors;
+
+ /**
+ * @var array[]
+ * @psalm-var array}>
+ */
+ private static $installedByVendor = array();
+
+ /**
+ * Returns a list of all package names which are present, either by being installed, replaced or provided
+ *
+ * @return string[]
+ * @psalm-return list
+ */
+ public static function getInstalledPackages()
+ {
+ $packages = array();
+ foreach (self::getInstalled() as $installed) {
+ $packages[] = array_keys($installed['versions']);
+ }
+
+ if (1 === \count($packages)) {
+ return $packages[0];
+ }
+
+ return array_keys(array_flip(\call_user_func_array('array_merge', $packages)));
+ }
+
+ /**
+ * Returns a list of all package names with a specific type e.g. 'library'
+ *
+ * @param string $type
+ * @return string[]
+ * @psalm-return list
+ */
+ public static function getInstalledPackagesByType($type)
+ {
+ $packagesByType = array();
+
+ foreach (self::getInstalled() as $installed) {
+ foreach ($installed['versions'] as $name => $package) {
+ if (isset($package['type']) && $package['type'] === $type) {
+ $packagesByType[] = $name;
+ }
+ }
+ }
+
+ return $packagesByType;
+ }
+
+ /**
+ * Checks whether the given package is installed
+ *
+ * This also returns true if the package name is provided or replaced by another package
+ *
+ * @param string $packageName
+ * @param bool $includeDevRequirements
+ * @return bool
+ */
+ public static function isInstalled($packageName, $includeDevRequirements = true)
+ {
+ foreach (self::getInstalled() as $installed) {
+ if (isset($installed['versions'][$packageName])) {
+ return $includeDevRequirements || !isset($installed['versions'][$packageName]['dev_requirement']) || $installed['versions'][$packageName]['dev_requirement'] === false;
+ }
+ }
+
+ return false;
+ }
+
+ /**
+ * Checks whether the given package satisfies a version constraint
+ *
+ * e.g. If you want to know whether version 2.3+ of package foo/bar is installed, you would call:
+ *
+ * Composer\InstalledVersions::satisfies(new VersionParser, 'foo/bar', '^2.3')
+ *
+ * @param VersionParser $parser Install composer/semver to have access to this class and functionality
+ * @param string $packageName
+ * @param string|null $constraint A version constraint to check for, if you pass one you have to make sure composer/semver is required by your package
+ * @return bool
+ */
+ public static function satisfies(VersionParser $parser, $packageName, $constraint)
+ {
+ $constraint = $parser->parseConstraints((string) $constraint);
+ $provided = $parser->parseConstraints(self::getVersionRanges($packageName));
+
+ return $provided->matches($constraint);
+ }
+
+ /**
+ * Returns a version constraint representing all the range(s) which are installed for a given package
+ *
+ * It is easier to use this via isInstalled() with the $constraint argument if you need to check
+ * whether a given version of a package is installed, and not just whether it exists
+ *
+ * @param string $packageName
+ * @return string Version constraint usable with composer/semver
+ */
+ public static function getVersionRanges($packageName)
+ {
+ foreach (self::getInstalled() as $installed) {
+ if (!isset($installed['versions'][$packageName])) {
+ continue;
+ }
+
+ $ranges = array();
+ if (isset($installed['versions'][$packageName]['pretty_version'])) {
+ $ranges[] = $installed['versions'][$packageName]['pretty_version'];
+ }
+ if (array_key_exists('aliases', $installed['versions'][$packageName])) {
+ $ranges = array_merge($ranges, $installed['versions'][$packageName]['aliases']);
+ }
+ if (array_key_exists('replaced', $installed['versions'][$packageName])) {
+ $ranges = array_merge($ranges, $installed['versions'][$packageName]['replaced']);
+ }
+ if (array_key_exists('provided', $installed['versions'][$packageName])) {
+ $ranges = array_merge($ranges, $installed['versions'][$packageName]['provided']);
+ }
+
+ return implode(' || ', $ranges);
+ }
+
+ throw new \OutOfBoundsException('Package "' . $packageName . '" is not installed');
+ }
+
+ /**
+ * @param string $packageName
+ * @return string|null If the package is being replaced or provided but is not really installed, null will be returned as version, use satisfies or getVersionRanges if you need to know if a given version is present
+ */
+ public static function getVersion($packageName)
+ {
+ foreach (self::getInstalled() as $installed) {
+ if (!isset($installed['versions'][$packageName])) {
+ continue;
+ }
+
+ if (!isset($installed['versions'][$packageName]['version'])) {
+ return null;
+ }
+
+ return $installed['versions'][$packageName]['version'];
+ }
+
+ throw new \OutOfBoundsException('Package "' . $packageName . '" is not installed');
+ }
+
+ /**
+ * @param string $packageName
+ * @return string|null If the package is being replaced or provided but is not really installed, null will be returned as version, use satisfies or getVersionRanges if you need to know if a given version is present
+ */
+ public static function getPrettyVersion($packageName)
+ {
+ foreach (self::getInstalled() as $installed) {
+ if (!isset($installed['versions'][$packageName])) {
+ continue;
+ }
+
+ if (!isset($installed['versions'][$packageName]['pretty_version'])) {
+ return null;
+ }
+
+ return $installed['versions'][$packageName]['pretty_version'];
+ }
+
+ throw new \OutOfBoundsException('Package "' . $packageName . '" is not installed');
+ }
+
+ /**
+ * @param string $packageName
+ * @return string|null If the package is being replaced or provided but is not really installed, null will be returned as reference
+ */
+ public static function getReference($packageName)
+ {
+ foreach (self::getInstalled() as $installed) {
+ if (!isset($installed['versions'][$packageName])) {
+ continue;
+ }
+
+ if (!isset($installed['versions'][$packageName]['reference'])) {
+ return null;
+ }
+
+ return $installed['versions'][$packageName]['reference'];
+ }
+
+ throw new \OutOfBoundsException('Package "' . $packageName . '" is not installed');
+ }
+
+ /**
+ * @param string $packageName
+ * @return string|null If the package is being replaced or provided but is not really installed, null will be returned as install path. Packages of type metapackages also have a null install path.
+ */
+ public static function getInstallPath($packageName)
+ {
+ foreach (self::getInstalled() as $installed) {
+ if (!isset($installed['versions'][$packageName])) {
+ continue;
+ }
+
+ return isset($installed['versions'][$packageName]['install_path']) ? $installed['versions'][$packageName]['install_path'] : null;
+ }
+
+ throw new \OutOfBoundsException('Package "' . $packageName . '" is not installed');
+ }
+
+ /**
+ * @return array
+ * @psalm-return array{name: string, pretty_version: string, version: string, reference: string|null, type: string, install_path: string, aliases: string[], dev: bool}
+ */
+ public static function getRootPackage()
+ {
+ $installed = self::getInstalled();
+
+ return $installed[0]['root'];
+ }
+
+ /**
+ * Returns the raw installed.php data for custom implementations
+ *
+ * @deprecated Use getAllRawData() instead which returns all datasets for all autoloaders present in the process. getRawData only returns the first dataset loaded, which may not be what you expect.
+ * @return array[]
+ * @psalm-return array{root: array{name: string, pretty_version: string, version: string, reference: string|null, type: string, install_path: string, aliases: string[], dev: bool}, versions: array}
+ */
+ public static function getRawData()
+ {
+ @trigger_error('getRawData only returns the first dataset loaded, which may not be what you expect. Use getAllRawData() instead which returns all datasets for all autoloaders present in the process.', E_USER_DEPRECATED);
+
+ if (null === self::$installed) {
+ // only require the installed.php file if this file is loaded from its dumped location,
+ // and not from its source location in the composer/composer package, see https://github.com/composer/composer/issues/9937
+ if (substr(__DIR__, -8, 1) !== 'C') {
+ self::$installed = include __DIR__ . '/installed.php';
+ } else {
+ self::$installed = array();
+ }
+ }
+
+ return self::$installed;
+ }
+
+ /**
+ * Returns the raw data of all installed.php which are currently loaded for custom implementations
+ *
+ * @return array[]
+ * @psalm-return list}>
+ */
+ public static function getAllRawData()
+ {
+ return self::getInstalled();
+ }
+
+ /**
+ * Lets you reload the static array from another file
+ *
+ * This is only useful for complex integrations in which a project needs to use
+ * this class but then also needs to execute another project's autoloader in process,
+ * and wants to ensure both projects have access to their version of installed.php.
+ *
+ * A typical case would be PHPUnit, where it would need to make sure it reads all
+ * the data it needs from this class, then call reload() with
+ * `require $CWD/vendor/composer/installed.php` (or similar) as input to make sure
+ * the project in which it runs can then also use this class safely, without
+ * interference between PHPUnit's dependencies and the project's dependencies.
+ *
+ * @param array[] $data A vendor/composer/installed.php data set
+ * @return void
+ *
+ * @psalm-param array{root: array{name: string, pretty_version: string, version: string, reference: string|null, type: string, install_path: string, aliases: string[], dev: bool}, versions: array} $data
+ */
+ public static function reload($data)
+ {
+ self::$installed = $data;
+ self::$installedByVendor = array();
+ }
+
+ /**
+ * @return array[]
+ * @psalm-return list}>
+ */
+ private static function getInstalled()
+ {
+ if (null === self::$canGetVendors) {
+ self::$canGetVendors = method_exists('Composer\Autoload\ClassLoader', 'getRegisteredLoaders');
+ }
+
+ $installed = array();
+
+ if (self::$canGetVendors) {
+ foreach (ClassLoader::getRegisteredLoaders() as $vendorDir => $loader) {
+ if (isset(self::$installedByVendor[$vendorDir])) {
+ $installed[] = self::$installedByVendor[$vendorDir];
+ } elseif (is_file($vendorDir.'/composer/installed.php')) {
+ /** @var array{root: array{name: string, pretty_version: string, version: string, reference: string|null, type: string, install_path: string, aliases: string[], dev: bool}, versions: array} $required */
+ $required = require $vendorDir.'/composer/installed.php';
+ $installed[] = self::$installedByVendor[$vendorDir] = $required;
+ if (null === self::$installed && strtr($vendorDir.'/composer', '\\', '/') === strtr(__DIR__, '\\', '/')) {
+ self::$installed = $installed[count($installed) - 1];
+ }
+ }
+ }
+ }
+
+ if (null === self::$installed) {
+ // only require the installed.php file if this file is loaded from its dumped location,
+ // and not from its source location in the composer/composer package, see https://github.com/composer/composer/issues/9937
+ if (substr(__DIR__, -8, 1) !== 'C') {
+ /** @var array{root: array{name: string, pretty_version: string, version: string, reference: string|null, type: string, install_path: string, aliases: string[], dev: bool}, versions: array} $required */
+ $required = require __DIR__ . '/installed.php';
+ self::$installed = $required;
+ } else {
+ self::$installed = array();
+ }
+ }
+
+ if (self::$installed !== array()) {
+ $installed[] = self::$installed;
+ }
+
+ return $installed;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/LICENSE b/wp/wp-content/plugins/imagify/vendor/composer/LICENSE
new file mode 100644
index 00000000..f27399a0
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/LICENSE
@@ -0,0 +1,21 @@
+
+Copyright (c) Nils Adermann, Jordi Boggiano
+
+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/wp/wp-content/plugins/imagify/vendor/composer/autoload_classmap.php b/wp/wp-content/plugins/imagify/vendor/composer/autoload_classmap.php
new file mode 100644
index 00000000..d454a928
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/autoload_classmap.php
@@ -0,0 +1,56 @@
+ $vendorDir . '/composer/InstalledVersions.php',
+ 'Imagify' => $baseDir . '/inc/classes/class-imagify.php',
+ 'Imagify\\EventManagement\\EventManager' => $baseDir . '/inc/classes/Dependencies/wp-media/event-manager/EventManager.php',
+ 'Imagify\\EventManagement\\EventManagerAwareSubscriberInterface' => $baseDir . '/inc/classes/Dependencies/wp-media/event-manager/EventManagerAwareSubscriberInterface.php',
+ 'Imagify\\EventManagement\\SubscriberInterface' => $baseDir . '/inc/classes/Dependencies/wp-media/event-manager/SubscriberInterface.php',
+ 'Imagify_AS3CF_Attachment' => $baseDir . '/inc/deprecated/classes/class-imagify-as3cf-attachment.php',
+ 'Imagify_AS3CF_Deprecated' => $baseDir . '/inc/deprecated/classes/class-imagify-as3cf-deprecated.php',
+ 'Imagify_Abstract_Attachment' => $baseDir . '/inc/deprecated/classes/class-imagify-abstract-attachment.php',
+ 'Imagify_Abstract_Background_Process' => $baseDir . '/inc/classes/class-imagify-abstract-background-process.php',
+ 'Imagify_Abstract_Cron' => $baseDir . '/inc/classes/class-imagify-abstract-cron.php',
+ 'Imagify_Abstract_DB' => $baseDir . '/inc/classes/class-imagify-abstract-db.php',
+ 'Imagify_Abstract_DB_Deprecated' => $baseDir . '/inc/deprecated/classes/class-imagify-abstract-db-deprecated.php',
+ 'Imagify_Abstract_Options' => $baseDir . '/inc/classes/class-imagify-abstract-options.php',
+ 'Imagify_Admin_Ajax_Post' => $baseDir . '/inc/classes/class-imagify-admin-ajax-post.php',
+ 'Imagify_Admin_Ajax_Post_Deprecated' => $baseDir . '/inc/deprecated/classes/class-imagify-admin-ajax-post-deprecated.php',
+ 'Imagify_Assets' => $baseDir . '/inc/classes/class-imagify-assets.php',
+ 'Imagify_Assets_Deprecated' => $baseDir . '/inc/deprecated/classes/class-imagify-assets-deprecated.php',
+ 'Imagify_Attachment' => $baseDir . '/inc/deprecated/classes/class-imagify-attachment.php',
+ 'Imagify_Auto_Optimization' => $baseDir . '/inc/classes/class-imagify-auto-optimization.php',
+ 'Imagify_Auto_Optimization_Deprecated' => $baseDir . '/inc/deprecated/classes/class-imagify-auto-optimization-deprecated.php',
+ 'Imagify_Cron_Library_Size' => $baseDir . '/inc/classes/class-imagify-cron-library-size.php',
+ 'Imagify_Cron_Rating' => $baseDir . '/inc/classes/class-imagify-cron-rating.php',
+ 'Imagify_Cron_Sync_Files' => $baseDir . '/inc/classes/class-imagify-cron-sync-files.php',
+ 'Imagify_Custom_Folders' => $baseDir . '/inc/classes/class-imagify-custom-folders.php',
+ 'Imagify_DB' => $baseDir . '/inc/classes/class-imagify-db.php',
+ 'Imagify_Data' => $baseDir . '/inc/classes/class-imagify-data.php',
+ 'Imagify_Enable_Media_Replace_Deprecated' => $baseDir . '/inc/deprecated/classes/class-imagify-enable-media-replace-deprecated.php',
+ 'Imagify_File_Attachment' => $baseDir . '/inc/deprecated/classes/class-imagify-file-attachment.php',
+ 'Imagify_Files_DB' => $baseDir . '/inc/classes/class-imagify-files-db.php',
+ 'Imagify_Files_Iterator' => $baseDir . '/inc/classes/class-imagify-files-iterator.php',
+ 'Imagify_Files_List_Table' => $baseDir . '/inc/classes/class-imagify-files-list-table.php',
+ 'Imagify_Files_Recursive_Iterator' => $baseDir . '/inc/classes/class-imagify-files-recursive-iterator.php',
+ 'Imagify_Files_Scan' => $baseDir . '/inc/classes/class-imagify-files-scan.php',
+ 'Imagify_Files_Stats' => $baseDir . '/inc/classes/class-imagify-files-stats.php',
+ 'Imagify_Filesystem' => $baseDir . '/inc/classes/class-imagify-filesystem.php',
+ 'Imagify_Folders_DB' => $baseDir . '/inc/classes/class-imagify-folders-db.php',
+ 'Imagify_NGG_Attachment' => $baseDir . '/inc/deprecated/classes/class-imagify-ngg-attachment.php',
+ 'Imagify_NGG_Dynamic_Thumbnails_Background_Process' => $baseDir . '/inc/deprecated/classes/class-imagify-ngg-dynamic-thumbnails-background-process.php',
+ 'Imagify_Notices_Deprecated' => $baseDir . '/inc/deprecated/classes/class-imagify-notices-deprecated.php',
+ 'Imagify_Options' => $baseDir . '/inc/classes/class-imagify-options.php',
+ 'Imagify_Regenerate_Thumbnails_Deprecated' => $baseDir . '/inc/deprecated/classes/class-imagify-regenerate-thumbnails-deprecated.php',
+ 'Imagify_Requirements' => $baseDir . '/inc/classes/class-imagify-requirements.php',
+ 'Imagify_Settings' => $baseDir . '/inc/classes/class-imagify-settings.php',
+ 'Imagify_User' => $baseDir . '/inc/deprecated/classes/class-imagify-user.php',
+ 'Imagify_Views' => $baseDir . '/inc/classes/class-imagify-views.php',
+ 'Imagify_WP_Async_Request' => $baseDir . '/inc/classes/Dependencies/deliciousbrains/wp-background-processing/classes/wp-async-request.php',
+ 'Imagify_WP_Background_Process' => $baseDir . '/inc/classes/Dependencies/deliciousbrains/wp-background-processing/classes/wp-background-process.php',
+);
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/autoload_namespaces.php b/wp/wp-content/plugins/imagify/vendor/composer/autoload_namespaces.php
new file mode 100644
index 00000000..15a2ff3a
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/autoload_namespaces.php
@@ -0,0 +1,9 @@
+ array($baseDir . '/inc/3rd-party/wp-rocket/classes'),
+ 'Imagify\\ThirdParty\\RegenerateThumbnails\\' => array($baseDir . '/inc/3rd-party/regenerate-thumbnails/classes'),
+ 'Imagify\\ThirdParty\\NGG\\' => array($baseDir . '/inc/3rd-party/nextgen-gallery/classes'),
+ 'Imagify\\ThirdParty\\FormidablePro\\' => array($baseDir . '/inc/3rd-party/formidable-pro/classes'),
+ 'Imagify\\ThirdParty\\EnableMediaReplace\\' => array($baseDir . '/inc/3rd-party/enable-media-replace/classes'),
+ 'Imagify\\ThirdParty\\AS3CF\\' => array($baseDir . '/inc/3rd-party/amazon-s3-and-cloudfront/classes'),
+ 'Imagify\\Deprecated\\Traits\\' => array($baseDir . '/inc/deprecated/Traits'),
+ 'Imagify\\' => array($baseDir . '/classes'),
+ 'Dangoodman\\ComposerForWordpress\\' => array($vendorDir . '/dangoodman/composer-for-wordpress'),
+ 'Composer\\Installers\\' => array($vendorDir . '/composer/installers/src/Composer/Installers'),
+);
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/autoload_real.php b/wp/wp-content/plugins/imagify/vendor/composer/autoload_real.php
new file mode 100644
index 00000000..13eb65d1
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/autoload_real.php
@@ -0,0 +1,38 @@
+register(true);
+
+ return $loader;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/autoload_static.php b/wp/wp-content/plugins/imagify/vendor/composer/autoload_static.php
new file mode 100644
index 00000000..a6e63559
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/autoload_static.php
@@ -0,0 +1,136 @@
+
+ array (
+ 'Imagify\\ThirdParty\\WPRocket\\' => 28,
+ 'Imagify\\ThirdParty\\RegenerateThumbnails\\' => 40,
+ 'Imagify\\ThirdParty\\NGG\\' => 23,
+ 'Imagify\\ThirdParty\\FormidablePro\\' => 33,
+ 'Imagify\\ThirdParty\\EnableMediaReplace\\' => 38,
+ 'Imagify\\ThirdParty\\AS3CF\\' => 25,
+ 'Imagify\\Deprecated\\Traits\\' => 26,
+ 'Imagify\\' => 8,
+ ),
+ 'D' =>
+ array (
+ 'Dangoodman\\ComposerForWordpress\\' => 32,
+ ),
+ 'C' =>
+ array (
+ 'Composer\\Installers\\' => 20,
+ ),
+ );
+
+ public static $prefixDirsPsr4 = array (
+ 'Imagify\\ThirdParty\\WPRocket\\' =>
+ array (
+ 0 => __DIR__ . '/../..' . '/inc/3rd-party/wp-rocket/classes',
+ ),
+ 'Imagify\\ThirdParty\\RegenerateThumbnails\\' =>
+ array (
+ 0 => __DIR__ . '/../..' . '/inc/3rd-party/regenerate-thumbnails/classes',
+ ),
+ 'Imagify\\ThirdParty\\NGG\\' =>
+ array (
+ 0 => __DIR__ . '/../..' . '/inc/3rd-party/nextgen-gallery/classes',
+ ),
+ 'Imagify\\ThirdParty\\FormidablePro\\' =>
+ array (
+ 0 => __DIR__ . '/../..' . '/inc/3rd-party/formidable-pro/classes',
+ ),
+ 'Imagify\\ThirdParty\\EnableMediaReplace\\' =>
+ array (
+ 0 => __DIR__ . '/../..' . '/inc/3rd-party/enable-media-replace/classes',
+ ),
+ 'Imagify\\ThirdParty\\AS3CF\\' =>
+ array (
+ 0 => __DIR__ . '/../..' . '/inc/3rd-party/amazon-s3-and-cloudfront/classes',
+ ),
+ 'Imagify\\Deprecated\\Traits\\' =>
+ array (
+ 0 => __DIR__ . '/../..' . '/inc/deprecated/Traits',
+ ),
+ 'Imagify\\' =>
+ array (
+ 0 => __DIR__ . '/../..' . '/classes',
+ ),
+ 'Dangoodman\\ComposerForWordpress\\' =>
+ array (
+ 0 => __DIR__ . '/..' . '/dangoodman/composer-for-wordpress',
+ ),
+ 'Composer\\Installers\\' =>
+ array (
+ 0 => __DIR__ . '/..' . '/composer/installers/src/Composer/Installers',
+ ),
+ );
+
+ public static $classMap = array (
+ 'Composer\\InstalledVersions' => __DIR__ . '/..' . '/composer/InstalledVersions.php',
+ 'Imagify' => __DIR__ . '/../..' . '/inc/classes/class-imagify.php',
+ 'Imagify\\EventManagement\\EventManager' => __DIR__ . '/../..' . '/inc/classes/Dependencies/wp-media/event-manager/EventManager.php',
+ 'Imagify\\EventManagement\\EventManagerAwareSubscriberInterface' => __DIR__ . '/../..' . '/inc/classes/Dependencies/wp-media/event-manager/EventManagerAwareSubscriberInterface.php',
+ 'Imagify\\EventManagement\\SubscriberInterface' => __DIR__ . '/../..' . '/inc/classes/Dependencies/wp-media/event-manager/SubscriberInterface.php',
+ 'Imagify_AS3CF_Attachment' => __DIR__ . '/../..' . '/inc/deprecated/classes/class-imagify-as3cf-attachment.php',
+ 'Imagify_AS3CF_Deprecated' => __DIR__ . '/../..' . '/inc/deprecated/classes/class-imagify-as3cf-deprecated.php',
+ 'Imagify_Abstract_Attachment' => __DIR__ . '/../..' . '/inc/deprecated/classes/class-imagify-abstract-attachment.php',
+ 'Imagify_Abstract_Background_Process' => __DIR__ . '/../..' . '/inc/classes/class-imagify-abstract-background-process.php',
+ 'Imagify_Abstract_Cron' => __DIR__ . '/../..' . '/inc/classes/class-imagify-abstract-cron.php',
+ 'Imagify_Abstract_DB' => __DIR__ . '/../..' . '/inc/classes/class-imagify-abstract-db.php',
+ 'Imagify_Abstract_DB_Deprecated' => __DIR__ . '/../..' . '/inc/deprecated/classes/class-imagify-abstract-db-deprecated.php',
+ 'Imagify_Abstract_Options' => __DIR__ . '/../..' . '/inc/classes/class-imagify-abstract-options.php',
+ 'Imagify_Admin_Ajax_Post' => __DIR__ . '/../..' . '/inc/classes/class-imagify-admin-ajax-post.php',
+ 'Imagify_Admin_Ajax_Post_Deprecated' => __DIR__ . '/../..' . '/inc/deprecated/classes/class-imagify-admin-ajax-post-deprecated.php',
+ 'Imagify_Assets' => __DIR__ . '/../..' . '/inc/classes/class-imagify-assets.php',
+ 'Imagify_Assets_Deprecated' => __DIR__ . '/../..' . '/inc/deprecated/classes/class-imagify-assets-deprecated.php',
+ 'Imagify_Attachment' => __DIR__ . '/../..' . '/inc/deprecated/classes/class-imagify-attachment.php',
+ 'Imagify_Auto_Optimization' => __DIR__ . '/../..' . '/inc/classes/class-imagify-auto-optimization.php',
+ 'Imagify_Auto_Optimization_Deprecated' => __DIR__ . '/../..' . '/inc/deprecated/classes/class-imagify-auto-optimization-deprecated.php',
+ 'Imagify_Cron_Library_Size' => __DIR__ . '/../..' . '/inc/classes/class-imagify-cron-library-size.php',
+ 'Imagify_Cron_Rating' => __DIR__ . '/../..' . '/inc/classes/class-imagify-cron-rating.php',
+ 'Imagify_Cron_Sync_Files' => __DIR__ . '/../..' . '/inc/classes/class-imagify-cron-sync-files.php',
+ 'Imagify_Custom_Folders' => __DIR__ . '/../..' . '/inc/classes/class-imagify-custom-folders.php',
+ 'Imagify_DB' => __DIR__ . '/../..' . '/inc/classes/class-imagify-db.php',
+ 'Imagify_Data' => __DIR__ . '/../..' . '/inc/classes/class-imagify-data.php',
+ 'Imagify_Enable_Media_Replace_Deprecated' => __DIR__ . '/../..' . '/inc/deprecated/classes/class-imagify-enable-media-replace-deprecated.php',
+ 'Imagify_File_Attachment' => __DIR__ . '/../..' . '/inc/deprecated/classes/class-imagify-file-attachment.php',
+ 'Imagify_Files_DB' => __DIR__ . '/../..' . '/inc/classes/class-imagify-files-db.php',
+ 'Imagify_Files_Iterator' => __DIR__ . '/../..' . '/inc/classes/class-imagify-files-iterator.php',
+ 'Imagify_Files_List_Table' => __DIR__ . '/../..' . '/inc/classes/class-imagify-files-list-table.php',
+ 'Imagify_Files_Recursive_Iterator' => __DIR__ . '/../..' . '/inc/classes/class-imagify-files-recursive-iterator.php',
+ 'Imagify_Files_Scan' => __DIR__ . '/../..' . '/inc/classes/class-imagify-files-scan.php',
+ 'Imagify_Files_Stats' => __DIR__ . '/../..' . '/inc/classes/class-imagify-files-stats.php',
+ 'Imagify_Filesystem' => __DIR__ . '/../..' . '/inc/classes/class-imagify-filesystem.php',
+ 'Imagify_Folders_DB' => __DIR__ . '/../..' . '/inc/classes/class-imagify-folders-db.php',
+ 'Imagify_NGG_Attachment' => __DIR__ . '/../..' . '/inc/deprecated/classes/class-imagify-ngg-attachment.php',
+ 'Imagify_NGG_Dynamic_Thumbnails_Background_Process' => __DIR__ . '/../..' . '/inc/deprecated/classes/class-imagify-ngg-dynamic-thumbnails-background-process.php',
+ 'Imagify_Notices_Deprecated' => __DIR__ . '/../..' . '/inc/deprecated/classes/class-imagify-notices-deprecated.php',
+ 'Imagify_Options' => __DIR__ . '/../..' . '/inc/classes/class-imagify-options.php',
+ 'Imagify_Regenerate_Thumbnails_Deprecated' => __DIR__ . '/../..' . '/inc/deprecated/classes/class-imagify-regenerate-thumbnails-deprecated.php',
+ 'Imagify_Requirements' => __DIR__ . '/../..' . '/inc/classes/class-imagify-requirements.php',
+ 'Imagify_Settings' => __DIR__ . '/../..' . '/inc/classes/class-imagify-settings.php',
+ 'Imagify_User' => __DIR__ . '/../..' . '/inc/deprecated/classes/class-imagify-user.php',
+ 'Imagify_Views' => __DIR__ . '/../..' . '/inc/classes/class-imagify-views.php',
+ 'Imagify_WP_Async_Request' => __DIR__ . '/../..' . '/inc/classes/Dependencies/deliciousbrains/wp-background-processing/classes/wp-async-request.php',
+ 'Imagify_WP_Background_Process' => __DIR__ . '/../..' . '/inc/classes/Dependencies/deliciousbrains/wp-background-processing/classes/wp-background-process.php',
+ );
+
+ public static function getInitializer(ClassLoaderWPMediaImagifyWordPressPlugin $loader)
+ {
+ return \Closure::bind(function () use ($loader) {
+ $loader->prefixLengthsPsr4 = ComposerStaticInit0382efa3332217fe0a96bbbe57e91464::$prefixLengthsPsr4;
+ $loader->prefixDirsPsr4 = ComposerStaticInit0382efa3332217fe0a96bbbe57e91464::$prefixDirsPsr4;
+ $loader->classMap = ComposerStaticInit0382efa3332217fe0a96bbbe57e91464::$classMap;
+
+ }, null, ClassLoaderWPMediaImagifyWordPressPlugin::class);
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installed.json b/wp/wp-content/plugins/imagify/vendor/composer/installed.json
new file mode 100644
index 00000000..09e33352
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installed.json
@@ -0,0 +1,193 @@
+{
+ "packages": [
+ {
+ "name": "composer/installers",
+ "version": "v2.2.0",
+ "version_normalized": "2.2.0.0",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/composer/installers.git",
+ "reference": "c29dc4b93137acb82734f672c37e029dfbd95b35"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/composer/installers/zipball/c29dc4b93137acb82734f672c37e029dfbd95b35",
+ "reference": "c29dc4b93137acb82734f672c37e029dfbd95b35",
+ "shasum": ""
+ },
+ "require": {
+ "composer-plugin-api": "^1.0 || ^2.0",
+ "php": "^7.2 || ^8.0"
+ },
+ "require-dev": {
+ "composer/composer": "1.6.* || ^2.0",
+ "composer/semver": "^1 || ^3",
+ "phpstan/phpstan": "^0.12.55",
+ "phpstan/phpstan-phpunit": "^0.12.16",
+ "symfony/phpunit-bridge": "^5.3",
+ "symfony/process": "^5"
+ },
+ "time": "2022-08-20T06:45:11+00:00",
+ "type": "composer-plugin",
+ "extra": {
+ "class": "Composer\\Installers\\Plugin",
+ "branch-alias": {
+ "dev-main": "2.x-dev"
+ },
+ "plugin-modifies-install-path": true
+ },
+ "installation-source": "dist",
+ "autoload": {
+ "psr-4": {
+ "Composer\\Installers\\": "src/Composer/Installers"
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Kyle Robinson Young",
+ "email": "kyle@dontkry.com",
+ "homepage": "https://github.com/shama"
+ }
+ ],
+ "description": "A multi-framework Composer library installer",
+ "homepage": "https://composer.github.io/installers/",
+ "keywords": [
+ "Dolibarr",
+ "Eliasis",
+ "Hurad",
+ "ImageCMS",
+ "Kanboard",
+ "Lan Management System",
+ "MODX Evo",
+ "MantisBT",
+ "Mautic",
+ "Maya",
+ "OXID",
+ "Plentymarkets",
+ "Porto",
+ "RadPHP",
+ "SMF",
+ "Starbug",
+ "Thelia",
+ "Whmcs",
+ "WolfCMS",
+ "agl",
+ "annotatecms",
+ "attogram",
+ "bitrix",
+ "cakephp",
+ "chef",
+ "cockpit",
+ "codeigniter",
+ "concrete5",
+ "croogo",
+ "dokuwiki",
+ "drupal",
+ "eZ Platform",
+ "elgg",
+ "expressionengine",
+ "fuelphp",
+ "grav",
+ "installer",
+ "itop",
+ "known",
+ "kohana",
+ "laravel",
+ "lavalite",
+ "lithium",
+ "magento",
+ "majima",
+ "mako",
+ "matomo",
+ "mediawiki",
+ "miaoxing",
+ "modulework",
+ "modx",
+ "moodle",
+ "osclass",
+ "pantheon",
+ "phpbb",
+ "piwik",
+ "ppi",
+ "processwire",
+ "puppet",
+ "pxcms",
+ "reindex",
+ "roundcube",
+ "shopware",
+ "silverstripe",
+ "sydes",
+ "sylius",
+ "tastyigniter",
+ "wordpress",
+ "yawik",
+ "zend",
+ "zikula"
+ ],
+ "support": {
+ "issues": "https://github.com/composer/installers/issues",
+ "source": "https://github.com/composer/installers/tree/v2.2.0"
+ },
+ "funding": [
+ {
+ "url": "https://packagist.com",
+ "type": "custom"
+ },
+ {
+ "url": "https://github.com/composer",
+ "type": "github"
+ },
+ {
+ "url": "https://tidelift.com/funding/github/packagist/composer/composer",
+ "type": "tidelift"
+ }
+ ],
+ "install-path": "./installers"
+ },
+ {
+ "name": "dangoodman/composer-for-wordpress",
+ "version": "2.0.2",
+ "version_normalized": "2.0.2.0",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/dangoodman/composer-for-wordpress.git",
+ "reference": "cc5b3d0a1122d87d60f378071159bac0dbd93daa"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/dangoodman/composer-for-wordpress/zipball/cc5b3d0a1122d87d60f378071159bac0dbd93daa",
+ "reference": "cc5b3d0a1122d87d60f378071159bac0dbd93daa",
+ "shasum": ""
+ },
+ "require": {
+ "composer-plugin-api": "^1.0 || ^2.0"
+ },
+ "time": "2020-11-16T19:32:10+00:00",
+ "type": "composer-plugin",
+ "extra": {
+ "class": "Dangoodman\\ComposerForWordpress\\ComposerForWordpress"
+ },
+ "installation-source": "dist",
+ "autoload": {
+ "psr-4": {
+ "Dangoodman\\ComposerForWordpress\\": "."
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "support": {
+ "issues": "https://github.com/dangoodman/composer-for-wordpress/issues",
+ "source": "https://github.com/dangoodman/composer-for-wordpress/tree/2.0.2"
+ },
+ "install-path": "../dangoodman/composer-for-wordpress"
+ }
+ ],
+ "dev": false,
+ "dev-package-names": []
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installed.php b/wp/wp-content/plugins/imagify/vendor/composer/installed.php
new file mode 100644
index 00000000..b3922c3a
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installed.php
@@ -0,0 +1,41 @@
+ array(
+ 'name' => 'wp-media/imagify-plugin',
+ 'pretty_version' => 'v2.2.2',
+ 'version' => '2.2.2.0',
+ 'reference' => '33e23dd026fd905ae6ae703be9456c84ae9ca591',
+ 'type' => 'wordpress-plugin',
+ 'install_path' => __DIR__ . '/../../',
+ 'aliases' => array(),
+ 'dev' => false,
+ ),
+ 'versions' => array(
+ 'composer/installers' => array(
+ 'pretty_version' => 'v2.2.0',
+ 'version' => '2.2.0.0',
+ 'reference' => 'c29dc4b93137acb82734f672c37e029dfbd95b35',
+ 'type' => 'composer-plugin',
+ 'install_path' => __DIR__ . '/./installers',
+ 'aliases' => array(),
+ 'dev_requirement' => false,
+ ),
+ 'dangoodman/composer-for-wordpress' => array(
+ 'pretty_version' => '2.0.2',
+ 'version' => '2.0.2.0',
+ 'reference' => 'cc5b3d0a1122d87d60f378071159bac0dbd93daa',
+ 'type' => 'composer-plugin',
+ 'install_path' => __DIR__ . '/../dangoodman/composer-for-wordpress',
+ 'aliases' => array(),
+ 'dev_requirement' => false,
+ ),
+ 'wp-media/imagify-plugin' => array(
+ 'pretty_version' => 'v2.2.2',
+ 'version' => '2.2.2.0',
+ 'reference' => '33e23dd026fd905ae6ae703be9456c84ae9ca591',
+ 'type' => 'wordpress-plugin',
+ 'install_path' => __DIR__ . '/../../',
+ 'aliases' => array(),
+ 'dev_requirement' => false,
+ ),
+ ),
+);
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/.github/workflows/continuous-integration.yml b/wp/wp-content/plugins/imagify/vendor/composer/installers/.github/workflows/continuous-integration.yml
new file mode 100644
index 00000000..03782570
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/.github/workflows/continuous-integration.yml
@@ -0,0 +1,62 @@
+name: "Continuous Integration"
+
+on:
+ - push
+ - pull_request
+
+env:
+ COMPOSER_FLAGS: "--ansi --no-interaction --no-progress --prefer-dist"
+ SYMFONY_PHPUNIT_REMOVE_RETURN_TYPEHINT: "1"
+
+jobs:
+ tests:
+ name: "CI"
+
+ runs-on: ubuntu-latest
+
+ strategy:
+ matrix:
+ php-version:
+ - "7.2"
+ - "7.3"
+ - "7.4"
+ - "8.0"
+ - "8.1"
+ dependencies: [locked]
+ include:
+ - php-version: "7.2"
+ dependencies: lowest
+ - php-version: "8.1"
+ dependencies: lowest
+
+ steps:
+ - name: "Checkout"
+ uses: "actions/checkout@v2"
+
+ - name: "Install PHP"
+ uses: "shivammathur/setup-php@v2"
+ with:
+ coverage: "none"
+ php-version: "${{ matrix.php-version }}"
+ tools: composer:snapshot
+
+ - name: Get composer cache directory
+ id: composercache
+ run: echo "::set-output name=dir::$(composer config cache-files-dir)"
+
+ - name: Cache dependencies
+ uses: actions/cache@v2
+ with:
+ path: ${{ steps.composercache.outputs.dir }}
+ key: ${{ runner.os }}-composer-${{ hashFiles('**/composer.json') }}
+ restore-keys: ${{ runner.os }}-composer-
+
+ - name: "Handle lowest dependencies update"
+ if: "contains(matrix.dependencies, 'lowest')"
+ run: "echo \"COMPOSER_FLAGS=$COMPOSER_FLAGS --prefer-lowest\" >> $GITHUB_ENV"
+
+ - name: "Install latest dependencies"
+ run: "composer update ${{ env.COMPOSER_FLAGS }}"
+
+ - name: "Run tests"
+ run: "vendor/bin/simple-phpunit --verbose"
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/.github/workflows/lint.yml b/wp/wp-content/plugins/imagify/vendor/composer/installers/.github/workflows/lint.yml
new file mode 100644
index 00000000..843ac352
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/.github/workflows/lint.yml
@@ -0,0 +1,30 @@
+name: "PHP Lint"
+
+on:
+ - push
+ - pull_request
+
+jobs:
+ tests:
+ name: "Lint"
+
+ runs-on: ubuntu-latest
+
+ strategy:
+ matrix:
+ php-version:
+ - "7.2"
+ - "latest"
+
+ steps:
+ - name: "Checkout"
+ uses: "actions/checkout@v2"
+
+ - name: "Install PHP"
+ uses: "shivammathur/setup-php@v2"
+ with:
+ coverage: "none"
+ php-version: "${{ matrix.php-version }}"
+
+ - name: "Lint PHP files"
+ run: "find src/ -type f -name '*.php' -print0 | xargs -0 -L1 -P4 -- php -l -f"
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/.github/workflows/phpstan.yml b/wp/wp-content/plugins/imagify/vendor/composer/installers/.github/workflows/phpstan.yml
new file mode 100644
index 00000000..559fae1d
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/.github/workflows/phpstan.yml
@@ -0,0 +1,49 @@
+name: "PHPStan"
+
+on:
+ - push
+ - pull_request
+
+env:
+ COMPOSER_FLAGS: "--ansi --no-interaction --no-progress --prefer-dist"
+ SYMFONY_PHPUNIT_VERSION: ""
+
+jobs:
+ tests:
+ name: "PHPStan"
+
+ runs-on: ubuntu-latest
+
+ strategy:
+ matrix:
+ php-version:
+ - "8.0"
+
+ steps:
+ - name: "Checkout"
+ uses: "actions/checkout@v2"
+
+ - name: "Install PHP"
+ uses: "shivammathur/setup-php@v2"
+ with:
+ coverage: "none"
+ php-version: "${{ matrix.php-version }}"
+
+ - name: Get composer cache directory
+ id: composercache
+ run: echo "::set-output name=dir::$(composer config cache-files-dir)"
+
+ - name: Cache dependencies
+ uses: actions/cache@v2
+ with:
+ path: ${{ steps.composercache.outputs.dir }}
+ key: ${{ runner.os }}-composer-${{ hashFiles('**/composer.json') }}
+ restore-keys: ${{ runner.os }}-composer-
+
+ - name: "Install latest dependencies"
+ run: "composer update ${{ env.COMPOSER_FLAGS }}"
+
+ - name: Run PHPStan
+ run: |
+ composer require --dev phpunit/phpunit:^8.5.18 --with-all-dependencies ${{ env.COMPOSER_FLAGS }}
+ vendor/bin/phpstan analyse
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/LICENSE b/wp/wp-content/plugins/imagify/vendor/composer/installers/LICENSE
new file mode 100644
index 00000000..85f97fc7
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/LICENSE
@@ -0,0 +1,19 @@
+Copyright (c) 2012 Kyle Robinson Young
+
+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.
\ No newline at end of file
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/composer.json b/wp/wp-content/plugins/imagify/vendor/composer/installers/composer.json
new file mode 100644
index 00000000..5745d3bc
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/composer.json
@@ -0,0 +1,116 @@
+{
+ "name": "composer/installers",
+ "type": "composer-plugin",
+ "license": "MIT",
+ "description": "A multi-framework Composer library installer",
+ "keywords": [
+ "installer",
+ "AGL",
+ "AnnotateCms",
+ "Attogram",
+ "Bitrix",
+ "CakePHP",
+ "Chef",
+ "Cockpit",
+ "CodeIgniter",
+ "concrete5",
+ "Croogo",
+ "DokuWiki",
+ "Dolibarr",
+ "Drupal",
+ "Elgg",
+ "Eliasis",
+ "ExpressionEngine",
+ "eZ Platform",
+ "FuelPHP",
+ "Grav",
+ "Hurad",
+ "ImageCMS",
+ "iTop",
+ "Kanboard",
+ "Known",
+ "Kohana",
+ "Lan Management System",
+ "Laravel",
+ "Lavalite",
+ "Lithium",
+ "Magento",
+ "majima",
+ "Mako",
+ "MantisBT",
+ "Matomo",
+ "Mautic",
+ "Maya",
+ "MODX",
+ "MODX Evo",
+ "MediaWiki",
+ "Miaoxing",
+ "OXID",
+ "osclass",
+ "MODULEWork",
+ "Moodle",
+ "Pantheon",
+ "Piwik",
+ "pxcms",
+ "phpBB",
+ "Plentymarkets",
+ "PPI",
+ "Puppet",
+ "Porto",
+ "ProcessWire",
+ "RadPHP",
+ "ReIndex",
+ "Roundcube",
+ "shopware",
+ "SilverStripe",
+ "SMF",
+ "Starbug",
+ "SyDES",
+ "Sylius",
+ "TastyIgniter",
+ "Thelia",
+ "WHMCS",
+ "WolfCMS",
+ "WordPress",
+ "YAWIK",
+ "Zend",
+ "Zikula"
+ ],
+ "homepage": "https://composer.github.io/installers/",
+ "authors": [
+ {
+ "name": "Kyle Robinson Young",
+ "email": "kyle@dontkry.com",
+ "homepage": "https://github.com/shama"
+ }
+ ],
+ "autoload": {
+ "psr-4": { "Composer\\Installers\\": "src/Composer/Installers" }
+ },
+ "autoload-dev": {
+ "psr-4": { "Composer\\Installers\\Test\\": "tests/Composer/Installers/Test" }
+ },
+ "extra": {
+ "class": "Composer\\Installers\\Plugin",
+ "branch-alias": {
+ "dev-main": "2.x-dev"
+ },
+ "plugin-modifies-install-path": true
+ },
+ "require": {
+ "php": "^7.2 || ^8.0",
+ "composer-plugin-api": "^1.0 || ^2.0"
+ },
+ "require-dev": {
+ "composer/composer": "1.6.* || ^2.0",
+ "composer/semver": "^1 || ^3",
+ "symfony/phpunit-bridge": "^5.3",
+ "phpstan/phpstan": "^0.12.55",
+ "symfony/process": "^5",
+ "phpstan/phpstan-phpunit": "^0.12.16"
+ },
+ "scripts": {
+ "test": "vendor/bin/simple-phpunit",
+ "phpstan": "vendor/bin/phpstan analyse"
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/phpstan.neon.dist b/wp/wp-content/plugins/imagify/vendor/composer/installers/phpstan.neon.dist
new file mode 100644
index 00000000..b15782ac
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/phpstan.neon.dist
@@ -0,0 +1,12 @@
+parameters:
+ level: 8
+ paths:
+ - src
+ - tests
+ excludes_analyse:
+ - tests/Composer/Installers/Test/PolyfillTestCase.php
+ ignoreErrors:
+ - '~Test::[a-zA-Z0-9]+Provider\(\) return type~'
+
+includes:
+ - vendor/phpstan/phpstan-phpunit/extension.neon
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/AglInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/AglInstaller.php
new file mode 100644
index 00000000..b0996a6a
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/AglInstaller.php
@@ -0,0 +1,29 @@
+ */
+ protected $locations = array(
+ 'module' => 'More/{$name}/',
+ );
+
+ /**
+ * Format package name to CamelCase
+ */
+ public function inflectPackageVars(array $vars): array
+ {
+ $name = preg_replace_callback('/(?:^|_|-)(.?)/', function ($matches) {
+ return strtoupper($matches[1]);
+ }, $vars['name']);
+
+ if (null === $name) {
+ throw new \RuntimeException('Failed to run preg_replace_callback: '.preg_last_error());
+ }
+
+ $vars['name'] = $name;
+
+ return $vars;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/AkauntingInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/AkauntingInstaller.php
new file mode 100644
index 00000000..c504c70f
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/AkauntingInstaller.php
@@ -0,0 +1,23 @@
+ */
+ protected $locations = array(
+ 'module' => 'modules/{$name}',
+ );
+
+ /**
+ * Format package name to CamelCase
+ */
+ public function inflectPackageVars(array $vars): array
+ {
+ $vars['name'] = strtolower($this->pregReplace('/(?<=\\w)([A-Z])/', '_\\1', $vars['name']));
+ $vars['name'] = str_replace(array('-', '_'), ' ', $vars['name']);
+ $vars['name'] = str_replace(' ', '', ucwords($vars['name']));
+
+ return $vars;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/AnnotateCmsInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/AnnotateCmsInstaller.php
new file mode 100644
index 00000000..58a0f666
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/AnnotateCmsInstaller.php
@@ -0,0 +1,13 @@
+ */
+ protected $locations = array(
+ 'module' => 'addons/modules/{$name}/',
+ 'component' => 'addons/components/{$name}/',
+ 'service' => 'addons/services/{$name}/',
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/AsgardInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/AsgardInstaller.php
new file mode 100644
index 00000000..f01b3991
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/AsgardInstaller.php
@@ -0,0 +1,58 @@
+ */
+ protected $locations = array(
+ 'module' => 'Modules/{$name}/',
+ 'theme' => 'Themes/{$name}/'
+ );
+
+ /**
+ * Format package name.
+ *
+ * For package type asgard-module, cut off a trailing '-plugin' if present.
+ *
+ * For package type asgard-theme, cut off a trailing '-theme' if present.
+ */
+ public function inflectPackageVars(array $vars): array
+ {
+ if ($vars['type'] === 'asgard-module') {
+ return $this->inflectPluginVars($vars);
+ }
+
+ if ($vars['type'] === 'asgard-theme') {
+ return $this->inflectThemeVars($vars);
+ }
+
+ return $vars;
+ }
+
+ /**
+ * @param array $vars
+ * @return array
+ */
+ protected function inflectPluginVars(array $vars): array
+ {
+ $vars['name'] = $this->pregReplace('/-module$/', '', $vars['name']);
+ $vars['name'] = str_replace(array('-', '_'), ' ', $vars['name']);
+ $vars['name'] = str_replace(' ', '', ucwords($vars['name']));
+
+ return $vars;
+ }
+
+ /**
+ * @param array $vars
+ * @return array
+ */
+ protected function inflectThemeVars(array $vars): array
+ {
+ $vars['name'] = $this->pregReplace('/-theme$/', '', $vars['name']);
+ $vars['name'] = str_replace(array('-', '_'), ' ', $vars['name']);
+ $vars['name'] = str_replace(' ', '', ucwords($vars['name']));
+
+ return $vars;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/AttogramInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/AttogramInstaller.php
new file mode 100644
index 00000000..bd7dd8d7
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/AttogramInstaller.php
@@ -0,0 +1,11 @@
+ */
+ protected $locations = array(
+ 'module' => 'modules/{$name}/',
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/BaseInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/BaseInstaller.php
new file mode 100644
index 00000000..663ec2af
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/BaseInstaller.php
@@ -0,0 +1,137 @@
+ */
+ protected $locations = array();
+ /** @var Composer */
+ protected $composer;
+ /** @var PackageInterface */
+ protected $package;
+ /** @var IOInterface */
+ protected $io;
+
+ /**
+ * Initializes base installer.
+ */
+ public function __construct(PackageInterface $package, Composer $composer, IOInterface $io)
+ {
+ $this->composer = $composer;
+ $this->package = $package;
+ $this->io = $io;
+ }
+
+ /**
+ * Return the install path based on package type.
+ */
+ public function getInstallPath(PackageInterface $package, string $frameworkType = ''): string
+ {
+ $type = $this->package->getType();
+
+ $prettyName = $this->package->getPrettyName();
+ if (strpos($prettyName, '/') !== false) {
+ list($vendor, $name) = explode('/', $prettyName);
+ } else {
+ $vendor = '';
+ $name = $prettyName;
+ }
+
+ $availableVars = $this->inflectPackageVars(compact('name', 'vendor', 'type'));
+
+ $extra = $package->getExtra();
+ if (!empty($extra['installer-name'])) {
+ $availableVars['name'] = $extra['installer-name'];
+ }
+
+ $extra = $this->composer->getPackage()->getExtra();
+ if (!empty($extra['installer-paths'])) {
+ $customPath = $this->mapCustomInstallPaths($extra['installer-paths'], $prettyName, $type, $vendor);
+ if ($customPath !== false) {
+ return $this->templatePath($customPath, $availableVars);
+ }
+ }
+
+ $packageType = substr($type, strlen($frameworkType) + 1);
+ $locations = $this->getLocations($frameworkType);
+ if (!isset($locations[$packageType])) {
+ throw new \InvalidArgumentException(sprintf('Package type "%s" is not supported', $type));
+ }
+
+ return $this->templatePath($locations[$packageType], $availableVars);
+ }
+
+ /**
+ * For an installer to override to modify the vars per installer.
+ *
+ * @param array $vars This will normally receive array{name: string, vendor: string, type: string}
+ * @return array
+ */
+ public function inflectPackageVars(array $vars): array
+ {
+ return $vars;
+ }
+
+ /**
+ * Gets the installer's locations
+ *
+ * @return array map of package types => install path
+ */
+ public function getLocations(string $frameworkType)
+ {
+ return $this->locations;
+ }
+
+ /**
+ * Replace vars in a path
+ *
+ * @param array $vars
+ */
+ protected function templatePath(string $path, array $vars = array()): string
+ {
+ if (strpos($path, '{') !== false) {
+ extract($vars);
+ preg_match_all('@\{\$([A-Za-z0-9_]*)\}@i', $path, $matches);
+ if (!empty($matches[1])) {
+ foreach ($matches[1] as $var) {
+ $path = str_replace('{$' . $var . '}', $$var, $path);
+ }
+ }
+ }
+
+ return $path;
+ }
+
+ /**
+ * Search through a passed paths array for a custom install path.
+ *
+ * @param array $paths
+ * @return string|false
+ */
+ protected function mapCustomInstallPaths(array $paths, string $name, string $type, ?string $vendor = null)
+ {
+ foreach ($paths as $path => $names) {
+ $names = (array) $names;
+ if (in_array($name, $names) || in_array('type:' . $type, $names) || in_array('vendor:' . $vendor, $names)) {
+ return $path;
+ }
+ }
+
+ return false;
+ }
+
+ protected function pregReplace(string $pattern, string $replacement, string $subject): string
+ {
+ $result = preg_replace($pattern, $replacement, $subject);
+ if (null === $result) {
+ throw new \RuntimeException('Failed to run preg_replace with '.$pattern.': '.preg_last_error());
+ }
+
+ return $result;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/BitrixInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/BitrixInstaller.php
new file mode 100644
index 00000000..705ecb4f
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/BitrixInstaller.php
@@ -0,0 +1,123 @@
+.`.
+ * - `bitrix-d7-component` — copy the component to directory `bitrix/components//`.
+ * - `bitrix-d7-template` — copy the template to directory `bitrix/templates/_`.
+ *
+ * You can set custom path to directory with Bitrix kernel in `composer.json`:
+ *
+ * ```json
+ * {
+ * "extra": {
+ * "bitrix-dir": "s1/bitrix"
+ * }
+ * }
+ * ```
+ *
+ * @author Nik Samokhvalov
+ * @author Denis Kulichkin
+ */
+class BitrixInstaller extends BaseInstaller
+{
+ /** @var array */
+ protected $locations = array(
+ 'module' => '{$bitrix_dir}/modules/{$name}/', // deprecated, remove on the major release (Backward compatibility will be broken)
+ 'component' => '{$bitrix_dir}/components/{$name}/', // deprecated, remove on the major release (Backward compatibility will be broken)
+ 'theme' => '{$bitrix_dir}/templates/{$name}/', // deprecated, remove on the major release (Backward compatibility will be broken)
+ 'd7-module' => '{$bitrix_dir}/modules/{$vendor}.{$name}/',
+ 'd7-component' => '{$bitrix_dir}/components/{$vendor}/{$name}/',
+ 'd7-template' => '{$bitrix_dir}/templates/{$vendor}_{$name}/',
+ );
+
+ /**
+ * @var string[] Storage for informations about duplicates at all the time of installation packages.
+ */
+ private static $checkedDuplicates = array();
+
+ public function inflectPackageVars(array $vars): array
+ {
+ /** @phpstan-ignore-next-line */
+ if ($this->composer->getPackage()) {
+ $extra = $this->composer->getPackage()->getExtra();
+
+ if (isset($extra['bitrix-dir'])) {
+ $vars['bitrix_dir'] = $extra['bitrix-dir'];
+ }
+ }
+
+ if (!isset($vars['bitrix_dir'])) {
+ $vars['bitrix_dir'] = 'bitrix';
+ }
+
+ return parent::inflectPackageVars($vars);
+ }
+
+ /**
+ * {@inheritdoc}
+ */
+ protected function templatePath(string $path, array $vars = array()): string
+ {
+ $templatePath = parent::templatePath($path, $vars);
+ $this->checkDuplicates($templatePath, $vars);
+
+ return $templatePath;
+ }
+
+ /**
+ * Duplicates search packages.
+ *
+ * @param array $vars
+ */
+ protected function checkDuplicates(string $path, array $vars = array()): void
+ {
+ $packageType = substr($vars['type'], strlen('bitrix') + 1);
+ $localDir = explode('/', $vars['bitrix_dir']);
+ array_pop($localDir);
+ $localDir[] = 'local';
+ $localDir = implode('/', $localDir);
+
+ $oldPath = str_replace(
+ array('{$bitrix_dir}', '{$name}'),
+ array($localDir, $vars['name']),
+ $this->locations[$packageType]
+ );
+
+ if (in_array($oldPath, static::$checkedDuplicates)) {
+ return;
+ }
+
+ if ($oldPath !== $path && file_exists($oldPath) && $this->io->isInteractive()) {
+ $this->io->writeError(' Duplication of packages: ');
+ $this->io->writeError(' Package ' . $oldPath . ' will be called instead package ' . $path . ' ');
+
+ while (true) {
+ switch ($this->io->ask(' Delete ' . $oldPath . ' [y,n,?]? ', '?')) {
+ case 'y':
+ $fs = new Filesystem();
+ $fs->removeDirectory($oldPath);
+ break 2;
+
+ case 'n':
+ break 2;
+
+ case '?':
+ default:
+ $this->io->writeError(array(
+ ' y - delete package ' . $oldPath . ' and to continue with the installation',
+ ' n - don\'t delete and to continue with the installation',
+ ));
+ $this->io->writeError(' ? - print help');
+ break;
+ }
+ }
+ }
+
+ static::$checkedDuplicates[] = $oldPath;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/BonefishInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/BonefishInstaller.php
new file mode 100644
index 00000000..ab022d99
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/BonefishInstaller.php
@@ -0,0 +1,11 @@
+ */
+ protected $locations = array(
+ 'package' => 'Packages/{$vendor}/{$name}/'
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/CakePHPInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/CakePHPInstaller.php
new file mode 100644
index 00000000..df45895b
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/CakePHPInstaller.php
@@ -0,0 +1,67 @@
+ */
+ protected $locations = array(
+ 'plugin' => 'Plugin/{$name}/',
+ );
+
+ /**
+ * Format package name to CamelCase
+ */
+ public function inflectPackageVars(array $vars): array
+ {
+ if ($this->matchesCakeVersion('>=', '3.0.0')) {
+ return $vars;
+ }
+
+ $nameParts = explode('/', $vars['name']);
+ foreach ($nameParts as &$value) {
+ $value = strtolower($this->pregReplace('/(?<=\\w)([A-Z])/', '_\\1', $value));
+ $value = str_replace(array('-', '_'), ' ', $value);
+ $value = str_replace(' ', '', ucwords($value));
+ }
+ $vars['name'] = implode('/', $nameParts);
+
+ return $vars;
+ }
+
+ /**
+ * Change the default plugin location when cakephp >= 3.0
+ */
+ public function getLocations(string $frameworkType): array
+ {
+ if ($this->matchesCakeVersion('>=', '3.0.0')) {
+ $this->locations['plugin'] = $this->composer->getConfig()->get('vendor-dir') . '/{$vendor}/{$name}/';
+ }
+ return $this->locations;
+ }
+
+ /**
+ * Check if CakePHP version matches against a version
+ *
+ * @phpstan-param Constraint::STR_OP_* $matcher
+ */
+ protected function matchesCakeVersion(string $matcher, string $version): bool
+ {
+ $repositoryManager = $this->composer->getRepositoryManager();
+ /** @phpstan-ignore-next-line */
+ if (!$repositoryManager) {
+ return false;
+ }
+
+ $repos = $repositoryManager->getLocalRepository();
+ /** @phpstan-ignore-next-line */
+ if (!$repos) {
+ return false;
+ }
+
+ return $repos->findPackage('cakephp/cakephp', new Constraint($matcher, $version)) !== null;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/ChefInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/ChefInstaller.php
new file mode 100644
index 00000000..b0d3c5f7
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/ChefInstaller.php
@@ -0,0 +1,12 @@
+ */
+ protected $locations = array(
+ 'cookbook' => 'Chef/{$vendor}/{$name}/',
+ 'role' => 'Chef/roles/{$name}/',
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/CiviCrmInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/CiviCrmInstaller.php
new file mode 100644
index 00000000..1c52e0cd
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/CiviCrmInstaller.php
@@ -0,0 +1,11 @@
+ */
+ protected $locations = array(
+ 'ext' => 'ext/{$name}/'
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/ClanCatsFrameworkInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/ClanCatsFrameworkInstaller.php
new file mode 100644
index 00000000..2c943b21
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/ClanCatsFrameworkInstaller.php
@@ -0,0 +1,12 @@
+ */
+ protected $locations = array(
+ 'ship' => 'CCF/orbit/{$name}/',
+ 'theme' => 'CCF/app/themes/{$name}/',
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/CockpitInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/CockpitInstaller.php
new file mode 100644
index 00000000..d3fcdf7d
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/CockpitInstaller.php
@@ -0,0 +1,36 @@
+ */
+ protected $locations = array(
+ 'module' => 'cockpit/modules/addons/{$name}/',
+ );
+
+ /**
+ * Format module name.
+ *
+ * Strip `module-` prefix from package name.
+ */
+ public function inflectPackageVars(array $vars): array
+ {
+ if ($vars['type'] == 'cockpit-module') {
+ return $this->inflectModuleVars($vars);
+ }
+
+ return $vars;
+ }
+
+ /**
+ * @param array $vars
+ * @return array
+ */
+ public function inflectModuleVars(array $vars): array
+ {
+ $vars['name'] = ucfirst($this->pregReplace('/cockpit-/i', '', $vars['name']));
+
+ return $vars;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/CodeIgniterInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/CodeIgniterInstaller.php
new file mode 100644
index 00000000..a183e078
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/CodeIgniterInstaller.php
@@ -0,0 +1,13 @@
+ */
+ protected $locations = array(
+ 'library' => 'application/libraries/{$name}/',
+ 'third-party' => 'application/third_party/{$name}/',
+ 'module' => 'application/modules/{$name}/',
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/Concrete5Installer.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/Concrete5Installer.php
new file mode 100644
index 00000000..2f5fecb3
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/Concrete5Installer.php
@@ -0,0 +1,15 @@
+ */
+ protected $locations = array(
+ 'core' => 'concrete/',
+ 'block' => 'application/blocks/{$name}/',
+ 'package' => 'packages/{$name}/',
+ 'theme' => 'application/themes/{$name}/',
+ 'update' => 'updates/{$name}/',
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/CroogoInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/CroogoInstaller.php
new file mode 100644
index 00000000..31d4939b
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/CroogoInstaller.php
@@ -0,0 +1,23 @@
+ */
+ protected $locations = array(
+ 'plugin' => 'Plugin/{$name}/',
+ 'theme' => 'View/Themed/{$name}/',
+ );
+
+ /**
+ * Format package name to CamelCase
+ */
+ public function inflectPackageVars(array $vars): array
+ {
+ $vars['name'] = strtolower(str_replace(array('-', '_'), ' ', $vars['name']));
+ $vars['name'] = str_replace(' ', '', ucwords($vars['name']));
+
+ return $vars;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/DecibelInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/DecibelInstaller.php
new file mode 100644
index 00000000..88f53f73
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/DecibelInstaller.php
@@ -0,0 +1,12 @@
+ */
+ protected $locations = array(
+ 'app' => 'app/{$name}/',
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/DframeInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/DframeInstaller.php
new file mode 100644
index 00000000..196f60ef
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/DframeInstaller.php
@@ -0,0 +1,11 @@
+ */
+ protected $locations = array(
+ 'module' => 'modules/{$vendor}/{$name}/',
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/DokuWikiInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/DokuWikiInstaller.php
new file mode 100644
index 00000000..aa3a2e60
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/DokuWikiInstaller.php
@@ -0,0 +1,57 @@
+ */
+ protected $locations = array(
+ 'plugin' => 'lib/plugins/{$name}/',
+ 'template' => 'lib/tpl/{$name}/',
+ );
+
+ /**
+ * Format package name.
+ *
+ * For package type dokuwiki-plugin, cut off a trailing '-plugin',
+ * or leading dokuwiki_ if present.
+ *
+ * For package type dokuwiki-template, cut off a trailing '-template' if present.
+ */
+ public function inflectPackageVars(array $vars): array
+ {
+ if ($vars['type'] === 'dokuwiki-plugin') {
+ return $this->inflectPluginVars($vars);
+ }
+
+ if ($vars['type'] === 'dokuwiki-template') {
+ return $this->inflectTemplateVars($vars);
+ }
+
+ return $vars;
+ }
+
+ /**
+ * @param array $vars
+ * @return array
+ */
+ protected function inflectPluginVars(array $vars): array
+ {
+ $vars['name'] = $this->pregReplace('/-plugin$/', '', $vars['name']);
+ $vars['name'] = $this->pregReplace('/^dokuwiki_?-?/', '', $vars['name']);
+
+ return $vars;
+ }
+
+ /**
+ * @param array $vars
+ * @return array
+ */
+ protected function inflectTemplateVars(array $vars): array
+ {
+ $vars['name'] = $this->pregReplace('/-template$/', '', $vars['name']);
+ $vars['name'] = $this->pregReplace('/^dokuwiki_?-?/', '', $vars['name']);
+
+ return $vars;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/DolibarrInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/DolibarrInstaller.php
new file mode 100644
index 00000000..c583619c
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/DolibarrInstaller.php
@@ -0,0 +1,18 @@
+
+ */
+class DolibarrInstaller extends BaseInstaller
+{
+ //TODO: Add support for scripts and themes
+ /** @var array */
+ protected $locations = array(
+ 'module' => 'htdocs/custom/{$name}/',
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/DrupalInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/DrupalInstaller.php
new file mode 100644
index 00000000..7690f306
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/DrupalInstaller.php
@@ -0,0 +1,24 @@
+ */
+ protected $locations = array(
+ 'core' => 'core/',
+ 'module' => 'modules/{$name}/',
+ 'theme' => 'themes/{$name}/',
+ 'library' => 'libraries/{$name}/',
+ 'profile' => 'profiles/{$name}/',
+ 'database-driver' => 'drivers/lib/Drupal/Driver/Database/{$name}/',
+ 'drush' => 'drush/{$name}/',
+ 'custom-theme' => 'themes/custom/{$name}/',
+ 'custom-module' => 'modules/custom/{$name}/',
+ 'custom-profile' => 'profiles/custom/{$name}/',
+ 'drupal-multisite' => 'sites/{$name}/',
+ 'console' => 'console/{$name}/',
+ 'console-language' => 'console/language/{$name}/',
+ 'config' => 'config/sync/',
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/ElggInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/ElggInstaller.php
new file mode 100644
index 00000000..48ef2ecd
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/ElggInstaller.php
@@ -0,0 +1,11 @@
+ */
+ protected $locations = array(
+ 'plugin' => 'mod/{$name}/',
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/EliasisInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/EliasisInstaller.php
new file mode 100644
index 00000000..d7dd9a92
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/EliasisInstaller.php
@@ -0,0 +1,14 @@
+ */
+ protected $locations = array(
+ 'component' => 'components/{$name}/',
+ 'module' => 'modules/{$name}/',
+ 'plugin' => 'plugins/{$name}/',
+ 'template' => 'templates/{$name}/',
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/ExpressionEngineInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/ExpressionEngineInstaller.php
new file mode 100644
index 00000000..fe1d468a
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/ExpressionEngineInstaller.php
@@ -0,0 +1,31 @@
+ */
+ private $ee2Locations = array(
+ 'addon' => 'system/expressionengine/third_party/{$name}/',
+ 'theme' => 'themes/third_party/{$name}/',
+ );
+
+ /** @var array */
+ private $ee3Locations = array(
+ 'addon' => 'system/user/addons/{$name}/',
+ 'theme' => 'themes/user/{$name}/',
+ );
+
+ public function getLocations(string $frameworkType): array
+ {
+ if ($frameworkType === 'ee2') {
+ $this->locations = $this->ee2Locations;
+ } else {
+ $this->locations = $this->ee3Locations;
+ }
+
+ return $this->locations;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/EzPlatformInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/EzPlatformInstaller.php
new file mode 100644
index 00000000..1f5b84e2
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/EzPlatformInstaller.php
@@ -0,0 +1,12 @@
+ */
+ protected $locations = array(
+ 'meta-assets' => 'web/assets/ezplatform/',
+ 'assets' => 'web/assets/ezplatform/{$name}/',
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/FuelInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/FuelInstaller.php
new file mode 100644
index 00000000..5948572e
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/FuelInstaller.php
@@ -0,0 +1,13 @@
+ */
+ protected $locations = array(
+ 'module' => 'fuel/app/modules/{$name}/',
+ 'package' => 'fuel/packages/{$name}/',
+ 'theme' => 'fuel/app/themes/{$name}/',
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/FuelphpInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/FuelphpInstaller.php
new file mode 100644
index 00000000..b4d80ed3
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/FuelphpInstaller.php
@@ -0,0 +1,11 @@
+ */
+ protected $locations = array(
+ 'component' => 'components/{$name}/',
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/GravInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/GravInstaller.php
new file mode 100644
index 00000000..f5792e36
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/GravInstaller.php
@@ -0,0 +1,29 @@
+ */
+ protected $locations = array(
+ 'plugin' => 'user/plugins/{$name}/',
+ 'theme' => 'user/themes/{$name}/',
+ );
+
+ /**
+ * Format package name
+ */
+ public function inflectPackageVars(array $vars): array
+ {
+ $restrictedWords = implode('|', array_keys($this->locations));
+
+ $vars['name'] = strtolower($vars['name']);
+ $vars['name'] = $this->pregReplace(
+ '/^(?:grav-)?(?:(?:'.$restrictedWords.')-)?(.*?)(?:-(?:'.$restrictedWords.'))?$/ui',
+ '$1',
+ $vars['name']
+ );
+
+ return $vars;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/HuradInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/HuradInstaller.php
new file mode 100644
index 00000000..dd76c5b6
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/HuradInstaller.php
@@ -0,0 +1,27 @@
+ */
+ protected $locations = array(
+ 'plugin' => 'plugins/{$name}/',
+ 'theme' => 'plugins/{$name}/',
+ );
+
+ /**
+ * Format package name to CamelCase
+ */
+ public function inflectPackageVars(array $vars): array
+ {
+ $nameParts = explode('/', $vars['name']);
+ foreach ($nameParts as &$value) {
+ $value = strtolower($this->pregReplace('/(?<=\\w)([A-Z])/', '_\\1', $value));
+ $value = str_replace(array('-', '_'), ' ', $value);
+ $value = str_replace(' ', '', ucwords($value));
+ }
+ $vars['name'] = implode('/', $nameParts);
+ return $vars;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/ImageCMSInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/ImageCMSInstaller.php
new file mode 100644
index 00000000..4157ceca
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/ImageCMSInstaller.php
@@ -0,0 +1,13 @@
+ */
+ protected $locations = array(
+ 'template' => 'templates/{$name}/',
+ 'module' => 'application/modules/{$name}/',
+ 'library' => 'application/libraries/{$name}/',
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/Installer.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/Installer.php
new file mode 100644
index 00000000..67a73e9d
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/Installer.php
@@ -0,0 +1,280 @@
+
+ */
+ private $supportedTypes = array(
+ 'akaunting' => 'AkauntingInstaller',
+ 'asgard' => 'AsgardInstaller',
+ 'attogram' => 'AttogramInstaller',
+ 'agl' => 'AglInstaller',
+ 'annotatecms' => 'AnnotateCmsInstaller',
+ 'bitrix' => 'BitrixInstaller',
+ 'bonefish' => 'BonefishInstaller',
+ 'cakephp' => 'CakePHPInstaller',
+ 'chef' => 'ChefInstaller',
+ 'civicrm' => 'CiviCrmInstaller',
+ 'ccframework' => 'ClanCatsFrameworkInstaller',
+ 'cockpit' => 'CockpitInstaller',
+ 'codeigniter' => 'CodeIgniterInstaller',
+ 'concrete5' => 'Concrete5Installer',
+ 'croogo' => 'CroogoInstaller',
+ 'dframe' => 'DframeInstaller',
+ 'dokuwiki' => 'DokuWikiInstaller',
+ 'dolibarr' => 'DolibarrInstaller',
+ 'decibel' => 'DecibelInstaller',
+ 'drupal' => 'DrupalInstaller',
+ 'elgg' => 'ElggInstaller',
+ 'eliasis' => 'EliasisInstaller',
+ 'ee3' => 'ExpressionEngineInstaller',
+ 'ee2' => 'ExpressionEngineInstaller',
+ 'ezplatform' => 'EzPlatformInstaller',
+ 'fuel' => 'FuelInstaller',
+ 'fuelphp' => 'FuelphpInstaller',
+ 'grav' => 'GravInstaller',
+ 'hurad' => 'HuradInstaller',
+ 'tastyigniter' => 'TastyIgniterInstaller',
+ 'imagecms' => 'ImageCMSInstaller',
+ 'itop' => 'ItopInstaller',
+ 'kanboard' => 'KanboardInstaller',
+ 'known' => 'KnownInstaller',
+ 'kodicms' => 'KodiCMSInstaller',
+ 'kohana' => 'KohanaInstaller',
+ 'lms' => 'LanManagementSystemInstaller',
+ 'laravel' => 'LaravelInstaller',
+ 'lavalite' => 'LavaLiteInstaller',
+ 'lithium' => 'LithiumInstaller',
+ 'magento' => 'MagentoInstaller',
+ 'majima' => 'MajimaInstaller',
+ 'mantisbt' => 'MantisBTInstaller',
+ 'mako' => 'MakoInstaller',
+ 'matomo' => 'MatomoInstaller',
+ 'maya' => 'MayaInstaller',
+ 'mautic' => 'MauticInstaller',
+ 'mediawiki' => 'MediaWikiInstaller',
+ 'miaoxing' => 'MiaoxingInstaller',
+ 'microweber' => 'MicroweberInstaller',
+ 'modulework' => 'MODULEWorkInstaller',
+ 'modx' => 'ModxInstaller',
+ 'modxevo' => 'MODXEvoInstaller',
+ 'moodle' => 'MoodleInstaller',
+ 'october' => 'OctoberInstaller',
+ 'ontowiki' => 'OntoWikiInstaller',
+ 'oxid' => 'OxidInstaller',
+ 'osclass' => 'OsclassInstaller',
+ 'pxcms' => 'PxcmsInstaller',
+ 'phpbb' => 'PhpBBInstaller',
+ 'piwik' => 'PiwikInstaller',
+ 'plentymarkets'=> 'PlentymarketsInstaller',
+ 'ppi' => 'PPIInstaller',
+ 'puppet' => 'PuppetInstaller',
+ 'radphp' => 'RadPHPInstaller',
+ 'phifty' => 'PhiftyInstaller',
+ 'porto' => 'PortoInstaller',
+ 'processwire' => 'ProcessWireInstaller',
+ 'quicksilver' => 'PantheonInstaller',
+ 'redaxo' => 'RedaxoInstaller',
+ 'redaxo5' => 'Redaxo5Installer',
+ 'reindex' => 'ReIndexInstaller',
+ 'roundcube' => 'RoundcubeInstaller',
+ 'shopware' => 'ShopwareInstaller',
+ 'sitedirect' => 'SiteDirectInstaller',
+ 'silverstripe' => 'SilverStripeInstaller',
+ 'smf' => 'SMFInstaller',
+ 'starbug' => 'StarbugInstaller',
+ 'sydes' => 'SyDESInstaller',
+ 'sylius' => 'SyliusInstaller',
+ 'tao' => 'TaoInstaller',
+ 'thelia' => 'TheliaInstaller',
+ 'tusk' => 'TuskInstaller',
+ 'userfrosting' => 'UserFrostingInstaller',
+ 'vanilla' => 'VanillaInstaller',
+ 'whmcs' => 'WHMCSInstaller',
+ 'winter' => 'WinterInstaller',
+ 'wolfcms' => 'WolfCMSInstaller',
+ 'wordpress' => 'WordPressInstaller',
+ 'yawik' => 'YawikInstaller',
+ 'zend' => 'ZendInstaller',
+ 'zikula' => 'ZikulaInstaller',
+ 'prestashop' => 'PrestashopInstaller'
+ );
+
+ /**
+ * Disables installers specified in main composer extra installer-disable
+ * list
+ */
+ public function __construct(
+ IOInterface $io,
+ Composer $composer,
+ string $type = 'library',
+ ?Filesystem $filesystem = null,
+ ?BinaryInstaller $binaryInstaller = null
+ ) {
+ parent::__construct($io, $composer, $type, $filesystem, $binaryInstaller);
+ $this->removeDisabledInstallers();
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ public function getInstallPath(PackageInterface $package)
+ {
+ $type = $package->getType();
+ $frameworkType = $this->findFrameworkType($type);
+
+ if ($frameworkType === false) {
+ throw new \InvalidArgumentException(
+ 'Sorry the package type of this package is not yet supported.'
+ );
+ }
+
+ $class = 'Composer\\Installers\\' . $this->supportedTypes[$frameworkType];
+ $installer = new $class($package, $this->composer, $this->getIO());
+
+ $path = $installer->getInstallPath($package, $frameworkType);
+ if (!$this->filesystem->isAbsolutePath($path)) {
+ $path = getcwd() . '/' . $path;
+ }
+
+ return $path;
+ }
+
+ public function uninstall(InstalledRepositoryInterface $repo, PackageInterface $package)
+ {
+ $installPath = $this->getPackageBasePath($package);
+ $io = $this->io;
+ $outputStatus = function () use ($io, $installPath) {
+ $io->write(sprintf('Deleting %s - %s', $installPath, !file_exists($installPath) ? 'deleted ' : 'not deleted '));
+ };
+
+ $promise = parent::uninstall($repo, $package);
+
+ // Composer v2 might return a promise here
+ if ($promise instanceof PromiseInterface) {
+ return $promise->then($outputStatus);
+ }
+
+ // If not, execute the code right away as parent::uninstall executed synchronously (composer v1, or v2 without async)
+ $outputStatus();
+
+ return null;
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ public function supports($packageType)
+ {
+ $frameworkType = $this->findFrameworkType($packageType);
+
+ if ($frameworkType === false) {
+ return false;
+ }
+
+ $locationPattern = $this->getLocationPattern($frameworkType);
+
+ return preg_match('#' . $frameworkType . '-' . $locationPattern . '#', $packageType, $matches) === 1;
+ }
+
+ /**
+ * Finds a supported framework type if it exists and returns it
+ *
+ * @return string|false
+ */
+ protected function findFrameworkType(string $type)
+ {
+ krsort($this->supportedTypes);
+
+ foreach ($this->supportedTypes as $key => $val) {
+ if ($key === substr($type, 0, strlen($key))) {
+ return substr($type, 0, strlen($key));
+ }
+ }
+
+ return false;
+ }
+
+ /**
+ * Get the second part of the regular expression to check for support of a
+ * package type
+ */
+ protected function getLocationPattern(string $frameworkType): string
+ {
+ $pattern = null;
+ if (!empty($this->supportedTypes[$frameworkType])) {
+ $frameworkClass = 'Composer\\Installers\\' . $this->supportedTypes[$frameworkType];
+ /** @var BaseInstaller $framework */
+ $framework = new $frameworkClass(new Package('dummy/pkg', '1.0.0.0', '1.0.0'), $this->composer, $this->getIO());
+ $locations = array_keys($framework->getLocations($frameworkType));
+ if ($locations) {
+ $pattern = '(' . implode('|', $locations) . ')';
+ }
+ }
+
+ return $pattern ?: '(\w+)';
+ }
+
+ private function getIO(): IOInterface
+ {
+ return $this->io;
+ }
+
+ /**
+ * Look for installers set to be disabled in composer's extra config and
+ * remove them from the list of supported installers.
+ *
+ * Globals:
+ * - true, "all", and "*" - disable all installers.
+ * - false - enable all installers (useful with
+ * wikimedia/composer-merge-plugin or similar)
+ */
+ protected function removeDisabledInstallers(): void
+ {
+ $extra = $this->composer->getPackage()->getExtra();
+
+ if (!isset($extra['installer-disable']) || $extra['installer-disable'] === false) {
+ // No installers are disabled
+ return;
+ }
+
+ // Get installers to disable
+ $disable = $extra['installer-disable'];
+
+ // Ensure $disabled is an array
+ if (!is_array($disable)) {
+ $disable = array($disable);
+ }
+
+ // Check which installers should be disabled
+ $all = array(true, "all", "*");
+ $intersect = array_intersect($all, $disable);
+ if (!empty($intersect)) {
+ // Disable all installers
+ $this->supportedTypes = array();
+ return;
+ }
+
+ // Disable specified installers
+ foreach ($disable as $key => $installer) {
+ if (is_string($installer) && key_exists($installer, $this->supportedTypes)) {
+ unset($this->supportedTypes[$installer]);
+ }
+ }
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/ItopInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/ItopInstaller.php
new file mode 100644
index 00000000..06af0687
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/ItopInstaller.php
@@ -0,0 +1,11 @@
+ */
+ protected $locations = array(
+ 'extension' => 'extensions/{$name}/',
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/KanboardInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/KanboardInstaller.php
new file mode 100644
index 00000000..bca954b2
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/KanboardInstaller.php
@@ -0,0 +1,20 @@
+ */
+ protected $locations = array(
+ 'plugin' => 'plugins/{$name}/',
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/KnownInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/KnownInstaller.php
new file mode 100644
index 00000000..61910a86
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/KnownInstaller.php
@@ -0,0 +1,13 @@
+ */
+ protected $locations = array(
+ 'plugin' => 'IdnoPlugins/{$name}/',
+ 'theme' => 'Themes/{$name}/',
+ 'console' => 'ConsolePlugins/{$name}/',
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/KodiCMSInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/KodiCMSInstaller.php
new file mode 100644
index 00000000..2505ac68
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/KodiCMSInstaller.php
@@ -0,0 +1,12 @@
+ */
+ protected $locations = array(
+ 'plugin' => 'cms/plugins/{$name}/',
+ 'media' => 'cms/media/vendor/{$name}/'
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/KohanaInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/KohanaInstaller.php
new file mode 100644
index 00000000..b6aa8097
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/KohanaInstaller.php
@@ -0,0 +1,11 @@
+ */
+ protected $locations = array(
+ 'module' => 'modules/{$name}/',
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/LanManagementSystemInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/LanManagementSystemInstaller.php
new file mode 100644
index 00000000..7fe9d9b7
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/LanManagementSystemInstaller.php
@@ -0,0 +1,27 @@
+ */
+ protected $locations = array(
+ 'plugin' => 'plugins/{$name}/',
+ 'template' => 'templates/{$name}/',
+ 'document-template' => 'documents/templates/{$name}/',
+ 'userpanel-module' => 'userpanel/modules/{$name}/',
+ );
+
+ /**
+ * Format package name to CamelCase
+ */
+ public function inflectPackageVars(array $vars): array
+ {
+ $vars['name'] = strtolower($this->pregReplace('/(?<=\\w)([A-Z])/', '_\\1', $vars['name']));
+ $vars['name'] = str_replace(array('-', '_'), ' ', $vars['name']);
+ $vars['name'] = str_replace(' ', '', ucwords($vars['name']));
+
+ return $vars;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/LaravelInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/LaravelInstaller.php
new file mode 100644
index 00000000..a69dc889
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/LaravelInstaller.php
@@ -0,0 +1,11 @@
+ */
+ protected $locations = array(
+ 'library' => 'libraries/{$name}/',
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/LavaLiteInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/LavaLiteInstaller.php
new file mode 100644
index 00000000..e4a7c7da
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/LavaLiteInstaller.php
@@ -0,0 +1,12 @@
+ */
+ protected $locations = array(
+ 'package' => 'packages/{$vendor}/{$name}/',
+ 'theme' => 'public/themes/{$name}/',
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/LithiumInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/LithiumInstaller.php
new file mode 100644
index 00000000..b24bea20
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/LithiumInstaller.php
@@ -0,0 +1,12 @@
+ */
+ protected $locations = array(
+ 'library' => 'libraries/{$name}/',
+ 'source' => 'libraries/_source/{$name}/',
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/MODULEWorkInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/MODULEWorkInstaller.php
new file mode 100644
index 00000000..369e8b45
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/MODULEWorkInstaller.php
@@ -0,0 +1,11 @@
+ */
+ protected $locations = array(
+ 'module' => 'modules/{$name}/',
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/MODXEvoInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/MODXEvoInstaller.php
new file mode 100644
index 00000000..062a839b
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/MODXEvoInstaller.php
@@ -0,0 +1,18 @@
+ */
+ protected $locations = array(
+ 'snippet' => 'assets/snippets/{$name}/',
+ 'plugin' => 'assets/plugins/{$name}/',
+ 'module' => 'assets/modules/{$name}/',
+ 'template' => 'assets/templates/{$name}/',
+ 'lib' => 'assets/lib/{$name}/'
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/MagentoInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/MagentoInstaller.php
new file mode 100644
index 00000000..ec07cd64
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/MagentoInstaller.php
@@ -0,0 +1,13 @@
+ */
+ protected $locations = array(
+ 'theme' => 'app/design/frontend/{$name}/',
+ 'skin' => 'skin/frontend/default/{$name}/',
+ 'library' => 'lib/{$name}/',
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/MajimaInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/MajimaInstaller.php
new file mode 100644
index 00000000..6fc3089d
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/MajimaInstaller.php
@@ -0,0 +1,46 @@
+ */
+ protected $locations = array(
+ 'plugin' => 'plugins/{$name}/',
+ );
+
+ /**
+ * Transforms the names
+ *
+ * @param array $vars
+ * @return array
+ */
+ public function inflectPackageVars(array $vars): array
+ {
+ return $this->correctPluginName($vars);
+ }
+
+ /**
+ * Change hyphenated names to camelcase
+ *
+ * @param array $vars
+ * @return array
+ */
+ private function correctPluginName(array $vars): array
+ {
+ $camelCasedName = preg_replace_callback('/(-[a-z])/', function ($matches) {
+ return strtoupper($matches[0][1]);
+ }, $vars['name']);
+
+ if (null === $camelCasedName) {
+ throw new \RuntimeException('Failed to run preg_replace_callback: '.preg_last_error());
+ }
+
+ $vars['name'] = ucfirst($camelCasedName);
+ return $vars;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/MakoInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/MakoInstaller.php
new file mode 100644
index 00000000..cbe3760b
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/MakoInstaller.php
@@ -0,0 +1,11 @@
+ */
+ protected $locations = array(
+ 'package' => 'app/packages/{$name}/',
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/MantisBTInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/MantisBTInstaller.php
new file mode 100644
index 00000000..98e230fb
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/MantisBTInstaller.php
@@ -0,0 +1,25 @@
+ */
+ protected $locations = array(
+ 'plugin' => 'plugins/{$name}/',
+ );
+
+ /**
+ * Format package name to CamelCase
+ */
+ public function inflectPackageVars(array $vars): array
+ {
+ $vars['name'] = strtolower($this->pregReplace('/(?<=\\w)([A-Z])/', '_\\1', $vars['name']));
+ $vars['name'] = str_replace(array('-', '_'), ' ', $vars['name']);
+ $vars['name'] = str_replace(' ', '', ucwords($vars['name']));
+
+ return $vars;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/MatomoInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/MatomoInstaller.php
new file mode 100644
index 00000000..57fdb033
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/MatomoInstaller.php
@@ -0,0 +1,28 @@
+ */
+ protected $locations = array(
+ 'plugin' => 'plugins/{$name}/',
+ );
+
+ /**
+ * Format package name to CamelCase
+ */
+ public function inflectPackageVars(array $vars): array
+ {
+ $vars['name'] = strtolower($this->pregReplace('/(?<=\\w)([A-Z])/', '_\\1', $vars['name']));
+ $vars['name'] = str_replace(array('-', '_'), ' ', $vars['name']);
+ $vars['name'] = str_replace(' ', '', ucwords($vars['name']));
+
+ return $vars;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/MauticInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/MauticInstaller.php
new file mode 100644
index 00000000..e48c133b
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/MauticInstaller.php
@@ -0,0 +1,43 @@
+ */
+ protected $locations = array(
+ 'plugin' => 'plugins/{$name}/',
+ 'theme' => 'themes/{$name}/',
+ 'core' => 'app/',
+ );
+
+ private function getDirectoryName(): string
+ {
+ $extra = $this->package->getExtra();
+ if (!empty($extra['install-directory-name'])) {
+ return $extra['install-directory-name'];
+ }
+
+ return $this->toCamelCase($this->package->getPrettyName());
+ }
+
+ private function toCamelCase(string $packageName): string
+ {
+ return str_replace(' ', '', ucwords(str_replace('-', ' ', basename($packageName))));
+ }
+
+ /**
+ * Format package name of mautic-plugins to CamelCase
+ */
+ public function inflectPackageVars(array $vars): array
+ {
+ if ($vars['type'] == 'mautic-plugin' || $vars['type'] == 'mautic-theme') {
+ $directoryName = $this->getDirectoryName();
+ $vars['name'] = $directoryName;
+ }
+
+ return $vars;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/MayaInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/MayaInstaller.php
new file mode 100644
index 00000000..df486dac
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/MayaInstaller.php
@@ -0,0 +1,38 @@
+ */
+ protected $locations = array(
+ 'module' => 'modules/{$name}/',
+ );
+
+ /**
+ * Format package name.
+ *
+ * For package type maya-module, cut off a trailing '-module' if present.
+ */
+ public function inflectPackageVars(array $vars): array
+ {
+ if ($vars['type'] === 'maya-module') {
+ return $this->inflectModuleVars($vars);
+ }
+
+ return $vars;
+ }
+
+ /**
+ * @param array $vars
+ * @return array
+ */
+ protected function inflectModuleVars(array $vars): array
+ {
+ $vars['name'] = $this->pregReplace('/-module$/', '', $vars['name']);
+ $vars['name'] = str_replace(array('-', '_'), ' ', $vars['name']);
+ $vars['name'] = str_replace(' ', '', ucwords($vars['name']));
+
+ return $vars;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/MediaWikiInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/MediaWikiInstaller.php
new file mode 100644
index 00000000..8e9d7713
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/MediaWikiInstaller.php
@@ -0,0 +1,58 @@
+ */
+ protected $locations = array(
+ 'core' => 'core/',
+ 'extension' => 'extensions/{$name}/',
+ 'skin' => 'skins/{$name}/',
+ );
+
+ /**
+ * Format package name.
+ *
+ * For package type mediawiki-extension, cut off a trailing '-extension' if present and transform
+ * to CamelCase keeping existing uppercase chars.
+ *
+ * For package type mediawiki-skin, cut off a trailing '-skin' if present.
+ */
+ public function inflectPackageVars(array $vars): array
+ {
+ if ($vars['type'] === 'mediawiki-extension') {
+ return $this->inflectExtensionVars($vars);
+ }
+
+ if ($vars['type'] === 'mediawiki-skin') {
+ return $this->inflectSkinVars($vars);
+ }
+
+ return $vars;
+ }
+
+ /**
+ * @param array $vars
+ * @return array
+ */
+ protected function inflectExtensionVars(array $vars): array
+ {
+ $vars['name'] = $this->pregReplace('/-extension$/', '', $vars['name']);
+ $vars['name'] = str_replace('-', ' ', $vars['name']);
+ $vars['name'] = str_replace(' ', '', ucwords($vars['name']));
+
+ return $vars;
+ }
+
+ /**
+ * @param array $vars
+ * @return array
+ */
+ protected function inflectSkinVars(array $vars): array
+ {
+ $vars['name'] = $this->pregReplace('/-skin$/', '', $vars['name']);
+
+ return $vars;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/MiaoxingInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/MiaoxingInstaller.php
new file mode 100644
index 00000000..02541779
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/MiaoxingInstaller.php
@@ -0,0 +1,11 @@
+ */
+ protected $locations = array(
+ 'plugin' => 'plugins/{$name}/',
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/MicroweberInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/MicroweberInstaller.php
new file mode 100644
index 00000000..a4d97ab0
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/MicroweberInstaller.php
@@ -0,0 +1,145 @@
+ */
+ protected $locations = array(
+ 'module' => 'userfiles/modules/{$install_item_dir}/',
+ 'module-skin' => 'userfiles/modules/{$install_item_dir}/templates/',
+ 'template' => 'userfiles/templates/{$install_item_dir}/',
+ 'element' => 'userfiles/elements/{$install_item_dir}/',
+ 'vendor' => 'vendor/{$install_item_dir}/',
+ 'components' => 'components/{$install_item_dir}/'
+ );
+
+ /**
+ * Format package name.
+ *
+ * For package type microweber-module, cut off a trailing '-module' if present
+ *
+ * For package type microweber-template, cut off a trailing '-template' if present.
+ */
+ public function inflectPackageVars(array $vars): array
+ {
+ if ($this->package->getTargetDir() !== null && $this->package->getTargetDir() !== '') {
+ $vars['install_item_dir'] = $this->package->getTargetDir();
+ } else {
+ $vars['install_item_dir'] = $vars['name'];
+ if ($vars['type'] === 'microweber-template') {
+ return $this->inflectTemplateVars($vars);
+ }
+ if ($vars['type'] === 'microweber-templates') {
+ return $this->inflectTemplatesVars($vars);
+ }
+ if ($vars['type'] === 'microweber-core') {
+ return $this->inflectCoreVars($vars);
+ }
+ if ($vars['type'] === 'microweber-adapter') {
+ return $this->inflectCoreVars($vars);
+ }
+ if ($vars['type'] === 'microweber-module') {
+ return $this->inflectModuleVars($vars);
+ }
+ if ($vars['type'] === 'microweber-modules') {
+ return $this->inflectModulesVars($vars);
+ }
+ if ($vars['type'] === 'microweber-skin') {
+ return $this->inflectSkinVars($vars);
+ }
+ if ($vars['type'] === 'microweber-element' or $vars['type'] === 'microweber-elements') {
+ return $this->inflectElementVars($vars);
+ }
+ }
+
+ return $vars;
+ }
+
+ /**
+ * @param array $vars
+ * @return array
+ */
+ protected function inflectTemplateVars(array $vars): array
+ {
+ $vars['install_item_dir'] = $this->pregReplace('/-template$/', '', $vars['install_item_dir']);
+ $vars['install_item_dir'] = $this->pregReplace('/template-$/', '', $vars['install_item_dir']);
+
+ return $vars;
+ }
+
+ /**
+ * @param array $vars
+ * @return array
+ */
+ protected function inflectTemplatesVars(array $vars): array
+ {
+ $vars['install_item_dir'] = $this->pregReplace('/-templates$/', '', $vars['install_item_dir']);
+ $vars['install_item_dir'] = $this->pregReplace('/templates-$/', '', $vars['install_item_dir']);
+
+ return $vars;
+ }
+
+ /**
+ * @param array $vars
+ * @return array
+ */
+ protected function inflectCoreVars(array $vars): array
+ {
+ $vars['install_item_dir'] = $this->pregReplace('/-providers$/', '', $vars['install_item_dir']);
+ $vars['install_item_dir'] = $this->pregReplace('/-provider$/', '', $vars['install_item_dir']);
+ $vars['install_item_dir'] = $this->pregReplace('/-adapter$/', '', $vars['install_item_dir']);
+
+ return $vars;
+ }
+
+ /**
+ * @param array $vars
+ * @return array
+ */
+ protected function inflectModuleVars(array $vars): array
+ {
+ $vars['install_item_dir'] = $this->pregReplace('/-module$/', '', $vars['install_item_dir']);
+ $vars['install_item_dir'] = $this->pregReplace('/module-$/', '', $vars['install_item_dir']);
+
+ return $vars;
+ }
+
+ /**
+ * @param array $vars
+ * @return array
+ */
+ protected function inflectModulesVars(array $vars): array
+ {
+ $vars['install_item_dir'] = $this->pregReplace('/-modules$/', '', $vars['install_item_dir']);
+ $vars['install_item_dir'] = $this->pregReplace('/modules-$/', '', $vars['install_item_dir']);
+
+ return $vars;
+ }
+
+ /**
+ * @param array $vars
+ * @return array
+ */
+ protected function inflectSkinVars(array $vars): array
+ {
+ $vars['install_item_dir'] = $this->pregReplace('/-skin$/', '', $vars['install_item_dir']);
+ $vars['install_item_dir'] = $this->pregReplace('/skin-$/', '', $vars['install_item_dir']);
+
+ return $vars;
+ }
+
+ /**
+ * @param array $vars
+ * @return array
+ */
+ protected function inflectElementVars(array $vars): array
+ {
+ $vars['install_item_dir'] = $this->pregReplace('/-elements$/', '', $vars['install_item_dir']);
+ $vars['install_item_dir'] = $this->pregReplace('/elements-$/', '', $vars['install_item_dir']);
+ $vars['install_item_dir'] = $this->pregReplace('/-element$/', '', $vars['install_item_dir']);
+ $vars['install_item_dir'] = $this->pregReplace('/element-$/', '', $vars['install_item_dir']);
+
+ return $vars;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/ModxInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/ModxInstaller.php
new file mode 100644
index 00000000..e2dddec5
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/ModxInstaller.php
@@ -0,0 +1,14 @@
+ */
+ protected $locations = array(
+ 'extra' => 'core/packages/{$name}/'
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/MoodleInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/MoodleInstaller.php
new file mode 100644
index 00000000..d9babb37
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/MoodleInstaller.php
@@ -0,0 +1,67 @@
+ */
+ protected $locations = array(
+ 'mod' => 'mod/{$name}/',
+ 'admin_report' => 'admin/report/{$name}/',
+ 'atto' => 'lib/editor/atto/plugins/{$name}/',
+ 'tool' => 'admin/tool/{$name}/',
+ 'assignment' => 'mod/assignment/type/{$name}/',
+ 'assignsubmission' => 'mod/assign/submission/{$name}/',
+ 'assignfeedback' => 'mod/assign/feedback/{$name}/',
+ 'antivirus' => 'lib/antivirus/{$name}/',
+ 'auth' => 'auth/{$name}/',
+ 'availability' => 'availability/condition/{$name}/',
+ 'block' => 'blocks/{$name}/',
+ 'booktool' => 'mod/book/tool/{$name}/',
+ 'cachestore' => 'cache/stores/{$name}/',
+ 'cachelock' => 'cache/locks/{$name}/',
+ 'calendartype' => 'calendar/type/{$name}/',
+ 'customfield' => 'customfield/field/{$name}/',
+ 'fileconverter' => 'files/converter/{$name}/',
+ 'format' => 'course/format/{$name}/',
+ 'coursereport' => 'course/report/{$name}/',
+ 'contenttype' => 'contentbank/contenttype/{$name}/',
+ 'customcertelement' => 'mod/customcert/element/{$name}/',
+ 'datafield' => 'mod/data/field/{$name}/',
+ 'dataformat' => 'dataformat/{$name}/',
+ 'datapreset' => 'mod/data/preset/{$name}/',
+ 'editor' => 'lib/editor/{$name}/',
+ 'enrol' => 'enrol/{$name}/',
+ 'filter' => 'filter/{$name}/',
+ 'gradeexport' => 'grade/export/{$name}/',
+ 'gradeimport' => 'grade/import/{$name}/',
+ 'gradereport' => 'grade/report/{$name}/',
+ 'gradingform' => 'grade/grading/form/{$name}/',
+ 'local' => 'local/{$name}/',
+ 'logstore' => 'admin/tool/log/store/{$name}/',
+ 'ltisource' => 'mod/lti/source/{$name}/',
+ 'ltiservice' => 'mod/lti/service/{$name}/',
+ 'media' => 'media/player/{$name}/',
+ 'message' => 'message/output/{$name}/',
+ 'mnetservice' => 'mnet/service/{$name}/',
+ 'paygw' => 'payment/gateway/{$name}/',
+ 'plagiarism' => 'plagiarism/{$name}/',
+ 'portfolio' => 'portfolio/{$name}/',
+ 'qbehaviour' => 'question/behaviour/{$name}/',
+ 'qformat' => 'question/format/{$name}/',
+ 'qtype' => 'question/type/{$name}/',
+ 'quizaccess' => 'mod/quiz/accessrule/{$name}/',
+ 'quiz' => 'mod/quiz/report/{$name}/',
+ 'report' => 'report/{$name}/',
+ 'repository' => 'repository/{$name}/',
+ 'scormreport' => 'mod/scorm/report/{$name}/',
+ 'search' => 'search/engine/{$name}/',
+ 'theme' => 'theme/{$name}/',
+ 'tinymce' => 'lib/editor/tinymce/plugins/{$name}/',
+ 'profilefield' => 'user/profile/field/{$name}/',
+ 'webservice' => 'webservice/{$name}/',
+ 'workshopallocation' => 'mod/workshop/allocation/{$name}/',
+ 'workshopeval' => 'mod/workshop/eval/{$name}/',
+ 'workshopform' => 'mod/workshop/form/{$name}/'
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/OctoberInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/OctoberInstaller.php
new file mode 100644
index 00000000..524f17d8
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/OctoberInstaller.php
@@ -0,0 +1,57 @@
+ */
+ protected $locations = array(
+ 'module' => 'modules/{$name}/',
+ 'plugin' => 'plugins/{$vendor}/{$name}/',
+ 'theme' => 'themes/{$vendor}-{$name}/'
+ );
+
+ /**
+ * Format package name.
+ *
+ * For package type october-plugin, cut off a trailing '-plugin' if present.
+ *
+ * For package type october-theme, cut off a trailing '-theme' if present.
+ */
+ public function inflectPackageVars(array $vars): array
+ {
+ if ($vars['type'] === 'october-plugin') {
+ return $this->inflectPluginVars($vars);
+ }
+
+ if ($vars['type'] === 'october-theme') {
+ return $this->inflectThemeVars($vars);
+ }
+
+ return $vars;
+ }
+
+ /**
+ * @param array $vars
+ * @return array
+ */
+ protected function inflectPluginVars(array $vars): array
+ {
+ $vars['name'] = $this->pregReplace('/^oc-|-plugin$/', '', $vars['name']);
+ $vars['vendor'] = $this->pregReplace('/[^a-z0-9_]/i', '', $vars['vendor']);
+
+ return $vars;
+ }
+
+ /**
+ * @param array $vars
+ * @return array
+ */
+ protected function inflectThemeVars(array $vars): array
+ {
+ $vars['name'] = $this->pregReplace('/^oc-|-theme$/', '', $vars['name']);
+ $vars['vendor'] = $this->pregReplace('/[^a-z0-9_]/i', '', $vars['vendor']);
+
+ return $vars;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/OntoWikiInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/OntoWikiInstaller.php
new file mode 100644
index 00000000..fd20c1a8
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/OntoWikiInstaller.php
@@ -0,0 +1,26 @@
+ */
+ protected $locations = array(
+ 'extension' => 'extensions/{$name}/',
+ 'theme' => 'extensions/themes/{$name}/',
+ 'translation' => 'extensions/translations/{$name}/',
+ );
+
+ /**
+ * Format package name to lower case and remove ".ontowiki" suffix
+ */
+ public function inflectPackageVars(array $vars): array
+ {
+ $vars['name'] = strtolower($vars['name']);
+ $vars['name'] = $this->pregReplace('/.ontowiki$/', '', $vars['name']);
+ $vars['name'] = $this->pregReplace('/-theme$/', '', $vars['name']);
+ $vars['name'] = $this->pregReplace('/-translation$/', '', $vars['name']);
+
+ return $vars;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/OsclassInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/OsclassInstaller.php
new file mode 100644
index 00000000..e61d61f8
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/OsclassInstaller.php
@@ -0,0 +1,14 @@
+ */
+ protected $locations = array(
+ 'plugin' => 'oc-content/plugins/{$name}/',
+ 'theme' => 'oc-content/themes/{$name}/',
+ 'language' => 'oc-content/languages/{$name}/',
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/OxidInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/OxidInstaller.php
new file mode 100644
index 00000000..6e1e8624
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/OxidInstaller.php
@@ -0,0 +1,49 @@
+.+)\/.+/';
+
+ /** @var array */
+ protected $locations = array(
+ 'module' => 'modules/{$name}/',
+ 'theme' => 'application/views/{$name}/',
+ 'out' => 'out/{$name}/',
+ );
+
+ public function getInstallPath(PackageInterface $package, string $frameworkType = ''): string
+ {
+ $installPath = parent::getInstallPath($package, $frameworkType);
+ $type = $this->package->getType();
+ if ($type === 'oxid-module') {
+ $this->prepareVendorDirectory($installPath);
+ }
+ return $installPath;
+ }
+
+ /**
+ * Makes sure there is a vendormetadata.php file inside
+ * the vendor folder if there is a vendor folder.
+ */
+ protected function prepareVendorDirectory(string $installPath): void
+ {
+ $matches = '';
+ $hasVendorDirectory = preg_match(self::VENDOR_PATTERN, $installPath, $matches);
+ if (!$hasVendorDirectory) {
+ return;
+ }
+
+ $vendorDirectory = $matches['vendor'];
+ $vendorPath = getcwd() . '/modules/' . $vendorDirectory;
+ if (!file_exists($vendorPath)) {
+ mkdir($vendorPath, 0755, true);
+ }
+
+ $vendorMetaDataPath = $vendorPath . '/vendormetadata.php';
+ touch($vendorMetaDataPath);
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/PPIInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/PPIInstaller.php
new file mode 100644
index 00000000..714c4679
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/PPIInstaller.php
@@ -0,0 +1,11 @@
+ */
+ protected $locations = array(
+ 'module' => 'modules/{$name}/',
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/PantheonInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/PantheonInstaller.php
new file mode 100644
index 00000000..439f61a0
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/PantheonInstaller.php
@@ -0,0 +1,12 @@
+ */
+ protected $locations = array(
+ 'script' => 'web/private/scripts/quicksilver/{$name}',
+ 'module' => 'web/private/scripts/quicksilver/{$name}',
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/PhiftyInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/PhiftyInstaller.php
new file mode 100644
index 00000000..3c970e21
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/PhiftyInstaller.php
@@ -0,0 +1,13 @@
+ */
+ protected $locations = array(
+ 'bundle' => 'bundles/{$name}/',
+ 'library' => 'libraries/{$name}/',
+ 'framework' => 'frameworks/{$name}/',
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/PhpBBInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/PhpBBInstaller.php
new file mode 100644
index 00000000..d53ee4f6
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/PhpBBInstaller.php
@@ -0,0 +1,13 @@
+ */
+ protected $locations = array(
+ 'extension' => 'ext/{$vendor}/{$name}/',
+ 'language' => 'language/{$name}/',
+ 'style' => 'styles/{$name}/',
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/PiwikInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/PiwikInstaller.php
new file mode 100644
index 00000000..b2faf44a
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/PiwikInstaller.php
@@ -0,0 +1,28 @@
+ */
+ protected $locations = array(
+ 'plugin' => 'plugins/{$name}/',
+ );
+
+ /**
+ * Format package name to CamelCase
+ */
+ public function inflectPackageVars(array $vars): array
+ {
+ $vars['name'] = strtolower($this->pregReplace('/(?<=\\w)([A-Z])/', '_\\1', $vars['name']));
+ $vars['name'] = str_replace(array('-', '_'), ' ', $vars['name']);
+ $vars['name'] = str_replace(' ', '', ucwords($vars['name']));
+
+ return $vars;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/PlentymarketsInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/PlentymarketsInstaller.php
new file mode 100644
index 00000000..0c063598
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/PlentymarketsInstaller.php
@@ -0,0 +1,28 @@
+ */
+ protected $locations = array(
+ 'plugin' => '{$name}/'
+ );
+
+ /**
+ * Remove hyphen, "plugin" and format to camelcase
+ */
+ public function inflectPackageVars(array $vars): array
+ {
+ $nameBits = explode("-", $vars['name']);
+ foreach ($nameBits as $key => $name) {
+ $nameBits[$key] = ucfirst($name);
+ if (strcasecmp($name, "Plugin") == 0) {
+ unset($nameBits[$key]);
+ }
+ }
+ $vars['name'] = implode('', $nameBits);
+
+ return $vars;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/Plugin.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/Plugin.php
new file mode 100644
index 00000000..437a9493
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/Plugin.php
@@ -0,0 +1,28 @@
+installer = new Installer($io, $composer);
+ $composer->getInstallationManager()->addInstaller($this->installer);
+ }
+
+ public function deactivate(Composer $composer, IOInterface $io): void
+ {
+ $composer->getInstallationManager()->removeInstaller($this->installer);
+ }
+
+ public function uninstall(Composer $composer, IOInterface $io): void
+ {
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/PortoInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/PortoInstaller.php
new file mode 100644
index 00000000..a01d7a0b
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/PortoInstaller.php
@@ -0,0 +1,11 @@
+ */
+ protected $locations = array(
+ 'container' => 'app/Containers/{$name}/',
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/PrestashopInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/PrestashopInstaller.php
new file mode 100644
index 00000000..23f156f5
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/PrestashopInstaller.php
@@ -0,0 +1,12 @@
+ */
+ protected $locations = array(
+ 'module' => 'modules/{$name}/',
+ 'theme' => 'themes/{$name}/',
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/ProcessWireInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/ProcessWireInstaller.php
new file mode 100644
index 00000000..a7eb1eec
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/ProcessWireInstaller.php
@@ -0,0 +1,23 @@
+ */
+ protected $locations = array(
+ 'module' => 'site/modules/{$name}/',
+ );
+
+ /**
+ * Format package name to CamelCase
+ */
+ public function inflectPackageVars(array $vars): array
+ {
+ $vars['name'] = strtolower($this->pregReplace('/(?<=\\w)([A-Z])/', '_\\1', $vars['name']));
+ $vars['name'] = str_replace(array('-', '_'), ' ', $vars['name']);
+ $vars['name'] = str_replace(' ', '', ucwords($vars['name']));
+
+ return $vars;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/PuppetInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/PuppetInstaller.php
new file mode 100644
index 00000000..1a0a8a3f
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/PuppetInstaller.php
@@ -0,0 +1,12 @@
+ */
+ protected $locations = array(
+ 'module' => 'modules/{$name}/',
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/PxcmsInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/PxcmsInstaller.php
new file mode 100644
index 00000000..fc58b8a6
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/PxcmsInstaller.php
@@ -0,0 +1,62 @@
+ */
+ protected $locations = array(
+ 'module' => 'app/Modules/{$name}/',
+ 'theme' => 'themes/{$name}/',
+ );
+
+ /**
+ * Format package name.
+ */
+ public function inflectPackageVars(array $vars): array
+ {
+ if ($vars['type'] === 'pxcms-module') {
+ return $this->inflectModuleVars($vars);
+ }
+
+ if ($vars['type'] === 'pxcms-theme') {
+ return $this->inflectThemeVars($vars);
+ }
+
+ return $vars;
+ }
+
+ /**
+ * For package type pxcms-module, cut off a trailing '-plugin' if present.
+ *
+ * @param array $vars
+ * @return array
+ */
+ protected function inflectModuleVars(array $vars): array
+ {
+ $vars['name'] = str_replace('pxcms-', '', $vars['name']); // strip out pxcms- just incase (legacy)
+ $vars['name'] = str_replace('module-', '', $vars['name']); // strip out module-
+ $vars['name'] = $this->pregReplace('/-module$/', '', $vars['name']); // strip out -module
+ $vars['name'] = str_replace('-', '_', $vars['name']); // make -'s be _'s
+ $vars['name'] = ucwords($vars['name']); // make module name camelcased
+
+ return $vars;
+ }
+
+ /**
+ * For package type pxcms-module, cut off a trailing '-plugin' if present.
+ *
+ * @param array $vars
+ * @return array
+ */
+ protected function inflectThemeVars(array $vars): array
+ {
+ $vars['name'] = str_replace('pxcms-', '', $vars['name']); // strip out pxcms- just incase (legacy)
+ $vars['name'] = str_replace('theme-', '', $vars['name']); // strip out theme-
+ $vars['name'] = $this->pregReplace('/-theme$/', '', $vars['name']); // strip out -theme
+ $vars['name'] = str_replace('-', '_', $vars['name']); // make -'s be _'s
+ $vars['name'] = ucwords($vars['name']); // make module name camelcased
+
+ return $vars;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/RadPHPInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/RadPHPInstaller.php
new file mode 100644
index 00000000..4caae51d
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/RadPHPInstaller.php
@@ -0,0 +1,26 @@
+ */
+ protected $locations = array(
+ 'bundle' => 'src/{$name}/'
+ );
+
+ /**
+ * Format package name to CamelCase
+ */
+ public function inflectPackageVars(array $vars): array
+ {
+ $nameParts = explode('/', $vars['name']);
+ foreach ($nameParts as &$value) {
+ $value = strtolower($this->pregReplace('/(?<=\\w)([A-Z])/', '_\\1', $value));
+ $value = str_replace(array('-', '_'), ' ', $value);
+ $value = str_replace(' ', '', ucwords($value));
+ }
+ $vars['name'] = implode('/', $nameParts);
+ return $vars;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/ReIndexInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/ReIndexInstaller.php
new file mode 100644
index 00000000..a19eaaf2
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/ReIndexInstaller.php
@@ -0,0 +1,12 @@
+ */
+ protected $locations = array(
+ 'theme' => 'themes/{$name}/',
+ 'plugin' => 'plugins/{$name}/'
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/Redaxo5Installer.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/Redaxo5Installer.php
new file mode 100644
index 00000000..b62c926a
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/Redaxo5Installer.php
@@ -0,0 +1,12 @@
+ */
+ protected $locations = array(
+ 'addon' => 'redaxo/src/addons/{$name}/',
+ 'bestyle-plugin' => 'redaxo/src/addons/be_style/plugins/{$name}/'
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/RedaxoInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/RedaxoInstaller.php
new file mode 100644
index 00000000..26b3aa84
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/RedaxoInstaller.php
@@ -0,0 +1,12 @@
+ */
+ protected $locations = array(
+ 'addon' => 'redaxo/include/addons/{$name}/',
+ 'bestyle-plugin' => 'redaxo/include/addons/be_style/plugins/{$name}/'
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/RoundcubeInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/RoundcubeInstaller.php
new file mode 100644
index 00000000..7e716748
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/RoundcubeInstaller.php
@@ -0,0 +1,21 @@
+ */
+ protected $locations = array(
+ 'plugin' => 'plugins/{$name}/',
+ );
+
+ /**
+ * Lowercase name and changes the name to a underscores
+ */
+ public function inflectPackageVars(array $vars): array
+ {
+ $vars['name'] = strtolower(str_replace('-', '_', $vars['name']));
+
+ return $vars;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/SMFInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/SMFInstaller.php
new file mode 100644
index 00000000..7321046f
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/SMFInstaller.php
@@ -0,0 +1,12 @@
+ */
+ protected $locations = array(
+ 'module' => 'Sources/{$name}/',
+ 'theme' => 'Themes/{$name}/',
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/ShopwareInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/ShopwareInstaller.php
new file mode 100644
index 00000000..82b8e28c
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/ShopwareInstaller.php
@@ -0,0 +1,66 @@
+ */
+ protected $locations = array(
+ 'backend-plugin' => 'engine/Shopware/Plugins/Local/Backend/{$name}/',
+ 'core-plugin' => 'engine/Shopware/Plugins/Local/Core/{$name}/',
+ 'frontend-plugin' => 'engine/Shopware/Plugins/Local/Frontend/{$name}/',
+ 'theme' => 'templates/{$name}/',
+ 'plugin' => 'custom/plugins/{$name}/',
+ 'frontend-theme' => 'themes/Frontend/{$name}/',
+ );
+
+ /**
+ * Transforms the names
+ */
+ public function inflectPackageVars(array $vars): array
+ {
+ if ($vars['type'] === 'shopware-theme') {
+ return $this->correctThemeName($vars);
+ }
+
+ return $this->correctPluginName($vars);
+ }
+
+ /**
+ * Changes the name to a camelcased combination of vendor and name
+ *
+ * @param array $vars
+ * @return array
+ */
+ private function correctPluginName(array $vars): array
+ {
+ $camelCasedName = preg_replace_callback('/(-[a-z])/', function ($matches) {
+ return strtoupper($matches[0][1]);
+ }, $vars['name']);
+
+ if (null === $camelCasedName) {
+ throw new \RuntimeException('Failed to run preg_replace_callback: '.preg_last_error());
+ }
+
+ $vars['name'] = ucfirst($vars['vendor']) . ucfirst($camelCasedName);
+
+ return $vars;
+ }
+
+ /**
+ * Changes the name to a underscore separated name
+ *
+ * @param array $vars
+ * @return array
+ */
+ private function correctThemeName(array $vars): array
+ {
+ $vars['name'] = str_replace('-', '_', $vars['name']);
+
+ return $vars;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/SilverStripeInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/SilverStripeInstaller.php
new file mode 100644
index 00000000..aa2de216
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/SilverStripeInstaller.php
@@ -0,0 +1,33 @@
+ */
+ protected $locations = array(
+ 'module' => '{$name}/',
+ 'theme' => 'themes/{$name}/',
+ );
+
+ /**
+ * Return the install path based on package type.
+ *
+ * Relies on built-in BaseInstaller behaviour with one exception: silverstripe/framework
+ * must be installed to 'sapphire' and not 'framework' if the version is <3.0.0
+ */
+ public function getInstallPath(PackageInterface $package, string $frameworkType = ''): string
+ {
+ if (
+ $package->getName() == 'silverstripe/framework'
+ && preg_match('/^\d+\.\d+\.\d+/', $package->getVersion())
+ && version_compare($package->getVersion(), '2.999.999') < 0
+ ) {
+ return $this->templatePath($this->locations['module'], array('name' => 'sapphire'));
+ }
+
+ return parent::getInstallPath($package, $frameworkType);
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/SiteDirectInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/SiteDirectInstaller.php
new file mode 100644
index 00000000..0af3239b
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/SiteDirectInstaller.php
@@ -0,0 +1,34 @@
+ */
+ protected $locations = array(
+ 'module' => 'modules/{$vendor}/{$name}/',
+ 'plugin' => 'plugins/{$vendor}/{$name}/'
+ );
+
+ /**
+ * @param array $vars
+ * @return array
+ */
+ public function inflectPackageVars(array $vars): array
+ {
+ return $this->parseVars($vars);
+ }
+
+ /**
+ * @param array $vars
+ * @return array
+ */
+ protected function parseVars(array $vars): array
+ {
+ $vars['vendor'] = strtolower($vars['vendor']) == 'sitedirect' ? 'SiteDirect' : $vars['vendor'];
+ $vars['name'] = str_replace(array('-', '_'), ' ', $vars['name']);
+ $vars['name'] = str_replace(' ', '', ucwords($vars['name']));
+
+ return $vars;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/StarbugInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/StarbugInstaller.php
new file mode 100644
index 00000000..72afa081
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/StarbugInstaller.php
@@ -0,0 +1,14 @@
+ */
+ protected $locations = array(
+ 'module' => 'modules/{$name}/',
+ 'theme' => 'themes/{$name}/',
+ 'custom-module' => 'app/modules/{$name}/',
+ 'custom-theme' => 'app/themes/{$name}/'
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/SyDESInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/SyDESInstaller.php
new file mode 100644
index 00000000..24673d2f
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/SyDESInstaller.php
@@ -0,0 +1,55 @@
+ */
+ protected $locations = array(
+ 'module' => 'app/modules/{$name}/',
+ 'theme' => 'themes/{$name}/',
+ );
+
+ /**
+ * Format module name.
+ *
+ * Strip `sydes-` prefix and a trailing '-theme' or '-module' from package name if present.
+ */
+ public function inflectPackageVars(array $vars): array
+ {
+ if ($vars['type'] == 'sydes-module') {
+ return $this->inflectModuleVars($vars);
+ }
+
+ if ($vars['type'] === 'sydes-theme') {
+ return $this->inflectThemeVars($vars);
+ }
+
+ return $vars;
+ }
+
+ /**
+ * @param array $vars
+ * @return array
+ */
+ public function inflectModuleVars(array $vars): array
+ {
+ $vars['name'] = $this->pregReplace('/(^sydes-|-module$)/i', '', $vars['name']);
+ $vars['name'] = str_replace(array('-', '_'), ' ', $vars['name']);
+ $vars['name'] = str_replace(' ', '', ucwords($vars['name']));
+
+ return $vars;
+ }
+
+ /**
+ * @param array $vars
+ * @return array
+ */
+ protected function inflectThemeVars(array $vars): array
+ {
+ $vars['name'] = $this->pregReplace('/(^sydes-|-theme$)/', '', $vars['name']);
+ $vars['name'] = strtolower($vars['name']);
+
+ return $vars;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/SyliusInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/SyliusInstaller.php
new file mode 100644
index 00000000..c82bd855
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/SyliusInstaller.php
@@ -0,0 +1,11 @@
+ */
+ protected $locations = array(
+ 'theme' => 'themes/{$name}/',
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/TaoInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/TaoInstaller.php
new file mode 100644
index 00000000..8c1d8144
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/TaoInstaller.php
@@ -0,0 +1,32 @@
+ */
+ protected $locations = array(
+ 'extension' => '{$name}'
+ );
+
+ public function inflectPackageVars(array $vars): array
+ {
+ $extra = $this->package->getExtra();
+
+ if (array_key_exists(self::EXTRA_TAO_EXTENSION_NAME, $extra)) {
+ $vars['name'] = $extra[self::EXTRA_TAO_EXTENSION_NAME];
+ return $vars;
+ }
+
+ $vars['name'] = str_replace('extension-', '', $vars['name']);
+ $vars['name'] = str_replace('-', ' ', $vars['name']);
+ $vars['name'] = lcfirst(str_replace(' ', '', ucwords($vars['name'])));
+
+ return $vars;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/TastyIgniterInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/TastyIgniterInstaller.php
new file mode 100644
index 00000000..39ceae07
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/TastyIgniterInstaller.php
@@ -0,0 +1,85 @@
+ */
+ protected $locations = [
+ 'module' => 'app/{$name}/',
+ 'extension' => 'extensions/{$vendor}/{$name}/',
+ 'theme' => 'themes/{$name}/',
+ ];
+
+ /**
+ * Format package name.
+ *
+ * Cut off leading 'ti-ext-' or 'ti-theme-' if present.
+ * Strip vendor name of characters that is not alphanumeric or an underscore
+ *
+ */
+ public function inflectPackageVars(array $vars): array
+ {
+ $extra = $this->package->getExtra();
+
+ if ($vars['type'] === 'tastyigniter-module') {
+ return $this->inflectModuleVars($vars);
+ }
+
+ if ($vars['type'] === 'tastyigniter-extension') {
+ return $this->inflectExtensionVars($vars, $extra);
+ }
+
+ if ($vars['type'] === 'tastyigniter-theme') {
+ return $this->inflectThemeVars($vars, $extra);
+ }
+
+ return $vars;
+ }
+
+ /**
+ * @param array $vars
+ * @return array
+ */
+ protected function inflectModuleVars(array $vars): array
+ {
+ $vars['name'] = $this->pregReplace('/^ti-module-/', '', $vars['name']);
+
+ return $vars;
+ }
+
+ /**
+ * @param array $vars
+ * @param array $extra
+ * @return array
+ */
+ protected function inflectExtensionVars(array $vars, array $extra): array
+ {
+ if (!empty($extra['tastyigniter-extension']['code'])) {
+ $parts = explode('.', $extra['tastyigniter-extension']['code']);
+ $vars['vendor'] = (string)$parts[0];
+ $vars['name'] = (string)($parts[1] ?? '');
+ }
+
+ $vars['vendor'] = $this->pregReplace('/[^a-z0-9_]/i', '', $vars['vendor']);
+ $vars['name'] = $this->pregReplace('/^ti-ext-/', '', $vars['name']);
+
+ return $vars;
+ }
+
+ /**
+ * @param array $vars
+ * @param array $extra
+ * @return array
+ */
+ protected function inflectThemeVars(array $vars, array $extra): array
+ {
+ if (!empty($extra['tastyigniter-theme']['code'])) {
+ $vars['name'] = $extra['tastyigniter-theme']['code'];
+ }
+
+ $vars['name'] = $this->pregReplace('/^ti-theme-/', '', $vars['name']);
+
+ return $vars;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/TheliaInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/TheliaInstaller.php
new file mode 100644
index 00000000..896bed5c
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/TheliaInstaller.php
@@ -0,0 +1,14 @@
+ */
+ protected $locations = array(
+ 'module' => 'local/modules/{$name}/',
+ 'frontoffice-template' => 'templates/frontOffice/{$name}/',
+ 'backoffice-template' => 'templates/backOffice/{$name}/',
+ 'email-template' => 'templates/email/{$name}/',
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/TuskInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/TuskInstaller.php
new file mode 100644
index 00000000..3b5f1424
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/TuskInstaller.php
@@ -0,0 +1,17 @@
+
+ */
+class TuskInstaller extends BaseInstaller
+{
+ /** @var array */
+ protected $locations = array(
+ 'task' => '.tusk/tasks/{$name}/',
+ 'command' => '.tusk/commands/{$name}/',
+ 'asset' => 'assets/tusk/{$name}/',
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/UserFrostingInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/UserFrostingInstaller.php
new file mode 100644
index 00000000..a646c5b2
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/UserFrostingInstaller.php
@@ -0,0 +1,11 @@
+ */
+ protected $locations = array(
+ 'sprinkle' => 'app/sprinkles/{$name}/',
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/VanillaInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/VanillaInstaller.php
new file mode 100644
index 00000000..06d5db3a
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/VanillaInstaller.php
@@ -0,0 +1,12 @@
+ */
+ protected $locations = array(
+ 'plugin' => 'plugins/{$name}/',
+ 'theme' => 'themes/{$name}/',
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/VgmcpInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/VgmcpInstaller.php
new file mode 100644
index 00000000..cf094dd5
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/VgmcpInstaller.php
@@ -0,0 +1,59 @@
+ */
+ protected $locations = array(
+ 'bundle' => 'src/{$vendor}/{$name}/',
+ 'theme' => 'themes/{$name}/'
+ );
+
+ /**
+ * Format package name.
+ *
+ * For package type vgmcp-bundle, cut off a trailing '-bundle' if present.
+ *
+ * For package type vgmcp-theme, cut off a trailing '-theme' if present.
+ *
+ */
+ public function inflectPackageVars(array $vars): array
+ {
+ if ($vars['type'] === 'vgmcp-bundle') {
+ return $this->inflectPluginVars($vars);
+ }
+
+ if ($vars['type'] === 'vgmcp-theme') {
+ return $this->inflectThemeVars($vars);
+ }
+
+ return $vars;
+ }
+
+ /**
+ * @param array $vars
+ * @return array
+ */
+ protected function inflectPluginVars(array $vars): array
+ {
+ $vars['name'] = $this->pregReplace('/-bundle$/', '', $vars['name']);
+ $vars['name'] = str_replace(array('-', '_'), ' ', $vars['name']);
+ $vars['name'] = str_replace(' ', '', ucwords($vars['name']));
+
+ return $vars;
+ }
+
+ /**
+ * @param array $vars
+ * @return array
+ */
+ protected function inflectThemeVars(array $vars): array
+ {
+ $vars['name'] = $this->pregReplace('/-theme$/', '', $vars['name']);
+ $vars['name'] = str_replace(array('-', '_'), ' ', $vars['name']);
+ $vars['name'] = str_replace(' ', '', ucwords($vars['name']));
+
+ return $vars;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/WHMCSInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/WHMCSInstaller.php
new file mode 100644
index 00000000..91b19fd0
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/WHMCSInstaller.php
@@ -0,0 +1,22 @@
+ */
+ protected $locations = array(
+ 'addons' => 'modules/addons/{$vendor}_{$name}/',
+ 'fraud' => 'modules/fraud/{$vendor}_{$name}/',
+ 'gateways' => 'modules/gateways/{$vendor}_{$name}/',
+ 'notifications' => 'modules/notifications/{$vendor}_{$name}/',
+ 'registrars' => 'modules/registrars/{$vendor}_{$name}/',
+ 'reports' => 'modules/reports/{$vendor}_{$name}/',
+ 'security' => 'modules/security/{$vendor}_{$name}/',
+ 'servers' => 'modules/servers/{$vendor}_{$name}/',
+ 'social' => 'modules/social/{$vendor}_{$name}/',
+ 'support' => 'modules/support/{$vendor}_{$name}/',
+ 'templates' => 'templates/{$vendor}_{$name}/',
+ 'includes' => 'includes/{$vendor}_{$name}/'
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/WinterInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/WinterInstaller.php
new file mode 100644
index 00000000..f75a6817
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/WinterInstaller.php
@@ -0,0 +1,71 @@
+ */
+ protected $locations = array(
+ 'module' => 'modules/{$name}/',
+ 'plugin' => 'plugins/{$vendor}/{$name}/',
+ 'theme' => 'themes/{$name}/'
+ );
+
+ /**
+ * Format package name.
+ *
+ * For package type winter-plugin, cut off a trailing '-plugin' if present.
+ *
+ * For package type winter-theme, cut off a trailing '-theme' if present.
+ */
+ public function inflectPackageVars(array $vars): array
+ {
+ if ($vars['type'] === 'winter-module') {
+ return $this->inflectModuleVars($vars);
+ }
+
+ if ($vars['type'] === 'winter-plugin') {
+ return $this->inflectPluginVars($vars);
+ }
+
+ if ($vars['type'] === 'winter-theme') {
+ return $this->inflectThemeVars($vars);
+ }
+
+ return $vars;
+ }
+
+ /**
+ * @param array $vars
+ * @return array
+ */
+ protected function inflectModuleVars(array $vars): array
+ {
+ $vars['name'] = $this->pregReplace('/^wn-|-module$/', '', $vars['name']);
+
+ return $vars;
+ }
+
+ /**
+ * @param array $vars
+ * @return array
+ */
+ protected function inflectPluginVars(array $vars): array
+ {
+ $vars['name'] = $this->pregReplace('/^wn-|-plugin$/', '', $vars['name']);
+ $vars['vendor'] = $this->pregReplace('/[^a-z0-9_]/i', '', $vars['vendor']);
+
+ return $vars;
+ }
+
+ /**
+ * @param array $vars
+ * @return array
+ */
+ protected function inflectThemeVars(array $vars): array
+ {
+ $vars['name'] = $this->pregReplace('/^wn-|-theme$/', '', $vars['name']);
+
+ return $vars;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/WolfCMSInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/WolfCMSInstaller.php
new file mode 100644
index 00000000..58a95879
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/WolfCMSInstaller.php
@@ -0,0 +1,11 @@
+ */
+ protected $locations = array(
+ 'plugin' => 'wolf/plugins/{$name}/',
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/WordPressInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/WordPressInstaller.php
new file mode 100644
index 00000000..d46d5ab8
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/WordPressInstaller.php
@@ -0,0 +1,14 @@
+ */
+ protected $locations = array(
+ 'plugin' => 'wp-content/plugins/{$name}/',
+ 'theme' => 'wp-content/themes/{$name}/',
+ 'muplugin' => 'wp-content/mu-plugins/{$name}/',
+ 'dropin' => 'wp-content/{$name}/',
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/YawikInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/YawikInstaller.php
new file mode 100644
index 00000000..d609dea5
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/YawikInstaller.php
@@ -0,0 +1,23 @@
+ */
+ protected $locations = array(
+ 'module' => 'module/{$name}/',
+ );
+
+ /**
+ * Format package name to CamelCase
+ */
+ public function inflectPackageVars(array $vars): array
+ {
+ $vars['name'] = strtolower($this->pregReplace('/(?<=\\w)([A-Z])/', '_\\1', $vars['name']));
+ $vars['name'] = str_replace(array('-', '_'), ' ', $vars['name']);
+ $vars['name'] = str_replace(' ', '', ucwords($vars['name']));
+
+ return $vars;
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/ZendInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/ZendInstaller.php
new file mode 100644
index 00000000..ccfcd4a0
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/ZendInstaller.php
@@ -0,0 +1,13 @@
+ */
+ protected $locations = array(
+ 'library' => 'library/{$name}/',
+ 'extra' => 'extras/library/{$name}/',
+ 'module' => 'module/{$name}/',
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/ZikulaInstaller.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/ZikulaInstaller.php
new file mode 100644
index 00000000..d1fd1d78
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/Composer/Installers/ZikulaInstaller.php
@@ -0,0 +1,12 @@
+ */
+ protected $locations = array(
+ 'module' => 'modules/{$vendor}-{$name}/',
+ 'theme' => 'themes/{$vendor}-{$name}/'
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/composer/installers/src/bootstrap.php b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/bootstrap.php
new file mode 100644
index 00000000..a5bb9add
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/composer/installers/src/bootstrap.php
@@ -0,0 +1,18 @@
+= 70200)) {
+ $issues[] = 'Your Composer dependencies require a PHP version ">= 7.2.0". You are running ' . PHP_VERSION . '.';
+}
+
+if ($issues) {
+ if (!headers_sent()) {
+ header('HTTP/1.1 500 Internal Server Error');
+ }
+ if (!ini_get('display_errors')) {
+ if (PHP_SAPI === 'cli' || PHP_SAPI === 'phpdbg') {
+ fwrite(STDERR, 'Composer detected issues in your platform:' . PHP_EOL.PHP_EOL . implode(PHP_EOL, $issues) . PHP_EOL.PHP_EOL);
+ } elseif (!headers_sent()) {
+ echo 'Composer detected issues in your platform:' . PHP_EOL.PHP_EOL . str_replace('You are running '.PHP_VERSION.'.', '', implode(PHP_EOL, $issues)) . PHP_EOL.PHP_EOL;
+ }
+ }
+ trigger_error(
+ 'Composer detected issues in your platform: ' . implode(' ', $issues),
+ E_USER_ERROR
+ );
+}
diff --git a/wp/wp-content/plugins/imagify/vendor/dangoodman/composer-for-wordpress/ComposerForWordpress.php b/wp/wp-content/plugins/imagify/vendor/dangoodman/composer-for-wordpress/ComposerForWordpress.php
new file mode 100644
index 00000000..a155eecd
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/vendor/dangoodman/composer-for-wordpress/ComposerForWordpress.php
@@ -0,0 +1,75 @@
+ array(
+ array('onPostAutoloadDump', 0)
+ ),
+ );
+ }
+
+ public function onPostAutoloadDump(Event $event)
+ {
+ $composerConfig = $event->getComposer()->getConfig();
+ $composerAutoloadDir = "{$composerConfig->get('vendor-dir')}/composer";
+
+ $classLoader = "{$composerAutoloadDir}/ClassLoader.php";
+ $autoloadReal = "{$composerAutoloadDir}/autoload_real.php";
+ $autoloadStatic = "{$composerAutoloadDir}/autoload_static.php";
+
+ $suffix = $composerConfig->get('classloader-suffix') ?: md5(uniqid('', true));
+
+ self::replaceInFiles(
+ array($classLoader, $autoloadReal),
+ '/Composer\\\\Autoload(;|\\\\(?!ComposerStaticInit))/',
+ "Composer\\Autoload{$suffix}\$1"
+ );
+
+ self::replaceInFiles(
+ array($autoloadStatic),
+ array(
+ '/\bClassLoader\b/'
+ => "ClassLoader{$suffix}",
+ '/'.preg_quote("\nnamespace Composer\\Autoload;\n", '/').'/'
+ => "$0\nuse Composer\\Autoload{$suffix}\\ClassLoader as ClassLoader{$suffix};\n\n",
+ )
+ );
+ }
+
+ private static function replaceInFiles(array $files, $search, $replace = null)
+ {
+ if (func_num_args() == 3) {
+ $search = array($search => $replace);
+ }
+
+ foreach ($files as $file) {
+ $contents = file_get_contents($file);
+ $contents = preg_replace(array_keys($search), array_values($search), $contents);
+ file_put_contents($file, $contents);
+ }
+ }
+}
diff --git a/wp/wp-content/plugins/imagify/views/admin/admin-bar-status.php b/wp/wp-content/plugins/imagify/views/admin/admin-bar-status.php
new file mode 100644
index 00000000..d59aff71
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/views/admin/admin-bar-status.php
@@ -0,0 +1,41 @@
+
+
+
+
+
+
+
+
' . $data['unconsumed_quota'] . '%' );
+ ?>
+
+
+
+
+
+
+
+
diff --git a/wp/wp-content/plugins/imagify/views/button/compare-images.php b/wp/wp-content/plugins/imagify/views/button/compare-images.php
new file mode 100644
index 00000000..0b37b8a0
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/views/button/compare-images.php
@@ -0,0 +1,13 @@
+%7$s',
+ esc_url( $data['url'] ),
+ $data['media_id'],
+ esc_url( $data['backup_url'] ),
+ esc_url( $data['original_url'] ),
+ $data['width'],
+ $data['height'],
+ esc_html__( 'Compare Original VS Optimized', 'imagify' )
+);
diff --git a/wp/wp-content/plugins/imagify/views/button/delete-webp.php b/wp/wp-content/plugins/imagify/views/button/delete-webp.php
new file mode 100644
index 00000000..527bef57
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/views/button/delete-webp.php
@@ -0,0 +1,31 @@
+build_attributes( $data['atts'] );
+?>
+
+>
+
+
+
+
+print_js_template_in_footer( 'button/processing' );
+}
diff --git a/wp/wp-content/plugins/imagify/views/button/generate-webp.php b/wp/wp-content/plugins/imagify/views/button/generate-webp.php
new file mode 100644
index 00000000..b4a15c75
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/views/button/generate-webp.php
@@ -0,0 +1,33 @@
+build_attributes( $data['atts'] );
+?>
+
+>
+
+
+
+
+print_js_template_in_footer( 'button/processing' );
+}
diff --git a/wp/wp-content/plugins/imagify/views/button/optimize-missing-sizes.php b/wp/wp-content/plugins/imagify/views/button/optimize-missing-sizes.php
new file mode 100644
index 00000000..bede0e14
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/views/button/optimize-missing-sizes.php
@@ -0,0 +1,39 @@
+build_attributes( $data['atts'] );
+?>
+
+>
+
+ ',
+ ''
+ );
+ ?>
+
+
+print_js_template_in_footer( 'button/processing' );
+}
diff --git a/wp/wp-content/plugins/imagify/views/button/optimize.php b/wp/wp-content/plugins/imagify/views/button/optimize.php
new file mode 100644
index 00000000..89e0a79f
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/views/button/optimize.php
@@ -0,0 +1,30 @@
+build_attributes( $data['atts'] );
+?>
+
+>
+
+
+
+print_js_template_in_footer( 'button/processing' );
+}
diff --git a/wp/wp-content/plugins/imagify/views/button/processing.php b/wp/wp-content/plugins/imagify/views/button/processing.php
new file mode 100644
index 00000000..dc9d7bcf
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/views/button/processing.php
@@ -0,0 +1,16 @@
+
+
+
+
+
+
+
+print_js_template_in_footer( 'button/processing' );
diff --git a/wp/wp-content/plugins/imagify/views/button/re-optimize.php b/wp/wp-content/plugins/imagify/views/button/re-optimize.php
new file mode 100644
index 00000000..3d9d1adc
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/views/button/re-optimize.php
@@ -0,0 +1,46 @@
+ __( 'Lossless', 'imagify' ),
+ 1 => __( 'Smart', 'imagify' ),
+ 2 => __( 'Smart', 'imagify' ),
+];
+$level_label = $level_labels[ $data['optimization_level'] ];
+
+$html_atts = $this->build_attributes( $data['atts'] );
+?>
+
+>
+
+
+ ' . esc_html( $level_label ) . ''
+ );
+ ?>
+
+
+
+print_js_template_in_footer( 'button/processing' );
+}
diff --git a/wp/wp-content/plugins/imagify/views/button/refresh-status.php b/wp/wp-content/plugins/imagify/views/button/refresh-status.php
new file mode 100644
index 00000000..af429923
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/views/button/refresh-status.php
@@ -0,0 +1,31 @@
+build_attributes( $data['atts'] );
+?>
+
+>
+
+
+
+
+print_js_template_in_footer( 'button/processing' );
+}
diff --git a/wp/wp-content/plugins/imagify/views/button/restore.php b/wp/wp-content/plugins/imagify/views/button/restore.php
new file mode 100644
index 00000000..2daeda9f
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/views/button/restore.php
@@ -0,0 +1,31 @@
+build_attributes( $data['atts'] );
+?>
+
+>
+
+
+
+
+print_js_template_in_footer( 'button/processing' );
+}
diff --git a/wp/wp-content/plugins/imagify/views/button/retry-optimize.php b/wp/wp-content/plugins/imagify/views/button/retry-optimize.php
new file mode 100644
index 00000000..12d4a9fb
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/views/button/retry-optimize.php
@@ -0,0 +1,48 @@
+build_attributes( $data['atts'] );
+
+if ( ! empty( $data['error'] ) ) {
+ ?>
+
+ true,
+ 'code' => true,
+ 'em' => true,
+ 'strong' => true,
+ ]
+ );
+ ?>
+
+
+
+>
+
+
+
+print_js_template_in_footer( 'button/processing' );
+}
diff --git a/wp/wp-content/plugins/imagify/views/container/data-actions.php b/wp/wp-content/plugins/imagify/views/container/data-actions.php
new file mode 100644
index 00000000..9d4bd822
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/views/container/data-actions.php
@@ -0,0 +1,9 @@
+
+
+
+
+
+
+
+
diff --git a/wp/wp-content/plugins/imagify/views/modal-payment.php b/wp/wp-content/plugins/imagify/views/modal-payment.php
new file mode 100644
index 00000000..9e21fbfe
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/views/modal-payment.php
@@ -0,0 +1,433 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ ' . number_format_i18n( $attachments_number ) . ' '
+ );
+ ?>
+
+
+
+
+
+
+ 0'
+ );
+ ?>
+
+
+
+ 0'
+ );
+ ?>
+
+
+
+
+
+ print_template( 'part-discount-banner' ); ?>
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ 1 GB
+
+
+
+ ' . number_format_i18n( 5000 ) . ' '
+ );
+ ?>
+
+
+
+
+
+ $
+
+
+
+ 3
+ .99
+
+
+ 3
+ .16
+
+
+
+
+
+
+
+ additional Gb', 'imagify' ),
+ ' '
+ );
+ ?>
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ 3 GB
+
+
+ ' . number_format_i18n( 54000 ) . ' '
+ );
+ ?>
+
+
+
+
+
+ $
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ coupon code use it here:', 'imagify' ); ?>
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ print_template( 'part-settings-discount-banner' ); ?>
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ ',
+ ' '
+ );
+ ?>
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ 12.24 %
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ 68.36 %
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ 86.57 %
+
+
+
+
+
+
+
+
+
+
+
+
+print_template( 'notice-header', array(
+ 'classes' => array( 'error' ),
+) );
+
+$backup_path = $this->filesystem->make_path_relative( get_imagify_backup_dir_path( true ) );
+
+if ( $this->filesystem->exists( get_imagify_backup_dir_path() ) ) {
+ /* translators: %s is a file path. */
+ $message = __( 'The backup folder %s is not writable by the server, original images cannot be saved!', 'imagify' );
+} else {
+ /* translators: %s is a file path. */
+ $message = __( 'The backup folder %s cannot be created. Is its parent directory writable by the server? Original images cannot be saved!', 'imagify' );
+}
+
+echo '' . sprintf( $message, "$backup_path" ) . '
';
+
+$this->print_template( 'notice-footer' );
diff --git a/wp/wp-content/plugins/imagify/views/notice-bulk-optimization-complete.php b/wp/wp-content/plugins/imagify/views/notice-bulk-optimization-complete.php
new file mode 100644
index 00000000..d05536ba
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/views/notice-bulk-optimization-complete.php
@@ -0,0 +1,29 @@
+
+
+
+
+
+
+
+
+
+
+
',
+ ''
+ );
+ ?>
+
+
+print_template( 'notice-footer', [ 'dismissible' => 'bulk-optimization-complete' ] ); ?>
diff --git a/wp/wp-content/plugins/imagify/views/notice-bulk-optimization-running.php b/wp/wp-content/plugins/imagify/views/notice-bulk-optimization-running.php
new file mode 100644
index 00000000..a7736550
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/views/notice-bulk-optimization-running.php
@@ -0,0 +1,19 @@
+
+
+
+
+
+ ',
+ '',
+ '',
+ ' '
+ );
+ ?>
+
+print_template( 'notice-footer', [ 'dismissible' => 'bulk-optimization-complete' ] ); ?>
diff --git a/wp/wp-content/plugins/imagify/views/notice-footer.php b/wp/wp-content/plugins/imagify/views/notice-footer.php
new file mode 100644
index 00000000..6b079aba
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/views/notice-footer.php
@@ -0,0 +1,8 @@
+
+
+
+
+
+
diff --git a/wp/wp-content/plugins/imagify/views/notice-grid-view.php b/wp/wp-content/plugins/imagify/views/notice-grid-view.php
new file mode 100644
index 00000000..9c5dc938
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/views/notice-grid-view.php
@@ -0,0 +1,13 @@
+print_template( 'notice-header', array(
+ 'title' => __( 'You\'re missing out!', 'imagify' ),
+) );
+?>
+
+
+print_template( 'notice-footer', array(
+ 'dismissible' => 'grid-view',
+) );
diff --git a/wp/wp-content/plugins/imagify/views/notice-header.php b/wp/wp-content/plugins/imagify/views/notice-header.php
new file mode 100644
index 00000000..f9f170d5
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/views/notice-header.php
@@ -0,0 +1,12 @@
+
+
+
+
+
+
+
+
+
+
diff --git a/wp/wp-content/plugins/imagify/views/notice-http-block-external.php b/wp/wp-content/plugins/imagify/views/notice-http-block-external.php
new file mode 100644
index 00000000..82774987
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/views/notice-http-block-external.php
@@ -0,0 +1,22 @@
+print_template( 'notice-header', array(
+ 'title' => __( 'The external HTTP requests are blocked!', 'imagify' ),
+ 'classes' => array( 'error' ),
+) );
+?>
+
+ WP_HTTP_BLOCK_EXTERNAL constant in the wp-config.php to block all external HTTP requests.', 'imagify' ); ?>
+
+
+ wp-config.php file so that it works correctly.', 'imagify' ); ?>
+
+
+
+
+
+print_template( 'notice-footer', array(
+ 'dismissible' => 'http-block-external',
+) );
diff --git a/wp/wp-content/plugins/imagify/views/notice-plugins-to-deactivate.php b/wp/wp-content/plugins/imagify/views/notice-plugins-to-deactivate.php
new file mode 100644
index 00000000..67ab8e06
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/views/notice-plugins-to-deactivate.php
@@ -0,0 +1,22 @@
+print_template( 'notice-header', array(
+ 'classes' => array( 'error' ),
+) );
+?>
+
+
+
+print_template( 'notice-footer' );
diff --git a/wp/wp-content/plugins/imagify/views/notice-rating.php b/wp/wp-content/plugins/imagify/views/notice-rating.php
new file mode 100644
index 00000000..9f13d707
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/views/notice-rating.php
@@ -0,0 +1,36 @@
+print_template( 'notice-header', array(
+ 'classes' => array( 'updated' ),
+) );
+?>
+
+ ',
+ '',
+ number_format_i18n( $data )
+ );
+ ?>
+
+
+ ',
+ ' ',
+ '',
+ ' '
+ );
+ ?>
+
+ â†â†â†â†â†
+
+print_template( 'notice-footer', array(
+ 'dismissible' => 'rating',
+) );
diff --git a/wp/wp-content/plugins/imagify/views/notice-temporary.php b/wp/wp-content/plugins/imagify/views/notice-temporary.php
new file mode 100644
index 00000000..ff128a98
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/views/notice-temporary.php
@@ -0,0 +1,22 @@
+ $type_notices ) {
+ ?>
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ ',
+ ''
+ );
+ ?>
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/wp/wp-content/plugins/imagify/views/notice-wp-rocket.php b/wp/wp-content/plugins/imagify/views/notice-wp-rocket.php
new file mode 100644
index 00000000..661c1165
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/views/notice-wp-rocket.php
@@ -0,0 +1,21 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/wp/wp-content/plugins/imagify/views/notice-wrong-api-key.php b/wp/wp-content/plugins/imagify/views/notice-wrong-api-key.php
new file mode 100644
index 00000000..c65ab5d1
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/views/notice-wrong-api-key.php
@@ -0,0 +1,24 @@
+print_template( 'notice-header', array(
+ 'title' => __( 'Your API key isn\'t valid!', 'imagify' ),
+ 'classes' => array( 'error' ),
+) );
+?>
+
+
+ ',
+ '',
+ ' '
+ );
+ ?>
+
+print_template( 'notice-footer', array(
+ 'dismissible' => 'wrong-api-key',
+) );
diff --git a/wp/wp-content/plugins/imagify/views/page-bulk.php b/wp/wp-content/plugins/imagify/views/page-bulk.php
new file mode 100644
index 00000000..a6657ace
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/views/page-bulk.php
@@ -0,0 +1,190 @@
+
+
+
+ print_template( 'part-bulk-optimization-header' ); ?>
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ '
+ );
+ ?>
+
+
+
+
+
+
+
+
+ %
+
+ '
+ );
+ ?>
+
+
+
+
+
+
+
+
+
+
+ ' . esc_html( min( $data['optimized_attachments_percent'], 100 ) ) . '%'
+ );
+ ?>
+
+
+
+
+
+
+
+
+
+ print_template( 'part-upsell' ); ?>
+
+
+
+
+
+
+ print_template( 'part-bulk-optimization-success' );
+
+ $this->print_template( 'part-bulk-optimization-table', $data );
+
+ // New Feature!
+ if ( ! empty( $data['no-custom-folders'] ) ) {
+ $this->print_template( 'part-bulk-optimization-newbie' );
+ }
+ ?>
+
+
+
+
+ print_template( 'modal-payment' );
+
+ if ( Imagify_Requirements::is_api_key_valid() ) {
+ $display_infos = get_transient( 'imagify_bulk_optimization_infos' );
+
+ ?>
+
+
+
+
+
+
+
+
+ print_template( 'part-files-list-header' ); ?>
+
+
+
+
+get_option_name();
+$hidden_class = Imagify_Requirements::is_api_key_valid() ? '' : ' hidden';
+$lang = imagify_get_current_lang_in( array( 'de', 'es', 'fr', 'it' ) );
+
+/* Ads notice */
+$plugins = get_plugins();
+$notice = 'wp-rocket';
+$user_id = get_current_user_id();
+$notices = get_user_meta( $user_id, '_imagify_ignore_ads', true );
+$notices = $notices && is_array( $notices ) ? array_flip( $notices ) : array();
+$wrapper_class = isset( $notices[ $notice ] ) || isset( $plugins['wp-rocket/wp-rocket.php'] ) ? 'imagify-have-rocket' : 'imagify-dont-have-rocket';
+?>
+
+
+
+
+ print_template( 'part-settings-header' ); ?>
+
+
+
+ print_template( 'part-rocket-ad' );
+ $this->print_template( 'modal-settings-infos' );
+ $this->print_template( 'modal-settings-partners-infos' );
+ $this->print_template( 'modal-settings-visual-comparison' );
+ $this->print_template( 'modal-payment' );
+ ?>
+
+
+
+
+
– Imagify
+
+
+
+
+
+
+
+
+
+
+
+
+
+ print_template( 'part-documentation-link' ); ?>
+
+
+
+
+
+
+ ' . esc_html( $data['quota'] ) . '%'
+ );
+ ?>
+
+
+
+
+
+
+
+
+
diff --git a/wp/wp-content/plugins/imagify/views/part-bulk-optimization-overquota-alert.php b/wp/wp-content/plugins/imagify/views/part-bulk-optimization-overquota-alert.php
new file mode 100644
index 00000000..49093c5e
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/views/part-bulk-optimization-overquota-alert.php
@@ -0,0 +1,21 @@
+ 'plugin',
+ 'utm_medium' => 'imagify-wp',
+ 'utm_content' => 'over-quota',
+) );
+?>
+
+
+
+
+
+
+
diff --git a/wp/wp-content/plugins/imagify/views/part-bulk-optimization-success.php b/wp/wp-content/plugins/imagify/views/part-bulk-optimization-success.php
new file mode 100644
index 00000000..044fd566
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/views/part-bulk-optimization-success.php
@@ -0,0 +1,51 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ ',
+ ' ',
+ ' '
+ );
+ ?>
+
+
+
+
+
+
+
+
+
+
+
+ >
+
+
+ >
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ print_template( 'input/selector', [
+ 'current_label' => __( 'Current level:', 'imagify' ),
+ 'name' => 'level[' . $data['group_id'] . ']',
+ 'value' => $data['level'],
+ 'values' => [
+ 0 => imagify_get_optimization_level_label( 0, '%ICON% %s' ),
+ 2 => imagify_get_optimization_level_label( 2, '%ICON% %s' ),
+ ],
+ ] );
+ ?>
+
+
+
+
+
+
diff --git a/wp/wp-content/plugins/imagify/views/part-bulk-optimization-table.php b/wp/wp-content/plugins/imagify/views/part-bulk-optimization-table.php
new file mode 100644
index 00000000..75aa41d6
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/views/part-bulk-optimization-table.php
@@ -0,0 +1,113 @@
+
+
+
+
+
+
+
+
+
+
class="imagify-row-progress " >
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ get_bulk_instance( $group['context'] )->get_context_data();
+ $group = array_merge( $group, $context_data );
+ $default_level = Imagify_Options::get_instance()->get( 'optimization_level' );
+
+ if ( Imagify_Options::get_instance()->get( 'lossless' ) ) {
+ $default_level = 0;
+ }
+
+ $group['level'] = $default_level;
+
+ $running = get_transient( "imagify_{$group['context']}_optimize_running" );
+
+ $group['spinner_class'] = 'hidden';
+ $group['spinner_aria'] = 'aria-hidden="true"';
+ $group['checkbox_class'] = '';
+ $group['checkbox_aria'] = 'aria-hidden="false"';
+
+ if ( false !== $running ) {
+ $group['spinner_class'] = '';
+ $group['spinner_aria'] = 'aria-hidden="false"';
+ $group['checkbox_class'] = 'hidden';
+ $group['checkbox_aria'] = 'aria-hidden="true"';
+ }
+
+ $this->print_template( 'part-bulk-optimization-table-row-folder-type', $group );
+ }
+ ?>
+
+
+
+
+
diff --git a/wp/wp-content/plugins/imagify/views/part-discount-banner.php b/wp/wp-content/plugins/imagify/views/part-discount-banner.php
new file mode 100644
index 00000000..762a77a2
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/views/part-discount-banner.php
@@ -0,0 +1,26 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ localize_script( 'options', 'imagifyUser', array(
+ 'action' => 'imagify_get_user_data',
+ '_wpnonce' => wp_create_nonce( 'imagify_get_user_data' ),
+ ) );
+ }
+}
+?>
+
+print_template( 'part-upsell' ); ?>
+
+
+
+
+
+
+
+
+
+
+ get( 'api_key' ) ) {
+ ?>
+
+
+
+
+
+
+ get( 'api_key' ) ? esc_html__( 'API Key', 'imagify' ) : esc_html__( 'Enter Your API Key Below', 'imagify' ); ?>
+
+
+
+
+ âś“
+
+
+ get( 'api_key' ) ) {
+ ?>
+
+
+
+
+
+
+
+
+
+
+get_active_folders_column( 'path' );
+$themes = array();
+
+if ( $custom_folders ) {
+ $custom_folders = array_combine( $custom_folders, $custom_folders );
+ $custom_folders = array_map( array( 'Imagify_Files_Scan', 'remove_placeholder' ), $custom_folders );
+ $custom_folders = array_map( 'trailingslashit', $custom_folders );
+ $custom_folders = array_filter( $custom_folders, array( 'Imagify_Files_Scan', 'is_path_autorized' ) );
+}
+
+if ( $custom_folders ) {
+ $custom_folders = array_map( array( $this->filesystem, 'make_path_relative' ), $custom_folders );
+ $custom_folders = array_map( 'untrailingslashit', $custom_folders );
+ natcasesort( $custom_folders );
+ $custom_folders = array_map( 'trailingslashit', $custom_folders );
+
+ if ( isset( $custom_folders['{{ROOT}}/'] ) ) {
+ $custom_folders['{{ROOT}}/'] = __( 'Site\'s root', 'imagify' );
+ }
+}
+
+// Current used theme(s).
+if ( ! is_network_admin() ) {
+ $current_theme = wp_get_theme();
+ $themes_not_added = array();
+
+ foreach ( array( $current_theme, $current_theme->parent() ) as $theme ) {
+ if ( ! $theme || ! $theme->exists() ) {
+ continue;
+ }
+
+ $theme_path = trailingslashit( $theme->get_stylesheet_directory() );
+
+ if ( ! Imagify_Files_Scan::is_path_forbidden( $theme_path ) ) {
+ $theme = array(
+ 'name' => $theme->display( 'Name' ),
+ 'path' => Imagify_Files_Scan::add_placeholder( $theme_path ),
+ 'label' => $this->filesystem->make_path_relative( $theme_path ),
+ );
+
+ $themes[ $theme['path'] ] = $theme;
+ $added = false;
+ $rel_path = strtolower( $theme['label'] );
+
+ foreach ( $custom_folders as $path => $label ) {
+ if ( strpos( $rel_path, strtolower( $label ) ) === 0 ) {
+ $added = true;
+ break;
+ }
+ }
+
+ if ( ! $added ) {
+ $themes_not_added[] = $theme['path'];
+ }
+ }
+ }
+
+ $themes_count = count( $themes );
+}
+?>
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ ' . $theme['name'] . '' );
+ ?>
+
+ $theme ) {
+ $themes[ $path ] = esc_attr( $theme['path'] ) . '#///#' . esc_attr( $theme['label'] );
+ }
+ ?>
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ $label ) {
+ $this->print_template( 'part-settings-row-custom-folder', array(
+ 'value' => $placeholder,
+ 'label' => $label,
+ ) );
+ }
+ }
+ ?>
+
+
+
+ opening and closing tags. */
+ __( '%1$sSelecting a folder will also optimize images in sub-folders.%2$s The only exception is "Site’s root": when selected, only images that are directly at the site’s root will be optimized (sub-folders can be selected separately).', 'imagify' ),
+ '',
+ ' '
+ );
+ ?>
+
+
+
+
+
+
+
+
+
+
+
';
+?>
+
+
>
+
+ title="">
+
+
+
+
+
+
+
+
+
+
+
+ />
+
+ ">
+
+
+
+
+
+
+
+
diff --git a/wp/wp-content/plugins/imagify/views/part-settings-footer.php b/wp/wp-content/plugins/imagify/views/part-settings-footer.php
new file mode 100644
index 00000000..ae1e45cb
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/views/part-settings-footer.php
@@ -0,0 +1,28 @@
+
+
+
+ current_user_can( 'bulk-optimize' ) || imagify_get_context( 'custom-folders' )->current_user_can( 'bulk-optimize' );
+
+ if ( $user_can ) {
+ // Submit and go to bulk page.
+ submit_button(
+ esc_html__( 'Save & Go to Bulk Optimizer', 'imagify' ),
+ 'secondary imagify-button-secondary', // Type/classes.
+ 'submit-goto-bulk', // Name (id).
+ true, // Wrap.
+ array() // Other attributes.
+ );
+ }
+ }
+ ?>
+
+
+
+
— Imagify
+
+
+
+
+
+
+
+
+
+
+
+
+ get( 'api_key' ) ) {
+ ?>
+
+ ',
+ ' ',
+ '',
+ ' '
+ );
+ ?>
+
+ ', 5 ); ?>
+
+
+
+ print_template( 'part-documentation-link' ); ?>
+
+get_option_name();
+?>
+
+
+
+
+
+
+
diff --git a/wp/wp-content/plugins/imagify/views/part-settings-webp-missing-message.php b/wp/wp-content/plugins/imagify/views/part-settings-webp-missing-message.php
new file mode 100644
index 00000000..182122a3
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/views/part-settings-webp-missing-message.php
@@ -0,0 +1,17 @@
+
+
+
+
diff --git a/wp/wp-content/plugins/imagify/views/part-settings-webp.php b/wp/wp-content/plugins/imagify/views/part-settings-webp.php
new file mode 100644
index 00000000..d8c6ac40
--- /dev/null
+++ b/wp/wp-content/plugins/imagify/views/part-settings-webp.php
@@ -0,0 +1,220 @@
+
+
+
+
+
+ tag opening and closing, %3$s and %4$s are
tag opening and closing.
+ __( 'Next-Gen Images format is currently defined by the %1$simagify_nextgen_images_format%2$s filter. %3$sRead more%4$s', 'imagify' ),
+ '',
+ '',
+ ' ',
+ ' '
+ );
+
+ $message_class = 'error';
+ $disabled = true;
+ }
+
+ $attributes = [
+ 'aria-describedby' => 'describe-optimization_format',
+ ];
+
+ if ( $disabled ) {
+ $attributes['disabled'] = true;
+ }
+
+ $settings->field_inline_radio_list(
+ [
+ 'option_name' => 'optimization_format',
+ 'legend' => __( 'Next-gen image format', 'imagify' ),
+ 'info' => $message,
+ 'info_class' => $message_class,
+ 'values' => [
+ 'off' => __( 'Off', 'imagify' ),
+ 'avif' => __( 'AVIF', 'imagify' ),
+ 'webp' => __( 'WebP', 'imagify' ),
+ ],
+ 'attributes' => $attributes,
+ ]
+ );
+ ?>
+
+
+
+
+
+ field_checkbox( [
+ 'option_name' => 'display_nextgen',
+ 'label' => __( 'Display images in Next-Gen format on the site', 'imagify' ),
+ ] );
+ ?>
+
+
+ field_radio_list( [
+ 'option_name' => 'display_nextgen_method',
+ 'values' => [
+ 'rewrite' => __( 'Use rewrite rules', 'imagify' ),
+ /* translators: 1 and 2 are
tag opening and closing. */
+ 'picture' => sprintf( __( 'Use <picture> tags %1$s(preferred)%2$s', 'imagify' ), '', ' ' ),
+ ],
+ 'attributes' => [
+ 'aria-describedby' => 'describe-convert_to_webp',
+ ],
+ ] );
+ ?>
+
+
+ ' . esc_url( $cdn_source['url'] ) . '',
+ '' . esc_html( $cdn_source['name'] ) . ''
+ );
+ } elseif ( ! empty( $cdn_source['name'] ) ) {
+ printf(
+ /* translators: 1 is an URL, 2 is a plugin name. */
+ esc_html__( 'Your CDN URL is set to %1$s by %2$s.', 'imagify' ),
+ '' . esc_url( $cdn_source['url'] ) . '',
+ '' . esc_html( $cdn_source['name'] ) . ''
+ );
+ } else {
+ printf(
+ /* translators: %s is an URL. */
+ esc_html__( 'Your CDN URL is set to %1$s by filter.', 'imagify' ),
+ '' . esc_url( $cdn_source['url'] ) . ''
+ );
+ }
+
+ $settings->field_hidden( [
+ 'option_name' => 'cdn_url',
+ 'current_value' => $cdn_source['url'],
+ ] );
+ } else {
+ $settings->field_text_box( [
+ 'option_name' => 'cdn_url',
+ 'label' => __( 'If you use a CDN, specify the URL:', 'imagify' ),
+ 'attributes' => [
+ 'size' => 30,
+ 'placeholder' => __( 'https://cdn.example.com', 'imagify' ),
+ ],
+ ] );
+ }
+ ?>
+
+
+
+
+
+ get_file_path( true );
+
+ if ( $conf_file_path ) {
+ printf(
+ /* translators: 1 is a file name, 2 is a tag opening, 3 is the tag closing. */
+ esc_html__( 'The first option adds rewrite rules to your site’s configuration file (%1$s) and does not alter your pages code. %2$sThis does not work with CDN though.%3$s', 'imagify' ),
+ '' . esc_html( $conf_file_path ) . '',
+ '',
+ ' '
+ );
+
+ echo ' ';
+ }
+
+ printf(
+ /* translators: 1 and 2 are HTML tag names, 3 is a tag opening, 4 is the tag closing. */
+ esc_html__( 'The second option replaces the %1$s tags with %2$s tags. %3$sThis is the preferred solution but some themes may break%4$s, so make sure to verify that everything seems fine.', 'imagify' ),
+ '<img>',
+ '<picture>',
+ '',
+ ' '
+ );
+
+ echo ' ';
+
+ /**
+ * Add more information about WebP.
+ *
+ * @since 1.9
+ * @author Grégory Viguier
+ */
+ do_action( 'imagify_settings_webp_info' );
+ ?>
+
+
+
+ get_cached_stat();
+
+ if ( $count ) {
+ ?>
+
+ print_template( 'part-settings-webp-missing-message', [ 'count' => $count ] ); ?>
+
+
+
+
+
+
+ get_stat();
+ $total = get_transient( 'imagify_missing_next_gen_total' );
+ $progress = 0;
+ $aria = ' aria-hidden="true"';
+ $class = 'hidden';
+ $style = '';
+
+ if (
+ false !== $total
+ &&
+ $total > 0
+ ) {
+ $aria = '';
+ $class = '';
+ $processed = $total - $remaining;
+ $progress = $processed . '/' . $total;
+ $percent = $processed / $total * 100;
+ $style = 'style="width:' . $percent . '%;"';
+ }
+ ?>
+
+
class="imagify-progress ">
+
+
+
+
+
+
+
+
+get_percent_unconsumed_quota() : 0;
+$infinite = $imagify_user->is_infinite();
+$upgrade = '';
+$price = '';
+$upgrade_link = '';
+$user_id = get_current_user_id();
+$notices = get_user_meta( $user_id, '_imagify_ignore_notices', true );
+$notices = $notices && is_array( $notices ) ? array_flip( $notices ) : [];
+$api_key_valid = Imagify_Requirements::is_api_key_valid();
+
+if (
+ $imagify_user->is_free()
+ &&
+ $api_key_valid
+ &&
+ $unconsumed_quota > 20
+) {
+ ?>
+
+
+
+
+
get_quota_icon(); ?>
+
+
+ ' . $this->get_quota_percent() . '%'
+ );
+ ?>
+
+
+
+
+
+ is_free() ) {
+ $upgrade = esc_html__( 'Upgrade your plan now for more!', 'imagify' );
+ $price = esc_html__( 'From $5.99/month only, keep going with image optimization!', 'imagify' );
+ $upgrade_link = IMAGIFY_APP_DOMAIN . '/subscription/?utm_source=plugin&utm_medium=upsell_banner';
+ } elseif ( $imagify_user->is_growth() ) {
+ $upgrade = esc_html__( 'Upgrade your plan now to keep optimizing your images.', 'imagify' );
+
+ if ( $imagify_user->is_monthly ) {
+ $price = esc_html__( 'For $9.99/month only, choose unlimited image optimization!', 'imagify' );
+ $upgrade_link = IMAGIFY_APP_DOMAIN . '/subscription/plan_switch/?label=infinite&payment_plan=1&utm_source=plugin&utm_medium=upsell_banner';
+ } else {
+ $price = esc_html__( 'For $99.9/year only, choose unlimited image optimization!', 'imagify' );
+ $upgrade_link = IMAGIFY_APP_DOMAIN . '/subscription/plan_switch/?label=infinite&payment_plan=2&utm_source=plugin&utm_medium=upsell_banner';
+ }
+ }
+ ?>
+
+
+
+
+
+
+
diff --git a/wp/wp-content/plugins/leadin/build/elementor.asset.php b/wp/wp-content/plugins/leadin/build/elementor.asset.php
new file mode 100644
index 00000000..accc85f3
--- /dev/null
+++ b/wp/wp-content/plugins/leadin/build/elementor.asset.php
@@ -0,0 +1 @@
+ array('jquery', 'react', 'react-dom', 'wp-i18n'), 'version' => '6c8968024c67158cce44');
diff --git a/wp/wp-content/plugins/leadin/build/elementor.css b/wp/wp-content/plugins/leadin/build/elementor.css
new file mode 100644
index 00000000..aaf2028e
--- /dev/null
+++ b/wp/wp-content/plugins/leadin/build/elementor.css
@@ -0,0 +1,72 @@
+/*!***************************************************************************************************************************************************************************!*\
+ !*** css ./node_modules/css-loader/dist/cjs.js!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/UIComponents/UISpinner.tsx ***!
+ \***************************************************************************************************************************************************************************/
+.sxa9zrc{-webkit-align-items:center;-webkit-box-align:center;-ms-flex-align:center;align-items:center;color:#00a4bd;display:-webkit-box;display:-webkit-flex;display:-ms-flexbox;display:flex;-webkit-flex-direction:column;-ms-flex-direction:column;flex-direction:column;-webkit-box-pack:center;-webkit-justify-content:center;-ms-flex-pack:center;justify-content:center;width:100%;height:100%;margin:'2px';}
+.s14430wa{-webkit-align-items:center;-webkit-box-align:center;-ms-flex-align:center;align-items:center;display:-webkit-box;display:-webkit-flex;display:-ms-flexbox;display:flex;-webkit-box-pack:center;-webkit-justify-content:center;-ms-flex-pack:center;justify-content:center;width:100%;height:100%;}
+.ct87ghk{fill:none;stroke:var(--ct87ghk-0);stroke-width:5;stroke-linecap:round;-webkit-transform-origin:center;-ms-transform-origin:center;transform-origin:center;}
+.avili0h{fill:none;stroke:var(--avili0h-0);stroke-width:5;stroke-linecap:round;-webkit-transform-origin:center;-ms-transform-origin:center;transform-origin:center;-webkit-animation:dashAnimation-avili0h 2s ease-in-out infinite,spinAnimation-avili0h 2s linear infinite;animation:dashAnimation-avili0h 2s ease-in-out infinite,spinAnimation-avili0h 2s linear infinite;}@-webkit-keyframes dashAnimation-avili0h{0%{stroke-dasharray:1,150;stroke-dashoffset:0;}50%{stroke-dasharray:90,150;stroke-dashoffset:-50;}100%{stroke-dasharray:90,150;stroke-dashoffset:-140;}}@keyframes dashAnimation-avili0h{0%{stroke-dasharray:1,150;stroke-dashoffset:0;}50%{stroke-dasharray:90,150;stroke-dashoffset:-50;}100%{stroke-dasharray:90,150;stroke-dashoffset:-140;}}@-webkit-keyframes spinAnimation-avili0h{{-webkit-transform:rotate(360deg);-ms-transform:rotate(360deg);transform:rotate(360deg);}}@keyframes spinAnimation-avili0h{{-webkit-transform:rotate(360deg);-ms-transform:rotate(360deg);transform:rotate(360deg);}}
+/*# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIi91c3Ivc2hhcmUvaHVic3BvdC9idWlsZC93b3Jrc3BhY2UvTGVhZGluV29yZFByZXNzUGx1Z2luL2xlYWRpbi9zY3JpcHRzL3NoYXJlZC9VSUNvbXBvbmVudHMvVUlTcGlubmVyLnRzeCJdLCJuYW1lcyI6WyIuc3hhOXpyYyIsIi5zMTQ0MzB3YSIsIi5jdDg3Z2hrIiwiLmF2aWxpMGgiXSwibWFwcGluZ3MiOiJBQUdxQkE7QUFVQUM7QUFPTkM7QUFPUUMiLCJmaWxlIjoiL3Vzci9zaGFyZS9odWJzcG90L2J1aWxkL3dvcmtzcGFjZS9MZWFkaW5Xb3JkUHJlc3NQbHVnaW4vbGVhZGluL3NjcmlwdHMvc2hhcmVkL1VJQ29tcG9uZW50cy9VSVNwaW5uZXIudHN4Iiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsganN4IGFzIF9qc3gsIGpzeHMgYXMgX2pzeHMgfSBmcm9tIFwicmVhY3QvanN4LXJ1bnRpbWVcIjtcbmltcG9ydCB7IHN0eWxlZCB9IGZyb20gJ0BsaW5hcmlhL3JlYWN0JztcbmltcG9ydCB7IENBTFlQU09fTUVESVVNLCBDQUxZUFNPIH0gZnJvbSAnLi9jb2xvcnMnO1xuY29uc3QgU3Bpbm5lck91dGVyID0gc3R5bGVkLmRpdiBgXG4gIGFsaWduLWl0ZW1zOiBjZW50ZXI7XG4gIGNvbG9yOiAjMDBhNGJkO1xuICBkaXNwbGF5OiBmbGV4O1xuICBmbGV4LWRpcmVjdGlvbjogY29sdW1uO1xuICBqdXN0aWZ5LWNvbnRlbnQ6IGNlbnRlcjtcbiAgd2lkdGg6IDEwMCU7XG4gIGhlaWdodDogMTAwJTtcbiAgbWFyZ2luOiAnMnB4JztcbmA7XG5jb25zdCBTcGlubmVySW5uZXIgPSBzdHlsZWQuZGl2IGBcbiAgYWxpZ24taXRlbXM6IGNlbnRlcjtcbiAgZGlzcGxheTogZmxleDtcbiAganVzdGlmeS1jb250ZW50OiBjZW50ZXI7XG4gIHdpZHRoOiAxMDAlO1xuICBoZWlnaHQ6IDEwMCU7XG5gO1xuY29uc3QgQ2lyY2xlID0gc3R5bGVkLmNpcmNsZSBgXG4gIGZpbGw6IG5vbmU7XG4gIHN0cm9rZTogJHtwcm9wcyA9PiBwcm9wcy5jb2xvcn07XG4gIHN0cm9rZS13aWR0aDogNTtcbiAgc3Ryb2tlLWxpbmVjYXA6IHJvdW5kO1xuICB0cmFuc2Zvcm0tb3JpZ2luOiBjZW50ZXI7XG5gO1xuY29uc3QgQW5pbWF0ZWRDaXJjbGUgPSBzdHlsZWQuY2lyY2xlIGBcbiAgZmlsbDogbm9uZTtcbiAgc3Ryb2tlOiAke3Byb3BzID0+IHByb3BzLmNvbG9yfTtcbiAgc3Ryb2tlLXdpZHRoOiA1O1xuICBzdHJva2UtbGluZWNhcDogcm91bmQ7XG4gIHRyYW5zZm9ybS1vcmlnaW46IGNlbnRlcjtcbiAgYW5pbWF0aW9uOiBkYXNoQW5pbWF0aW9uIDJzIGVhc2UtaW4tb3V0IGluZmluaXRlLFxuICAgIHNwaW5BbmltYXRpb24gMnMgbGluZWFyIGluZmluaXRlO1xuXG4gIEBrZXlmcmFtZXMgZGFzaEFuaW1hdGlvbiB7XG4gICAgMCUge1xuICAgICAgc3Ryb2tlLWRhc2hhcnJheTogMSwgMTUwO1xuICAgICAgc3Ryb2tlLWRhc2hvZmZzZXQ6IDA7XG4gICAgfVxuXG4gICAgNTAlIHtcbiAgICAgIHN0cm9rZS1kYXNoYXJyYXk6IDkwLCAxNTA7XG4gICAgICBzdHJva2UtZGFzaG9mZnNldDogLTUwO1xuICAgIH1cblxuICAgIDEwMCUge1xuICAgICAgc3Ryb2tlLWRhc2hhcnJheTogOTAsIDE1MDtcbiAgICAgIHN0cm9rZS1kYXNob2Zmc2V0OiAtMTQwO1xuICAgIH1cbiAgfVxuXG4gIEBrZXlmcmFtZXMgc3BpbkFuaW1hdGlvbiB7XG4gICAgdHJhbnNmb3JtOiByb3RhdGUoMzYwZGVnKTtcbiAgfVxuYDtcbmV4cG9ydCBkZWZhdWx0IGZ1bmN0aW9uIFVJU3Bpbm5lcih7IHNpemUgPSAyMCB9KSB7XG4gICAgcmV0dXJuIChfanN4KFNwaW5uZXJPdXRlciwgeyBjaGlsZHJlbjogX2pzeChTcGlubmVySW5uZXIsIHsgY2hpbGRyZW46IF9qc3hzKFwic3ZnXCIsIHsgaGVpZ2h0OiBzaXplLCB3aWR0aDogc2l6ZSwgdmlld0JveDogXCIwIDAgNTAgNTBcIiwgY2hpbGRyZW46IFtfanN4KENpcmNsZSwgeyBjb2xvcjogQ0FMWVBTT19NRURJVU0sIGN4OiBcIjI1XCIsIGN5OiBcIjI1XCIsIHI6IFwiMjIuNVwiIH0pLCBfanN4KEFuaW1hdGVkQ2lyY2xlLCB7IGNvbG9yOiBDQUxZUFNPLCBjeDogXCIyNVwiLCBjeTogXCIyNVwiLCByOiBcIjIyLjVcIiB9KV0gfSkgfSkgfSkpO1xufVxuIl19*/
+/*!*************************************************************************************************************************************************************************!*\
+ !*** css ./node_modules/css-loader/dist/cjs.js!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/UIComponents/UIButton.ts ***!
+ \*************************************************************************************************************************************************************************/
+.ug152ch{background-color:var(--ug152ch-0);border:3px solid var(--ug152ch-0);color:#ffffff;border-radius:3px;font-size:14px;line-height:14px;padding:12px 24px;font-family:'Lexend Deca',Helvetica,Arial,sans-serif;font-weight:500;white-space:nowrap;}
+/*# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIi91c3Ivc2hhcmUvaHVic3BvdC9idWlsZC93b3Jrc3BhY2UvTGVhZGluV29yZFByZXNzUGx1Z2luL2xlYWRpbi9zY3JpcHRzL3NoYXJlZC9VSUNvbXBvbmVudHMvVUlCdXR0b24udHMiXSwibmFtZXMiOlsiLnVnMTUyY2giXSwibWFwcGluZ3MiOiJBQUVlQSIsImZpbGUiOiIvdXNyL3NoYXJlL2h1YnNwb3QvYnVpbGQvd29ya3NwYWNlL0xlYWRpbldvcmRQcmVzc1BsdWdpbi9sZWFkaW4vc2NyaXB0cy9zaGFyZWQvVUlDb21wb25lbnRzL1VJQnV0dG9uLnRzIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsgc3R5bGVkIH0gZnJvbSAnQGxpbmFyaWEvcmVhY3QnO1xuaW1wb3J0IHsgSEVGRkFMVU1QLCBMT1JBWCwgT0xBRiB9IGZyb20gJy4vY29sb3JzJztcbmV4cG9ydCBkZWZhdWx0IHN0eWxlZC5idXR0b24gYFxuICBiYWNrZ3JvdW5kLWNvbG9yOiR7cHJvcHMgPT4gKHByb3BzLnVzZSA9PT0gJ3RlcnRpYXJ5JyA/IEhFRkZBTFVNUCA6IExPUkFYKX07XG4gIGJvcmRlcjogM3B4IHNvbGlkICR7cHJvcHMgPT4gKHByb3BzLnVzZSA9PT0gJ3RlcnRpYXJ5JyA/IEhFRkZBTFVNUCA6IExPUkFYKX07XG4gIGNvbG9yOiAke09MQUZ9XG4gIGJvcmRlci1yYWRpdXM6IDNweDtcbiAgZm9udC1zaXplOiAxNHB4O1xuICBsaW5lLWhlaWdodDogMTRweDtcbiAgcGFkZGluZzogMTJweCAyNHB4O1xuICBmb250LWZhbWlseTogJ0xleGVuZCBEZWNhJywgSGVsdmV0aWNhLCBBcmlhbCwgc2Fucy1zZXJpZjtcbiAgZm9udC13ZWlnaHQ6IDUwMDtcbiAgd2hpdGUtc3BhY2U6IG5vd3JhcDtcbmA7XG4iXX0=*/
+/*!****************************************************************************************************************************************************************************!*\
+ !*** css ./node_modules/css-loader/dist/cjs.js!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/UIComponents/UIContainer.ts ***!
+ \****************************************************************************************************************************************************************************/
+.ua13n1c{text-align:var(--ua13n1c-0);}
+/*# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIi91c3Ivc2hhcmUvaHVic3BvdC9idWlsZC93b3Jrc3BhY2UvTGVhZGluV29yZFByZXNzUGx1Z2luL2xlYWRpbi9zY3JpcHRzL3NoYXJlZC9VSUNvbXBvbmVudHMvVUlDb250YWluZXIudHMiXSwibmFtZXMiOlsiLnVhMTNuMWMiXSwibWFwcGluZ3MiOiJBQUNlQSIsImZpbGUiOiIvdXNyL3NoYXJlL2h1YnNwb3QvYnVpbGQvd29ya3NwYWNlL0xlYWRpbldvcmRQcmVzc1BsdWdpbi9sZWFkaW4vc2NyaXB0cy9zaGFyZWQvVUlDb21wb25lbnRzL1VJQ29udGFpbmVyLnRzIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsgc3R5bGVkIH0gZnJvbSAnQGxpbmFyaWEvcmVhY3QnO1xuZXhwb3J0IGRlZmF1bHQgc3R5bGVkLmRpdiBgXG4gIHRleHQtYWxpZ246ICR7cHJvcHMgPT4gKHByb3BzLnRleHRBbGlnbiA/IHByb3BzLnRleHRBbGlnbiA6ICdpbmhlcml0Jyl9O1xuYDtcbiJdfQ==*/
+/*!*************************************************************************************************************************************************************************!*\
+ !*** css ./node_modules/css-loader/dist/cjs.js!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/Common/HubspotWrapper.ts ***!
+ \*************************************************************************************************************************************************************************/
+.h1q5v5ee{background-image:var(--h1q5v5ee-0);background-color:#f5f8fa;background-repeat:no-repeat;background-position:center 25px;background-size:120px;color:#33475b;font-family:'Lexend Deca',Helvetica,Arial,sans-serif;font-size:14px;padding:var(--h1q5v5ee-1);}.h1q5v5ee p{font-size:inherit !important;line-height:24px;margin:4px 0;}
+/*# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIi91c3Ivc2hhcmUvaHVic3BvdC9idWlsZC93b3Jrc3BhY2UvTGVhZGluV29yZFByZXNzUGx1Z2luL2xlYWRpbi9zY3JpcHRzL3NoYXJlZC9Db21tb24vSHVic3BvdFdyYXBwZXIudHMiXSwibmFtZXMiOlsiLmgxcTV2NWVlIl0sIm1hcHBpbmdzIjoiQUFDZUEiLCJmaWxlIjoiL3Vzci9zaGFyZS9odWJzcG90L2J1aWxkL3dvcmtzcGFjZS9MZWFkaW5Xb3JkUHJlc3NQbHVnaW4vbGVhZGluL3NjcmlwdHMvc2hhcmVkL0NvbW1vbi9IdWJzcG90V3JhcHBlci50cyIsInNvdXJjZXNDb250ZW50IjpbImltcG9ydCB7IHN0eWxlZCB9IGZyb20gJ0BsaW5hcmlhL3JlYWN0JztcbmV4cG9ydCBkZWZhdWx0IHN0eWxlZC5kaXYgYFxuICBiYWNrZ3JvdW5kLWltYWdlOiAke3Byb3BzID0+IGB1cmwoJHtwcm9wcy5wbHVnaW5QYXRofS9wdWJsaWMvYXNzZXRzL2ltYWdlcy9odWJzcG90LnN2ZylgfTtcbiAgYmFja2dyb3VuZC1jb2xvcjogI2Y1ZjhmYTtcbiAgYmFja2dyb3VuZC1yZXBlYXQ6IG5vLXJlcGVhdDtcbiAgYmFja2dyb3VuZC1wb3NpdGlvbjogY2VudGVyIDI1cHg7XG4gIGJhY2tncm91bmQtc2l6ZTogMTIwcHg7XG4gIGNvbG9yOiAjMzM0NzViO1xuICBmb250LWZhbWlseTogJ0xleGVuZCBEZWNhJywgSGVsdmV0aWNhLCBBcmlhbCwgc2Fucy1zZXJpZjtcbiAgZm9udC1zaXplOiAxNHB4O1xuXG4gIHBhZGRpbmc6ICR7KHByb3BzKSA9PiBwcm9wcy5wYWRkaW5nIHx8ICc5MHB4IDIwJSAyNXB4J307XG5cbiAgcCB7XG4gICAgZm9udC1zaXplOiBpbmhlcml0ICFpbXBvcnRhbnQ7XG4gICAgbGluZS1oZWlnaHQ6IDI0cHg7XG4gICAgbWFyZ2luOiA0cHggMDtcbiAgfVxuYDtcbiJdfQ==*/
+/*!*************************************************************************************************************************************************************************!*\
+ !*** css ./node_modules/css-loader/dist/cjs.js!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/UIComponents/UISpacer.ts ***!
+ \*************************************************************************************************************************************************************************/
+.u3qxofx{height:30px;}
+/*# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIi91c3Ivc2hhcmUvaHVic3BvdC9idWlsZC93b3Jrc3BhY2UvTGVhZGluV29yZFByZXNzUGx1Z2luL2xlYWRpbi9zY3JpcHRzL3NoYXJlZC9VSUNvbXBvbmVudHMvVUlTcGFjZXIudHMiXSwibmFtZXMiOlsiLnUzcXhvZngiXSwibWFwcGluZ3MiOiJBQUNlQSIsImZpbGUiOiIvdXNyL3NoYXJlL2h1YnNwb3QvYnVpbGQvd29ya3NwYWNlL0xlYWRpbldvcmRQcmVzc1BsdWdpbi9sZWFkaW4vc2NyaXB0cy9zaGFyZWQvVUlDb21wb25lbnRzL1VJU3BhY2VyLnRzIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsgc3R5bGVkIH0gZnJvbSAnQGxpbmFyaWEvcmVhY3QnO1xuZXhwb3J0IGRlZmF1bHQgc3R5bGVkLmRpdiBgXG4gIGhlaWdodDogMzBweDtcbmA7XG4iXX0=*/
+/*!**************************************************************************************************************************************************************************!*\
+ !*** css ./node_modules/css-loader/dist/cjs.js!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/UIComponents/UIOverlay.ts ***!
+ \**************************************************************************************************************************************************************************/
+.u1q7a48k{position:relative;}.u1q7a48k:after{content:'';position:absolute;top:0;bottom:0;right:0;left:0;}
+/*# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIi91c3Ivc2hhcmUvaHVic3BvdC9idWlsZC93b3Jrc3BhY2UvTGVhZGluV29yZFByZXNzUGx1Z2luL2xlYWRpbi9zY3JpcHRzL3NoYXJlZC9VSUNvbXBvbmVudHMvVUlPdmVybGF5LnRzIl0sIm5hbWVzIjpbIi51MXE3YTQ4ayJdLCJtYXBwaW5ncyI6IkFBQ2VBIiwiZmlsZSI6Ii91c3Ivc2hhcmUvaHVic3BvdC9idWlsZC93b3Jrc3BhY2UvTGVhZGluV29yZFByZXNzUGx1Z2luL2xlYWRpbi9zY3JpcHRzL3NoYXJlZC9VSUNvbXBvbmVudHMvVUlPdmVybGF5LnRzIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsgc3R5bGVkIH0gZnJvbSAnQGxpbmFyaWEvcmVhY3QnO1xuZXhwb3J0IGRlZmF1bHQgc3R5bGVkLmRpdiBgXG4gIHBvc2l0aW9uOiByZWxhdGl2ZTtcblxuICAmOmFmdGVyIHtcbiAgICBjb250ZW50OiAnJztcbiAgICBwb3NpdGlvbjogYWJzb2x1dGU7XG4gICAgdG9wOiAwO1xuICAgIGJvdHRvbTogMDtcbiAgICByaWdodDogMDtcbiAgICBsZWZ0OiAwO1xuICB9XG5gO1xuIl19*/
+/*!***********************************************************************************************************************************************************************!*\
+ !*** css ./node_modules/css-loader/dist/cjs.js!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/Common/AsyncSelect.tsx ***!
+ \***********************************************************************************************************************************************************************/
+.c1wxx7eu{color:#33475b;font-family:'Lexend Deca',Helvetica,Arial,sans-serif;font-size:14px;position:relative;}
+.c1rgwbep{-webkit-align-items:center;-webkit-box-align:center;-ms-flex-align:center;align-items:center;background-color:hsl(0,0%,100%);border-color:hsl(0,0%,80%);border-radius:4px;border-style:solid;border-width:var(--c1rgwbep-0);cursor:default;display:-webkit-box;display:-webkit-flex;display:-ms-flexbox;display:flex;-webkit-flex-wrap:wrap;-ms-flex-wrap:wrap;flex-wrap:wrap;-webkit-box-pack:justify;-webkit-justify-content:space-between;-ms-flex-pack:justify;justify-content:space-between;min-height:38px;outline:0 !important;position:relative;-webkit-transition:all 100ms;transition:all 100ms;box-sizing:border-box;box-shadow:var(--c1rgwbep-1);}.c1rgwbep:hover{border-color:hsl(0,0%,70%);}
+.v1mdmbaj{-webkit-align-items:center;-webkit-box-align:center;-ms-flex-align:center;align-items:center;display:-webkit-box;display:-webkit-flex;display:-ms-flexbox;display:flex;-webkit-flex:1;-ms-flex:1;flex:1;-webkit-flex-wrap:wrap;-ms-flex-wrap:wrap;flex-wrap:wrap;padding:2px 8px;position:relative;overflow:hidden;box-sizing:border-box;}
+.p1gwkvxy{color:hsl(0,0%,50%);margin-left:2px;margin-right:2px;position:absolute;top:50%;-webkit-transform:translateY(-50%);-ms-transform:translateY(-50%);transform:translateY(-50%);box-sizing:border-box;font-size:16px;}
+.s1bwlafs{color:hsl(0,0%,20%);margin-left:2px;margin-right:2px;max-width:calc(100% - 8px);overflow:hidden;position:absolute;text-overflow:ellipsis;white-space:nowrap;top:50%;-webkit-transform:translateY(-50%);-ms-transform:translateY(-50%);transform:translateY(-50%);box-sizing:border-box;}
+.i196z9y5{-webkit-align-items:center;-webkit-box-align:center;-ms-flex-align:center;align-items:center;-webkit-align-self:stretch;-ms-flex-item-align:stretch;align-self:stretch;display:-webkit-box;display:-webkit-flex;display:-ms-flexbox;display:flex;-webkit-flex-shrink:0;-ms-flex-negative:0;flex-shrink:0;box-sizing:border-box;}
+.d1dfo5ow{border-top:8px solid #00a4bd;border-left:6px solid transparent;border-right:6px solid transparent;width:0px;height:0px;margin:10px;}
+.if3lze{margin:2px;padding-bottom:2px;padding-top:2px;visibility:visible;color:hsl(0,0%,20%);box-sizing:border-box;}
+.i9kxf50{box-sizing:content-box;background:rgba(0,0,0,0) none repeat scroll 0px center;border:0px none;font-size:inherit;opacity:1;outline:currentcolor none 0px;padding:0px;color:inherit;font-family:inherit;}
+.igjr3uc{position:absolute;opacity:0;font-size:inherit;}
+.mhb9if7{position:absolute;top:100%;background-color:#fff;border-radius:4px;margin-bottom:8px;margin-top:8px;z-index:9999;box-shadow:0 0 0 1px hsla(0,0%,0%,0.1),0 4px 11px hsla(0,0%,0%,0.1);width:100%;}
+.mxaof7s{max-height:300px;overflow-y:auto;padding-bottom:4px;padding-top:4px;position:relative;}
+.mw50s5v{padding-bottom:8px;padding-top:8px;}
+.m11rzvjw{color:#999;cursor:default;font-size:75%;font-weight:500;margin-bottom:0.25em;text-transform:uppercase;padding-left:12px;padding-left:12px;}
+.m1jcdsjv{display:block;background-color:var(--m1jcdsjv-0);color:var(--m1jcdsjv-1);cursor:default;font-size:inherit;width:100%;padding:8px 12px;}.m1jcdsjv:hover{background-color:var(--m1jcdsjv-2);}
+/*# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIi91c3Ivc2hhcmUvaHVic3BvdC9idWlsZC93b3Jrc3BhY2UvTGVhZGluV29yZFByZXNzUGx1Z2luL2xlYWRpbi9zY3JpcHRzL3NoYXJlZC9Db21tb24vQXN5bmNTZWxlY3QudHN4Il0sIm5hbWVzIjpbIi5jMXd4eDdldSIsIi5jMXJnd2JlcCIsIi52MW1kbWJhaiIsIi5wMWd3a3Z4eSIsIi5zMWJ3bGFmcyIsIi5pMTk2ejl5NSIsIi5kMWRmbzVvdyIsIi5pZjNsemUiLCIuaTlreGY1MCIsIi5pZ2pyM3VjIiwiLm1oYjlpZjciLCIubXhhb2Y3cyIsIi5tdzUwczV2IiwiLm0xMXJ6dmp3IiwiLm0xamNkc2p2Il0sIm1hcHBpbmdzIjoiQUFNa0JBO0FBTU9DO0FBcUJGQztBQVVIQztBQVVBQztBQWFPQztBQU9EQztBQVFIQztBQVFUQztBQVdNQztBQUtFQztBQVdMQztBQU9DQztBQUlNQztBQVVQQyIsImZpbGUiOiIvdXNyL3NoYXJlL2h1YnNwb3QvYnVpbGQvd29ya3NwYWNlL0xlYWRpbldvcmRQcmVzc1BsdWdpbi9sZWFkaW4vc2NyaXB0cy9zaGFyZWQvQ29tbW9uL0FzeW5jU2VsZWN0LnRzeCIsInNvdXJjZXNDb250ZW50IjpbImltcG9ydCB7IGpzeCBhcyBfanN4LCBqc3hzIGFzIF9qc3hzIH0gZnJvbSBcInJlYWN0L2pzeC1ydW50aW1lXCI7XG5pbXBvcnQgeyB1c2VSZWYsIHVzZVN0YXRlLCB1c2VFZmZlY3QgfSBmcm9tICdyZWFjdCc7XG5pbXBvcnQgeyBzdHlsZWQgfSBmcm9tICdAbGluYXJpYS9yZWFjdCc7XG5pbXBvcnQgeyBDQUxZUFNPLCBDQUxZUFNPX0xJR0hULCBDQUxZUFNPX01FRElVTSwgT0JTSURJQU4sIH0gZnJvbSAnLi4vVUlDb21wb25lbnRzL2NvbG9ycyc7XG5pbXBvcnQgVUlTcGlubmVyIGZyb20gJy4uL1VJQ29tcG9uZW50cy9VSVNwaW5uZXInO1xuaW1wb3J0IExvYWRTdGF0ZSBmcm9tICcuLi9lbnVtcy9sb2FkU3RhdGUnO1xuY29uc3QgQ29udGFpbmVyID0gc3R5bGVkLmRpdiBgXG4gIGNvbG9yOiAke09CU0lESUFOfTtcbiAgZm9udC1mYW1pbHk6ICdMZXhlbmQgRGVjYScsIEhlbHZldGljYSwgQXJpYWwsIHNhbnMtc2VyaWY7XG4gIGZvbnQtc2l6ZTogMTRweDtcbiAgcG9zaXRpb246IHJlbGF0aXZlO1xuYDtcbmNvbnN0IENvbnRyb2xDb250YWluZXIgPSBzdHlsZWQuZGl2IGBcbiAgYWxpZ24taXRlbXM6IGNlbnRlcjtcbiAgYmFja2dyb3VuZC1jb2xvcjogaHNsKDAsIDAlLCAxMDAlKTtcbiAgYm9yZGVyLWNvbG9yOiBoc2woMCwgMCUsIDgwJSk7XG4gIGJvcmRlci1yYWRpdXM6IDRweDtcbiAgYm9yZGVyLXN0eWxlOiBzb2xpZDtcbiAgYm9yZGVyLXdpZHRoOiAke3Byb3BzID0+IChwcm9wcy5mb2N1c2VkID8gJzAnIDogJzFweCcpfTtcbiAgY3Vyc29yOiBkZWZhdWx0O1xuICBkaXNwbGF5OiBmbGV4O1xuICBmbGV4LXdyYXA6IHdyYXA7XG4gIGp1c3RpZnktY29udGVudDogc3BhY2UtYmV0d2VlbjtcbiAgbWluLWhlaWdodDogMzhweDtcbiAgb3V0bGluZTogMCAhaW1wb3J0YW50O1xuICBwb3NpdGlvbjogcmVsYXRpdmU7XG4gIHRyYW5zaXRpb246IGFsbCAxMDBtcztcbiAgYm94LXNpemluZzogYm9yZGVyLWJveDtcbiAgYm94LXNoYWRvdzogJHtwcm9wcyA9PiBwcm9wcy5mb2N1c2VkID8gYDAgMCAwIDJweCAke0NBTFlQU09fTUVESVVNfWAgOiAnbm9uZSd9O1xuICAmOmhvdmVyIHtcbiAgICBib3JkZXItY29sb3I6IGhzbCgwLCAwJSwgNzAlKTtcbiAgfVxuYDtcbmNvbnN0IFZhbHVlQ29udGFpbmVyID0gc3R5bGVkLmRpdiBgXG4gIGFsaWduLWl0ZW1zOiBjZW50ZXI7XG4gIGRpc3BsYXk6IGZsZXg7XG4gIGZsZXg6IDE7XG4gIGZsZXgtd3JhcDogd3JhcDtcbiAgcGFkZGluZzogMnB4IDhweDtcbiAgcG9zaXRpb246IHJlbGF0aXZlO1xuICBvdmVyZmxvdzogaGlkZGVuO1xuICBib3gtc2l6aW5nOiBib3JkZXItYm94O1xuYDtcbmNvbnN0IFBsYWNlaG9sZGVyID0gc3R5bGVkLmRpdiBgXG4gIGNvbG9yOiBoc2woMCwgMCUsIDUwJSk7XG4gIG1hcmdpbi1sZWZ0OiAycHg7XG4gIG1hcmdpbi1yaWdodDogMnB4O1xuICBwb3NpdGlvbjogYWJzb2x1dGU7XG4gIHRvcDogNTAlO1xuICB0cmFuc2Zvcm06IHRyYW5zbGF0ZVkoLTUwJSk7XG4gIGJveC1zaXppbmc6IGJvcmRlci1ib3g7XG4gIGZvbnQtc2l6ZTogMTZweDtcbmA7XG5jb25zdCBTaW5nbGVWYWx1ZSA9IHN0eWxlZC5kaXYgYFxuICBjb2xvcjogaHNsKDAsIDAlLCAyMCUpO1xuICBtYXJnaW4tbGVmdDogMnB4O1xuICBtYXJnaW4tcmlnaHQ6IDJweDtcbiAgbWF4LXdpZHRoOiBjYWxjKDEwMCUgLSA4cHgpO1xuICBvdmVyZmxvdzogaGlkZGVuO1xuICBwb3NpdGlvbjogYWJzb2x1dGU7XG4gIHRleHQtb3ZlcmZsb3c6IGVsbGlwc2lzO1xuICB3aGl0ZS1zcGFjZTogbm93cmFwO1xuICB0b3A6IDUwJTtcbiAgdHJhbnNmb3JtOiB0cmFuc2xhdGVZKC01MCUpO1xuICBib3gtc2l6aW5nOiBib3JkZXItYm94O1xuYDtcbmNvbnN0IEluZGljYXRvckNvbnRhaW5lciA9IHN0eWxlZC5kaXYgYFxuICBhbGlnbi1pdGVtczogY2VudGVyO1xuICBhbGlnbi1zZWxmOiBzdHJldGNoO1xuICBkaXNwbGF5OiBmbGV4O1xuICBmbGV4LXNocmluazogMDtcbiAgYm94LXNpemluZzogYm9yZGVyLWJveDtcbmA7XG5jb25zdCBEcm9wZG93bkluZGljYXRvciA9IHN0eWxlZC5kaXYgYFxuICBib3JkZXItdG9wOiA4cHggc29saWQgJHtDQUxZUFNPfTtcbiAgYm9yZGVyLWxlZnQ6IDZweCBzb2xpZCB0cmFuc3BhcmVudDtcbiAgYm9yZGVyLXJpZ2h0OiA2cHggc29saWQgdHJhbnNwYXJlbnQ7XG4gIHdpZHRoOiAwcHg7XG4gIGhlaWdodDogMHB4O1xuICBtYXJnaW46IDEwcHg7XG5gO1xuY29uc3QgSW5wdXRDb250YWluZXIgPSBzdHlsZWQuZGl2IGBcbiAgbWFyZ2luOiAycHg7XG4gIHBhZGRpbmctYm90dG9tOiAycHg7XG4gIHBhZGRpbmctdG9wOiAycHg7XG4gIHZpc2liaWxpdHk6IHZpc2libGU7XG4gIGNvbG9yOiBoc2woMCwgMCUsIDIwJSk7XG4gIGJveC1zaXppbmc6IGJvcmRlci1ib3g7XG5gO1xuY29uc3QgSW5wdXQgPSBzdHlsZWQuaW5wdXQgYFxuICBib3gtc2l6aW5nOiBjb250ZW50LWJveDtcbiAgYmFja2dyb3VuZDogcmdiYSgwLCAwLCAwLCAwKSBub25lIHJlcGVhdCBzY3JvbGwgMHB4IGNlbnRlcjtcbiAgYm9yZGVyOiAwcHggbm9uZTtcbiAgZm9udC1zaXplOiBpbmhlcml0O1xuICBvcGFjaXR5OiAxO1xuICBvdXRsaW5lOiBjdXJyZW50Y29sb3Igbm9uZSAwcHg7XG4gIHBhZGRpbmc6IDBweDtcbiAgY29sb3I6IGluaGVyaXQ7XG4gIGZvbnQtZmFtaWx5OiBpbmhlcml0O1xuYDtcbmNvbnN0IElucHV0U2hhZG93ID0gc3R5bGVkLmRpdiBgXG4gIHBvc2l0aW9uOiBhYnNvbHV0ZTtcbiAgb3BhY2l0eTogMDtcbiAgZm9udC1zaXplOiBpbmhlcml0O1xuYDtcbmNvbnN0IE1lbnVDb250YWluZXIgPSBzdHlsZWQuZGl2IGBcbiAgcG9zaXRpb246IGFic29sdXRlO1xuICB0b3A6IDEwMCU7XG4gIGJhY2tncm91bmQtY29sb3I6ICNmZmY7XG4gIGJvcmRlci1yYWRpdXM6IDRweDtcbiAgbWFyZ2luLWJvdHRvbTogOHB4O1xuICBtYXJnaW4tdG9wOiA4cHg7XG4gIHotaW5kZXg6IDk5OTk7XG4gIGJveC1zaGFkb3c6IDAgMCAwIDFweCBoc2xhKDAsIDAlLCAwJSwgMC4xKSwgMCA0cHggMTFweCBoc2xhKDAsIDAlLCAwJSwgMC4xKTtcbiAgd2lkdGg6IDEwMCU7XG5gO1xuY29uc3QgTWVudUxpc3QgPSBzdHlsZWQuZGl2IGBcbiAgbWF4LWhlaWdodDogMzAwcHg7XG4gIG92ZXJmbG93LXk6IGF1dG87XG4gIHBhZGRpbmctYm90dG9tOiA0cHg7XG4gIHBhZGRpbmctdG9wOiA0cHg7XG4gIHBvc2l0aW9uOiByZWxhdGl2ZTtcbmA7XG5jb25zdCBNZW51R3JvdXAgPSBzdHlsZWQuZGl2IGBcbiAgcGFkZGluZy1ib3R0b206IDhweDtcbiAgcGFkZGluZy10b3A6IDhweDtcbmA7XG5jb25zdCBNZW51R3JvdXBIZWFkZXIgPSBzdHlsZWQuZGl2IGBcbiAgY29sb3I6ICM5OTk7XG4gIGN1cnNvcjogZGVmYXVsdDtcbiAgZm9udC1zaXplOiA3NSU7XG4gIGZvbnQtd2VpZ2h0OiA1MDA7XG4gIG1hcmdpbi1ib3R0b206IDAuMjVlbTtcbiAgdGV4dC10cmFuc2Zvcm06IHVwcGVyY2FzZTtcbiAgcGFkZGluZy1sZWZ0OiAxMnB4O1xuICBwYWRkaW5nLWxlZnQ6IDEycHg7XG5gO1xuY29uc3QgTWVudUl0ZW0gPSBzdHlsZWQuZGl2IGBcbiAgZGlzcGxheTogYmxvY2s7XG4gIGJhY2tncm91bmQtY29sb3I6ICR7cHJvcHMgPT4gcHJvcHMuc2VsZWN0ZWQgPyBDQUxZUFNPX01FRElVTSA6ICd0cmFuc3BhcmVudCd9O1xuICBjb2xvcjogJHtwcm9wcyA9PiAocHJvcHMuc2VsZWN0ZWQgPyAnI2ZmZicgOiAnaW5oZXJpdCcpfTtcbiAgY3Vyc29yOiBkZWZhdWx0O1xuICBmb250LXNpemU6IGluaGVyaXQ7XG4gIHdpZHRoOiAxMDAlO1xuICBwYWRkaW5nOiA4cHggMTJweDtcbiAgJjpob3ZlciB7XG4gICAgYmFja2dyb3VuZC1jb2xvcjogJHtwcm9wcyA9PiBwcm9wcy5zZWxlY3RlZCA/IENBTFlQU09fTUVESVVNIDogQ0FMWVBTT19MSUdIVH07XG4gIH1cbmA7XG5leHBvcnQgZGVmYXVsdCBmdW5jdGlvbiBBc3luY1NlbGVjdCh7IHBsYWNlaG9sZGVyLCB2YWx1ZSwgbG9hZE9wdGlvbnMsIG9uQ2hhbmdlLCBkZWZhdWx0T3B0aW9ucywgfSkge1xuICAgIGNvbnN0IGlucHV0RWwgPSB1c2VSZWYobnVsbCk7XG4gICAgY29uc3QgaW5wdXRTaGFkb3dFbCA9IHVzZVJlZihudWxsKTtcbiAgICBjb25zdCBbaXNGb2N1c2VkLCBzZXRGb2N1c10gPSB1c2VTdGF0ZShmYWxzZSk7XG4gICAgY29uc3QgW2xvYWRTdGF0ZSwgc2V0TG9hZFN0YXRlXSA9IHVzZVN0YXRlKExvYWRTdGF0ZS5Ob3RMb2FkZWQpO1xuICAgIGNvbnN0IFtsb2NhbFZhbHVlLCBzZXRMb2NhbFZhbHVlXSA9IHVzZVN0YXRlKCcnKTtcbiAgICBjb25zdCBbb3B0aW9ucywgc2V0T3B0aW9uc10gPSB1c2VTdGF0ZShkZWZhdWx0T3B0aW9ucyk7XG4gICAgY29uc3QgaW5wdXRTaXplID0gYCR7aW5wdXRTaGFkb3dFbC5jdXJyZW50ID8gaW5wdXRTaGFkb3dFbC5jdXJyZW50LmNsaWVudFdpZHRoICsgMTAgOiAyfXB4YDtcbiAgICB1c2VFZmZlY3QoKCkgPT4ge1xuICAgICAgICBpZiAobG9hZE9wdGlvbnMgJiYgbG9hZFN0YXRlID09PSBMb2FkU3RhdGUuTm90TG9hZGVkKSB7XG4gICAgICAgICAgICBsb2FkT3B0aW9ucygnJywgKHJlc3VsdCkgPT4ge1xuICAgICAgICAgICAgICAgIHNldE9wdGlvbnMocmVzdWx0KTtcbiAgICAgICAgICAgICAgICBzZXRMb2FkU3RhdGUoTG9hZFN0YXRlLklkbGUpO1xuICAgICAgICAgICAgfSk7XG4gICAgICAgIH1cbiAgICB9LCBbbG9hZE9wdGlvbnMsIGxvYWRTdGF0ZV0pO1xuICAgIGNvbnN0IHJlbmRlckl0ZW1zID0gKGl0ZW1zID0gW10sIHBhcmVudEtleSkgPT4ge1xuICAgICAgICByZXR1cm4gaXRlbXMubWFwKChpdGVtLCBpbmRleCkgPT4ge1xuICAgICAgICAgICAgaWYgKGl0ZW0ub3B0aW9ucykge1xuICAgICAgICAgICAgICAgIHJldHVybiAoX2pzeHMoTWVudUdyb3VwLCB7IGNoaWxkcmVuOiBbX2pzeChNZW51R3JvdXBIZWFkZXIsIHsgaWQ6IGAke2luZGV4fS1oZWFkaW5nYCwgY2hpbGRyZW46IGl0ZW0ubGFiZWwgfSksIF9qc3goXCJkaXZcIiwgeyBjaGlsZHJlbjogcmVuZGVySXRlbXMoaXRlbS5vcHRpb25zLCBpbmRleCkgfSldIH0sIGBhc3luYy1zZWxlY3QtaXRlbS0ke2luZGV4fWApKTtcbiAgICAgICAgICAgIH1cbiAgICAgICAgICAgIGVsc2Uge1xuICAgICAgICAgICAgICAgIGNvbnN0IGtleSA9IGBhc3luYy1zZWxlY3QtaXRlbS0ke3BhcmVudEtleSAhPT0gdW5kZWZpbmVkID8gYCR7cGFyZW50S2V5fS0ke2luZGV4fWAgOiBpbmRleH1gO1xuICAgICAgICAgICAgICAgIHJldHVybiAoX2pzeChNZW51SXRlbSwgeyBpZDoga2V5LCBzZWxlY3RlZDogdmFsdWUgJiYgaXRlbS52YWx1ZSA9PT0gdmFsdWUudmFsdWUsIG9uQ2xpY2s6ICgpID0+IHtcbiAgICAgICAgICAgICAgICAgICAgICAgIG9uQ2hhbmdlKGl0ZW0pO1xuICAgICAgICAgICAgICAgICAgICAgICAgc2V0Rm9jdXMoZmFsc2UpO1xuICAgICAgICAgICAgICAgICAgICB9LCBjaGlsZHJlbjogaXRlbS5sYWJlbCB9LCBrZXkpKTtcbiAgICAgICAgICAgIH1cbiAgICAgICAgfSk7XG4gICAgfTtcbiAgICByZXR1cm4gKF9qc3hzKENvbnRhaW5lciwgeyBjaGlsZHJlbjogW19qc3hzKENvbnRyb2xDb250YWluZXIsIHsgaWQ6IFwibGVhZGluLWFzeW5jLXNlbGVjdG9yXCIsIGZvY3VzZWQ6IGlzRm9jdXNlZCwgb25DbGljazogKCkgPT4ge1xuICAgICAgICAgICAgICAgICAgICBpZiAoaXNGb2N1c2VkKSB7XG4gICAgICAgICAgICAgICAgICAgICAgICBpZiAoaW5wdXRFbC5jdXJyZW50KSB7XG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgaW5wdXRFbC5jdXJyZW50LmJsdXIoKTtcbiAgICAgICAgICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgICAgICAgICAgICAgIHNldEZvY3VzKGZhbHNlKTtcbiAgICAgICAgICAgICAgICAgICAgICAgIHNldExvY2FsVmFsdWUoJycpO1xuICAgICAgICAgICAgICAgICAgICB9XG4gICAgICAgICAgICAgICAgICAgIGVsc2Uge1xuICAgICAgICAgICAgICAgICAgICAgICAgaWYgKGlucHV0RWwuY3VycmVudCkge1xuICAgICAgICAgICAgICAgICAgICAgICAgICAgIGlucHV0RWwuY3VycmVudC5mb2N1cygpO1xuICAgICAgICAgICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgICAgICAgICAgICAgc2V0Rm9jdXModHJ1ZSk7XG4gICAgICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgICAgICB9LCBjaGlsZHJlbjogW19qc3hzKFZhbHVlQ29udGFpbmVyLCB7IGNoaWxkcmVuOiBbbG9jYWxWYWx1ZSA9PT0gJycgJiZcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgKCF2YWx1ZSA/IChfanN4KFBsYWNlaG9sZGVyLCB7IGNoaWxkcmVuOiBwbGFjZWhvbGRlciB9KSkgOiAoX2pzeChTaW5nbGVWYWx1ZSwgeyBjaGlsZHJlbjogdmFsdWUubGFiZWwgfSkpKSwgX2pzeHMoSW5wdXRDb250YWluZXIsIHsgY2hpbGRyZW46IFtfanN4KElucHV0LCB7IHJlZjogaW5wdXRFbCwgb25Gb2N1czogKCkgPT4ge1xuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBzZXRGb2N1cyh0cnVlKTtcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB9LCBvbkNoYW5nZTogZSA9PiB7XG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHNldExvY2FsVmFsdWUoZS50YXJnZXQudmFsdWUpO1xuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBzZXRMb2FkU3RhdGUoTG9hZFN0YXRlLkxvYWRpbmcpO1xuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBsb2FkT3B0aW9ucyAmJlxuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgbG9hZE9wdGlvbnMoZS50YXJnZXQudmFsdWUsIChyZXN1bHQpID0+IHtcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBzZXRPcHRpb25zKHJlc3VsdCk7XG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgc2V0TG9hZFN0YXRlKExvYWRTdGF0ZS5JZGxlKTtcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIH0pO1xuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIH0sIHZhbHVlOiBsb2NhbFZhbHVlLCB3aWR0aDogaW5wdXRTaXplLCBpZDogXCJhc3ljbi1zZWxlY3QtaW5wdXRcIiB9KSwgX2pzeChJbnB1dFNoYWRvdywgeyByZWY6IGlucHV0U2hhZG93RWwsIGNoaWxkcmVuOiBsb2NhbFZhbHVlIH0pXSB9KV0gfSksIF9qc3hzKEluZGljYXRvckNvbnRhaW5lciwgeyBjaGlsZHJlbjogW2xvYWRTdGF0ZSA9PT0gTG9hZFN0YXRlLkxvYWRpbmcgJiYgX2pzeChVSVNwaW5uZXIsIHt9KSwgX2pzeChEcm9wZG93bkluZGljYXRvciwge30pXSB9KV0gfSksIGlzRm9jdXNlZCAmJiAoX2pzeChNZW51Q29udGFpbmVyLCB7IGNoaWxkcmVuOiBfanN4KE1lbnVMaXN0LCB7IGNoaWxkcmVuOiByZW5kZXJJdGVtcyhvcHRpb25zKSB9KSB9KSldIH0pKTtcbn1cbiJdfQ==*/
+/*!******************************************************************************************************************************************************************************!*\
+ !*** css ./node_modules/css-loader/dist/cjs.js!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/elementor/Common/ElementorButton.tsx ***!
+ \******************************************************************************************************************************************************************************/
+.czoccom{display:-webkit-box;display:-webkit-flex;display:-ms-flexbox;display:flex;-webkit-box-pack:center;-webkit-justify-content:center;-ms-flex-pack:center;justify-content:center;padding-bottom:8px;}
+/*# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIi91c3Ivc2hhcmUvaHVic3BvdC9idWlsZC93b3Jrc3BhY2UvTGVhZGluV29yZFByZXNzUGx1Z2luL2xlYWRpbi9zY3JpcHRzL2VsZW1lbnRvci9Db21tb24vRWxlbWVudG9yQnV0dG9uLnRzeCJdLCJuYW1lcyI6WyIuY3pvY2NvbSJdLCJtYXBwaW5ncyI6IkFBRWtCQSIsImZpbGUiOiIvdXNyL3NoYXJlL2h1YnNwb3QvYnVpbGQvd29ya3NwYWNlL0xlYWRpbldvcmRQcmVzc1BsdWdpbi9sZWFkaW4vc2NyaXB0cy9lbGVtZW50b3IvQ29tbW9uL0VsZW1lbnRvckJ1dHRvbi50c3giLCJzb3VyY2VzQ29udGVudCI6WyJpbXBvcnQgeyBqc3ggYXMgX2pzeCB9IGZyb20gXCJyZWFjdC9qc3gtcnVudGltZVwiO1xuaW1wb3J0IHsgc3R5bGVkIH0gZnJvbSAnQGxpbmFyaWEvcmVhY3QnO1xuY29uc3QgQ29udGFpbmVyID0gc3R5bGVkLmRpdiBgXG4gIGRpc3BsYXk6IGZsZXg7XG4gIGp1c3RpZnktY29udGVudDogY2VudGVyO1xuICBwYWRkaW5nLWJvdHRvbTogOHB4O1xuYDtcbmV4cG9ydCBkZWZhdWx0IGZ1bmN0aW9uIEVsZW1lbnRvckJ1dHRvbih7IGNoaWxkcmVuLCAuLi5wYXJhbXMgfSkge1xuICAgIHJldHVybiAoX2pzeChDb250YWluZXIsIHsgY2xhc3NOYW1lOiBcImVsZW1lbnRvci1idXR0b24td3JhcHBlclwiLCBjaGlsZHJlbjogX2pzeChcImJ1dHRvblwiLCB7IGNsYXNzTmFtZTogXCJlbGVtZW50b3ItYnV0dG9uIGVsZW1lbnRvci1idXR0b24tZGVmYXVsdFwiLCB0eXBlOiBcImJ1dHRvblwiLCAuLi5wYXJhbXMsIGNoaWxkcmVuOiBjaGlsZHJlbiB9KSB9KSk7XG59XG4iXX0=*/
+/*!*********************************************************************************************************************************************************************************************!*\
+ !*** css ./node_modules/css-loader/dist/cjs.js!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/elementor/MeetingWidget/ElementorMeetingWarning.tsx ***!
+ \*********************************************************************************************************************************************************************************************/
+.c1p032ba{padding-bottom:8px;}
+/*# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIi91c3Ivc2hhcmUvaHVic3BvdC9idWlsZC93b3Jrc3BhY2UvTGVhZGluV29yZFByZXNzUGx1Z2luL2xlYWRpbi9zY3JpcHRzL2VsZW1lbnRvci9NZWV0aW5nV2lkZ2V0L0VsZW1lbnRvck1lZXRpbmdXYXJuaW5nLnRzeCJdLCJuYW1lcyI6WyIuYzFwMDMyYmEiXSwibWFwcGluZ3MiOiJBQU9rQkEiLCJmaWxlIjoiL3Vzci9zaGFyZS9odWJzcG90L2J1aWxkL3dvcmtzcGFjZS9MZWFkaW5Xb3JkUHJlc3NQbHVnaW4vbGVhZGluL3NjcmlwdHMvZWxlbWVudG9yL01lZXRpbmdXaWRnZXQvRWxlbWVudG9yTWVldGluZ1dhcm5pbmcudHN4Iiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsganN4IGFzIF9qc3gsIGpzeHMgYXMgX2pzeHMgfSBmcm9tIFwicmVhY3QvanN4LXJ1bnRpbWVcIjtcbmltcG9ydCB7IEZyYWdtZW50IH0gZnJvbSAncmVhY3QnO1xuaW1wb3J0IHsgQ1VSUkVOVF9VU0VSX0NBTEVOREFSX01JU1NJTkcgfSBmcm9tICcuLi8uLi9zaGFyZWQvTWVldGluZy9jb25zdGFudHMnO1xuaW1wb3J0IEVsZW1lbnRvckJ1dHRvbiBmcm9tICcuLi9Db21tb24vRWxlbWVudG9yQnV0dG9uJztcbmltcG9ydCBFbGVtZW50b3JCYW5uZXIgZnJvbSAnLi4vQ29tbW9uL0VsZW1lbnRvckJhbm5lcic7XG5pbXBvcnQgeyBzdHlsZWQgfSBmcm9tICdAbGluYXJpYS9yZWFjdCc7XG5pbXBvcnQgeyBfXyB9IGZyb20gJ0B3b3JkcHJlc3MvaTE4bic7XG5jb25zdCBDb250YWluZXIgPSBzdHlsZWQuZGl2IGBcbiAgcGFkZGluZy1ib3R0b206IDhweDtcbmA7XG5leHBvcnQgZGVmYXVsdCBmdW5jdGlvbiBNZWV0aW5nV2FybmluZyh7IG9uQ29ubmVjdENhbGVuZGFyLCBzdGF0dXMsIH0pIHtcbiAgICBjb25zdCBpc01lZXRpbmdPd25lciA9IHN0YXR1cyA9PT0gQ1VSUkVOVF9VU0VSX0NBTEVOREFSX01JU1NJTkc7XG4gICAgY29uc3QgdGl0bGVUZXh0ID0gaXNNZWV0aW5nT3duZXJcbiAgICAgICAgPyBfXygnWW91ciBjYWxlbmRhciBpcyBub3QgY29ubmVjdGVkJywgJ2xlYWRpbicpXG4gICAgICAgIDogX18oJ0NhbGVuZGFyIGlzIG5vdCBjb25uZWN0ZWQnLCAnbGVhZGluJyk7XG4gICAgY29uc3QgdGl0bGVNZXNzYWdlID0gaXNNZWV0aW5nT3duZXJcbiAgICAgICAgPyBfXygnUGxlYXNlIGNvbm5lY3QgeW91ciBjYWxlbmRhciB0byBhY3RpdmF0ZSB5b3VyIHNjaGVkdWxpbmcgcGFnZXMnLCAnbGVhZGluJylcbiAgICAgICAgOiBfXygnTWFrZSBzdXJlIHRoYXQgZXZlcnlib2R5IGluIHRoaXMgbWVldGluZyBoYXMgY29ubmVjdGVkIHRoZWlyIGNhbGVuZGFyIGZyb20gdGhlIE1lZXRpbmdzIHBhZ2UgaW4gSHViU3BvdCcsICdsZWFkaW4nKTtcbiAgICByZXR1cm4gKF9qc3hzKEZyYWdtZW50LCB7IGNoaWxkcmVuOiBbX2pzeChDb250YWluZXIsIHsgY2hpbGRyZW46IF9qc3hzKEVsZW1lbnRvckJhbm5lciwgeyB0eXBlOiBcIndhcm5pbmdcIiwgY2hpbGRyZW46IFtfanN4KFwiYlwiLCB7IGNoaWxkcmVuOiB0aXRsZVRleHQgfSksIF9qc3goXCJiclwiLCB7fSksIHRpdGxlTWVzc2FnZV0gfSkgfSksIGlzTWVldGluZ093bmVyICYmIChfanN4KEVsZW1lbnRvckJ1dHRvbiwgeyBpZDogXCJtZWV0aW5ncy1jb25uZWN0LWNhbGVuZGFyXCIsIG9uQ2xpY2s6IG9uQ29ubmVjdENhbGVuZGFyLCBjaGlsZHJlbjogX18oJ0Nvbm5lY3QgY2FsZW5kYXInLCAnbGVhZGluJykgfSkpXSB9KSk7XG59XG4iXX0=*/
+/*!*************************************************************************************************************************************************************************!*\
+ !*** css ./node_modules/css-loader/dist/cjs.js!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/UIComponents/UIAlert.tsx ***!
+ \*************************************************************************************************************************************************************************/
+.a1h8m4fo{background-color:#fef8f0;border-color:#fae0b5;color:#33475b;font-size:14px;-webkit-align-items:center;-webkit-box-align:center;-ms-flex-align:center;align-items:center;-webkit-box-pack:justify;-webkit-justify-content:space-between;-ms-flex-pack:justify;justify-content:space-between;display:-webkit-box;display:-webkit-flex;display:-ms-flexbox;display:flex;border-style:solid;border-top-style:solid;border-right-style:solid;border-bottom-style:solid;border-left-style:solid;border-width:1px;min-height:60px;padding:8px 20px;position:relative;text-align:left;}
+.tyndzxk{font-family:'Lexend Deca';font-style:normal;font-weight:700;font-size:16px;line-height:19px;color:#33475b;margin:0;padding:0;}
+.m1m9sbk4{font-family:'Lexend Deca';font-style:normal;font-weight:400;font-size:14px;margin:0;padding:0;}
+.mg5o421{display:-webkit-box;display:-webkit-flex;display:-ms-flexbox;display:flex;-webkit-flex-direction:column;-ms-flex-direction:column;flex-direction:column;}
+/*# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIi91c3Ivc2hhcmUvaHVic3BvdC9idWlsZC93b3Jrc3BhY2UvTGVhZGluV29yZFByZXNzUGx1Z2luL2xlYWRpbi9zY3JpcHRzL3NoYXJlZC9VSUNvbXBvbmVudHMvVUlBbGVydC50c3giXSwibmFtZXMiOlsiLmExaDhtNGZvIiwiLnR5bmR6eGsiLCIubTFtOXNiazQiLCIubWc1bzQyMSJdLCJtYXBwaW5ncyI6IkFBR3VCQTtBQW1CVEM7QUFVRUM7QUFRU0MiLCJmaWxlIjoiL3Vzci9zaGFyZS9odWJzcG90L2J1aWxkL3dvcmtzcGFjZS9MZWFkaW5Xb3JkUHJlc3NQbHVnaW4vbGVhZGluL3NjcmlwdHMvc2hhcmVkL1VJQ29tcG9uZW50cy9VSUFsZXJ0LnRzeCIsInNvdXJjZXNDb250ZW50IjpbImltcG9ydCB7IGpzeCBhcyBfanN4LCBqc3hzIGFzIF9qc3hzIH0gZnJvbSBcInJlYWN0L2pzeC1ydW50aW1lXCI7XG5pbXBvcnQgeyBzdHlsZWQgfSBmcm9tICdAbGluYXJpYS9yZWFjdCc7XG5pbXBvcnQgeyBNQVJJR09MRF9MSUdIVCwgTUFSSUdPTERfTUVESVVNLCBPQlNJRElBTiB9IGZyb20gJy4vY29sb3JzJztcbmNvbnN0IEFsZXJ0Q29udGFpbmVyID0gc3R5bGVkLmRpdiBgXG4gIGJhY2tncm91bmQtY29sb3I6ICR7TUFSSUdPTERfTElHSFR9O1xuICBib3JkZXItY29sb3I6ICR7TUFSSUdPTERfTUVESVVNfTtcbiAgY29sb3I6ICR7T0JTSURJQU59O1xuICBmb250LXNpemU6IDE0cHg7XG4gIGFsaWduLWl0ZW1zOiBjZW50ZXI7XG4gIGp1c3RpZnktY29udGVudDogc3BhY2UtYmV0d2VlbjtcbiAgZGlzcGxheTogZmxleDtcbiAgYm9yZGVyLXN0eWxlOiBzb2xpZDtcbiAgYm9yZGVyLXRvcC1zdHlsZTogc29saWQ7XG4gIGJvcmRlci1yaWdodC1zdHlsZTogc29saWQ7XG4gIGJvcmRlci1ib3R0b20tc3R5bGU6IHNvbGlkO1xuICBib3JkZXItbGVmdC1zdHlsZTogc29saWQ7XG4gIGJvcmRlci13aWR0aDogMXB4O1xuICBtaW4taGVpZ2h0OiA2MHB4O1xuICBwYWRkaW5nOiA4cHggMjBweDtcbiAgcG9zaXRpb246IHJlbGF0aXZlO1xuICB0ZXh0LWFsaWduOiBsZWZ0O1xuYDtcbmNvbnN0IFRpdGxlID0gc3R5bGVkLnAgYFxuICBmb250LWZhbWlseTogJ0xleGVuZCBEZWNhJztcbiAgZm9udC1zdHlsZTogbm9ybWFsO1xuICBmb250LXdlaWdodDogNzAwO1xuICBmb250LXNpemU6IDE2cHg7XG4gIGxpbmUtaGVpZ2h0OiAxOXB4O1xuICBjb2xvcjogJHtPQlNJRElBTn07XG4gIG1hcmdpbjogMDtcbiAgcGFkZGluZzogMDtcbmA7XG5jb25zdCBNZXNzYWdlID0gc3R5bGVkLnAgYFxuICBmb250LWZhbWlseTogJ0xleGVuZCBEZWNhJztcbiAgZm9udC1zdHlsZTogbm9ybWFsO1xuICBmb250LXdlaWdodDogNDAwO1xuICBmb250LXNpemU6IDE0cHg7XG4gIG1hcmdpbjogMDtcbiAgcGFkZGluZzogMDtcbmA7XG5jb25zdCBNZXNzYWdlQ29udGFpbmVyID0gc3R5bGVkLmRpdiBgXG4gIGRpc3BsYXk6IGZsZXg7XG4gIGZsZXgtZGlyZWN0aW9uOiBjb2x1bW47XG5gO1xuZXhwb3J0IGRlZmF1bHQgZnVuY3Rpb24gVUlBbGVydCh7IHRpdGxlVGV4dCwgdGl0bGVNZXNzYWdlLCBjaGlsZHJlbiwgfSkge1xuICAgIHJldHVybiAoX2pzeHMoQWxlcnRDb250YWluZXIsIHsgY2hpbGRyZW46IFtfanN4cyhNZXNzYWdlQ29udGFpbmVyLCB7IGNoaWxkcmVuOiBbX2pzeChUaXRsZSwgeyBjaGlsZHJlbjogdGl0bGVUZXh0IH0pLCBfanN4KE1lc3NhZ2UsIHsgY2hpbGRyZW46IHRpdGxlTWVzc2FnZSB9KV0gfSksIGNoaWxkcmVuXSB9KSk7XG59XG4iXX0=*/
+
+/*# sourceMappingURL=elementor.css.map*/
\ No newline at end of file
diff --git a/wp/wp-content/plugins/leadin/build/elementor.css.map b/wp/wp-content/plugins/leadin/build/elementor.css.map
new file mode 100644
index 00000000..43be833e
--- /dev/null
+++ b/wp/wp-content/plugins/leadin/build/elementor.css.map
@@ -0,0 +1 @@
+{"version":3,"file":"elementor.css","mappings":";;;AAGqBA,SAAAA,0BAAAA,CAAAA,wBAAAA,CAAAA,qBAAAA,CAAAA,kBAAAA,CAAAA,aAAAA,CAAAA,mBAAAA,CAAAA,oBAAAA,CAAAA,mBAAAA,CAAAA,YAAAA,CAAAA,6BAAAA,CAAAA,yBAAAA,CAAAA,qBAAAA,CAAAA,uBAAAA,CAAAA,8BAAAA,CAAAA,oBAAAA,CAAAA,sBAAAA,CAAAA,UAAAA,CAAAA,WAAAA,CAAAA,YAAAA,CAAAA;AAUAC,UAAAA,0BAAAA,CAAAA,wBAAAA,CAAAA,qBAAAA,CAAAA,kBAAAA,CAAAA,mBAAAA,CAAAA,oBAAAA,CAAAA,mBAAAA,CAAAA,YAAAA,CAAAA,uBAAAA,CAAAA,8BAAAA,CAAAA,oBAAAA,CAAAA,sBAAAA,CAAAA,UAAAA,CAAAA,WAAAA,CAAAA;AAONC,SAAAA,SAAAA,CAAAA,uBAAAA,CAAAA,cAAAA,CAAAA,oBAAAA,CAAAA,+BAAAA,CAAAA,2BAAAA,CAAAA,uBAAAA,CAAAA;AAOQC,SAAAA,SAAAA,CAAAA,uBAAAA,CAAAA,cAAAA,CAAAA,oBAAAA,CAAAA,+BAAAA,CAAAA,2BAAAA,CAAAA,uBAAAA,CAAAA,wGAAAA,CAAAA,gGAAAA,CAAAA,CAAAA,yCAAAA,GAAAA,sBAAAA,CAAAA,mBAAAA,CAAAA,CAAAA,IAAAA,uBAAAA,CAAAA,qBAAAA,CAAAA,CAAAA,KAAAA,uBAAAA,CAAAA,sBAAAA,CAAAA,CAAAA,CAAAA,iCAAAA,GAAAA,sBAAAA,CAAAA,mBAAAA,CAAAA,CAAAA,IAAAA,uBAAAA,CAAAA,qBAAAA,CAAAA,CAAAA,KAAAA,uBAAAA,CAAAA,sBAAAA,CAAAA,CAAAA,CAAAA,yCAAAA,CAAAA,gCAAAA,CAAAA,4BAAAA,CAAAA,wBAAAA,CAAAA,CAAAA,CAAAA,iCAAAA,CAAAA,gCAAAA,CAAAA,4BAAAA,CAAAA,wBAAAA,CAAAA,CAAAA;ACvBvB,usFAAusF,C;;;;ACFxrFC,SAAAA,iCAAAA,CAAAA,iCAAAA,CAAAA,aAAAA,CAAAA,iBAAAA,CAAAA,cAAAA,CAAAA,gBAAAA,CAAAA,iBAAAA,CAAAA,oDAAAA,CAAAA,eAAAA,CAAAA,kBAAAA,CAAAA;ACDf,2mCAA2mC,C;;;;ACA5lCC,SAAAA,2BAAAA,CAAAA;ACAf,+pBAA+pB,C;;;;ACAhpBC,UAAAA,kCAAAA,CAAAA,wBAAAA,CAAAA,2BAAAA,CAAAA,+BAAAA,CAAAA,qBAAAA,CAAAA,aAAAA,CAAAA,oDAAAA,CAAAA,cAAAA,CAAAA,yBAAAA,CAAAA,CAAAA,YAAAA,4BAAAA,CAAAA,gBAAAA,CAAAA,YAAAA,CAAAA;ACAf,+qCAA+qC,C;;;;ACAhqCC,SAAAA,WAAAA,CAAAA;ACAf,ukBAAukB,C;;;;ACAxjBC,UAAAA,iBAAAA,CAAAA,CAAAA,gBAAAA,UAAAA,CAAAA,iBAAAA,CAAAA,KAAAA,CAAAA,QAAAA,CAAAA,OAAAA,CAAAA,MAAAA,CAAAA;ACAf,mvBAAmvB,C;;;;ACKjuBC,UAAAA,aAAAA,CAAAA,oDAAAA,CAAAA,cAAAA,CAAAA,iBAAAA,CAAAA;AAMOC,UAAAA,0BAAAA,CAAAA,wBAAAA,CAAAA,qBAAAA,CAAAA,kBAAAA,CAAAA,+BAAAA,CAAAA,0BAAAA,CAAAA,iBAAAA,CAAAA,kBAAAA,CAAAA,8BAAAA,CAAAA,cAAAA,CAAAA,mBAAAA,CAAAA,oBAAAA,CAAAA,mBAAAA,CAAAA,YAAAA,CAAAA,sBAAAA,CAAAA,kBAAAA,CAAAA,cAAAA,CAAAA,wBAAAA,CAAAA,qCAAAA,CAAAA,qBAAAA,CAAAA,6BAAAA,CAAAA,eAAAA,CAAAA,oBAAAA,CAAAA,iBAAAA,CAAAA,4BAAAA,CAAAA,oBAAAA,CAAAA,qBAAAA,CAAAA,4BAAAA,CAAAA,CAAAA,gBAAAA,0BAAAA,CAAAA;AAqBFC,UAAAA,0BAAAA,CAAAA,wBAAAA,CAAAA,qBAAAA,CAAAA,kBAAAA,CAAAA,mBAAAA,CAAAA,oBAAAA,CAAAA,mBAAAA,CAAAA,YAAAA,CAAAA,cAAAA,CAAAA,UAAAA,CAAAA,MAAAA,CAAAA,sBAAAA,CAAAA,kBAAAA,CAAAA,cAAAA,CAAAA,eAAAA,CAAAA,iBAAAA,CAAAA,eAAAA,CAAAA,qBAAAA,CAAAA;AAUHC,UAAAA,mBAAAA,CAAAA,eAAAA,CAAAA,gBAAAA,CAAAA,iBAAAA,CAAAA,OAAAA,CAAAA,kCAAAA,CAAAA,8BAAAA,CAAAA,0BAAAA,CAAAA,qBAAAA,CAAAA,cAAAA,CAAAA;AAUAC,UAAAA,mBAAAA,CAAAA,eAAAA,CAAAA,gBAAAA,CAAAA,0BAAAA,CAAAA,eAAAA,CAAAA,iBAAAA,CAAAA,sBAAAA,CAAAA,kBAAAA,CAAAA,OAAAA,CAAAA,kCAAAA,CAAAA,8BAAAA,CAAAA,0BAAAA,CAAAA,qBAAAA,CAAAA;AAaOC,UAAAA,0BAAAA,CAAAA,wBAAAA,CAAAA,qBAAAA,CAAAA,kBAAAA,CAAAA,0BAAAA,CAAAA,2BAAAA,CAAAA,kBAAAA,CAAAA,mBAAAA,CAAAA,oBAAAA,CAAAA,mBAAAA,CAAAA,YAAAA,CAAAA,qBAAAA,CAAAA,mBAAAA,CAAAA,aAAAA,CAAAA,qBAAAA,CAAAA;AAODC,UAAAA,4BAAAA,CAAAA,iCAAAA,CAAAA,kCAAAA,CAAAA,SAAAA,CAAAA,UAAAA,CAAAA,WAAAA,CAAAA;AAQHC,QAAAA,UAAAA,CAAAA,kBAAAA,CAAAA,eAAAA,CAAAA,kBAAAA,CAAAA,mBAAAA,CAAAA,qBAAAA,CAAAA;AAQTC,SAAAA,sBAAAA,CAAAA,sDAAAA,CAAAA,eAAAA,CAAAA,iBAAAA,CAAAA,SAAAA,CAAAA,6BAAAA,CAAAA,WAAAA,CAAAA,aAAAA,CAAAA,mBAAAA,CAAAA;AAWMC,SAAAA,iBAAAA,CAAAA,SAAAA,CAAAA,iBAAAA,CAAAA;AAKEC,SAAAA,iBAAAA,CAAAA,QAAAA,CAAAA,qBAAAA,CAAAA,iBAAAA,CAAAA,iBAAAA,CAAAA,cAAAA,CAAAA,YAAAA,CAAAA,mEAAAA,CAAAA,UAAAA,CAAAA;AAWLC,SAAAA,gBAAAA,CAAAA,eAAAA,CAAAA,kBAAAA,CAAAA,eAAAA,CAAAA,iBAAAA,CAAAA;AAOCC,SAAAA,kBAAAA,CAAAA,eAAAA,CAAAA;AAIMC,UAAAA,UAAAA,CAAAA,cAAAA,CAAAA,aAAAA,CAAAA,eAAAA,CAAAA,oBAAAA,CAAAA,wBAAAA,CAAAA,iBAAAA,CAAAA,iBAAAA,CAAAA;AAUPC,UAAAA,aAAAA,CAAAA,kCAAAA,CAAAA,uBAAAA,CAAAA,cAAAA,CAAAA,iBAAAA,CAAAA,UAAAA,CAAAA,gBAAAA,CAAAA,CAAAA,gBAAAA,kCAAAA,CAAAA;AC1HjB,ugVAAugV,C;;;;ACbr/UC,SAAAA,mBAAAA,CAAAA,oBAAAA,CAAAA,mBAAAA,CAAAA,YAAAA,CAAAA,uBAAAA,CAAAA,8BAAAA,CAAAA,oBAAAA,CAAAA,sBAAAA,CAAAA,kBAAAA,CAAAA;ACDlB,mmCAAmmC,C;;;;ACMjlCC,UAAAA,kBAAAA,CAAAA;ACNlB,2xEAA2xE,C;;;;ACEpwEC,UAAAA,wBAAAA,CAAAA,oBAAAA,CAAAA,aAAAA,CAAAA,cAAAA,CAAAA,0BAAAA,CAAAA,wBAAAA,CAAAA,qBAAAA,CAAAA,kBAAAA,CAAAA,wBAAAA,CAAAA,qCAAAA,CAAAA,qBAAAA,CAAAA,6BAAAA,CAAAA,mBAAAA,CAAAA,oBAAAA,CAAAA,mBAAAA,CAAAA,YAAAA,CAAAA,kBAAAA,CAAAA,sBAAAA,CAAAA,wBAAAA,CAAAA,yBAAAA,CAAAA,uBAAAA,CAAAA,gBAAAA,CAAAA,eAAAA,CAAAA,gBAAAA,CAAAA,iBAAAA,CAAAA,eAAAA,CAAAA;AAmBTC,SAAAA,yBAAAA,CAAAA,iBAAAA,CAAAA,eAAAA,CAAAA,cAAAA,CAAAA,gBAAAA,CAAAA,aAAAA,CAAAA,QAAAA,CAAAA,SAAAA,CAAAA;AAUEC,UAAAA,yBAAAA,CAAAA,iBAAAA,CAAAA,eAAAA,CAAAA,cAAAA,CAAAA,QAAAA,CAAAA,SAAAA,CAAAA;AAQSC,SAAAA,mBAAAA,CAAAA,oBAAAA,CAAAA,mBAAAA,CAAAA,YAAAA,CAAAA,6BAAAA,CAAAA,yBAAAA,CAAAA,qBAAAA,CAAAA;ACpCzB,+zEAA+zE,C","sources":["webpack://leadin/./scripts/shared/UIComponents/UISpinner.tsx","webpack://leadin/./scripts/shared/UIComponents/UISpinner.tsx","webpack://leadin/./scripts/shared/UIComponents/UIButton.ts","webpack://leadin/./scripts/shared/UIComponents/UIButton.ts","webpack://leadin/./scripts/shared/UIComponents/UIContainer.ts","webpack://leadin/./scripts/shared/UIComponents/UIContainer.ts","webpack://leadin/./scripts/shared/Common/HubspotWrapper.ts","webpack://leadin/./scripts/shared/Common/HubspotWrapper.ts","webpack://leadin/./scripts/shared/UIComponents/UISpacer.ts","webpack://leadin/./scripts/shared/UIComponents/UISpacer.ts","webpack://leadin/./scripts/shared/UIComponents/UIOverlay.ts","webpack://leadin/./scripts/shared/UIComponents/UIOverlay.ts","webpack://leadin/./scripts/shared/Common/AsyncSelect.tsx","webpack://leadin/./scripts/shared/Common/AsyncSelect.tsx","webpack://leadin/./scripts/elementor/Common/ElementorButton.tsx","webpack://leadin/./scripts/elementor/Common/ElementorButton.tsx","webpack://leadin/./scripts/elementor/MeetingWidget/ElementorMeetingWarning.tsx","webpack://leadin/./scripts/elementor/MeetingWidget/ElementorMeetingWarning.tsx","webpack://leadin/./scripts/shared/UIComponents/UIAlert.tsx","webpack://leadin/./scripts/shared/UIComponents/UIAlert.tsx"],"sourcesContent":["import { jsx as _jsx, jsxs as _jsxs } from \"react/jsx-runtime\";\nimport { styled } from '@linaria/react';\nimport { CALYPSO_MEDIUM, CALYPSO } from './colors';\nconst SpinnerOuter = styled.div `\n align-items: center;\n color: #00a4bd;\n display: flex;\n flex-direction: column;\n justify-content: center;\n width: 100%;\n height: 100%;\n margin: '2px';\n`;\nconst SpinnerInner = styled.div `\n align-items: center;\n display: flex;\n justify-content: center;\n width: 100%;\n height: 100%;\n`;\nconst Circle = styled.circle `\n fill: none;\n stroke: ${props => props.color};\n stroke-width: 5;\n stroke-linecap: round;\n transform-origin: center;\n`;\nconst AnimatedCircle = styled.circle `\n fill: none;\n stroke: ${props => props.color};\n stroke-width: 5;\n stroke-linecap: round;\n transform-origin: center;\n animation: dashAnimation 2s ease-in-out infinite,\n spinAnimation 2s linear infinite;\n\n @keyframes dashAnimation {\n 0% {\n stroke-dasharray: 1, 150;\n stroke-dashoffset: 0;\n }\n\n 50% {\n stroke-dasharray: 90, 150;\n stroke-dashoffset: -50;\n }\n\n 100% {\n stroke-dasharray: 90, 150;\n stroke-dashoffset: -140;\n }\n }\n\n @keyframes spinAnimation {\n transform: rotate(360deg);\n }\n`;\nexport default function UISpinner({ size = 20 }) {\n return (_jsx(SpinnerOuter, { children: _jsx(SpinnerInner, { children: _jsxs(\"svg\", { height: size, width: size, viewBox: \"0 0 50 50\", children: [_jsx(Circle, { color: CALYPSO_MEDIUM, cx: \"25\", cy: \"25\", r: \"22.5\" }), _jsx(AnimatedCircle, { color: CALYPSO, cx: \"25\", cy: \"25\", r: \"22.5\" })] }) }) }));\n}\n",".sxa9zrc{-webkit-align-items:center;-webkit-box-align:center;-ms-flex-align:center;align-items:center;color:#00a4bd;display:-webkit-box;display:-webkit-flex;display:-ms-flexbox;display:flex;-webkit-flex-direction:column;-ms-flex-direction:column;flex-direction:column;-webkit-box-pack:center;-webkit-justify-content:center;-ms-flex-pack:center;justify-content:center;width:100%;height:100%;margin:'2px';}\n.s14430wa{-webkit-align-items:center;-webkit-box-align:center;-ms-flex-align:center;align-items:center;display:-webkit-box;display:-webkit-flex;display:-ms-flexbox;display:flex;-webkit-box-pack:center;-webkit-justify-content:center;-ms-flex-pack:center;justify-content:center;width:100%;height:100%;}\n.ct87ghk{fill:none;stroke:var(--ct87ghk-0);stroke-width:5;stroke-linecap:round;-webkit-transform-origin:center;-ms-transform-origin:center;transform-origin:center;}\n.avili0h{fill:none;stroke:var(--avili0h-0);stroke-width:5;stroke-linecap:round;-webkit-transform-origin:center;-ms-transform-origin:center;transform-origin:center;-webkit-animation:dashAnimation-avili0h 2s ease-in-out infinite,spinAnimation-avili0h 2s linear infinite;animation:dashAnimation-avili0h 2s ease-in-out infinite,spinAnimation-avili0h 2s linear infinite;}@-webkit-keyframes dashAnimation-avili0h{0%{stroke-dasharray:1,150;stroke-dashoffset:0;}50%{stroke-dasharray:90,150;stroke-dashoffset:-50;}100%{stroke-dasharray:90,150;stroke-dashoffset:-140;}}@keyframes dashAnimation-avili0h{0%{stroke-dasharray:1,150;stroke-dashoffset:0;}50%{stroke-dasharray:90,150;stroke-dashoffset:-50;}100%{stroke-dasharray:90,150;stroke-dashoffset:-140;}}@-webkit-keyframes spinAnimation-avili0h{{-webkit-transform:rotate(360deg);-ms-transform:rotate(360deg);transform:rotate(360deg);}}@keyframes spinAnimation-avili0h{{-webkit-transform:rotate(360deg);-ms-transform:rotate(360deg);transform:rotate(360deg);}}\n/*# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIi91c3Ivc2hhcmUvaHVic3BvdC9idWlsZC93b3Jrc3BhY2UvTGVhZGluV29yZFByZXNzUGx1Z2luL2xlYWRpbi9zY3JpcHRzL3NoYXJlZC9VSUNvbXBvbmVudHMvVUlTcGlubmVyLnRzeCJdLCJuYW1lcyI6WyIuc3hhOXpyYyIsIi5zMTQ0MzB3YSIsIi5jdDg3Z2hrIiwiLmF2aWxpMGgiXSwibWFwcGluZ3MiOiJBQUdxQkE7QUFVQUM7QUFPTkM7QUFPUUMiLCJmaWxlIjoiL3Vzci9zaGFyZS9odWJzcG90L2J1aWxkL3dvcmtzcGFjZS9MZWFkaW5Xb3JkUHJlc3NQbHVnaW4vbGVhZGluL3NjcmlwdHMvc2hhcmVkL1VJQ29tcG9uZW50cy9VSVNwaW5uZXIudHN4Iiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsganN4IGFzIF9qc3gsIGpzeHMgYXMgX2pzeHMgfSBmcm9tIFwicmVhY3QvanN4LXJ1bnRpbWVcIjtcbmltcG9ydCB7IHN0eWxlZCB9IGZyb20gJ0BsaW5hcmlhL3JlYWN0JztcbmltcG9ydCB7IENBTFlQU09fTUVESVVNLCBDQUxZUFNPIH0gZnJvbSAnLi9jb2xvcnMnO1xuY29uc3QgU3Bpbm5lck91dGVyID0gc3R5bGVkLmRpdiBgXG4gIGFsaWduLWl0ZW1zOiBjZW50ZXI7XG4gIGNvbG9yOiAjMDBhNGJkO1xuICBkaXNwbGF5OiBmbGV4O1xuICBmbGV4LWRpcmVjdGlvbjogY29sdW1uO1xuICBqdXN0aWZ5LWNvbnRlbnQ6IGNlbnRlcjtcbiAgd2lkdGg6IDEwMCU7XG4gIGhlaWdodDogMTAwJTtcbiAgbWFyZ2luOiAnMnB4JztcbmA7XG5jb25zdCBTcGlubmVySW5uZXIgPSBzdHlsZWQuZGl2IGBcbiAgYWxpZ24taXRlbXM6IGNlbnRlcjtcbiAgZGlzcGxheTogZmxleDtcbiAganVzdGlmeS1jb250ZW50OiBjZW50ZXI7XG4gIHdpZHRoOiAxMDAlO1xuICBoZWlnaHQ6IDEwMCU7XG5gO1xuY29uc3QgQ2lyY2xlID0gc3R5bGVkLmNpcmNsZSBgXG4gIGZpbGw6IG5vbmU7XG4gIHN0cm9rZTogJHtwcm9wcyA9PiBwcm9wcy5jb2xvcn07XG4gIHN0cm9rZS13aWR0aDogNTtcbiAgc3Ryb2tlLWxpbmVjYXA6IHJvdW5kO1xuICB0cmFuc2Zvcm0tb3JpZ2luOiBjZW50ZXI7XG5gO1xuY29uc3QgQW5pbWF0ZWRDaXJjbGUgPSBzdHlsZWQuY2lyY2xlIGBcbiAgZmlsbDogbm9uZTtcbiAgc3Ryb2tlOiAke3Byb3BzID0+IHByb3BzLmNvbG9yfTtcbiAgc3Ryb2tlLXdpZHRoOiA1O1xuICBzdHJva2UtbGluZWNhcDogcm91bmQ7XG4gIHRyYW5zZm9ybS1vcmlnaW46IGNlbnRlcjtcbiAgYW5pbWF0aW9uOiBkYXNoQW5pbWF0aW9uIDJzIGVhc2UtaW4tb3V0IGluZmluaXRlLFxuICAgIHNwaW5BbmltYXRpb24gMnMgbGluZWFyIGluZmluaXRlO1xuXG4gIEBrZXlmcmFtZXMgZGFzaEFuaW1hdGlvbiB7XG4gICAgMCUge1xuICAgICAgc3Ryb2tlLWRhc2hhcnJheTogMSwgMTUwO1xuICAgICAgc3Ryb2tlLWRhc2hvZmZzZXQ6IDA7XG4gICAgfVxuXG4gICAgNTAlIHtcbiAgICAgIHN0cm9rZS1kYXNoYXJyYXk6IDkwLCAxNTA7XG4gICAgICBzdHJva2UtZGFzaG9mZnNldDogLTUwO1xuICAgIH1cblxuICAgIDEwMCUge1xuICAgICAgc3Ryb2tlLWRhc2hhcnJheTogOTAsIDE1MDtcbiAgICAgIHN0cm9rZS1kYXNob2Zmc2V0OiAtMTQwO1xuICAgIH1cbiAgfVxuXG4gIEBrZXlmcmFtZXMgc3BpbkFuaW1hdGlvbiB7XG4gICAgdHJhbnNmb3JtOiByb3RhdGUoMzYwZGVnKTtcbiAgfVxuYDtcbmV4cG9ydCBkZWZhdWx0IGZ1bmN0aW9uIFVJU3Bpbm5lcih7IHNpemUgPSAyMCB9KSB7XG4gICAgcmV0dXJuIChfanN4KFNwaW5uZXJPdXRlciwgeyBjaGlsZHJlbjogX2pzeChTcGlubmVySW5uZXIsIHsgY2hpbGRyZW46IF9qc3hzKFwic3ZnXCIsIHsgaGVpZ2h0OiBzaXplLCB3aWR0aDogc2l6ZSwgdmlld0JveDogXCIwIDAgNTAgNTBcIiwgY2hpbGRyZW46IFtfanN4KENpcmNsZSwgeyBjb2xvcjogQ0FMWVBTT19NRURJVU0sIGN4OiBcIjI1XCIsIGN5OiBcIjI1XCIsIHI6IFwiMjIuNVwiIH0pLCBfanN4KEFuaW1hdGVkQ2lyY2xlLCB7IGNvbG9yOiBDQUxZUFNPLCBjeDogXCIyNVwiLCBjeTogXCIyNVwiLCByOiBcIjIyLjVcIiB9KV0gfSkgfSkgfSkpO1xufVxuIl19*/","import { styled } from '@linaria/react';\nimport { HEFFALUMP, LORAX, OLAF } from './colors';\nexport default styled.button `\n background-color:${props => (props.use === 'tertiary' ? HEFFALUMP : LORAX)};\n border: 3px solid ${props => (props.use === 'tertiary' ? HEFFALUMP : LORAX)};\n color: ${OLAF}\n border-radius: 3px;\n font-size: 14px;\n line-height: 14px;\n padding: 12px 24px;\n font-family: 'Lexend Deca', Helvetica, Arial, sans-serif;\n font-weight: 500;\n white-space: nowrap;\n`;\n",".ug152ch{background-color:var(--ug152ch-0);border:3px solid var(--ug152ch-0);color:#ffffff;border-radius:3px;font-size:14px;line-height:14px;padding:12px 24px;font-family:'Lexend Deca',Helvetica,Arial,sans-serif;font-weight:500;white-space:nowrap;}\n/*# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIi91c3Ivc2hhcmUvaHVic3BvdC9idWlsZC93b3Jrc3BhY2UvTGVhZGluV29yZFByZXNzUGx1Z2luL2xlYWRpbi9zY3JpcHRzL3NoYXJlZC9VSUNvbXBvbmVudHMvVUlCdXR0b24udHMiXSwibmFtZXMiOlsiLnVnMTUyY2giXSwibWFwcGluZ3MiOiJBQUVlQSIsImZpbGUiOiIvdXNyL3NoYXJlL2h1YnNwb3QvYnVpbGQvd29ya3NwYWNlL0xlYWRpbldvcmRQcmVzc1BsdWdpbi9sZWFkaW4vc2NyaXB0cy9zaGFyZWQvVUlDb21wb25lbnRzL1VJQnV0dG9uLnRzIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsgc3R5bGVkIH0gZnJvbSAnQGxpbmFyaWEvcmVhY3QnO1xuaW1wb3J0IHsgSEVGRkFMVU1QLCBMT1JBWCwgT0xBRiB9IGZyb20gJy4vY29sb3JzJztcbmV4cG9ydCBkZWZhdWx0IHN0eWxlZC5idXR0b24gYFxuICBiYWNrZ3JvdW5kLWNvbG9yOiR7cHJvcHMgPT4gKHByb3BzLnVzZSA9PT0gJ3RlcnRpYXJ5JyA/IEhFRkZBTFVNUCA6IExPUkFYKX07XG4gIGJvcmRlcjogM3B4IHNvbGlkICR7cHJvcHMgPT4gKHByb3BzLnVzZSA9PT0gJ3RlcnRpYXJ5JyA/IEhFRkZBTFVNUCA6IExPUkFYKX07XG4gIGNvbG9yOiAke09MQUZ9XG4gIGJvcmRlci1yYWRpdXM6IDNweDtcbiAgZm9udC1zaXplOiAxNHB4O1xuICBsaW5lLWhlaWdodDogMTRweDtcbiAgcGFkZGluZzogMTJweCAyNHB4O1xuICBmb250LWZhbWlseTogJ0xleGVuZCBEZWNhJywgSGVsdmV0aWNhLCBBcmlhbCwgc2Fucy1zZXJpZjtcbiAgZm9udC13ZWlnaHQ6IDUwMDtcbiAgd2hpdGUtc3BhY2U6IG5vd3JhcDtcbmA7XG4iXX0=*/","import { styled } from '@linaria/react';\nexport default styled.div `\n text-align: ${props => (props.textAlign ? props.textAlign : 'inherit')};\n`;\n",".ua13n1c{text-align:var(--ua13n1c-0);}\n/*# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIi91c3Ivc2hhcmUvaHVic3BvdC9idWlsZC93b3Jrc3BhY2UvTGVhZGluV29yZFByZXNzUGx1Z2luL2xlYWRpbi9zY3JpcHRzL3NoYXJlZC9VSUNvbXBvbmVudHMvVUlDb250YWluZXIudHMiXSwibmFtZXMiOlsiLnVhMTNuMWMiXSwibWFwcGluZ3MiOiJBQUNlQSIsImZpbGUiOiIvdXNyL3NoYXJlL2h1YnNwb3QvYnVpbGQvd29ya3NwYWNlL0xlYWRpbldvcmRQcmVzc1BsdWdpbi9sZWFkaW4vc2NyaXB0cy9zaGFyZWQvVUlDb21wb25lbnRzL1VJQ29udGFpbmVyLnRzIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsgc3R5bGVkIH0gZnJvbSAnQGxpbmFyaWEvcmVhY3QnO1xuZXhwb3J0IGRlZmF1bHQgc3R5bGVkLmRpdiBgXG4gIHRleHQtYWxpZ246ICR7cHJvcHMgPT4gKHByb3BzLnRleHRBbGlnbiA/IHByb3BzLnRleHRBbGlnbiA6ICdpbmhlcml0Jyl9O1xuYDtcbiJdfQ==*/","import { styled } from '@linaria/react';\nexport default styled.div `\n background-image: ${props => `url(${props.pluginPath}/public/assets/images/hubspot.svg)`};\n background-color: #f5f8fa;\n background-repeat: no-repeat;\n background-position: center 25px;\n background-size: 120px;\n color: #33475b;\n font-family: 'Lexend Deca', Helvetica, Arial, sans-serif;\n font-size: 14px;\n\n padding: ${(props) => props.padding || '90px 20% 25px'};\n\n p {\n font-size: inherit !important;\n line-height: 24px;\n margin: 4px 0;\n }\n`;\n",".h1q5v5ee{background-image:var(--h1q5v5ee-0);background-color:#f5f8fa;background-repeat:no-repeat;background-position:center 25px;background-size:120px;color:#33475b;font-family:'Lexend Deca',Helvetica,Arial,sans-serif;font-size:14px;padding:var(--h1q5v5ee-1);}.h1q5v5ee p{font-size:inherit !important;line-height:24px;margin:4px 0;}\n/*# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIi91c3Ivc2hhcmUvaHVic3BvdC9idWlsZC93b3Jrc3BhY2UvTGVhZGluV29yZFByZXNzUGx1Z2luL2xlYWRpbi9zY3JpcHRzL3NoYXJlZC9Db21tb24vSHVic3BvdFdyYXBwZXIudHMiXSwibmFtZXMiOlsiLmgxcTV2NWVlIl0sIm1hcHBpbmdzIjoiQUFDZUEiLCJmaWxlIjoiL3Vzci9zaGFyZS9odWJzcG90L2J1aWxkL3dvcmtzcGFjZS9MZWFkaW5Xb3JkUHJlc3NQbHVnaW4vbGVhZGluL3NjcmlwdHMvc2hhcmVkL0NvbW1vbi9IdWJzcG90V3JhcHBlci50cyIsInNvdXJjZXNDb250ZW50IjpbImltcG9ydCB7IHN0eWxlZCB9IGZyb20gJ0BsaW5hcmlhL3JlYWN0JztcbmV4cG9ydCBkZWZhdWx0IHN0eWxlZC5kaXYgYFxuICBiYWNrZ3JvdW5kLWltYWdlOiAke3Byb3BzID0+IGB1cmwoJHtwcm9wcy5wbHVnaW5QYXRofS9wdWJsaWMvYXNzZXRzL2ltYWdlcy9odWJzcG90LnN2ZylgfTtcbiAgYmFja2dyb3VuZC1jb2xvcjogI2Y1ZjhmYTtcbiAgYmFja2dyb3VuZC1yZXBlYXQ6IG5vLXJlcGVhdDtcbiAgYmFja2dyb3VuZC1wb3NpdGlvbjogY2VudGVyIDI1cHg7XG4gIGJhY2tncm91bmQtc2l6ZTogMTIwcHg7XG4gIGNvbG9yOiAjMzM0NzViO1xuICBmb250LWZhbWlseTogJ0xleGVuZCBEZWNhJywgSGVsdmV0aWNhLCBBcmlhbCwgc2Fucy1zZXJpZjtcbiAgZm9udC1zaXplOiAxNHB4O1xuXG4gIHBhZGRpbmc6ICR7KHByb3BzKSA9PiBwcm9wcy5wYWRkaW5nIHx8ICc5MHB4IDIwJSAyNXB4J307XG5cbiAgcCB7XG4gICAgZm9udC1zaXplOiBpbmhlcml0ICFpbXBvcnRhbnQ7XG4gICAgbGluZS1oZWlnaHQ6IDI0cHg7XG4gICAgbWFyZ2luOiA0cHggMDtcbiAgfVxuYDtcbiJdfQ==*/","import { styled } from '@linaria/react';\nexport default styled.div `\n height: 30px;\n`;\n",".u3qxofx{height:30px;}\n/*# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIi91c3Ivc2hhcmUvaHVic3BvdC9idWlsZC93b3Jrc3BhY2UvTGVhZGluV29yZFByZXNzUGx1Z2luL2xlYWRpbi9zY3JpcHRzL3NoYXJlZC9VSUNvbXBvbmVudHMvVUlTcGFjZXIudHMiXSwibmFtZXMiOlsiLnUzcXhvZngiXSwibWFwcGluZ3MiOiJBQUNlQSIsImZpbGUiOiIvdXNyL3NoYXJlL2h1YnNwb3QvYnVpbGQvd29ya3NwYWNlL0xlYWRpbldvcmRQcmVzc1BsdWdpbi9sZWFkaW4vc2NyaXB0cy9zaGFyZWQvVUlDb21wb25lbnRzL1VJU3BhY2VyLnRzIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsgc3R5bGVkIH0gZnJvbSAnQGxpbmFyaWEvcmVhY3QnO1xuZXhwb3J0IGRlZmF1bHQgc3R5bGVkLmRpdiBgXG4gIGhlaWdodDogMzBweDtcbmA7XG4iXX0=*/","import { styled } from '@linaria/react';\nexport default styled.div `\n position: relative;\n\n &:after {\n content: '';\n position: absolute;\n top: 0;\n bottom: 0;\n right: 0;\n left: 0;\n }\n`;\n",".u1q7a48k{position:relative;}.u1q7a48k:after{content:'';position:absolute;top:0;bottom:0;right:0;left:0;}\n/*# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIi91c3Ivc2hhcmUvaHVic3BvdC9idWlsZC93b3Jrc3BhY2UvTGVhZGluV29yZFByZXNzUGx1Z2luL2xlYWRpbi9zY3JpcHRzL3NoYXJlZC9VSUNvbXBvbmVudHMvVUlPdmVybGF5LnRzIl0sIm5hbWVzIjpbIi51MXE3YTQ4ayJdLCJtYXBwaW5ncyI6IkFBQ2VBIiwiZmlsZSI6Ii91c3Ivc2hhcmUvaHVic3BvdC9idWlsZC93b3Jrc3BhY2UvTGVhZGluV29yZFByZXNzUGx1Z2luL2xlYWRpbi9zY3JpcHRzL3NoYXJlZC9VSUNvbXBvbmVudHMvVUlPdmVybGF5LnRzIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsgc3R5bGVkIH0gZnJvbSAnQGxpbmFyaWEvcmVhY3QnO1xuZXhwb3J0IGRlZmF1bHQgc3R5bGVkLmRpdiBgXG4gIHBvc2l0aW9uOiByZWxhdGl2ZTtcblxuICAmOmFmdGVyIHtcbiAgICBjb250ZW50OiAnJztcbiAgICBwb3NpdGlvbjogYWJzb2x1dGU7XG4gICAgdG9wOiAwO1xuICAgIGJvdHRvbTogMDtcbiAgICByaWdodDogMDtcbiAgICBsZWZ0OiAwO1xuICB9XG5gO1xuIl19*/","import { jsx as _jsx, jsxs as _jsxs } from \"react/jsx-runtime\";\nimport { useRef, useState, useEffect } from 'react';\nimport { styled } from '@linaria/react';\nimport { CALYPSO, CALYPSO_LIGHT, CALYPSO_MEDIUM, OBSIDIAN, } from '../UIComponents/colors';\nimport UISpinner from '../UIComponents/UISpinner';\nimport LoadState from '../enums/loadState';\nconst Container = styled.div `\n color: ${OBSIDIAN};\n font-family: 'Lexend Deca', Helvetica, Arial, sans-serif;\n font-size: 14px;\n position: relative;\n`;\nconst ControlContainer = styled.div `\n align-items: center;\n background-color: hsl(0, 0%, 100%);\n border-color: hsl(0, 0%, 80%);\n border-radius: 4px;\n border-style: solid;\n border-width: ${props => (props.focused ? '0' : '1px')};\n cursor: default;\n display: flex;\n flex-wrap: wrap;\n justify-content: space-between;\n min-height: 38px;\n outline: 0 !important;\n position: relative;\n transition: all 100ms;\n box-sizing: border-box;\n box-shadow: ${props => props.focused ? `0 0 0 2px ${CALYPSO_MEDIUM}` : 'none'};\n &:hover {\n border-color: hsl(0, 0%, 70%);\n }\n`;\nconst ValueContainer = styled.div `\n align-items: center;\n display: flex;\n flex: 1;\n flex-wrap: wrap;\n padding: 2px 8px;\n position: relative;\n overflow: hidden;\n box-sizing: border-box;\n`;\nconst Placeholder = styled.div `\n color: hsl(0, 0%, 50%);\n margin-left: 2px;\n margin-right: 2px;\n position: absolute;\n top: 50%;\n transform: translateY(-50%);\n box-sizing: border-box;\n font-size: 16px;\n`;\nconst SingleValue = styled.div `\n color: hsl(0, 0%, 20%);\n margin-left: 2px;\n margin-right: 2px;\n max-width: calc(100% - 8px);\n overflow: hidden;\n position: absolute;\n text-overflow: ellipsis;\n white-space: nowrap;\n top: 50%;\n transform: translateY(-50%);\n box-sizing: border-box;\n`;\nconst IndicatorContainer = styled.div `\n align-items: center;\n align-self: stretch;\n display: flex;\n flex-shrink: 0;\n box-sizing: border-box;\n`;\nconst DropdownIndicator = styled.div `\n border-top: 8px solid ${CALYPSO};\n border-left: 6px solid transparent;\n border-right: 6px solid transparent;\n width: 0px;\n height: 0px;\n margin: 10px;\n`;\nconst InputContainer = styled.div `\n margin: 2px;\n padding-bottom: 2px;\n padding-top: 2px;\n visibility: visible;\n color: hsl(0, 0%, 20%);\n box-sizing: border-box;\n`;\nconst Input = styled.input `\n box-sizing: content-box;\n background: rgba(0, 0, 0, 0) none repeat scroll 0px center;\n border: 0px none;\n font-size: inherit;\n opacity: 1;\n outline: currentcolor none 0px;\n padding: 0px;\n color: inherit;\n font-family: inherit;\n`;\nconst InputShadow = styled.div `\n position: absolute;\n opacity: 0;\n font-size: inherit;\n`;\nconst MenuContainer = styled.div `\n position: absolute;\n top: 100%;\n background-color: #fff;\n border-radius: 4px;\n margin-bottom: 8px;\n margin-top: 8px;\n z-index: 9999;\n box-shadow: 0 0 0 1px hsla(0, 0%, 0%, 0.1), 0 4px 11px hsla(0, 0%, 0%, 0.1);\n width: 100%;\n`;\nconst MenuList = styled.div `\n max-height: 300px;\n overflow-y: auto;\n padding-bottom: 4px;\n padding-top: 4px;\n position: relative;\n`;\nconst MenuGroup = styled.div `\n padding-bottom: 8px;\n padding-top: 8px;\n`;\nconst MenuGroupHeader = styled.div `\n color: #999;\n cursor: default;\n font-size: 75%;\n font-weight: 500;\n margin-bottom: 0.25em;\n text-transform: uppercase;\n padding-left: 12px;\n padding-left: 12px;\n`;\nconst MenuItem = styled.div `\n display: block;\n background-color: ${props => props.selected ? CALYPSO_MEDIUM : 'transparent'};\n color: ${props => (props.selected ? '#fff' : 'inherit')};\n cursor: default;\n font-size: inherit;\n width: 100%;\n padding: 8px 12px;\n &:hover {\n background-color: ${props => props.selected ? CALYPSO_MEDIUM : CALYPSO_LIGHT};\n }\n`;\nexport default function AsyncSelect({ placeholder, value, loadOptions, onChange, defaultOptions, }) {\n const inputEl = useRef(null);\n const inputShadowEl = useRef(null);\n const [isFocused, setFocus] = useState(false);\n const [loadState, setLoadState] = useState(LoadState.NotLoaded);\n const [localValue, setLocalValue] = useState('');\n const [options, setOptions] = useState(defaultOptions);\n const inputSize = `${inputShadowEl.current ? inputShadowEl.current.clientWidth + 10 : 2}px`;\n useEffect(() => {\n if (loadOptions && loadState === LoadState.NotLoaded) {\n loadOptions('', (result) => {\n setOptions(result);\n setLoadState(LoadState.Idle);\n });\n }\n }, [loadOptions, loadState]);\n const renderItems = (items = [], parentKey) => {\n return items.map((item, index) => {\n if (item.options) {\n return (_jsxs(MenuGroup, { children: [_jsx(MenuGroupHeader, { id: `${index}-heading`, children: item.label }), _jsx(\"div\", { children: renderItems(item.options, index) })] }, `async-select-item-${index}`));\n }\n else {\n const key = `async-select-item-${parentKey !== undefined ? `${parentKey}-${index}` : index}`;\n return (_jsx(MenuItem, { id: key, selected: value && item.value === value.value, onClick: () => {\n onChange(item);\n setFocus(false);\n }, children: item.label }, key));\n }\n });\n };\n return (_jsxs(Container, { children: [_jsxs(ControlContainer, { id: \"leadin-async-selector\", focused: isFocused, onClick: () => {\n if (isFocused) {\n if (inputEl.current) {\n inputEl.current.blur();\n }\n setFocus(false);\n setLocalValue('');\n }\n else {\n if (inputEl.current) {\n inputEl.current.focus();\n }\n setFocus(true);\n }\n }, children: [_jsxs(ValueContainer, { children: [localValue === '' &&\n (!value ? (_jsx(Placeholder, { children: placeholder })) : (_jsx(SingleValue, { children: value.label }))), _jsxs(InputContainer, { children: [_jsx(Input, { ref: inputEl, onFocus: () => {\n setFocus(true);\n }, onChange: e => {\n setLocalValue(e.target.value);\n setLoadState(LoadState.Loading);\n loadOptions &&\n loadOptions(e.target.value, (result) => {\n setOptions(result);\n setLoadState(LoadState.Idle);\n });\n }, value: localValue, width: inputSize, id: \"asycn-select-input\" }), _jsx(InputShadow, { ref: inputShadowEl, children: localValue })] })] }), _jsxs(IndicatorContainer, { children: [loadState === LoadState.Loading && _jsx(UISpinner, {}), _jsx(DropdownIndicator, {})] })] }), isFocused && (_jsx(MenuContainer, { children: _jsx(MenuList, { children: renderItems(options) }) }))] }));\n}\n",".c1wxx7eu{color:#33475b;font-family:'Lexend Deca',Helvetica,Arial,sans-serif;font-size:14px;position:relative;}\n.c1rgwbep{-webkit-align-items:center;-webkit-box-align:center;-ms-flex-align:center;align-items:center;background-color:hsl(0,0%,100%);border-color:hsl(0,0%,80%);border-radius:4px;border-style:solid;border-width:var(--c1rgwbep-0);cursor:default;display:-webkit-box;display:-webkit-flex;display:-ms-flexbox;display:flex;-webkit-flex-wrap:wrap;-ms-flex-wrap:wrap;flex-wrap:wrap;-webkit-box-pack:justify;-webkit-justify-content:space-between;-ms-flex-pack:justify;justify-content:space-between;min-height:38px;outline:0 !important;position:relative;-webkit-transition:all 100ms;transition:all 100ms;box-sizing:border-box;box-shadow:var(--c1rgwbep-1);}.c1rgwbep:hover{border-color:hsl(0,0%,70%);}\n.v1mdmbaj{-webkit-align-items:center;-webkit-box-align:center;-ms-flex-align:center;align-items:center;display:-webkit-box;display:-webkit-flex;display:-ms-flexbox;display:flex;-webkit-flex:1;-ms-flex:1;flex:1;-webkit-flex-wrap:wrap;-ms-flex-wrap:wrap;flex-wrap:wrap;padding:2px 8px;position:relative;overflow:hidden;box-sizing:border-box;}\n.p1gwkvxy{color:hsl(0,0%,50%);margin-left:2px;margin-right:2px;position:absolute;top:50%;-webkit-transform:translateY(-50%);-ms-transform:translateY(-50%);transform:translateY(-50%);box-sizing:border-box;font-size:16px;}\n.s1bwlafs{color:hsl(0,0%,20%);margin-left:2px;margin-right:2px;max-width:calc(100% - 8px);overflow:hidden;position:absolute;text-overflow:ellipsis;white-space:nowrap;top:50%;-webkit-transform:translateY(-50%);-ms-transform:translateY(-50%);transform:translateY(-50%);box-sizing:border-box;}\n.i196z9y5{-webkit-align-items:center;-webkit-box-align:center;-ms-flex-align:center;align-items:center;-webkit-align-self:stretch;-ms-flex-item-align:stretch;align-self:stretch;display:-webkit-box;display:-webkit-flex;display:-ms-flexbox;display:flex;-webkit-flex-shrink:0;-ms-flex-negative:0;flex-shrink:0;box-sizing:border-box;}\n.d1dfo5ow{border-top:8px solid #00a4bd;border-left:6px solid transparent;border-right:6px solid transparent;width:0px;height:0px;margin:10px;}\n.if3lze{margin:2px;padding-bottom:2px;padding-top:2px;visibility:visible;color:hsl(0,0%,20%);box-sizing:border-box;}\n.i9kxf50{box-sizing:content-box;background:rgba(0,0,0,0) none repeat scroll 0px center;border:0px none;font-size:inherit;opacity:1;outline:currentcolor none 0px;padding:0px;color:inherit;font-family:inherit;}\n.igjr3uc{position:absolute;opacity:0;font-size:inherit;}\n.mhb9if7{position:absolute;top:100%;background-color:#fff;border-radius:4px;margin-bottom:8px;margin-top:8px;z-index:9999;box-shadow:0 0 0 1px hsla(0,0%,0%,0.1),0 4px 11px hsla(0,0%,0%,0.1);width:100%;}\n.mxaof7s{max-height:300px;overflow-y:auto;padding-bottom:4px;padding-top:4px;position:relative;}\n.mw50s5v{padding-bottom:8px;padding-top:8px;}\n.m11rzvjw{color:#999;cursor:default;font-size:75%;font-weight:500;margin-bottom:0.25em;text-transform:uppercase;padding-left:12px;padding-left:12px;}\n.m1jcdsjv{display:block;background-color:var(--m1jcdsjv-0);color:var(--m1jcdsjv-1);cursor:default;font-size:inherit;width:100%;padding:8px 12px;}.m1jcdsjv:hover{background-color:var(--m1jcdsjv-2);}\n/*# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIi91c3Ivc2hhcmUvaHVic3BvdC9idWlsZC93b3Jrc3BhY2UvTGVhZGluV29yZFByZXNzUGx1Z2luL2xlYWRpbi9zY3JpcHRzL3NoYXJlZC9Db21tb24vQXN5bmNTZWxlY3QudHN4Il0sIm5hbWVzIjpbIi5jMXd4eDdldSIsIi5jMXJnd2JlcCIsIi52MW1kbWJhaiIsIi5wMWd3a3Z4eSIsIi5zMWJ3bGFmcyIsIi5pMTk2ejl5NSIsIi5kMWRmbzVvdyIsIi5pZjNsemUiLCIuaTlreGY1MCIsIi5pZ2pyM3VjIiwiLm1oYjlpZjciLCIubXhhb2Y3cyIsIi5tdzUwczV2IiwiLm0xMXJ6dmp3IiwiLm0xamNkc2p2Il0sIm1hcHBpbmdzIjoiQUFNa0JBO0FBTU9DO0FBcUJGQztBQVVIQztBQVVBQztBQWFPQztBQU9EQztBQVFIQztBQVFUQztBQVdNQztBQUtFQztBQVdMQztBQU9DQztBQUlNQztBQVVQQyIsImZpbGUiOiIvdXNyL3NoYXJlL2h1YnNwb3QvYnVpbGQvd29ya3NwYWNlL0xlYWRpbldvcmRQcmVzc1BsdWdpbi9sZWFkaW4vc2NyaXB0cy9zaGFyZWQvQ29tbW9uL0FzeW5jU2VsZWN0LnRzeCIsInNvdXJjZXNDb250ZW50IjpbImltcG9ydCB7IGpzeCBhcyBfanN4LCBqc3hzIGFzIF9qc3hzIH0gZnJvbSBcInJlYWN0L2pzeC1ydW50aW1lXCI7XG5pbXBvcnQgeyB1c2VSZWYsIHVzZVN0YXRlLCB1c2VFZmZlY3QgfSBmcm9tICdyZWFjdCc7XG5pbXBvcnQgeyBzdHlsZWQgfSBmcm9tICdAbGluYXJpYS9yZWFjdCc7XG5pbXBvcnQgeyBDQUxZUFNPLCBDQUxZUFNPX0xJR0hULCBDQUxZUFNPX01FRElVTSwgT0JTSURJQU4sIH0gZnJvbSAnLi4vVUlDb21wb25lbnRzL2NvbG9ycyc7XG5pbXBvcnQgVUlTcGlubmVyIGZyb20gJy4uL1VJQ29tcG9uZW50cy9VSVNwaW5uZXInO1xuaW1wb3J0IExvYWRTdGF0ZSBmcm9tICcuLi9lbnVtcy9sb2FkU3RhdGUnO1xuY29uc3QgQ29udGFpbmVyID0gc3R5bGVkLmRpdiBgXG4gIGNvbG9yOiAke09CU0lESUFOfTtcbiAgZm9udC1mYW1pbHk6ICdMZXhlbmQgRGVjYScsIEhlbHZldGljYSwgQXJpYWwsIHNhbnMtc2VyaWY7XG4gIGZvbnQtc2l6ZTogMTRweDtcbiAgcG9zaXRpb246IHJlbGF0aXZlO1xuYDtcbmNvbnN0IENvbnRyb2xDb250YWluZXIgPSBzdHlsZWQuZGl2IGBcbiAgYWxpZ24taXRlbXM6IGNlbnRlcjtcbiAgYmFja2dyb3VuZC1jb2xvcjogaHNsKDAsIDAlLCAxMDAlKTtcbiAgYm9yZGVyLWNvbG9yOiBoc2woMCwgMCUsIDgwJSk7XG4gIGJvcmRlci1yYWRpdXM6IDRweDtcbiAgYm9yZGVyLXN0eWxlOiBzb2xpZDtcbiAgYm9yZGVyLXdpZHRoOiAke3Byb3BzID0+IChwcm9wcy5mb2N1c2VkID8gJzAnIDogJzFweCcpfTtcbiAgY3Vyc29yOiBkZWZhdWx0O1xuICBkaXNwbGF5OiBmbGV4O1xuICBmbGV4LXdyYXA6IHdyYXA7XG4gIGp1c3RpZnktY29udGVudDogc3BhY2UtYmV0d2VlbjtcbiAgbWluLWhlaWdodDogMzhweDtcbiAgb3V0bGluZTogMCAhaW1wb3J0YW50O1xuICBwb3NpdGlvbjogcmVsYXRpdmU7XG4gIHRyYW5zaXRpb246IGFsbCAxMDBtcztcbiAgYm94LXNpemluZzogYm9yZGVyLWJveDtcbiAgYm94LXNoYWRvdzogJHtwcm9wcyA9PiBwcm9wcy5mb2N1c2VkID8gYDAgMCAwIDJweCAke0NBTFlQU09fTUVESVVNfWAgOiAnbm9uZSd9O1xuICAmOmhvdmVyIHtcbiAgICBib3JkZXItY29sb3I6IGhzbCgwLCAwJSwgNzAlKTtcbiAgfVxuYDtcbmNvbnN0IFZhbHVlQ29udGFpbmVyID0gc3R5bGVkLmRpdiBgXG4gIGFsaWduLWl0ZW1zOiBjZW50ZXI7XG4gIGRpc3BsYXk6IGZsZXg7XG4gIGZsZXg6IDE7XG4gIGZsZXgtd3JhcDogd3JhcDtcbiAgcGFkZGluZzogMnB4IDhweDtcbiAgcG9zaXRpb246IHJlbGF0aXZlO1xuICBvdmVyZmxvdzogaGlkZGVuO1xuICBib3gtc2l6aW5nOiBib3JkZXItYm94O1xuYDtcbmNvbnN0IFBsYWNlaG9sZGVyID0gc3R5bGVkLmRpdiBgXG4gIGNvbG9yOiBoc2woMCwgMCUsIDUwJSk7XG4gIG1hcmdpbi1sZWZ0OiAycHg7XG4gIG1hcmdpbi1yaWdodDogMnB4O1xuICBwb3NpdGlvbjogYWJzb2x1dGU7XG4gIHRvcDogNTAlO1xuICB0cmFuc2Zvcm06IHRyYW5zbGF0ZVkoLTUwJSk7XG4gIGJveC1zaXppbmc6IGJvcmRlci1ib3g7XG4gIGZvbnQtc2l6ZTogMTZweDtcbmA7XG5jb25zdCBTaW5nbGVWYWx1ZSA9IHN0eWxlZC5kaXYgYFxuICBjb2xvcjogaHNsKDAsIDAlLCAyMCUpO1xuICBtYXJnaW4tbGVmdDogMnB4O1xuICBtYXJnaW4tcmlnaHQ6IDJweDtcbiAgbWF4LXdpZHRoOiBjYWxjKDEwMCUgLSA4cHgpO1xuICBvdmVyZmxvdzogaGlkZGVuO1xuICBwb3NpdGlvbjogYWJzb2x1dGU7XG4gIHRleHQtb3ZlcmZsb3c6IGVsbGlwc2lzO1xuICB3aGl0ZS1zcGFjZTogbm93cmFwO1xuICB0b3A6IDUwJTtcbiAgdHJhbnNmb3JtOiB0cmFuc2xhdGVZKC01MCUpO1xuICBib3gtc2l6aW5nOiBib3JkZXItYm94O1xuYDtcbmNvbnN0IEluZGljYXRvckNvbnRhaW5lciA9IHN0eWxlZC5kaXYgYFxuICBhbGlnbi1pdGVtczogY2VudGVyO1xuICBhbGlnbi1zZWxmOiBzdHJldGNoO1xuICBkaXNwbGF5OiBmbGV4O1xuICBmbGV4LXNocmluazogMDtcbiAgYm94LXNpemluZzogYm9yZGVyLWJveDtcbmA7XG5jb25zdCBEcm9wZG93bkluZGljYXRvciA9IHN0eWxlZC5kaXYgYFxuICBib3JkZXItdG9wOiA4cHggc29saWQgJHtDQUxZUFNPfTtcbiAgYm9yZGVyLWxlZnQ6IDZweCBzb2xpZCB0cmFuc3BhcmVudDtcbiAgYm9yZGVyLXJpZ2h0OiA2cHggc29saWQgdHJhbnNwYXJlbnQ7XG4gIHdpZHRoOiAwcHg7XG4gIGhlaWdodDogMHB4O1xuICBtYXJnaW46IDEwcHg7XG5gO1xuY29uc3QgSW5wdXRDb250YWluZXIgPSBzdHlsZWQuZGl2IGBcbiAgbWFyZ2luOiAycHg7XG4gIHBhZGRpbmctYm90dG9tOiAycHg7XG4gIHBhZGRpbmctdG9wOiAycHg7XG4gIHZpc2liaWxpdHk6IHZpc2libGU7XG4gIGNvbG9yOiBoc2woMCwgMCUsIDIwJSk7XG4gIGJveC1zaXppbmc6IGJvcmRlci1ib3g7XG5gO1xuY29uc3QgSW5wdXQgPSBzdHlsZWQuaW5wdXQgYFxuICBib3gtc2l6aW5nOiBjb250ZW50LWJveDtcbiAgYmFja2dyb3VuZDogcmdiYSgwLCAwLCAwLCAwKSBub25lIHJlcGVhdCBzY3JvbGwgMHB4IGNlbnRlcjtcbiAgYm9yZGVyOiAwcHggbm9uZTtcbiAgZm9udC1zaXplOiBpbmhlcml0O1xuICBvcGFjaXR5OiAxO1xuICBvdXRsaW5lOiBjdXJyZW50Y29sb3Igbm9uZSAwcHg7XG4gIHBhZGRpbmc6IDBweDtcbiAgY29sb3I6IGluaGVyaXQ7XG4gIGZvbnQtZmFtaWx5OiBpbmhlcml0O1xuYDtcbmNvbnN0IElucHV0U2hhZG93ID0gc3R5bGVkLmRpdiBgXG4gIHBvc2l0aW9uOiBhYnNvbHV0ZTtcbiAgb3BhY2l0eTogMDtcbiAgZm9udC1zaXplOiBpbmhlcml0O1xuYDtcbmNvbnN0IE1lbnVDb250YWluZXIgPSBzdHlsZWQuZGl2IGBcbiAgcG9zaXRpb246IGFic29sdXRlO1xuICB0b3A6IDEwMCU7XG4gIGJhY2tncm91bmQtY29sb3I6ICNmZmY7XG4gIGJvcmRlci1yYWRpdXM6IDRweDtcbiAgbWFyZ2luLWJvdHRvbTogOHB4O1xuICBtYXJnaW4tdG9wOiA4cHg7XG4gIHotaW5kZXg6IDk5OTk7XG4gIGJveC1zaGFkb3c6IDAgMCAwIDFweCBoc2xhKDAsIDAlLCAwJSwgMC4xKSwgMCA0cHggMTFweCBoc2xhKDAsIDAlLCAwJSwgMC4xKTtcbiAgd2lkdGg6IDEwMCU7XG5gO1xuY29uc3QgTWVudUxpc3QgPSBzdHlsZWQuZGl2IGBcbiAgbWF4LWhlaWdodDogMzAwcHg7XG4gIG92ZXJmbG93LXk6IGF1dG87XG4gIHBhZGRpbmctYm90dG9tOiA0cHg7XG4gIHBhZGRpbmctdG9wOiA0cHg7XG4gIHBvc2l0aW9uOiByZWxhdGl2ZTtcbmA7XG5jb25zdCBNZW51R3JvdXAgPSBzdHlsZWQuZGl2IGBcbiAgcGFkZGluZy1ib3R0b206IDhweDtcbiAgcGFkZGluZy10b3A6IDhweDtcbmA7XG5jb25zdCBNZW51R3JvdXBIZWFkZXIgPSBzdHlsZWQuZGl2IGBcbiAgY29sb3I6ICM5OTk7XG4gIGN1cnNvcjogZGVmYXVsdDtcbiAgZm9udC1zaXplOiA3NSU7XG4gIGZvbnQtd2VpZ2h0OiA1MDA7XG4gIG1hcmdpbi1ib3R0b206IDAuMjVlbTtcbiAgdGV4dC10cmFuc2Zvcm06IHVwcGVyY2FzZTtcbiAgcGFkZGluZy1sZWZ0OiAxMnB4O1xuICBwYWRkaW5nLWxlZnQ6IDEycHg7XG5gO1xuY29uc3QgTWVudUl0ZW0gPSBzdHlsZWQuZGl2IGBcbiAgZGlzcGxheTogYmxvY2s7XG4gIGJhY2tncm91bmQtY29sb3I6ICR7cHJvcHMgPT4gcHJvcHMuc2VsZWN0ZWQgPyBDQUxZUFNPX01FRElVTSA6ICd0cmFuc3BhcmVudCd9O1xuICBjb2xvcjogJHtwcm9wcyA9PiAocHJvcHMuc2VsZWN0ZWQgPyAnI2ZmZicgOiAnaW5oZXJpdCcpfTtcbiAgY3Vyc29yOiBkZWZhdWx0O1xuICBmb250LXNpemU6IGluaGVyaXQ7XG4gIHdpZHRoOiAxMDAlO1xuICBwYWRkaW5nOiA4cHggMTJweDtcbiAgJjpob3ZlciB7XG4gICAgYmFja2dyb3VuZC1jb2xvcjogJHtwcm9wcyA9PiBwcm9wcy5zZWxlY3RlZCA/IENBTFlQU09fTUVESVVNIDogQ0FMWVBTT19MSUdIVH07XG4gIH1cbmA7XG5leHBvcnQgZGVmYXVsdCBmdW5jdGlvbiBBc3luY1NlbGVjdCh7IHBsYWNlaG9sZGVyLCB2YWx1ZSwgbG9hZE9wdGlvbnMsIG9uQ2hhbmdlLCBkZWZhdWx0T3B0aW9ucywgfSkge1xuICAgIGNvbnN0IGlucHV0RWwgPSB1c2VSZWYobnVsbCk7XG4gICAgY29uc3QgaW5wdXRTaGFkb3dFbCA9IHVzZVJlZihudWxsKTtcbiAgICBjb25zdCBbaXNGb2N1c2VkLCBzZXRGb2N1c10gPSB1c2VTdGF0ZShmYWxzZSk7XG4gICAgY29uc3QgW2xvYWRTdGF0ZSwgc2V0TG9hZFN0YXRlXSA9IHVzZVN0YXRlKExvYWRTdGF0ZS5Ob3RMb2FkZWQpO1xuICAgIGNvbnN0IFtsb2NhbFZhbHVlLCBzZXRMb2NhbFZhbHVlXSA9IHVzZVN0YXRlKCcnKTtcbiAgICBjb25zdCBbb3B0aW9ucywgc2V0T3B0aW9uc10gPSB1c2VTdGF0ZShkZWZhdWx0T3B0aW9ucyk7XG4gICAgY29uc3QgaW5wdXRTaXplID0gYCR7aW5wdXRTaGFkb3dFbC5jdXJyZW50ID8gaW5wdXRTaGFkb3dFbC5jdXJyZW50LmNsaWVudFdpZHRoICsgMTAgOiAyfXB4YDtcbiAgICB1c2VFZmZlY3QoKCkgPT4ge1xuICAgICAgICBpZiAobG9hZE9wdGlvbnMgJiYgbG9hZFN0YXRlID09PSBMb2FkU3RhdGUuTm90TG9hZGVkKSB7XG4gICAgICAgICAgICBsb2FkT3B0aW9ucygnJywgKHJlc3VsdCkgPT4ge1xuICAgICAgICAgICAgICAgIHNldE9wdGlvbnMocmVzdWx0KTtcbiAgICAgICAgICAgICAgICBzZXRMb2FkU3RhdGUoTG9hZFN0YXRlLklkbGUpO1xuICAgICAgICAgICAgfSk7XG4gICAgICAgIH1cbiAgICB9LCBbbG9hZE9wdGlvbnMsIGxvYWRTdGF0ZV0pO1xuICAgIGNvbnN0IHJlbmRlckl0ZW1zID0gKGl0ZW1zID0gW10sIHBhcmVudEtleSkgPT4ge1xuICAgICAgICByZXR1cm4gaXRlbXMubWFwKChpdGVtLCBpbmRleCkgPT4ge1xuICAgICAgICAgICAgaWYgKGl0ZW0ub3B0aW9ucykge1xuICAgICAgICAgICAgICAgIHJldHVybiAoX2pzeHMoTWVudUdyb3VwLCB7IGNoaWxkcmVuOiBbX2pzeChNZW51R3JvdXBIZWFkZXIsIHsgaWQ6IGAke2luZGV4fS1oZWFkaW5nYCwgY2hpbGRyZW46IGl0ZW0ubGFiZWwgfSksIF9qc3goXCJkaXZcIiwgeyBjaGlsZHJlbjogcmVuZGVySXRlbXMoaXRlbS5vcHRpb25zLCBpbmRleCkgfSldIH0sIGBhc3luYy1zZWxlY3QtaXRlbS0ke2luZGV4fWApKTtcbiAgICAgICAgICAgIH1cbiAgICAgICAgICAgIGVsc2Uge1xuICAgICAgICAgICAgICAgIGNvbnN0IGtleSA9IGBhc3luYy1zZWxlY3QtaXRlbS0ke3BhcmVudEtleSAhPT0gdW5kZWZpbmVkID8gYCR7cGFyZW50S2V5fS0ke2luZGV4fWAgOiBpbmRleH1gO1xuICAgICAgICAgICAgICAgIHJldHVybiAoX2pzeChNZW51SXRlbSwgeyBpZDoga2V5LCBzZWxlY3RlZDogdmFsdWUgJiYgaXRlbS52YWx1ZSA9PT0gdmFsdWUudmFsdWUsIG9uQ2xpY2s6ICgpID0+IHtcbiAgICAgICAgICAgICAgICAgICAgICAgIG9uQ2hhbmdlKGl0ZW0pO1xuICAgICAgICAgICAgICAgICAgICAgICAgc2V0Rm9jdXMoZmFsc2UpO1xuICAgICAgICAgICAgICAgICAgICB9LCBjaGlsZHJlbjogaXRlbS5sYWJlbCB9LCBrZXkpKTtcbiAgICAgICAgICAgIH1cbiAgICAgICAgfSk7XG4gICAgfTtcbiAgICByZXR1cm4gKF9qc3hzKENvbnRhaW5lciwgeyBjaGlsZHJlbjogW19qc3hzKENvbnRyb2xDb250YWluZXIsIHsgaWQ6IFwibGVhZGluLWFzeW5jLXNlbGVjdG9yXCIsIGZvY3VzZWQ6IGlzRm9jdXNlZCwgb25DbGljazogKCkgPT4ge1xuICAgICAgICAgICAgICAgICAgICBpZiAoaXNGb2N1c2VkKSB7XG4gICAgICAgICAgICAgICAgICAgICAgICBpZiAoaW5wdXRFbC5jdXJyZW50KSB7XG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgaW5wdXRFbC5jdXJyZW50LmJsdXIoKTtcbiAgICAgICAgICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgICAgICAgICAgICAgIHNldEZvY3VzKGZhbHNlKTtcbiAgICAgICAgICAgICAgICAgICAgICAgIHNldExvY2FsVmFsdWUoJycpO1xuICAgICAgICAgICAgICAgICAgICB9XG4gICAgICAgICAgICAgICAgICAgIGVsc2Uge1xuICAgICAgICAgICAgICAgICAgICAgICAgaWYgKGlucHV0RWwuY3VycmVudCkge1xuICAgICAgICAgICAgICAgICAgICAgICAgICAgIGlucHV0RWwuY3VycmVudC5mb2N1cygpO1xuICAgICAgICAgICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgICAgICAgICAgICAgc2V0Rm9jdXModHJ1ZSk7XG4gICAgICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgICAgICB9LCBjaGlsZHJlbjogW19qc3hzKFZhbHVlQ29udGFpbmVyLCB7IGNoaWxkcmVuOiBbbG9jYWxWYWx1ZSA9PT0gJycgJiZcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgKCF2YWx1ZSA/IChfanN4KFBsYWNlaG9sZGVyLCB7IGNoaWxkcmVuOiBwbGFjZWhvbGRlciB9KSkgOiAoX2pzeChTaW5nbGVWYWx1ZSwgeyBjaGlsZHJlbjogdmFsdWUubGFiZWwgfSkpKSwgX2pzeHMoSW5wdXRDb250YWluZXIsIHsgY2hpbGRyZW46IFtfanN4KElucHV0LCB7IHJlZjogaW5wdXRFbCwgb25Gb2N1czogKCkgPT4ge1xuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBzZXRGb2N1cyh0cnVlKTtcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB9LCBvbkNoYW5nZTogZSA9PiB7XG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHNldExvY2FsVmFsdWUoZS50YXJnZXQudmFsdWUpO1xuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBzZXRMb2FkU3RhdGUoTG9hZFN0YXRlLkxvYWRpbmcpO1xuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBsb2FkT3B0aW9ucyAmJlxuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgbG9hZE9wdGlvbnMoZS50YXJnZXQudmFsdWUsIChyZXN1bHQpID0+IHtcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBzZXRPcHRpb25zKHJlc3VsdCk7XG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgc2V0TG9hZFN0YXRlKExvYWRTdGF0ZS5JZGxlKTtcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIH0pO1xuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIH0sIHZhbHVlOiBsb2NhbFZhbHVlLCB3aWR0aDogaW5wdXRTaXplLCBpZDogXCJhc3ljbi1zZWxlY3QtaW5wdXRcIiB9KSwgX2pzeChJbnB1dFNoYWRvdywgeyByZWY6IGlucHV0U2hhZG93RWwsIGNoaWxkcmVuOiBsb2NhbFZhbHVlIH0pXSB9KV0gfSksIF9qc3hzKEluZGljYXRvckNvbnRhaW5lciwgeyBjaGlsZHJlbjogW2xvYWRTdGF0ZSA9PT0gTG9hZFN0YXRlLkxvYWRpbmcgJiYgX2pzeChVSVNwaW5uZXIsIHt9KSwgX2pzeChEcm9wZG93bkluZGljYXRvciwge30pXSB9KV0gfSksIGlzRm9jdXNlZCAmJiAoX2pzeChNZW51Q29udGFpbmVyLCB7IGNoaWxkcmVuOiBfanN4KE1lbnVMaXN0LCB7IGNoaWxkcmVuOiByZW5kZXJJdGVtcyhvcHRpb25zKSB9KSB9KSldIH0pKTtcbn1cbiJdfQ==*/","import { jsx as _jsx } from \"react/jsx-runtime\";\nimport { styled } from '@linaria/react';\nconst Container = styled.div `\n display: flex;\n justify-content: center;\n padding-bottom: 8px;\n`;\nexport default function ElementorButton({ children, ...params }) {\n return (_jsx(Container, { className: \"elementor-button-wrapper\", children: _jsx(\"button\", { className: \"elementor-button elementor-button-default\", type: \"button\", ...params, children: children }) }));\n}\n",".czoccom{display:-webkit-box;display:-webkit-flex;display:-ms-flexbox;display:flex;-webkit-box-pack:center;-webkit-justify-content:center;-ms-flex-pack:center;justify-content:center;padding-bottom:8px;}\n/*# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIi91c3Ivc2hhcmUvaHVic3BvdC9idWlsZC93b3Jrc3BhY2UvTGVhZGluV29yZFByZXNzUGx1Z2luL2xlYWRpbi9zY3JpcHRzL2VsZW1lbnRvci9Db21tb24vRWxlbWVudG9yQnV0dG9uLnRzeCJdLCJuYW1lcyI6WyIuY3pvY2NvbSJdLCJtYXBwaW5ncyI6IkFBRWtCQSIsImZpbGUiOiIvdXNyL3NoYXJlL2h1YnNwb3QvYnVpbGQvd29ya3NwYWNlL0xlYWRpbldvcmRQcmVzc1BsdWdpbi9sZWFkaW4vc2NyaXB0cy9lbGVtZW50b3IvQ29tbW9uL0VsZW1lbnRvckJ1dHRvbi50c3giLCJzb3VyY2VzQ29udGVudCI6WyJpbXBvcnQgeyBqc3ggYXMgX2pzeCB9IGZyb20gXCJyZWFjdC9qc3gtcnVudGltZVwiO1xuaW1wb3J0IHsgc3R5bGVkIH0gZnJvbSAnQGxpbmFyaWEvcmVhY3QnO1xuY29uc3QgQ29udGFpbmVyID0gc3R5bGVkLmRpdiBgXG4gIGRpc3BsYXk6IGZsZXg7XG4gIGp1c3RpZnktY29udGVudDogY2VudGVyO1xuICBwYWRkaW5nLWJvdHRvbTogOHB4O1xuYDtcbmV4cG9ydCBkZWZhdWx0IGZ1bmN0aW9uIEVsZW1lbnRvckJ1dHRvbih7IGNoaWxkcmVuLCAuLi5wYXJhbXMgfSkge1xuICAgIHJldHVybiAoX2pzeChDb250YWluZXIsIHsgY2xhc3NOYW1lOiBcImVsZW1lbnRvci1idXR0b24td3JhcHBlclwiLCBjaGlsZHJlbjogX2pzeChcImJ1dHRvblwiLCB7IGNsYXNzTmFtZTogXCJlbGVtZW50b3ItYnV0dG9uIGVsZW1lbnRvci1idXR0b24tZGVmYXVsdFwiLCB0eXBlOiBcImJ1dHRvblwiLCAuLi5wYXJhbXMsIGNoaWxkcmVuOiBjaGlsZHJlbiB9KSB9KSk7XG59XG4iXX0=*/","import { jsx as _jsx, jsxs as _jsxs } from \"react/jsx-runtime\";\nimport { Fragment } from 'react';\nimport { CURRENT_USER_CALENDAR_MISSING } from '../../shared/Meeting/constants';\nimport ElementorButton from '../Common/ElementorButton';\nimport ElementorBanner from '../Common/ElementorBanner';\nimport { styled } from '@linaria/react';\nimport { __ } from '@wordpress/i18n';\nconst Container = styled.div `\n padding-bottom: 8px;\n`;\nexport default function MeetingWarning({ onConnectCalendar, status, }) {\n const isMeetingOwner = status === CURRENT_USER_CALENDAR_MISSING;\n const titleText = isMeetingOwner\n ? __('Your calendar is not connected', 'leadin')\n : __('Calendar is not connected', 'leadin');\n const titleMessage = isMeetingOwner\n ? __('Please connect your calendar to activate your scheduling pages', 'leadin')\n : __('Make sure that everybody in this meeting has connected their calendar from the Meetings page in HubSpot', 'leadin');\n return (_jsxs(Fragment, { children: [_jsx(Container, { children: _jsxs(ElementorBanner, { type: \"warning\", children: [_jsx(\"b\", { children: titleText }), _jsx(\"br\", {}), titleMessage] }) }), isMeetingOwner && (_jsx(ElementorButton, { id: \"meetings-connect-calendar\", onClick: onConnectCalendar, children: __('Connect calendar', 'leadin') }))] }));\n}\n",".c1p032ba{padding-bottom:8px;}\n/*# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIi91c3Ivc2hhcmUvaHVic3BvdC9idWlsZC93b3Jrc3BhY2UvTGVhZGluV29yZFByZXNzUGx1Z2luL2xlYWRpbi9zY3JpcHRzL2VsZW1lbnRvci9NZWV0aW5nV2lkZ2V0L0VsZW1lbnRvck1lZXRpbmdXYXJuaW5nLnRzeCJdLCJuYW1lcyI6WyIuYzFwMDMyYmEiXSwibWFwcGluZ3MiOiJBQU9rQkEiLCJmaWxlIjoiL3Vzci9zaGFyZS9odWJzcG90L2J1aWxkL3dvcmtzcGFjZS9MZWFkaW5Xb3JkUHJlc3NQbHVnaW4vbGVhZGluL3NjcmlwdHMvZWxlbWVudG9yL01lZXRpbmdXaWRnZXQvRWxlbWVudG9yTWVldGluZ1dhcm5pbmcudHN4Iiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsganN4IGFzIF9qc3gsIGpzeHMgYXMgX2pzeHMgfSBmcm9tIFwicmVhY3QvanN4LXJ1bnRpbWVcIjtcbmltcG9ydCB7IEZyYWdtZW50IH0gZnJvbSAncmVhY3QnO1xuaW1wb3J0IHsgQ1VSUkVOVF9VU0VSX0NBTEVOREFSX01JU1NJTkcgfSBmcm9tICcuLi8uLi9zaGFyZWQvTWVldGluZy9jb25zdGFudHMnO1xuaW1wb3J0IEVsZW1lbnRvckJ1dHRvbiBmcm9tICcuLi9Db21tb24vRWxlbWVudG9yQnV0dG9uJztcbmltcG9ydCBFbGVtZW50b3JCYW5uZXIgZnJvbSAnLi4vQ29tbW9uL0VsZW1lbnRvckJhbm5lcic7XG5pbXBvcnQgeyBzdHlsZWQgfSBmcm9tICdAbGluYXJpYS9yZWFjdCc7XG5pbXBvcnQgeyBfXyB9IGZyb20gJ0B3b3JkcHJlc3MvaTE4bic7XG5jb25zdCBDb250YWluZXIgPSBzdHlsZWQuZGl2IGBcbiAgcGFkZGluZy1ib3R0b206IDhweDtcbmA7XG5leHBvcnQgZGVmYXVsdCBmdW5jdGlvbiBNZWV0aW5nV2FybmluZyh7IG9uQ29ubmVjdENhbGVuZGFyLCBzdGF0dXMsIH0pIHtcbiAgICBjb25zdCBpc01lZXRpbmdPd25lciA9IHN0YXR1cyA9PT0gQ1VSUkVOVF9VU0VSX0NBTEVOREFSX01JU1NJTkc7XG4gICAgY29uc3QgdGl0bGVUZXh0ID0gaXNNZWV0aW5nT3duZXJcbiAgICAgICAgPyBfXygnWW91ciBjYWxlbmRhciBpcyBub3QgY29ubmVjdGVkJywgJ2xlYWRpbicpXG4gICAgICAgIDogX18oJ0NhbGVuZGFyIGlzIG5vdCBjb25uZWN0ZWQnLCAnbGVhZGluJyk7XG4gICAgY29uc3QgdGl0bGVNZXNzYWdlID0gaXNNZWV0aW5nT3duZXJcbiAgICAgICAgPyBfXygnUGxlYXNlIGNvbm5lY3QgeW91ciBjYWxlbmRhciB0byBhY3RpdmF0ZSB5b3VyIHNjaGVkdWxpbmcgcGFnZXMnLCAnbGVhZGluJylcbiAgICAgICAgOiBfXygnTWFrZSBzdXJlIHRoYXQgZXZlcnlib2R5IGluIHRoaXMgbWVldGluZyBoYXMgY29ubmVjdGVkIHRoZWlyIGNhbGVuZGFyIGZyb20gdGhlIE1lZXRpbmdzIHBhZ2UgaW4gSHViU3BvdCcsICdsZWFkaW4nKTtcbiAgICByZXR1cm4gKF9qc3hzKEZyYWdtZW50LCB7IGNoaWxkcmVuOiBbX2pzeChDb250YWluZXIsIHsgY2hpbGRyZW46IF9qc3hzKEVsZW1lbnRvckJhbm5lciwgeyB0eXBlOiBcIndhcm5pbmdcIiwgY2hpbGRyZW46IFtfanN4KFwiYlwiLCB7IGNoaWxkcmVuOiB0aXRsZVRleHQgfSksIF9qc3goXCJiclwiLCB7fSksIHRpdGxlTWVzc2FnZV0gfSkgfSksIGlzTWVldGluZ093bmVyICYmIChfanN4KEVsZW1lbnRvckJ1dHRvbiwgeyBpZDogXCJtZWV0aW5ncy1jb25uZWN0LWNhbGVuZGFyXCIsIG9uQ2xpY2s6IG9uQ29ubmVjdENhbGVuZGFyLCBjaGlsZHJlbjogX18oJ0Nvbm5lY3QgY2FsZW5kYXInLCAnbGVhZGluJykgfSkpXSB9KSk7XG59XG4iXX0=*/","import { jsx as _jsx, jsxs as _jsxs } from \"react/jsx-runtime\";\nimport { styled } from '@linaria/react';\nimport { MARIGOLD_LIGHT, MARIGOLD_MEDIUM, OBSIDIAN } from './colors';\nconst AlertContainer = styled.div `\n background-color: ${MARIGOLD_LIGHT};\n border-color: ${MARIGOLD_MEDIUM};\n color: ${OBSIDIAN};\n font-size: 14px;\n align-items: center;\n justify-content: space-between;\n display: flex;\n border-style: solid;\n border-top-style: solid;\n border-right-style: solid;\n border-bottom-style: solid;\n border-left-style: solid;\n border-width: 1px;\n min-height: 60px;\n padding: 8px 20px;\n position: relative;\n text-align: left;\n`;\nconst Title = styled.p `\n font-family: 'Lexend Deca';\n font-style: normal;\n font-weight: 700;\n font-size: 16px;\n line-height: 19px;\n color: ${OBSIDIAN};\n margin: 0;\n padding: 0;\n`;\nconst Message = styled.p `\n font-family: 'Lexend Deca';\n font-style: normal;\n font-weight: 400;\n font-size: 14px;\n margin: 0;\n padding: 0;\n`;\nconst MessageContainer = styled.div `\n display: flex;\n flex-direction: column;\n`;\nexport default function UIAlert({ titleText, titleMessage, children, }) {\n return (_jsxs(AlertContainer, { children: [_jsxs(MessageContainer, { children: [_jsx(Title, { children: titleText }), _jsx(Message, { children: titleMessage })] }), children] }));\n}\n",".a1h8m4fo{background-color:#fef8f0;border-color:#fae0b5;color:#33475b;font-size:14px;-webkit-align-items:center;-webkit-box-align:center;-ms-flex-align:center;align-items:center;-webkit-box-pack:justify;-webkit-justify-content:space-between;-ms-flex-pack:justify;justify-content:space-between;display:-webkit-box;display:-webkit-flex;display:-ms-flexbox;display:flex;border-style:solid;border-top-style:solid;border-right-style:solid;border-bottom-style:solid;border-left-style:solid;border-width:1px;min-height:60px;padding:8px 20px;position:relative;text-align:left;}\n.tyndzxk{font-family:'Lexend Deca';font-style:normal;font-weight:700;font-size:16px;line-height:19px;color:#33475b;margin:0;padding:0;}\n.m1m9sbk4{font-family:'Lexend Deca';font-style:normal;font-weight:400;font-size:14px;margin:0;padding:0;}\n.mg5o421{display:-webkit-box;display:-webkit-flex;display:-ms-flexbox;display:flex;-webkit-flex-direction:column;-ms-flex-direction:column;flex-direction:column;}\n/*# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIi91c3Ivc2hhcmUvaHVic3BvdC9idWlsZC93b3Jrc3BhY2UvTGVhZGluV29yZFByZXNzUGx1Z2luL2xlYWRpbi9zY3JpcHRzL3NoYXJlZC9VSUNvbXBvbmVudHMvVUlBbGVydC50c3giXSwibmFtZXMiOlsiLmExaDhtNGZvIiwiLnR5bmR6eGsiLCIubTFtOXNiazQiLCIubWc1bzQyMSJdLCJtYXBwaW5ncyI6IkFBR3VCQTtBQW1CVEM7QUFVRUM7QUFRU0MiLCJmaWxlIjoiL3Vzci9zaGFyZS9odWJzcG90L2J1aWxkL3dvcmtzcGFjZS9MZWFkaW5Xb3JkUHJlc3NQbHVnaW4vbGVhZGluL3NjcmlwdHMvc2hhcmVkL1VJQ29tcG9uZW50cy9VSUFsZXJ0LnRzeCIsInNvdXJjZXNDb250ZW50IjpbImltcG9ydCB7IGpzeCBhcyBfanN4LCBqc3hzIGFzIF9qc3hzIH0gZnJvbSBcInJlYWN0L2pzeC1ydW50aW1lXCI7XG5pbXBvcnQgeyBzdHlsZWQgfSBmcm9tICdAbGluYXJpYS9yZWFjdCc7XG5pbXBvcnQgeyBNQVJJR09MRF9MSUdIVCwgTUFSSUdPTERfTUVESVVNLCBPQlNJRElBTiB9IGZyb20gJy4vY29sb3JzJztcbmNvbnN0IEFsZXJ0Q29udGFpbmVyID0gc3R5bGVkLmRpdiBgXG4gIGJhY2tncm91bmQtY29sb3I6ICR7TUFSSUdPTERfTElHSFR9O1xuICBib3JkZXItY29sb3I6ICR7TUFSSUdPTERfTUVESVVNfTtcbiAgY29sb3I6ICR7T0JTSURJQU59O1xuICBmb250LXNpemU6IDE0cHg7XG4gIGFsaWduLWl0ZW1zOiBjZW50ZXI7XG4gIGp1c3RpZnktY29udGVudDogc3BhY2UtYmV0d2VlbjtcbiAgZGlzcGxheTogZmxleDtcbiAgYm9yZGVyLXN0eWxlOiBzb2xpZDtcbiAgYm9yZGVyLXRvcC1zdHlsZTogc29saWQ7XG4gIGJvcmRlci1yaWdodC1zdHlsZTogc29saWQ7XG4gIGJvcmRlci1ib3R0b20tc3R5bGU6IHNvbGlkO1xuICBib3JkZXItbGVmdC1zdHlsZTogc29saWQ7XG4gIGJvcmRlci13aWR0aDogMXB4O1xuICBtaW4taGVpZ2h0OiA2MHB4O1xuICBwYWRkaW5nOiA4cHggMjBweDtcbiAgcG9zaXRpb246IHJlbGF0aXZlO1xuICB0ZXh0LWFsaWduOiBsZWZ0O1xuYDtcbmNvbnN0IFRpdGxlID0gc3R5bGVkLnAgYFxuICBmb250LWZhbWlseTogJ0xleGVuZCBEZWNhJztcbiAgZm9udC1zdHlsZTogbm9ybWFsO1xuICBmb250LXdlaWdodDogNzAwO1xuICBmb250LXNpemU6IDE2cHg7XG4gIGxpbmUtaGVpZ2h0OiAxOXB4O1xuICBjb2xvcjogJHtPQlNJRElBTn07XG4gIG1hcmdpbjogMDtcbiAgcGFkZGluZzogMDtcbmA7XG5jb25zdCBNZXNzYWdlID0gc3R5bGVkLnAgYFxuICBmb250LWZhbWlseTogJ0xleGVuZCBEZWNhJztcbiAgZm9udC1zdHlsZTogbm9ybWFsO1xuICBmb250LXdlaWdodDogNDAwO1xuICBmb250LXNpemU6IDE0cHg7XG4gIG1hcmdpbjogMDtcbiAgcGFkZGluZzogMDtcbmA7XG5jb25zdCBNZXNzYWdlQ29udGFpbmVyID0gc3R5bGVkLmRpdiBgXG4gIGRpc3BsYXk6IGZsZXg7XG4gIGZsZXgtZGlyZWN0aW9uOiBjb2x1bW47XG5gO1xuZXhwb3J0IGRlZmF1bHQgZnVuY3Rpb24gVUlBbGVydCh7IHRpdGxlVGV4dCwgdGl0bGVNZXNzYWdlLCBjaGlsZHJlbiwgfSkge1xuICAgIHJldHVybiAoX2pzeHMoQWxlcnRDb250YWluZXIsIHsgY2hpbGRyZW46IFtfanN4cyhNZXNzYWdlQ29udGFpbmVyLCB7IGNoaWxkcmVuOiBbX2pzeChUaXRsZSwgeyBjaGlsZHJlbjogdGl0bGVUZXh0IH0pLCBfanN4KE1lc3NhZ2UsIHsgY2hpbGRyZW46IHRpdGxlTWVzc2FnZSB9KV0gfSksIGNoaWxkcmVuXSB9KSk7XG59XG4iXX0=*/"],"names":[".sxa9zrc",".s14430wa",".ct87ghk",".avili0h",".ug152ch",".ua13n1c",".h1q5v5ee",".u3qxofx",".u1q7a48k",".c1wxx7eu",".c1rgwbep",".v1mdmbaj",".p1gwkvxy",".s1bwlafs",".i196z9y5",".d1dfo5ow",".if3lze",".i9kxf50",".igjr3uc",".mhb9if7",".mxaof7s",".mw50s5v",".m11rzvjw",".m1jcdsjv",".czoccom",".c1p032ba",".a1h8m4fo",".tyndzxk",".m1m9sbk4",".mg5o421"],"sourceRoot":""}
\ No newline at end of file
diff --git a/wp/wp-content/plugins/leadin/build/elementor.js b/wp/wp-content/plugins/leadin/build/elementor.js
new file mode 100644
index 00000000..085ff5c5
--- /dev/null
+++ b/wp/wp-content/plugins/leadin/build/elementor.js
@@ -0,0 +1,8991 @@
+/******/ (() => { // webpackBootstrap
+/******/ var __webpack_modules__ = ({
+
+/***/ "./node_modules/@emotion/memoize/dist/emotion-memoize.esm.js":
+/*!*******************************************************************!*\
+ !*** ./node_modules/@emotion/memoize/dist/emotion-memoize.esm.js ***!
+ \*******************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (__WEBPACK_DEFAULT_EXPORT__)
+/* harmony export */ });
+function memoize(fn) {
+ var cache = Object.create(null);
+ return function (arg) {
+ if (cache[arg] === undefined) cache[arg] = fn(arg);
+ return cache[arg];
+ };
+}
+
+/* harmony default export */ const __WEBPACK_DEFAULT_EXPORT__ = (memoize);
+
+
+/***/ }),
+
+/***/ "./node_modules/@linaria/react/node_modules/@emotion/is-prop-valid/dist/emotion-is-prop-valid.esm.js":
+/*!***********************************************************************************************************!*\
+ !*** ./node_modules/@linaria/react/node_modules/@emotion/is-prop-valid/dist/emotion-is-prop-valid.esm.js ***!
+ \***********************************************************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (__WEBPACK_DEFAULT_EXPORT__)
+/* harmony export */ });
+/* harmony import */ var _emotion_memoize__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! @emotion/memoize */ "./node_modules/@emotion/memoize/dist/emotion-memoize.esm.js");
+
+
+var reactPropsRegex = /^((children|dangerouslySetInnerHTML|key|ref|autoFocus|defaultValue|defaultChecked|innerHTML|suppressContentEditableWarning|suppressHydrationWarning|valueLink|abbr|accept|acceptCharset|accessKey|action|allow|allowUserMedia|allowPaymentRequest|allowFullScreen|allowTransparency|alt|async|autoComplete|autoPlay|capture|cellPadding|cellSpacing|challenge|charSet|checked|cite|classID|className|cols|colSpan|content|contentEditable|contextMenu|controls|controlsList|coords|crossOrigin|data|dateTime|decoding|default|defer|dir|disabled|disablePictureInPicture|download|draggable|encType|enterKeyHint|form|formAction|formEncType|formMethod|formNoValidate|formTarget|frameBorder|headers|height|hidden|high|href|hrefLang|htmlFor|httpEquiv|id|inputMode|integrity|is|keyParams|keyType|kind|label|lang|list|loading|loop|low|marginHeight|marginWidth|max|maxLength|media|mediaGroup|method|min|minLength|multiple|muted|name|nonce|noValidate|open|optimum|pattern|placeholder|playsInline|poster|preload|profile|radioGroup|readOnly|referrerPolicy|rel|required|reversed|role|rows|rowSpan|sandbox|scope|scoped|scrolling|seamless|selected|shape|size|sizes|slot|span|spellCheck|src|srcDoc|srcLang|srcSet|start|step|style|summary|tabIndex|target|title|translate|type|useMap|value|width|wmode|wrap|about|datatype|inlist|prefix|property|resource|typeof|vocab|autoCapitalize|autoCorrect|autoSave|color|incremental|fallback|inert|itemProp|itemScope|itemType|itemID|itemRef|on|option|results|security|unselectable|accentHeight|accumulate|additive|alignmentBaseline|allowReorder|alphabetic|amplitude|arabicForm|ascent|attributeName|attributeType|autoReverse|azimuth|baseFrequency|baselineShift|baseProfile|bbox|begin|bias|by|calcMode|capHeight|clip|clipPathUnits|clipPath|clipRule|colorInterpolation|colorInterpolationFilters|colorProfile|colorRendering|contentScriptType|contentStyleType|cursor|cx|cy|d|decelerate|descent|diffuseConstant|direction|display|divisor|dominantBaseline|dur|dx|dy|edgeMode|elevation|enableBackground|end|exponent|externalResourcesRequired|fill|fillOpacity|fillRule|filter|filterRes|filterUnits|floodColor|floodOpacity|focusable|fontFamily|fontSize|fontSizeAdjust|fontStretch|fontStyle|fontVariant|fontWeight|format|from|fr|fx|fy|g1|g2|glyphName|glyphOrientationHorizontal|glyphOrientationVertical|glyphRef|gradientTransform|gradientUnits|hanging|horizAdvX|horizOriginX|ideographic|imageRendering|in|in2|intercept|k|k1|k2|k3|k4|kernelMatrix|kernelUnitLength|kerning|keyPoints|keySplines|keyTimes|lengthAdjust|letterSpacing|lightingColor|limitingConeAngle|local|markerEnd|markerMid|markerStart|markerHeight|markerUnits|markerWidth|mask|maskContentUnits|maskUnits|mathematical|mode|numOctaves|offset|opacity|operator|order|orient|orientation|origin|overflow|overlinePosition|overlineThickness|panose1|paintOrder|pathLength|patternContentUnits|patternTransform|patternUnits|pointerEvents|points|pointsAtX|pointsAtY|pointsAtZ|preserveAlpha|preserveAspectRatio|primitiveUnits|r|radius|refX|refY|renderingIntent|repeatCount|repeatDur|requiredExtensions|requiredFeatures|restart|result|rotate|rx|ry|scale|seed|shapeRendering|slope|spacing|specularConstant|specularExponent|speed|spreadMethod|startOffset|stdDeviation|stemh|stemv|stitchTiles|stopColor|stopOpacity|strikethroughPosition|strikethroughThickness|string|stroke|strokeDasharray|strokeDashoffset|strokeLinecap|strokeLinejoin|strokeMiterlimit|strokeOpacity|strokeWidth|surfaceScale|systemLanguage|tableValues|targetX|targetY|textAnchor|textDecoration|textRendering|textLength|to|transform|u1|u2|underlinePosition|underlineThickness|unicode|unicodeBidi|unicodeRange|unitsPerEm|vAlphabetic|vHanging|vIdeographic|vMathematical|values|vectorEffect|version|vertAdvY|vertOriginX|vertOriginY|viewBox|viewTarget|visibility|widths|wordSpacing|writingMode|x|xHeight|x1|x2|xChannelSelector|xlinkActuate|xlinkArcrole|xlinkHref|xlinkRole|xlinkShow|xlinkTitle|xlinkType|xmlBase|xmlns|xmlnsXlink|xmlLang|xmlSpace|y|y1|y2|yChannelSelector|z|zoomAndPan|for|class|autofocus)|(([Dd][Aa][Tt][Aa]|[Aa][Rr][Ii][Aa]|x)-.*))$/; // https://esbench.com/bench/5bfee68a4cd7e6009ef61d23
+
+var isPropValid = /* #__PURE__ */(0,_emotion_memoize__WEBPACK_IMPORTED_MODULE_0__["default"])(function (prop) {
+ return reactPropsRegex.test(prop) || prop.charCodeAt(0) === 111
+ /* o */
+ && prop.charCodeAt(1) === 110
+ /* n */
+ && prop.charCodeAt(2) < 91;
+}
+/* Z+1 */
+);
+
+/* harmony default export */ const __WEBPACK_DEFAULT_EXPORT__ = (isPropValid);
+
+
+/***/ }),
+
+/***/ "./scripts/constants/defaultFormOptions.ts":
+/*!*************************************************!*\
+ !*** ./scripts/constants/defaultFormOptions.ts ***!
+ \*************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "DEFAULT_OPTIONS": () => (/* binding */ DEFAULT_OPTIONS),
+/* harmony export */ "isDefaultForm": () => (/* binding */ isDefaultForm)
+/* harmony export */ });
+/* harmony import */ var _wordpress_i18n__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! @wordpress/i18n */ "@wordpress/i18n");
+/* harmony import */ var _wordpress_i18n__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(_wordpress_i18n__WEBPACK_IMPORTED_MODULE_0__);
+
+var REGISTRATION_FORM = 'REGISTRATION_FORM';
+var CONTACT_US_FORM = 'CONTACT_US_FORM';
+var NEWSLETTER_FORM = 'NEWSLETTER_FORM';
+var SUPPORT_FORM = 'SUPPORT_FORM';
+var EVENT_FORM = 'EVENT_FORM';
+var DEFAULT_OPTIONS = {
+ label: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_0__.__)('Templates', 'leadin'),
+ options: [{
+ label: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_0__.__)('Registration Form', 'leadin'),
+ value: REGISTRATION_FORM
+ }, {
+ label: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_0__.__)('Contact us Form', 'leadin'),
+ value: CONTACT_US_FORM
+ }, {
+ label: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_0__.__)('Newsletter sign-up Form', 'leadin'),
+ value: NEWSLETTER_FORM
+ }, {
+ label: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_0__.__)('Support Form', 'leadin'),
+ value: SUPPORT_FORM
+ }, {
+ label: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_0__.__)('Event Registration Form', 'leadin'),
+ value: EVENT_FORM
+ }]
+};
+function isDefaultForm(value) {
+ return value === REGISTRATION_FORM || value === CONTACT_US_FORM || value === NEWSLETTER_FORM || value === SUPPORT_FORM || value === EVENT_FORM;
+}
+
+/***/ }),
+
+/***/ "./scripts/constants/leadinConfig.ts":
+/*!*******************************************!*\
+ !*** ./scripts/constants/leadinConfig.ts ***!
+ \*******************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "accountName": () => (/* binding */ accountName),
+/* harmony export */ "activationTime": () => (/* binding */ activationTime),
+/* harmony export */ "adminUrl": () => (/* binding */ adminUrl),
+/* harmony export */ "connectionStatus": () => (/* binding */ connectionStatus),
+/* harmony export */ "contentEmbed": () => (/* binding */ contentEmbed),
+/* harmony export */ "deviceId": () => (/* binding */ deviceId),
+/* harmony export */ "didDisconnect": () => (/* binding */ didDisconnect),
+/* harmony export */ "env": () => (/* binding */ env),
+/* harmony export */ "formsScript": () => (/* binding */ formsScript),
+/* harmony export */ "formsScriptPayload": () => (/* binding */ formsScriptPayload),
+/* harmony export */ "hublet": () => (/* binding */ hublet),
+/* harmony export */ "hubspotBaseUrl": () => (/* binding */ hubspotBaseUrl),
+/* harmony export */ "hubspotNonce": () => (/* binding */ hubspotNonce),
+/* harmony export */ "iframeUrl": () => (/* binding */ iframeUrl),
+/* harmony export */ "impactLink": () => (/* binding */ impactLink),
+/* harmony export */ "lastAuthorizeTime": () => (/* binding */ lastAuthorizeTime),
+/* harmony export */ "lastDeauthorizeTime": () => (/* binding */ lastDeauthorizeTime),
+/* harmony export */ "lastDisconnectTime": () => (/* binding */ lastDisconnectTime),
+/* harmony export */ "leadinPluginVersion": () => (/* binding */ leadinPluginVersion),
+/* harmony export */ "leadinQueryParams": () => (/* binding */ leadinQueryParams),
+/* harmony export */ "locale": () => (/* binding */ locale),
+/* harmony export */ "loginUrl": () => (/* binding */ loginUrl),
+/* harmony export */ "meetingsScript": () => (/* binding */ meetingsScript),
+/* harmony export */ "phpVersion": () => (/* binding */ phpVersion),
+/* harmony export */ "pluginPath": () => (/* binding */ pluginPath),
+/* harmony export */ "plugins": () => (/* binding */ plugins),
+/* harmony export */ "portalDomain": () => (/* binding */ portalDomain),
+/* harmony export */ "portalEmail": () => (/* binding */ portalEmail),
+/* harmony export */ "portalId": () => (/* binding */ portalId),
+/* harmony export */ "redirectNonce": () => (/* binding */ redirectNonce),
+/* harmony export */ "refreshToken": () => (/* binding */ refreshToken),
+/* harmony export */ "refreshTokenError": () => (/* binding */ refreshTokenError),
+/* harmony export */ "requiresContentEmbedScope": () => (/* binding */ requiresContentEmbedScope),
+/* harmony export */ "restNonce": () => (/* binding */ restNonce),
+/* harmony export */ "restUrl": () => (/* binding */ restUrl),
+/* harmony export */ "reviewSkippedDate": () => (/* binding */ reviewSkippedDate),
+/* harmony export */ "theme": () => (/* binding */ theme),
+/* harmony export */ "trackConsent": () => (/* binding */ trackConsent),
+/* harmony export */ "wpVersion": () => (/* binding */ wpVersion)
+/* harmony export */ });
+var _window$leadinConfig = window.leadinConfig,
+ accountName = _window$leadinConfig.accountName,
+ adminUrl = _window$leadinConfig.adminUrl,
+ activationTime = _window$leadinConfig.activationTime,
+ connectionStatus = _window$leadinConfig.connectionStatus,
+ deviceId = _window$leadinConfig.deviceId,
+ didDisconnect = _window$leadinConfig.didDisconnect,
+ env = _window$leadinConfig.env,
+ formsScript = _window$leadinConfig.formsScript,
+ meetingsScript = _window$leadinConfig.meetingsScript,
+ formsScriptPayload = _window$leadinConfig.formsScriptPayload,
+ hublet = _window$leadinConfig.hublet,
+ hubspotBaseUrl = _window$leadinConfig.hubspotBaseUrl,
+ hubspotNonce = _window$leadinConfig.hubspotNonce,
+ iframeUrl = _window$leadinConfig.iframeUrl,
+ impactLink = _window$leadinConfig.impactLink,
+ lastAuthorizeTime = _window$leadinConfig.lastAuthorizeTime,
+ lastDeauthorizeTime = _window$leadinConfig.lastDeauthorizeTime,
+ lastDisconnectTime = _window$leadinConfig.lastDisconnectTime,
+ leadinPluginVersion = _window$leadinConfig.leadinPluginVersion,
+ leadinQueryParams = _window$leadinConfig.leadinQueryParams,
+ locale = _window$leadinConfig.locale,
+ loginUrl = _window$leadinConfig.loginUrl,
+ phpVersion = _window$leadinConfig.phpVersion,
+ pluginPath = _window$leadinConfig.pluginPath,
+ plugins = _window$leadinConfig.plugins,
+ portalDomain = _window$leadinConfig.portalDomain,
+ portalEmail = _window$leadinConfig.portalEmail,
+ portalId = _window$leadinConfig.portalId,
+ redirectNonce = _window$leadinConfig.redirectNonce,
+ restNonce = _window$leadinConfig.restNonce,
+ restUrl = _window$leadinConfig.restUrl,
+ refreshToken = _window$leadinConfig.refreshToken,
+ reviewSkippedDate = _window$leadinConfig.reviewSkippedDate,
+ theme = _window$leadinConfig.theme,
+ trackConsent = _window$leadinConfig.trackConsent,
+ wpVersion = _window$leadinConfig.wpVersion,
+ contentEmbed = _window$leadinConfig.contentEmbed,
+ requiresContentEmbedScope = _window$leadinConfig.requiresContentEmbedScope,
+ refreshTokenError = _window$leadinConfig.refreshTokenError;
+
+
+/***/ }),
+
+/***/ "./scripts/elementor/Common/ConnectPluginBanner.tsx":
+/*!**********************************************************!*\
+ !*** ./scripts/elementor/Common/ConnectPluginBanner.tsx ***!
+ \**********************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ ConnectPluginBanner)
+/* harmony export */ });
+/* harmony import */ var react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react/jsx-runtime */ "./node_modules/react/jsx-runtime.js");
+/* harmony import */ var _ElementorBanner__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! ./ElementorBanner */ "./scripts/elementor/Common/ElementorBanner.tsx");
+/* harmony import */ var _wordpress_i18n__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! @wordpress/i18n */ "@wordpress/i18n");
+/* harmony import */ var _wordpress_i18n__WEBPACK_IMPORTED_MODULE_2___default = /*#__PURE__*/__webpack_require__.n(_wordpress_i18n__WEBPACK_IMPORTED_MODULE_2__);
+
+
+
+function ConnectPluginBanner() {
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_ElementorBanner__WEBPACK_IMPORTED_MODULE_1__["default"], {
+ children: (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)("b", {
+ dangerouslySetInnerHTML: {
+ __html: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_2__.__)('The HubSpot plugin is not connected right now To use HubSpot tools on your WordPress site, %1$sconnect the plugin now%2$s').replace('%1$s', '
').replace('%2$s', ' ')
+ }
+ })
+ });
+}
+
+/***/ }),
+
+/***/ "./scripts/elementor/Common/ElementorBanner.tsx":
+/*!******************************************************!*\
+ !*** ./scripts/elementor/Common/ElementorBanner.tsx ***!
+ \******************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ ElementorBanner)
+/* harmony export */ });
+/* harmony import */ var react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react/jsx-runtime */ "./node_modules/react/jsx-runtime.js");
+
+function ElementorBanner(_ref) {
+ var _ref$type = _ref.type,
+ type = _ref$type === void 0 ? 'warning' : _ref$type,
+ children = _ref.children;
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)("div", {
+ className: "elementor-control-content",
+ children: (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)("div", {
+ className: "elementor-control-raw-html elementor-panel-alert elementor-panel-alert-".concat(type),
+ children: children
+ })
+ });
+}
+
+/***/ }),
+
+/***/ "./scripts/elementor/Common/ElementorButton.tsx":
+/*!******************************************************!*\
+ !*** ./scripts/elementor/Common/ElementorButton.tsx ***!
+ \******************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ ElementorButton)
+/* harmony export */ });
+/* harmony import */ var react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react/jsx-runtime */ "./node_modules/react/jsx-runtime.js");
+/* harmony import */ var _linaria_react__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! @linaria/react */ "./node_modules/@linaria/react/dist/index.mjs");
+var _excluded = ["children"];
+
+function ownKeys(object, enumerableOnly) { var keys = Object.keys(object); if (Object.getOwnPropertySymbols) { var symbols = Object.getOwnPropertySymbols(object); enumerableOnly && (symbols = symbols.filter(function (sym) { return Object.getOwnPropertyDescriptor(object, sym).enumerable; })), keys.push.apply(keys, symbols); } return keys; }
+
+function _objectSpread(target) { for (var i = 1; i < arguments.length; i++) { var source = null != arguments[i] ? arguments[i] : {}; i % 2 ? ownKeys(Object(source), !0).forEach(function (key) { _defineProperty(target, key, source[key]); }) : Object.getOwnPropertyDescriptors ? Object.defineProperties(target, Object.getOwnPropertyDescriptors(source)) : ownKeys(Object(source)).forEach(function (key) { Object.defineProperty(target, key, Object.getOwnPropertyDescriptor(source, key)); }); } return target; }
+
+function _defineProperty(obj, key, value) { if (key in obj) { Object.defineProperty(obj, key, { value: value, enumerable: true, configurable: true, writable: true }); } else { obj[key] = value; } return obj; }
+
+function _objectWithoutProperties(source, excluded) { if (source == null) return {}; var target = _objectWithoutPropertiesLoose(source, excluded); var key, i; if (Object.getOwnPropertySymbols) { var sourceSymbolKeys = Object.getOwnPropertySymbols(source); for (i = 0; i < sourceSymbolKeys.length; i++) { key = sourceSymbolKeys[i]; if (excluded.indexOf(key) >= 0) continue; if (!Object.prototype.propertyIsEnumerable.call(source, key)) continue; target[key] = source[key]; } } return target; }
+
+function _objectWithoutPropertiesLoose(source, excluded) { if (source == null) return {}; var target = {}; var sourceKeys = Object.keys(source); var key, i; for (i = 0; i < sourceKeys.length; i++) { key = sourceKeys[i]; if (excluded.indexOf(key) >= 0) continue; target[key] = source[key]; } return target; }
+
+
+
+var Container = /*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_1__.styled)('div')({
+ name: "Container",
+ "class": "czoccom",
+ propsAsIs: false
+});
+function ElementorButton(_ref) {
+ var children = _ref.children,
+ params = _objectWithoutProperties(_ref, _excluded);
+
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(Container, {
+ className: "elementor-button-wrapper",
+ children: (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)("button", _objectSpread(_objectSpread({
+ className: "elementor-button elementor-button-default",
+ type: "button"
+ }, params), {}, {
+ children: children
+ }))
+ });
+}
+
+__webpack_require__(/*! ./ElementorButton.linaria.css!=!../../../node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./ElementorButton.tsx */ "./scripts/elementor/Common/ElementorButton.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/elementor/Common/ElementorButton.tsx");
+
+/***/ }),
+
+/***/ "./scripts/elementor/FormWidget/ElementorFormSelect.tsx":
+/*!**************************************************************!*\
+ !*** ./scripts/elementor/FormWidget/ElementorFormSelect.tsx ***!
+ \**************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ ElementorFormSelectContainer)
+/* harmony export */ });
+/* harmony import */ var react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react/jsx-runtime */ "./node_modules/react/jsx-runtime.js");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! react */ "react");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(react__WEBPACK_IMPORTED_MODULE_1__);
+/* harmony import */ var _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ../../constants/leadinConfig */ "./scripts/constants/leadinConfig.ts");
+/* harmony import */ var _Common_ElementorBanner__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ../Common/ElementorBanner */ "./scripts/elementor/Common/ElementorBanner.tsx");
+/* harmony import */ var _shared_UIComponents_UISpinner__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__(/*! ../../shared/UIComponents/UISpinner */ "./scripts/shared/UIComponents/UISpinner.tsx");
+/* harmony import */ var _wordpress_i18n__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__(/*! @wordpress/i18n */ "@wordpress/i18n");
+/* harmony import */ var _wordpress_i18n__WEBPACK_IMPORTED_MODULE_5___default = /*#__PURE__*/__webpack_require__.n(_wordpress_i18n__WEBPACK_IMPORTED_MODULE_5__);
+/* harmony import */ var _iframe_useBackgroundApp__WEBPACK_IMPORTED_MODULE_6__ = __webpack_require__(/*! ../../iframe/useBackgroundApp */ "./scripts/iframe/useBackgroundApp.ts");
+/* harmony import */ var _hooks_useForms__WEBPACK_IMPORTED_MODULE_7__ = __webpack_require__(/*! ./hooks/useForms */ "./scripts/elementor/FormWidget/hooks/useForms.ts");
+/* harmony import */ var _utils_backgroundAppUtils__WEBPACK_IMPORTED_MODULE_8__ = __webpack_require__(/*! ../../utils/backgroundAppUtils */ "./scripts/utils/backgroundAppUtils.ts");
+function ownKeys(object, enumerableOnly) { var keys = Object.keys(object); if (Object.getOwnPropertySymbols) { var symbols = Object.getOwnPropertySymbols(object); enumerableOnly && (symbols = symbols.filter(function (sym) { return Object.getOwnPropertyDescriptor(object, sym).enumerable; })), keys.push.apply(keys, symbols); } return keys; }
+
+function _objectSpread(target) { for (var i = 1; i < arguments.length; i++) { var source = null != arguments[i] ? arguments[i] : {}; i % 2 ? ownKeys(Object(source), !0).forEach(function (key) { _defineProperty(target, key, source[key]); }) : Object.getOwnPropertyDescriptors ? Object.defineProperties(target, Object.getOwnPropertyDescriptors(source)) : ownKeys(Object(source)).forEach(function (key) { Object.defineProperty(target, key, Object.getOwnPropertyDescriptor(source, key)); }); } return target; }
+
+function _defineProperty(obj, key, value) { if (key in obj) { Object.defineProperty(obj, key, { value: value, enumerable: true, configurable: true, writable: true }); } else { obj[key] = value; } return obj; }
+
+
+
+
+
+
+
+
+
+
+
+function ElementorFormSelect(_ref) {
+ var formId = _ref.formId,
+ setAttributes = _ref.setAttributes;
+
+ var _useForms = (0,_hooks_useForms__WEBPACK_IMPORTED_MODULE_7__["default"])(),
+ hasError = _useForms.hasError,
+ forms = _useForms.forms,
+ loading = _useForms.loading;
+
+ return loading ? (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)("div", {
+ children: (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_shared_UIComponents_UISpinner__WEBPACK_IMPORTED_MODULE_4__["default"], {})
+ }) : hasError ? (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_Common_ElementorBanner__WEBPACK_IMPORTED_MODULE_3__["default"], {
+ type: "danger",
+ children: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_5__.__)('Please refresh your forms or try again in a few minutes', 'leadin')
+ }) : (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsxs)("select", {
+ value: formId,
+ onChange: function onChange(event) {
+ var selectedForm = forms.find(function (form) {
+ return form.value === event.target.value;
+ });
+
+ if (selectedForm) {
+ setAttributes({
+ portalId: _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_2__.portalId,
+ formId: selectedForm.value,
+ formName: selectedForm.label
+ });
+ }
+ },
+ children: [(0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)("option", {
+ value: "",
+ disabled: true,
+ selected: true,
+ children: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_5__.__)('Search for a form', 'leadin')
+ }), forms.map(function (form) {
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)("option", {
+ value: form.value,
+ children: form.label
+ }, form.value);
+ })]
+ });
+}
+
+function ElementorFormSelectWrapper(props) {
+ var isBackgroundAppReady = (0,_iframe_useBackgroundApp__WEBPACK_IMPORTED_MODULE_6__.useBackgroundAppContext)();
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(react__WEBPACK_IMPORTED_MODULE_1__.Fragment, {
+ children: !isBackgroundAppReady ? (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)("div", {
+ children: (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_shared_UIComponents_UISpinner__WEBPACK_IMPORTED_MODULE_4__["default"], {})
+ }) : (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(ElementorFormSelect, _objectSpread({}, props))
+ });
+}
+
+function ElementorFormSelectContainer(props) {
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_iframe_useBackgroundApp__WEBPACK_IMPORTED_MODULE_6__.BackgroudAppContext.Provider, {
+ value: _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_2__.refreshToken && (0,_utils_backgroundAppUtils__WEBPACK_IMPORTED_MODULE_8__.getOrCreateBackgroundApp)(_constants_leadinConfig__WEBPACK_IMPORTED_MODULE_2__.refreshToken),
+ children: (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(ElementorFormSelectWrapper, _objectSpread({}, props))
+ });
+}
+
+/***/ }),
+
+/***/ "./scripts/elementor/FormWidget/FormControlController.tsx":
+/*!****************************************************************!*\
+ !*** ./scripts/elementor/FormWidget/FormControlController.tsx ***!
+ \****************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ FormControlController)
+/* harmony export */ });
+/* harmony import */ var react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react/jsx-runtime */ "./node_modules/react/jsx-runtime.js");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! react */ "react");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(react__WEBPACK_IMPORTED_MODULE_1__);
+/* harmony import */ var _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ../../constants/leadinConfig */ "./scripts/constants/leadinConfig.ts");
+/* harmony import */ var _Common_ConnectPluginBanner__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ../Common/ConnectPluginBanner */ "./scripts/elementor/Common/ConnectPluginBanner.tsx");
+/* harmony import */ var _ElementorFormSelect__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__(/*! ./ElementorFormSelect */ "./scripts/elementor/FormWidget/ElementorFormSelect.tsx");
+
+
+
+
+
+var ConnectionStatus = {
+ Connected: 'Connected',
+ NotConnected: 'NotConnected'
+};
+function FormControlController(attributes, setValue) {
+ return function () {
+ var render = function render() {
+ if (_constants_leadinConfig__WEBPACK_IMPORTED_MODULE_2__.connectionStatus === ConnectionStatus.Connected) {
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_ElementorFormSelect__WEBPACK_IMPORTED_MODULE_4__["default"], {
+ formId: attributes.formId,
+ setAttributes: setValue
+ });
+ } else {
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_Common_ConnectPluginBanner__WEBPACK_IMPORTED_MODULE_3__["default"], {});
+ }
+ };
+
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(react__WEBPACK_IMPORTED_MODULE_1__.Fragment, {
+ children: render()
+ });
+ };
+}
+
+/***/ }),
+
+/***/ "./scripts/elementor/FormWidget/FormWidgetController.tsx":
+/*!***************************************************************!*\
+ !*** ./scripts/elementor/FormWidget/FormWidgetController.tsx ***!
+ \***************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ FormWidgetController)
+/* harmony export */ });
+/* harmony import */ var react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react/jsx-runtime */ "./node_modules/react/jsx-runtime.js");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! react */ "react");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(react__WEBPACK_IMPORTED_MODULE_1__);
+/* harmony import */ var _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ../../constants/leadinConfig */ "./scripts/constants/leadinConfig.ts");
+/* harmony import */ var _shared_Common_ErrorHandler__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ../../shared/Common/ErrorHandler */ "./scripts/shared/Common/ErrorHandler.tsx");
+/* harmony import */ var _shared_Form_FormEdit__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__(/*! ../../shared/Form/FormEdit */ "./scripts/shared/Form/FormEdit.tsx");
+/* harmony import */ var _shared_enums_connectionStatus__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__(/*! ../../shared/enums/connectionStatus */ "./scripts/shared/enums/connectionStatus.ts");
+
+
+
+
+
+
+function FormWidgetController(attributes, setValue) {
+ return function () {
+ var render = function render() {
+ if (_constants_leadinConfig__WEBPACK_IMPORTED_MODULE_2__.connectionStatus === _shared_enums_connectionStatus__WEBPACK_IMPORTED_MODULE_5__["default"].Connected) {
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_shared_Form_FormEdit__WEBPACK_IMPORTED_MODULE_4__["default"], {
+ attributes: attributes,
+ isSelected: true,
+ setAttributes: setValue,
+ preview: false,
+ origin: "elementor"
+ });
+ } else {
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_shared_Common_ErrorHandler__WEBPACK_IMPORTED_MODULE_3__["default"], {
+ status: 401
+ });
+ }
+ };
+
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(react__WEBPACK_IMPORTED_MODULE_1__.Fragment, {
+ children: render()
+ });
+ };
+}
+
+/***/ }),
+
+/***/ "./scripts/elementor/FormWidget/hooks/useForms.ts":
+/*!********************************************************!*\
+ !*** ./scripts/elementor/FormWidget/hooks/useForms.ts ***!
+ \********************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ useForms)
+/* harmony export */ });
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react */ "react");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(react__WEBPACK_IMPORTED_MODULE_0__);
+/* harmony import */ var _shared_enums_loadState__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! ../../../shared/enums/loadState */ "./scripts/shared/enums/loadState.ts");
+/* harmony import */ var _iframe_integratedMessages__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ../../../iframe/integratedMessages */ "./scripts/iframe/integratedMessages/index.ts");
+/* harmony import */ var _iframe_useBackgroundApp__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ../../../iframe/useBackgroundApp */ "./scripts/iframe/useBackgroundApp.ts");
+function _slicedToArray(arr, i) { return _arrayWithHoles(arr) || _iterableToArrayLimit(arr, i) || _unsupportedIterableToArray(arr, i) || _nonIterableRest(); }
+
+function _nonIterableRest() { throw new TypeError("Invalid attempt to destructure non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method."); }
+
+function _unsupportedIterableToArray(o, minLen) { if (!o) return; if (typeof o === "string") return _arrayLikeToArray(o, minLen); var n = Object.prototype.toString.call(o).slice(8, -1); if (n === "Object" && o.constructor) n = o.constructor.name; if (n === "Map" || n === "Set") return Array.from(o); if (n === "Arguments" || /^(?:Ui|I)nt(?:8|16|32)(?:Clamped)?Array$/.test(n)) return _arrayLikeToArray(o, minLen); }
+
+function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len = arr.length; for (var i = 0, arr2 = new Array(len); i < len; i++) { arr2[i] = arr[i]; } return arr2; }
+
+function _iterableToArrayLimit(arr, i) { var _i = arr == null ? null : typeof Symbol !== "undefined" && arr[Symbol.iterator] || arr["@@iterator"]; if (_i == null) return; var _arr = []; var _n = true; var _d = false; var _s, _e; try { for (_i = _i.call(arr); !(_n = (_s = _i.next()).done); _n = true) { _arr.push(_s.value); if (i && _arr.length === i) break; } } catch (err) { _d = true; _e = err; } finally { try { if (!_n && _i["return"] != null) _i["return"](); } finally { if (_d) throw _e; } } return _arr; }
+
+function _arrayWithHoles(arr) { if (Array.isArray(arr)) return arr; }
+
+
+
+
+
+function useForms() {
+ var proxy = (0,_iframe_useBackgroundApp__WEBPACK_IMPORTED_MODULE_3__.usePostAsyncBackgroundMessage)();
+
+ var _useState = (0,react__WEBPACK_IMPORTED_MODULE_0__.useState)(_shared_enums_loadState__WEBPACK_IMPORTED_MODULE_1__["default"].NotLoaded),
+ _useState2 = _slicedToArray(_useState, 2),
+ loadState = _useState2[0],
+ setLoadState = _useState2[1];
+
+ var _useState3 = (0,react__WEBPACK_IMPORTED_MODULE_0__.useState)(null),
+ _useState4 = _slicedToArray(_useState3, 2),
+ hasError = _useState4[0],
+ setError = _useState4[1];
+
+ var _useState5 = (0,react__WEBPACK_IMPORTED_MODULE_0__.useState)([]),
+ _useState6 = _slicedToArray(_useState5, 2),
+ forms = _useState6[0],
+ setForms = _useState6[1];
+
+ (0,react__WEBPACK_IMPORTED_MODULE_0__.useEffect)(function () {
+ if (loadState === _shared_enums_loadState__WEBPACK_IMPORTED_MODULE_1__["default"].NotLoaded) {
+ proxy({
+ key: _iframe_integratedMessages__WEBPACK_IMPORTED_MODULE_2__.ProxyMessages.FetchForms,
+ payload: {
+ search: ''
+ }
+ }).then(function (data) {
+ setForms(data.map(function (form) {
+ return {
+ label: form.name,
+ value: form.guid
+ };
+ }));
+ setLoadState(_shared_enums_loadState__WEBPACK_IMPORTED_MODULE_1__["default"].Loaded);
+ })["catch"](function (error) {
+ setError(error);
+ setLoadState(_shared_enums_loadState__WEBPACK_IMPORTED_MODULE_1__["default"].Failed);
+ });
+ }
+ }, [loadState]);
+ return {
+ forms: forms,
+ loading: loadState === _shared_enums_loadState__WEBPACK_IMPORTED_MODULE_1__["default"].Loading,
+ hasError: hasError
+ };
+}
+
+/***/ }),
+
+/***/ "./scripts/elementor/FormWidget/registerFormWidget.ts":
+/*!************************************************************!*\
+ !*** ./scripts/elementor/FormWidget/registerFormWidget.ts ***!
+ \************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ registerFormWidget)
+/* harmony export */ });
+/* harmony import */ var react_dom__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react-dom */ "react-dom");
+/* harmony import */ var react_dom__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(react_dom__WEBPACK_IMPORTED_MODULE_0__);
+/* harmony import */ var _FormControlController__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! ./FormControlController */ "./scripts/elementor/FormWidget/FormControlController.tsx");
+/* harmony import */ var _FormWidgetController__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ./FormWidgetController */ "./scripts/elementor/FormWidget/FormWidgetController.tsx");
+function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
+
+function _defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } }
+
+function _createClass(Constructor, protoProps, staticProps) { if (protoProps) _defineProperties(Constructor.prototype, protoProps); if (staticProps) _defineProperties(Constructor, staticProps); Object.defineProperty(Constructor, "prototype", { writable: false }); return Constructor; }
+
+function _defineProperty(obj, key, value) { if (key in obj) { Object.defineProperty(obj, key, { value: value, enumerable: true, configurable: true, writable: true }); } else { obj[key] = value; } return obj; }
+
+
+
+
+
+var registerFormWidget = /*#__PURE__*/function () {
+ function registerFormWidget(controlContainer, widgetContainer, setValue) {
+ _classCallCheck(this, registerFormWidget);
+
+ _defineProperty(this, "widgetContainer", void 0);
+
+ _defineProperty(this, "attributes", void 0);
+
+ _defineProperty(this, "controlContainer", void 0);
+
+ _defineProperty(this, "setValue", void 0);
+
+ var attributes = widgetContainer.dataset.attributes ? JSON.parse(widgetContainer.dataset.attributes) : {};
+ this.widgetContainer = widgetContainer;
+ this.controlContainer = controlContainer;
+ this.setValue = setValue;
+ this.attributes = attributes;
+ }
+
+ _createClass(registerFormWidget, [{
+ key: "render",
+ value: function render() {
+ react_dom__WEBPACK_IMPORTED_MODULE_0___default().render((0,_FormWidgetController__WEBPACK_IMPORTED_MODULE_2__["default"])(this.attributes, this.setValue)(), this.widgetContainer);
+ react_dom__WEBPACK_IMPORTED_MODULE_0___default().render((0,_FormControlController__WEBPACK_IMPORTED_MODULE_1__["default"])(this.attributes, this.setValue)(), this.controlContainer);
+ }
+ }, {
+ key: "done",
+ value: function done() {
+ react_dom__WEBPACK_IMPORTED_MODULE_0___default().unmountComponentAtNode(this.widgetContainer);
+ react_dom__WEBPACK_IMPORTED_MODULE_0___default().unmountComponentAtNode(this.controlContainer);
+ }
+ }]);
+
+ return registerFormWidget;
+}();
+
+
+
+/***/ }),
+
+/***/ "./scripts/elementor/MeetingWidget/ElementorMeetingSelect.tsx":
+/*!********************************************************************!*\
+ !*** ./scripts/elementor/MeetingWidget/ElementorMeetingSelect.tsx ***!
+ \********************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ ElementorMeetingsSelectContainer)
+/* harmony export */ });
+/* harmony import */ var react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react/jsx-runtime */ "./node_modules/react/jsx-runtime.js");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! react */ "react");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(react__WEBPACK_IMPORTED_MODULE_1__);
+/* harmony import */ var _Common_ElementorBanner__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ../Common/ElementorBanner */ "./scripts/elementor/Common/ElementorBanner.tsx");
+/* harmony import */ var _shared_UIComponents_UISpinner__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ../../shared/UIComponents/UISpinner */ "./scripts/shared/UIComponents/UISpinner.tsx");
+/* harmony import */ var _ElementorMeetingWarning__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__(/*! ./ElementorMeetingWarning */ "./scripts/elementor/MeetingWidget/ElementorMeetingWarning.tsx");
+/* harmony import */ var _shared_Meeting_hooks_useMeetings__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__(/*! ../../shared/Meeting/hooks/useMeetings */ "./scripts/shared/Meeting/hooks/useMeetings.ts");
+/* harmony import */ var _wordpress_i18n__WEBPACK_IMPORTED_MODULE_6__ = __webpack_require__(/*! @wordpress/i18n */ "@wordpress/i18n");
+/* harmony import */ var _wordpress_i18n__WEBPACK_IMPORTED_MODULE_6___default = /*#__PURE__*/__webpack_require__.n(_wordpress_i18n__WEBPACK_IMPORTED_MODULE_6__);
+/* harmony import */ var raven_js__WEBPACK_IMPORTED_MODULE_7__ = __webpack_require__(/*! raven-js */ "./node_modules/raven-js/src/singleton.js");
+/* harmony import */ var raven_js__WEBPACK_IMPORTED_MODULE_7___default = /*#__PURE__*/__webpack_require__.n(raven_js__WEBPACK_IMPORTED_MODULE_7__);
+/* harmony import */ var _iframe_useBackgroundApp__WEBPACK_IMPORTED_MODULE_8__ = __webpack_require__(/*! ../../iframe/useBackgroundApp */ "./scripts/iframe/useBackgroundApp.ts");
+/* harmony import */ var _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_9__ = __webpack_require__(/*! ../../constants/leadinConfig */ "./scripts/constants/leadinConfig.ts");
+/* harmony import */ var _utils_backgroundAppUtils__WEBPACK_IMPORTED_MODULE_10__ = __webpack_require__(/*! ../../utils/backgroundAppUtils */ "./scripts/utils/backgroundAppUtils.ts");
+function ownKeys(object, enumerableOnly) { var keys = Object.keys(object); if (Object.getOwnPropertySymbols) { var symbols = Object.getOwnPropertySymbols(object); enumerableOnly && (symbols = symbols.filter(function (sym) { return Object.getOwnPropertyDescriptor(object, sym).enumerable; })), keys.push.apply(keys, symbols); } return keys; }
+
+function _objectSpread(target) { for (var i = 1; i < arguments.length; i++) { var source = null != arguments[i] ? arguments[i] : {}; i % 2 ? ownKeys(Object(source), !0).forEach(function (key) { _defineProperty(target, key, source[key]); }) : Object.getOwnPropertyDescriptors ? Object.defineProperties(target, Object.getOwnPropertyDescriptors(source)) : ownKeys(Object(source)).forEach(function (key) { Object.defineProperty(target, key, Object.getOwnPropertyDescriptor(source, key)); }); } return target; }
+
+function _defineProperty(obj, key, value) { if (key in obj) { Object.defineProperty(obj, key, { value: value, enumerable: true, configurable: true, writable: true }); } else { obj[key] = value; } return obj; }
+
+function _slicedToArray(arr, i) { return _arrayWithHoles(arr) || _iterableToArrayLimit(arr, i) || _unsupportedIterableToArray(arr, i) || _nonIterableRest(); }
+
+function _nonIterableRest() { throw new TypeError("Invalid attempt to destructure non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method."); }
+
+function _unsupportedIterableToArray(o, minLen) { if (!o) return; if (typeof o === "string") return _arrayLikeToArray(o, minLen); var n = Object.prototype.toString.call(o).slice(8, -1); if (n === "Object" && o.constructor) n = o.constructor.name; if (n === "Map" || n === "Set") return Array.from(o); if (n === "Arguments" || /^(?:Ui|I)nt(?:8|16|32)(?:Clamped)?Array$/.test(n)) return _arrayLikeToArray(o, minLen); }
+
+function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len = arr.length; for (var i = 0, arr2 = new Array(len); i < len; i++) { arr2[i] = arr[i]; } return arr2; }
+
+function _iterableToArrayLimit(arr, i) { var _i = arr == null ? null : typeof Symbol !== "undefined" && arr[Symbol.iterator] || arr["@@iterator"]; if (_i == null) return; var _arr = []; var _n = true; var _d = false; var _s, _e; try { for (_i = _i.call(arr); !(_n = (_s = _i.next()).done); _n = true) { _arr.push(_s.value); if (i && _arr.length === i) break; } } catch (err) { _d = true; _e = err; } finally { try { if (!_n && _i["return"] != null) _i["return"](); } finally { if (_d) throw _e; } } return _arr; }
+
+function _arrayWithHoles(arr) { if (Array.isArray(arr)) return arr; }
+
+
+
+
+
+
+
+
+
+
+
+
+
+function ElementorMeetingSelect(_ref) {
+ var url = _ref.url,
+ setAttributes = _ref.setAttributes;
+
+ var _useMeetings = (0,_shared_Meeting_hooks_useMeetings__WEBPACK_IMPORTED_MODULE_5__["default"])(),
+ meetings = _useMeetings.mappedMeetings,
+ loading = _useMeetings.loading,
+ error = _useMeetings.error,
+ reload = _useMeetings.reload,
+ connectCalendar = _useMeetings.connectCalendar;
+
+ var selectedMeetingCalendar = (0,_shared_Meeting_hooks_useMeetings__WEBPACK_IMPORTED_MODULE_5__.useSelectedMeetingCalendar)(url);
+
+ var _useState = (0,react__WEBPACK_IMPORTED_MODULE_1__.useState)(url),
+ _useState2 = _slicedToArray(_useState, 2),
+ localUrl = _useState2[0],
+ setLocalUrl = _useState2[1];
+
+ var handleConnectCalendar = function handleConnectCalendar() {
+ return connectCalendar().then(function () {
+ reload();
+ })["catch"](function (error) {
+ raven_js__WEBPACK_IMPORTED_MODULE_7___default().captureMessage('Unable to connect calendar', {
+ extra: {
+ error: error
+ }
+ });
+ });
+ };
+
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(react__WEBPACK_IMPORTED_MODULE_1__.Fragment, {
+ children: loading ? (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)("div", {
+ children: (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_shared_UIComponents_UISpinner__WEBPACK_IMPORTED_MODULE_3__["default"], {})
+ }) : error ? (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_Common_ElementorBanner__WEBPACK_IMPORTED_MODULE_2__["default"], {
+ type: "danger",
+ children: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_6__.__)('Please refresh your meetings or try again in a few minutes', 'leadin')
+ }) : (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsxs)(react__WEBPACK_IMPORTED_MODULE_1__.Fragment, {
+ children: [selectedMeetingCalendar && (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_ElementorMeetingWarning__WEBPACK_IMPORTED_MODULE_4__["default"], {
+ status: selectedMeetingCalendar,
+ onConnectCalendar: connectCalendar
+ }), meetings.length > 1 && (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsxs)("select", {
+ value: localUrl,
+ onChange: function onChange(event) {
+ var newUrl = event.target.value;
+ setLocalUrl(newUrl);
+ setAttributes({
+ url: newUrl
+ });
+ },
+ children: [(0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)("option", {
+ value: "",
+ disabled: true,
+ selected: true,
+ children: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_6__.__)('Select a meeting', 'leadin')
+ }), meetings.map(function (item) {
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)("option", {
+ value: item.value,
+ children: item.label
+ }, item.value);
+ })]
+ })]
+ })
+ });
+}
+
+function ElementorMeetingSelectWrapper(props) {
+ var isBackgroundAppReady = (0,_iframe_useBackgroundApp__WEBPACK_IMPORTED_MODULE_8__.useBackgroundAppContext)();
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(react__WEBPACK_IMPORTED_MODULE_1__.Fragment, {
+ children: !isBackgroundAppReady ? (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)("div", {
+ children: (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_shared_UIComponents_UISpinner__WEBPACK_IMPORTED_MODULE_3__["default"], {})
+ }) : (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(ElementorMeetingSelect, _objectSpread({}, props))
+ });
+}
+
+function ElementorMeetingsSelectContainer(props) {
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_iframe_useBackgroundApp__WEBPACK_IMPORTED_MODULE_8__.BackgroudAppContext.Provider, {
+ value: _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_9__.refreshToken && (0,_utils_backgroundAppUtils__WEBPACK_IMPORTED_MODULE_10__.getOrCreateBackgroundApp)(_constants_leadinConfig__WEBPACK_IMPORTED_MODULE_9__.refreshToken),
+ children: (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(ElementorMeetingSelectWrapper, _objectSpread({}, props))
+ });
+}
+
+/***/ }),
+
+/***/ "./scripts/elementor/MeetingWidget/ElementorMeetingWarning.tsx":
+/*!*********************************************************************!*\
+ !*** ./scripts/elementor/MeetingWidget/ElementorMeetingWarning.tsx ***!
+ \*********************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ MeetingWarning)
+/* harmony export */ });
+/* harmony import */ var react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react/jsx-runtime */ "./node_modules/react/jsx-runtime.js");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! react */ "react");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(react__WEBPACK_IMPORTED_MODULE_1__);
+/* harmony import */ var _shared_Meeting_constants__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ../../shared/Meeting/constants */ "./scripts/shared/Meeting/constants.ts");
+/* harmony import */ var _Common_ElementorButton__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ../Common/ElementorButton */ "./scripts/elementor/Common/ElementorButton.tsx");
+/* harmony import */ var _Common_ElementorBanner__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__(/*! ../Common/ElementorBanner */ "./scripts/elementor/Common/ElementorBanner.tsx");
+/* harmony import */ var _linaria_react__WEBPACK_IMPORTED_MODULE_6__ = __webpack_require__(/*! @linaria/react */ "./node_modules/@linaria/react/dist/index.mjs");
+/* harmony import */ var _wordpress_i18n__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__(/*! @wordpress/i18n */ "@wordpress/i18n");
+/* harmony import */ var _wordpress_i18n__WEBPACK_IMPORTED_MODULE_5___default = /*#__PURE__*/__webpack_require__.n(_wordpress_i18n__WEBPACK_IMPORTED_MODULE_5__);
+
+
+
+
+
+
+
+var Container = /*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_6__.styled)('div')({
+ name: "Container",
+ "class": "c1p032ba",
+ propsAsIs: false
+});
+function MeetingWarning(_ref) {
+ var onConnectCalendar = _ref.onConnectCalendar,
+ status = _ref.status;
+ var isMeetingOwner = status === _shared_Meeting_constants__WEBPACK_IMPORTED_MODULE_2__.CURRENT_USER_CALENDAR_MISSING;
+ var titleText = isMeetingOwner ? (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_5__.__)('Your calendar is not connected', 'leadin') : (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_5__.__)('Calendar is not connected', 'leadin');
+ var titleMessage = isMeetingOwner ? (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_5__.__)('Please connect your calendar to activate your scheduling pages', 'leadin') : (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_5__.__)('Make sure that everybody in this meeting has connected their calendar from the Meetings page in HubSpot', 'leadin');
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsxs)(react__WEBPACK_IMPORTED_MODULE_1__.Fragment, {
+ children: [(0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(Container, {
+ children: (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsxs)(_Common_ElementorBanner__WEBPACK_IMPORTED_MODULE_4__["default"], {
+ type: "warning",
+ children: [(0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)("b", {
+ children: titleText
+ }), (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)("br", {}), titleMessage]
+ })
+ }), isMeetingOwner && (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_Common_ElementorButton__WEBPACK_IMPORTED_MODULE_3__["default"], {
+ id: "meetings-connect-calendar",
+ onClick: onConnectCalendar,
+ children: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_5__.__)('Connect calendar', 'leadin')
+ })]
+ });
+}
+
+__webpack_require__(/*! ./ElementorMeetingWarning.linaria.css!=!../../../node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./ElementorMeetingWarning.tsx */ "./scripts/elementor/MeetingWidget/ElementorMeetingWarning.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/elementor/MeetingWidget/ElementorMeetingWarning.tsx");
+
+/***/ }),
+
+/***/ "./scripts/elementor/MeetingWidget/MeetingControlController.tsx":
+/*!**********************************************************************!*\
+ !*** ./scripts/elementor/MeetingWidget/MeetingControlController.tsx ***!
+ \**********************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ MeetingControlController)
+/* harmony export */ });
+/* harmony import */ var react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react/jsx-runtime */ "./node_modules/react/jsx-runtime.js");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! react */ "react");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(react__WEBPACK_IMPORTED_MODULE_1__);
+/* harmony import */ var _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ../../constants/leadinConfig */ "./scripts/constants/leadinConfig.ts");
+/* harmony import */ var _Common_ConnectPluginBanner__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ../Common/ConnectPluginBanner */ "./scripts/elementor/Common/ConnectPluginBanner.tsx");
+/* harmony import */ var _ElementorMeetingSelect__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__(/*! ./ElementorMeetingSelect */ "./scripts/elementor/MeetingWidget/ElementorMeetingSelect.tsx");
+
+
+
+
+
+var ConnectionStatus = {
+ Connected: 'Connected',
+ NotConnected: 'NotConnected'
+};
+function MeetingControlController(attributes, setValue) {
+ return function () {
+ var render = function render() {
+ if (_constants_leadinConfig__WEBPACK_IMPORTED_MODULE_2__.connectionStatus === ConnectionStatus.Connected) {
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_ElementorMeetingSelect__WEBPACK_IMPORTED_MODULE_4__["default"], {
+ url: attributes.url,
+ setAttributes: setValue
+ });
+ } else {
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_Common_ConnectPluginBanner__WEBPACK_IMPORTED_MODULE_3__["default"], {});
+ }
+ };
+
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(react__WEBPACK_IMPORTED_MODULE_1__.Fragment, {
+ children: render()
+ });
+ };
+}
+
+/***/ }),
+
+/***/ "./scripts/elementor/MeetingWidget/MeetingWidgetController.tsx":
+/*!*********************************************************************!*\
+ !*** ./scripts/elementor/MeetingWidget/MeetingWidgetController.tsx ***!
+ \*********************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ MeetingWidgetController)
+/* harmony export */ });
+/* harmony import */ var react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react/jsx-runtime */ "./node_modules/react/jsx-runtime.js");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! react */ "react");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(react__WEBPACK_IMPORTED_MODULE_1__);
+/* harmony import */ var _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ../../constants/leadinConfig */ "./scripts/constants/leadinConfig.ts");
+/* harmony import */ var _shared_Common_ErrorHandler__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ../../shared/Common/ErrorHandler */ "./scripts/shared/Common/ErrorHandler.tsx");
+/* harmony import */ var _shared_Meeting_MeetingEdit__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__(/*! ../../shared/Meeting/MeetingEdit */ "./scripts/shared/Meeting/MeetingEdit.tsx");
+
+
+
+
+
+var ConnectionStatus = {
+ Connected: 'Connected',
+ NotConnected: 'NotConnected'
+};
+function MeetingWidgetController(attributes, setValue) {
+ return function () {
+ var render = function render() {
+ if (_constants_leadinConfig__WEBPACK_IMPORTED_MODULE_2__.connectionStatus === ConnectionStatus.Connected) {
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_shared_Meeting_MeetingEdit__WEBPACK_IMPORTED_MODULE_4__["default"], {
+ attributes: attributes,
+ isSelected: true,
+ setAttributes: setValue,
+ preview: false,
+ origin: "elementor"
+ });
+ } else {
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_shared_Common_ErrorHandler__WEBPACK_IMPORTED_MODULE_3__["default"], {
+ status: 401
+ });
+ }
+ };
+
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(react__WEBPACK_IMPORTED_MODULE_1__.Fragment, {
+ children: render()
+ });
+ };
+}
+
+/***/ }),
+
+/***/ "./scripts/elementor/MeetingWidget/registerMeetingWidget.ts":
+/*!******************************************************************!*\
+ !*** ./scripts/elementor/MeetingWidget/registerMeetingWidget.ts ***!
+ \******************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ registerMeetingsWidget)
+/* harmony export */ });
+/* harmony import */ var react_dom__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react-dom */ "react-dom");
+/* harmony import */ var react_dom__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(react_dom__WEBPACK_IMPORTED_MODULE_0__);
+/* harmony import */ var _MeetingControlController__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! ./MeetingControlController */ "./scripts/elementor/MeetingWidget/MeetingControlController.tsx");
+/* harmony import */ var _MeetingWidgetController__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ./MeetingWidgetController */ "./scripts/elementor/MeetingWidget/MeetingWidgetController.tsx");
+function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
+
+function _defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } }
+
+function _createClass(Constructor, protoProps, staticProps) { if (protoProps) _defineProperties(Constructor.prototype, protoProps); if (staticProps) _defineProperties(Constructor, staticProps); Object.defineProperty(Constructor, "prototype", { writable: false }); return Constructor; }
+
+function _defineProperty(obj, key, value) { if (key in obj) { Object.defineProperty(obj, key, { value: value, enumerable: true, configurable: true, writable: true }); } else { obj[key] = value; } return obj; }
+
+
+
+
+
+var registerMeetingsWidget = /*#__PURE__*/function () {
+ function registerMeetingsWidget(controlContainer, widgetContainer, setValue) {
+ _classCallCheck(this, registerMeetingsWidget);
+
+ _defineProperty(this, "widgetContainer", void 0);
+
+ _defineProperty(this, "controlContainer", void 0);
+
+ _defineProperty(this, "setValue", void 0);
+
+ _defineProperty(this, "attributes", void 0);
+
+ var attributes = widgetContainer.dataset.attributes ? JSON.parse(widgetContainer.dataset.attributes) : {};
+ this.widgetContainer = widgetContainer;
+ this.controlContainer = controlContainer;
+ this.setValue = setValue;
+ this.attributes = attributes;
+ }
+
+ _createClass(registerMeetingsWidget, [{
+ key: "render",
+ value: function render() {
+ react_dom__WEBPACK_IMPORTED_MODULE_0___default().render((0,_MeetingWidgetController__WEBPACK_IMPORTED_MODULE_2__["default"])(this.attributes, this.setValue)(), this.widgetContainer);
+ react_dom__WEBPACK_IMPORTED_MODULE_0___default().render((0,_MeetingControlController__WEBPACK_IMPORTED_MODULE_1__["default"])(this.attributes, this.setValue)(), this.controlContainer);
+ }
+ }, {
+ key: "done",
+ value: function done() {
+ react_dom__WEBPACK_IMPORTED_MODULE_0___default().unmountComponentAtNode(this.widgetContainer);
+ react_dom__WEBPACK_IMPORTED_MODULE_0___default().unmountComponentAtNode(this.controlContainer);
+ }
+ }]);
+
+ return registerMeetingsWidget;
+}();
+
+
+
+/***/ }),
+
+/***/ "./scripts/elementor/elementorWidget.ts":
+/*!**********************************************!*\
+ !*** ./scripts/elementor/elementorWidget.ts ***!
+ \**********************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ elementorWidget)
+/* harmony export */ });
+function elementorWidget(elementor, options, callback) {
+ var done = arguments.length > 3 && arguments[3] !== undefined ? arguments[3] : function () {};
+ return elementor.modules.controls.BaseData.extend({
+ onReady: function onReady() {
+ var self = this;
+ var controlContainer = this.ui.contentEditable.prevObject[0].querySelector(options.controlSelector);
+ var widgetContainer = this.options.element.$el[0].querySelector(options.containerSelector);
+
+ if (widgetContainer) {
+ callback(controlContainer, widgetContainer, function (args) {
+ return self.setValue(args);
+ });
+ } else {
+ //@ts-expect-error global
+ window.elementorFrontend.hooks.addAction("frontend/element_ready/".concat(options.widgetName, ".default"), function (element) {
+ widgetContainer = element[0].querySelector(options.containerSelector);
+ callback(controlContainer, widgetContainer, function (args) {
+ return self.setValue(args);
+ });
+ });
+ }
+ },
+ saveValue: function saveValue(props) {
+ this.setValue(props);
+ },
+ onBeforeDestroy: function onBeforeDestroy() {
+ //@ts-expect-error global
+ window.elementorFrontend.hooks.removeAction("frontend/element_ready/".concat(options.widgetName, ".default"));
+ done();
+ }
+ });
+}
+
+/***/ }),
+
+/***/ "./scripts/iframe/integratedMessages/core/CoreMessages.ts":
+/*!****************************************************************!*\
+ !*** ./scripts/iframe/integratedMessages/core/CoreMessages.ts ***!
+ \****************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "CoreMessages": () => (/* binding */ CoreMessages)
+/* harmony export */ });
+var CoreMessages = {
+ HandshakeReceive: 'INTEGRATED_APP_EMBEDDER_HANDSHAKE_RECEIVED',
+ SendRefreshToken: 'INTEGRATED_APP_EMBEDDER_SEND_REFRESH_TOKEN',
+ ReloadParentFrame: 'INTEGRATED_APP_EMBEDDER_RELOAD_PARENT_FRAME',
+ RedirectParentFrame: 'INTEGRATED_APP_EMBEDDER_REDIRECT_PARENT_FRAME',
+ SendLocale: 'INTEGRATED_APP_EMBEDDER_SEND_LOCALE',
+ SendDeviceId: 'INTEGRATED_APP_EMBEDDER_SEND_DEVICE_ID'
+};
+
+/***/ }),
+
+/***/ "./scripts/iframe/integratedMessages/forms/FormsMessages.ts":
+/*!******************************************************************!*\
+ !*** ./scripts/iframe/integratedMessages/forms/FormsMessages.ts ***!
+ \******************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "FormMessages": () => (/* binding */ FormMessages)
+/* harmony export */ });
+var FormMessages = {
+ CreateFormAppNavigation: 'CREATE_FORM_APP_NAVIGATION'
+};
+
+/***/ }),
+
+/***/ "./scripts/iframe/integratedMessages/index.ts":
+/*!****************************************************!*\
+ !*** ./scripts/iframe/integratedMessages/index.ts ***!
+ \****************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "CoreMessages": () => (/* reexport safe */ _core_CoreMessages__WEBPACK_IMPORTED_MODULE_0__.CoreMessages),
+/* harmony export */ "FormMessages": () => (/* reexport safe */ _forms_FormsMessages__WEBPACK_IMPORTED_MODULE_1__.FormMessages),
+/* harmony export */ "LiveChatMessages": () => (/* reexport safe */ _livechat_LiveChatMessages__WEBPACK_IMPORTED_MODULE_2__.LiveChatMessages),
+/* harmony export */ "PluginMessages": () => (/* reexport safe */ _plugin_PluginMessages__WEBPACK_IMPORTED_MODULE_3__.PluginMessages),
+/* harmony export */ "ProxyMessages": () => (/* reexport safe */ _proxy_ProxyMessages__WEBPACK_IMPORTED_MODULE_4__.ProxyMessages)
+/* harmony export */ });
+/* harmony import */ var _core_CoreMessages__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! ./core/CoreMessages */ "./scripts/iframe/integratedMessages/core/CoreMessages.ts");
+/* harmony import */ var _forms_FormsMessages__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! ./forms/FormsMessages */ "./scripts/iframe/integratedMessages/forms/FormsMessages.ts");
+/* harmony import */ var _livechat_LiveChatMessages__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ./livechat/LiveChatMessages */ "./scripts/iframe/integratedMessages/livechat/LiveChatMessages.ts");
+/* harmony import */ var _plugin_PluginMessages__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ./plugin/PluginMessages */ "./scripts/iframe/integratedMessages/plugin/PluginMessages.ts");
+/* harmony import */ var _proxy_ProxyMessages__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__(/*! ./proxy/ProxyMessages */ "./scripts/iframe/integratedMessages/proxy/ProxyMessages.ts");
+
+
+
+
+
+
+/***/ }),
+
+/***/ "./scripts/iframe/integratedMessages/livechat/LiveChatMessages.ts":
+/*!************************************************************************!*\
+ !*** ./scripts/iframe/integratedMessages/livechat/LiveChatMessages.ts ***!
+ \************************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "LiveChatMessages": () => (/* binding */ LiveChatMessages)
+/* harmony export */ });
+var LiveChatMessages = {
+ CreateLiveChatAppNavigation: 'CREATE_LIVE_CHAT_APP_NAVIGATION'
+};
+
+/***/ }),
+
+/***/ "./scripts/iframe/integratedMessages/plugin/PluginMessages.ts":
+/*!********************************************************************!*\
+ !*** ./scripts/iframe/integratedMessages/plugin/PluginMessages.ts ***!
+ \********************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "PluginMessages": () => (/* binding */ PluginMessages)
+/* harmony export */ });
+var PluginMessages = {
+ PluginSettingsNavigation: 'PLUGIN_SETTINGS_NAVIGATION',
+ PluginLeadinConfig: 'PLUGIN_LEADIN_CONFIG',
+ TrackConsent: 'INTEGRATED_APP_EMBEDDER_TRACK_CONSENT',
+ InternalTrackingFetchRequest: 'INTEGRATED_TRACKING_FETCH_REQUEST',
+ InternalTrackingFetchResponse: 'INTEGRATED_TRACKING_FETCH_RESPONSE',
+ InternalTrackingFetchError: 'INTEGRATED_TRACKING_FETCH_ERROR',
+ InternalTrackingChangeRequest: 'INTEGRATED_TRACKING_CHANGE_REQUEST',
+ InternalTrackingChangeError: 'INTEGRATED_TRACKING_CHANGE_ERROR',
+ BusinessUnitFetchRequest: 'BUSINESS_UNIT_FETCH_REQUEST',
+ BusinessUnitFetchResponse: 'BUSINESS_UNIT_FETCH_FETCH_RESPONSE',
+ BusinessUnitFetchError: 'BUSINESS_UNIT_FETCH_FETCH_ERROR',
+ BusinessUnitChangeRequest: 'BUSINESS_UNIT_CHANGE_REQUEST',
+ BusinessUnitChangeError: 'BUSINESS_UNIT_CHANGE_ERROR',
+ SkipReviewRequest: 'SKIP_REVIEW_REQUEST',
+ SkipReviewResponse: 'SKIP_REVIEW_RESPONSE',
+ SkipReviewError: 'SKIP_REVIEW_ERROR',
+ RemoveParentQueryParam: 'REMOVE_PARENT_QUERY_PARAM',
+ ContentEmbedInstallRequest: 'CONTENT_EMBED_INSTALL_REQUEST',
+ ContentEmbedInstallResponse: 'CONTENT_EMBED_INSTALL_RESPONSE',
+ ContentEmbedInstallError: 'CONTENT_EMBED_INSTALL_ERROR',
+ ContentEmbedActivationRequest: 'CONTENT_EMBED_ACTIVATION_REQUEST',
+ ContentEmbedActivationResponse: 'CONTENT_EMBED_ACTIVATION_RESPONSE',
+ ContentEmbedActivationError: 'CONTENT_EMBED_ACTIVATION_ERROR'
+};
+
+/***/ }),
+
+/***/ "./scripts/iframe/integratedMessages/proxy/ProxyMessages.ts":
+/*!******************************************************************!*\
+ !*** ./scripts/iframe/integratedMessages/proxy/ProxyMessages.ts ***!
+ \******************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "ProxyMessages": () => (/* binding */ ProxyMessages)
+/* harmony export */ });
+var ProxyMessages = {
+ FetchForms: 'FETCH_FORMS',
+ FetchForm: 'FETCH_FORM',
+ CreateFormFromTemplate: 'CREATE_FORM_FROM_TEMPLATE',
+ FetchAuth: 'FETCH_AUTH',
+ FetchMeetingsAndUsers: 'FETCH_MEETINGS_AND_USERS',
+ FetchContactsCreateSinceActivation: 'FETCH_CONTACTS_CREATED_SINCE_ACTIVATION',
+ FetchOrCreateMeetingUser: 'FETCH_OR_CREATE_MEETING_USER',
+ ConnectMeetingsCalendar: 'CONNECT_MEETINGS_CALENDAR',
+ TrackFormPreviewRender: 'TRACK_FORM_PREVIEW_RENDER',
+ TrackFormCreatedFromTemplate: 'TRACK_FORM_CREATED_FROM_TEMPLATE',
+ TrackFormCreationFailed: 'TRACK_FORM_CREATION_FAILED',
+ TrackMeetingPreviewRender: 'TRACK_MEETING_PREVIEW_RENDER',
+ TrackSidebarMetaChange: 'TRACK_SIDEBAR_META_CHANGE',
+ TrackReviewBannerRender: 'TRACK_REVIEW_BANNER_RENDER',
+ TrackReviewBannerInteraction: 'TRACK_REVIEW_BANNER_INTERACTION',
+ TrackReviewBannerDismissed: 'TRACK_REVIEW_BANNER_DISMISSED',
+ TrackPluginDeactivation: 'TRACK_PLUGIN_DEACTIVATION'
+};
+
+/***/ }),
+
+/***/ "./scripts/iframe/useBackgroundApp.ts":
+/*!********************************************!*\
+ !*** ./scripts/iframe/useBackgroundApp.ts ***!
+ \********************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "BackgroudAppContext": () => (/* binding */ BackgroudAppContext),
+/* harmony export */ "useBackgroundAppContext": () => (/* binding */ useBackgroundAppContext),
+/* harmony export */ "usePostAsyncBackgroundMessage": () => (/* binding */ usePostAsyncBackgroundMessage),
+/* harmony export */ "usePostBackgroundMessage": () => (/* binding */ usePostBackgroundMessage)
+/* harmony export */ });
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react */ "react");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(react__WEBPACK_IMPORTED_MODULE_0__);
+
+var BackgroudAppContext = /*#__PURE__*/(0,react__WEBPACK_IMPORTED_MODULE_0__.createContext)(null);
+function useBackgroundAppContext() {
+ return (0,react__WEBPACK_IMPORTED_MODULE_0__.useContext)(BackgroudAppContext);
+}
+function usePostBackgroundMessage() {
+ var app = useBackgroundAppContext();
+ return function (message) {
+ app.postMessage(message);
+ };
+}
+function usePostAsyncBackgroundMessage() {
+ var app = useBackgroundAppContext();
+ return function (message) {
+ return app.postAsyncMessage(message);
+ };
+}
+
+/***/ }),
+
+/***/ "./scripts/lib/Raven.ts":
+/*!******************************!*\
+ !*** ./scripts/lib/Raven.ts ***!
+ \******************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "configureRaven": () => (/* binding */ configureRaven),
+/* harmony export */ "default": () => (__WEBPACK_DEFAULT_EXPORT__)
+/* harmony export */ });
+/* harmony import */ var raven_js__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! raven-js */ "./node_modules/raven-js/src/singleton.js");
+/* harmony import */ var raven_js__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(raven_js__WEBPACK_IMPORTED_MODULE_0__);
+/* harmony import */ var _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! ../constants/leadinConfig */ "./scripts/constants/leadinConfig.ts");
+
+
+function configureRaven() {
+ if (_constants_leadinConfig__WEBPACK_IMPORTED_MODULE_1__.hubspotBaseUrl.indexOf('app.hubspot.com') === -1) {
+ return;
+ }
+
+ raven_js__WEBPACK_IMPORTED_MODULE_0___default().config('https://e9b8f382cdd130c0d415cd977d2be56f@exceptions.hubspot.com/1', {
+ instrument: {
+ tryCatch: false
+ },
+ release: _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_1__.leadinPluginVersion
+ }).install();
+ raven_js__WEBPACK_IMPORTED_MODULE_0___default().setTagsContext({
+ v: _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_1__.leadinPluginVersion,
+ php: _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_1__.phpVersion,
+ wordpress: _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_1__.wpVersion
+ });
+ raven_js__WEBPACK_IMPORTED_MODULE_0___default().setExtraContext({
+ hub: _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_1__.portalId,
+ plugins: Object.keys(_constants_leadinConfig__WEBPACK_IMPORTED_MODULE_1__.plugins).map(function (name) {
+ return "".concat(name, "#").concat(_constants_leadinConfig__WEBPACK_IMPORTED_MODULE_1__.plugins[name]);
+ }).join(',')
+ });
+}
+/* harmony default export */ const __WEBPACK_DEFAULT_EXPORT__ = ((raven_js__WEBPACK_IMPORTED_MODULE_0___default()));
+
+/***/ }),
+
+/***/ "./scripts/shared/Common/AsyncSelect.tsx":
+/*!***********************************************!*\
+ !*** ./scripts/shared/Common/AsyncSelect.tsx ***!
+ \***********************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ AsyncSelect)
+/* harmony export */ });
+/* harmony import */ var react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react/jsx-runtime */ "./node_modules/react/jsx-runtime.js");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! react */ "react");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(react__WEBPACK_IMPORTED_MODULE_1__);
+/* harmony import */ var _linaria_react__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__(/*! @linaria/react */ "./node_modules/@linaria/react/dist/index.mjs");
+/* harmony import */ var _UIComponents_colors__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ../UIComponents/colors */ "./scripts/shared/UIComponents/colors.ts");
+/* harmony import */ var _UIComponents_UISpinner__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ../UIComponents/UISpinner */ "./scripts/shared/UIComponents/UISpinner.tsx");
+/* harmony import */ var _enums_loadState__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__(/*! ../enums/loadState */ "./scripts/shared/enums/loadState.ts");
+function _slicedToArray(arr, i) { return _arrayWithHoles(arr) || _iterableToArrayLimit(arr, i) || _unsupportedIterableToArray(arr, i) || _nonIterableRest(); }
+
+function _nonIterableRest() { throw new TypeError("Invalid attempt to destructure non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method."); }
+
+function _unsupportedIterableToArray(o, minLen) { if (!o) return; if (typeof o === "string") return _arrayLikeToArray(o, minLen); var n = Object.prototype.toString.call(o).slice(8, -1); if (n === "Object" && o.constructor) n = o.constructor.name; if (n === "Map" || n === "Set") return Array.from(o); if (n === "Arguments" || /^(?:Ui|I)nt(?:8|16|32)(?:Clamped)?Array$/.test(n)) return _arrayLikeToArray(o, minLen); }
+
+function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len = arr.length; for (var i = 0, arr2 = new Array(len); i < len; i++) { arr2[i] = arr[i]; } return arr2; }
+
+function _iterableToArrayLimit(arr, i) { var _i = arr == null ? null : typeof Symbol !== "undefined" && arr[Symbol.iterator] || arr["@@iterator"]; if (_i == null) return; var _arr = []; var _n = true; var _d = false; var _s, _e; try { for (_i = _i.call(arr); !(_n = (_s = _i.next()).done); _n = true) { _arr.push(_s.value); if (i && _arr.length === i) break; } } catch (err) { _d = true; _e = err; } finally { try { if (!_n && _i["return"] != null) _i["return"](); } finally { if (_d) throw _e; } } return _arr; }
+
+function _arrayWithHoles(arr) { if (Array.isArray(arr)) return arr; }
+
+
+
+
+
+
+
+var Container = /*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_5__.styled)('div')({
+ name: "Container",
+ "class": "c1wxx7eu",
+ propsAsIs: false
+});
+
+var _exp2 = /*#__PURE__*/function _exp2() {
+ return function (props) {
+ return props.focused ? '0' : '1px';
+ };
+};
+
+var _exp3 = /*#__PURE__*/function _exp3() {
+ return function (props) {
+ return props.focused ? "0 0 0 2px ".concat(_UIComponents_colors__WEBPACK_IMPORTED_MODULE_2__.CALYPSO_MEDIUM) : 'none';
+ };
+};
+
+var ControlContainer = /*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_5__.styled)('div')({
+ name: "ControlContainer",
+ "class": "c1rgwbep",
+ propsAsIs: false,
+ vars: {
+ "c1rgwbep-0": [_exp2()],
+ "c1rgwbep-1": [_exp3()]
+ }
+});
+var ValueContainer = /*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_5__.styled)('div')({
+ name: "ValueContainer",
+ "class": "v1mdmbaj",
+ propsAsIs: false
+});
+var Placeholder = /*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_5__.styled)('div')({
+ name: "Placeholder",
+ "class": "p1gwkvxy",
+ propsAsIs: false
+});
+var SingleValue = /*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_5__.styled)('div')({
+ name: "SingleValue",
+ "class": "s1bwlafs",
+ propsAsIs: false
+});
+var IndicatorContainer = /*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_5__.styled)('div')({
+ name: "IndicatorContainer",
+ "class": "i196z9y5",
+ propsAsIs: false
+});
+var DropdownIndicator = /*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_5__.styled)('div')({
+ name: "DropdownIndicator",
+ "class": "d1dfo5ow",
+ propsAsIs: false
+});
+var InputContainer = /*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_5__.styled)('div')({
+ name: "InputContainer",
+ "class": "if3lze",
+ propsAsIs: false
+});
+var Input = /*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_5__.styled)('input')({
+ name: "Input",
+ "class": "i9kxf50",
+ propsAsIs: false
+});
+var InputShadow = /*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_5__.styled)('div')({
+ name: "InputShadow",
+ "class": "igjr3uc",
+ propsAsIs: false
+});
+var MenuContainer = /*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_5__.styled)('div')({
+ name: "MenuContainer",
+ "class": "mhb9if7",
+ propsAsIs: false
+});
+var MenuList = /*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_5__.styled)('div')({
+ name: "MenuList",
+ "class": "mxaof7s",
+ propsAsIs: false
+});
+var MenuGroup = /*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_5__.styled)('div')({
+ name: "MenuGroup",
+ "class": "mw50s5v",
+ propsAsIs: false
+});
+var MenuGroupHeader = /*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_5__.styled)('div')({
+ name: "MenuGroupHeader",
+ "class": "m11rzvjw",
+ propsAsIs: false
+});
+
+var _exp5 = /*#__PURE__*/function _exp5() {
+ return function (props) {
+ return props.selected ? _UIComponents_colors__WEBPACK_IMPORTED_MODULE_2__.CALYPSO_MEDIUM : 'transparent';
+ };
+};
+
+var _exp6 = /*#__PURE__*/function _exp6() {
+ return function (props) {
+ return props.selected ? '#fff' : 'inherit';
+ };
+};
+
+var _exp7 = /*#__PURE__*/function _exp7() {
+ return function (props) {
+ return props.selected ? _UIComponents_colors__WEBPACK_IMPORTED_MODULE_2__.CALYPSO_MEDIUM : _UIComponents_colors__WEBPACK_IMPORTED_MODULE_2__.CALYPSO_LIGHT;
+ };
+};
+
+var MenuItem = /*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_5__.styled)('div')({
+ name: "MenuItem",
+ "class": "m1jcdsjv",
+ propsAsIs: false,
+ vars: {
+ "m1jcdsjv-0": [_exp5()],
+ "m1jcdsjv-1": [_exp6()],
+ "m1jcdsjv-2": [_exp7()]
+ }
+});
+function AsyncSelect(_ref) {
+ var placeholder = _ref.placeholder,
+ value = _ref.value,
+ loadOptions = _ref.loadOptions,
+ onChange = _ref.onChange,
+ defaultOptions = _ref.defaultOptions;
+ var inputEl = (0,react__WEBPACK_IMPORTED_MODULE_1__.useRef)(null);
+ var inputShadowEl = (0,react__WEBPACK_IMPORTED_MODULE_1__.useRef)(null);
+
+ var _useState = (0,react__WEBPACK_IMPORTED_MODULE_1__.useState)(false),
+ _useState2 = _slicedToArray(_useState, 2),
+ isFocused = _useState2[0],
+ setFocus = _useState2[1];
+
+ var _useState3 = (0,react__WEBPACK_IMPORTED_MODULE_1__.useState)(_enums_loadState__WEBPACK_IMPORTED_MODULE_4__["default"].NotLoaded),
+ _useState4 = _slicedToArray(_useState3, 2),
+ loadState = _useState4[0],
+ setLoadState = _useState4[1];
+
+ var _useState5 = (0,react__WEBPACK_IMPORTED_MODULE_1__.useState)(''),
+ _useState6 = _slicedToArray(_useState5, 2),
+ localValue = _useState6[0],
+ setLocalValue = _useState6[1];
+
+ var _useState7 = (0,react__WEBPACK_IMPORTED_MODULE_1__.useState)(defaultOptions),
+ _useState8 = _slicedToArray(_useState7, 2),
+ options = _useState8[0],
+ setOptions = _useState8[1];
+
+ var inputSize = "".concat(inputShadowEl.current ? inputShadowEl.current.clientWidth + 10 : 2, "px");
+ (0,react__WEBPACK_IMPORTED_MODULE_1__.useEffect)(function () {
+ if (loadOptions && loadState === _enums_loadState__WEBPACK_IMPORTED_MODULE_4__["default"].NotLoaded) {
+ loadOptions('', function (result) {
+ setOptions(result);
+ setLoadState(_enums_loadState__WEBPACK_IMPORTED_MODULE_4__["default"].Idle);
+ });
+ }
+ }, [loadOptions, loadState]);
+
+ var renderItems = function renderItems() {
+ var items = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : [];
+ var parentKey = arguments.length > 1 ? arguments[1] : undefined;
+ return items.map(function (item, index) {
+ if (item.options) {
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsxs)(MenuGroup, {
+ children: [(0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(MenuGroupHeader, {
+ id: "".concat(index, "-heading"),
+ children: item.label
+ }), (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)("div", {
+ children: renderItems(item.options, index)
+ })]
+ }, "async-select-item-".concat(index));
+ } else {
+ var key = "async-select-item-".concat(parentKey !== undefined ? "".concat(parentKey, "-").concat(index) : index);
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(MenuItem, {
+ id: key,
+ selected: value && item.value === value.value,
+ onClick: function onClick() {
+ onChange(item);
+ setFocus(false);
+ },
+ children: item.label
+ }, key);
+ }
+ });
+ };
+
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsxs)(Container, {
+ children: [(0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsxs)(ControlContainer, {
+ id: "leadin-async-selector",
+ focused: isFocused,
+ onClick: function onClick() {
+ if (isFocused) {
+ if (inputEl.current) {
+ inputEl.current.blur();
+ }
+
+ setFocus(false);
+ setLocalValue('');
+ } else {
+ if (inputEl.current) {
+ inputEl.current.focus();
+ }
+
+ setFocus(true);
+ }
+ },
+ children: [(0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsxs)(ValueContainer, {
+ children: [localValue === '' && (!value ? (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(Placeholder, {
+ children: placeholder
+ }) : (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(SingleValue, {
+ children: value.label
+ })), (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsxs)(InputContainer, {
+ children: [(0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(Input, {
+ ref: inputEl,
+ onFocus: function onFocus() {
+ setFocus(true);
+ },
+ onChange: function onChange(e) {
+ setLocalValue(e.target.value);
+ setLoadState(_enums_loadState__WEBPACK_IMPORTED_MODULE_4__["default"].Loading);
+ loadOptions && loadOptions(e.target.value, function (result) {
+ setOptions(result);
+ setLoadState(_enums_loadState__WEBPACK_IMPORTED_MODULE_4__["default"].Idle);
+ });
+ },
+ value: localValue,
+ width: inputSize,
+ id: "asycn-select-input"
+ }), (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(InputShadow, {
+ ref: inputShadowEl,
+ children: localValue
+ })]
+ })]
+ }), (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsxs)(IndicatorContainer, {
+ children: [loadState === _enums_loadState__WEBPACK_IMPORTED_MODULE_4__["default"].Loading && (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_UIComponents_UISpinner__WEBPACK_IMPORTED_MODULE_3__["default"], {}), (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(DropdownIndicator, {})]
+ })]
+ }), isFocused && (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(MenuContainer, {
+ children: (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(MenuList, {
+ children: renderItems(options)
+ })
+ })]
+ });
+}
+
+__webpack_require__(/*! ./AsyncSelect.linaria.css!=!../../../node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./AsyncSelect.tsx */ "./scripts/shared/Common/AsyncSelect.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/Common/AsyncSelect.tsx");
+
+/***/ }),
+
+/***/ "./scripts/shared/Common/ErrorHandler.tsx":
+/*!************************************************!*\
+ !*** ./scripts/shared/Common/ErrorHandler.tsx ***!
+ \************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ ErrorHandler)
+/* harmony export */ });
+/* harmony import */ var react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react/jsx-runtime */ "./node_modules/react/jsx-runtime.js");
+/* harmony import */ var _UIComponents_UIButton__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! ../UIComponents/UIButton */ "./scripts/shared/UIComponents/UIButton.ts");
+/* harmony import */ var _UIComponents_UIContainer__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ../UIComponents/UIContainer */ "./scripts/shared/UIComponents/UIContainer.ts");
+/* harmony import */ var _HubspotWrapper__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ./HubspotWrapper */ "./scripts/shared/Common/HubspotWrapper.ts");
+/* harmony import */ var _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__(/*! ../../constants/leadinConfig */ "./scripts/constants/leadinConfig.ts");
+/* harmony import */ var _wordpress_i18n__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__(/*! @wordpress/i18n */ "@wordpress/i18n");
+/* harmony import */ var _wordpress_i18n__WEBPACK_IMPORTED_MODULE_5___default = /*#__PURE__*/__webpack_require__.n(_wordpress_i18n__WEBPACK_IMPORTED_MODULE_5__);
+
+
+
+
+
+
+
+
+function redirectToPlugin() {
+ window.location.href = "".concat(_constants_leadinConfig__WEBPACK_IMPORTED_MODULE_4__.adminUrl, "admin.php?page=leadin&leadin_expired=").concat(_constants_leadinConfig__WEBPACK_IMPORTED_MODULE_4__.redirectNonce);
+}
+
+function ErrorHandler(_ref) {
+ var status = _ref.status,
+ resetErrorState = _ref.resetErrorState,
+ _ref$errorInfo = _ref.errorInfo,
+ errorInfo = _ref$errorInfo === void 0 ? {
+ header: '',
+ message: '',
+ action: ''
+ } : _ref$errorInfo;
+ var isUnauthorized = status === 401 || status === 403;
+ var errorHeader = isUnauthorized ? (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_5__.__)("Your plugin isn't authorized", 'leadin') : errorInfo.header;
+ var errorMessage = isUnauthorized ? (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_5__.__)('Reauthorize your plugin to access your free HubSpot tools', 'leadin') : errorInfo.message;
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_HubspotWrapper__WEBPACK_IMPORTED_MODULE_3__["default"], {
+ pluginPath: _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_4__.pluginPath,
+ children: (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsxs)(_UIComponents_UIContainer__WEBPACK_IMPORTED_MODULE_2__["default"], {
+ textAlign: "center",
+ children: [(0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)("h4", {
+ children: errorHeader
+ }), (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)("p", {
+ children: (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)("b", {
+ children: errorMessage
+ })
+ }), isUnauthorized ? (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_UIComponents_UIButton__WEBPACK_IMPORTED_MODULE_1__["default"], {
+ "data-test-id": "authorize-button",
+ onClick: redirectToPlugin,
+ children: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_5__.__)('Go to plugin', 'leadin')
+ }) : (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_UIComponents_UIButton__WEBPACK_IMPORTED_MODULE_1__["default"], {
+ "data-test-id": "retry-button",
+ onClick: resetErrorState,
+ children: errorInfo.action
+ })]
+ })
+ });
+}
+
+/***/ }),
+
+/***/ "./scripts/shared/Common/HubspotWrapper.ts":
+/*!*************************************************!*\
+ !*** ./scripts/shared/Common/HubspotWrapper.ts ***!
+ \*************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (__WEBPACK_DEFAULT_EXPORT__)
+/* harmony export */ });
+/* harmony import */ var _linaria_react__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! @linaria/react */ "./node_modules/@linaria/react/dist/index.mjs");
+
+
+var _exp = /*#__PURE__*/function _exp() {
+ return function (props) {
+ return "url(".concat(props.pluginPath, "/public/assets/images/hubspot.svg)");
+ };
+};
+
+var _exp2 = /*#__PURE__*/function _exp2() {
+ return function (props) {
+ return props.padding || '90px 20% 25px';
+ };
+};
+
+/* harmony default export */ const __WEBPACK_DEFAULT_EXPORT__ = (/*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_0__.styled)('div')({
+ name: "HubspotWrapper0",
+ "class": "h1q5v5ee",
+ propsAsIs: false,
+ vars: {
+ "h1q5v5ee-0": [_exp()],
+ "h1q5v5ee-1": [_exp2()]
+ }
+}));
+
+__webpack_require__(/*! ./HubspotWrapper.linaria.css!=!../../../node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./HubspotWrapper.ts */ "./scripts/shared/Common/HubspotWrapper.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/Common/HubspotWrapper.ts");
+
+/***/ }),
+
+/***/ "./scripts/shared/Common/LoadingBlock.tsx":
+/*!************************************************!*\
+ !*** ./scripts/shared/Common/LoadingBlock.tsx ***!
+ \************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ LoadingBlock)
+/* harmony export */ });
+/* harmony import */ var react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react/jsx-runtime */ "./node_modules/react/jsx-runtime.js");
+/* harmony import */ var _HubspotWrapper__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! ./HubspotWrapper */ "./scripts/shared/Common/HubspotWrapper.ts");
+/* harmony import */ var _UIComponents_UISpinner__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ../UIComponents/UISpinner */ "./scripts/shared/UIComponents/UISpinner.tsx");
+/* harmony import */ var _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ../../constants/leadinConfig */ "./scripts/constants/leadinConfig.ts");
+
+
+
+
+function LoadingBlock() {
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_HubspotWrapper__WEBPACK_IMPORTED_MODULE_1__["default"], {
+ pluginPath: _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_3__.pluginPath,
+ children: (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_UIComponents_UISpinner__WEBPACK_IMPORTED_MODULE_2__["default"], {
+ size: 50
+ })
+ });
+}
+
+/***/ }),
+
+/***/ "./scripts/shared/Form/FormEdit.tsx":
+/*!******************************************!*\
+ !*** ./scripts/shared/Form/FormEdit.tsx ***!
+ \******************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ FormEditContainer)
+/* harmony export */ });
+/* harmony import */ var react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react/jsx-runtime */ "./node_modules/react/jsx-runtime.js");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! react */ "react");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(react__WEBPACK_IMPORTED_MODULE_1__);
+/* harmony import */ var _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ../../constants/leadinConfig */ "./scripts/constants/leadinConfig.ts");
+/* harmony import */ var _UIComponents_UISpacer__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ../UIComponents/UISpacer */ "./scripts/shared/UIComponents/UISpacer.ts");
+/* harmony import */ var _PreviewForm__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__(/*! ./PreviewForm */ "./scripts/shared/Form/PreviewForm.tsx");
+/* harmony import */ var _FormSelect__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__(/*! ./FormSelect */ "./scripts/shared/Form/FormSelect.tsx");
+/* harmony import */ var _iframe_useBackgroundApp__WEBPACK_IMPORTED_MODULE_6__ = __webpack_require__(/*! ../../iframe/useBackgroundApp */ "./scripts/iframe/useBackgroundApp.ts");
+/* harmony import */ var _iframe_integratedMessages__WEBPACK_IMPORTED_MODULE_7__ = __webpack_require__(/*! ../../iframe/integratedMessages */ "./scripts/iframe/integratedMessages/index.ts");
+/* harmony import */ var _Common_LoadingBlock__WEBPACK_IMPORTED_MODULE_8__ = __webpack_require__(/*! ../Common/LoadingBlock */ "./scripts/shared/Common/LoadingBlock.tsx");
+/* harmony import */ var _utils_backgroundAppUtils__WEBPACK_IMPORTED_MODULE_9__ = __webpack_require__(/*! ../../utils/backgroundAppUtils */ "./scripts/utils/backgroundAppUtils.ts");
+function ownKeys(object, enumerableOnly) { var keys = Object.keys(object); if (Object.getOwnPropertySymbols) { var symbols = Object.getOwnPropertySymbols(object); enumerableOnly && (symbols = symbols.filter(function (sym) { return Object.getOwnPropertyDescriptor(object, sym).enumerable; })), keys.push.apply(keys, symbols); } return keys; }
+
+function _objectSpread(target) { for (var i = 1; i < arguments.length; i++) { var source = null != arguments[i] ? arguments[i] : {}; i % 2 ? ownKeys(Object(source), !0).forEach(function (key) { _defineProperty(target, key, source[key]); }) : Object.getOwnPropertyDescriptors ? Object.defineProperties(target, Object.getOwnPropertyDescriptors(source)) : ownKeys(Object(source)).forEach(function (key) { Object.defineProperty(target, key, Object.getOwnPropertyDescriptor(source, key)); }); } return target; }
+
+function _defineProperty(obj, key, value) { if (key in obj) { Object.defineProperty(obj, key, { value: value, enumerable: true, configurable: true, writable: true }); } else { obj[key] = value; } return obj; }
+
+
+
+
+
+
+
+
+
+
+
+
+function FormEdit(_ref) {
+ var attributes = _ref.attributes,
+ isSelected = _ref.isSelected,
+ setAttributes = _ref.setAttributes,
+ _ref$preview = _ref.preview,
+ preview = _ref$preview === void 0 ? true : _ref$preview,
+ _ref$origin = _ref.origin,
+ origin = _ref$origin === void 0 ? 'gutenberg' : _ref$origin;
+ var formId = attributes.formId,
+ formName = attributes.formName;
+ var formSelected = _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_2__.portalId && formId;
+ var isBackgroundAppReady = (0,_iframe_useBackgroundApp__WEBPACK_IMPORTED_MODULE_6__.useBackgroundAppContext)();
+ var monitorFormPreviewRender = (0,_iframe_useBackgroundApp__WEBPACK_IMPORTED_MODULE_6__.usePostBackgroundMessage)();
+
+ var handleChange = function handleChange(selectedForm) {
+ setAttributes({
+ portalId: _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_2__.portalId,
+ formId: selectedForm.value,
+ formName: selectedForm.label
+ });
+ };
+
+ (0,react__WEBPACK_IMPORTED_MODULE_1__.useEffect)(function () {
+ monitorFormPreviewRender({
+ key: _iframe_integratedMessages__WEBPACK_IMPORTED_MODULE_7__.ProxyMessages.TrackFormPreviewRender,
+ payload: {
+ origin: origin
+ }
+ });
+ }, [origin]);
+ return !isBackgroundAppReady ? (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_Common_LoadingBlock__WEBPACK_IMPORTED_MODULE_8__["default"], {}) : (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsxs)(react__WEBPACK_IMPORTED_MODULE_1__.Fragment, {
+ children: [(isSelected || !formSelected) && (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_FormSelect__WEBPACK_IMPORTED_MODULE_5__["default"], {
+ formId: formId,
+ formName: formName,
+ handleChange: handleChange,
+ origin: origin
+ }), formSelected && (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsxs)(react__WEBPACK_IMPORTED_MODULE_1__.Fragment, {
+ children: [isSelected && (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_UIComponents_UISpacer__WEBPACK_IMPORTED_MODULE_3__["default"], {}), preview && (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_PreviewForm__WEBPACK_IMPORTED_MODULE_4__["default"], {
+ portalId: _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_2__.portalId,
+ formId: formId
+ })]
+ })]
+ });
+}
+
+function FormEditContainer(props) {
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_iframe_useBackgroundApp__WEBPACK_IMPORTED_MODULE_6__.BackgroudAppContext.Provider, {
+ value: _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_2__.refreshToken && (0,_utils_backgroundAppUtils__WEBPACK_IMPORTED_MODULE_9__.getOrCreateBackgroundApp)(_constants_leadinConfig__WEBPACK_IMPORTED_MODULE_2__.refreshToken),
+ children: (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(FormEdit, _objectSpread({}, props))
+ });
+}
+
+/***/ }),
+
+/***/ "./scripts/shared/Form/FormSelect.tsx":
+/*!********************************************!*\
+ !*** ./scripts/shared/Form/FormSelect.tsx ***!
+ \********************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ FormSelect)
+/* harmony export */ });
+/* harmony import */ var react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react/jsx-runtime */ "./node_modules/react/jsx-runtime.js");
+/* harmony import */ var _FormSelector__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! ./FormSelector */ "./scripts/shared/Form/FormSelector.tsx");
+/* harmony import */ var _Common_LoadingBlock__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ../Common/LoadingBlock */ "./scripts/shared/Common/LoadingBlock.tsx");
+/* harmony import */ var _wordpress_i18n__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! @wordpress/i18n */ "@wordpress/i18n");
+/* harmony import */ var _wordpress_i18n__WEBPACK_IMPORTED_MODULE_3___default = /*#__PURE__*/__webpack_require__.n(_wordpress_i18n__WEBPACK_IMPORTED_MODULE_3__);
+/* harmony import */ var _hooks_useForms__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__(/*! ./hooks/useForms */ "./scripts/shared/Form/hooks/useForms.ts");
+/* harmony import */ var _hooks_useCreateFormFromTemplate__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__(/*! ./hooks/useCreateFormFromTemplate */ "./scripts/shared/Form/hooks/useCreateFormFromTemplate.ts");
+/* harmony import */ var _constants_defaultFormOptions__WEBPACK_IMPORTED_MODULE_6__ = __webpack_require__(/*! ../../constants/defaultFormOptions */ "./scripts/constants/defaultFormOptions.ts");
+/* harmony import */ var _Common_ErrorHandler__WEBPACK_IMPORTED_MODULE_7__ = __webpack_require__(/*! ../Common/ErrorHandler */ "./scripts/shared/Common/ErrorHandler.tsx");
+
+
+
+
+
+
+
+
+function FormSelect(_ref) {
+ var formId = _ref.formId,
+ formName = _ref.formName,
+ handleChange = _ref.handleChange,
+ _ref$origin = _ref.origin,
+ origin = _ref$origin === void 0 ? 'gutenberg' : _ref$origin;
+
+ var _useForms = (0,_hooks_useForms__WEBPACK_IMPORTED_MODULE_4__["default"])(),
+ search = _useForms.search,
+ formApiError = _useForms.formApiError,
+ reset = _useForms.reset;
+
+ var _useCreateFormFromTem = (0,_hooks_useCreateFormFromTemplate__WEBPACK_IMPORTED_MODULE_5__["default"])(origin),
+ createFormByTemplate = _useCreateFormFromTem.createFormByTemplate,
+ createReset = _useCreateFormFromTem.reset,
+ isCreating = _useCreateFormFromTem.isCreating,
+ hasError = _useCreateFormFromTem.hasError,
+ createApiError = _useCreateFormFromTem.formApiError;
+
+ var value = formId && formName ? {
+ label: formName,
+ value: formId
+ } : null;
+
+ var handleLocalChange = function handleLocalChange(option) {
+ if ((0,_constants_defaultFormOptions__WEBPACK_IMPORTED_MODULE_6__.isDefaultForm)(option.value)) {
+ createFormByTemplate(option.value).then(function (_ref2) {
+ var guid = _ref2.guid,
+ name = _ref2.name;
+ handleChange({
+ value: guid,
+ label: name
+ });
+ });
+ } else {
+ handleChange(option);
+ }
+ };
+
+ return isCreating ? (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_Common_LoadingBlock__WEBPACK_IMPORTED_MODULE_2__["default"], {}) : formApiError || createApiError ? (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_Common_ErrorHandler__WEBPACK_IMPORTED_MODULE_7__["default"], {
+ status: formApiError ? formApiError.status : createApiError.status,
+ resetErrorState: function resetErrorState() {
+ if (hasError) {
+ createReset();
+ } else {
+ reset();
+ }
+ },
+ errorInfo: {
+ header: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_3__.__)('There was a problem retrieving your forms', 'leadin'),
+ message: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_3__.__)('Please refresh your forms or try again in a few minutes', 'leadin'),
+ action: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_3__.__)('Refresh forms', 'leadin')
+ }
+ }) : (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_FormSelector__WEBPACK_IMPORTED_MODULE_1__["default"], {
+ loadOptions: search,
+ onChange: function onChange(option) {
+ return handleLocalChange(option);
+ },
+ value: value
+ });
+}
+
+/***/ }),
+
+/***/ "./scripts/shared/Form/FormSelector.tsx":
+/*!**********************************************!*\
+ !*** ./scripts/shared/Form/FormSelector.tsx ***!
+ \**********************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ FormSelector)
+/* harmony export */ });
+/* harmony import */ var react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react/jsx-runtime */ "./node_modules/react/jsx-runtime.js");
+/* harmony import */ var _Common_HubspotWrapper__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! ../Common/HubspotWrapper */ "./scripts/shared/Common/HubspotWrapper.ts");
+/* harmony import */ var _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ../../constants/leadinConfig */ "./scripts/constants/leadinConfig.ts");
+/* harmony import */ var _Common_AsyncSelect__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ../Common/AsyncSelect */ "./scripts/shared/Common/AsyncSelect.tsx");
+/* harmony import */ var _wordpress_i18n__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__(/*! @wordpress/i18n */ "@wordpress/i18n");
+/* harmony import */ var _wordpress_i18n__WEBPACK_IMPORTED_MODULE_4___default = /*#__PURE__*/__webpack_require__.n(_wordpress_i18n__WEBPACK_IMPORTED_MODULE_4__);
+
+
+
+
+
+function FormSelector(_ref) {
+ var loadOptions = _ref.loadOptions,
+ onChange = _ref.onChange,
+ value = _ref.value;
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsxs)(_Common_HubspotWrapper__WEBPACK_IMPORTED_MODULE_1__["default"], {
+ pluginPath: _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_2__.pluginPath,
+ children: [(0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)("p", {
+ "data-test-id": "leadin-form-select",
+ children: (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)("b", {
+ children: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_4__.__)('Select an existing form or create a new one from a template', 'leadin')
+ })
+ }), (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_Common_AsyncSelect__WEBPACK_IMPORTED_MODULE_3__["default"], {
+ placeholder: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_4__.__)('Search for a form', 'leadin'),
+ value: value,
+ loadOptions: loadOptions,
+ onChange: onChange
+ })]
+ });
+}
+
+/***/ }),
+
+/***/ "./scripts/shared/Form/PreviewForm.tsx":
+/*!*********************************************!*\
+ !*** ./scripts/shared/Form/PreviewForm.tsx ***!
+ \*********************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ PreviewForm)
+/* harmony export */ });
+/* harmony import */ var react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react/jsx-runtime */ "./node_modules/react/jsx-runtime.js");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! react */ "react");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(react__WEBPACK_IMPORTED_MODULE_1__);
+/* harmony import */ var _UIComponents_UIOverlay__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ../UIComponents/UIOverlay */ "./scripts/shared/UIComponents/UIOverlay.ts");
+/* harmony import */ var _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ../../constants/leadinConfig */ "./scripts/constants/leadinConfig.ts");
+/* harmony import */ var _hooks_useFormsScript__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__(/*! ./hooks/useFormsScript */ "./scripts/shared/Form/hooks/useFormsScript.ts");
+
+
+
+
+
+function PreviewForm(_ref) {
+ var portalId = _ref.portalId,
+ formId = _ref.formId;
+ var inputEl = (0,react__WEBPACK_IMPORTED_MODULE_1__.useRef)(null);
+ var ready = (0,_hooks_useFormsScript__WEBPACK_IMPORTED_MODULE_4__["default"])();
+ (0,react__WEBPACK_IMPORTED_MODULE_1__.useEffect)(function () {
+ if (!ready) {
+ return;
+ }
+
+ if (inputEl.current) {
+ inputEl.current.innerHTML = '';
+ var embedScript = document.createElement('script');
+ embedScript.innerHTML = "hbspt.forms.create({ portalId: '".concat(portalId, "', formId: '").concat(formId, "', region: '").concat(_constants_leadinConfig__WEBPACK_IMPORTED_MODULE_3__.hublet, "', ").concat(_constants_leadinConfig__WEBPACK_IMPORTED_MODULE_3__.formsScriptPayload, " });");
+ inputEl.current.appendChild(embedScript);
+ }
+ }, [formId, portalId, ready, inputEl]);
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_UIComponents_UIOverlay__WEBPACK_IMPORTED_MODULE_2__["default"], {
+ ref: inputEl
+ });
+}
+
+/***/ }),
+
+/***/ "./scripts/shared/Form/hooks/useCreateFormFromTemplate.ts":
+/*!****************************************************************!*\
+ !*** ./scripts/shared/Form/hooks/useCreateFormFromTemplate.ts ***!
+ \****************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ useCreateFormFromTemplate)
+/* harmony export */ });
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react */ "react");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(react__WEBPACK_IMPORTED_MODULE_0__);
+/* harmony import */ var _iframe_useBackgroundApp__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! ../../../iframe/useBackgroundApp */ "./scripts/iframe/useBackgroundApp.ts");
+/* harmony import */ var _enums_loadState__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ../../enums/loadState */ "./scripts/shared/enums/loadState.ts");
+/* harmony import */ var _iframe_integratedMessages__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ../../../iframe/integratedMessages */ "./scripts/iframe/integratedMessages/index.ts");
+function _slicedToArray(arr, i) { return _arrayWithHoles(arr) || _iterableToArrayLimit(arr, i) || _unsupportedIterableToArray(arr, i) || _nonIterableRest(); }
+
+function _nonIterableRest() { throw new TypeError("Invalid attempt to destructure non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method."); }
+
+function _unsupportedIterableToArray(o, minLen) { if (!o) return; if (typeof o === "string") return _arrayLikeToArray(o, minLen); var n = Object.prototype.toString.call(o).slice(8, -1); if (n === "Object" && o.constructor) n = o.constructor.name; if (n === "Map" || n === "Set") return Array.from(o); if (n === "Arguments" || /^(?:Ui|I)nt(?:8|16|32)(?:Clamped)?Array$/.test(n)) return _arrayLikeToArray(o, minLen); }
+
+function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len = arr.length; for (var i = 0, arr2 = new Array(len); i < len; i++) { arr2[i] = arr[i]; } return arr2; }
+
+function _iterableToArrayLimit(arr, i) { var _i = arr == null ? null : typeof Symbol !== "undefined" && arr[Symbol.iterator] || arr["@@iterator"]; if (_i == null) return; var _arr = []; var _n = true; var _d = false; var _s, _e; try { for (_i = _i.call(arr); !(_n = (_s = _i.next()).done); _n = true) { _arr.push(_s.value); if (i && _arr.length === i) break; } } catch (err) { _d = true; _e = err; } finally { try { if (!_n && _i["return"] != null) _i["return"](); } finally { if (_d) throw _e; } } return _arr; }
+
+function _arrayWithHoles(arr) { if (Array.isArray(arr)) return arr; }
+
+
+
+
+
+function useCreateFormFromTemplate() {
+ var origin = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : 'gutenberg';
+ var proxy = (0,_iframe_useBackgroundApp__WEBPACK_IMPORTED_MODULE_1__.usePostAsyncBackgroundMessage)();
+ var track = (0,_iframe_useBackgroundApp__WEBPACK_IMPORTED_MODULE_1__.usePostBackgroundMessage)();
+
+ var _useState = (0,react__WEBPACK_IMPORTED_MODULE_0__.useState)(_enums_loadState__WEBPACK_IMPORTED_MODULE_2__["default"].Idle),
+ _useState2 = _slicedToArray(_useState, 2),
+ loadState = _useState2[0],
+ setLoadState = _useState2[1];
+
+ var _useState3 = (0,react__WEBPACK_IMPORTED_MODULE_0__.useState)(null),
+ _useState4 = _slicedToArray(_useState3, 2),
+ formApiError = _useState4[0],
+ setFormApiError = _useState4[1];
+
+ var createFormByTemplate = function createFormByTemplate(type) {
+ setLoadState(_enums_loadState__WEBPACK_IMPORTED_MODULE_2__["default"].Loading);
+ track({
+ key: _iframe_integratedMessages__WEBPACK_IMPORTED_MODULE_3__.ProxyMessages.TrackFormCreatedFromTemplate,
+ payload: {
+ type: type,
+ origin: origin
+ }
+ });
+ return proxy({
+ key: _iframe_integratedMessages__WEBPACK_IMPORTED_MODULE_3__.ProxyMessages.CreateFormFromTemplate,
+ payload: type
+ }).then(function (form) {
+ setLoadState(_enums_loadState__WEBPACK_IMPORTED_MODULE_2__["default"].Idle);
+ return form;
+ })["catch"](function (err) {
+ setFormApiError(err);
+ track({
+ key: _iframe_integratedMessages__WEBPACK_IMPORTED_MODULE_3__.ProxyMessages.TrackFormCreationFailed,
+ payload: {
+ origin: origin
+ }
+ });
+ setLoadState(_enums_loadState__WEBPACK_IMPORTED_MODULE_2__["default"].Failed);
+ });
+ };
+
+ return {
+ isCreating: loadState === _enums_loadState__WEBPACK_IMPORTED_MODULE_2__["default"].Loading,
+ hasError: loadState === _enums_loadState__WEBPACK_IMPORTED_MODULE_2__["default"].Failed,
+ formApiError: formApiError,
+ createFormByTemplate: createFormByTemplate,
+ reset: function reset() {
+ return setLoadState(_enums_loadState__WEBPACK_IMPORTED_MODULE_2__["default"].Idle);
+ }
+ };
+}
+
+/***/ }),
+
+/***/ "./scripts/shared/Form/hooks/useForms.ts":
+/*!***********************************************!*\
+ !*** ./scripts/shared/Form/hooks/useForms.ts ***!
+ \***********************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ useForms)
+/* harmony export */ });
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react */ "react");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(react__WEBPACK_IMPORTED_MODULE_0__);
+/* harmony import */ var lodash_debounce__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! lodash/debounce */ "./node_modules/lodash/debounce.js");
+/* harmony import */ var lodash_debounce__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(lodash_debounce__WEBPACK_IMPORTED_MODULE_1__);
+/* harmony import */ var _iframe_useBackgroundApp__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ../../../iframe/useBackgroundApp */ "./scripts/iframe/useBackgroundApp.ts");
+/* harmony import */ var _constants_defaultFormOptions__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ../../../constants/defaultFormOptions */ "./scripts/constants/defaultFormOptions.ts");
+/* harmony import */ var _iframe_integratedMessages__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__(/*! ../../../iframe/integratedMessages */ "./scripts/iframe/integratedMessages/index.ts");
+function _toConsumableArray(arr) { return _arrayWithoutHoles(arr) || _iterableToArray(arr) || _unsupportedIterableToArray(arr) || _nonIterableSpread(); }
+
+function _nonIterableSpread() { throw new TypeError("Invalid attempt to spread non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method."); }
+
+function _iterableToArray(iter) { if (typeof Symbol !== "undefined" && iter[Symbol.iterator] != null || iter["@@iterator"] != null) return Array.from(iter); }
+
+function _arrayWithoutHoles(arr) { if (Array.isArray(arr)) return _arrayLikeToArray(arr); }
+
+function _slicedToArray(arr, i) { return _arrayWithHoles(arr) || _iterableToArrayLimit(arr, i) || _unsupportedIterableToArray(arr, i) || _nonIterableRest(); }
+
+function _nonIterableRest() { throw new TypeError("Invalid attempt to destructure non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method."); }
+
+function _unsupportedIterableToArray(o, minLen) { if (!o) return; if (typeof o === "string") return _arrayLikeToArray(o, minLen); var n = Object.prototype.toString.call(o).slice(8, -1); if (n === "Object" && o.constructor) n = o.constructor.name; if (n === "Map" || n === "Set") return Array.from(o); if (n === "Arguments" || /^(?:Ui|I)nt(?:8|16|32)(?:Clamped)?Array$/.test(n)) return _arrayLikeToArray(o, minLen); }
+
+function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len = arr.length; for (var i = 0, arr2 = new Array(len); i < len; i++) { arr2[i] = arr[i]; } return arr2; }
+
+function _iterableToArrayLimit(arr, i) { var _i = arr == null ? null : typeof Symbol !== "undefined" && arr[Symbol.iterator] || arr["@@iterator"]; if (_i == null) return; var _arr = []; var _n = true; var _d = false; var _s, _e; try { for (_i = _i.call(arr); !(_n = (_s = _i.next()).done); _n = true) { _arr.push(_s.value); if (i && _arr.length === i) break; } } catch (err) { _d = true; _e = err; } finally { try { if (!_n && _i["return"] != null) _i["return"](); } finally { if (_d) throw _e; } } return _arr; }
+
+function _arrayWithHoles(arr) { if (Array.isArray(arr)) return arr; }
+
+
+
+
+
+
+function useForms() {
+ var proxy = (0,_iframe_useBackgroundApp__WEBPACK_IMPORTED_MODULE_2__.usePostAsyncBackgroundMessage)();
+
+ var _useState = (0,react__WEBPACK_IMPORTED_MODULE_0__.useState)(null),
+ _useState2 = _slicedToArray(_useState, 2),
+ formApiError = _useState2[0],
+ setFormApiError = _useState2[1];
+
+ var search = lodash_debounce__WEBPACK_IMPORTED_MODULE_1___default()(function (search, callback) {
+ return proxy({
+ key: _iframe_integratedMessages__WEBPACK_IMPORTED_MODULE_4__.ProxyMessages.FetchForms,
+ payload: {
+ search: search
+ }
+ }).then(function (forms) {
+ callback([].concat(_toConsumableArray(forms.map(function (form) {
+ return {
+ label: form.name,
+ value: form.guid
+ };
+ })), [_constants_defaultFormOptions__WEBPACK_IMPORTED_MODULE_3__.DEFAULT_OPTIONS]));
+ })["catch"](function (error) {
+ setFormApiError(error);
+ });
+ }, 300, {
+ trailing: true
+ });
+ return {
+ search: search,
+ formApiError: formApiError,
+ reset: function reset() {
+ return setFormApiError(null);
+ }
+ };
+}
+
+/***/ }),
+
+/***/ "./scripts/shared/Form/hooks/useFormsScript.ts":
+/*!*****************************************************!*\
+ !*** ./scripts/shared/Form/hooks/useFormsScript.ts ***!
+ \*****************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ useFormScript)
+/* harmony export */ });
+/* harmony import */ var jquery__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! jquery */ "jquery");
+/* harmony import */ var jquery__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(jquery__WEBPACK_IMPORTED_MODULE_0__);
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! react */ "react");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(react__WEBPACK_IMPORTED_MODULE_1__);
+/* harmony import */ var _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ../../../constants/leadinConfig */ "./scripts/constants/leadinConfig.ts");
+/* harmony import */ var _lib_Raven__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ../../../lib/Raven */ "./scripts/lib/Raven.ts");
+function _slicedToArray(arr, i) { return _arrayWithHoles(arr) || _iterableToArrayLimit(arr, i) || _unsupportedIterableToArray(arr, i) || _nonIterableRest(); }
+
+function _nonIterableRest() { throw new TypeError("Invalid attempt to destructure non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method."); }
+
+function _unsupportedIterableToArray(o, minLen) { if (!o) return; if (typeof o === "string") return _arrayLikeToArray(o, minLen); var n = Object.prototype.toString.call(o).slice(8, -1); if (n === "Object" && o.constructor) n = o.constructor.name; if (n === "Map" || n === "Set") return Array.from(o); if (n === "Arguments" || /^(?:Ui|I)nt(?:8|16|32)(?:Clamped)?Array$/.test(n)) return _arrayLikeToArray(o, minLen); }
+
+function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len = arr.length; for (var i = 0, arr2 = new Array(len); i < len; i++) { arr2[i] = arr[i]; } return arr2; }
+
+function _iterableToArrayLimit(arr, i) { var _i = arr == null ? null : typeof Symbol !== "undefined" && arr[Symbol.iterator] || arr["@@iterator"]; if (_i == null) return; var _arr = []; var _n = true; var _d = false; var _s, _e; try { for (_i = _i.call(arr); !(_n = (_s = _i.next()).done); _n = true) { _arr.push(_s.value); if (i && _arr.length === i) break; } } catch (err) { _d = true; _e = err; } finally { try { if (!_n && _i["return"] != null) _i["return"](); } finally { if (_d) throw _e; } } return _arr; }
+
+function _arrayWithHoles(arr) { if (Array.isArray(arr)) return arr; }
+
+
+
+
+
+var promise;
+
+function loadFormsScript() {
+ if (!promise) {
+ promise = new Promise(function (resolve, reject) {
+ return jquery__WEBPACK_IMPORTED_MODULE_0___default().getScript(_constants_leadinConfig__WEBPACK_IMPORTED_MODULE_2__.formsScript).done(resolve).fail(reject);
+ });
+ }
+
+ return promise;
+}
+
+function useFormScript() {
+ var _useState = (0,react__WEBPACK_IMPORTED_MODULE_1__.useState)(false),
+ _useState2 = _slicedToArray(_useState, 2),
+ ready = _useState2[0],
+ setReady = _useState2[1];
+
+ (0,react__WEBPACK_IMPORTED_MODULE_1__.useEffect)(function () {
+ loadFormsScript().then(function () {
+ return setReady(true);
+ })["catch"](function (error) {
+ return _lib_Raven__WEBPACK_IMPORTED_MODULE_3__["default"].captureException(error);
+ });
+ }, []);
+ return ready;
+}
+
+/***/ }),
+
+/***/ "./scripts/shared/Meeting/MeetingController.tsx":
+/*!******************************************************!*\
+ !*** ./scripts/shared/Meeting/MeetingController.tsx ***!
+ \******************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ MeetingController)
+/* harmony export */ });
+/* harmony import */ var react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react/jsx-runtime */ "./node_modules/react/jsx-runtime.js");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! react */ "react");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(react__WEBPACK_IMPORTED_MODULE_1__);
+/* harmony import */ var _Common_LoadingBlock__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ../Common/LoadingBlock */ "./scripts/shared/Common/LoadingBlock.tsx");
+/* harmony import */ var _MeetingSelector__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ./MeetingSelector */ "./scripts/shared/Meeting/MeetingSelector.tsx");
+/* harmony import */ var _MeetingWarning__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__(/*! ./MeetingWarning */ "./scripts/shared/Meeting/MeetingWarning.tsx");
+/* harmony import */ var _hooks_useMeetings__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__(/*! ./hooks/useMeetings */ "./scripts/shared/Meeting/hooks/useMeetings.ts");
+/* harmony import */ var _Common_HubspotWrapper__WEBPACK_IMPORTED_MODULE_6__ = __webpack_require__(/*! ../Common/HubspotWrapper */ "./scripts/shared/Common/HubspotWrapper.ts");
+/* harmony import */ var _Common_ErrorHandler__WEBPACK_IMPORTED_MODULE_7__ = __webpack_require__(/*! ../Common/ErrorHandler */ "./scripts/shared/Common/ErrorHandler.tsx");
+/* harmony import */ var _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_8__ = __webpack_require__(/*! ../../constants/leadinConfig */ "./scripts/constants/leadinConfig.ts");
+/* harmony import */ var _wordpress_i18n__WEBPACK_IMPORTED_MODULE_9__ = __webpack_require__(/*! @wordpress/i18n */ "@wordpress/i18n");
+/* harmony import */ var _wordpress_i18n__WEBPACK_IMPORTED_MODULE_9___default = /*#__PURE__*/__webpack_require__.n(_wordpress_i18n__WEBPACK_IMPORTED_MODULE_9__);
+/* harmony import */ var raven_js__WEBPACK_IMPORTED_MODULE_10__ = __webpack_require__(/*! raven-js */ "./node_modules/raven-js/src/singleton.js");
+/* harmony import */ var raven_js__WEBPACK_IMPORTED_MODULE_10___default = /*#__PURE__*/__webpack_require__.n(raven_js__WEBPACK_IMPORTED_MODULE_10__);
+
+
+
+
+
+
+
+
+
+
+
+function MeetingController(_ref) {
+ var handleChange = _ref.handleChange,
+ url = _ref.url;
+
+ var _useMeetings = (0,_hooks_useMeetings__WEBPACK_IMPORTED_MODULE_5__["default"])(),
+ meetings = _useMeetings.mappedMeetings,
+ loading = _useMeetings.loading,
+ error = _useMeetings.error,
+ reload = _useMeetings.reload,
+ connectCalendar = _useMeetings.connectCalendar;
+
+ var selectedMeetingOption = (0,_hooks_useMeetings__WEBPACK_IMPORTED_MODULE_5__.useSelectedMeeting)(url);
+ var selectedMeetingCalendar = (0,_hooks_useMeetings__WEBPACK_IMPORTED_MODULE_5__.useSelectedMeetingCalendar)(url);
+ (0,react__WEBPACK_IMPORTED_MODULE_1__.useEffect)(function () {
+ if (!url && meetings.length > 0) {
+ handleChange(meetings[0].value);
+ }
+ }, [meetings, url, handleChange]);
+
+ var handleLocalChange = function handleLocalChange(option) {
+ handleChange(option.value);
+ };
+
+ var handleConnectCalendar = function handleConnectCalendar() {
+ return connectCalendar().then(function () {
+ reload();
+ })["catch"](function (error) {
+ raven_js__WEBPACK_IMPORTED_MODULE_10___default().captureMessage('Unable to connect calendar', {
+ extra: {
+ error: error
+ }
+ });
+ });
+ };
+
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(react__WEBPACK_IMPORTED_MODULE_1__.Fragment, {
+ children: loading ? (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_Common_LoadingBlock__WEBPACK_IMPORTED_MODULE_2__["default"], {}) : error ? (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_Common_ErrorHandler__WEBPACK_IMPORTED_MODULE_7__["default"], {
+ status: error && error.status || error,
+ resetErrorState: function resetErrorState() {
+ return reload();
+ },
+ errorInfo: {
+ header: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_9__.__)('There was a problem retrieving your meetings', 'leadin'),
+ message: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_9__.__)('Please refresh your meetings or try again in a few minutes', 'leadin'),
+ action: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_9__.__)('Refresh meetings', 'leadin')
+ }
+ }) : (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsxs)(_Common_HubspotWrapper__WEBPACK_IMPORTED_MODULE_6__["default"], {
+ padding: "90px 32px 24px",
+ pluginPath: _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_8__.pluginPath,
+ children: [selectedMeetingCalendar && (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_MeetingWarning__WEBPACK_IMPORTED_MODULE_4__["default"], {
+ status: selectedMeetingCalendar,
+ onConnectCalendar: handleConnectCalendar
+ }), meetings.length > 1 && (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_MeetingSelector__WEBPACK_IMPORTED_MODULE_3__["default"], {
+ onChange: handleLocalChange,
+ options: meetings,
+ value: selectedMeetingOption
+ })]
+ })
+ });
+}
+
+/***/ }),
+
+/***/ "./scripts/shared/Meeting/MeetingEdit.tsx":
+/*!************************************************!*\
+ !*** ./scripts/shared/Meeting/MeetingEdit.tsx ***!
+ \************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ MeetingsEditContainer)
+/* harmony export */ });
+/* harmony import */ var react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react/jsx-runtime */ "./node_modules/react/jsx-runtime.js");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! react */ "react");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(react__WEBPACK_IMPORTED_MODULE_1__);
+/* harmony import */ var _MeetingController__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ./MeetingController */ "./scripts/shared/Meeting/MeetingController.tsx");
+/* harmony import */ var _PreviewMeeting__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ./PreviewMeeting */ "./scripts/shared/Meeting/PreviewMeeting.tsx");
+/* harmony import */ var _iframe_useBackgroundApp__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__(/*! ../../iframe/useBackgroundApp */ "./scripts/iframe/useBackgroundApp.ts");
+/* harmony import */ var _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__(/*! ../../constants/leadinConfig */ "./scripts/constants/leadinConfig.ts");
+/* harmony import */ var _iframe_integratedMessages__WEBPACK_IMPORTED_MODULE_6__ = __webpack_require__(/*! ../../iframe/integratedMessages */ "./scripts/iframe/integratedMessages/index.ts");
+/* harmony import */ var _Common_LoadingBlock__WEBPACK_IMPORTED_MODULE_7__ = __webpack_require__(/*! ../Common/LoadingBlock */ "./scripts/shared/Common/LoadingBlock.tsx");
+/* harmony import */ var _utils_backgroundAppUtils__WEBPACK_IMPORTED_MODULE_8__ = __webpack_require__(/*! ../../utils/backgroundAppUtils */ "./scripts/utils/backgroundAppUtils.ts");
+function ownKeys(object, enumerableOnly) { var keys = Object.keys(object); if (Object.getOwnPropertySymbols) { var symbols = Object.getOwnPropertySymbols(object); enumerableOnly && (symbols = symbols.filter(function (sym) { return Object.getOwnPropertyDescriptor(object, sym).enumerable; })), keys.push.apply(keys, symbols); } return keys; }
+
+function _objectSpread(target) { for (var i = 1; i < arguments.length; i++) { var source = null != arguments[i] ? arguments[i] : {}; i % 2 ? ownKeys(Object(source), !0).forEach(function (key) { _defineProperty(target, key, source[key]); }) : Object.getOwnPropertyDescriptors ? Object.defineProperties(target, Object.getOwnPropertyDescriptors(source)) : ownKeys(Object(source)).forEach(function (key) { Object.defineProperty(target, key, Object.getOwnPropertyDescriptor(source, key)); }); } return target; }
+
+function _defineProperty(obj, key, value) { if (key in obj) { Object.defineProperty(obj, key, { value: value, enumerable: true, configurable: true, writable: true }); } else { obj[key] = value; } return obj; }
+
+
+
+
+
+
+
+
+
+
+
+function MeetingEdit(_ref) {
+ var url = _ref.attributes.url,
+ isSelected = _ref.isSelected,
+ setAttributes = _ref.setAttributes,
+ _ref$preview = _ref.preview,
+ preview = _ref$preview === void 0 ? true : _ref$preview,
+ _ref$origin = _ref.origin,
+ origin = _ref$origin === void 0 ? 'gutenberg' : _ref$origin;
+ var isBackgroundAppReady = (0,_iframe_useBackgroundApp__WEBPACK_IMPORTED_MODULE_4__.useBackgroundAppContext)();
+ var monitorFormPreviewRender = (0,_iframe_useBackgroundApp__WEBPACK_IMPORTED_MODULE_4__.usePostBackgroundMessage)();
+
+ var handleChange = function handleChange(newUrl) {
+ setAttributes({
+ url: newUrl
+ });
+ };
+
+ (0,react__WEBPACK_IMPORTED_MODULE_1__.useEffect)(function () {
+ monitorFormPreviewRender({
+ key: _iframe_integratedMessages__WEBPACK_IMPORTED_MODULE_6__.ProxyMessages.TrackMeetingPreviewRender,
+ payload: {
+ origin: origin
+ }
+ });
+ }, [origin]);
+ return !isBackgroundAppReady ? (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_Common_LoadingBlock__WEBPACK_IMPORTED_MODULE_7__["default"], {}) : (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsxs)(react__WEBPACK_IMPORTED_MODULE_1__.Fragment, {
+ children: [(isSelected || !url) && (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_MeetingController__WEBPACK_IMPORTED_MODULE_2__["default"], {
+ url: url,
+ handleChange: handleChange
+ }), preview && url && (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_PreviewMeeting__WEBPACK_IMPORTED_MODULE_3__["default"], {
+ url: url
+ })]
+ });
+}
+
+function MeetingsEditContainer(props) {
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_iframe_useBackgroundApp__WEBPACK_IMPORTED_MODULE_4__.BackgroudAppContext.Provider, {
+ value: _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_5__.refreshToken && (0,_utils_backgroundAppUtils__WEBPACK_IMPORTED_MODULE_8__.getOrCreateBackgroundApp)(_constants_leadinConfig__WEBPACK_IMPORTED_MODULE_5__.refreshToken),
+ children: (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(MeetingEdit, _objectSpread({}, props))
+ });
+}
+
+/***/ }),
+
+/***/ "./scripts/shared/Meeting/MeetingSelector.tsx":
+/*!****************************************************!*\
+ !*** ./scripts/shared/Meeting/MeetingSelector.tsx ***!
+ \****************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ MeetingSelector)
+/* harmony export */ });
+/* harmony import */ var react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react/jsx-runtime */ "./node_modules/react/jsx-runtime.js");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! react */ "react");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(react__WEBPACK_IMPORTED_MODULE_1__);
+/* harmony import */ var _Common_AsyncSelect__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ../Common/AsyncSelect */ "./scripts/shared/Common/AsyncSelect.tsx");
+/* harmony import */ var _UIComponents_UISpacer__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ../UIComponents/UISpacer */ "./scripts/shared/UIComponents/UISpacer.ts");
+/* harmony import */ var _wordpress_i18n__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__(/*! @wordpress/i18n */ "@wordpress/i18n");
+/* harmony import */ var _wordpress_i18n__WEBPACK_IMPORTED_MODULE_4___default = /*#__PURE__*/__webpack_require__.n(_wordpress_i18n__WEBPACK_IMPORTED_MODULE_4__);
+
+
+
+
+
+function MeetingSelector(_ref) {
+ var options = _ref.options,
+ onChange = _ref.onChange,
+ value = _ref.value;
+ var optionsWrapper = [{
+ label: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_4__.__)('Meeting name', 'leadin'),
+ options: options
+ }];
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsxs)(react__WEBPACK_IMPORTED_MODULE_1__.Fragment, {
+ children: [(0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_UIComponents_UISpacer__WEBPACK_IMPORTED_MODULE_3__["default"], {}), (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)("p", {
+ "data-test-id": "leadin-meeting-select",
+ children: (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)("b", {
+ children: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_4__.__)('Select a meeting scheduling page', 'leadin')
+ })
+ }), (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_Common_AsyncSelect__WEBPACK_IMPORTED_MODULE_2__["default"], {
+ defaultOptions: optionsWrapper,
+ onChange: onChange,
+ placeholder: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_4__.__)('Select a meeting', 'leadin'),
+ value: value
+ })]
+ });
+}
+
+/***/ }),
+
+/***/ "./scripts/shared/Meeting/MeetingWarning.tsx":
+/*!***************************************************!*\
+ !*** ./scripts/shared/Meeting/MeetingWarning.tsx ***!
+ \***************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ MeetingWarning)
+/* harmony export */ });
+/* harmony import */ var react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react/jsx-runtime */ "./node_modules/react/jsx-runtime.js");
+/* harmony import */ var _UIComponents_UIAlert__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! ../UIComponents/UIAlert */ "./scripts/shared/UIComponents/UIAlert.tsx");
+/* harmony import */ var _UIComponents_UIButton__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ../UIComponents/UIButton */ "./scripts/shared/UIComponents/UIButton.ts");
+/* harmony import */ var _constants__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ./constants */ "./scripts/shared/Meeting/constants.ts");
+/* harmony import */ var _wordpress_i18n__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__(/*! @wordpress/i18n */ "@wordpress/i18n");
+/* harmony import */ var _wordpress_i18n__WEBPACK_IMPORTED_MODULE_4___default = /*#__PURE__*/__webpack_require__.n(_wordpress_i18n__WEBPACK_IMPORTED_MODULE_4__);
+
+
+
+
+
+function MeetingWarning(_ref) {
+ var status = _ref.status,
+ onConnectCalendar = _ref.onConnectCalendar;
+ var isMeetingOwner = status === _constants__WEBPACK_IMPORTED_MODULE_3__.CURRENT_USER_CALENDAR_MISSING;
+ var titleText = isMeetingOwner ? (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_4__.__)('Your calendar is not connected', 'leadin') : (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_4__.__)('Calendar is not connected', 'leadin');
+ var titleMessage = isMeetingOwner ? (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_4__.__)('Please connect your calendar to activate your scheduling pages', 'leadin') : (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_4__.__)('Make sure that everybody in this meeting has connected their calendar from the Meetings page in HubSpot', 'leadin');
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_UIComponents_UIAlert__WEBPACK_IMPORTED_MODULE_1__["default"], {
+ titleText: titleText,
+ titleMessage: titleMessage,
+ children: isMeetingOwner && (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_UIComponents_UIButton__WEBPACK_IMPORTED_MODULE_2__["default"], {
+ use: "tertiary",
+ id: "meetings-connect-calendar",
+ onClick: onConnectCalendar,
+ children: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_4__.__)('Connect calendar', 'leadin')
+ })
+ });
+}
+
+/***/ }),
+
+/***/ "./scripts/shared/Meeting/PreviewMeeting.tsx":
+/*!***************************************************!*\
+ !*** ./scripts/shared/Meeting/PreviewMeeting.tsx ***!
+ \***************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ PreviewForm)
+/* harmony export */ });
+/* harmony import */ var react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react/jsx-runtime */ "./node_modules/react/jsx-runtime.js");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! react */ "react");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(react__WEBPACK_IMPORTED_MODULE_1__);
+/* harmony import */ var _UIComponents_UIOverlay__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ../UIComponents/UIOverlay */ "./scripts/shared/UIComponents/UIOverlay.ts");
+/* harmony import */ var _hooks_useMeetingsScript__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ./hooks/useMeetingsScript */ "./scripts/shared/Meeting/hooks/useMeetingsScript.ts");
+
+
+
+
+function PreviewForm(_ref) {
+ var url = _ref.url;
+ var ready = (0,_hooks_useMeetingsScript__WEBPACK_IMPORTED_MODULE_3__["default"])();
+ var inputEl = (0,react__WEBPACK_IMPORTED_MODULE_1__.useRef)(null);
+ (0,react__WEBPACK_IMPORTED_MODULE_1__.useEffect)(function () {
+ if (!ready) {
+ return;
+ }
+
+ if (inputEl.current) {
+ inputEl.current.innerHTML = '';
+ var container = document.createElement('div');
+ container.dataset.src = "".concat(url, "?embed=true");
+ container.classList.add('meetings-iframe-container');
+ inputEl.current.appendChild(container);
+ var embedScript = document.createElement('script');
+ embedScript.innerHTML = 'hbspt.meetings.create(".meetings-iframe-container");';
+ inputEl.current.appendChild(embedScript);
+ }
+ }, [url, ready, inputEl]);
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(react__WEBPACK_IMPORTED_MODULE_1__.Fragment, {
+ children: url && (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_UIComponents_UIOverlay__WEBPACK_IMPORTED_MODULE_2__["default"], {
+ ref: inputEl
+ })
+ });
+}
+
+/***/ }),
+
+/***/ "./scripts/shared/Meeting/constants.ts":
+/*!*********************************************!*\
+ !*** ./scripts/shared/Meeting/constants.ts ***!
+ \*********************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "CURRENT_USER_CALENDAR_MISSING": () => (/* binding */ CURRENT_USER_CALENDAR_MISSING),
+/* harmony export */ "OTHER_USER_CALENDAR_MISSING": () => (/* binding */ OTHER_USER_CALENDAR_MISSING)
+/* harmony export */ });
+var OTHER_USER_CALENDAR_MISSING = 'OTHER_USER_CALENDAR_MISSING';
+var CURRENT_USER_CALENDAR_MISSING = 'CURRENT_USER_CALENDAR_MISSING';
+
+/***/ }),
+
+/***/ "./scripts/shared/Meeting/hooks/useCurrentUserFetch.ts":
+/*!*************************************************************!*\
+ !*** ./scripts/shared/Meeting/hooks/useCurrentUserFetch.ts ***!
+ \*************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ useCurrentUserFetch)
+/* harmony export */ });
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react */ "react");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(react__WEBPACK_IMPORTED_MODULE_0__);
+/* harmony import */ var _iframe_useBackgroundApp__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! ../../../iframe/useBackgroundApp */ "./scripts/iframe/useBackgroundApp.ts");
+/* harmony import */ var _enums_loadState__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ../../enums/loadState */ "./scripts/shared/enums/loadState.ts");
+/* harmony import */ var _iframe_integratedMessages__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ../../../iframe/integratedMessages */ "./scripts/iframe/integratedMessages/index.ts");
+function _slicedToArray(arr, i) { return _arrayWithHoles(arr) || _iterableToArrayLimit(arr, i) || _unsupportedIterableToArray(arr, i) || _nonIterableRest(); }
+
+function _nonIterableRest() { throw new TypeError("Invalid attempt to destructure non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method."); }
+
+function _unsupportedIterableToArray(o, minLen) { if (!o) return; if (typeof o === "string") return _arrayLikeToArray(o, minLen); var n = Object.prototype.toString.call(o).slice(8, -1); if (n === "Object" && o.constructor) n = o.constructor.name; if (n === "Map" || n === "Set") return Array.from(o); if (n === "Arguments" || /^(?:Ui|I)nt(?:8|16|32)(?:Clamped)?Array$/.test(n)) return _arrayLikeToArray(o, minLen); }
+
+function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len = arr.length; for (var i = 0, arr2 = new Array(len); i < len; i++) { arr2[i] = arr[i]; } return arr2; }
+
+function _iterableToArrayLimit(arr, i) { var _i = arr == null ? null : typeof Symbol !== "undefined" && arr[Symbol.iterator] || arr["@@iterator"]; if (_i == null) return; var _arr = []; var _n = true; var _d = false; var _s, _e; try { for (_i = _i.call(arr); !(_n = (_s = _i.next()).done); _n = true) { _arr.push(_s.value); if (i && _arr.length === i) break; } } catch (err) { _d = true; _e = err; } finally { try { if (!_n && _i["return"] != null) _i["return"](); } finally { if (_d) throw _e; } } return _arr; }
+
+function _arrayWithHoles(arr) { if (Array.isArray(arr)) return arr; }
+
+
+
+
+
+var user = null;
+function useCurrentUserFetch() {
+ var proxy = (0,_iframe_useBackgroundApp__WEBPACK_IMPORTED_MODULE_1__.usePostAsyncBackgroundMessage)();
+
+ var _useState = (0,react__WEBPACK_IMPORTED_MODULE_0__.useState)(_enums_loadState__WEBPACK_IMPORTED_MODULE_2__["default"].NotLoaded),
+ _useState2 = _slicedToArray(_useState, 2),
+ loadState = _useState2[0],
+ setLoadState = _useState2[1];
+
+ var _useState3 = (0,react__WEBPACK_IMPORTED_MODULE_0__.useState)(null),
+ _useState4 = _slicedToArray(_useState3, 2),
+ error = _useState4[0],
+ setError = _useState4[1];
+
+ var createUser = function createUser() {
+ if (!user) {
+ setLoadState(_enums_loadState__WEBPACK_IMPORTED_MODULE_2__["default"].NotLoaded);
+ }
+ };
+
+ var reload = function reload() {
+ user = null;
+ setLoadState(_enums_loadState__WEBPACK_IMPORTED_MODULE_2__["default"].NotLoaded);
+ setError(null);
+ };
+
+ (0,react__WEBPACK_IMPORTED_MODULE_0__.useEffect)(function () {
+ if (loadState === _enums_loadState__WEBPACK_IMPORTED_MODULE_2__["default"].NotLoaded && !user) {
+ setLoadState(_enums_loadState__WEBPACK_IMPORTED_MODULE_2__["default"].Loading);
+ proxy({
+ key: _iframe_integratedMessages__WEBPACK_IMPORTED_MODULE_3__.ProxyMessages.FetchOrCreateMeetingUser
+ }).then(function (data) {
+ user = data;
+ setLoadState(_enums_loadState__WEBPACK_IMPORTED_MODULE_2__["default"].Idle);
+ })["catch"](function (err) {
+ setError(err);
+ setLoadState(_enums_loadState__WEBPACK_IMPORTED_MODULE_2__["default"].Failed);
+ });
+ }
+ }, [loadState]);
+ return {
+ user: user,
+ loadUserState: loadState,
+ error: error,
+ createUser: createUser,
+ reload: reload
+ };
+}
+
+/***/ }),
+
+/***/ "./scripts/shared/Meeting/hooks/useMeetings.ts":
+/*!*****************************************************!*\
+ !*** ./scripts/shared/Meeting/hooks/useMeetings.ts ***!
+ \*****************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ useMeetings),
+/* harmony export */ "useSelectedMeeting": () => (/* binding */ useSelectedMeeting),
+/* harmony export */ "useSelectedMeetingCalendar": () => (/* binding */ useSelectedMeetingCalendar)
+/* harmony export */ });
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react */ "react");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(react__WEBPACK_IMPORTED_MODULE_0__);
+/* harmony import */ var _wordpress_i18n__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! @wordpress/i18n */ "@wordpress/i18n");
+/* harmony import */ var _wordpress_i18n__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(_wordpress_i18n__WEBPACK_IMPORTED_MODULE_1__);
+/* harmony import */ var _constants__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ../constants */ "./scripts/shared/Meeting/constants.ts");
+/* harmony import */ var _useMeetingsFetch__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ./useMeetingsFetch */ "./scripts/shared/Meeting/hooks/useMeetingsFetch.ts");
+/* harmony import */ var _useCurrentUserFetch__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__(/*! ./useCurrentUserFetch */ "./scripts/shared/Meeting/hooks/useCurrentUserFetch.ts");
+/* harmony import */ var _enums_loadState__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__(/*! ../../enums/loadState */ "./scripts/shared/enums/loadState.ts");
+/* harmony import */ var _iframe_useBackgroundApp__WEBPACK_IMPORTED_MODULE_6__ = __webpack_require__(/*! ../../../iframe/useBackgroundApp */ "./scripts/iframe/useBackgroundApp.ts");
+/* harmony import */ var _iframe_integratedMessages__WEBPACK_IMPORTED_MODULE_7__ = __webpack_require__(/*! ../../../iframe/integratedMessages */ "./scripts/iframe/integratedMessages/index.ts");
+function ownKeys(object, enumerableOnly) { var keys = Object.keys(object); if (Object.getOwnPropertySymbols) { var symbols = Object.getOwnPropertySymbols(object); enumerableOnly && (symbols = symbols.filter(function (sym) { return Object.getOwnPropertyDescriptor(object, sym).enumerable; })), keys.push.apply(keys, symbols); } return keys; }
+
+function _objectSpread(target) { for (var i = 1; i < arguments.length; i++) { var source = null != arguments[i] ? arguments[i] : {}; i % 2 ? ownKeys(Object(source), !0).forEach(function (key) { _defineProperty(target, key, source[key]); }) : Object.getOwnPropertyDescriptors ? Object.defineProperties(target, Object.getOwnPropertyDescriptors(source)) : ownKeys(Object(source)).forEach(function (key) { Object.defineProperty(target, key, Object.getOwnPropertyDescriptor(source, key)); }); } return target; }
+
+function _defineProperty(obj, key, value) { if (key in obj) { Object.defineProperty(obj, key, { value: value, enumerable: true, configurable: true, writable: true }); } else { obj[key] = value; } return obj; }
+
+function _slicedToArray(arr, i) { return _arrayWithHoles(arr) || _iterableToArrayLimit(arr, i) || _unsupportedIterableToArray(arr, i) || _nonIterableRest(); }
+
+function _nonIterableRest() { throw new TypeError("Invalid attempt to destructure non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method."); }
+
+function _unsupportedIterableToArray(o, minLen) { if (!o) return; if (typeof o === "string") return _arrayLikeToArray(o, minLen); var n = Object.prototype.toString.call(o).slice(8, -1); if (n === "Object" && o.constructor) n = o.constructor.name; if (n === "Map" || n === "Set") return Array.from(o); if (n === "Arguments" || /^(?:Ui|I)nt(?:8|16|32)(?:Clamped)?Array$/.test(n)) return _arrayLikeToArray(o, minLen); }
+
+function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len = arr.length; for (var i = 0, arr2 = new Array(len); i < len; i++) { arr2[i] = arr[i]; } return arr2; }
+
+function _iterableToArrayLimit(arr, i) { var _i = arr == null ? null : typeof Symbol !== "undefined" && arr[Symbol.iterator] || arr["@@iterator"]; if (_i == null) return; var _arr = []; var _n = true; var _d = false; var _s, _e; try { for (_i = _i.call(arr); !(_n = (_s = _i.next()).done); _n = true) { _arr.push(_s.value); if (i && _arr.length === i) break; } } catch (err) { _d = true; _e = err; } finally { try { if (!_n && _i["return"] != null) _i["return"](); } finally { if (_d) throw _e; } } return _arr; }
+
+function _arrayWithHoles(arr) { if (Array.isArray(arr)) return arr; }
+
+
+
+
+
+
+
+
+
+
+function getDefaultMeetingName(meeting, currentUser, meetingUsers) {
+ var _meeting$meetingsUser = _slicedToArray(meeting.meetingsUserIds, 1),
+ meetingOwnerId = _meeting$meetingsUser[0];
+
+ var result = (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_1__.__)('Default', 'leadin');
+
+ if (currentUser && meetingOwnerId !== currentUser.id && meetingUsers[meetingOwnerId]) {
+ var user = meetingUsers[meetingOwnerId];
+ result += " (".concat(user.userProfile.fullName, ")");
+ }
+
+ return result;
+}
+
+function hasCalendarObject(user) {
+ return user && user.meetingsUserBlob && user.meetingsUserBlob.calendarSettings && user.meetingsUserBlob.calendarSettings.email;
+}
+
+function useMeetings() {
+ var proxy = (0,_iframe_useBackgroundApp__WEBPACK_IMPORTED_MODULE_6__.usePostAsyncBackgroundMessage)();
+
+ var _useMeetingsFetch = (0,_useMeetingsFetch__WEBPACK_IMPORTED_MODULE_3__["default"])(),
+ meetings = _useMeetingsFetch.meetings,
+ meetingUsers = _useMeetingsFetch.meetingUsers,
+ meetingsError = _useMeetingsFetch.error,
+ loadMeetingsState = _useMeetingsFetch.loadMeetingsState,
+ reloadMeetings = _useMeetingsFetch.reload;
+
+ var _useCurrentUserFetch = (0,_useCurrentUserFetch__WEBPACK_IMPORTED_MODULE_4__["default"])(),
+ currentUser = _useCurrentUserFetch.user,
+ userError = _useCurrentUserFetch.error,
+ loadUserState = _useCurrentUserFetch.loadUserState,
+ reloadUser = _useCurrentUserFetch.reload;
+
+ var reload = (0,react__WEBPACK_IMPORTED_MODULE_0__.useCallback)(function () {
+ reloadUser();
+ reloadMeetings();
+ }, [reloadUser, reloadMeetings]);
+
+ var connectCalendar = function connectCalendar() {
+ return proxy({
+ key: _iframe_integratedMessages__WEBPACK_IMPORTED_MODULE_7__.ProxyMessages.ConnectMeetingsCalendar
+ });
+ };
+
+ return {
+ mappedMeetings: meetings.map(function (meet) {
+ return {
+ label: meet.name || getDefaultMeetingName(meet, currentUser, meetingUsers),
+ value: meet.link
+ };
+ }),
+ meetings: meetings,
+ meetingUsers: meetingUsers,
+ currentUser: currentUser,
+ error: meetingsError || userError,
+ loading: loadMeetingsState == _enums_loadState__WEBPACK_IMPORTED_MODULE_5__["default"].Loading || loadUserState === _enums_loadState__WEBPACK_IMPORTED_MODULE_5__["default"].Loading,
+ reload: reload,
+ connectCalendar: connectCalendar
+ };
+}
+function useSelectedMeeting(url) {
+ var _useMeetings = useMeetings(),
+ meetings = _useMeetings.mappedMeetings;
+
+ var option = meetings.find(function (_ref) {
+ var value = _ref.value;
+ return value === url;
+ });
+ return option;
+}
+function useSelectedMeetingCalendar(url) {
+ var _useMeetings2 = useMeetings(),
+ meetings = _useMeetings2.meetings,
+ meetingUsers = _useMeetings2.meetingUsers,
+ currentUser = _useMeetings2.currentUser;
+
+ var meeting = meetings.find(function (meet) {
+ return meet.link === url;
+ });
+ var mappedMeetingUsersId = meetingUsers.reduce(function (p, c) {
+ return _objectSpread(_objectSpread({}, p), {}, _defineProperty({}, c.id, c));
+ }, {});
+
+ if (!meeting) {
+ return null;
+ } else {
+ var meetingsUserIds = meeting.meetingsUserIds;
+
+ if (currentUser && meetingsUserIds.includes(currentUser.id) && !hasCalendarObject(currentUser)) {
+ return _constants__WEBPACK_IMPORTED_MODULE_2__.CURRENT_USER_CALENDAR_MISSING;
+ } else if (meetingsUserIds.map(function (id) {
+ return mappedMeetingUsersId[id];
+ }).some(function (user) {
+ return !hasCalendarObject(user);
+ })) {
+ return _constants__WEBPACK_IMPORTED_MODULE_2__.OTHER_USER_CALENDAR_MISSING;
+ } else {
+ return null;
+ }
+ }
+}
+
+/***/ }),
+
+/***/ "./scripts/shared/Meeting/hooks/useMeetingsFetch.ts":
+/*!**********************************************************!*\
+ !*** ./scripts/shared/Meeting/hooks/useMeetingsFetch.ts ***!
+ \**********************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ useMeetingsFetch)
+/* harmony export */ });
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react */ "react");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(react__WEBPACK_IMPORTED_MODULE_0__);
+/* harmony import */ var _iframe_useBackgroundApp__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! ../../../iframe/useBackgroundApp */ "./scripts/iframe/useBackgroundApp.ts");
+/* harmony import */ var _enums_loadState__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ../../enums/loadState */ "./scripts/shared/enums/loadState.ts");
+/* harmony import */ var _iframe_integratedMessages__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ../../../iframe/integratedMessages */ "./scripts/iframe/integratedMessages/index.ts");
+function _slicedToArray(arr, i) { return _arrayWithHoles(arr) || _iterableToArrayLimit(arr, i) || _unsupportedIterableToArray(arr, i) || _nonIterableRest(); }
+
+function _nonIterableRest() { throw new TypeError("Invalid attempt to destructure non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method."); }
+
+function _unsupportedIterableToArray(o, minLen) { if (!o) return; if (typeof o === "string") return _arrayLikeToArray(o, minLen); var n = Object.prototype.toString.call(o).slice(8, -1); if (n === "Object" && o.constructor) n = o.constructor.name; if (n === "Map" || n === "Set") return Array.from(o); if (n === "Arguments" || /^(?:Ui|I)nt(?:8|16|32)(?:Clamped)?Array$/.test(n)) return _arrayLikeToArray(o, minLen); }
+
+function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len = arr.length; for (var i = 0, arr2 = new Array(len); i < len; i++) { arr2[i] = arr[i]; } return arr2; }
+
+function _iterableToArrayLimit(arr, i) { var _i = arr == null ? null : typeof Symbol !== "undefined" && arr[Symbol.iterator] || arr["@@iterator"]; if (_i == null) return; var _arr = []; var _n = true; var _d = false; var _s, _e; try { for (_i = _i.call(arr); !(_n = (_s = _i.next()).done); _n = true) { _arr.push(_s.value); if (i && _arr.length === i) break; } } catch (err) { _d = true; _e = err; } finally { try { if (!_n && _i["return"] != null) _i["return"](); } finally { if (_d) throw _e; } } return _arr; }
+
+function _arrayWithHoles(arr) { if (Array.isArray(arr)) return arr; }
+
+
+
+
+
+var meetings = [];
+var meetingUsers = [];
+function useMeetingsFetch() {
+ var proxy = (0,_iframe_useBackgroundApp__WEBPACK_IMPORTED_MODULE_1__.usePostAsyncBackgroundMessage)();
+
+ var _useState = (0,react__WEBPACK_IMPORTED_MODULE_0__.useState)(_enums_loadState__WEBPACK_IMPORTED_MODULE_2__["default"].NotLoaded),
+ _useState2 = _slicedToArray(_useState, 2),
+ loadState = _useState2[0],
+ setLoadState = _useState2[1];
+
+ var _useState3 = (0,react__WEBPACK_IMPORTED_MODULE_0__.useState)(null),
+ _useState4 = _slicedToArray(_useState3, 2),
+ error = _useState4[0],
+ setError = _useState4[1];
+
+ var reload = function reload() {
+ meetings = [];
+ setError(null);
+ setLoadState(_enums_loadState__WEBPACK_IMPORTED_MODULE_2__["default"].NotLoaded);
+ };
+
+ (0,react__WEBPACK_IMPORTED_MODULE_0__.useEffect)(function () {
+ if (loadState === _enums_loadState__WEBPACK_IMPORTED_MODULE_2__["default"].NotLoaded && meetings.length === 0) {
+ setLoadState(_enums_loadState__WEBPACK_IMPORTED_MODULE_2__["default"].Loading);
+ proxy({
+ key: _iframe_integratedMessages__WEBPACK_IMPORTED_MODULE_3__.ProxyMessages.FetchMeetingsAndUsers
+ }).then(function (data) {
+ setLoadState(_enums_loadState__WEBPACK_IMPORTED_MODULE_2__["default"].Loaded);
+ meetings = data && data.meetingLinks;
+ meetingUsers = data && data.meetingUsers;
+ })["catch"](function (e) {
+ setError(e);
+ setLoadState(_enums_loadState__WEBPACK_IMPORTED_MODULE_2__["default"].Failed);
+ });
+ }
+ }, [loadState]);
+ return {
+ meetings: meetings,
+ meetingUsers: meetingUsers,
+ loadMeetingsState: loadState,
+ error: error,
+ reload: reload
+ };
+}
+
+/***/ }),
+
+/***/ "./scripts/shared/Meeting/hooks/useMeetingsScript.ts":
+/*!***********************************************************!*\
+ !*** ./scripts/shared/Meeting/hooks/useMeetingsScript.ts ***!
+ \***********************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ useMeetingsScript)
+/* harmony export */ });
+/* harmony import */ var jquery__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! jquery */ "jquery");
+/* harmony import */ var jquery__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(jquery__WEBPACK_IMPORTED_MODULE_0__);
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! react */ "react");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(react__WEBPACK_IMPORTED_MODULE_1__);
+/* harmony import */ var _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ../../../constants/leadinConfig */ "./scripts/constants/leadinConfig.ts");
+/* harmony import */ var _lib_Raven__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ../../../lib/Raven */ "./scripts/lib/Raven.ts");
+function _slicedToArray(arr, i) { return _arrayWithHoles(arr) || _iterableToArrayLimit(arr, i) || _unsupportedIterableToArray(arr, i) || _nonIterableRest(); }
+
+function _nonIterableRest() { throw new TypeError("Invalid attempt to destructure non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method."); }
+
+function _unsupportedIterableToArray(o, minLen) { if (!o) return; if (typeof o === "string") return _arrayLikeToArray(o, minLen); var n = Object.prototype.toString.call(o).slice(8, -1); if (n === "Object" && o.constructor) n = o.constructor.name; if (n === "Map" || n === "Set") return Array.from(o); if (n === "Arguments" || /^(?:Ui|I)nt(?:8|16|32)(?:Clamped)?Array$/.test(n)) return _arrayLikeToArray(o, minLen); }
+
+function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len = arr.length; for (var i = 0, arr2 = new Array(len); i < len; i++) { arr2[i] = arr[i]; } return arr2; }
+
+function _iterableToArrayLimit(arr, i) { var _i = arr == null ? null : typeof Symbol !== "undefined" && arr[Symbol.iterator] || arr["@@iterator"]; if (_i == null) return; var _arr = []; var _n = true; var _d = false; var _s, _e; try { for (_i = _i.call(arr); !(_n = (_s = _i.next()).done); _n = true) { _arr.push(_s.value); if (i && _arr.length === i) break; } } catch (err) { _d = true; _e = err; } finally { try { if (!_n && _i["return"] != null) _i["return"](); } finally { if (_d) throw _e; } } return _arr; }
+
+function _arrayWithHoles(arr) { if (Array.isArray(arr)) return arr; }
+
+
+
+
+
+var promise;
+
+function loadMeetingsScript() {
+ if (!promise) {
+ promise = new Promise(function (resolve, reject) {
+ return jquery__WEBPACK_IMPORTED_MODULE_0___default().getScript(_constants_leadinConfig__WEBPACK_IMPORTED_MODULE_2__.meetingsScript).done(resolve).fail(reject);
+ });
+ }
+
+ return promise;
+}
+
+function useMeetingsScript() {
+ var _useState = (0,react__WEBPACK_IMPORTED_MODULE_1__.useState)(false),
+ _useState2 = _slicedToArray(_useState, 2),
+ ready = _useState2[0],
+ setReady = _useState2[1];
+
+ (0,react__WEBPACK_IMPORTED_MODULE_1__.useEffect)(function () {
+ loadMeetingsScript().then(function () {
+ return setReady(true);
+ })["catch"](function (error) {
+ return _lib_Raven__WEBPACK_IMPORTED_MODULE_3__["default"].captureException(error);
+ });
+ }, []);
+ return ready;
+}
+
+/***/ }),
+
+/***/ "./scripts/shared/UIComponents/UIAlert.tsx":
+/*!*************************************************!*\
+ !*** ./scripts/shared/UIComponents/UIAlert.tsx ***!
+ \*************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ UIAlert)
+/* harmony export */ });
+/* harmony import */ var react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react/jsx-runtime */ "./node_modules/react/jsx-runtime.js");
+/* harmony import */ var _linaria_react__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! @linaria/react */ "./node_modules/@linaria/react/dist/index.mjs");
+
+
+var AlertContainer = /*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_1__.styled)('div')({
+ name: "AlertContainer",
+ "class": "a1h8m4fo",
+ propsAsIs: false
+});
+var Title = /*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_1__.styled)('p')({
+ name: "Title",
+ "class": "tyndzxk",
+ propsAsIs: false
+});
+var Message = /*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_1__.styled)('p')({
+ name: "Message",
+ "class": "m1m9sbk4",
+ propsAsIs: false
+});
+var MessageContainer = /*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_1__.styled)('div')({
+ name: "MessageContainer",
+ "class": "mg5o421",
+ propsAsIs: false
+});
+function UIAlert(_ref) {
+ var titleText = _ref.titleText,
+ titleMessage = _ref.titleMessage,
+ children = _ref.children;
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsxs)(AlertContainer, {
+ children: [(0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsxs)(MessageContainer, {
+ children: [(0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(Title, {
+ children: titleText
+ }), (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(Message, {
+ children: titleMessage
+ })]
+ }), children]
+ });
+}
+
+__webpack_require__(/*! ./UIAlert.linaria.css!=!../../../node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./UIAlert.tsx */ "./scripts/shared/UIComponents/UIAlert.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/UIComponents/UIAlert.tsx");
+
+/***/ }),
+
+/***/ "./scripts/shared/UIComponents/UIButton.ts":
+/*!*************************************************!*\
+ !*** ./scripts/shared/UIComponents/UIButton.ts ***!
+ \*************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (__WEBPACK_DEFAULT_EXPORT__)
+/* harmony export */ });
+/* harmony import */ var _linaria_react__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! @linaria/react */ "./node_modules/@linaria/react/dist/index.mjs");
+/* harmony import */ var _colors__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! ./colors */ "./scripts/shared/UIComponents/colors.ts");
+
+
+
+var _exp2 = /*#__PURE__*/function _exp2() {
+ return function (props) {
+ return props.use === 'tertiary' ? _colors__WEBPACK_IMPORTED_MODULE_0__.HEFFALUMP : _colors__WEBPACK_IMPORTED_MODULE_0__.LORAX;
+ };
+};
+
+/* harmony default export */ const __WEBPACK_DEFAULT_EXPORT__ = (/*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_1__.styled)('button')({
+ name: "UIButton0",
+ "class": "ug152ch",
+ propsAsIs: false,
+ vars: {
+ "ug152ch-0": [_exp2()]
+ }
+}));
+
+__webpack_require__(/*! ./UIButton.linaria.css!=!../../../node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./UIButton.ts */ "./scripts/shared/UIComponents/UIButton.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/UIComponents/UIButton.ts");
+
+/***/ }),
+
+/***/ "./scripts/shared/UIComponents/UIContainer.ts":
+/*!****************************************************!*\
+ !*** ./scripts/shared/UIComponents/UIContainer.ts ***!
+ \****************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (__WEBPACK_DEFAULT_EXPORT__)
+/* harmony export */ });
+/* harmony import */ var _linaria_react__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! @linaria/react */ "./node_modules/@linaria/react/dist/index.mjs");
+
+
+var _exp = /*#__PURE__*/function _exp() {
+ return function (props) {
+ return props.textAlign ? props.textAlign : 'inherit';
+ };
+};
+
+/* harmony default export */ const __WEBPACK_DEFAULT_EXPORT__ = (/*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_0__.styled)('div')({
+ name: "UIContainer0",
+ "class": "ua13n1c",
+ propsAsIs: false,
+ vars: {
+ "ua13n1c-0": [_exp()]
+ }
+}));
+
+__webpack_require__(/*! ./UIContainer.linaria.css!=!../../../node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./UIContainer.ts */ "./scripts/shared/UIComponents/UIContainer.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/UIComponents/UIContainer.ts");
+
+/***/ }),
+
+/***/ "./scripts/shared/UIComponents/UIOverlay.ts":
+/*!**************************************************!*\
+ !*** ./scripts/shared/UIComponents/UIOverlay.ts ***!
+ \**************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (__WEBPACK_DEFAULT_EXPORT__)
+/* harmony export */ });
+/* harmony import */ var _linaria_react__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! @linaria/react */ "./node_modules/@linaria/react/dist/index.mjs");
+
+/* harmony default export */ const __WEBPACK_DEFAULT_EXPORT__ = (/*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_0__.styled)('div')({
+ name: "UIOverlay0",
+ "class": "u1q7a48k",
+ propsAsIs: false
+}));
+
+__webpack_require__(/*! ./UIOverlay.linaria.css!=!../../../node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./UIOverlay.ts */ "./scripts/shared/UIComponents/UIOverlay.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/UIComponents/UIOverlay.ts");
+
+/***/ }),
+
+/***/ "./scripts/shared/UIComponents/UISpacer.ts":
+/*!*************************************************!*\
+ !*** ./scripts/shared/UIComponents/UISpacer.ts ***!
+ \*************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (__WEBPACK_DEFAULT_EXPORT__)
+/* harmony export */ });
+/* harmony import */ var _linaria_react__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! @linaria/react */ "./node_modules/@linaria/react/dist/index.mjs");
+
+/* harmony default export */ const __WEBPACK_DEFAULT_EXPORT__ = (/*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_0__.styled)('div')({
+ name: "UISpacer0",
+ "class": "u3qxofx",
+ propsAsIs: false
+}));
+
+__webpack_require__(/*! ./UISpacer.linaria.css!=!../../../node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./UISpacer.ts */ "./scripts/shared/UIComponents/UISpacer.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/UIComponents/UISpacer.ts");
+
+/***/ }),
+
+/***/ "./scripts/shared/UIComponents/UISpinner.tsx":
+/*!***************************************************!*\
+ !*** ./scripts/shared/UIComponents/UISpinner.tsx ***!
+ \***************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ UISpinner)
+/* harmony export */ });
+/* harmony import */ var react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react/jsx-runtime */ "./node_modules/react/jsx-runtime.js");
+/* harmony import */ var _linaria_react__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! @linaria/react */ "./node_modules/@linaria/react/dist/index.mjs");
+/* harmony import */ var _colors__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! ./colors */ "./scripts/shared/UIComponents/colors.ts");
+
+
+
+var SpinnerOuter = /*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_2__.styled)('div')({
+ name: "SpinnerOuter",
+ "class": "sxa9zrc",
+ propsAsIs: false
+});
+var SpinnerInner = /*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_2__.styled)('div')({
+ name: "SpinnerInner",
+ "class": "s14430wa",
+ propsAsIs: false
+});
+
+var _exp = /*#__PURE__*/function _exp() {
+ return function (props) {
+ return props.color;
+ };
+};
+
+var Circle = /*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_2__.styled)('circle')({
+ name: "Circle",
+ "class": "ct87ghk",
+ propsAsIs: true,
+ vars: {
+ "ct87ghk-0": [_exp()]
+ }
+});
+
+var _exp2 = /*#__PURE__*/function _exp2() {
+ return function (props) {
+ return props.color;
+ };
+};
+
+var AnimatedCircle = /*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_2__.styled)('circle')({
+ name: "AnimatedCircle",
+ "class": "avili0h",
+ propsAsIs: true,
+ vars: {
+ "avili0h-0": [_exp2()]
+ }
+});
+function UISpinner(_ref) {
+ var _ref$size = _ref.size,
+ size = _ref$size === void 0 ? 20 : _ref$size;
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(SpinnerOuter, {
+ children: (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(SpinnerInner, {
+ children: (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsxs)("svg", {
+ height: size,
+ width: size,
+ viewBox: "0 0 50 50",
+ children: [(0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(Circle, {
+ color: _colors__WEBPACK_IMPORTED_MODULE_1__.CALYPSO_MEDIUM,
+ cx: "25",
+ cy: "25",
+ r: "22.5"
+ }), (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(AnimatedCircle, {
+ color: _colors__WEBPACK_IMPORTED_MODULE_1__.CALYPSO,
+ cx: "25",
+ cy: "25",
+ r: "22.5"
+ })]
+ })
+ })
+ });
+}
+
+__webpack_require__(/*! ./UISpinner.linaria.css!=!../../../node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./UISpinner.tsx */ "./scripts/shared/UIComponents/UISpinner.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/UIComponents/UISpinner.tsx");
+
+/***/ }),
+
+/***/ "./scripts/shared/UIComponents/colors.ts":
+/*!***********************************************!*\
+ !*** ./scripts/shared/UIComponents/colors.ts ***!
+ \***********************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "CALYPSO": () => (/* binding */ CALYPSO),
+/* harmony export */ "CALYPSO_LIGHT": () => (/* binding */ CALYPSO_LIGHT),
+/* harmony export */ "CALYPSO_MEDIUM": () => (/* binding */ CALYPSO_MEDIUM),
+/* harmony export */ "HEFFALUMP": () => (/* binding */ HEFFALUMP),
+/* harmony export */ "LORAX": () => (/* binding */ LORAX),
+/* harmony export */ "MARIGOLD_LIGHT": () => (/* binding */ MARIGOLD_LIGHT),
+/* harmony export */ "MARIGOLD_MEDIUM": () => (/* binding */ MARIGOLD_MEDIUM),
+/* harmony export */ "OBSIDIAN": () => (/* binding */ OBSIDIAN),
+/* harmony export */ "OLAF": () => (/* binding */ OLAF)
+/* harmony export */ });
+var CALYPSO = '#00a4bd';
+var CALYPSO_MEDIUM = '#7fd1de';
+var CALYPSO_LIGHT = '#e5f5f8';
+var LORAX = '#ff7a59';
+var OLAF = '#ffffff';
+var HEFFALUMP = '#425b76';
+var MARIGOLD_LIGHT = '#fef8f0';
+var MARIGOLD_MEDIUM = '#fae0b5';
+var OBSIDIAN = '#33475b';
+
+/***/ }),
+
+/***/ "./scripts/shared/enums/connectionStatus.ts":
+/*!**************************************************!*\
+ !*** ./scripts/shared/enums/connectionStatus.ts ***!
+ \**************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (__WEBPACK_DEFAULT_EXPORT__)
+/* harmony export */ });
+var ConnectionStatus = {
+ Connected: 'Connected',
+ NotConnected: 'NotConnected'
+};
+/* harmony default export */ const __WEBPACK_DEFAULT_EXPORT__ = (ConnectionStatus);
+
+/***/ }),
+
+/***/ "./scripts/shared/enums/loadState.ts":
+/*!*******************************************!*\
+ !*** ./scripts/shared/enums/loadState.ts ***!
+ \*******************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (__WEBPACK_DEFAULT_EXPORT__)
+/* harmony export */ });
+var LoadState = {
+ NotLoaded: 'NotLoaded',
+ Loading: 'Loading',
+ Loaded: 'Loaded',
+ Idle: 'Idle',
+ Failed: 'Failed'
+};
+/* harmony default export */ const __WEBPACK_DEFAULT_EXPORT__ = (LoadState);
+
+/***/ }),
+
+/***/ "./scripts/utils/appUtils.ts":
+/*!***********************************!*\
+ !*** ./scripts/utils/appUtils.ts ***!
+ \***********************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "initApp": () => (/* binding */ initApp),
+/* harmony export */ "initAppOnReady": () => (/* binding */ initAppOnReady)
+/* harmony export */ });
+/* harmony import */ var jquery__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! jquery */ "jquery");
+/* harmony import */ var jquery__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(jquery__WEBPACK_IMPORTED_MODULE_0__);
+/* harmony import */ var _lib_Raven__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! ../lib/Raven */ "./scripts/lib/Raven.ts");
+
+
+function initApp(initFn) {
+ (0,_lib_Raven__WEBPACK_IMPORTED_MODULE_1__.configureRaven)();
+ _lib_Raven__WEBPACK_IMPORTED_MODULE_1__["default"].context(initFn);
+}
+function initAppOnReady(initFn) {
+ function main() {
+ jquery__WEBPACK_IMPORTED_MODULE_0___default()(initFn);
+ }
+
+ initApp(main);
+}
+
+/***/ }),
+
+/***/ "./scripts/utils/backgroundAppUtils.ts":
+/*!*********************************************!*\
+ !*** ./scripts/utils/backgroundAppUtils.ts ***!
+ \*********************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "getOrCreateBackgroundApp": () => (/* binding */ getOrCreateBackgroundApp),
+/* harmony export */ "initBackgroundApp": () => (/* binding */ initBackgroundApp)
+/* harmony export */ });
+/* harmony import */ var _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! ../constants/leadinConfig */ "./scripts/constants/leadinConfig.ts");
+/* harmony import */ var _appUtils__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! ./appUtils */ "./scripts/utils/appUtils.ts");
+
+
+function initBackgroundApp(initFn) {
+ function main() {
+ if (Array.isArray(initFn)) {
+ initFn.forEach(function (callback) {
+ return callback();
+ });
+ } else {
+ initFn();
+ }
+ }
+
+ (0,_appUtils__WEBPACK_IMPORTED_MODULE_1__.initApp)(main);
+}
+var getOrCreateBackgroundApp = function getOrCreateBackgroundApp(refreshToken) {
+ if (window.LeadinBackgroundApp) {
+ return window.LeadinBackgroundApp;
+ }
+
+ var _window = window,
+ IntegratedAppEmbedder = _window.IntegratedAppEmbedder,
+ IntegratedAppOptions = _window.IntegratedAppOptions;
+ var options = new IntegratedAppOptions().setLocale(_constants_leadinConfig__WEBPACK_IMPORTED_MODULE_0__.locale).setDeviceId(_constants_leadinConfig__WEBPACK_IMPORTED_MODULE_0__.deviceId).setRefreshToken(refreshToken);
+ var embedder = new IntegratedAppEmbedder('integrated-plugin-proxy', _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_0__.portalId, _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_0__.hubspotBaseUrl, function () {}).setOptions(options);
+ embedder.attachTo(document.body, false);
+ embedder.postStartAppMessage(); // lets the app know all all data has been passed to it
+
+ window.LeadinBackgroundApp = embedder;
+ return window.LeadinBackgroundApp;
+};
+
+/***/ }),
+
+/***/ "./node_modules/lodash/_Symbol.js":
+/*!****************************************!*\
+ !*** ./node_modules/lodash/_Symbol.js ***!
+ \****************************************/
+/***/ ((module, __unused_webpack_exports, __webpack_require__) => {
+
+var root = __webpack_require__(/*! ./_root */ "./node_modules/lodash/_root.js");
+
+/** Built-in value references. */
+var Symbol = root.Symbol;
+
+module.exports = Symbol;
+
+
+/***/ }),
+
+/***/ "./node_modules/lodash/_baseGetTag.js":
+/*!********************************************!*\
+ !*** ./node_modules/lodash/_baseGetTag.js ***!
+ \********************************************/
+/***/ ((module, __unused_webpack_exports, __webpack_require__) => {
+
+var Symbol = __webpack_require__(/*! ./_Symbol */ "./node_modules/lodash/_Symbol.js"),
+ getRawTag = __webpack_require__(/*! ./_getRawTag */ "./node_modules/lodash/_getRawTag.js"),
+ objectToString = __webpack_require__(/*! ./_objectToString */ "./node_modules/lodash/_objectToString.js");
+
+/** `Object#toString` result references. */
+var nullTag = '[object Null]',
+ undefinedTag = '[object Undefined]';
+
+/** Built-in value references. */
+var symToStringTag = Symbol ? Symbol.toStringTag : undefined;
+
+/**
+ * The base implementation of `getTag` without fallbacks for buggy environments.
+ *
+ * @private
+ * @param {*} value The value to query.
+ * @returns {string} Returns the `toStringTag`.
+ */
+function baseGetTag(value) {
+ if (value == null) {
+ return value === undefined ? undefinedTag : nullTag;
+ }
+ return (symToStringTag && symToStringTag in Object(value))
+ ? getRawTag(value)
+ : objectToString(value);
+}
+
+module.exports = baseGetTag;
+
+
+/***/ }),
+
+/***/ "./node_modules/lodash/_baseTrim.js":
+/*!******************************************!*\
+ !*** ./node_modules/lodash/_baseTrim.js ***!
+ \******************************************/
+/***/ ((module, __unused_webpack_exports, __webpack_require__) => {
+
+var trimmedEndIndex = __webpack_require__(/*! ./_trimmedEndIndex */ "./node_modules/lodash/_trimmedEndIndex.js");
+
+/** Used to match leading whitespace. */
+var reTrimStart = /^\s+/;
+
+/**
+ * The base implementation of `_.trim`.
+ *
+ * @private
+ * @param {string} string The string to trim.
+ * @returns {string} Returns the trimmed string.
+ */
+function baseTrim(string) {
+ return string
+ ? string.slice(0, trimmedEndIndex(string) + 1).replace(reTrimStart, '')
+ : string;
+}
+
+module.exports = baseTrim;
+
+
+/***/ }),
+
+/***/ "./node_modules/lodash/_freeGlobal.js":
+/*!********************************************!*\
+ !*** ./node_modules/lodash/_freeGlobal.js ***!
+ \********************************************/
+/***/ ((module, __unused_webpack_exports, __webpack_require__) => {
+
+/** Detect free variable `global` from Node.js. */
+var freeGlobal = typeof __webpack_require__.g == 'object' && __webpack_require__.g && __webpack_require__.g.Object === Object && __webpack_require__.g;
+
+module.exports = freeGlobal;
+
+
+/***/ }),
+
+/***/ "./node_modules/lodash/_getRawTag.js":
+/*!*******************************************!*\
+ !*** ./node_modules/lodash/_getRawTag.js ***!
+ \*******************************************/
+/***/ ((module, __unused_webpack_exports, __webpack_require__) => {
+
+var Symbol = __webpack_require__(/*! ./_Symbol */ "./node_modules/lodash/_Symbol.js");
+
+/** Used for built-in method references. */
+var objectProto = Object.prototype;
+
+/** Used to check objects for own properties. */
+var hasOwnProperty = objectProto.hasOwnProperty;
+
+/**
+ * Used to resolve the
+ * [`toStringTag`](http://ecma-international.org/ecma-262/7.0/#sec-object.prototype.tostring)
+ * of values.
+ */
+var nativeObjectToString = objectProto.toString;
+
+/** Built-in value references. */
+var symToStringTag = Symbol ? Symbol.toStringTag : undefined;
+
+/**
+ * A specialized version of `baseGetTag` which ignores `Symbol.toStringTag` values.
+ *
+ * @private
+ * @param {*} value The value to query.
+ * @returns {string} Returns the raw `toStringTag`.
+ */
+function getRawTag(value) {
+ var isOwn = hasOwnProperty.call(value, symToStringTag),
+ tag = value[symToStringTag];
+
+ try {
+ value[symToStringTag] = undefined;
+ var unmasked = true;
+ } catch (e) {}
+
+ var result = nativeObjectToString.call(value);
+ if (unmasked) {
+ if (isOwn) {
+ value[symToStringTag] = tag;
+ } else {
+ delete value[symToStringTag];
+ }
+ }
+ return result;
+}
+
+module.exports = getRawTag;
+
+
+/***/ }),
+
+/***/ "./node_modules/lodash/_objectToString.js":
+/*!************************************************!*\
+ !*** ./node_modules/lodash/_objectToString.js ***!
+ \************************************************/
+/***/ ((module) => {
+
+/** Used for built-in method references. */
+var objectProto = Object.prototype;
+
+/**
+ * Used to resolve the
+ * [`toStringTag`](http://ecma-international.org/ecma-262/7.0/#sec-object.prototype.tostring)
+ * of values.
+ */
+var nativeObjectToString = objectProto.toString;
+
+/**
+ * Converts `value` to a string using `Object.prototype.toString`.
+ *
+ * @private
+ * @param {*} value The value to convert.
+ * @returns {string} Returns the converted string.
+ */
+function objectToString(value) {
+ return nativeObjectToString.call(value);
+}
+
+module.exports = objectToString;
+
+
+/***/ }),
+
+/***/ "./node_modules/lodash/_root.js":
+/*!**************************************!*\
+ !*** ./node_modules/lodash/_root.js ***!
+ \**************************************/
+/***/ ((module, __unused_webpack_exports, __webpack_require__) => {
+
+var freeGlobal = __webpack_require__(/*! ./_freeGlobal */ "./node_modules/lodash/_freeGlobal.js");
+
+/** Detect free variable `self`. */
+var freeSelf = typeof self == 'object' && self && self.Object === Object && self;
+
+/** Used as a reference to the global object. */
+var root = freeGlobal || freeSelf || Function('return this')();
+
+module.exports = root;
+
+
+/***/ }),
+
+/***/ "./node_modules/lodash/_trimmedEndIndex.js":
+/*!*************************************************!*\
+ !*** ./node_modules/lodash/_trimmedEndIndex.js ***!
+ \*************************************************/
+/***/ ((module) => {
+
+/** Used to match a single whitespace character. */
+var reWhitespace = /\s/;
+
+/**
+ * Used by `_.trim` and `_.trimEnd` to get the index of the last non-whitespace
+ * character of `string`.
+ *
+ * @private
+ * @param {string} string The string to inspect.
+ * @returns {number} Returns the index of the last non-whitespace character.
+ */
+function trimmedEndIndex(string) {
+ var index = string.length;
+
+ while (index-- && reWhitespace.test(string.charAt(index))) {}
+ return index;
+}
+
+module.exports = trimmedEndIndex;
+
+
+/***/ }),
+
+/***/ "./node_modules/lodash/debounce.js":
+/*!*****************************************!*\
+ !*** ./node_modules/lodash/debounce.js ***!
+ \*****************************************/
+/***/ ((module, __unused_webpack_exports, __webpack_require__) => {
+
+var isObject = __webpack_require__(/*! ./isObject */ "./node_modules/lodash/isObject.js"),
+ now = __webpack_require__(/*! ./now */ "./node_modules/lodash/now.js"),
+ toNumber = __webpack_require__(/*! ./toNumber */ "./node_modules/lodash/toNumber.js");
+
+/** Error message constants. */
+var FUNC_ERROR_TEXT = 'Expected a function';
+
+/* Built-in method references for those with the same name as other `lodash` methods. */
+var nativeMax = Math.max,
+ nativeMin = Math.min;
+
+/**
+ * Creates a debounced function that delays invoking `func` until after `wait`
+ * milliseconds have elapsed since the last time the debounced function was
+ * invoked. The debounced function comes with a `cancel` method to cancel
+ * delayed `func` invocations and a `flush` method to immediately invoke them.
+ * Provide `options` to indicate whether `func` should be invoked on the
+ * leading and/or trailing edge of the `wait` timeout. The `func` is invoked
+ * with the last arguments provided to the debounced function. Subsequent
+ * calls to the debounced function return the result of the last `func`
+ * invocation.
+ *
+ * **Note:** If `leading` and `trailing` options are `true`, `func` is
+ * invoked on the trailing edge of the timeout only if the debounced function
+ * is invoked more than once during the `wait` timeout.
+ *
+ * If `wait` is `0` and `leading` is `false`, `func` invocation is deferred
+ * until to the next tick, similar to `setTimeout` with a timeout of `0`.
+ *
+ * See [David Corbacho's article](https://css-tricks.com/debouncing-throttling-explained-examples/)
+ * for details over the differences between `_.debounce` and `_.throttle`.
+ *
+ * @static
+ * @memberOf _
+ * @since 0.1.0
+ * @category Function
+ * @param {Function} func The function to debounce.
+ * @param {number} [wait=0] The number of milliseconds to delay.
+ * @param {Object} [options={}] The options object.
+ * @param {boolean} [options.leading=false]
+ * Specify invoking on the leading edge of the timeout.
+ * @param {number} [options.maxWait]
+ * The maximum time `func` is allowed to be delayed before it's invoked.
+ * @param {boolean} [options.trailing=true]
+ * Specify invoking on the trailing edge of the timeout.
+ * @returns {Function} Returns the new debounced function.
+ * @example
+ *
+ * // Avoid costly calculations while the window size is in flux.
+ * jQuery(window).on('resize', _.debounce(calculateLayout, 150));
+ *
+ * // Invoke `sendMail` when clicked, debouncing subsequent calls.
+ * jQuery(element).on('click', _.debounce(sendMail, 300, {
+ * 'leading': true,
+ * 'trailing': false
+ * }));
+ *
+ * // Ensure `batchLog` is invoked once after 1 second of debounced calls.
+ * var debounced = _.debounce(batchLog, 250, { 'maxWait': 1000 });
+ * var source = new EventSource('/stream');
+ * jQuery(source).on('message', debounced);
+ *
+ * // Cancel the trailing debounced invocation.
+ * jQuery(window).on('popstate', debounced.cancel);
+ */
+function debounce(func, wait, options) {
+ var lastArgs,
+ lastThis,
+ maxWait,
+ result,
+ timerId,
+ lastCallTime,
+ lastInvokeTime = 0,
+ leading = false,
+ maxing = false,
+ trailing = true;
+
+ if (typeof func != 'function') {
+ throw new TypeError(FUNC_ERROR_TEXT);
+ }
+ wait = toNumber(wait) || 0;
+ if (isObject(options)) {
+ leading = !!options.leading;
+ maxing = 'maxWait' in options;
+ maxWait = maxing ? nativeMax(toNumber(options.maxWait) || 0, wait) : maxWait;
+ trailing = 'trailing' in options ? !!options.trailing : trailing;
+ }
+
+ function invokeFunc(time) {
+ var args = lastArgs,
+ thisArg = lastThis;
+
+ lastArgs = lastThis = undefined;
+ lastInvokeTime = time;
+ result = func.apply(thisArg, args);
+ return result;
+ }
+
+ function leadingEdge(time) {
+ // Reset any `maxWait` timer.
+ lastInvokeTime = time;
+ // Start the timer for the trailing edge.
+ timerId = setTimeout(timerExpired, wait);
+ // Invoke the leading edge.
+ return leading ? invokeFunc(time) : result;
+ }
+
+ function remainingWait(time) {
+ var timeSinceLastCall = time - lastCallTime,
+ timeSinceLastInvoke = time - lastInvokeTime,
+ timeWaiting = wait - timeSinceLastCall;
+
+ return maxing
+ ? nativeMin(timeWaiting, maxWait - timeSinceLastInvoke)
+ : timeWaiting;
+ }
+
+ function shouldInvoke(time) {
+ var timeSinceLastCall = time - lastCallTime,
+ timeSinceLastInvoke = time - lastInvokeTime;
+
+ // Either this is the first call, activity has stopped and we're at the
+ // trailing edge, the system time has gone backwards and we're treating
+ // it as the trailing edge, or we've hit the `maxWait` limit.
+ return (lastCallTime === undefined || (timeSinceLastCall >= wait) ||
+ (timeSinceLastCall < 0) || (maxing && timeSinceLastInvoke >= maxWait));
+ }
+
+ function timerExpired() {
+ var time = now();
+ if (shouldInvoke(time)) {
+ return trailingEdge(time);
+ }
+ // Restart the timer.
+ timerId = setTimeout(timerExpired, remainingWait(time));
+ }
+
+ function trailingEdge(time) {
+ timerId = undefined;
+
+ // Only invoke if we have `lastArgs` which means `func` has been
+ // debounced at least once.
+ if (trailing && lastArgs) {
+ return invokeFunc(time);
+ }
+ lastArgs = lastThis = undefined;
+ return result;
+ }
+
+ function cancel() {
+ if (timerId !== undefined) {
+ clearTimeout(timerId);
+ }
+ lastInvokeTime = 0;
+ lastArgs = lastCallTime = lastThis = timerId = undefined;
+ }
+
+ function flush() {
+ return timerId === undefined ? result : trailingEdge(now());
+ }
+
+ function debounced() {
+ var time = now(),
+ isInvoking = shouldInvoke(time);
+
+ lastArgs = arguments;
+ lastThis = this;
+ lastCallTime = time;
+
+ if (isInvoking) {
+ if (timerId === undefined) {
+ return leadingEdge(lastCallTime);
+ }
+ if (maxing) {
+ // Handle invocations in a tight loop.
+ clearTimeout(timerId);
+ timerId = setTimeout(timerExpired, wait);
+ return invokeFunc(lastCallTime);
+ }
+ }
+ if (timerId === undefined) {
+ timerId = setTimeout(timerExpired, wait);
+ }
+ return result;
+ }
+ debounced.cancel = cancel;
+ debounced.flush = flush;
+ return debounced;
+}
+
+module.exports = debounce;
+
+
+/***/ }),
+
+/***/ "./node_modules/lodash/isObject.js":
+/*!*****************************************!*\
+ !*** ./node_modules/lodash/isObject.js ***!
+ \*****************************************/
+/***/ ((module) => {
+
+/**
+ * Checks if `value` is the
+ * [language type](http://www.ecma-international.org/ecma-262/7.0/#sec-ecmascript-language-types)
+ * of `Object`. (e.g. arrays, functions, objects, regexes, `new Number(0)`, and `new String('')`)
+ *
+ * @static
+ * @memberOf _
+ * @since 0.1.0
+ * @category Lang
+ * @param {*} value The value to check.
+ * @returns {boolean} Returns `true` if `value` is an object, else `false`.
+ * @example
+ *
+ * _.isObject({});
+ * // => true
+ *
+ * _.isObject([1, 2, 3]);
+ * // => true
+ *
+ * _.isObject(_.noop);
+ * // => true
+ *
+ * _.isObject(null);
+ * // => false
+ */
+function isObject(value) {
+ var type = typeof value;
+ return value != null && (type == 'object' || type == 'function');
+}
+
+module.exports = isObject;
+
+
+/***/ }),
+
+/***/ "./node_modules/lodash/isObjectLike.js":
+/*!*********************************************!*\
+ !*** ./node_modules/lodash/isObjectLike.js ***!
+ \*********************************************/
+/***/ ((module) => {
+
+/**
+ * Checks if `value` is object-like. A value is object-like if it's not `null`
+ * and has a `typeof` result of "object".
+ *
+ * @static
+ * @memberOf _
+ * @since 4.0.0
+ * @category Lang
+ * @param {*} value The value to check.
+ * @returns {boolean} Returns `true` if `value` is object-like, else `false`.
+ * @example
+ *
+ * _.isObjectLike({});
+ * // => true
+ *
+ * _.isObjectLike([1, 2, 3]);
+ * // => true
+ *
+ * _.isObjectLike(_.noop);
+ * // => false
+ *
+ * _.isObjectLike(null);
+ * // => false
+ */
+function isObjectLike(value) {
+ return value != null && typeof value == 'object';
+}
+
+module.exports = isObjectLike;
+
+
+/***/ }),
+
+/***/ "./node_modules/lodash/isSymbol.js":
+/*!*****************************************!*\
+ !*** ./node_modules/lodash/isSymbol.js ***!
+ \*****************************************/
+/***/ ((module, __unused_webpack_exports, __webpack_require__) => {
+
+var baseGetTag = __webpack_require__(/*! ./_baseGetTag */ "./node_modules/lodash/_baseGetTag.js"),
+ isObjectLike = __webpack_require__(/*! ./isObjectLike */ "./node_modules/lodash/isObjectLike.js");
+
+/** `Object#toString` result references. */
+var symbolTag = '[object Symbol]';
+
+/**
+ * Checks if `value` is classified as a `Symbol` primitive or object.
+ *
+ * @static
+ * @memberOf _
+ * @since 4.0.0
+ * @category Lang
+ * @param {*} value The value to check.
+ * @returns {boolean} Returns `true` if `value` is a symbol, else `false`.
+ * @example
+ *
+ * _.isSymbol(Symbol.iterator);
+ * // => true
+ *
+ * _.isSymbol('abc');
+ * // => false
+ */
+function isSymbol(value) {
+ return typeof value == 'symbol' ||
+ (isObjectLike(value) && baseGetTag(value) == symbolTag);
+}
+
+module.exports = isSymbol;
+
+
+/***/ }),
+
+/***/ "./node_modules/lodash/now.js":
+/*!************************************!*\
+ !*** ./node_modules/lodash/now.js ***!
+ \************************************/
+/***/ ((module, __unused_webpack_exports, __webpack_require__) => {
+
+var root = __webpack_require__(/*! ./_root */ "./node_modules/lodash/_root.js");
+
+/**
+ * Gets the timestamp of the number of milliseconds that have elapsed since
+ * the Unix epoch (1 January 1970 00:00:00 UTC).
+ *
+ * @static
+ * @memberOf _
+ * @since 2.4.0
+ * @category Date
+ * @returns {number} Returns the timestamp.
+ * @example
+ *
+ * _.defer(function(stamp) {
+ * console.log(_.now() - stamp);
+ * }, _.now());
+ * // => Logs the number of milliseconds it took for the deferred invocation.
+ */
+var now = function() {
+ return root.Date.now();
+};
+
+module.exports = now;
+
+
+/***/ }),
+
+/***/ "./node_modules/lodash/toNumber.js":
+/*!*****************************************!*\
+ !*** ./node_modules/lodash/toNumber.js ***!
+ \*****************************************/
+/***/ ((module, __unused_webpack_exports, __webpack_require__) => {
+
+var baseTrim = __webpack_require__(/*! ./_baseTrim */ "./node_modules/lodash/_baseTrim.js"),
+ isObject = __webpack_require__(/*! ./isObject */ "./node_modules/lodash/isObject.js"),
+ isSymbol = __webpack_require__(/*! ./isSymbol */ "./node_modules/lodash/isSymbol.js");
+
+/** Used as references for various `Number` constants. */
+var NAN = 0 / 0;
+
+/** Used to detect bad signed hexadecimal string values. */
+var reIsBadHex = /^[-+]0x[0-9a-f]+$/i;
+
+/** Used to detect binary string values. */
+var reIsBinary = /^0b[01]+$/i;
+
+/** Used to detect octal string values. */
+var reIsOctal = /^0o[0-7]+$/i;
+
+/** Built-in method references without a dependency on `root`. */
+var freeParseInt = parseInt;
+
+/**
+ * Converts `value` to a number.
+ *
+ * @static
+ * @memberOf _
+ * @since 4.0.0
+ * @category Lang
+ * @param {*} value The value to process.
+ * @returns {number} Returns the number.
+ * @example
+ *
+ * _.toNumber(3.2);
+ * // => 3.2
+ *
+ * _.toNumber(Number.MIN_VALUE);
+ * // => 5e-324
+ *
+ * _.toNumber(Infinity);
+ * // => Infinity
+ *
+ * _.toNumber('3.2');
+ * // => 3.2
+ */
+function toNumber(value) {
+ if (typeof value == 'number') {
+ return value;
+ }
+ if (isSymbol(value)) {
+ return NAN;
+ }
+ if (isObject(value)) {
+ var other = typeof value.valueOf == 'function' ? value.valueOf() : value;
+ value = isObject(other) ? (other + '') : other;
+ }
+ if (typeof value != 'string') {
+ return value === 0 ? value : +value;
+ }
+ value = baseTrim(value);
+ var isBinary = reIsBinary.test(value);
+ return (isBinary || reIsOctal.test(value))
+ ? freeParseInt(value.slice(2), isBinary ? 2 : 8)
+ : (reIsBadHex.test(value) ? NAN : +value);
+}
+
+module.exports = toNumber;
+
+
+/***/ }),
+
+/***/ "./scripts/elementor/Common/ElementorButton.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/elementor/Common/ElementorButton.tsx":
+/*!*********************************************************************************************************************************************************************************************!*\
+ !*** ./scripts/elementor/Common/ElementorButton.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/elementor/Common/ElementorButton.tsx ***!
+ \*********************************************************************************************************************************************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+// extracted by mini-css-extract-plugin
+
+
+/***/ }),
+
+/***/ "./scripts/elementor/MeetingWidget/ElementorMeetingWarning.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/elementor/MeetingWidget/ElementorMeetingWarning.tsx":
+/*!***************************************************************************************************************************************************************************************************************************!*\
+ !*** ./scripts/elementor/MeetingWidget/ElementorMeetingWarning.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/elementor/MeetingWidget/ElementorMeetingWarning.tsx ***!
+ \***************************************************************************************************************************************************************************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+// extracted by mini-css-extract-plugin
+
+
+/***/ }),
+
+/***/ "./scripts/shared/Common/AsyncSelect.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/Common/AsyncSelect.tsx":
+/*!*******************************************************************************************************************************************************************************!*\
+ !*** ./scripts/shared/Common/AsyncSelect.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/Common/AsyncSelect.tsx ***!
+ \*******************************************************************************************************************************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+// extracted by mini-css-extract-plugin
+
+
+/***/ }),
+
+/***/ "./scripts/shared/Common/HubspotWrapper.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/Common/HubspotWrapper.ts":
+/*!************************************************************************************************************************************************************************************!*\
+ !*** ./scripts/shared/Common/HubspotWrapper.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/Common/HubspotWrapper.ts ***!
+ \************************************************************************************************************************************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+// extracted by mini-css-extract-plugin
+
+
+/***/ }),
+
+/***/ "./scripts/shared/UIComponents/UIAlert.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/UIComponents/UIAlert.tsx":
+/*!***********************************************************************************************************************************************************************************!*\
+ !*** ./scripts/shared/UIComponents/UIAlert.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/UIComponents/UIAlert.tsx ***!
+ \***********************************************************************************************************************************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+// extracted by mini-css-extract-plugin
+
+
+/***/ }),
+
+/***/ "./scripts/shared/UIComponents/UIButton.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/UIComponents/UIButton.ts":
+/*!************************************************************************************************************************************************************************************!*\
+ !*** ./scripts/shared/UIComponents/UIButton.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/UIComponents/UIButton.ts ***!
+ \************************************************************************************************************************************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+// extracted by mini-css-extract-plugin
+
+
+/***/ }),
+
+/***/ "./scripts/shared/UIComponents/UIContainer.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/UIComponents/UIContainer.ts":
+/*!******************************************************************************************************************************************************************************************!*\
+ !*** ./scripts/shared/UIComponents/UIContainer.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/UIComponents/UIContainer.ts ***!
+ \******************************************************************************************************************************************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+// extracted by mini-css-extract-plugin
+
+
+/***/ }),
+
+/***/ "./scripts/shared/UIComponents/UIOverlay.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/UIComponents/UIOverlay.ts":
+/*!**************************************************************************************************************************************************************************************!*\
+ !*** ./scripts/shared/UIComponents/UIOverlay.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/UIComponents/UIOverlay.ts ***!
+ \**************************************************************************************************************************************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+// extracted by mini-css-extract-plugin
+
+
+/***/ }),
+
+/***/ "./scripts/shared/UIComponents/UISpacer.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/UIComponents/UISpacer.ts":
+/*!************************************************************************************************************************************************************************************!*\
+ !*** ./scripts/shared/UIComponents/UISpacer.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/UIComponents/UISpacer.ts ***!
+ \************************************************************************************************************************************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+// extracted by mini-css-extract-plugin
+
+
+/***/ }),
+
+/***/ "./scripts/shared/UIComponents/UISpinner.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/UIComponents/UISpinner.tsx":
+/*!***************************************************************************************************************************************************************************************!*\
+ !*** ./scripts/shared/UIComponents/UISpinner.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/UIComponents/UISpinner.tsx ***!
+ \***************************************************************************************************************************************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+// extracted by mini-css-extract-plugin
+
+
+/***/ }),
+
+/***/ "./node_modules/object-assign/index.js":
+/*!*********************************************!*\
+ !*** ./node_modules/object-assign/index.js ***!
+ \*********************************************/
+/***/ ((module) => {
+
+"use strict";
+/*
+object-assign
+(c) Sindre Sorhus
+@license MIT
+*/
+
+
+/* eslint-disable no-unused-vars */
+var getOwnPropertySymbols = Object.getOwnPropertySymbols;
+var hasOwnProperty = Object.prototype.hasOwnProperty;
+var propIsEnumerable = Object.prototype.propertyIsEnumerable;
+
+function toObject(val) {
+ if (val === null || val === undefined) {
+ throw new TypeError('Object.assign cannot be called with null or undefined');
+ }
+
+ return Object(val);
+}
+
+function shouldUseNative() {
+ try {
+ if (!Object.assign) {
+ return false;
+ }
+
+ // Detect buggy property enumeration order in older V8 versions.
+
+ // https://bugs.chromium.org/p/v8/issues/detail?id=4118
+ var test1 = new String('abc'); // eslint-disable-line no-new-wrappers
+ test1[5] = 'de';
+ if (Object.getOwnPropertyNames(test1)[0] === '5') {
+ return false;
+ }
+
+ // https://bugs.chromium.org/p/v8/issues/detail?id=3056
+ var test2 = {};
+ for (var i = 0; i < 10; i++) {
+ test2['_' + String.fromCharCode(i)] = i;
+ }
+ var order2 = Object.getOwnPropertyNames(test2).map(function (n) {
+ return test2[n];
+ });
+ if (order2.join('') !== '0123456789') {
+ return false;
+ }
+
+ // https://bugs.chromium.org/p/v8/issues/detail?id=3056
+ var test3 = {};
+ 'abcdefghijklmnopqrst'.split('').forEach(function (letter) {
+ test3[letter] = letter;
+ });
+ if (Object.keys(Object.assign({}, test3)).join('') !==
+ 'abcdefghijklmnopqrst') {
+ return false;
+ }
+
+ return true;
+ } catch (err) {
+ // We don't expect any of the above to throw, but better to be safe.
+ return false;
+ }
+}
+
+module.exports = shouldUseNative() ? Object.assign : function (target, source) {
+ var from;
+ var to = toObject(target);
+ var symbols;
+
+ for (var s = 1; s < arguments.length; s++) {
+ from = Object(arguments[s]);
+
+ for (var key in from) {
+ if (hasOwnProperty.call(from, key)) {
+ to[key] = from[key];
+ }
+ }
+
+ if (getOwnPropertySymbols) {
+ symbols = getOwnPropertySymbols(from);
+ for (var i = 0; i < symbols.length; i++) {
+ if (propIsEnumerable.call(from, symbols[i])) {
+ to[symbols[i]] = from[symbols[i]];
+ }
+ }
+ }
+ }
+
+ return to;
+};
+
+
+/***/ }),
+
+/***/ "./node_modules/raven-js/src/configError.js":
+/*!**************************************************!*\
+ !*** ./node_modules/raven-js/src/configError.js ***!
+ \**************************************************/
+/***/ ((module) => {
+
+function RavenConfigError(message) {
+ this.name = 'RavenConfigError';
+ this.message = message;
+}
+RavenConfigError.prototype = new Error();
+RavenConfigError.prototype.constructor = RavenConfigError;
+
+module.exports = RavenConfigError;
+
+
+/***/ }),
+
+/***/ "./node_modules/raven-js/src/console.js":
+/*!**********************************************!*\
+ !*** ./node_modules/raven-js/src/console.js ***!
+ \**********************************************/
+/***/ ((module) => {
+
+var wrapMethod = function(console, level, callback) {
+ var originalConsoleLevel = console[level];
+ var originalConsole = console;
+
+ if (!(level in console)) {
+ return;
+ }
+
+ var sentryLevel = level === 'warn' ? 'warning' : level;
+
+ console[level] = function() {
+ var args = [].slice.call(arguments);
+
+ var msg = '' + args.join(' ');
+ var data = {level: sentryLevel, logger: 'console', extra: {arguments: args}};
+
+ if (level === 'assert') {
+ if (args[0] === false) {
+ // Default browsers message
+ msg = 'Assertion failed: ' + (args.slice(1).join(' ') || 'console.assert');
+ data.extra.arguments = args.slice(1);
+ callback && callback(msg, data);
+ }
+ } else {
+ callback && callback(msg, data);
+ }
+
+ // this fails for some browsers. :(
+ if (originalConsoleLevel) {
+ // IE9 doesn't allow calling apply on console functions directly
+ // See: https://stackoverflow.com/questions/5472938/does-ie9-support-console-log-and-is-it-a-real-function#answer-5473193
+ Function.prototype.apply.call(originalConsoleLevel, originalConsole, args);
+ }
+ };
+};
+
+module.exports = {
+ wrapMethod: wrapMethod
+};
+
+
+/***/ }),
+
+/***/ "./node_modules/raven-js/src/raven.js":
+/*!********************************************!*\
+ !*** ./node_modules/raven-js/src/raven.js ***!
+ \********************************************/
+/***/ ((module, __unused_webpack_exports, __webpack_require__) => {
+
+/*global XDomainRequest:false */
+
+var TraceKit = __webpack_require__(/*! ../vendor/TraceKit/tracekit */ "./node_modules/raven-js/vendor/TraceKit/tracekit.js");
+var stringify = __webpack_require__(/*! ../vendor/json-stringify-safe/stringify */ "./node_modules/raven-js/vendor/json-stringify-safe/stringify.js");
+var RavenConfigError = __webpack_require__(/*! ./configError */ "./node_modules/raven-js/src/configError.js");
+
+var utils = __webpack_require__(/*! ./utils */ "./node_modules/raven-js/src/utils.js");
+var isError = utils.isError;
+var isObject = utils.isObject;
+var isObject = utils.isObject;
+var isErrorEvent = utils.isErrorEvent;
+var isUndefined = utils.isUndefined;
+var isFunction = utils.isFunction;
+var isString = utils.isString;
+var isEmptyObject = utils.isEmptyObject;
+var each = utils.each;
+var objectMerge = utils.objectMerge;
+var truncate = utils.truncate;
+var objectFrozen = utils.objectFrozen;
+var hasKey = utils.hasKey;
+var joinRegExp = utils.joinRegExp;
+var urlencode = utils.urlencode;
+var uuid4 = utils.uuid4;
+var htmlTreeAsString = utils.htmlTreeAsString;
+var isSameException = utils.isSameException;
+var isSameStacktrace = utils.isSameStacktrace;
+var parseUrl = utils.parseUrl;
+var fill = utils.fill;
+
+var wrapConsoleMethod = (__webpack_require__(/*! ./console */ "./node_modules/raven-js/src/console.js").wrapMethod);
+
+var dsnKeys = 'source protocol user pass host port path'.split(' '),
+ dsnPattern = /^(?:(\w+):)?\/\/(?:(\w+)(:\w+)?@)?([\w\.-]+)(?::(\d+))?(\/.*)/;
+
+function now() {
+ return +new Date();
+}
+
+// This is to be defensive in environments where window does not exist (see https://github.com/getsentry/raven-js/pull/785)
+var _window =
+ typeof window !== 'undefined'
+ ? window
+ : typeof __webpack_require__.g !== 'undefined' ? __webpack_require__.g : typeof self !== 'undefined' ? self : {};
+var _document = _window.document;
+var _navigator = _window.navigator;
+
+function keepOriginalCallback(original, callback) {
+ return isFunction(callback)
+ ? function(data) {
+ return callback(data, original);
+ }
+ : callback;
+}
+
+// First, check for JSON support
+// If there is no JSON, we no-op the core features of Raven
+// since JSON is required to encode the payload
+function Raven() {
+ this._hasJSON = !!(typeof JSON === 'object' && JSON.stringify);
+ // Raven can run in contexts where there's no document (react-native)
+ this._hasDocument = !isUndefined(_document);
+ this._hasNavigator = !isUndefined(_navigator);
+ this._lastCapturedException = null;
+ this._lastData = null;
+ this._lastEventId = null;
+ this._globalServer = null;
+ this._globalKey = null;
+ this._globalProject = null;
+ this._globalContext = {};
+ this._globalOptions = {
+ logger: 'javascript',
+ ignoreErrors: [],
+ ignoreUrls: [],
+ whitelistUrls: [],
+ includePaths: [],
+ collectWindowErrors: true,
+ maxMessageLength: 0,
+
+ // By default, truncates URL values to 250 chars
+ maxUrlLength: 250,
+ stackTraceLimit: 50,
+ autoBreadcrumbs: true,
+ instrument: true,
+ sampleRate: 1
+ };
+ this._ignoreOnError = 0;
+ this._isRavenInstalled = false;
+ this._originalErrorStackTraceLimit = Error.stackTraceLimit;
+ // capture references to window.console *and* all its methods first
+ // before the console plugin has a chance to monkey patch
+ this._originalConsole = _window.console || {};
+ this._originalConsoleMethods = {};
+ this._plugins = [];
+ this._startTime = now();
+ this._wrappedBuiltIns = [];
+ this._breadcrumbs = [];
+ this._lastCapturedEvent = null;
+ this._keypressTimeout;
+ this._location = _window.location;
+ this._lastHref = this._location && this._location.href;
+ this._resetBackoff();
+
+ // eslint-disable-next-line guard-for-in
+ for (var method in this._originalConsole) {
+ this._originalConsoleMethods[method] = this._originalConsole[method];
+ }
+}
+
+/*
+ * The core Raven singleton
+ *
+ * @this {Raven}
+ */
+
+Raven.prototype = {
+ // Hardcode version string so that raven source can be loaded directly via
+ // webpack (using a build step causes webpack #1617). Grunt verifies that
+ // this value matches package.json during build.
+ // See: https://github.com/getsentry/raven-js/issues/465
+ VERSION: '3.19.1',
+
+ debug: false,
+
+ TraceKit: TraceKit, // alias to TraceKit
+
+ /*
+ * Configure Raven with a DSN and extra options
+ *
+ * @param {string} dsn The public Sentry DSN
+ * @param {object} options Set of global options [optional]
+ * @return {Raven}
+ */
+ config: function(dsn, options) {
+ var self = this;
+
+ if (self._globalServer) {
+ this._logDebug('error', 'Error: Raven has already been configured');
+ return self;
+ }
+ if (!dsn) return self;
+
+ var globalOptions = self._globalOptions;
+
+ // merge in options
+ if (options) {
+ each(options, function(key, value) {
+ // tags and extra are special and need to be put into context
+ if (key === 'tags' || key === 'extra' || key === 'user') {
+ self._globalContext[key] = value;
+ } else {
+ globalOptions[key] = value;
+ }
+ });
+ }
+
+ self.setDSN(dsn);
+
+ // "Script error." is hard coded into browsers for errors that it can't read.
+ // this is the result of a script being pulled in from an external domain and CORS.
+ globalOptions.ignoreErrors.push(/^Script error\.?$/);
+ globalOptions.ignoreErrors.push(/^Javascript error: Script error\.? on line 0$/);
+
+ // join regexp rules into one big rule
+ globalOptions.ignoreErrors = joinRegExp(globalOptions.ignoreErrors);
+ globalOptions.ignoreUrls = globalOptions.ignoreUrls.length
+ ? joinRegExp(globalOptions.ignoreUrls)
+ : false;
+ globalOptions.whitelistUrls = globalOptions.whitelistUrls.length
+ ? joinRegExp(globalOptions.whitelistUrls)
+ : false;
+ globalOptions.includePaths = joinRegExp(globalOptions.includePaths);
+ globalOptions.maxBreadcrumbs = Math.max(
+ 0,
+ Math.min(globalOptions.maxBreadcrumbs || 100, 100)
+ ); // default and hard limit is 100
+
+ var autoBreadcrumbDefaults = {
+ xhr: true,
+ console: true,
+ dom: true,
+ location: true
+ };
+
+ var autoBreadcrumbs = globalOptions.autoBreadcrumbs;
+ if ({}.toString.call(autoBreadcrumbs) === '[object Object]') {
+ autoBreadcrumbs = objectMerge(autoBreadcrumbDefaults, autoBreadcrumbs);
+ } else if (autoBreadcrumbs !== false) {
+ autoBreadcrumbs = autoBreadcrumbDefaults;
+ }
+ globalOptions.autoBreadcrumbs = autoBreadcrumbs;
+
+ var instrumentDefaults = {
+ tryCatch: true
+ };
+
+ var instrument = globalOptions.instrument;
+ if ({}.toString.call(instrument) === '[object Object]') {
+ instrument = objectMerge(instrumentDefaults, instrument);
+ } else if (instrument !== false) {
+ instrument = instrumentDefaults;
+ }
+ globalOptions.instrument = instrument;
+
+ TraceKit.collectWindowErrors = !!globalOptions.collectWindowErrors;
+
+ // return for chaining
+ return self;
+ },
+
+ /*
+ * Installs a global window.onerror error handler
+ * to capture and report uncaught exceptions.
+ * At this point, install() is required to be called due
+ * to the way TraceKit is set up.
+ *
+ * @return {Raven}
+ */
+ install: function() {
+ var self = this;
+ if (self.isSetup() && !self._isRavenInstalled) {
+ TraceKit.report.subscribe(function() {
+ self._handleOnErrorStackInfo.apply(self, arguments);
+ });
+ if (self._globalOptions.instrument && self._globalOptions.instrument.tryCatch) {
+ self._instrumentTryCatch();
+ }
+
+ if (self._globalOptions.autoBreadcrumbs) self._instrumentBreadcrumbs();
+
+ // Install all of the plugins
+ self._drainPlugins();
+
+ self._isRavenInstalled = true;
+ }
+
+ Error.stackTraceLimit = self._globalOptions.stackTraceLimit;
+ return this;
+ },
+
+ /*
+ * Set the DSN (can be called multiple time unlike config)
+ *
+ * @param {string} dsn The public Sentry DSN
+ */
+ setDSN: function(dsn) {
+ var self = this,
+ uri = self._parseDSN(dsn),
+ lastSlash = uri.path.lastIndexOf('/'),
+ path = uri.path.substr(1, lastSlash);
+
+ self._dsn = dsn;
+ self._globalKey = uri.user;
+ self._globalSecret = uri.pass && uri.pass.substr(1);
+ self._globalProject = uri.path.substr(lastSlash + 1);
+
+ self._globalServer = self._getGlobalServer(uri);
+
+ self._globalEndpoint =
+ self._globalServer + '/' + path + 'api/' + self._globalProject + '/store/';
+
+ // Reset backoff state since we may be pointing at a
+ // new project/server
+ this._resetBackoff();
+ },
+
+ /*
+ * Wrap code within a context so Raven can capture errors
+ * reliably across domains that is executed immediately.
+ *
+ * @param {object} options A specific set of options for this context [optional]
+ * @param {function} func The callback to be immediately executed within the context
+ * @param {array} args An array of arguments to be called with the callback [optional]
+ */
+ context: function(options, func, args) {
+ if (isFunction(options)) {
+ args = func || [];
+ func = options;
+ options = undefined;
+ }
+
+ return this.wrap(options, func).apply(this, args);
+ },
+
+ /*
+ * Wrap code within a context and returns back a new function to be executed
+ *
+ * @param {object} options A specific set of options for this context [optional]
+ * @param {function} func The function to be wrapped in a new context
+ * @param {function} func A function to call before the try/catch wrapper [optional, private]
+ * @return {function} The newly wrapped functions with a context
+ */
+ wrap: function(options, func, _before) {
+ var self = this;
+ // 1 argument has been passed, and it's not a function
+ // so just return it
+ if (isUndefined(func) && !isFunction(options)) {
+ return options;
+ }
+
+ // options is optional
+ if (isFunction(options)) {
+ func = options;
+ options = undefined;
+ }
+
+ // At this point, we've passed along 2 arguments, and the second one
+ // is not a function either, so we'll just return the second argument.
+ if (!isFunction(func)) {
+ return func;
+ }
+
+ // We don't wanna wrap it twice!
+ try {
+ if (func.__raven__) {
+ return func;
+ }
+
+ // If this has already been wrapped in the past, return that
+ if (func.__raven_wrapper__) {
+ return func.__raven_wrapper__;
+ }
+ } catch (e) {
+ // Just accessing custom props in some Selenium environments
+ // can cause a "Permission denied" exception (see raven-js#495).
+ // Bail on wrapping and return the function as-is (defers to window.onerror).
+ return func;
+ }
+
+ function wrapped() {
+ var args = [],
+ i = arguments.length,
+ deep = !options || (options && options.deep !== false);
+
+ if (_before && isFunction(_before)) {
+ _before.apply(this, arguments);
+ }
+
+ // Recursively wrap all of a function's arguments that are
+ // functions themselves.
+ while (i--) args[i] = deep ? self.wrap(options, arguments[i]) : arguments[i];
+
+ try {
+ // Attempt to invoke user-land function
+ // NOTE: If you are a Sentry user, and you are seeing this stack frame, it
+ // means Raven caught an error invoking your application code. This is
+ // expected behavior and NOT indicative of a bug with Raven.js.
+ return func.apply(this, args);
+ } catch (e) {
+ self._ignoreNextOnError();
+ self.captureException(e, options);
+ throw e;
+ }
+ }
+
+ // copy over properties of the old function
+ for (var property in func) {
+ if (hasKey(func, property)) {
+ wrapped[property] = func[property];
+ }
+ }
+ wrapped.prototype = func.prototype;
+
+ func.__raven_wrapper__ = wrapped;
+ // Signal that this function has been wrapped already
+ // for both debugging and to prevent it to being wrapped twice
+ wrapped.__raven__ = true;
+ wrapped.__inner__ = func;
+
+ return wrapped;
+ },
+
+ /*
+ * Uninstalls the global error handler.
+ *
+ * @return {Raven}
+ */
+ uninstall: function() {
+ TraceKit.report.uninstall();
+
+ this._restoreBuiltIns();
+
+ Error.stackTraceLimit = this._originalErrorStackTraceLimit;
+ this._isRavenInstalled = false;
+
+ return this;
+ },
+
+ /*
+ * Manually capture an exception and send it over to Sentry
+ *
+ * @param {error} ex An exception to be logged
+ * @param {object} options A specific set of options for this error [optional]
+ * @return {Raven}
+ */
+ captureException: function(ex, options) {
+ // Cases for sending ex as a message, rather than an exception
+ var isNotError = !isError(ex);
+ var isNotErrorEvent = !isErrorEvent(ex);
+ var isErrorEventWithoutError = isErrorEvent(ex) && !ex.error;
+
+ if ((isNotError && isNotErrorEvent) || isErrorEventWithoutError) {
+ return this.captureMessage(
+ ex,
+ objectMerge(
+ {
+ trimHeadFrames: 1,
+ stacktrace: true // if we fall back to captureMessage, default to attempting a new trace
+ },
+ options
+ )
+ );
+ }
+
+ // Get actual Error from ErrorEvent
+ if (isErrorEvent(ex)) ex = ex.error;
+
+ // Store the raw exception object for potential debugging and introspection
+ this._lastCapturedException = ex;
+
+ // TraceKit.report will re-raise any exception passed to it,
+ // which means you have to wrap it in try/catch. Instead, we
+ // can wrap it here and only re-raise if TraceKit.report
+ // raises an exception different from the one we asked to
+ // report on.
+ try {
+ var stack = TraceKit.computeStackTrace(ex);
+ this._handleStackInfo(stack, options);
+ } catch (ex1) {
+ if (ex !== ex1) {
+ throw ex1;
+ }
+ }
+
+ return this;
+ },
+
+ /*
+ * Manually send a message to Sentry
+ *
+ * @param {string} msg A plain message to be captured in Sentry
+ * @param {object} options A specific set of options for this message [optional]
+ * @return {Raven}
+ */
+ captureMessage: function(msg, options) {
+ // config() automagically converts ignoreErrors from a list to a RegExp so we need to test for an
+ // early call; we'll error on the side of logging anything called before configuration since it's
+ // probably something you should see:
+ if (
+ !!this._globalOptions.ignoreErrors.test &&
+ this._globalOptions.ignoreErrors.test(msg)
+ ) {
+ return;
+ }
+
+ options = options || {};
+
+ var data = objectMerge(
+ {
+ message: msg + '' // Make sure it's actually a string
+ },
+ options
+ );
+
+ var ex;
+ // Generate a "synthetic" stack trace from this point.
+ // NOTE: If you are a Sentry user, and you are seeing this stack frame, it is NOT indicative
+ // of a bug with Raven.js. Sentry generates synthetic traces either by configuration,
+ // or if it catches a thrown object without a "stack" property.
+ try {
+ throw new Error(msg);
+ } catch (ex1) {
+ ex = ex1;
+ }
+
+ // null exception name so `Error` isn't prefixed to msg
+ ex.name = null;
+ var stack = TraceKit.computeStackTrace(ex);
+
+ // stack[0] is `throw new Error(msg)` call itself, we are interested in the frame that was just before that, stack[1]
+ var initialCall = stack.stack[1];
+
+ var fileurl = (initialCall && initialCall.url) || '';
+
+ if (
+ !!this._globalOptions.ignoreUrls.test &&
+ this._globalOptions.ignoreUrls.test(fileurl)
+ ) {
+ return;
+ }
+
+ if (
+ !!this._globalOptions.whitelistUrls.test &&
+ !this._globalOptions.whitelistUrls.test(fileurl)
+ ) {
+ return;
+ }
+
+ if (this._globalOptions.stacktrace || (options && options.stacktrace)) {
+ options = objectMerge(
+ {
+ // fingerprint on msg, not stack trace (legacy behavior, could be
+ // revisited)
+ fingerprint: msg,
+ // since we know this is a synthetic trace, the top N-most frames
+ // MUST be from Raven.js, so mark them as in_app later by setting
+ // trimHeadFrames
+ trimHeadFrames: (options.trimHeadFrames || 0) + 1
+ },
+ options
+ );
+
+ var frames = this._prepareFrames(stack, options);
+ data.stacktrace = {
+ // Sentry expects frames oldest to newest
+ frames: frames.reverse()
+ };
+ }
+
+ // Fire away!
+ this._send(data);
+
+ return this;
+ },
+
+ captureBreadcrumb: function(obj) {
+ var crumb = objectMerge(
+ {
+ timestamp: now() / 1000
+ },
+ obj
+ );
+
+ if (isFunction(this._globalOptions.breadcrumbCallback)) {
+ var result = this._globalOptions.breadcrumbCallback(crumb);
+
+ if (isObject(result) && !isEmptyObject(result)) {
+ crumb = result;
+ } else if (result === false) {
+ return this;
+ }
+ }
+
+ this._breadcrumbs.push(crumb);
+ if (this._breadcrumbs.length > this._globalOptions.maxBreadcrumbs) {
+ this._breadcrumbs.shift();
+ }
+ return this;
+ },
+
+ addPlugin: function(plugin /*arg1, arg2, ... argN*/) {
+ var pluginArgs = [].slice.call(arguments, 1);
+
+ this._plugins.push([plugin, pluginArgs]);
+ if (this._isRavenInstalled) {
+ this._drainPlugins();
+ }
+
+ return this;
+ },
+
+ /*
+ * Set/clear a user to be sent along with the payload.
+ *
+ * @param {object} user An object representing user data [optional]
+ * @return {Raven}
+ */
+ setUserContext: function(user) {
+ // Intentionally do not merge here since that's an unexpected behavior.
+ this._globalContext.user = user;
+
+ return this;
+ },
+
+ /*
+ * Merge extra attributes to be sent along with the payload.
+ *
+ * @param {object} extra An object representing extra data [optional]
+ * @return {Raven}
+ */
+ setExtraContext: function(extra) {
+ this._mergeContext('extra', extra);
+
+ return this;
+ },
+
+ /*
+ * Merge tags to be sent along with the payload.
+ *
+ * @param {object} tags An object representing tags [optional]
+ * @return {Raven}
+ */
+ setTagsContext: function(tags) {
+ this._mergeContext('tags', tags);
+
+ return this;
+ },
+
+ /*
+ * Clear all of the context.
+ *
+ * @return {Raven}
+ */
+ clearContext: function() {
+ this._globalContext = {};
+
+ return this;
+ },
+
+ /*
+ * Get a copy of the current context. This cannot be mutated.
+ *
+ * @return {object} copy of context
+ */
+ getContext: function() {
+ // lol javascript
+ return JSON.parse(stringify(this._globalContext));
+ },
+
+ /*
+ * Set environment of application
+ *
+ * @param {string} environment Typically something like 'production'.
+ * @return {Raven}
+ */
+ setEnvironment: function(environment) {
+ this._globalOptions.environment = environment;
+
+ return this;
+ },
+
+ /*
+ * Set release version of application
+ *
+ * @param {string} release Typically something like a git SHA to identify version
+ * @return {Raven}
+ */
+ setRelease: function(release) {
+ this._globalOptions.release = release;
+
+ return this;
+ },
+
+ /*
+ * Set the dataCallback option
+ *
+ * @param {function} callback The callback to run which allows the
+ * data blob to be mutated before sending
+ * @return {Raven}
+ */
+ setDataCallback: function(callback) {
+ var original = this._globalOptions.dataCallback;
+ this._globalOptions.dataCallback = keepOriginalCallback(original, callback);
+ return this;
+ },
+
+ /*
+ * Set the breadcrumbCallback option
+ *
+ * @param {function} callback The callback to run which allows filtering
+ * or mutating breadcrumbs
+ * @return {Raven}
+ */
+ setBreadcrumbCallback: function(callback) {
+ var original = this._globalOptions.breadcrumbCallback;
+ this._globalOptions.breadcrumbCallback = keepOriginalCallback(original, callback);
+ return this;
+ },
+
+ /*
+ * Set the shouldSendCallback option
+ *
+ * @param {function} callback The callback to run which allows
+ * introspecting the blob before sending
+ * @return {Raven}
+ */
+ setShouldSendCallback: function(callback) {
+ var original = this._globalOptions.shouldSendCallback;
+ this._globalOptions.shouldSendCallback = keepOriginalCallback(original, callback);
+ return this;
+ },
+
+ /**
+ * Override the default HTTP transport mechanism that transmits data
+ * to the Sentry server.
+ *
+ * @param {function} transport Function invoked instead of the default
+ * `makeRequest` handler.
+ *
+ * @return {Raven}
+ */
+ setTransport: function(transport) {
+ this._globalOptions.transport = transport;
+
+ return this;
+ },
+
+ /*
+ * Get the latest raw exception that was captured by Raven.
+ *
+ * @return {error}
+ */
+ lastException: function() {
+ return this._lastCapturedException;
+ },
+
+ /*
+ * Get the last event id
+ *
+ * @return {string}
+ */
+ lastEventId: function() {
+ return this._lastEventId;
+ },
+
+ /*
+ * Determine if Raven is setup and ready to go.
+ *
+ * @return {boolean}
+ */
+ isSetup: function() {
+ if (!this._hasJSON) return false; // needs JSON support
+ if (!this._globalServer) {
+ if (!this.ravenNotConfiguredError) {
+ this.ravenNotConfiguredError = true;
+ this._logDebug('error', 'Error: Raven has not been configured.');
+ }
+ return false;
+ }
+ return true;
+ },
+
+ afterLoad: function() {
+ // TODO: remove window dependence?
+
+ // Attempt to initialize Raven on load
+ var RavenConfig = _window.RavenConfig;
+ if (RavenConfig) {
+ this.config(RavenConfig.dsn, RavenConfig.config).install();
+ }
+ },
+
+ showReportDialog: function(options) {
+ if (
+ !_document // doesn't work without a document (React native)
+ )
+ return;
+
+ options = options || {};
+
+ var lastEventId = options.eventId || this.lastEventId();
+ if (!lastEventId) {
+ throw new RavenConfigError('Missing eventId');
+ }
+
+ var dsn = options.dsn || this._dsn;
+ if (!dsn) {
+ throw new RavenConfigError('Missing DSN');
+ }
+
+ var encode = encodeURIComponent;
+ var qs = '';
+ qs += '?eventId=' + encode(lastEventId);
+ qs += '&dsn=' + encode(dsn);
+
+ var user = options.user || this._globalContext.user;
+ if (user) {
+ if (user.name) qs += '&name=' + encode(user.name);
+ if (user.email) qs += '&email=' + encode(user.email);
+ }
+
+ var globalServer = this._getGlobalServer(this._parseDSN(dsn));
+
+ var script = _document.createElement('script');
+ script.async = true;
+ script.src = globalServer + '/api/embed/error-page/' + qs;
+ (_document.head || _document.body).appendChild(script);
+ },
+
+ /**** Private functions ****/
+ _ignoreNextOnError: function() {
+ var self = this;
+ this._ignoreOnError += 1;
+ setTimeout(function() {
+ // onerror should trigger before setTimeout
+ self._ignoreOnError -= 1;
+ });
+ },
+
+ _triggerEvent: function(eventType, options) {
+ // NOTE: `event` is a native browser thing, so let's avoid conflicting wiht it
+ var evt, key;
+
+ if (!this._hasDocument) return;
+
+ options = options || {};
+
+ eventType = 'raven' + eventType.substr(0, 1).toUpperCase() + eventType.substr(1);
+
+ if (_document.createEvent) {
+ evt = _document.createEvent('HTMLEvents');
+ evt.initEvent(eventType, true, true);
+ } else {
+ evt = _document.createEventObject();
+ evt.eventType = eventType;
+ }
+
+ for (key in options)
+ if (hasKey(options, key)) {
+ evt[key] = options[key];
+ }
+
+ if (_document.createEvent) {
+ // IE9 if standards
+ _document.dispatchEvent(evt);
+ } else {
+ // IE8 regardless of Quirks or Standards
+ // IE9 if quirks
+ try {
+ _document.fireEvent('on' + evt.eventType.toLowerCase(), evt);
+ } catch (e) {
+ // Do nothing
+ }
+ }
+ },
+
+ /**
+ * Wraps addEventListener to capture UI breadcrumbs
+ * @param evtName the event name (e.g. "click")
+ * @returns {Function}
+ * @private
+ */
+ _breadcrumbEventHandler: function(evtName) {
+ var self = this;
+ return function(evt) {
+ // reset keypress timeout; e.g. triggering a 'click' after
+ // a 'keypress' will reset the keypress debounce so that a new
+ // set of keypresses can be recorded
+ self._keypressTimeout = null;
+
+ // It's possible this handler might trigger multiple times for the same
+ // event (e.g. event propagation through node ancestors). Ignore if we've
+ // already captured the event.
+ if (self._lastCapturedEvent === evt) return;
+
+ self._lastCapturedEvent = evt;
+
+ // try/catch both:
+ // - accessing evt.target (see getsentry/raven-js#838, #768)
+ // - `htmlTreeAsString` because it's complex, and just accessing the DOM incorrectly
+ // can throw an exception in some circumstances.
+ var target;
+ try {
+ target = htmlTreeAsString(evt.target);
+ } catch (e) {
+ target = '
';
+ }
+
+ self.captureBreadcrumb({
+ category: 'ui.' + evtName, // e.g. ui.click, ui.input
+ message: target
+ });
+ };
+ },
+
+ /**
+ * Wraps addEventListener to capture keypress UI events
+ * @returns {Function}
+ * @private
+ */
+ _keypressEventHandler: function() {
+ var self = this,
+ debounceDuration = 1000; // milliseconds
+
+ // TODO: if somehow user switches keypress target before
+ // debounce timeout is triggered, we will only capture
+ // a single breadcrumb from the FIRST target (acceptable?)
+ return function(evt) {
+ var target;
+ try {
+ target = evt.target;
+ } catch (e) {
+ // just accessing event properties can throw an exception in some rare circumstances
+ // see: https://github.com/getsentry/raven-js/issues/838
+ return;
+ }
+ var tagName = target && target.tagName;
+
+ // only consider keypress events on actual input elements
+ // this will disregard keypresses targeting body (e.g. tabbing
+ // through elements, hotkeys, etc)
+ if (
+ !tagName ||
+ (tagName !== 'INPUT' && tagName !== 'TEXTAREA' && !target.isContentEditable)
+ )
+ return;
+
+ // record first keypress in a series, but ignore subsequent
+ // keypresses until debounce clears
+ var timeout = self._keypressTimeout;
+ if (!timeout) {
+ self._breadcrumbEventHandler('input')(evt);
+ }
+ clearTimeout(timeout);
+ self._keypressTimeout = setTimeout(function() {
+ self._keypressTimeout = null;
+ }, debounceDuration);
+ };
+ },
+
+ /**
+ * Captures a breadcrumb of type "navigation", normalizing input URLs
+ * @param to the originating URL
+ * @param from the target URL
+ * @private
+ */
+ _captureUrlChange: function(from, to) {
+ var parsedLoc = parseUrl(this._location.href);
+ var parsedTo = parseUrl(to);
+ var parsedFrom = parseUrl(from);
+
+ // because onpopstate only tells you the "new" (to) value of location.href, and
+ // not the previous (from) value, we need to track the value of the current URL
+ // state ourselves
+ this._lastHref = to;
+
+ // Use only the path component of the URL if the URL matches the current
+ // document (almost all the time when using pushState)
+ if (parsedLoc.protocol === parsedTo.protocol && parsedLoc.host === parsedTo.host)
+ to = parsedTo.relative;
+ if (parsedLoc.protocol === parsedFrom.protocol && parsedLoc.host === parsedFrom.host)
+ from = parsedFrom.relative;
+
+ this.captureBreadcrumb({
+ category: 'navigation',
+ data: {
+ to: to,
+ from: from
+ }
+ });
+ },
+
+ /**
+ * Wrap timer functions and event targets to catch errors and provide
+ * better metadata.
+ */
+ _instrumentTryCatch: function() {
+ var self = this;
+
+ var wrappedBuiltIns = self._wrappedBuiltIns;
+
+ function wrapTimeFn(orig) {
+ return function(fn, t) {
+ // preserve arity
+ // Make a copy of the arguments to prevent deoptimization
+ // https://github.com/petkaantonov/bluebird/wiki/Optimization-killers#32-leaking-arguments
+ var args = new Array(arguments.length);
+ for (var i = 0; i < args.length; ++i) {
+ args[i] = arguments[i];
+ }
+ var originalCallback = args[0];
+ if (isFunction(originalCallback)) {
+ args[0] = self.wrap(originalCallback);
+ }
+
+ // IE < 9 doesn't support .call/.apply on setInterval/setTimeout, but it
+ // also supports only two arguments and doesn't care what this is, so we
+ // can just call the original function directly.
+ if (orig.apply) {
+ return orig.apply(this, args);
+ } else {
+ return orig(args[0], args[1]);
+ }
+ };
+ }
+
+ var autoBreadcrumbs = this._globalOptions.autoBreadcrumbs;
+
+ function wrapEventTarget(global) {
+ var proto = _window[global] && _window[global].prototype;
+ if (proto && proto.hasOwnProperty && proto.hasOwnProperty('addEventListener')) {
+ fill(
+ proto,
+ 'addEventListener',
+ function(orig) {
+ return function(evtName, fn, capture, secure) {
+ // preserve arity
+ try {
+ if (fn && fn.handleEvent) {
+ fn.handleEvent = self.wrap(fn.handleEvent);
+ }
+ } catch (err) {
+ // can sometimes get 'Permission denied to access property "handle Event'
+ }
+
+ // More breadcrumb DOM capture ... done here and not in `_instrumentBreadcrumbs`
+ // so that we don't have more than one wrapper function
+ var before, clickHandler, keypressHandler;
+
+ if (
+ autoBreadcrumbs &&
+ autoBreadcrumbs.dom &&
+ (global === 'EventTarget' || global === 'Node')
+ ) {
+ // NOTE: generating multiple handlers per addEventListener invocation, should
+ // revisit and verify we can just use one (almost certainly)
+ clickHandler = self._breadcrumbEventHandler('click');
+ keypressHandler = self._keypressEventHandler();
+ before = function(evt) {
+ // need to intercept every DOM event in `before` argument, in case that
+ // same wrapped method is re-used for different events (e.g. mousemove THEN click)
+ // see #724
+ if (!evt) return;
+
+ var eventType;
+ try {
+ eventType = evt.type;
+ } catch (e) {
+ // just accessing event properties can throw an exception in some rare circumstances
+ // see: https://github.com/getsentry/raven-js/issues/838
+ return;
+ }
+ if (eventType === 'click') return clickHandler(evt);
+ else if (eventType === 'keypress') return keypressHandler(evt);
+ };
+ }
+ return orig.call(
+ this,
+ evtName,
+ self.wrap(fn, undefined, before),
+ capture,
+ secure
+ );
+ };
+ },
+ wrappedBuiltIns
+ );
+ fill(
+ proto,
+ 'removeEventListener',
+ function(orig) {
+ return function(evt, fn, capture, secure) {
+ try {
+ fn = fn && (fn.__raven_wrapper__ ? fn.__raven_wrapper__ : fn);
+ } catch (e) {
+ // ignore, accessing __raven_wrapper__ will throw in some Selenium environments
+ }
+ return orig.call(this, evt, fn, capture, secure);
+ };
+ },
+ wrappedBuiltIns
+ );
+ }
+ }
+
+ fill(_window, 'setTimeout', wrapTimeFn, wrappedBuiltIns);
+ fill(_window, 'setInterval', wrapTimeFn, wrappedBuiltIns);
+ if (_window.requestAnimationFrame) {
+ fill(
+ _window,
+ 'requestAnimationFrame',
+ function(orig) {
+ return function(cb) {
+ return orig(self.wrap(cb));
+ };
+ },
+ wrappedBuiltIns
+ );
+ }
+
+ // event targets borrowed from bugsnag-js:
+ // https://github.com/bugsnag/bugsnag-js/blob/master/src/bugsnag.js#L666
+ var eventTargets = [
+ 'EventTarget',
+ 'Window',
+ 'Node',
+ 'ApplicationCache',
+ 'AudioTrackList',
+ 'ChannelMergerNode',
+ 'CryptoOperation',
+ 'EventSource',
+ 'FileReader',
+ 'HTMLUnknownElement',
+ 'IDBDatabase',
+ 'IDBRequest',
+ 'IDBTransaction',
+ 'KeyOperation',
+ 'MediaController',
+ 'MessagePort',
+ 'ModalWindow',
+ 'Notification',
+ 'SVGElementInstance',
+ 'Screen',
+ 'TextTrack',
+ 'TextTrackCue',
+ 'TextTrackList',
+ 'WebSocket',
+ 'WebSocketWorker',
+ 'Worker',
+ 'XMLHttpRequest',
+ 'XMLHttpRequestEventTarget',
+ 'XMLHttpRequestUpload'
+ ];
+ for (var i = 0; i < eventTargets.length; i++) {
+ wrapEventTarget(eventTargets[i]);
+ }
+ },
+
+ /**
+ * Instrument browser built-ins w/ breadcrumb capturing
+ * - XMLHttpRequests
+ * - DOM interactions (click/typing)
+ * - window.location changes
+ * - console
+ *
+ * Can be disabled or individually configured via the `autoBreadcrumbs` config option
+ */
+ _instrumentBreadcrumbs: function() {
+ var self = this;
+ var autoBreadcrumbs = this._globalOptions.autoBreadcrumbs;
+
+ var wrappedBuiltIns = self._wrappedBuiltIns;
+
+ function wrapProp(prop, xhr) {
+ if (prop in xhr && isFunction(xhr[prop])) {
+ fill(xhr, prop, function(orig) {
+ return self.wrap(orig);
+ }); // intentionally don't track filled methods on XHR instances
+ }
+ }
+
+ if (autoBreadcrumbs.xhr && 'XMLHttpRequest' in _window) {
+ var xhrproto = XMLHttpRequest.prototype;
+ fill(
+ xhrproto,
+ 'open',
+ function(origOpen) {
+ return function(method, url) {
+ // preserve arity
+
+ // if Sentry key appears in URL, don't capture
+ if (isString(url) && url.indexOf(self._globalKey) === -1) {
+ this.__raven_xhr = {
+ method: method,
+ url: url,
+ status_code: null
+ };
+ }
+
+ return origOpen.apply(this, arguments);
+ };
+ },
+ wrappedBuiltIns
+ );
+
+ fill(
+ xhrproto,
+ 'send',
+ function(origSend) {
+ return function(data) {
+ // preserve arity
+ var xhr = this;
+
+ function onreadystatechangeHandler() {
+ if (xhr.__raven_xhr && xhr.readyState === 4) {
+ try {
+ // touching statusCode in some platforms throws
+ // an exception
+ xhr.__raven_xhr.status_code = xhr.status;
+ } catch (e) {
+ /* do nothing */
+ }
+
+ self.captureBreadcrumb({
+ type: 'http',
+ category: 'xhr',
+ data: xhr.__raven_xhr
+ });
+ }
+ }
+
+ var props = ['onload', 'onerror', 'onprogress'];
+ for (var j = 0; j < props.length; j++) {
+ wrapProp(props[j], xhr);
+ }
+
+ if ('onreadystatechange' in xhr && isFunction(xhr.onreadystatechange)) {
+ fill(
+ xhr,
+ 'onreadystatechange',
+ function(orig) {
+ return self.wrap(orig, undefined, onreadystatechangeHandler);
+ } /* intentionally don't track this instrumentation */
+ );
+ } else {
+ // if onreadystatechange wasn't actually set by the page on this xhr, we
+ // are free to set our own and capture the breadcrumb
+ xhr.onreadystatechange = onreadystatechangeHandler;
+ }
+
+ return origSend.apply(this, arguments);
+ };
+ },
+ wrappedBuiltIns
+ );
+ }
+
+ if (autoBreadcrumbs.xhr && 'fetch' in _window) {
+ fill(
+ _window,
+ 'fetch',
+ function(origFetch) {
+ return function(fn, t) {
+ // preserve arity
+ // Make a copy of the arguments to prevent deoptimization
+ // https://github.com/petkaantonov/bluebird/wiki/Optimization-killers#32-leaking-arguments
+ var args = new Array(arguments.length);
+ for (var i = 0; i < args.length; ++i) {
+ args[i] = arguments[i];
+ }
+
+ var fetchInput = args[0];
+ var method = 'GET';
+ var url;
+
+ if (typeof fetchInput === 'string') {
+ url = fetchInput;
+ } else if ('Request' in _window && fetchInput instanceof _window.Request) {
+ url = fetchInput.url;
+ if (fetchInput.method) {
+ method = fetchInput.method;
+ }
+ } else {
+ url = '' + fetchInput;
+ }
+
+ if (args[1] && args[1].method) {
+ method = args[1].method;
+ }
+
+ var fetchData = {
+ method: method,
+ url: url,
+ status_code: null
+ };
+
+ self.captureBreadcrumb({
+ type: 'http',
+ category: 'fetch',
+ data: fetchData
+ });
+
+ return origFetch.apply(this, args).then(function(response) {
+ fetchData.status_code = response.status;
+
+ return response;
+ });
+ };
+ },
+ wrappedBuiltIns
+ );
+ }
+
+ // Capture breadcrumbs from any click that is unhandled / bubbled up all the way
+ // to the document. Do this before we instrument addEventListener.
+ if (autoBreadcrumbs.dom && this._hasDocument) {
+ if (_document.addEventListener) {
+ _document.addEventListener('click', self._breadcrumbEventHandler('click'), false);
+ _document.addEventListener('keypress', self._keypressEventHandler(), false);
+ } else {
+ // IE8 Compatibility
+ _document.attachEvent('onclick', self._breadcrumbEventHandler('click'));
+ _document.attachEvent('onkeypress', self._keypressEventHandler());
+ }
+ }
+
+ // record navigation (URL) changes
+ // NOTE: in Chrome App environment, touching history.pushState, *even inside
+ // a try/catch block*, will cause Chrome to output an error to console.error
+ // borrowed from: https://github.com/angular/angular.js/pull/13945/files
+ var chrome = _window.chrome;
+ var isChromePackagedApp = chrome && chrome.app && chrome.app.runtime;
+ var hasPushAndReplaceState =
+ !isChromePackagedApp &&
+ _window.history &&
+ history.pushState &&
+ history.replaceState;
+ if (autoBreadcrumbs.location && hasPushAndReplaceState) {
+ // TODO: remove onpopstate handler on uninstall()
+ var oldOnPopState = _window.onpopstate;
+ _window.onpopstate = function() {
+ var currentHref = self._location.href;
+ self._captureUrlChange(self._lastHref, currentHref);
+
+ if (oldOnPopState) {
+ return oldOnPopState.apply(this, arguments);
+ }
+ };
+
+ var historyReplacementFunction = function(origHistFunction) {
+ // note history.pushState.length is 0; intentionally not declaring
+ // params to preserve 0 arity
+ return function(/* state, title, url */) {
+ var url = arguments.length > 2 ? arguments[2] : undefined;
+
+ // url argument is optional
+ if (url) {
+ // coerce to string (this is what pushState does)
+ self._captureUrlChange(self._lastHref, url + '');
+ }
+
+ return origHistFunction.apply(this, arguments);
+ };
+ };
+
+ fill(history, 'pushState', historyReplacementFunction, wrappedBuiltIns);
+ fill(history, 'replaceState', historyReplacementFunction, wrappedBuiltIns);
+ }
+
+ if (autoBreadcrumbs.console && 'console' in _window && console.log) {
+ // console
+ var consoleMethodCallback = function(msg, data) {
+ self.captureBreadcrumb({
+ message: msg,
+ level: data.level,
+ category: 'console'
+ });
+ };
+
+ each(['debug', 'info', 'warn', 'error', 'log'], function(_, level) {
+ wrapConsoleMethod(console, level, consoleMethodCallback);
+ });
+ }
+ },
+
+ _restoreBuiltIns: function() {
+ // restore any wrapped builtins
+ var builtin;
+ while (this._wrappedBuiltIns.length) {
+ builtin = this._wrappedBuiltIns.shift();
+
+ var obj = builtin[0],
+ name = builtin[1],
+ orig = builtin[2];
+
+ obj[name] = orig;
+ }
+ },
+
+ _drainPlugins: function() {
+ var self = this;
+
+ // FIX ME TODO
+ each(this._plugins, function(_, plugin) {
+ var installer = plugin[0];
+ var args = plugin[1];
+ installer.apply(self, [self].concat(args));
+ });
+ },
+
+ _parseDSN: function(str) {
+ var m = dsnPattern.exec(str),
+ dsn = {},
+ i = 7;
+
+ try {
+ while (i--) dsn[dsnKeys[i]] = m[i] || '';
+ } catch (e) {
+ throw new RavenConfigError('Invalid DSN: ' + str);
+ }
+
+ if (dsn.pass && !this._globalOptions.allowSecretKey) {
+ throw new RavenConfigError(
+ 'Do not specify your secret key in the DSN. See: http://bit.ly/raven-secret-key'
+ );
+ }
+
+ return dsn;
+ },
+
+ _getGlobalServer: function(uri) {
+ // assemble the endpoint from the uri pieces
+ var globalServer = '//' + uri.host + (uri.port ? ':' + uri.port : '');
+
+ if (uri.protocol) {
+ globalServer = uri.protocol + ':' + globalServer;
+ }
+ return globalServer;
+ },
+
+ _handleOnErrorStackInfo: function() {
+ // if we are intentionally ignoring errors via onerror, bail out
+ if (!this._ignoreOnError) {
+ this._handleStackInfo.apply(this, arguments);
+ }
+ },
+
+ _handleStackInfo: function(stackInfo, options) {
+ var frames = this._prepareFrames(stackInfo, options);
+
+ this._triggerEvent('handle', {
+ stackInfo: stackInfo,
+ options: options
+ });
+
+ this._processException(
+ stackInfo.name,
+ stackInfo.message,
+ stackInfo.url,
+ stackInfo.lineno,
+ frames,
+ options
+ );
+ },
+
+ _prepareFrames: function(stackInfo, options) {
+ var self = this;
+ var frames = [];
+ if (stackInfo.stack && stackInfo.stack.length) {
+ each(stackInfo.stack, function(i, stack) {
+ var frame = self._normalizeFrame(stack, stackInfo.url);
+ if (frame) {
+ frames.push(frame);
+ }
+ });
+
+ // e.g. frames captured via captureMessage throw
+ if (options && options.trimHeadFrames) {
+ for (var j = 0; j < options.trimHeadFrames && j < frames.length; j++) {
+ frames[j].in_app = false;
+ }
+ }
+ }
+ frames = frames.slice(0, this._globalOptions.stackTraceLimit);
+ return frames;
+ },
+
+ _normalizeFrame: function(frame, stackInfoUrl) {
+ // normalize the frames data
+ var normalized = {
+ filename: frame.url,
+ lineno: frame.line,
+ colno: frame.column,
+ function: frame.func || '?'
+ };
+
+ // Case when we don't have any information about the error
+ // E.g. throwing a string or raw object, instead of an `Error` in Firefox
+ // Generating synthetic error doesn't add any value here
+ //
+ // We should probably somehow let a user know that they should fix their code
+ if (!frame.url) {
+ normalized.filename = stackInfoUrl; // fallback to whole stacks url from onerror handler
+ }
+
+ normalized.in_app = !// determine if an exception came from outside of our app
+ // first we check the global includePaths list.
+ (
+ (!!this._globalOptions.includePaths.test &&
+ !this._globalOptions.includePaths.test(normalized.filename)) ||
+ // Now we check for fun, if the function name is Raven or TraceKit
+ /(Raven|TraceKit)\./.test(normalized['function']) ||
+ // finally, we do a last ditch effort and check for raven.min.js
+ /raven\.(min\.)?js$/.test(normalized.filename)
+ );
+
+ return normalized;
+ },
+
+ _processException: function(type, message, fileurl, lineno, frames, options) {
+ var prefixedMessage = (type ? type + ': ' : '') + (message || '');
+ if (
+ !!this._globalOptions.ignoreErrors.test &&
+ (this._globalOptions.ignoreErrors.test(message) ||
+ this._globalOptions.ignoreErrors.test(prefixedMessage))
+ ) {
+ return;
+ }
+
+ var stacktrace;
+
+ if (frames && frames.length) {
+ fileurl = frames[0].filename || fileurl;
+ // Sentry expects frames oldest to newest
+ // and JS sends them as newest to oldest
+ frames.reverse();
+ stacktrace = {frames: frames};
+ } else if (fileurl) {
+ stacktrace = {
+ frames: [
+ {
+ filename: fileurl,
+ lineno: lineno,
+ in_app: true
+ }
+ ]
+ };
+ }
+
+ if (
+ !!this._globalOptions.ignoreUrls.test &&
+ this._globalOptions.ignoreUrls.test(fileurl)
+ ) {
+ return;
+ }
+
+ if (
+ !!this._globalOptions.whitelistUrls.test &&
+ !this._globalOptions.whitelistUrls.test(fileurl)
+ ) {
+ return;
+ }
+
+ var data = objectMerge(
+ {
+ // sentry.interfaces.Exception
+ exception: {
+ values: [
+ {
+ type: type,
+ value: message,
+ stacktrace: stacktrace
+ }
+ ]
+ },
+ culprit: fileurl
+ },
+ options
+ );
+
+ // Fire away!
+ this._send(data);
+ },
+
+ _trimPacket: function(data) {
+ // For now, we only want to truncate the two different messages
+ // but this could/should be expanded to just trim everything
+ var max = this._globalOptions.maxMessageLength;
+ if (data.message) {
+ data.message = truncate(data.message, max);
+ }
+ if (data.exception) {
+ var exception = data.exception.values[0];
+ exception.value = truncate(exception.value, max);
+ }
+
+ var request = data.request;
+ if (request) {
+ if (request.url) {
+ request.url = truncate(request.url, this._globalOptions.maxUrlLength);
+ }
+ if (request.Referer) {
+ request.Referer = truncate(request.Referer, this._globalOptions.maxUrlLength);
+ }
+ }
+
+ if (data.breadcrumbs && data.breadcrumbs.values)
+ this._trimBreadcrumbs(data.breadcrumbs);
+
+ return data;
+ },
+
+ /**
+ * Truncate breadcrumb values (right now just URLs)
+ */
+ _trimBreadcrumbs: function(breadcrumbs) {
+ // known breadcrumb properties with urls
+ // TODO: also consider arbitrary prop values that start with (https?)?://
+ var urlProps = ['to', 'from', 'url'],
+ urlProp,
+ crumb,
+ data;
+
+ for (var i = 0; i < breadcrumbs.values.length; ++i) {
+ crumb = breadcrumbs.values[i];
+ if (
+ !crumb.hasOwnProperty('data') ||
+ !isObject(crumb.data) ||
+ objectFrozen(crumb.data)
+ )
+ continue;
+
+ data = objectMerge({}, crumb.data);
+ for (var j = 0; j < urlProps.length; ++j) {
+ urlProp = urlProps[j];
+ if (data.hasOwnProperty(urlProp) && data[urlProp]) {
+ data[urlProp] = truncate(data[urlProp], this._globalOptions.maxUrlLength);
+ }
+ }
+ breadcrumbs.values[i].data = data;
+ }
+ },
+
+ _getHttpData: function() {
+ if (!this._hasNavigator && !this._hasDocument) return;
+ var httpData = {};
+
+ if (this._hasNavigator && _navigator.userAgent) {
+ httpData.headers = {
+ 'User-Agent': navigator.userAgent
+ };
+ }
+
+ if (this._hasDocument) {
+ if (_document.location && _document.location.href) {
+ httpData.url = _document.location.href;
+ }
+ if (_document.referrer) {
+ if (!httpData.headers) httpData.headers = {};
+ httpData.headers.Referer = _document.referrer;
+ }
+ }
+
+ return httpData;
+ },
+
+ _resetBackoff: function() {
+ this._backoffDuration = 0;
+ this._backoffStart = null;
+ },
+
+ _shouldBackoff: function() {
+ return this._backoffDuration && now() - this._backoffStart < this._backoffDuration;
+ },
+
+ /**
+ * Returns true if the in-process data payload matches the signature
+ * of the previously-sent data
+ *
+ * NOTE: This has to be done at this level because TraceKit can generate
+ * data from window.onerror WITHOUT an exception object (IE8, IE9,
+ * other old browsers). This can take the form of an "exception"
+ * data object with a single frame (derived from the onerror args).
+ */
+ _isRepeatData: function(current) {
+ var last = this._lastData;
+
+ if (
+ !last ||
+ current.message !== last.message || // defined for captureMessage
+ current.culprit !== last.culprit // defined for captureException/onerror
+ )
+ return false;
+
+ // Stacktrace interface (i.e. from captureMessage)
+ if (current.stacktrace || last.stacktrace) {
+ return isSameStacktrace(current.stacktrace, last.stacktrace);
+ } else if (current.exception || last.exception) {
+ // Exception interface (i.e. from captureException/onerror)
+ return isSameException(current.exception, last.exception);
+ }
+
+ return true;
+ },
+
+ _setBackoffState: function(request) {
+ // If we are already in a backoff state, don't change anything
+ if (this._shouldBackoff()) {
+ return;
+ }
+
+ var status = request.status;
+
+ // 400 - project_id doesn't exist or some other fatal
+ // 401 - invalid/revoked dsn
+ // 429 - too many requests
+ if (!(status === 400 || status === 401 || status === 429)) return;
+
+ var retry;
+ try {
+ // If Retry-After is not in Access-Control-Expose-Headers, most
+ // browsers will throw an exception trying to access it
+ retry = request.getResponseHeader('Retry-After');
+ retry = parseInt(retry, 10) * 1000; // Retry-After is returned in seconds
+ } catch (e) {
+ /* eslint no-empty:0 */
+ }
+
+ this._backoffDuration = retry
+ ? // If Sentry server returned a Retry-After value, use it
+ retry
+ : // Otherwise, double the last backoff duration (starts at 1 sec)
+ this._backoffDuration * 2 || 1000;
+
+ this._backoffStart = now();
+ },
+
+ _send: function(data) {
+ var globalOptions = this._globalOptions;
+
+ var baseData = {
+ project: this._globalProject,
+ logger: globalOptions.logger,
+ platform: 'javascript'
+ },
+ httpData = this._getHttpData();
+
+ if (httpData) {
+ baseData.request = httpData;
+ }
+
+ // HACK: delete `trimHeadFrames` to prevent from appearing in outbound payload
+ if (data.trimHeadFrames) delete data.trimHeadFrames;
+
+ data = objectMerge(baseData, data);
+
+ // Merge in the tags and extra separately since objectMerge doesn't handle a deep merge
+ data.tags = objectMerge(objectMerge({}, this._globalContext.tags), data.tags);
+ data.extra = objectMerge(objectMerge({}, this._globalContext.extra), data.extra);
+
+ // Send along our own collected metadata with extra
+ data.extra['session:duration'] = now() - this._startTime;
+
+ if (this._breadcrumbs && this._breadcrumbs.length > 0) {
+ // intentionally make shallow copy so that additions
+ // to breadcrumbs aren't accidentally sent in this request
+ data.breadcrumbs = {
+ values: [].slice.call(this._breadcrumbs, 0)
+ };
+ }
+
+ // If there are no tags/extra, strip the key from the payload alltogther.
+ if (isEmptyObject(data.tags)) delete data.tags;
+
+ if (this._globalContext.user) {
+ // sentry.interfaces.User
+ data.user = this._globalContext.user;
+ }
+
+ // Include the environment if it's defined in globalOptions
+ if (globalOptions.environment) data.environment = globalOptions.environment;
+
+ // Include the release if it's defined in globalOptions
+ if (globalOptions.release) data.release = globalOptions.release;
+
+ // Include server_name if it's defined in globalOptions
+ if (globalOptions.serverName) data.server_name = globalOptions.serverName;
+
+ if (isFunction(globalOptions.dataCallback)) {
+ data = globalOptions.dataCallback(data) || data;
+ }
+
+ // Why??????????
+ if (!data || isEmptyObject(data)) {
+ return;
+ }
+
+ // Check if the request should be filtered or not
+ if (
+ isFunction(globalOptions.shouldSendCallback) &&
+ !globalOptions.shouldSendCallback(data)
+ ) {
+ return;
+ }
+
+ // Backoff state: Sentry server previously responded w/ an error (e.g. 429 - too many requests),
+ // so drop requests until "cool-off" period has elapsed.
+ if (this._shouldBackoff()) {
+ this._logDebug('warn', 'Raven dropped error due to backoff: ', data);
+ return;
+ }
+
+ if (typeof globalOptions.sampleRate === 'number') {
+ if (Math.random() < globalOptions.sampleRate) {
+ this._sendProcessedPayload(data);
+ }
+ } else {
+ this._sendProcessedPayload(data);
+ }
+ },
+
+ _getUuid: function() {
+ return uuid4();
+ },
+
+ _sendProcessedPayload: function(data, callback) {
+ var self = this;
+ var globalOptions = this._globalOptions;
+
+ if (!this.isSetup()) return;
+
+ // Try and clean up the packet before sending by truncating long values
+ data = this._trimPacket(data);
+
+ // ideally duplicate error testing should occur *before* dataCallback/shouldSendCallback,
+ // but this would require copying an un-truncated copy of the data packet, which can be
+ // arbitrarily deep (extra_data) -- could be worthwhile? will revisit
+ if (!this._globalOptions.allowDuplicates && this._isRepeatData(data)) {
+ this._logDebug('warn', 'Raven dropped repeat event: ', data);
+ return;
+ }
+
+ // Send along an event_id if not explicitly passed.
+ // This event_id can be used to reference the error within Sentry itself.
+ // Set lastEventId after we know the error should actually be sent
+ this._lastEventId = data.event_id || (data.event_id = this._getUuid());
+
+ // Store outbound payload after trim
+ this._lastData = data;
+
+ this._logDebug('debug', 'Raven about to send:', data);
+
+ var auth = {
+ sentry_version: '7',
+ sentry_client: 'raven-js/' + this.VERSION,
+ sentry_key: this._globalKey
+ };
+
+ if (this._globalSecret) {
+ auth.sentry_secret = this._globalSecret;
+ }
+
+ var exception = data.exception && data.exception.values[0];
+ this.captureBreadcrumb({
+ category: 'sentry',
+ message: exception
+ ? (exception.type ? exception.type + ': ' : '') + exception.value
+ : data.message,
+ event_id: data.event_id,
+ level: data.level || 'error' // presume error unless specified
+ });
+
+ var url = this._globalEndpoint;
+ (globalOptions.transport || this._makeRequest).call(this, {
+ url: url,
+ auth: auth,
+ data: data,
+ options: globalOptions,
+ onSuccess: function success() {
+ self._resetBackoff();
+
+ self._triggerEvent('success', {
+ data: data,
+ src: url
+ });
+ callback && callback();
+ },
+ onError: function failure(error) {
+ self._logDebug('error', 'Raven transport failed to send: ', error);
+
+ if (error.request) {
+ self._setBackoffState(error.request);
+ }
+
+ self._triggerEvent('failure', {
+ data: data,
+ src: url
+ });
+ error = error || new Error('Raven send failed (no additional details provided)');
+ callback && callback(error);
+ }
+ });
+ },
+
+ _makeRequest: function(opts) {
+ var request = _window.XMLHttpRequest && new _window.XMLHttpRequest();
+ if (!request) return;
+
+ // if browser doesn't support CORS (e.g. IE7), we are out of luck
+ var hasCORS = 'withCredentials' in request || typeof XDomainRequest !== 'undefined';
+
+ if (!hasCORS) return;
+
+ var url = opts.url;
+
+ if ('withCredentials' in request) {
+ request.onreadystatechange = function() {
+ if (request.readyState !== 4) {
+ return;
+ } else if (request.status === 200) {
+ opts.onSuccess && opts.onSuccess();
+ } else if (opts.onError) {
+ var err = new Error('Sentry error code: ' + request.status);
+ err.request = request;
+ opts.onError(err);
+ }
+ };
+ } else {
+ request = new XDomainRequest();
+ // xdomainrequest cannot go http -> https (or vice versa),
+ // so always use protocol relative
+ url = url.replace(/^https?:/, '');
+
+ // onreadystatechange not supported by XDomainRequest
+ if (opts.onSuccess) {
+ request.onload = opts.onSuccess;
+ }
+ if (opts.onError) {
+ request.onerror = function() {
+ var err = new Error('Sentry error code: XDomainRequest');
+ err.request = request;
+ opts.onError(err);
+ };
+ }
+ }
+
+ // NOTE: auth is intentionally sent as part of query string (NOT as custom
+ // HTTP header) so as to avoid preflight CORS requests
+ request.open('POST', url + '?' + urlencode(opts.auth));
+ request.send(stringify(opts.data));
+ },
+
+ _logDebug: function(level) {
+ if (this._originalConsoleMethods[level] && this.debug) {
+ // In IE<10 console methods do not have their own 'apply' method
+ Function.prototype.apply.call(
+ this._originalConsoleMethods[level],
+ this._originalConsole,
+ [].slice.call(arguments, 1)
+ );
+ }
+ },
+
+ _mergeContext: function(key, context) {
+ if (isUndefined(context)) {
+ delete this._globalContext[key];
+ } else {
+ this._globalContext[key] = objectMerge(this._globalContext[key] || {}, context);
+ }
+ }
+};
+
+// Deprecations
+Raven.prototype.setUser = Raven.prototype.setUserContext;
+Raven.prototype.setReleaseContext = Raven.prototype.setRelease;
+
+module.exports = Raven;
+
+
+/***/ }),
+
+/***/ "./node_modules/raven-js/src/singleton.js":
+/*!************************************************!*\
+ !*** ./node_modules/raven-js/src/singleton.js ***!
+ \************************************************/
+/***/ ((module, __unused_webpack_exports, __webpack_require__) => {
+
+/**
+ * Enforces a single instance of the Raven client, and the
+ * main entry point for Raven. If you are a consumer of the
+ * Raven library, you SHOULD load this file (vs raven.js).
+ **/
+
+var RavenConstructor = __webpack_require__(/*! ./raven */ "./node_modules/raven-js/src/raven.js");
+
+// This is to be defensive in environments where window does not exist (see https://github.com/getsentry/raven-js/pull/785)
+var _window =
+ typeof window !== 'undefined'
+ ? window
+ : typeof __webpack_require__.g !== 'undefined' ? __webpack_require__.g : typeof self !== 'undefined' ? self : {};
+var _Raven = _window.Raven;
+
+var Raven = new RavenConstructor();
+
+/*
+ * Allow multiple versions of Raven to be installed.
+ * Strip Raven from the global context and returns the instance.
+ *
+ * @return {Raven}
+ */
+Raven.noConflict = function() {
+ _window.Raven = _Raven;
+ return Raven;
+};
+
+Raven.afterLoad();
+
+module.exports = Raven;
+
+
+/***/ }),
+
+/***/ "./node_modules/raven-js/src/utils.js":
+/*!********************************************!*\
+ !*** ./node_modules/raven-js/src/utils.js ***!
+ \********************************************/
+/***/ ((module, __unused_webpack_exports, __webpack_require__) => {
+
+var _window =
+ typeof window !== 'undefined'
+ ? window
+ : typeof __webpack_require__.g !== 'undefined' ? __webpack_require__.g : typeof self !== 'undefined' ? self : {};
+
+function isObject(what) {
+ return typeof what === 'object' && what !== null;
+}
+
+// Yanked from https://git.io/vS8DV re-used under CC0
+// with some tiny modifications
+function isError(value) {
+ switch ({}.toString.call(value)) {
+ case '[object Error]':
+ return true;
+ case '[object Exception]':
+ return true;
+ case '[object DOMException]':
+ return true;
+ default:
+ return value instanceof Error;
+ }
+}
+
+function isErrorEvent(value) {
+ return supportsErrorEvent() && {}.toString.call(value) === '[object ErrorEvent]';
+}
+
+function isUndefined(what) {
+ return what === void 0;
+}
+
+function isFunction(what) {
+ return typeof what === 'function';
+}
+
+function isString(what) {
+ return Object.prototype.toString.call(what) === '[object String]';
+}
+
+function isEmptyObject(what) {
+ for (var _ in what) return false; // eslint-disable-line guard-for-in, no-unused-vars
+ return true;
+}
+
+function supportsErrorEvent() {
+ try {
+ new ErrorEvent(''); // eslint-disable-line no-new
+ return true;
+ } catch (e) {
+ return false;
+ }
+}
+
+function wrappedCallback(callback) {
+ function dataCallback(data, original) {
+ var normalizedData = callback(data) || data;
+ if (original) {
+ return original(normalizedData) || normalizedData;
+ }
+ return normalizedData;
+ }
+
+ return dataCallback;
+}
+
+function each(obj, callback) {
+ var i, j;
+
+ if (isUndefined(obj.length)) {
+ for (i in obj) {
+ if (hasKey(obj, i)) {
+ callback.call(null, i, obj[i]);
+ }
+ }
+ } else {
+ j = obj.length;
+ if (j) {
+ for (i = 0; i < j; i++) {
+ callback.call(null, i, obj[i]);
+ }
+ }
+ }
+}
+
+function objectMerge(obj1, obj2) {
+ if (!obj2) {
+ return obj1;
+ }
+ each(obj2, function(key, value) {
+ obj1[key] = value;
+ });
+ return obj1;
+}
+
+/**
+ * This function is only used for react-native.
+ * react-native freezes object that have already been sent over the
+ * js bridge. We need this function in order to check if the object is frozen.
+ * So it's ok that objectFrozen returns false if Object.isFrozen is not
+ * supported because it's not relevant for other "platforms". See related issue:
+ * https://github.com/getsentry/react-native-sentry/issues/57
+ */
+function objectFrozen(obj) {
+ if (!Object.isFrozen) {
+ return false;
+ }
+ return Object.isFrozen(obj);
+}
+
+function truncate(str, max) {
+ return !max || str.length <= max ? str : str.substr(0, max) + '\u2026';
+}
+
+/**
+ * hasKey, a better form of hasOwnProperty
+ * Example: hasKey(MainHostObject, property) === true/false
+ *
+ * @param {Object} host object to check property
+ * @param {string} key to check
+ */
+function hasKey(object, key) {
+ return Object.prototype.hasOwnProperty.call(object, key);
+}
+
+function joinRegExp(patterns) {
+ // Combine an array of regular expressions and strings into one large regexp
+ // Be mad.
+ var sources = [],
+ i = 0,
+ len = patterns.length,
+ pattern;
+
+ for (; i < len; i++) {
+ pattern = patterns[i];
+ if (isString(pattern)) {
+ // If it's a string, we need to escape it
+ // Taken from: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Guide/Regular_Expressions
+ sources.push(pattern.replace(/([.*+?^=!:${}()|\[\]\/\\])/g, '\\$1'));
+ } else if (pattern && pattern.source) {
+ // If it's a regexp already, we want to extract the source
+ sources.push(pattern.source);
+ }
+ // Intentionally skip other cases
+ }
+ return new RegExp(sources.join('|'), 'i');
+}
+
+function urlencode(o) {
+ var pairs = [];
+ each(o, function(key, value) {
+ pairs.push(encodeURIComponent(key) + '=' + encodeURIComponent(value));
+ });
+ return pairs.join('&');
+}
+
+// borrowed from https://tools.ietf.org/html/rfc3986#appendix-B
+// intentionally using regex and not href parsing trick because React Native and other
+// environments where DOM might not be available
+function parseUrl(url) {
+ var match = url.match(/^(([^:\/?#]+):)?(\/\/([^\/?#]*))?([^?#]*)(\?([^#]*))?(#(.*))?$/);
+ if (!match) return {};
+
+ // coerce to undefined values to empty string so we don't get 'undefined'
+ var query = match[6] || '';
+ var fragment = match[8] || '';
+ return {
+ protocol: match[2],
+ host: match[4],
+ path: match[5],
+ relative: match[5] + query + fragment // everything minus origin
+ };
+}
+function uuid4() {
+ var crypto = _window.crypto || _window.msCrypto;
+
+ if (!isUndefined(crypto) && crypto.getRandomValues) {
+ // Use window.crypto API if available
+ // eslint-disable-next-line no-undef
+ var arr = new Uint16Array(8);
+ crypto.getRandomValues(arr);
+
+ // set 4 in byte 7
+ arr[3] = (arr[3] & 0xfff) | 0x4000;
+ // set 2 most significant bits of byte 9 to '10'
+ arr[4] = (arr[4] & 0x3fff) | 0x8000;
+
+ var pad = function(num) {
+ var v = num.toString(16);
+ while (v.length < 4) {
+ v = '0' + v;
+ }
+ return v;
+ };
+
+ return (
+ pad(arr[0]) +
+ pad(arr[1]) +
+ pad(arr[2]) +
+ pad(arr[3]) +
+ pad(arr[4]) +
+ pad(arr[5]) +
+ pad(arr[6]) +
+ pad(arr[7])
+ );
+ } else {
+ // http://stackoverflow.com/questions/105034/how-to-create-a-guid-uuid-in-javascript/2117523#2117523
+ return 'xxxxxxxxxxxx4xxxyxxxxxxxxxxxxxxx'.replace(/[xy]/g, function(c) {
+ var r = (Math.random() * 16) | 0,
+ v = c === 'x' ? r : (r & 0x3) | 0x8;
+ return v.toString(16);
+ });
+ }
+}
+
+/**
+ * Given a child DOM element, returns a query-selector statement describing that
+ * and its ancestors
+ * e.g. [HTMLElement] => body > div > input#foo.btn[name=baz]
+ * @param elem
+ * @returns {string}
+ */
+function htmlTreeAsString(elem) {
+ /* eslint no-extra-parens:0*/
+ var MAX_TRAVERSE_HEIGHT = 5,
+ MAX_OUTPUT_LEN = 80,
+ out = [],
+ height = 0,
+ len = 0,
+ separator = ' > ',
+ sepLength = separator.length,
+ nextStr;
+
+ while (elem && height++ < MAX_TRAVERSE_HEIGHT) {
+ nextStr = htmlElementAsString(elem);
+ // bail out if
+ // - nextStr is the 'html' element
+ // - the length of the string that would be created exceeds MAX_OUTPUT_LEN
+ // (ignore this limit if we are on the first iteration)
+ if (
+ nextStr === 'html' ||
+ (height > 1 && len + out.length * sepLength + nextStr.length >= MAX_OUTPUT_LEN)
+ ) {
+ break;
+ }
+
+ out.push(nextStr);
+
+ len += nextStr.length;
+ elem = elem.parentNode;
+ }
+
+ return out.reverse().join(separator);
+}
+
+/**
+ * Returns a simple, query-selector representation of a DOM element
+ * e.g. [HTMLElement] => input#foo.btn[name=baz]
+ * @param HTMLElement
+ * @returns {string}
+ */
+function htmlElementAsString(elem) {
+ var out = [],
+ className,
+ classes,
+ key,
+ attr,
+ i;
+
+ if (!elem || !elem.tagName) {
+ return '';
+ }
+
+ out.push(elem.tagName.toLowerCase());
+ if (elem.id) {
+ out.push('#' + elem.id);
+ }
+
+ className = elem.className;
+ if (className && isString(className)) {
+ classes = className.split(/\s+/);
+ for (i = 0; i < classes.length; i++) {
+ out.push('.' + classes[i]);
+ }
+ }
+ var attrWhitelist = ['type', 'name', 'title', 'alt'];
+ for (i = 0; i < attrWhitelist.length; i++) {
+ key = attrWhitelist[i];
+ attr = elem.getAttribute(key);
+ if (attr) {
+ out.push('[' + key + '="' + attr + '"]');
+ }
+ }
+ return out.join('');
+}
+
+/**
+ * Returns true if either a OR b is truthy, but not both
+ */
+function isOnlyOneTruthy(a, b) {
+ return !!(!!a ^ !!b);
+}
+
+/**
+ * Returns true if the two input exception interfaces have the same content
+ */
+function isSameException(ex1, ex2) {
+ if (isOnlyOneTruthy(ex1, ex2)) return false;
+
+ ex1 = ex1.values[0];
+ ex2 = ex2.values[0];
+
+ if (ex1.type !== ex2.type || ex1.value !== ex2.value) return false;
+
+ return isSameStacktrace(ex1.stacktrace, ex2.stacktrace);
+}
+
+/**
+ * Returns true if the two input stack trace interfaces have the same content
+ */
+function isSameStacktrace(stack1, stack2) {
+ if (isOnlyOneTruthy(stack1, stack2)) return false;
+
+ var frames1 = stack1.frames;
+ var frames2 = stack2.frames;
+
+ // Exit early if frame count differs
+ if (frames1.length !== frames2.length) return false;
+
+ // Iterate through every frame; bail out if anything differs
+ var a, b;
+ for (var i = 0; i < frames1.length; i++) {
+ a = frames1[i];
+ b = frames2[i];
+ if (
+ a.filename !== b.filename ||
+ a.lineno !== b.lineno ||
+ a.colno !== b.colno ||
+ a['function'] !== b['function']
+ )
+ return false;
+ }
+ return true;
+}
+
+/**
+ * Polyfill a method
+ * @param obj object e.g. `document`
+ * @param name method name present on object e.g. `addEventListener`
+ * @param replacement replacement function
+ * @param track {optional} record instrumentation to an array
+ */
+function fill(obj, name, replacement, track) {
+ var orig = obj[name];
+ obj[name] = replacement(orig);
+ if (track) {
+ track.push([obj, name, orig]);
+ }
+}
+
+module.exports = {
+ isObject: isObject,
+ isError: isError,
+ isErrorEvent: isErrorEvent,
+ isUndefined: isUndefined,
+ isFunction: isFunction,
+ isString: isString,
+ isEmptyObject: isEmptyObject,
+ supportsErrorEvent: supportsErrorEvent,
+ wrappedCallback: wrappedCallback,
+ each: each,
+ objectMerge: objectMerge,
+ truncate: truncate,
+ objectFrozen: objectFrozen,
+ hasKey: hasKey,
+ joinRegExp: joinRegExp,
+ urlencode: urlencode,
+ uuid4: uuid4,
+ htmlTreeAsString: htmlTreeAsString,
+ htmlElementAsString: htmlElementAsString,
+ isSameException: isSameException,
+ isSameStacktrace: isSameStacktrace,
+ parseUrl: parseUrl,
+ fill: fill
+};
+
+
+/***/ }),
+
+/***/ "./node_modules/raven-js/vendor/TraceKit/tracekit.js":
+/*!***********************************************************!*\
+ !*** ./node_modules/raven-js/vendor/TraceKit/tracekit.js ***!
+ \***********************************************************/
+/***/ ((module, __unused_webpack_exports, __webpack_require__) => {
+
+var utils = __webpack_require__(/*! ../../src/utils */ "./node_modules/raven-js/src/utils.js");
+
+/*
+ TraceKit - Cross brower stack traces
+
+ This was originally forked from github.com/occ/TraceKit, but has since been
+ largely re-written and is now maintained as part of raven-js. Tests for
+ this are in test/vendor.
+
+ MIT license
+*/
+
+var TraceKit = {
+ collectWindowErrors: true,
+ debug: false
+};
+
+// This is to be defensive in environments where window does not exist (see https://github.com/getsentry/raven-js/pull/785)
+var _window =
+ typeof window !== 'undefined'
+ ? window
+ : typeof __webpack_require__.g !== 'undefined' ? __webpack_require__.g : typeof self !== 'undefined' ? self : {};
+
+// global reference to slice
+var _slice = [].slice;
+var UNKNOWN_FUNCTION = '?';
+
+// https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Error#Error_types
+var ERROR_TYPES_RE = /^(?:[Uu]ncaught (?:exception: )?)?(?:((?:Eval|Internal|Range|Reference|Syntax|Type|URI|)Error): )?(.*)$/;
+
+function getLocationHref() {
+ if (typeof document === 'undefined' || document.location == null) return '';
+
+ return document.location.href;
+}
+
+/**
+ * TraceKit.report: cross-browser processing of unhandled exceptions
+ *
+ * Syntax:
+ * TraceKit.report.subscribe(function(stackInfo) { ... })
+ * TraceKit.report.unsubscribe(function(stackInfo) { ... })
+ * TraceKit.report(exception)
+ * try { ...code... } catch(ex) { TraceKit.report(ex); }
+ *
+ * Supports:
+ * - Firefox: full stack trace with line numbers, plus column number
+ * on top frame; column number is not guaranteed
+ * - Opera: full stack trace with line and column numbers
+ * - Chrome: full stack trace with line and column numbers
+ * - Safari: line and column number for the top frame only; some frames
+ * may be missing, and column number is not guaranteed
+ * - IE: line and column number for the top frame only; some frames
+ * may be missing, and column number is not guaranteed
+ *
+ * In theory, TraceKit should work on all of the following versions:
+ * - IE5.5+ (only 8.0 tested)
+ * - Firefox 0.9+ (only 3.5+ tested)
+ * - Opera 7+ (only 10.50 tested; versions 9 and earlier may require
+ * Exceptions Have Stacktrace to be enabled in opera:config)
+ * - Safari 3+ (only 4+ tested)
+ * - Chrome 1+ (only 5+ tested)
+ * - Konqueror 3.5+ (untested)
+ *
+ * Requires TraceKit.computeStackTrace.
+ *
+ * Tries to catch all unhandled exceptions and report them to the
+ * subscribed handlers. Please note that TraceKit.report will rethrow the
+ * exception. This is REQUIRED in order to get a useful stack trace in IE.
+ * If the exception does not reach the top of the browser, you will only
+ * get a stack trace from the point where TraceKit.report was called.
+ *
+ * Handlers receive a stackInfo object as described in the
+ * TraceKit.computeStackTrace docs.
+ */
+TraceKit.report = (function reportModuleWrapper() {
+ var handlers = [],
+ lastArgs = null,
+ lastException = null,
+ lastExceptionStack = null;
+
+ /**
+ * Add a crash handler.
+ * @param {Function} handler
+ */
+ function subscribe(handler) {
+ installGlobalHandler();
+ handlers.push(handler);
+ }
+
+ /**
+ * Remove a crash handler.
+ * @param {Function} handler
+ */
+ function unsubscribe(handler) {
+ for (var i = handlers.length - 1; i >= 0; --i) {
+ if (handlers[i] === handler) {
+ handlers.splice(i, 1);
+ }
+ }
+ }
+
+ /**
+ * Remove all crash handlers.
+ */
+ function unsubscribeAll() {
+ uninstallGlobalHandler();
+ handlers = [];
+ }
+
+ /**
+ * Dispatch stack information to all handlers.
+ * @param {Object.} stack
+ */
+ function notifyHandlers(stack, isWindowError) {
+ var exception = null;
+ if (isWindowError && !TraceKit.collectWindowErrors) {
+ return;
+ }
+ for (var i in handlers) {
+ if (handlers.hasOwnProperty(i)) {
+ try {
+ handlers[i].apply(null, [stack].concat(_slice.call(arguments, 2)));
+ } catch (inner) {
+ exception = inner;
+ }
+ }
+ }
+
+ if (exception) {
+ throw exception;
+ }
+ }
+
+ var _oldOnerrorHandler, _onErrorHandlerInstalled;
+
+ /**
+ * Ensures all global unhandled exceptions are recorded.
+ * Supported by Gecko and IE.
+ * @param {string} message Error message.
+ * @param {string} url URL of script that generated the exception.
+ * @param {(number|string)} lineNo The line number at which the error
+ * occurred.
+ * @param {?(number|string)} colNo The column number at which the error
+ * occurred.
+ * @param {?Error} ex The actual Error object.
+ */
+ function traceKitWindowOnError(message, url, lineNo, colNo, ex) {
+ var stack = null;
+
+ if (lastExceptionStack) {
+ TraceKit.computeStackTrace.augmentStackTraceWithInitialElement(
+ lastExceptionStack,
+ url,
+ lineNo,
+ message
+ );
+ processLastException();
+ } else if (ex && utils.isError(ex)) {
+ // non-string `ex` arg; attempt to extract stack trace
+
+ // New chrome and blink send along a real error object
+ // Let's just report that like a normal error.
+ // See: https://mikewest.org/2013/08/debugging-runtime-errors-with-window-onerror
+ stack = TraceKit.computeStackTrace(ex);
+ notifyHandlers(stack, true);
+ } else {
+ var location = {
+ url: url,
+ line: lineNo,
+ column: colNo
+ };
+
+ var name = undefined;
+ var msg = message; // must be new var or will modify original `arguments`
+ var groups;
+ if ({}.toString.call(message) === '[object String]') {
+ var groups = message.match(ERROR_TYPES_RE);
+ if (groups) {
+ name = groups[1];
+ msg = groups[2];
+ }
+ }
+
+ location.func = UNKNOWN_FUNCTION;
+
+ stack = {
+ name: name,
+ message: msg,
+ url: getLocationHref(),
+ stack: [location]
+ };
+ notifyHandlers(stack, true);
+ }
+
+ if (_oldOnerrorHandler) {
+ return _oldOnerrorHandler.apply(this, arguments);
+ }
+
+ return false;
+ }
+
+ function installGlobalHandler() {
+ if (_onErrorHandlerInstalled) {
+ return;
+ }
+ _oldOnerrorHandler = _window.onerror;
+ _window.onerror = traceKitWindowOnError;
+ _onErrorHandlerInstalled = true;
+ }
+
+ function uninstallGlobalHandler() {
+ if (!_onErrorHandlerInstalled) {
+ return;
+ }
+ _window.onerror = _oldOnerrorHandler;
+ _onErrorHandlerInstalled = false;
+ _oldOnerrorHandler = undefined;
+ }
+
+ function processLastException() {
+ var _lastExceptionStack = lastExceptionStack,
+ _lastArgs = lastArgs;
+ lastArgs = null;
+ lastExceptionStack = null;
+ lastException = null;
+ notifyHandlers.apply(null, [_lastExceptionStack, false].concat(_lastArgs));
+ }
+
+ /**
+ * Reports an unhandled Error to TraceKit.
+ * @param {Error} ex
+ * @param {?boolean} rethrow If false, do not re-throw the exception.
+ * Only used for window.onerror to not cause an infinite loop of
+ * rethrowing.
+ */
+ function report(ex, rethrow) {
+ var args = _slice.call(arguments, 1);
+ if (lastExceptionStack) {
+ if (lastException === ex) {
+ return; // already caught by an inner catch block, ignore
+ } else {
+ processLastException();
+ }
+ }
+
+ var stack = TraceKit.computeStackTrace(ex);
+ lastExceptionStack = stack;
+ lastException = ex;
+ lastArgs = args;
+
+ // If the stack trace is incomplete, wait for 2 seconds for
+ // slow slow IE to see if onerror occurs or not before reporting
+ // this exception; otherwise, we will end up with an incomplete
+ // stack trace
+ setTimeout(function() {
+ if (lastException === ex) {
+ processLastException();
+ }
+ }, stack.incomplete ? 2000 : 0);
+
+ if (rethrow !== false) {
+ throw ex; // re-throw to propagate to the top level (and cause window.onerror)
+ }
+ }
+
+ report.subscribe = subscribe;
+ report.unsubscribe = unsubscribe;
+ report.uninstall = unsubscribeAll;
+ return report;
+})();
+
+/**
+ * TraceKit.computeStackTrace: cross-browser stack traces in JavaScript
+ *
+ * Syntax:
+ * s = TraceKit.computeStackTrace(exception) // consider using TraceKit.report instead (see below)
+ * Returns:
+ * s.name - exception name
+ * s.message - exception message
+ * s.stack[i].url - JavaScript or HTML file URL
+ * s.stack[i].func - function name, or empty for anonymous functions (if guessing did not work)
+ * s.stack[i].args - arguments passed to the function, if known
+ * s.stack[i].line - line number, if known
+ * s.stack[i].column - column number, if known
+ *
+ * Supports:
+ * - Firefox: full stack trace with line numbers and unreliable column
+ * number on top frame
+ * - Opera 10: full stack trace with line and column numbers
+ * - Opera 9-: full stack trace with line numbers
+ * - Chrome: full stack trace with line and column numbers
+ * - Safari: line and column number for the topmost stacktrace element
+ * only
+ * - IE: no line numbers whatsoever
+ *
+ * Tries to guess names of anonymous functions by looking for assignments
+ * in the source code. In IE and Safari, we have to guess source file names
+ * by searching for function bodies inside all page scripts. This will not
+ * work for scripts that are loaded cross-domain.
+ * Here be dragons: some function names may be guessed incorrectly, and
+ * duplicate functions may be mismatched.
+ *
+ * TraceKit.computeStackTrace should only be used for tracing purposes.
+ * Logging of unhandled exceptions should be done with TraceKit.report,
+ * which builds on top of TraceKit.computeStackTrace and provides better
+ * IE support by utilizing the window.onerror event to retrieve information
+ * about the top of the stack.
+ *
+ * Note: In IE and Safari, no stack trace is recorded on the Error object,
+ * so computeStackTrace instead walks its *own* chain of callers.
+ * This means that:
+ * * in Safari, some methods may be missing from the stack trace;
+ * * in IE, the topmost function in the stack trace will always be the
+ * caller of computeStackTrace.
+ *
+ * This is okay for tracing (because you are likely to be calling
+ * computeStackTrace from the function you want to be the topmost element
+ * of the stack trace anyway), but not okay for logging unhandled
+ * exceptions (because your catch block will likely be far away from the
+ * inner function that actually caused the exception).
+ *
+ */
+TraceKit.computeStackTrace = (function computeStackTraceWrapper() {
+ // Contents of Exception in various browsers.
+ //
+ // SAFARI:
+ // ex.message = Can't find variable: qq
+ // ex.line = 59
+ // ex.sourceId = 580238192
+ // ex.sourceURL = http://...
+ // ex.expressionBeginOffset = 96
+ // ex.expressionCaretOffset = 98
+ // ex.expressionEndOffset = 98
+ // ex.name = ReferenceError
+ //
+ // FIREFOX:
+ // ex.message = qq is not defined
+ // ex.fileName = http://...
+ // ex.lineNumber = 59
+ // ex.columnNumber = 69
+ // ex.stack = ...stack trace... (see the example below)
+ // ex.name = ReferenceError
+ //
+ // CHROME:
+ // ex.message = qq is not defined
+ // ex.name = ReferenceError
+ // ex.type = not_defined
+ // ex.arguments = ['aa']
+ // ex.stack = ...stack trace...
+ //
+ // INTERNET EXPLORER:
+ // ex.message = ...
+ // ex.name = ReferenceError
+ //
+ // OPERA:
+ // ex.message = ...message... (see the example below)
+ // ex.name = ReferenceError
+ // ex.opera#sourceloc = 11 (pretty much useless, duplicates the info in ex.message)
+ // ex.stacktrace = n/a; see 'opera:config#UserPrefs|Exceptions Have Stacktrace'
+
+ /**
+ * Computes stack trace information from the stack property.
+ * Chrome and Gecko use this property.
+ * @param {Error} ex
+ * @return {?Object.} Stack trace information.
+ */
+ function computeStackTraceFromStackProp(ex) {
+ if (typeof ex.stack === 'undefined' || !ex.stack) return;
+
+ var chrome = /^\s*at (.*?) ?\(((?:file|https?|blob|chrome-extension|native|eval|webpack||[a-z]:|\/).*?)(?::(\d+))?(?::(\d+))?\)?\s*$/i,
+ gecko = /^\s*(.*?)(?:\((.*?)\))?(?:^|@)((?:file|https?|blob|chrome|webpack|resource|\[native).*?|[^@]*bundle)(?::(\d+))?(?::(\d+))?\s*$/i,
+ winjs = /^\s*at (?:((?:\[object object\])?.+) )?\(?((?:file|ms-appx|https?|webpack|blob):.*?):(\d+)(?::(\d+))?\)?\s*$/i,
+ // Used to additionally parse URL/line/column from eval frames
+ geckoEval = /(\S+) line (\d+)(?: > eval line \d+)* > eval/i,
+ chromeEval = /\((\S*)(?::(\d+))(?::(\d+))\)/,
+ lines = ex.stack.split('\n'),
+ stack = [],
+ submatch,
+ parts,
+ element,
+ reference = /^(.*) is undefined$/.exec(ex.message);
+
+ for (var i = 0, j = lines.length; i < j; ++i) {
+ if ((parts = chrome.exec(lines[i]))) {
+ var isNative = parts[2] && parts[2].indexOf('native') === 0; // start of line
+ var isEval = parts[2] && parts[2].indexOf('eval') === 0; // start of line
+ if (isEval && (submatch = chromeEval.exec(parts[2]))) {
+ // throw out eval line/column and use top-most line/column number
+ parts[2] = submatch[1]; // url
+ parts[3] = submatch[2]; // line
+ parts[4] = submatch[3]; // column
+ }
+ element = {
+ url: !isNative ? parts[2] : null,
+ func: parts[1] || UNKNOWN_FUNCTION,
+ args: isNative ? [parts[2]] : [],
+ line: parts[3] ? +parts[3] : null,
+ column: parts[4] ? +parts[4] : null
+ };
+ } else if ((parts = winjs.exec(lines[i]))) {
+ element = {
+ url: parts[2],
+ func: parts[1] || UNKNOWN_FUNCTION,
+ args: [],
+ line: +parts[3],
+ column: parts[4] ? +parts[4] : null
+ };
+ } else if ((parts = gecko.exec(lines[i]))) {
+ var isEval = parts[3] && parts[3].indexOf(' > eval') > -1;
+ if (isEval && (submatch = geckoEval.exec(parts[3]))) {
+ // throw out eval line/column and use top-most line number
+ parts[3] = submatch[1];
+ parts[4] = submatch[2];
+ parts[5] = null; // no column when eval
+ } else if (i === 0 && !parts[5] && typeof ex.columnNumber !== 'undefined') {
+ // FireFox uses this awesome columnNumber property for its top frame
+ // Also note, Firefox's column number is 0-based and everything else expects 1-based,
+ // so adding 1
+ // NOTE: this hack doesn't work if top-most frame is eval
+ stack[0].column = ex.columnNumber + 1;
+ }
+ element = {
+ url: parts[3],
+ func: parts[1] || UNKNOWN_FUNCTION,
+ args: parts[2] ? parts[2].split(',') : [],
+ line: parts[4] ? +parts[4] : null,
+ column: parts[5] ? +parts[5] : null
+ };
+ } else {
+ continue;
+ }
+
+ if (!element.func && element.line) {
+ element.func = UNKNOWN_FUNCTION;
+ }
+
+ stack.push(element);
+ }
+
+ if (!stack.length) {
+ return null;
+ }
+
+ return {
+ name: ex.name,
+ message: ex.message,
+ url: getLocationHref(),
+ stack: stack
+ };
+ }
+
+ /**
+ * Adds information about the first frame to incomplete stack traces.
+ * Safari and IE require this to get complete data on the first frame.
+ * @param {Object.} stackInfo Stack trace information from
+ * one of the compute* methods.
+ * @param {string} url The URL of the script that caused an error.
+ * @param {(number|string)} lineNo The line number of the script that
+ * caused an error.
+ * @param {string=} message The error generated by the browser, which
+ * hopefully contains the name of the object that caused the error.
+ * @return {boolean} Whether or not the stack information was
+ * augmented.
+ */
+ function augmentStackTraceWithInitialElement(stackInfo, url, lineNo, message) {
+ var initial = {
+ url: url,
+ line: lineNo
+ };
+
+ if (initial.url && initial.line) {
+ stackInfo.incomplete = false;
+
+ if (!initial.func) {
+ initial.func = UNKNOWN_FUNCTION;
+ }
+
+ if (stackInfo.stack.length > 0) {
+ if (stackInfo.stack[0].url === initial.url) {
+ if (stackInfo.stack[0].line === initial.line) {
+ return false; // already in stack trace
+ } else if (
+ !stackInfo.stack[0].line &&
+ stackInfo.stack[0].func === initial.func
+ ) {
+ stackInfo.stack[0].line = initial.line;
+ return false;
+ }
+ }
+ }
+
+ stackInfo.stack.unshift(initial);
+ stackInfo.partial = true;
+ return true;
+ } else {
+ stackInfo.incomplete = true;
+ }
+
+ return false;
+ }
+
+ /**
+ * Computes stack trace information by walking the arguments.caller
+ * chain at the time the exception occurred. This will cause earlier
+ * frames to be missed but is the only way to get any stack trace in
+ * Safari and IE. The top frame is restored by
+ * {@link augmentStackTraceWithInitialElement}.
+ * @param {Error} ex
+ * @return {?Object.} Stack trace information.
+ */
+ function computeStackTraceByWalkingCallerChain(ex, depth) {
+ var functionName = /function\s+([_$a-zA-Z\xA0-\uFFFF][_$a-zA-Z0-9\xA0-\uFFFF]*)?\s*\(/i,
+ stack = [],
+ funcs = {},
+ recursion = false,
+ parts,
+ item,
+ source;
+
+ for (
+ var curr = computeStackTraceByWalkingCallerChain.caller;
+ curr && !recursion;
+ curr = curr.caller
+ ) {
+ if (curr === computeStackTrace || curr === TraceKit.report) {
+ // console.log('skipping internal function');
+ continue;
+ }
+
+ item = {
+ url: null,
+ func: UNKNOWN_FUNCTION,
+ line: null,
+ column: null
+ };
+
+ if (curr.name) {
+ item.func = curr.name;
+ } else if ((parts = functionName.exec(curr.toString()))) {
+ item.func = parts[1];
+ }
+
+ if (typeof item.func === 'undefined') {
+ try {
+ item.func = parts.input.substring(0, parts.input.indexOf('{'));
+ } catch (e) {}
+ }
+
+ if (funcs['' + curr]) {
+ recursion = true;
+ } else {
+ funcs['' + curr] = true;
+ }
+
+ stack.push(item);
+ }
+
+ if (depth) {
+ // console.log('depth is ' + depth);
+ // console.log('stack is ' + stack.length);
+ stack.splice(0, depth);
+ }
+
+ var result = {
+ name: ex.name,
+ message: ex.message,
+ url: getLocationHref(),
+ stack: stack
+ };
+ augmentStackTraceWithInitialElement(
+ result,
+ ex.sourceURL || ex.fileName,
+ ex.line || ex.lineNumber,
+ ex.message || ex.description
+ );
+ return result;
+ }
+
+ /**
+ * Computes a stack trace for an exception.
+ * @param {Error} ex
+ * @param {(string|number)=} depth
+ */
+ function computeStackTrace(ex, depth) {
+ var stack = null;
+ depth = depth == null ? 0 : +depth;
+
+ try {
+ stack = computeStackTraceFromStackProp(ex);
+ if (stack) {
+ return stack;
+ }
+ } catch (e) {
+ if (TraceKit.debug) {
+ throw e;
+ }
+ }
+
+ try {
+ stack = computeStackTraceByWalkingCallerChain(ex, depth + 1);
+ if (stack) {
+ return stack;
+ }
+ } catch (e) {
+ if (TraceKit.debug) {
+ throw e;
+ }
+ }
+ return {
+ name: ex.name,
+ message: ex.message,
+ url: getLocationHref()
+ };
+ }
+
+ computeStackTrace.augmentStackTraceWithInitialElement = augmentStackTraceWithInitialElement;
+ computeStackTrace.computeStackTraceFromStackProp = computeStackTraceFromStackProp;
+
+ return computeStackTrace;
+})();
+
+module.exports = TraceKit;
+
+
+/***/ }),
+
+/***/ "./node_modules/raven-js/vendor/json-stringify-safe/stringify.js":
+/*!***********************************************************************!*\
+ !*** ./node_modules/raven-js/vendor/json-stringify-safe/stringify.js ***!
+ \***********************************************************************/
+/***/ ((module, exports) => {
+
+/*
+ json-stringify-safe
+ Like JSON.stringify, but doesn't throw on circular references.
+
+ Originally forked from https://github.com/isaacs/json-stringify-safe
+ version 5.0.1 on 3/8/2017 and modified to handle Errors serialization
+ and IE8 compatibility. Tests for this are in test/vendor.
+
+ ISC license: https://github.com/isaacs/json-stringify-safe/blob/master/LICENSE
+*/
+
+exports = module.exports = stringify;
+exports.getSerialize = serializer;
+
+function indexOf(haystack, needle) {
+ for (var i = 0; i < haystack.length; ++i) {
+ if (haystack[i] === needle) return i;
+ }
+ return -1;
+}
+
+function stringify(obj, replacer, spaces, cycleReplacer) {
+ return JSON.stringify(obj, serializer(replacer, cycleReplacer), spaces);
+}
+
+// https://github.com/ftlabs/js-abbreviate/blob/fa709e5f139e7770a71827b1893f22418097fbda/index.js#L95-L106
+function stringifyError(value) {
+ var err = {
+ // These properties are implemented as magical getters and don't show up in for in
+ stack: value.stack,
+ message: value.message,
+ name: value.name
+ };
+
+ for (var i in value) {
+ if (Object.prototype.hasOwnProperty.call(value, i)) {
+ err[i] = value[i];
+ }
+ }
+
+ return err;
+}
+
+function serializer(replacer, cycleReplacer) {
+ var stack = [];
+ var keys = [];
+
+ if (cycleReplacer == null) {
+ cycleReplacer = function(key, value) {
+ if (stack[0] === value) {
+ return '[Circular ~]';
+ }
+ return '[Circular ~.' + keys.slice(0, indexOf(stack, value)).join('.') + ']';
+ };
+ }
+
+ return function(key, value) {
+ if (stack.length > 0) {
+ var thisPos = indexOf(stack, this);
+ ~thisPos ? stack.splice(thisPos + 1) : stack.push(this);
+ ~thisPos ? keys.splice(thisPos, Infinity, key) : keys.push(key);
+
+ if (~indexOf(stack, value)) {
+ value = cycleReplacer.call(this, key, value);
+ }
+ } else {
+ stack.push(value);
+ }
+
+ return replacer == null
+ ? value instanceof Error ? stringifyError(value) : value
+ : replacer.call(this, key, value);
+ };
+}
+
+
+/***/ }),
+
+/***/ "./node_modules/react/cjs/react-jsx-runtime.development.js":
+/*!*****************************************************************!*\
+ !*** ./node_modules/react/cjs/react-jsx-runtime.development.js ***!
+ \*****************************************************************/
+/***/ ((__unused_webpack_module, exports, __webpack_require__) => {
+
+"use strict";
+/** @license React v17.0.2
+ * react-jsx-runtime.development.js
+ *
+ * Copyright (c) Facebook, Inc. and its affiliates.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+
+
+if (true) {
+ (function() {
+'use strict';
+
+var React = __webpack_require__(/*! react */ "react");
+var _assign = __webpack_require__(/*! object-assign */ "./node_modules/object-assign/index.js");
+
+// ATTENTION
+// When adding new symbols to this file,
+// Please consider also adding to 'react-devtools-shared/src/backend/ReactSymbols'
+// The Symbol used to tag the ReactElement-like types. If there is no native Symbol
+// nor polyfill, then a plain number is used for performance.
+var REACT_ELEMENT_TYPE = 0xeac7;
+var REACT_PORTAL_TYPE = 0xeaca;
+exports.Fragment = 0xeacb;
+var REACT_STRICT_MODE_TYPE = 0xeacc;
+var REACT_PROFILER_TYPE = 0xead2;
+var REACT_PROVIDER_TYPE = 0xeacd;
+var REACT_CONTEXT_TYPE = 0xeace;
+var REACT_FORWARD_REF_TYPE = 0xead0;
+var REACT_SUSPENSE_TYPE = 0xead1;
+var REACT_SUSPENSE_LIST_TYPE = 0xead8;
+var REACT_MEMO_TYPE = 0xead3;
+var REACT_LAZY_TYPE = 0xead4;
+var REACT_BLOCK_TYPE = 0xead9;
+var REACT_SERVER_BLOCK_TYPE = 0xeada;
+var REACT_FUNDAMENTAL_TYPE = 0xead5;
+var REACT_SCOPE_TYPE = 0xead7;
+var REACT_OPAQUE_ID_TYPE = 0xeae0;
+var REACT_DEBUG_TRACING_MODE_TYPE = 0xeae1;
+var REACT_OFFSCREEN_TYPE = 0xeae2;
+var REACT_LEGACY_HIDDEN_TYPE = 0xeae3;
+
+if (typeof Symbol === 'function' && Symbol.for) {
+ var symbolFor = Symbol.for;
+ REACT_ELEMENT_TYPE = symbolFor('react.element');
+ REACT_PORTAL_TYPE = symbolFor('react.portal');
+ exports.Fragment = symbolFor('react.fragment');
+ REACT_STRICT_MODE_TYPE = symbolFor('react.strict_mode');
+ REACT_PROFILER_TYPE = symbolFor('react.profiler');
+ REACT_PROVIDER_TYPE = symbolFor('react.provider');
+ REACT_CONTEXT_TYPE = symbolFor('react.context');
+ REACT_FORWARD_REF_TYPE = symbolFor('react.forward_ref');
+ REACT_SUSPENSE_TYPE = symbolFor('react.suspense');
+ REACT_SUSPENSE_LIST_TYPE = symbolFor('react.suspense_list');
+ REACT_MEMO_TYPE = symbolFor('react.memo');
+ REACT_LAZY_TYPE = symbolFor('react.lazy');
+ REACT_BLOCK_TYPE = symbolFor('react.block');
+ REACT_SERVER_BLOCK_TYPE = symbolFor('react.server.block');
+ REACT_FUNDAMENTAL_TYPE = symbolFor('react.fundamental');
+ REACT_SCOPE_TYPE = symbolFor('react.scope');
+ REACT_OPAQUE_ID_TYPE = symbolFor('react.opaque.id');
+ REACT_DEBUG_TRACING_MODE_TYPE = symbolFor('react.debug_trace_mode');
+ REACT_OFFSCREEN_TYPE = symbolFor('react.offscreen');
+ REACT_LEGACY_HIDDEN_TYPE = symbolFor('react.legacy_hidden');
+}
+
+var MAYBE_ITERATOR_SYMBOL = typeof Symbol === 'function' && Symbol.iterator;
+var FAUX_ITERATOR_SYMBOL = '@@iterator';
+function getIteratorFn(maybeIterable) {
+ if (maybeIterable === null || typeof maybeIterable !== 'object') {
+ return null;
+ }
+
+ var maybeIterator = MAYBE_ITERATOR_SYMBOL && maybeIterable[MAYBE_ITERATOR_SYMBOL] || maybeIterable[FAUX_ITERATOR_SYMBOL];
+
+ if (typeof maybeIterator === 'function') {
+ return maybeIterator;
+ }
+
+ return null;
+}
+
+var ReactSharedInternals = React.__SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED;
+
+function error(format) {
+ {
+ for (var _len2 = arguments.length, args = new Array(_len2 > 1 ? _len2 - 1 : 0), _key2 = 1; _key2 < _len2; _key2++) {
+ args[_key2 - 1] = arguments[_key2];
+ }
+
+ printWarning('error', format, args);
+ }
+}
+
+function printWarning(level, format, args) {
+ // When changing this logic, you might want to also
+ // update consoleWithStackDev.www.js as well.
+ {
+ var ReactDebugCurrentFrame = ReactSharedInternals.ReactDebugCurrentFrame;
+ var stack = ReactDebugCurrentFrame.getStackAddendum();
+
+ if (stack !== '') {
+ format += '%s';
+ args = args.concat([stack]);
+ }
+
+ var argsWithFormat = args.map(function (item) {
+ return '' + item;
+ }); // Careful: RN currently depends on this prefix
+
+ argsWithFormat.unshift('Warning: ' + format); // We intentionally don't use spread (or .apply) directly because it
+ // breaks IE9: https://github.com/facebook/react/issues/13610
+ // eslint-disable-next-line react-internal/no-production-logging
+
+ Function.prototype.apply.call(console[level], console, argsWithFormat);
+ }
+}
+
+// Filter certain DOM attributes (e.g. src, href) if their values are empty strings.
+
+var enableScopeAPI = false; // Experimental Create Event Handle API.
+
+function isValidElementType(type) {
+ if (typeof type === 'string' || typeof type === 'function') {
+ return true;
+ } // Note: typeof might be other than 'symbol' or 'number' (e.g. if it's a polyfill).
+
+
+ if (type === exports.Fragment || type === REACT_PROFILER_TYPE || type === REACT_DEBUG_TRACING_MODE_TYPE || type === REACT_STRICT_MODE_TYPE || type === REACT_SUSPENSE_TYPE || type === REACT_SUSPENSE_LIST_TYPE || type === REACT_LEGACY_HIDDEN_TYPE || enableScopeAPI ) {
+ return true;
+ }
+
+ if (typeof type === 'object' && type !== null) {
+ if (type.$$typeof === REACT_LAZY_TYPE || type.$$typeof === REACT_MEMO_TYPE || type.$$typeof === REACT_PROVIDER_TYPE || type.$$typeof === REACT_CONTEXT_TYPE || type.$$typeof === REACT_FORWARD_REF_TYPE || type.$$typeof === REACT_FUNDAMENTAL_TYPE || type.$$typeof === REACT_BLOCK_TYPE || type[0] === REACT_SERVER_BLOCK_TYPE) {
+ return true;
+ }
+ }
+
+ return false;
+}
+
+function getWrappedName(outerType, innerType, wrapperName) {
+ var functionName = innerType.displayName || innerType.name || '';
+ return outerType.displayName || (functionName !== '' ? wrapperName + "(" + functionName + ")" : wrapperName);
+}
+
+function getContextName(type) {
+ return type.displayName || 'Context';
+}
+
+function getComponentName(type) {
+ if (type == null) {
+ // Host root, text node or just invalid type.
+ return null;
+ }
+
+ {
+ if (typeof type.tag === 'number') {
+ error('Received an unexpected object in getComponentName(). ' + 'This is likely a bug in React. Please file an issue.');
+ }
+ }
+
+ if (typeof type === 'function') {
+ return type.displayName || type.name || null;
+ }
+
+ if (typeof type === 'string') {
+ return type;
+ }
+
+ switch (type) {
+ case exports.Fragment:
+ return 'Fragment';
+
+ case REACT_PORTAL_TYPE:
+ return 'Portal';
+
+ case REACT_PROFILER_TYPE:
+ return 'Profiler';
+
+ case REACT_STRICT_MODE_TYPE:
+ return 'StrictMode';
+
+ case REACT_SUSPENSE_TYPE:
+ return 'Suspense';
+
+ case REACT_SUSPENSE_LIST_TYPE:
+ return 'SuspenseList';
+ }
+
+ if (typeof type === 'object') {
+ switch (type.$$typeof) {
+ case REACT_CONTEXT_TYPE:
+ var context = type;
+ return getContextName(context) + '.Consumer';
+
+ case REACT_PROVIDER_TYPE:
+ var provider = type;
+ return getContextName(provider._context) + '.Provider';
+
+ case REACT_FORWARD_REF_TYPE:
+ return getWrappedName(type, type.render, 'ForwardRef');
+
+ case REACT_MEMO_TYPE:
+ return getComponentName(type.type);
+
+ case REACT_BLOCK_TYPE:
+ return getComponentName(type._render);
+
+ case REACT_LAZY_TYPE:
+ {
+ var lazyComponent = type;
+ var payload = lazyComponent._payload;
+ var init = lazyComponent._init;
+
+ try {
+ return getComponentName(init(payload));
+ } catch (x) {
+ return null;
+ }
+ }
+ }
+ }
+
+ return null;
+}
+
+// Helpers to patch console.logs to avoid logging during side-effect free
+// replaying on render function. This currently only patches the object
+// lazily which won't cover if the log function was extracted eagerly.
+// We could also eagerly patch the method.
+var disabledDepth = 0;
+var prevLog;
+var prevInfo;
+var prevWarn;
+var prevError;
+var prevGroup;
+var prevGroupCollapsed;
+var prevGroupEnd;
+
+function disabledLog() {}
+
+disabledLog.__reactDisabledLog = true;
+function disableLogs() {
+ {
+ if (disabledDepth === 0) {
+ /* eslint-disable react-internal/no-production-logging */
+ prevLog = console.log;
+ prevInfo = console.info;
+ prevWarn = console.warn;
+ prevError = console.error;
+ prevGroup = console.group;
+ prevGroupCollapsed = console.groupCollapsed;
+ prevGroupEnd = console.groupEnd; // https://github.com/facebook/react/issues/19099
+
+ var props = {
+ configurable: true,
+ enumerable: true,
+ value: disabledLog,
+ writable: true
+ }; // $FlowFixMe Flow thinks console is immutable.
+
+ Object.defineProperties(console, {
+ info: props,
+ log: props,
+ warn: props,
+ error: props,
+ group: props,
+ groupCollapsed: props,
+ groupEnd: props
+ });
+ /* eslint-enable react-internal/no-production-logging */
+ }
+
+ disabledDepth++;
+ }
+}
+function reenableLogs() {
+ {
+ disabledDepth--;
+
+ if (disabledDepth === 0) {
+ /* eslint-disable react-internal/no-production-logging */
+ var props = {
+ configurable: true,
+ enumerable: true,
+ writable: true
+ }; // $FlowFixMe Flow thinks console is immutable.
+
+ Object.defineProperties(console, {
+ log: _assign({}, props, {
+ value: prevLog
+ }),
+ info: _assign({}, props, {
+ value: prevInfo
+ }),
+ warn: _assign({}, props, {
+ value: prevWarn
+ }),
+ error: _assign({}, props, {
+ value: prevError
+ }),
+ group: _assign({}, props, {
+ value: prevGroup
+ }),
+ groupCollapsed: _assign({}, props, {
+ value: prevGroupCollapsed
+ }),
+ groupEnd: _assign({}, props, {
+ value: prevGroupEnd
+ })
+ });
+ /* eslint-enable react-internal/no-production-logging */
+ }
+
+ if (disabledDepth < 0) {
+ error('disabledDepth fell below zero. ' + 'This is a bug in React. Please file an issue.');
+ }
+ }
+}
+
+var ReactCurrentDispatcher = ReactSharedInternals.ReactCurrentDispatcher;
+var prefix;
+function describeBuiltInComponentFrame(name, source, ownerFn) {
+ {
+ if (prefix === undefined) {
+ // Extract the VM specific prefix used by each line.
+ try {
+ throw Error();
+ } catch (x) {
+ var match = x.stack.trim().match(/\n( *(at )?)/);
+ prefix = match && match[1] || '';
+ }
+ } // We use the prefix to ensure our stacks line up with native stack frames.
+
+
+ return '\n' + prefix + name;
+ }
+}
+var reentry = false;
+var componentFrameCache;
+
+{
+ var PossiblyWeakMap = typeof WeakMap === 'function' ? WeakMap : Map;
+ componentFrameCache = new PossiblyWeakMap();
+}
+
+function describeNativeComponentFrame(fn, construct) {
+ // If something asked for a stack inside a fake render, it should get ignored.
+ if (!fn || reentry) {
+ return '';
+ }
+
+ {
+ var frame = componentFrameCache.get(fn);
+
+ if (frame !== undefined) {
+ return frame;
+ }
+ }
+
+ var control;
+ reentry = true;
+ var previousPrepareStackTrace = Error.prepareStackTrace; // $FlowFixMe It does accept undefined.
+
+ Error.prepareStackTrace = undefined;
+ var previousDispatcher;
+
+ {
+ previousDispatcher = ReactCurrentDispatcher.current; // Set the dispatcher in DEV because this might be call in the render function
+ // for warnings.
+
+ ReactCurrentDispatcher.current = null;
+ disableLogs();
+ }
+
+ try {
+ // This should throw.
+ if (construct) {
+ // Something should be setting the props in the constructor.
+ var Fake = function () {
+ throw Error();
+ }; // $FlowFixMe
+
+
+ Object.defineProperty(Fake.prototype, 'props', {
+ set: function () {
+ // We use a throwing setter instead of frozen or non-writable props
+ // because that won't throw in a non-strict mode function.
+ throw Error();
+ }
+ });
+
+ if (typeof Reflect === 'object' && Reflect.construct) {
+ // We construct a different control for this case to include any extra
+ // frames added by the construct call.
+ try {
+ Reflect.construct(Fake, []);
+ } catch (x) {
+ control = x;
+ }
+
+ Reflect.construct(fn, [], Fake);
+ } else {
+ try {
+ Fake.call();
+ } catch (x) {
+ control = x;
+ }
+
+ fn.call(Fake.prototype);
+ }
+ } else {
+ try {
+ throw Error();
+ } catch (x) {
+ control = x;
+ }
+
+ fn();
+ }
+ } catch (sample) {
+ // This is inlined manually because closure doesn't do it for us.
+ if (sample && control && typeof sample.stack === 'string') {
+ // This extracts the first frame from the sample that isn't also in the control.
+ // Skipping one frame that we assume is the frame that calls the two.
+ var sampleLines = sample.stack.split('\n');
+ var controlLines = control.stack.split('\n');
+ var s = sampleLines.length - 1;
+ var c = controlLines.length - 1;
+
+ while (s >= 1 && c >= 0 && sampleLines[s] !== controlLines[c]) {
+ // We expect at least one stack frame to be shared.
+ // Typically this will be the root most one. However, stack frames may be
+ // cut off due to maximum stack limits. In this case, one maybe cut off
+ // earlier than the other. We assume that the sample is longer or the same
+ // and there for cut off earlier. So we should find the root most frame in
+ // the sample somewhere in the control.
+ c--;
+ }
+
+ for (; s >= 1 && c >= 0; s--, c--) {
+ // Next we find the first one that isn't the same which should be the
+ // frame that called our sample function and the control.
+ if (sampleLines[s] !== controlLines[c]) {
+ // In V8, the first line is describing the message but other VMs don't.
+ // If we're about to return the first line, and the control is also on the same
+ // line, that's a pretty good indicator that our sample threw at same line as
+ // the control. I.e. before we entered the sample frame. So we ignore this result.
+ // This can happen if you passed a class to function component, or non-function.
+ if (s !== 1 || c !== 1) {
+ do {
+ s--;
+ c--; // We may still have similar intermediate frames from the construct call.
+ // The next one that isn't the same should be our match though.
+
+ if (c < 0 || sampleLines[s] !== controlLines[c]) {
+ // V8 adds a "new" prefix for native classes. Let's remove it to make it prettier.
+ var _frame = '\n' + sampleLines[s].replace(' at new ', ' at ');
+
+ {
+ if (typeof fn === 'function') {
+ componentFrameCache.set(fn, _frame);
+ }
+ } // Return the line we found.
+
+
+ return _frame;
+ }
+ } while (s >= 1 && c >= 0);
+ }
+
+ break;
+ }
+ }
+ }
+ } finally {
+ reentry = false;
+
+ {
+ ReactCurrentDispatcher.current = previousDispatcher;
+ reenableLogs();
+ }
+
+ Error.prepareStackTrace = previousPrepareStackTrace;
+ } // Fallback to just using the name if we couldn't make it throw.
+
+
+ var name = fn ? fn.displayName || fn.name : '';
+ var syntheticFrame = name ? describeBuiltInComponentFrame(name) : '';
+
+ {
+ if (typeof fn === 'function') {
+ componentFrameCache.set(fn, syntheticFrame);
+ }
+ }
+
+ return syntheticFrame;
+}
+function describeFunctionComponentFrame(fn, source, ownerFn) {
+ {
+ return describeNativeComponentFrame(fn, false);
+ }
+}
+
+function shouldConstruct(Component) {
+ var prototype = Component.prototype;
+ return !!(prototype && prototype.isReactComponent);
+}
+
+function describeUnknownElementTypeFrameInDEV(type, source, ownerFn) {
+
+ if (type == null) {
+ return '';
+ }
+
+ if (typeof type === 'function') {
+ {
+ return describeNativeComponentFrame(type, shouldConstruct(type));
+ }
+ }
+
+ if (typeof type === 'string') {
+ return describeBuiltInComponentFrame(type);
+ }
+
+ switch (type) {
+ case REACT_SUSPENSE_TYPE:
+ return describeBuiltInComponentFrame('Suspense');
+
+ case REACT_SUSPENSE_LIST_TYPE:
+ return describeBuiltInComponentFrame('SuspenseList');
+ }
+
+ if (typeof type === 'object') {
+ switch (type.$$typeof) {
+ case REACT_FORWARD_REF_TYPE:
+ return describeFunctionComponentFrame(type.render);
+
+ case REACT_MEMO_TYPE:
+ // Memo may contain any component type so we recursively resolve it.
+ return describeUnknownElementTypeFrameInDEV(type.type, source, ownerFn);
+
+ case REACT_BLOCK_TYPE:
+ return describeFunctionComponentFrame(type._render);
+
+ case REACT_LAZY_TYPE:
+ {
+ var lazyComponent = type;
+ var payload = lazyComponent._payload;
+ var init = lazyComponent._init;
+
+ try {
+ // Lazy may contain any component type so we recursively resolve it.
+ return describeUnknownElementTypeFrameInDEV(init(payload), source, ownerFn);
+ } catch (x) {}
+ }
+ }
+ }
+
+ return '';
+}
+
+var loggedTypeFailures = {};
+var ReactDebugCurrentFrame = ReactSharedInternals.ReactDebugCurrentFrame;
+
+function setCurrentlyValidatingElement(element) {
+ {
+ if (element) {
+ var owner = element._owner;
+ var stack = describeUnknownElementTypeFrameInDEV(element.type, element._source, owner ? owner.type : null);
+ ReactDebugCurrentFrame.setExtraStackFrame(stack);
+ } else {
+ ReactDebugCurrentFrame.setExtraStackFrame(null);
+ }
+ }
+}
+
+function checkPropTypes(typeSpecs, values, location, componentName, element) {
+ {
+ // $FlowFixMe This is okay but Flow doesn't know it.
+ var has = Function.call.bind(Object.prototype.hasOwnProperty);
+
+ for (var typeSpecName in typeSpecs) {
+ if (has(typeSpecs, typeSpecName)) {
+ var error$1 = void 0; // Prop type validation may throw. In case they do, we don't want to
+ // fail the render phase where it didn't fail before. So we log it.
+ // After these have been cleaned up, we'll let them throw.
+
+ try {
+ // This is intentionally an invariant that gets caught. It's the same
+ // behavior as without this statement except with a better message.
+ if (typeof typeSpecs[typeSpecName] !== 'function') {
+ var err = Error((componentName || 'React class') + ': ' + location + ' type `' + typeSpecName + '` is invalid; ' + 'it must be a function, usually from the `prop-types` package, but received `' + typeof typeSpecs[typeSpecName] + '`.' + 'This often happens because of typos such as `PropTypes.function` instead of `PropTypes.func`.');
+ err.name = 'Invariant Violation';
+ throw err;
+ }
+
+ error$1 = typeSpecs[typeSpecName](values, typeSpecName, componentName, location, null, 'SECRET_DO_NOT_PASS_THIS_OR_YOU_WILL_BE_FIRED');
+ } catch (ex) {
+ error$1 = ex;
+ }
+
+ if (error$1 && !(error$1 instanceof Error)) {
+ setCurrentlyValidatingElement(element);
+
+ error('%s: type specification of %s' + ' `%s` is invalid; the type checker ' + 'function must return `null` or an `Error` but returned a %s. ' + 'You may have forgotten to pass an argument to the type checker ' + 'creator (arrayOf, instanceOf, objectOf, oneOf, oneOfType, and ' + 'shape all require an argument).', componentName || 'React class', location, typeSpecName, typeof error$1);
+
+ setCurrentlyValidatingElement(null);
+ }
+
+ if (error$1 instanceof Error && !(error$1.message in loggedTypeFailures)) {
+ // Only monitor this failure once because there tends to be a lot of the
+ // same error.
+ loggedTypeFailures[error$1.message] = true;
+ setCurrentlyValidatingElement(element);
+
+ error('Failed %s type: %s', location, error$1.message);
+
+ setCurrentlyValidatingElement(null);
+ }
+ }
+ }
+ }
+}
+
+var ReactCurrentOwner = ReactSharedInternals.ReactCurrentOwner;
+var hasOwnProperty = Object.prototype.hasOwnProperty;
+var RESERVED_PROPS = {
+ key: true,
+ ref: true,
+ __self: true,
+ __source: true
+};
+var specialPropKeyWarningShown;
+var specialPropRefWarningShown;
+var didWarnAboutStringRefs;
+
+{
+ didWarnAboutStringRefs = {};
+}
+
+function hasValidRef(config) {
+ {
+ if (hasOwnProperty.call(config, 'ref')) {
+ var getter = Object.getOwnPropertyDescriptor(config, 'ref').get;
+
+ if (getter && getter.isReactWarning) {
+ return false;
+ }
+ }
+ }
+
+ return config.ref !== undefined;
+}
+
+function hasValidKey(config) {
+ {
+ if (hasOwnProperty.call(config, 'key')) {
+ var getter = Object.getOwnPropertyDescriptor(config, 'key').get;
+
+ if (getter && getter.isReactWarning) {
+ return false;
+ }
+ }
+ }
+
+ return config.key !== undefined;
+}
+
+function warnIfStringRefCannotBeAutoConverted(config, self) {
+ {
+ if (typeof config.ref === 'string' && ReactCurrentOwner.current && self && ReactCurrentOwner.current.stateNode !== self) {
+ var componentName = getComponentName(ReactCurrentOwner.current.type);
+
+ if (!didWarnAboutStringRefs[componentName]) {
+ error('Component "%s" contains the string ref "%s". ' + 'Support for string refs will be removed in a future major release. ' + 'This case cannot be automatically converted to an arrow function. ' + 'We ask you to manually fix this case by using useRef() or createRef() instead. ' + 'Learn more about using refs safely here: ' + 'https://reactjs.org/link/strict-mode-string-ref', getComponentName(ReactCurrentOwner.current.type), config.ref);
+
+ didWarnAboutStringRefs[componentName] = true;
+ }
+ }
+ }
+}
+
+function defineKeyPropWarningGetter(props, displayName) {
+ {
+ var warnAboutAccessingKey = function () {
+ if (!specialPropKeyWarningShown) {
+ specialPropKeyWarningShown = true;
+
+ error('%s: `key` is not a prop. Trying to access it will result ' + 'in `undefined` being returned. If you need to access the same ' + 'value within the child component, you should pass it as a different ' + 'prop. (https://reactjs.org/link/special-props)', displayName);
+ }
+ };
+
+ warnAboutAccessingKey.isReactWarning = true;
+ Object.defineProperty(props, 'key', {
+ get: warnAboutAccessingKey,
+ configurable: true
+ });
+ }
+}
+
+function defineRefPropWarningGetter(props, displayName) {
+ {
+ var warnAboutAccessingRef = function () {
+ if (!specialPropRefWarningShown) {
+ specialPropRefWarningShown = true;
+
+ error('%s: `ref` is not a prop. Trying to access it will result ' + 'in `undefined` being returned. If you need to access the same ' + 'value within the child component, you should pass it as a different ' + 'prop. (https://reactjs.org/link/special-props)', displayName);
+ }
+ };
+
+ warnAboutAccessingRef.isReactWarning = true;
+ Object.defineProperty(props, 'ref', {
+ get: warnAboutAccessingRef,
+ configurable: true
+ });
+ }
+}
+/**
+ * Factory method to create a new React element. This no longer adheres to
+ * the class pattern, so do not use new to call it. Also, instanceof check
+ * will not work. Instead test $$typeof field against Symbol.for('react.element') to check
+ * if something is a React Element.
+ *
+ * @param {*} type
+ * @param {*} props
+ * @param {*} key
+ * @param {string|object} ref
+ * @param {*} owner
+ * @param {*} self A *temporary* helper to detect places where `this` is
+ * different from the `owner` when React.createElement is called, so that we
+ * can warn. We want to get rid of owner and replace string `ref`s with arrow
+ * functions, and as long as `this` and owner are the same, there will be no
+ * change in behavior.
+ * @param {*} source An annotation object (added by a transpiler or otherwise)
+ * indicating filename, line number, and/or other information.
+ * @internal
+ */
+
+
+var ReactElement = function (type, key, ref, self, source, owner, props) {
+ var element = {
+ // This tag allows us to uniquely identify this as a React Element
+ $$typeof: REACT_ELEMENT_TYPE,
+ // Built-in properties that belong on the element
+ type: type,
+ key: key,
+ ref: ref,
+ props: props,
+ // Record the component responsible for creating this element.
+ _owner: owner
+ };
+
+ {
+ // The validation flag is currently mutative. We put it on
+ // an external backing store so that we can freeze the whole object.
+ // This can be replaced with a WeakMap once they are implemented in
+ // commonly used development environments.
+ element._store = {}; // To make comparing ReactElements easier for testing purposes, we make
+ // the validation flag non-enumerable (where possible, which should
+ // include every environment we run tests in), so the test framework
+ // ignores it.
+
+ Object.defineProperty(element._store, 'validated', {
+ configurable: false,
+ enumerable: false,
+ writable: true,
+ value: false
+ }); // self and source are DEV only properties.
+
+ Object.defineProperty(element, '_self', {
+ configurable: false,
+ enumerable: false,
+ writable: false,
+ value: self
+ }); // Two elements created in two different places should be considered
+ // equal for testing purposes and therefore we hide it from enumeration.
+
+ Object.defineProperty(element, '_source', {
+ configurable: false,
+ enumerable: false,
+ writable: false,
+ value: source
+ });
+
+ if (Object.freeze) {
+ Object.freeze(element.props);
+ Object.freeze(element);
+ }
+ }
+
+ return element;
+};
+/**
+ * https://github.com/reactjs/rfcs/pull/107
+ * @param {*} type
+ * @param {object} props
+ * @param {string} key
+ */
+
+function jsxDEV(type, config, maybeKey, source, self) {
+ {
+ var propName; // Reserved names are extracted
+
+ var props = {};
+ var key = null;
+ var ref = null; // Currently, key can be spread in as a prop. This causes a potential
+ // issue if key is also explicitly declared (ie.
+ // or
). We want to deprecate key spread,
+ // but as an intermediary step, we will use jsxDEV for everything except
+ //
, because we aren't currently able to tell if
+ // key is explicitly declared to be undefined or not.
+
+ if (maybeKey !== undefined) {
+ key = '' + maybeKey;
+ }
+
+ if (hasValidKey(config)) {
+ key = '' + config.key;
+ }
+
+ if (hasValidRef(config)) {
+ ref = config.ref;
+ warnIfStringRefCannotBeAutoConverted(config, self);
+ } // Remaining properties are added to a new props object
+
+
+ for (propName in config) {
+ if (hasOwnProperty.call(config, propName) && !RESERVED_PROPS.hasOwnProperty(propName)) {
+ props[propName] = config[propName];
+ }
+ } // Resolve default props
+
+
+ if (type && type.defaultProps) {
+ var defaultProps = type.defaultProps;
+
+ for (propName in defaultProps) {
+ if (props[propName] === undefined) {
+ props[propName] = defaultProps[propName];
+ }
+ }
+ }
+
+ if (key || ref) {
+ var displayName = typeof type === 'function' ? type.displayName || type.name || 'Unknown' : type;
+
+ if (key) {
+ defineKeyPropWarningGetter(props, displayName);
+ }
+
+ if (ref) {
+ defineRefPropWarningGetter(props, displayName);
+ }
+ }
+
+ return ReactElement(type, key, ref, self, source, ReactCurrentOwner.current, props);
+ }
+}
+
+var ReactCurrentOwner$1 = ReactSharedInternals.ReactCurrentOwner;
+var ReactDebugCurrentFrame$1 = ReactSharedInternals.ReactDebugCurrentFrame;
+
+function setCurrentlyValidatingElement$1(element) {
+ {
+ if (element) {
+ var owner = element._owner;
+ var stack = describeUnknownElementTypeFrameInDEV(element.type, element._source, owner ? owner.type : null);
+ ReactDebugCurrentFrame$1.setExtraStackFrame(stack);
+ } else {
+ ReactDebugCurrentFrame$1.setExtraStackFrame(null);
+ }
+ }
+}
+
+var propTypesMisspellWarningShown;
+
+{
+ propTypesMisspellWarningShown = false;
+}
+/**
+ * Verifies the object is a ReactElement.
+ * See https://reactjs.org/docs/react-api.html#isvalidelement
+ * @param {?object} object
+ * @return {boolean} True if `object` is a ReactElement.
+ * @final
+ */
+
+function isValidElement(object) {
+ {
+ return typeof object === 'object' && object !== null && object.$$typeof === REACT_ELEMENT_TYPE;
+ }
+}
+
+function getDeclarationErrorAddendum() {
+ {
+ if (ReactCurrentOwner$1.current) {
+ var name = getComponentName(ReactCurrentOwner$1.current.type);
+
+ if (name) {
+ return '\n\nCheck the render method of `' + name + '`.';
+ }
+ }
+
+ return '';
+ }
+}
+
+function getSourceInfoErrorAddendum(source) {
+ {
+ if (source !== undefined) {
+ var fileName = source.fileName.replace(/^.*[\\\/]/, '');
+ var lineNumber = source.lineNumber;
+ return '\n\nCheck your code at ' + fileName + ':' + lineNumber + '.';
+ }
+
+ return '';
+ }
+}
+/**
+ * Warn if there's no key explicitly set on dynamic arrays of children or
+ * object keys are not valid. This allows us to keep track of children between
+ * updates.
+ */
+
+
+var ownerHasKeyUseWarning = {};
+
+function getCurrentComponentErrorInfo(parentType) {
+ {
+ var info = getDeclarationErrorAddendum();
+
+ if (!info) {
+ var parentName = typeof parentType === 'string' ? parentType : parentType.displayName || parentType.name;
+
+ if (parentName) {
+ info = "\n\nCheck the top-level render call using <" + parentName + ">.";
+ }
+ }
+
+ return info;
+ }
+}
+/**
+ * Warn if the element doesn't have an explicit key assigned to it.
+ * This element is in an array. The array could grow and shrink or be
+ * reordered. All children that haven't already been validated are required to
+ * have a "key" property assigned to it. Error statuses are cached so a warning
+ * will only be shown once.
+ *
+ * @internal
+ * @param {ReactElement} element Element that requires a key.
+ * @param {*} parentType element's parent's type.
+ */
+
+
+function validateExplicitKey(element, parentType) {
+ {
+ if (!element._store || element._store.validated || element.key != null) {
+ return;
+ }
+
+ element._store.validated = true;
+ var currentComponentErrorInfo = getCurrentComponentErrorInfo(parentType);
+
+ if (ownerHasKeyUseWarning[currentComponentErrorInfo]) {
+ return;
+ }
+
+ ownerHasKeyUseWarning[currentComponentErrorInfo] = true; // Usually the current owner is the offender, but if it accepts children as a
+ // property, it may be the creator of the child that's responsible for
+ // assigning it a key.
+
+ var childOwner = '';
+
+ if (element && element._owner && element._owner !== ReactCurrentOwner$1.current) {
+ // Give the component that originally created this child.
+ childOwner = " It was passed a child from " + getComponentName(element._owner.type) + ".";
+ }
+
+ setCurrentlyValidatingElement$1(element);
+
+ error('Each child in a list should have a unique "key" prop.' + '%s%s See https://reactjs.org/link/warning-keys for more information.', currentComponentErrorInfo, childOwner);
+
+ setCurrentlyValidatingElement$1(null);
+ }
+}
+/**
+ * Ensure that every element either is passed in a static location, in an
+ * array with an explicit keys property defined, or in an object literal
+ * with valid key property.
+ *
+ * @internal
+ * @param {ReactNode} node Statically passed child of any type.
+ * @param {*} parentType node's parent's type.
+ */
+
+
+function validateChildKeys(node, parentType) {
+ {
+ if (typeof node !== 'object') {
+ return;
+ }
+
+ if (Array.isArray(node)) {
+ for (var i = 0; i < node.length; i++) {
+ var child = node[i];
+
+ if (isValidElement(child)) {
+ validateExplicitKey(child, parentType);
+ }
+ }
+ } else if (isValidElement(node)) {
+ // This element was passed in a valid location.
+ if (node._store) {
+ node._store.validated = true;
+ }
+ } else if (node) {
+ var iteratorFn = getIteratorFn(node);
+
+ if (typeof iteratorFn === 'function') {
+ // Entry iterators used to provide implicit keys,
+ // but now we print a separate warning for them later.
+ if (iteratorFn !== node.entries) {
+ var iterator = iteratorFn.call(node);
+ var step;
+
+ while (!(step = iterator.next()).done) {
+ if (isValidElement(step.value)) {
+ validateExplicitKey(step.value, parentType);
+ }
+ }
+ }
+ }
+ }
+ }
+}
+/**
+ * Given an element, validate that its props follow the propTypes definition,
+ * provided by the type.
+ *
+ * @param {ReactElement} element
+ */
+
+
+function validatePropTypes(element) {
+ {
+ var type = element.type;
+
+ if (type === null || type === undefined || typeof type === 'string') {
+ return;
+ }
+
+ var propTypes;
+
+ if (typeof type === 'function') {
+ propTypes = type.propTypes;
+ } else if (typeof type === 'object' && (type.$$typeof === REACT_FORWARD_REF_TYPE || // Note: Memo only checks outer props here.
+ // Inner props are checked in the reconciler.
+ type.$$typeof === REACT_MEMO_TYPE)) {
+ propTypes = type.propTypes;
+ } else {
+ return;
+ }
+
+ if (propTypes) {
+ // Intentionally inside to avoid triggering lazy initializers:
+ var name = getComponentName(type);
+ checkPropTypes(propTypes, element.props, 'prop', name, element);
+ } else if (type.PropTypes !== undefined && !propTypesMisspellWarningShown) {
+ propTypesMisspellWarningShown = true; // Intentionally inside to avoid triggering lazy initializers:
+
+ var _name = getComponentName(type);
+
+ error('Component %s declared `PropTypes` instead of `propTypes`. Did you misspell the property assignment?', _name || 'Unknown');
+ }
+
+ if (typeof type.getDefaultProps === 'function' && !type.getDefaultProps.isReactClassApproved) {
+ error('getDefaultProps is only used on classic React.createClass ' + 'definitions. Use a static property named `defaultProps` instead.');
+ }
+ }
+}
+/**
+ * Given a fragment, validate that it can only be provided with fragment props
+ * @param {ReactElement} fragment
+ */
+
+
+function validateFragmentProps(fragment) {
+ {
+ var keys = Object.keys(fragment.props);
+
+ for (var i = 0; i < keys.length; i++) {
+ var key = keys[i];
+
+ if (key !== 'children' && key !== 'key') {
+ setCurrentlyValidatingElement$1(fragment);
+
+ error('Invalid prop `%s` supplied to `React.Fragment`. ' + 'React.Fragment can only have `key` and `children` props.', key);
+
+ setCurrentlyValidatingElement$1(null);
+ break;
+ }
+ }
+
+ if (fragment.ref !== null) {
+ setCurrentlyValidatingElement$1(fragment);
+
+ error('Invalid attribute `ref` supplied to `React.Fragment`.');
+
+ setCurrentlyValidatingElement$1(null);
+ }
+ }
+}
+
+function jsxWithValidation(type, props, key, isStaticChildren, source, self) {
+ {
+ var validType = isValidElementType(type); // We warn in this case but don't throw. We expect the element creation to
+ // succeed and there will likely be errors in render.
+
+ if (!validType) {
+ var info = '';
+
+ if (type === undefined || typeof type === 'object' && type !== null && Object.keys(type).length === 0) {
+ info += ' You likely forgot to export your component from the file ' + "it's defined in, or you might have mixed up default and named imports.";
+ }
+
+ var sourceInfo = getSourceInfoErrorAddendum(source);
+
+ if (sourceInfo) {
+ info += sourceInfo;
+ } else {
+ info += getDeclarationErrorAddendum();
+ }
+
+ var typeString;
+
+ if (type === null) {
+ typeString = 'null';
+ } else if (Array.isArray(type)) {
+ typeString = 'array';
+ } else if (type !== undefined && type.$$typeof === REACT_ELEMENT_TYPE) {
+ typeString = "<" + (getComponentName(type.type) || 'Unknown') + " />";
+ info = ' Did you accidentally export a JSX literal instead of a component?';
+ } else {
+ typeString = typeof type;
+ }
+
+ error('React.jsx: type is invalid -- expected a string (for ' + 'built-in components) or a class/function (for composite ' + 'components) but got: %s.%s', typeString, info);
+ }
+
+ var element = jsxDEV(type, props, key, source, self); // The result can be nullish if a mock or a custom function is used.
+ // TODO: Drop this when these are no longer allowed as the type argument.
+
+ if (element == null) {
+ return element;
+ } // Skip key warning if the type isn't valid since our key validation logic
+ // doesn't expect a non-string/function type and can throw confusing errors.
+ // We don't want exception behavior to differ between dev and prod.
+ // (Rendering will throw with a helpful message and as soon as the type is
+ // fixed, the key warnings will appear.)
+
+
+ if (validType) {
+ var children = props.children;
+
+ if (children !== undefined) {
+ if (isStaticChildren) {
+ if (Array.isArray(children)) {
+ for (var i = 0; i < children.length; i++) {
+ validateChildKeys(children[i], type);
+ }
+
+ if (Object.freeze) {
+ Object.freeze(children);
+ }
+ } else {
+ error('React.jsx: Static children should always be an array. ' + 'You are likely explicitly calling React.jsxs or React.jsxDEV. ' + 'Use the Babel transform instead.');
+ }
+ } else {
+ validateChildKeys(children, type);
+ }
+ }
+ }
+
+ if (type === exports.Fragment) {
+ validateFragmentProps(element);
+ } else {
+ validatePropTypes(element);
+ }
+
+ return element;
+ }
+} // These two functions exist to still get child warnings in dev
+// even with the prod transform. This means that jsxDEV is purely
+// opt-in behavior for better messages but that we won't stop
+// giving you warnings if you use production apis.
+
+function jsxWithValidationStatic(type, props, key) {
+ {
+ return jsxWithValidation(type, props, key, true);
+ }
+}
+function jsxWithValidationDynamic(type, props, key) {
+ {
+ return jsxWithValidation(type, props, key, false);
+ }
+}
+
+var jsx = jsxWithValidationDynamic ; // we may want to special case jsxs internally to take advantage of static children.
+// for now we can ship identical prod functions
+
+var jsxs = jsxWithValidationStatic ;
+
+exports.jsx = jsx;
+exports.jsxs = jsxs;
+ })();
+}
+
+
+/***/ }),
+
+/***/ "./node_modules/react/jsx-runtime.js":
+/*!*******************************************!*\
+ !*** ./node_modules/react/jsx-runtime.js ***!
+ \*******************************************/
+/***/ ((module, __unused_webpack_exports, __webpack_require__) => {
+
+"use strict";
+
+
+if (false) {} else {
+ module.exports = __webpack_require__(/*! ./cjs/react-jsx-runtime.development.js */ "./node_modules/react/cjs/react-jsx-runtime.development.js");
+}
+
+
+/***/ }),
+
+/***/ "react":
+/*!************************!*\
+ !*** external "React" ***!
+ \************************/
+/***/ ((module) => {
+
+"use strict";
+module.exports = window["React"];
+
+/***/ }),
+
+/***/ "react-dom":
+/*!***************************!*\
+ !*** external "ReactDOM" ***!
+ \***************************/
+/***/ ((module) => {
+
+"use strict";
+module.exports = window["ReactDOM"];
+
+/***/ }),
+
+/***/ "jquery":
+/*!*************************!*\
+ !*** external "jQuery" ***!
+ \*************************/
+/***/ ((module) => {
+
+"use strict";
+module.exports = window["jQuery"];
+
+/***/ }),
+
+/***/ "@wordpress/i18n":
+/*!******************************!*\
+ !*** external ["wp","i18n"] ***!
+ \******************************/
+/***/ ((module) => {
+
+"use strict";
+module.exports = window["wp"]["i18n"];
+
+/***/ }),
+
+/***/ "./node_modules/@linaria/react/dist/index.mjs":
+/*!****************************************************!*\
+ !*** ./node_modules/@linaria/react/dist/index.mjs ***!
+ \****************************************************/
+/***/ ((__unused_webpack___webpack_module__, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "styled": () => (/* binding */ styled_default)
+/* harmony export */ });
+/* harmony import */ var _emotion_is_prop_valid__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! @emotion/is-prop-valid */ "./node_modules/@linaria/react/node_modules/@emotion/is-prop-valid/dist/emotion-is-prop-valid.esm.js");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! react */ "react");
+/* harmony import */ var _linaria_core__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! @linaria/core */ "./node_modules/@linaria/react/node_modules/@linaria/core/dist/index.mjs");
+// src/styled.ts
+
+
+
+var isCapital = (ch) => ch.toUpperCase() === ch;
+var filterKey = (keys) => (key) => keys.indexOf(key) === -1;
+var omit = (obj, keys) => {
+ const res = {};
+ Object.keys(obj).filter(filterKey(keys)).forEach((key) => {
+ res[key] = obj[key];
+ });
+ return res;
+};
+function filterProps(asIs, props, omitKeys) {
+ const filteredProps = omit(props, omitKeys);
+ if (!asIs) {
+ const interopValidAttr = typeof _emotion_is_prop_valid__WEBPACK_IMPORTED_MODULE_0__["default"] === "function" ? { default: _emotion_is_prop_valid__WEBPACK_IMPORTED_MODULE_0__["default"] } : _emotion_is_prop_valid__WEBPACK_IMPORTED_MODULE_0__["default"];
+ Object.keys(filteredProps).forEach((key) => {
+ if (!interopValidAttr.default(key)) {
+ delete filteredProps[key];
+ }
+ });
+ }
+ return filteredProps;
+}
+var warnIfInvalid = (value, componentName) => {
+ if (true) {
+ if (typeof value === "string" || typeof value === "number" && isFinite(value)) {
+ return;
+ }
+ const stringified = typeof value === "object" ? JSON.stringify(value) : String(value);
+ console.warn(
+ `An interpolation evaluated to '${stringified}' in the component '${componentName}', which is probably a mistake. You should explicitly cast or transform the value to a string.`
+ );
+ }
+};
+function styled(tag) {
+ return (options) => {
+ if (true) {
+ if (Array.isArray(options)) {
+ throw new Error(
+ 'Using the "styled" tag in runtime is not supported. Make sure you have set up the Babel plugin correctly. See https://github.com/callstack/linaria#setup'
+ );
+ }
+ }
+ const render = (props, ref) => {
+ const { as: component = tag, class: className } = props;
+ const shouldKeepProps = options.propsAsIs === void 0 ? !(typeof component === "string" && component.indexOf("-") === -1 && !isCapital(component[0])) : options.propsAsIs;
+ const filteredProps = filterProps(shouldKeepProps, props, [
+ "as",
+ "class"
+ ]);
+ filteredProps.ref = ref;
+ filteredProps.className = options.atomic ? (0,_linaria_core__WEBPACK_IMPORTED_MODULE_2__.cx)(options.class, filteredProps.className || className) : (0,_linaria_core__WEBPACK_IMPORTED_MODULE_2__.cx)(filteredProps.className || className, options.class);
+ const { vars } = options;
+ if (vars) {
+ const style = {};
+ for (const name in vars) {
+ const variable = vars[name];
+ const result = variable[0];
+ const unit = variable[1] || "";
+ const value = typeof result === "function" ? result(props) : result;
+ warnIfInvalid(value, options.name);
+ style[`--${name}`] = `${value}${unit}`;
+ }
+ const ownStyle = filteredProps.style || {};
+ const keys = Object.keys(ownStyle);
+ if (keys.length > 0) {
+ keys.forEach((key) => {
+ style[key] = ownStyle[key];
+ });
+ }
+ filteredProps.style = style;
+ }
+ if (tag.__linaria && tag !== component) {
+ filteredProps.as = component;
+ return react__WEBPACK_IMPORTED_MODULE_1__.createElement(tag, filteredProps);
+ }
+ return react__WEBPACK_IMPORTED_MODULE_1__.createElement(component, filteredProps);
+ };
+ const Result = react__WEBPACK_IMPORTED_MODULE_1__.forwardRef ? react__WEBPACK_IMPORTED_MODULE_1__.forwardRef(render) : (props) => {
+ const rest = omit(props, ["innerRef"]);
+ return render(rest, props.innerRef);
+ };
+ Result.displayName = options.name;
+ Result.__linaria = {
+ className: options.class,
+ extends: tag
+ };
+ return Result;
+ };
+}
+var styled_default = true ? new Proxy(styled, {
+ get(o, prop) {
+ return o(prop);
+ }
+}) : 0;
+
+//# sourceMappingURL=index.mjs.map
+
+/***/ }),
+
+/***/ "./node_modules/@linaria/react/node_modules/@linaria/core/dist/index.mjs":
+/*!*******************************************************************************!*\
+ !*** ./node_modules/@linaria/react/node_modules/@linaria/core/dist/index.mjs ***!
+ \*******************************************************************************/
+/***/ ((__unused_webpack___webpack_module__, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "css": () => (/* binding */ css_default),
+/* harmony export */ "cx": () => (/* binding */ cx_default)
+/* harmony export */ });
+// src/css.ts
+var css = () => {
+ throw new Error(
+ 'Using the "css" tag in runtime is not supported. Make sure you have set up the Babel plugin correctly.'
+ );
+};
+var css_default = css;
+
+// src/cx.ts
+var cx = function cx2() {
+ const presentClassNames = Array.prototype.slice.call(arguments).filter(Boolean);
+ const atomicClasses = {};
+ const nonAtomicClasses = [];
+ presentClassNames.forEach((arg) => {
+ const individualClassNames = arg ? arg.split(" ") : [];
+ individualClassNames.forEach((className) => {
+ if (className.startsWith("atm_")) {
+ const [, keyHash] = className.split("_");
+ atomicClasses[keyHash] = className;
+ } else {
+ nonAtomicClasses.push(className);
+ }
+ });
+ });
+ const result = [];
+ for (const keyHash in atomicClasses) {
+ if (Object.prototype.hasOwnProperty.call(atomicClasses, keyHash)) {
+ result.push(atomicClasses[keyHash]);
+ }
+ }
+ result.push(...nonAtomicClasses);
+ return result.join(" ");
+};
+var cx_default = cx;
+
+//# sourceMappingURL=index.mjs.map
+
+/***/ })
+
+/******/ });
+/************************************************************************/
+/******/ // The module cache
+/******/ var __webpack_module_cache__ = {};
+/******/
+/******/ // The require function
+/******/ function __webpack_require__(moduleId) {
+/******/ // Check if module is in cache
+/******/ var cachedModule = __webpack_module_cache__[moduleId];
+/******/ if (cachedModule !== undefined) {
+/******/ return cachedModule.exports;
+/******/ }
+/******/ // Create a new module (and put it into the cache)
+/******/ var module = __webpack_module_cache__[moduleId] = {
+/******/ // no module.id needed
+/******/ // no module.loaded needed
+/******/ exports: {}
+/******/ };
+/******/
+/******/ // Execute the module function
+/******/ __webpack_modules__[moduleId](module, module.exports, __webpack_require__);
+/******/
+/******/ // Return the exports of the module
+/******/ return module.exports;
+/******/ }
+/******/
+/************************************************************************/
+/******/ /* webpack/runtime/compat get default export */
+/******/ (() => {
+/******/ // getDefaultExport function for compatibility with non-harmony modules
+/******/ __webpack_require__.n = (module) => {
+/******/ var getter = module && module.__esModule ?
+/******/ () => (module['default']) :
+/******/ () => (module);
+/******/ __webpack_require__.d(getter, { a: getter });
+/******/ return getter;
+/******/ };
+/******/ })();
+/******/
+/******/ /* webpack/runtime/define property getters */
+/******/ (() => {
+/******/ // define getter functions for harmony exports
+/******/ __webpack_require__.d = (exports, definition) => {
+/******/ for(var key in definition) {
+/******/ if(__webpack_require__.o(definition, key) && !__webpack_require__.o(exports, key)) {
+/******/ Object.defineProperty(exports, key, { enumerable: true, get: definition[key] });
+/******/ }
+/******/ }
+/******/ };
+/******/ })();
+/******/
+/******/ /* webpack/runtime/global */
+/******/ (() => {
+/******/ __webpack_require__.g = (function() {
+/******/ if (typeof globalThis === 'object') return globalThis;
+/******/ try {
+/******/ return this || new Function('return this')();
+/******/ } catch (e) {
+/******/ if (typeof window === 'object') return window;
+/******/ }
+/******/ })();
+/******/ })();
+/******/
+/******/ /* webpack/runtime/hasOwnProperty shorthand */
+/******/ (() => {
+/******/ __webpack_require__.o = (obj, prop) => (Object.prototype.hasOwnProperty.call(obj, prop))
+/******/ })();
+/******/
+/******/ /* webpack/runtime/make namespace object */
+/******/ (() => {
+/******/ // define __esModule on exports
+/******/ __webpack_require__.r = (exports) => {
+/******/ if(typeof Symbol !== 'undefined' && Symbol.toStringTag) {
+/******/ Object.defineProperty(exports, Symbol.toStringTag, { value: 'Module' });
+/******/ }
+/******/ Object.defineProperty(exports, '__esModule', { value: true });
+/******/ };
+/******/ })();
+/******/
+/************************************************************************/
+var __webpack_exports__ = {};
+// This entry need to be wrapped in an IIFE because it need to be in strict mode.
+(() => {
+"use strict";
+/*!**************************************!*\
+ !*** ./scripts/entries/elementor.ts ***!
+ \**************************************/
+__webpack_require__.r(__webpack_exports__);
+/* harmony import */ var _elementor_elementorWidget__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! ../elementor/elementorWidget */ "./scripts/elementor/elementorWidget.ts");
+/* harmony import */ var _elementor_FormWidget_registerFormWidget__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! ../elementor/FormWidget/registerFormWidget */ "./scripts/elementor/FormWidget/registerFormWidget.ts");
+/* harmony import */ var _utils_backgroundAppUtils__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ../utils/backgroundAppUtils */ "./scripts/utils/backgroundAppUtils.ts");
+/* harmony import */ var _elementor_MeetingWidget_registerMeetingWidget__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ../elementor/MeetingWidget/registerMeetingWidget */ "./scripts/elementor/MeetingWidget/registerMeetingWidget.ts");
+
+
+
+
+var ELEMENTOR_READY_INTERVAL = 500;
+var MAX_POLL_TIMEOUT = 30000;
+
+var registerElementorWidgets = function registerElementorWidgets() {
+ (0,_utils_backgroundAppUtils__WEBPACK_IMPORTED_MODULE_2__.initBackgroundApp)(function () {
+ var FormWidget;
+ var MeetingsWidget;
+ var leadinSelectFormItemView = (0,_elementor_elementorWidget__WEBPACK_IMPORTED_MODULE_0__["default"])( //@ts-expect-error global
+ window.elementor, {
+ widgetName: 'hubspot-form',
+ controlSelector: '.elementor-hbspt-form-selector',
+ containerSelector: '.hubspot-form-edit-mode'
+ }, function (controlContainer, widgetContainer, setValue) {
+ FormWidget = new _elementor_FormWidget_registerFormWidget__WEBPACK_IMPORTED_MODULE_1__["default"](controlContainer, widgetContainer, setValue);
+ FormWidget.render();
+ }, function () {
+ FormWidget.done();
+ });
+ var leadinSelectMeetingItemView = (0,_elementor_elementorWidget__WEBPACK_IMPORTED_MODULE_0__["default"])( //@ts-expect-error global
+ window.elementor, {
+ widgetName: 'hubspot-meeting',
+ controlSelector: '.elementor-hbspt-meeting-selector',
+ containerSelector: '.hubspot-meeting-edit-mode'
+ }, function (controlContainer, widgetContainer, setValue) {
+ MeetingsWidget = new _elementor_MeetingWidget_registerMeetingWidget__WEBPACK_IMPORTED_MODULE_3__["default"](controlContainer, widgetContainer, setValue);
+ MeetingsWidget.render();
+ }, function () {
+ MeetingsWidget.done();
+ }); //@ts-expect-error global
+
+ window.elementor.addControlView('leadinformselect', leadinSelectFormItemView); //@ts-expect-error global
+
+ window.elementor.addControlView('leadinmeetingselect', leadinSelectMeetingItemView);
+ });
+};
+
+var pollForElementorReady = setInterval(function () {
+ var elementorFrontend = window.elementorFrontend;
+
+ if (elementorFrontend) {
+ registerElementorWidgets();
+ clearInterval(pollForElementorReady);
+ }
+}, ELEMENTOR_READY_INTERVAL);
+setTimeout(function () {
+ clearInterval(pollForElementorReady);
+}, MAX_POLL_TIMEOUT);
+})();
+
+/******/ })()
+;
+//# sourceMappingURL=elementor.js.map
\ No newline at end of file
diff --git a/wp/wp-content/plugins/leadin/build/elementor.js.map b/wp/wp-content/plugins/leadin/build/elementor.js.map
new file mode 100644
index 00000000..8644d63d
--- /dev/null
+++ b/wp/wp-content/plugins/leadin/build/elementor.js.map
@@ -0,0 +1 @@
+{"version":3,"file":"elementor.js","mappings":";;;;;;;;;;;;;;AAAA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA,iEAAe,OAAO,EAAC;;;;;;;;;;;;;;;;;ACRgB;;AAEvC,2+HAA2+H;;AAE3+H,iCAAiC,4DAAO;AACxC;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA,iEAAe,WAAW,EAAC;;;;;;;;;;;;;;;;;;;ACd3B;AACA,IAAMC,iBAAiB,GAAG,mBAA1B;AACA,IAAMC,eAAe,GAAG,iBAAxB;AACA,IAAMC,eAAe,GAAG,iBAAxB;AACA,IAAMC,YAAY,GAAG,cAArB;AACA,IAAMC,UAAU,GAAG,YAAnB;AACO,IAAMC,eAAe,GAAG;EAC3BC,KAAK,EAAEP,mDAAE,CAAC,WAAD,EAAc,QAAd,CADkB;EAE3BQ,OAAO,EAAE,CACL;IAAED,KAAK,EAAEP,mDAAE,CAAC,mBAAD,EAAsB,QAAtB,CAAX;IAA4CS,KAAK,EAAER;EAAnD,CADK,EAEL;IAAEM,KAAK,EAAEP,mDAAE,CAAC,iBAAD,EAAoB,QAApB,CAAX;IAA0CS,KAAK,EAAEP;EAAjD,CAFK,EAGL;IAAEK,KAAK,EAAEP,mDAAE,CAAC,yBAAD,EAA4B,QAA5B,CAAX;IAAkDS,KAAK,EAAEN;EAAzD,CAHK,EAIL;IAAEI,KAAK,EAAEP,mDAAE,CAAC,cAAD,EAAiB,QAAjB,CAAX;IAAuCS,KAAK,EAAEL;EAA9C,CAJK,EAKL;IAAEG,KAAK,EAAEP,mDAAE,CAAC,yBAAD,EAA4B,QAA5B,CAAX;IAAkDS,KAAK,EAAEJ;EAAzD,CALK;AAFkB,CAAxB;AAUA,SAASK,aAAT,CAAuBD,KAAvB,EAA8B;EACjC,OAAQA,KAAK,KAAKR,iBAAV,IACJQ,KAAK,KAAKP,eADN,IAEJO,KAAK,KAAKN,eAFN,IAGJM,KAAK,KAAKL,YAHN,IAIJK,KAAK,KAAKJ,UAJd;AAKH;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;ACtBD,2BAA6iBM,MAAM,CAACC,YAApjB;AAAA,IAAQC,WAAR,wBAAQA,WAAR;AAAA,IAAqBC,QAArB,wBAAqBA,QAArB;AAAA,IAA+BC,cAA/B,wBAA+BA,cAA/B;AAAA,IAA+CC,gBAA/C,wBAA+CA,gBAA/C;AAAA,IAAiEC,QAAjE,wBAAiEA,QAAjE;AAAA,IAA2EC,aAA3E,wBAA2EA,aAA3E;AAAA,IAA0FC,GAA1F,wBAA0FA,GAA1F;AAAA,IAA+FC,WAA/F,wBAA+FA,WAA/F;AAAA,IAA4GC,cAA5G,wBAA4GA,cAA5G;AAAA,IAA4HC,kBAA5H,wBAA4HA,kBAA5H;AAAA,IAAgJC,MAAhJ,wBAAgJA,MAAhJ;AAAA,IAAwJC,cAAxJ,wBAAwJA,cAAxJ;AAAA,IAAwKC,YAAxK,wBAAwKA,YAAxK;AAAA,IAAsLC,SAAtL,wBAAsLA,SAAtL;AAAA,IAAiMC,UAAjM,wBAAiMA,UAAjM;AAAA,IAA6MC,iBAA7M,wBAA6MA,iBAA7M;AAAA,IAAgOC,mBAAhO,wBAAgOA,mBAAhO;AAAA,IAAqPC,kBAArP,wBAAqPA,kBAArP;AAAA,IAAyQC,mBAAzQ,wBAAyQA,mBAAzQ;AAAA,IAA8RC,iBAA9R,wBAA8RA,iBAA9R;AAAA,IAAiTC,MAAjT,wBAAiTA,MAAjT;AAAA,IAAyTC,QAAzT,wBAAyTA,QAAzT;AAAA,IAAmUC,UAAnU,wBAAmUA,UAAnU;AAAA,IAA+UC,UAA/U,wBAA+UA,UAA/U;AAAA,IAA2VC,OAA3V,wBAA2VA,OAA3V;AAAA,IAAoWC,YAApW,wBAAoWA,YAApW;AAAA,IAAkXC,WAAlX,wBAAkXA,WAAlX;AAAA,IAA+XC,QAA/X,wBAA+XA,QAA/X;AAAA,IAAyYC,aAAzY,wBAAyYA,aAAzY;AAAA,IAAwZC,SAAxZ,wBAAwZA,SAAxZ;AAAA,IAAmaC,OAAna,wBAAmaA,OAAna;AAAA,IAA4aC,YAA5a,wBAA4aA,YAA5a;AAAA,IAA0bC,iBAA1b,wBAA0bA,iBAA1b;AAAA,IAA6cC,KAA7c,wBAA6cA,KAA7c;AAAA,IAAodC,YAApd,wBAAodA,YAApd;AAAA,IAAkeC,SAAle,wBAAkeA,SAAle;AAAA,IAA6eC,YAA7e,wBAA6eA,YAA7e;AAAA,IAA2fC,yBAA3f,wBAA2fA,yBAA3f;AAAA,IAAshBC,iBAAthB,wBAAshBA,iBAAthB;;;;;;;;;;;;;;;;;;;;ACAA;AACA;AACA;AACe,SAASI,mBAAT,GAA+B;EAC1C,OAAQF,sDAAI,CAACC,wDAAD,EAAkB;IAAEE,QAAQ,EAAEH,sDAAI,CAAC,GAAD,EAAM;MAAEI,uBAAuB,EAAE;QACnEC,MAAM,EAAE1D,mDAAE,CAAC,2HAAD,CAAF,CACH2D,OADG,CACK,MADL,EACa,+EADb,EAEHA,OAFG,CAEK,MAFL,EAEa,MAFb;MAD2D;IAA3B,CAAN;EAAhB,CAAlB,CAAZ;AAKH;;;;;;;;;;;;;;;;ACTD;AACe,SAASL,eAAT,OAA0D;EAAA,qBAA/BM,IAA+B;EAAA,IAA/BA,IAA+B,0BAAxB,SAAwB;EAAA,IAAbJ,QAAa,QAAbA,QAAa;EACrE,OAAQH,sDAAI,CAAC,KAAD,EAAQ;IAAEQ,SAAS,EAAE,2BAAb;IAA0CL,QAAQ,EAAEH,sDAAI,CAAC,KAAD,EAAQ;MAAEQ,SAAS,mFAA4ED,IAA5E,CAAX;MAA+FJ,QAAQ,EAAEA;IAAzG,CAAR;EAAxD,CAAR,CAAZ;AACH;;;;;;;;;;;;;;;;;;;;;;;;;;;;;ACHD;AACA;AACA,IAAMO,SAAS,gBAAGD,sDAAM,OAANA,CAAM;EAAAE;EAAA;EAAAC;AAAA,CAANH,CAAlB;AAKe,SAASI,eAAT,OAAkD;EAAA,IAAvBV,QAAuB,QAAvBA,QAAuB;EAAA,IAAVW,MAAU;;EAC7D,OAAQd,sDAAI,CAACU,SAAD,EAAY;IAAEF,SAAS,EAAE,0BAAb;IAAyCL,QAAQ,EAAEH,sDAAI,CAAC,QAAD;MAAaQ,SAAS,EAAE,2CAAxB;MAAqED,IAAI,EAAE;IAA3E,GAAwFO,MAAxF;MAAgGX,QAAQ,EAAEA;IAA1G;EAAvD,CAAZ,CAAZ;AACJ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;ACTA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AACA,SAASoB,mBAAT,OAAyD;EAAA,IAA1BC,MAA0B,QAA1BA,MAA0B;EAAA,IAAlBC,aAAkB,QAAlBA,aAAkB;;EACrD,gBAAqCJ,2DAAQ,EAA7C;EAAA,IAAQK,QAAR,aAAQA,QAAR;EAAA,IAAkBC,KAAlB,aAAkBA,KAAlB;EAAA,IAAyBC,OAAzB,aAAyBA,OAAzB;;EACA,OAAOA,OAAO,GAAI5B,sDAAI,CAAC,KAAD,EAAQ;IAAEG,QAAQ,EAAEH,sDAAI,CAACkB,sEAAD,EAAY,EAAZ;EAAhB,CAAR,CAAR,GAAsDQ,QAAQ,GAAI1B,sDAAI,CAACC,+DAAD,EAAkB;IAAEM,IAAI,EAAE,QAAR;IAAkBJ,QAAQ,EAAExD,mDAAE,CAAC,yDAAD,EAA4D,QAA5D;EAA9B,CAAlB,CAAR,GAAqIqE,uDAAK,CAAC,QAAD,EAAW;IAAE5D,KAAK,EAAEoE,MAAT;IAAiBK,QAAQ,EAAE,kBAAAC,KAAK,EAAI;MAC7P,IAAMC,YAAY,GAAGJ,KAAK,CAACK,IAAN,CAAW,UAAAC,IAAI;QAAA,OAAIA,IAAI,CAAC7E,KAAL,KAAe0E,KAAK,CAACI,MAAN,CAAa9E,KAAhC;MAAA,CAAf,CAArB;;MACA,IAAI2E,YAAJ,EAAkB;QACdN,aAAa,CAAC;UACVtC,QAAQ,EAARA,6DADU;UAEVqC,MAAM,EAAEO,YAAY,CAAC3E,KAFX;UAGV+E,QAAQ,EAAEJ,YAAY,CAAC7E;QAHb,CAAD,CAAb;MAKH;IACJ,CAT4N;IAS1NiD,QAAQ,EAAE,CAACH,sDAAI,CAAC,QAAD,EAAW;MAAE5C,KAAK,EAAE,EAAT;MAAagF,QAAQ,EAAE,IAAvB;MAA6BC,QAAQ,EAAE,IAAvC;MAA6ClC,QAAQ,EAAExD,mDAAE,CAAC,mBAAD,EAAsB,QAAtB;IAAzD,CAAX,CAAL,EAA6GgF,KAAK,CAACW,GAAN,CAAU,UAAAL,IAAI;MAAA,OAAKjC,sDAAI,CAAC,QAAD,EAAW;QAAE5C,KAAK,EAAE6E,IAAI,CAAC7E,KAAd;QAAqB+C,QAAQ,EAAE8B,IAAI,CAAC/E;MAApC,CAAX,EAAwD+E,IAAI,CAAC7E,KAA7D,CAAT;IAAA,CAAd,CAA7G;EATgN,CAAX,CAAtN;AAUH;;AACD,SAASmF,0BAAT,CAAoCC,KAApC,EAA2C;EACvC,IAAMC,oBAAoB,GAAGrB,iFAAuB,EAApD;EACA,OAAQpB,sDAAI,CAACiB,2CAAD,EAAW;IAAEd,QAAQ,EAAE,CAACsC,oBAAD,GAAyBzC,sDAAI,CAAC,KAAD,EAAQ;MAAEG,QAAQ,EAAEH,sDAAI,CAACkB,sEAAD,EAAY,EAAZ;IAAhB,CAAR,CAA7B,GAA4ElB,sDAAI,CAACuB,mBAAD,oBAA2BiB,KAA3B;EAA5F,CAAX,CAAZ;AACH;;AACc,SAASE,4BAAT,CAAsCF,KAAtC,EAA6C;EACxD,OAAQxC,sDAAI,CAACmB,kFAAD,EAA+B;IAAE/D,KAAK,EAAEmC,iEAAY,IAAI+B,mFAAwB,CAAC/B,iEAAD,CAAjD;IAAiEY,QAAQ,EAAEH,sDAAI,CAACuC,0BAAD,oBAAkCC,KAAlC;EAA/E,CAA/B,CAAZ;AACH;;;;;;;;;;;;;;;;;;;;;AC5BD;AACA;AACA;AACA;AACA;AACA,IAAMI,gBAAgB,GAAG;EACrBC,SAAS,EAAE,WADU;EAErBC,YAAY,EAAE;AAFO,CAAzB;AAIe,SAASC,qBAAT,CAA+BC,UAA/B,EAA2CC,QAA3C,EAAqD;EAChE,OAAO,YAAM;IACT,IAAMC,MAAM,GAAG,SAATA,MAAS,GAAM;MACjB,IAAIvF,qEAAgB,KAAKiF,gBAAgB,CAACC,SAA1C,EAAqD;QACjD,OAAQ7C,sDAAI,CAACuB,4DAAD,EAAsB;UAAEC,MAAM,EAAEwB,UAAU,CAACxB,MAArB;UAA6BC,aAAa,EAAEwB;QAA5C,CAAtB,CAAZ;MACH,CAFD,MAGK;QACD,OAAOjD,sDAAI,CAACE,mEAAD,EAAsB,EAAtB,CAAX;MACH;IACJ,CAPD;;IAQA,OAAOF,sDAAI,CAACiB,2CAAD,EAAW;MAAEd,QAAQ,EAAE+C,MAAM;IAAlB,CAAX,CAAX;EACH,CAVD;AAWH;;;;;;;;;;;;;;;;;;;;;;ACrBD;AACA;AACA;AACA;AACA;AACA;AACe,SAASG,oBAAT,CAA8BL,UAA9B,EAA0CC,QAA1C,EAAoD;EAC/D,OAAO,YAAM;IACT,IAAMC,MAAM,GAAG,SAATA,MAAS,GAAM;MACjB,IAAIvF,qEAAgB,KAAKiF,gFAAzB,EAAqD;QACjD,OAAQ5C,sDAAI,CAACoD,6DAAD,EAAW;UAAEJ,UAAU,EAAEA,UAAd;UAA0BM,UAAU,EAAE,IAAtC;UAA4C7B,aAAa,EAAEwB,QAA3D;UAAqEM,OAAO,EAAE,KAA9E;UAAqFC,MAAM,EAAE;QAA7F,CAAX,CAAZ;MACH,CAFD,MAGK;QACD,OAAOxD,sDAAI,CAACmD,mEAAD,EAAe;UAAEM,MAAM,EAAE;QAAV,CAAf,CAAX;MACH;IACJ,CAPD;;IAQA,OAAOzD,sDAAI,CAACiB,2CAAD,EAAW;MAAEd,QAAQ,EAAE+C,MAAM;IAAlB,CAAX,CAAX;EACH,CAVD;AAWH;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AClBD;AACA;AACA;AACA;AACe,SAAS7B,QAAT,GAAoB;EAC/B,IAAM0C,KAAK,GAAGD,uFAA6B,EAA3C;;EACA,gBAAkCJ,+CAAQ,CAACE,yEAAD,CAA1C;EAAA;EAAA,IAAOK,SAAP;EAAA,IAAkBC,YAAlB;;EACA,iBAA6BR,+CAAQ,CAAC,IAAD,CAArC;EAAA;EAAA,IAAOhC,QAAP;EAAA,IAAiByC,QAAjB;;EACA,iBAA0BT,+CAAQ,CAAC,EAAD,CAAlC;EAAA;EAAA,IAAO/B,KAAP;EAAA,IAAcyC,QAAd;;EACAT,gDAAS,CAAC,YAAM;IACZ,IAAIM,SAAS,KAAKL,yEAAlB,EAAuC;MACnCG,KAAK,CAAC;QACFM,GAAG,EAAER,gFADH;QAEFU,OAAO,EAAE;UACLC,MAAM,EAAE;QADH;MAFP,CAAD,CAAL,CAMKC,IANL,CAMU,UAAAC,IAAI,EAAI;QACdN,QAAQ,CAACM,IAAI,CAACpC,GAAL,CAAS,UAACL,IAAD;UAAA,OAAW;YACzB/E,KAAK,EAAE+E,IAAI,CAACtB,IADa;YAEzBvD,KAAK,EAAE6E,IAAI,CAAC0C;UAFa,CAAX;QAAA,CAAT,CAAD,CAAR;QAIAT,YAAY,CAACN,sEAAD,CAAZ;MACH,CAZD,WAaW,UAAAiB,KAAK,EAAI;QAChBV,QAAQ,CAACU,KAAD,CAAR;QACAX,YAAY,CAACN,sEAAD,CAAZ;MACH,CAhBD;IAiBH;EACJ,CApBQ,EAoBN,CAACK,SAAD,CApBM,CAAT;EAqBA,OAAO;IAAEtC,KAAK,EAALA,KAAF;IAASC,OAAO,EAAEqC,SAAS,KAAKL,uEAAhC;IAAmDlC,QAAQ,EAARA;EAAnD,CAAP;AACH;;;;;;;;;;;;;;;;;;;;;;;;;;;AC/BD;AACA;AACA;;IACqBuD;EAKjB,4BAAYC,gBAAZ,EAA8BC,eAA9B,EAA+ClC,QAA/C,EAAyD;IAAA;;IAAA;;IAAA;;IAAA;;IAAA;;IACrD,IAAMD,UAAU,GAAGmC,eAAe,CAACC,OAAhB,CAAwBpC,UAAxB,GACbqC,IAAI,CAACC,KAAL,CAAWH,eAAe,CAACC,OAAhB,CAAwBpC,UAAnC,CADa,GAEb,EAFN;IAGA,KAAKmC,eAAL,GAAuBA,eAAvB;IACA,KAAKD,gBAAL,GAAwBA,gBAAxB;IACA,KAAKjC,QAAL,GAAgBA,QAAhB;IACA,KAAKD,UAAL,GAAkBA,UAAlB;EACH;;;;WACD,kBAAS;MACLgC,uDAAA,CAAgB3B,iEAAoB,CAAC,KAAKL,UAAN,EAAkB,KAAKC,QAAvB,CAApB,EAAhB,EAAwE,KAAKkC,eAA7E;MACAH,uDAAA,CAAgBjC,kEAAqB,CAAC,KAAKC,UAAN,EAAkB,KAAKC,QAAvB,CAArB,EAAhB,EAAyE,KAAKiC,gBAA9E;IACH;;;WACD,gBAAO;MACHF,uEAAA,CAAgC,KAAKG,eAArC;MACAH,uEAAA,CAAgC,KAAKE,gBAArC;IACH;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;ACxBL;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AACA,SAASU,sBAAT,OAAyD;EAAA,IAAvBC,GAAuB,QAAvBA,GAAuB;EAAA,IAAlBpE,aAAkB,QAAlBA,aAAkB;;EACrD,mBAA+EgE,6EAAW,EAA1F;EAAA,IAAwBK,QAAxB,gBAAQC,cAAR;EAAA,IAAkCnE,OAAlC,gBAAkCA,OAAlC;EAAA,IAA2CiD,KAA3C,gBAA2CA,KAA3C;EAAA,IAAkDmB,MAAlD,gBAAkDA,MAAlD;EAAA,IAA0DC,eAA1D,gBAA0DA,eAA1D;;EACA,IAAMC,uBAAuB,GAAGR,6FAA0B,CAACG,GAAD,CAA1D;;EACA,gBAAgCnC,+CAAQ,CAACmC,GAAD,CAAxC;EAAA;EAAA,IAAOM,QAAP;EAAA,IAAiBC,WAAjB;;EACA,IAAMC,qBAAqB,GAAG,SAAxBA,qBAAwB,GAAM;IAChC,OAAOJ,eAAe,GACjBxB,IADE,CACG,YAAM;MACZuB,MAAM;IACT,CAHM,WAII,UAAAnB,KAAK,EAAI;MAChBc,8DAAA,CAAqB,4BAArB,EAAmD;QAC/CY,KAAK,EAAE;UAAE1B,KAAK,EAALA;QAAF;MADwC,CAAnD;IAGH,CARM,CAAP;EASH,CAVD;;EAWA,OAAQ7E,sDAAI,CAACiB,2CAAD,EAAW;IAAEd,QAAQ,EAAEyB,OAAO,GAAI5B,sDAAI,CAAC,KAAD,EAAQ;MAAEG,QAAQ,EAAEH,sDAAI,CAACkB,sEAAD,EAAY,EAAZ;IAAhB,CAAR,CAAR,GAAsD2D,KAAK,GAAI7E,sDAAI,CAACC,+DAAD,EAAkB;MAAEM,IAAI,EAAE,QAAR;MAAkBJ,QAAQ,EAAExD,mDAAE,CAAC,4DAAD,EAA+D,QAA/D;IAA9B,CAAlB,CAAR,GAAwIqE,uDAAK,CAACC,2CAAD,EAAW;MAAEd,QAAQ,EAAE,CAAC+F,uBAAuB,IAAKlG,sDAAI,CAACwF,gEAAD,EAA0B;QAAE/B,MAAM,EAAEyC,uBAAV;QAAmCM,iBAAiB,EAAEP;MAAtD,CAA1B,CAAjC,EAAsIH,QAAQ,CAACW,MAAT,GAAkB,CAAlB,IAAwBzF,uDAAK,CAAC,QAAD,EAAW;QAAE5D,KAAK,EAAE+I,QAAT;QAAmBtE,QAAQ,EAAE,kBAAAC,KAAK,EAAI;UACzc,IAAM4E,MAAM,GAAG5E,KAAK,CAACI,MAAN,CAAa9E,KAA5B;UACAgJ,WAAW,CAACM,MAAD,CAAX;UACAjF,aAAa,CAAC;YACVoE,GAAG,EAAEa;UADK,CAAD,CAAb;QAGH,CANsa;QAMpavG,QAAQ,EAAE,CAACH,sDAAI,CAAC,QAAD,EAAW;UAAE5C,KAAK,EAAE,EAAT;UAAagF,QAAQ,EAAE,IAAvB;UAA6BC,QAAQ,EAAE,IAAvC;UAA6ClC,QAAQ,EAAExD,mDAAE,CAAC,kBAAD,EAAqB,QAArB;QAAzD,CAAX,CAAL,EAA4GmJ,QAAQ,CAACxD,GAAT,CAAa,UAAAqE,IAAI;UAAA,OAAK3G,sDAAI,CAAC,QAAD,EAAW;YAAE5C,KAAK,EAAEuJ,IAAI,CAACvJ,KAAd;YAAqB+C,QAAQ,EAAEwG,IAAI,CAACzJ;UAApC,CAAX,EAAwDyJ,IAAI,CAACvJ,KAA7D,CAAT;QAAA,CAAjB,CAA5G;MAN0Z,CAAX,CAAnK;IAAZ,CAAX;EAA3N,CAAX,CAAZ;AAOH;;AACD,SAASwJ,6BAAT,CAAuCpE,KAAvC,EAA8C;EAC1C,IAAMC,oBAAoB,GAAGrB,iFAAuB,EAApD;EACA,OAAQpB,sDAAI,CAACiB,2CAAD,EAAW;IAAEd,QAAQ,EAAE,CAACsC,oBAAD,GAAyBzC,sDAAI,CAAC,KAAD,EAAQ;MAAEG,QAAQ,EAAEH,sDAAI,CAACkB,sEAAD,EAAY,EAAZ;IAAhB,CAAR,CAA7B,GAA4ElB,sDAAI,CAAC4F,sBAAD,oBAA8BpD,KAA9B;EAA5F,CAAX,CAAZ;AACH;;AACc,SAASqE,gCAAT,CAA0CrE,KAA1C,EAAiD;EAC5D,OAAQxC,sDAAI,CAACmB,kFAAD,EAA+B;IAAE/D,KAAK,EAAEmC,iEAAY,IAAI+B,oFAAwB,CAAC/B,iEAAD,CAAjD;IAAiEY,QAAQ,EAAEH,sDAAI,CAAC4G,6BAAD,oBAAqCpE,KAArC;EAA/E,CAA/B,CAAZ;AACH;;;;;;;;;;;;;;;;;;;;;;;;ACxCD;AACA;AACA;AACA;AACA;AACA;AACA;AACA,IAAM9B,SAAS,gBAAGD,sDAAM,OAANA,CAAM;EAAAE;EAAA;EAAAC;AAAA,CAANH,CAAlB;AAGe,SAASsG,cAAT,OAAwD;EAAA,IAA9BP,iBAA8B,QAA9BA,iBAA8B;EAAA,IAAX/C,MAAW,QAAXA,MAAW;EACnE,IAAMuD,cAAc,GAAGvD,MAAM,KAAKqD,oFAAlC;EACA,IAAMG,SAAS,GAAGD,cAAc,GAC1BrK,mDAAE,CAAC,gCAAD,EAAmC,QAAnC,CADwB,GAE1BA,mDAAE,CAAC,2BAAD,EAA8B,QAA9B,CAFR;EAGA,IAAMuK,YAAY,GAAGF,cAAc,GAC7BrK,mDAAE,CAAC,gEAAD,EAAmE,QAAnE,CAD2B,GAE7BA,mDAAE,CAAC,yGAAD,EAA4G,QAA5G,CAFR;EAGA,OAAQqE,uDAAK,CAACC,2CAAD,EAAW;IAAEd,QAAQ,EAAE,CAACH,sDAAI,CAACU,SAAD,EAAY;MAAEP,QAAQ,EAAEa,uDAAK,CAACf,+DAAD,EAAkB;QAAEM,IAAI,EAAE,SAAR;QAAmBJ,QAAQ,EAAE,CAACH,sDAAI,CAAC,GAAD,EAAM;UAAEG,QAAQ,EAAE8G;QAAZ,CAAN,CAAL,EAAqCjH,sDAAI,CAAC,IAAD,EAAO,EAAP,CAAzC,EAAqDkH,YAArD;MAA7B,CAAlB;IAAjB,CAAZ,CAAL,EAA2JF,cAAc,IAAKhH,sDAAI,CAACa,+DAAD,EAAkB;MAAEsG,EAAE,EAAE,2BAAN;MAAmCC,OAAO,EAAEZ,iBAA5C;MAA+DrG,QAAQ,EAAExD,mDAAE,CAAC,kBAAD,EAAqB,QAArB;IAA3E,CAAlB,CAAlL;EAAZ,CAAX,CAAb;AACJ;;;;;;;;;;;;;;;;;;;;;;;ACnBA;AACA;AACA;AACA;AACA;AACA,IAAMiG,gBAAgB,GAAG;EACrBC,SAAS,EAAE,WADU;EAErBC,YAAY,EAAE;AAFO,CAAzB;AAIe,SAASuE,wBAAT,CAAkCrE,UAAlC,EAA8CC,QAA9C,EAAwD;EACnE,OAAO,YAAM;IACT,IAAMC,MAAM,GAAG,SAATA,MAAS,GAAM;MACjB,IAAIvF,qEAAgB,KAAKiF,gBAAgB,CAACC,SAA1C,EAAqD;QACjD,OAAQ7C,sDAAI,CAAC4F,+DAAD,EAAyB;UAAEC,GAAG,EAAE7C,UAAU,CAAC6C,GAAlB;UAAuBpE,aAAa,EAAEwB;QAAtC,CAAzB,CAAZ;MACH,CAFD,MAGK;QACD,OAAOjD,sDAAI,CAACE,mEAAD,EAAsB,EAAtB,CAAX;MACH;IACJ,CAPD;;IAQA,OAAOF,sDAAI,CAACiB,2CAAD,EAAW;MAAEd,QAAQ,EAAE+C,MAAM;IAAlB,CAAX,CAAX;EACH,CAVD;AAWH;;;;;;;;;;;;;;;;;;;;;ACrBD;AACA;AACA;AACA;AACA;AACA,IAAMN,gBAAgB,GAAG;EACrBC,SAAS,EAAE,WADU;EAErBC,YAAY,EAAE;AAFO,CAAzB;AAIe,SAASyE,uBAAT,CAAiCvE,UAAjC,EAA6CC,QAA7C,EAAuD;EAClE,OAAO,YAAM;IACT,IAAMC,MAAM,GAAG,SAATA,MAAS,GAAM;MACjB,IAAIvF,qEAAgB,KAAKiF,gBAAgB,CAACC,SAA1C,EAAqD;QACjD,OAAQ7C,sDAAI,CAACsH,mEAAD,EAAe;UAAEtE,UAAU,EAAEA,UAAd;UAA0BM,UAAU,EAAE,IAAtC;UAA4C7B,aAAa,EAAEwB,QAA3D;UAAqEM,OAAO,EAAE,KAA9E;UAAqFC,MAAM,EAAE;QAA7F,CAAf,CAAZ;MACH,CAFD,MAGK;QACD,OAAOxD,sDAAI,CAACmD,mEAAD,EAAe;UAAEM,MAAM,EAAE;QAAV,CAAf,CAAX;MACH;IACJ,CAPD;;IAQA,OAAOzD,sDAAI,CAACiB,2CAAD,EAAW;MAAEd,QAAQ,EAAE+C,MAAM;IAAlB,CAAX,CAAX;EACH,CAVD;AAWH;;;;;;;;;;;;;;;;;;;;;;;;;;;ACrBD;AACA;AACA;;IACqBsE;EAKjB,gCAAYtC,gBAAZ,EAA8BC,eAA9B,EAA+ClC,QAA/C,EAAyD;IAAA;;IAAA;;IAAA;;IAAA;;IAAA;;IACrD,IAAMD,UAAU,GAAGmC,eAAe,CAACC,OAAhB,CAAwBpC,UAAxB,GACbqC,IAAI,CAACC,KAAL,CAAWH,eAAe,CAACC,OAAhB,CAAwBpC,UAAnC,CADa,GAEb,EAFN;IAGA,KAAKmC,eAAL,GAAuBA,eAAvB;IACA,KAAKD,gBAAL,GAAwBA,gBAAxB;IACA,KAAKjC,QAAL,GAAgBA,QAAhB;IACA,KAAKD,UAAL,GAAkBA,UAAlB;EACH;;;;WACD,kBAAS;MACLgC,uDAAA,CAAgBuC,oEAAuB,CAAC,KAAKvE,UAAN,EAAkB,KAAKC,QAAvB,CAAvB,EAAhB,EAA2E,KAAKkC,eAAhF;MACAH,uDAAA,CAAgBqC,qEAAwB,CAAC,KAAKrE,UAAN,EAAkB,KAAKC,QAAvB,CAAxB,EAAhB,EAA4E,KAAKiC,gBAAjF;IACH;;;WACD,gBAAO;MACHF,uEAAA,CAAgC,KAAKG,eAArC;MACAH,uEAAA,CAAgC,KAAKE,gBAArC;IACH;;;;;;;;;;;;;;;;;;;;;ACxBU,SAASuC,eAAT,CAAyBC,SAAzB,EAAoCvK,OAApC,EAA6CwK,QAA7C,EAAyE;EAAA,IAAlBC,IAAkB,uEAAX,YAAM,CAAG,CAAE;EACpF,OAAOF,SAAS,CAACG,OAAV,CAAkBC,QAAlB,CAA2BC,QAA3B,CAAoCC,MAApC,CAA2C;IAC9CC,OAD8C,qBACpC;MACN,IAAMC,IAAI,GAAG,IAAb;MACA,IAAMhD,gBAAgB,GAAG,KAAKiD,EAAL,CAAQC,eAAR,CAAwBC,UAAxB,CAAmC,CAAnC,EAAsCC,aAAtC,CAAoDnL,OAAO,CAACoL,eAA5D,CAAzB;MACA,IAAIpD,eAAe,GAAG,KAAKhI,OAAL,CAAaqL,OAAb,CAAqBC,GAArB,CAAyB,CAAzB,EAA4BH,aAA5B,CAA0CnL,OAAO,CAACuL,iBAAlD,CAAtB;;MACA,IAAIvD,eAAJ,EAAqB;QACjBwC,QAAQ,CAACzC,gBAAD,EAAmBC,eAAnB,EAAoC,UAACwD,IAAD;UAAA,OAAUT,IAAI,CAACjF,QAAL,CAAc0F,IAAd,CAAV;QAAA,CAApC,CAAR;MACH,CAFD,MAGK;QACD;QACArL,MAAM,CAACsL,iBAAP,CAAyBC,KAAzB,CAA+BC,SAA/B,kCAAmE3L,OAAO,CAAC4L,UAA3E,eAAiG,UAACP,OAAD,EAAa;UAC1GrD,eAAe,GAAGqD,OAAO,CAAC,CAAD,CAAP,CAAWF,aAAX,CAAyBnL,OAAO,CAACuL,iBAAjC,CAAlB;UACAf,QAAQ,CAACzC,gBAAD,EAAmBC,eAAnB,EAAoC,UAACwD,IAAD;YAAA,OAAUT,IAAI,CAACjF,QAAL,CAAc0F,IAAd,CAAV;UAAA,CAApC,CAAR;QACH,CAHD;MAIH;IACJ,CAf6C;IAgB9CK,SAhB8C,qBAgBpCxG,KAhBoC,EAgB7B;MACb,KAAKS,QAAL,CAAcT,KAAd;IACH,CAlB6C;IAmB9CyG,eAnB8C,6BAmB5B;MACd;MACA3L,MAAM,CAACsL,iBAAP,CAAyBC,KAAzB,CAA+BK,YAA/B,kCAAsE/L,OAAO,CAAC4L,UAA9E;MACAnB,IAAI;IACP;EAvB6C,CAA3C,CAAP;AAyBH;;;;;;;;;;;;;;;AC1BM,IAAMuB,YAAY,GAAG;EACxBC,gBAAgB,EAAE,4CADM;EAExBC,gBAAgB,EAAE,4CAFM;EAGxBC,iBAAiB,EAAE,6CAHK;EAIxBC,mBAAmB,EAAE,+CAJG;EAKxBC,UAAU,EAAE,qCALY;EAMxBC,YAAY,EAAE;AANU,CAArB;;;;;;;;;;;;;;;ACAA,IAAMC,YAAY,GAAG;EACxBC,uBAAuB,EAAE;AADD,CAArB;;;;;;;;;;;;;;;;;;;;;;;;ACAP;AACA;AACA;AACA;;;;;;;;;;;;;;;;ACHO,IAAMC,gBAAgB,GAAG;EAC5BC,2BAA2B,EAAE;AADD,CAAzB;;;;;;;;;;;;;;;ACAA,IAAMC,cAAc,GAAG;EAC1BC,wBAAwB,EAAE,4BADA;EAE1BC,kBAAkB,EAAE,sBAFM;EAG1BC,YAAY,EAAE,uCAHY;EAI1BC,4BAA4B,EAAE,mCAJJ;EAK1BC,6BAA6B,EAAE,oCALL;EAM1BC,0BAA0B,EAAE,iCANF;EAO1BC,6BAA6B,EAAE,oCAPL;EAQ1BC,2BAA2B,EAAE,kCARH;EAS1BC,wBAAwB,EAAE,6BATA;EAU1BC,yBAAyB,EAAE,oCAVD;EAW1BC,sBAAsB,EAAE,iCAXE;EAY1BC,yBAAyB,EAAE,8BAZD;EAa1BC,uBAAuB,EAAE,4BAbC;EAc1BC,iBAAiB,EAAE,qBAdO;EAe1BC,kBAAkB,EAAE,sBAfM;EAgB1BC,eAAe,EAAE,mBAhBS;EAiB1BC,sBAAsB,EAAE,2BAjBE;EAkB1BC,0BAA0B,EAAE,+BAlBF;EAmB1BC,2BAA2B,EAAE,gCAnBH;EAoB1BC,wBAAwB,EAAE,6BApBA;EAqB1BC,6BAA6B,EAAE,kCArBL;EAsB1BC,8BAA8B,EAAE,mCAtBN;EAuB1BC,2BAA2B,EAAE;AAvBH,CAAvB;;;;;;;;;;;;;;;ACAA,IAAMxH,aAAa,GAAG;EACzBS,UAAU,EAAE,aADa;EAEzBgH,SAAS,EAAE,YAFc;EAGzBC,sBAAsB,EAAE,2BAHC;EAIzBC,SAAS,EAAE,YAJc;EAKzBC,qBAAqB,EAAE,0BALE;EAMzBC,kCAAkC,EAAE,yCANX;EAOzBC,wBAAwB,EAAE,8BAPD;EAQzBC,uBAAuB,EAAE,2BARA;EASzBC,sBAAsB,EAAE,2BATC;EAUzBC,4BAA4B,EAAE,kCAVL;EAWzBC,uBAAuB,EAAE,4BAXA;EAYzBC,yBAAyB,EAAE,8BAZF;EAazBC,sBAAsB,EAAE,2BAbC;EAczBC,uBAAuB,EAAE,4BAdA;EAezBC,4BAA4B,EAAE,iCAfL;EAgBzBC,0BAA0B,EAAE,+BAhBH;EAiBzBC,uBAAuB,EAAE;AAjBA,CAAtB;;;;;;;;;;;;;;;;;;;;ACAP;AACO,IAAMlL,mBAAmB,gBAAGmL,oDAAa,CAAC,IAAD,CAAzC;AACA,SAASlL,uBAAT,GAAmC;EACtC,OAAOmL,iDAAU,CAACpL,mBAAD,CAAjB;AACH;AACM,SAASqL,wBAAT,GAAoC;EACvC,IAAMC,GAAG,GAAGrL,uBAAuB,EAAnC;EACA,OAAO,UAACsL,OAAD,EAAa;IAChBD,GAAG,CAACE,WAAJ,CAAgBD,OAAhB;EACH,CAFD;AAGH;AACM,SAAS5I,6BAAT,GAAyC;EAC5C,IAAM2I,GAAG,GAAGrL,uBAAuB,EAAnC;EACA,OAAO,UAACsL,OAAD;IAAA,OAAaD,GAAG,CAACG,gBAAJ,CAAqBF,OAArB,CAAb;EAAA,CAAP;AACH;;;;;;;;;;;;;;;;;;;ACdD;AACA;AACO,SAASG,cAAT,GAA0B;EAC7B,IAAI1O,2EAAA,CAAuB,iBAAvB,MAA8C,CAAC,CAAnD,EAAsD;IAClD;EACH;;EACDwH,sDAAA,CAAa,mEAAb,EAAkF;IAC9EqH,UAAU,EAAE;MACRC,QAAQ,EAAE;IADF,CADkE;IAI9EC,OAAO,EAAExO,wEAAmBA;EAJkD,CAAlF,EAKGyO,OALH;EAMAxH,8DAAA,CAAqB;IACjB0H,CAAC,EAAE3O,wEADc;IAEjB4O,GAAG,EAAExO,+DAFY;IAGjByO,SAAS,EAAE5N,8DAASA;EAHH,CAArB;EAKAgG,+DAAA,CAAsB;IAClB8H,GAAG,EAAEtO,6DADa;IAElBH,OAAO,EAAE0O,MAAM,CAACC,IAAP,CAAY3O,4DAAZ,EACJsD,GADI,CACA,UAAA3B,IAAI;MAAA,iBAAOA,IAAP,cAAe3B,4DAAO,CAAC2B,IAAD,CAAtB;IAAA,CADJ,EAEJiN,IAFI,CAEC,GAFD;EAFS,CAAtB;AAMH;AACD,iEAAejI,iDAAf;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;ACxBA;AACA;AACA;AACA;AACA;AACA;AACA,IAAMjF,SAAS,gBAAGD,sDAAM,OAANA,CAAM;EAAAE;EAAA;EAAAC;AAAA,CAANH,CAAlB;;AAKE,YAVgB,sBAUhBuN,KAVgB;EAAA,OAiBAxL,eAAK;IAAA,OAAKA,KAAK,CAACyL,OAANzL,GAAgB,GAAhBA,GAAsB,KAA3B;EAAA,CAjBL;AAAA,CAUhB;;AAOsD,YAjBtC,sBAiBsC0L,KAjBtC;EAAA,OA2BF1L,eAAK;IAAA,OAAIA,KAAK,CAACyL,OAANzL,uBAA6BuL,gEAA7BvL,IAAgD,MAApD;EAAA,CA3BH;AAAA,CAiBsC;;AANxD,IAAM2L,gBAAgB,gBAAG1N,sDAAM,OAANA,CAAM;EAAAE;EAAA;EAAAC;EAAAwN;IAAA,eAMbJ,KAAsC,EANzB;IAMyB,eAUxCE,KAA+D,EAVvB;EANzB;AAAA,CAANzN,CAAzB;AAqBA,IAAM4N,cAAc,gBAAG5N,sDAAM,OAANA,CAAM;EAAAE;EAAA;EAAAC;AAAA,CAANH,CAAvB;AAUA,IAAM6N,WAAW,gBAAG7N,sDAAM,OAANA,CAAM;EAAAE;EAAA;EAAAC;AAAA,CAANH,CAApB;AAUA,IAAM8N,WAAW,gBAAG9N,sDAAM,OAANA,CAAM;EAAAE;EAAA;EAAAC;AAAA,CAANH,CAApB;AAaA,IAAM+N,kBAAkB,gBAAG/N,sDAAM,OAANA,CAAM;EAAAE;EAAA;EAAAC;AAAA,CAANH,CAA3B;AAOA,IAAMgO,iBAAiB,gBAAGhO,sDAAM,OAANA,CAAM;EAAAE;EAAA;EAAAC;AAAA,CAANH,CAA1B;AAQA,IAAMiO,cAAc,gBAAGjO,sDAAM,OAANA,CAAM;EAAAE;EAAA;EAAAC;AAAA,CAANH,CAAvB;AAQA,IAAMkO,KAAK,gBAAGlO,sDAAM,SAANA,CAAM;EAAAE;EAAA;EAAAC;AAAA,CAANH,CAAd;AAWA,IAAMmO,WAAW,gBAAGnO,sDAAM,OAANA,CAAM;EAAAE;EAAA;EAAAC;AAAA,CAANH,CAApB;AAKA,IAAMoO,aAAa,gBAAGpO,sDAAM,OAANA,CAAM;EAAAE;EAAA;EAAAC;AAAA,CAANH,CAAtB;AAWA,IAAMqO,QAAQ,gBAAGrO,sDAAM,OAANA,CAAM;EAAAE;EAAA;EAAAC;AAAA,CAANH,CAAjB;AAOA,IAAMsO,SAAS,gBAAGtO,sDAAM,OAANA,CAAM;EAAAE;EAAA;EAAAC;AAAA,CAANH,CAAlB;AAIA,IAAMuO,eAAe,gBAAGvO,sDAAM,OAANA,CAAM;EAAAE;EAAA;EAAAC;AAAA,CAANH,CAAxB;;AASE,YAvIgB,sBAuIhBwO,KAvIgB;EAAA,OA0IIzM,eAAK;IAAA,OAAIA,KAAK,CAACH,QAANG,GAAiBuL,gEAAjBvL,GAAkC,aAAtC;EAAA,CA1IT;AAAA,CAuIhB;;AAG4E,YA1I5D,sBA0I4D0M,KA1I5D;EAAA,OA2IP1M,eAAK;IAAA,OAAKA,KAAK,CAACH,QAANG,GAAiB,MAAjBA,GAA0B,SAA/B;EAAA,CA3IE;AAAA,CA0I4D;;AACrB,YA3IvC,sBA2IuC2M,KA3IvC;EAAA,OAiJM3M,eAAK;IAAA,OAAIA,KAAK,CAACH,QAANG,GAAiBuL,gEAAjBvL,GAAkCsL,+DAAtC;EAAA,CAjJX;AAAA,CA2IuC;;AAHzD,IAAMsB,QAAQ,gBAAG3O,sDAAM,OAANA,CAAM;EAAAE;EAAA;EAAAC;EAAAwN;IAAA,eAEDa,KAAwD,EAFvD;IAEuD,eACnEC,KAA8C,EADqB,CAFvD;IAGkC,eAMjCC,KAAwD,EANvB;EAHlC;AAAA,CAAN1O,CAAjB;AAYe,SAAS4O,WAAT,OAAqF;EAAA,IAA9DC,WAA8D,QAA9DA,WAA8D;EAAA,IAAjDlS,KAAiD,QAAjDA,KAAiD;EAAA,IAA1CmS,WAA0C,QAA1CA,WAA0C;EAAA,IAA7B1N,QAA6B,QAA7BA,QAA6B;EAAA,IAAnB2N,cAAmB,QAAnBA,cAAmB;EAChG,IAAMC,OAAO,GAAG5B,6CAAM,CAAC,IAAD,CAAtB;EACA,IAAM6B,aAAa,GAAG7B,6CAAM,CAAC,IAAD,CAA5B;;EACA,gBAA8BnK,+CAAQ,CAAC,KAAD,CAAtC;EAAA;EAAA,IAAOiM,SAAP;EAAA,IAAkBC,QAAlB;;EACA,iBAAkClM,+CAAQ,CAACE,kEAAD,CAA1C;EAAA;EAAA,IAAOK,SAAP;EAAA,IAAkBC,YAAlB;;EACA,iBAAoCR,+CAAQ,CAAC,EAAD,CAA5C;EAAA;EAAA,IAAOmM,UAAP;EAAA,IAAmBC,aAAnB;;EACA,iBAA8BpM,+CAAQ,CAAC8L,cAAD,CAAtC;EAAA;EAAA,IAAOrS,OAAP;EAAA,IAAgB4S,UAAhB;;EACA,IAAMC,SAAS,aAAMN,aAAa,CAACO,OAAdP,GAAwBA,aAAa,CAACO,OAAdP,CAAsBQ,WAAtBR,GAAoC,EAA5DA,GAAiE,CAAvE,OAAf;EACA/L,gDAAS,CAAC,YAAM;IACZ,IAAI4L,WAAW,IAAItL,SAAS,KAAKL,kEAAjC,EAAsD;MAClD2L,WAAW,CAAC,EAAD,EAAMY,gBAAM,EAAK;QACxBJ,UAAU,CAACI,MAAD,CAAVJ;QACA7L,YAAY,CAACN,6DAAD,CAAZM;MACH,CAHU,CAAXqL;IAIJ;EACH,CAPQ,EAON,CAACA,WAAD,EAActL,SAAd,CAPM,CAATN;;EAQA,IAAM0M,WAAW,GAAG,SAAdA,WAAc,GAA2B;IAAA,IAA1BC,KAA0B,uEAAlB,EAAkB;IAAA,IAAdC,SAAc;IAC3C,OAAOD,KAAK,CAAChO,GAANgO,CAAU,UAAC3J,IAAD,EAAO6J,KAAP,EAAiB;MAC9B,IAAI7J,IAAI,CAACxJ,OAAT,EAAkB;QACd,OAAQ6D,uDAAK,CAAC+N,SAAD,EAAY;UAAE5O,QAAQ,EAAE,CAACH,sDAAI,CAACgP,eAAD,EAAkB;YAAE7H,EAAE,YAAKqJ,KAAL,aAAJ;YAA0BrQ,QAAQ,EAAEwG,IAAI,CAACzJ;UAAzC,CAAlB,CAAL,EAA0E8C,sDAAI,CAAC,KAAD,EAAQ;YAAEG,QAAQ,EAAEkQ,WAAW,CAAC1J,IAAI,CAACxJ,OAAN,EAAeqT,KAAf;UAAvB,CAAR,CAA9E;QAAZ,CAAZ,8BAAuLA,KAAvL,EAAb;MACH,CAFD,MAGK;QACD,IAAMnM,GAAG,+BAAwBkM,SAAS,KAAKE,SAAdF,aAA6BA,SAA7BA,cAA0CC,KAA1CD,IAAoDC,KAA5E,CAAT;QACA,OAAQxQ,sDAAI,CAACoP,QAAD,EAAW;UAAEjI,EAAE,EAAE9C,GAAN;UAAWhC,QAAQ,EAAEjF,KAAK,IAAIuJ,IAAI,CAACvJ,KAALuJ,KAAevJ,KAAK,CAACA,KAAnD;UAA0DgK,OAAO,EAAE,mBAAM;YACxFvF,QAAQ,CAAC8E,IAAD,CAAR9E;YACA+N,QAAQ,CAAC,KAAD,CAARA;UACH,CAHkB;UAGhBzP,QAAQ,EAAEwG,IAAI,CAACzJ;QAHC,CAAX,EAGmBmH,GAHnB,CAAZ;MAIJ;IACH,CAXMiM,CAAP;EAYH,CAbD;;EAcA,OAAQtP,uDAAK,CAACN,SAAD,EAAY;IAAEP,QAAQ,EAAE,CAACa,uDAAK,CAACmN,gBAAD,EAAmB;MAAEhH,EAAE,EAAE,uBAAN;MAA+B8G,OAAO,EAAE0B,SAAxC;MAAmDvI,OAAO,EAAE,mBAAM;QAChH,IAAIuI,SAAJ,EAAe;UACX,IAAIF,OAAO,CAACQ,OAAZ,EAAqB;YACjBR,OAAO,CAACQ,OAARR,CAAgBiB,IAAhBjB;UACJ;;UACAG,QAAQ,CAAC,KAAD,CAARA;UACAE,aAAa,CAAC,EAAD,CAAbA;QACH,CAND,MAOK;UACD,IAAIL,OAAO,CAACQ,OAAZ,EAAqB;YACjBR,OAAO,CAACQ,OAARR,CAAgBkB,KAAhBlB;UACJ;;UACAG,QAAQ,CAAC,IAAD,CAARA;QACJ;MACH,CAdiD;MAc/CzP,QAAQ,EAAE,CAACa,uDAAK,CAACqN,cAAD,EAAiB;QAAElO,QAAQ,EAAE,CAAC0P,UAAU,KAAK,EAAfA,KAChC,CAACzS,KAAD,GAAU4C,sDAAI,CAACsO,WAAD,EAAc;UAAEnO,QAAQ,EAAEmP;QAAZ,CAAd,CAAd,GAA2DtP,sDAAI,CAACuO,WAAD,EAAc;UAAEpO,QAAQ,EAAE/C,KAAK,CAACF;QAAlB,CAAd,CAD/B2S,CAAD,EAC4E7O,uDAAK,CAAC0N,cAAD,EAAiB;UAAEvO,QAAQ,EAAE,CAACH,sDAAI,CAAC2O,KAAD,EAAQ;YAAEiC,GAAG,EAAEnB,OAAP;YAAgBoB,OAAO,EAAE,mBAAM;cAC9KjB,QAAQ,CAAC,IAAD,CAARA;YACH,CAFkJ;YAEhJ/N,QAAQ,EAAEiP,mBAAC,EAAI;cACdhB,aAAa,CAACgB,CAAC,CAAC5O,MAAF4O,CAAS1T,KAAV,CAAb0S;cACA5L,YAAY,CAACN,gEAAD,CAAZM;cACAqL,WAAW,IACPA,WAAW,CAACuB,CAAC,CAAC5O,MAAF4O,CAAS1T,KAAV,EAAkB+S,gBAAM,EAAK;gBACpCJ,UAAU,CAACI,MAAD,CAAVJ;gBACA7L,YAAY,CAACN,6DAAD,CAAZM;cACH,CAHU,CADfqL;YAKH,CAVkJ;YAUhJnS,KAAK,EAAEyS,UAVyI;YAU7HkB,KAAK,EAAEf,SAVsH;YAU3G7I,EAAE,EAAE;UAVuG,CAAR,CAAL,EAUjEnH,sDAAI,CAAC4O,WAAD,EAAc;YAAEgC,GAAG,EAAElB,aAAP;YAAsBvP,QAAQ,EAAE0P;UAAhC,CAAd,CAV6D;QAAZ,CAAjB,CADjF;MAAZ,CAAjB,CAAN,EAWyJ7O,uDAAK,CAACwN,kBAAD,EAAqB;QAAErO,QAAQ,EAAE,CAAC8D,SAAS,KAAKL,gEAAdK,IAAmCjE,sDAAI,CAACkB,+DAAD,EAAY,EAAZ,CAAxC,EAAyDlB,sDAAI,CAACyO,iBAAD,EAAoB,EAApB,CAA7D;MAAZ,CAArB,CAX9J;IAdqC,CAAnB,CAAN,EAyBiRkB,SAAS,IAAK3P,sDAAI,CAAC6O,aAAD,EAAgB;MAAE1O,QAAQ,EAAEH,sDAAI,CAAC8O,QAAD,EAAW;QAAE3O,QAAQ,EAAEkQ,WAAW,CAAClT,OAAD;MAAvB,CAAX;IAAhB,CAAhB,CAzBnS;EAAZ,CAAZ,CAAb;AA0BJ;;;;;;;;;;;;;;;;;;;;;;;;AC7MA;AACA;AACA;AACA;AACA;AACA;AACA;;AACA,SAASgU,gBAAT,GAA4B;EACxB7T,MAAM,CAAC8T,QAAP,CAAgBC,IAAhB,aAA0B5T,6DAA1B,kDAA0E2B,kEAA1E;AACH;;AACc,SAAS+D,YAAT,OAAyG;EAAA,IAAjFM,MAAiF,QAAjFA,MAAiF;EAAA,IAAzE6N,eAAyE,QAAzEA,eAAyE;EAAA,0BAAxDC,SAAwD;EAAA,IAAxDA,SAAwD,+BAA5C;IAAEC,MAAM,EAAE,EAAV;IAAc9E,OAAO,EAAE,EAAvB;IAA2B+E,MAAM,EAAE;EAAnC,CAA4C;EACpH,IAAMC,cAAc,GAAGjO,MAAM,KAAK,GAAX,IAAkBA,MAAM,KAAK,GAApD;EACA,IAAMkO,WAAW,GAAGD,cAAc,GAC5B/U,mDAAE,CAAC,8BAAD,EAAiC,QAAjC,CAD0B,GAE5B4U,SAAS,CAACC,MAFhB;EAGA,IAAMI,YAAY,GAAGF,cAAc,GAC7B/U,mDAAE,CAAC,2DAAD,EAA8D,QAA9D,CAD2B,GAE7B4U,SAAS,CAAC7E,OAFhB;EAGA,OAAQ1M,sDAAI,CAACkR,uDAAD,EAAiB;IAAEnS,UAAU,EAAEA,+DAAd;IAA0BoB,QAAQ,EAAEa,uDAAK,CAACiQ,iEAAD,EAAc;MAAEY,SAAS,EAAE,QAAb;MAAuB1R,QAAQ,EAAE,CAACH,sDAAI,CAAC,IAAD,EAAO;QAAEG,QAAQ,EAAEwR;MAAZ,CAAP,CAAL,EAAwC3R,sDAAI,CAAC,GAAD,EAAM;QAAEG,QAAQ,EAAEH,sDAAI,CAAC,GAAD,EAAM;UAAEG,QAAQ,EAAEyR;QAAZ,CAAN;MAAhB,CAAN,CAA5C,EAAwGF,cAAc,GAAI1R,sDAAI,CAACgR,8DAAD,EAAW;QAAE,gBAAgB,kBAAlB;QAAsC5J,OAAO,EAAE+J,gBAA/C;QAAiEhR,QAAQ,EAAExD,mDAAE,CAAC,cAAD,EAAiB,QAAjB;MAA7E,CAAX,CAAR,GAAkIqD,sDAAI,CAACgR,8DAAD,EAAW;QAAE,gBAAgB,cAAlB;QAAkC5J,OAAO,EAAEkK,eAA3C;QAA4DnR,QAAQ,EAAEoR,SAAS,CAACE;MAAhF,CAAX,CAA5P;IAAjC,CAAd;EAAzC,CAAjB,CAAZ;AACH;;;;;;;;;;;;;;;;ACnBD;;AAAwC,WACtB,sBADsBK,IACtB;EAAA,OACItP,eAAK;IAAA,qBAAWA,KAAK,CAACzD,UAAjB;EAAA,CADT;AAAA,CADsB;;AAEkD,YADxE,sBACwEiP,KADxE;EAAA,OAUJxL,eAAK;IAAA,OAAKA,KAAK,CAACuP,OAANvP,IAAiB,eAAtB;EAAA,CAVD;AAAA,CACwE;;AAD1F,8EAAe/B,sDAAM,OAANA,CAAM;EAAAE;EAAA;EAAAC;EAAAwN;IAAA,eACC0D,IAAoE,EADrE;IACqE,eAS7E9D,KAA2C,EATkC;EADrE;AAAA,CAANvN,CAAf;;;;;;;;;;;;;;;;;;;;;ACDA;AACA;AACA;AACA;AACe,SAASuR,YAAT,GAAwB;EACnC,OAAQhS,sDAAI,CAACkR,uDAAD,EAAiB;IAAEnS,UAAU,EAAEA,+DAAd;IAA0BoB,QAAQ,EAAEH,sDAAI,CAACkB,+DAAD,EAAY;MAAE+Q,IAAI,EAAE;IAAR,CAAZ;EAAxC,CAAjB,CAAZ;AACH;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;ACND;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AACA,SAAS7O,QAAT,OAAoG;EAAA,IAAhFJ,UAAgF,QAAhFA,UAAgF;EAAA,IAApEM,UAAoE,QAApEA,UAAoE;EAAA,IAAxD7B,aAAwD,QAAxDA,aAAwD;EAAA,wBAAzC8B,OAAyC;EAAA,IAAzCA,OAAyC,6BAA/B,IAA+B;EAAA,uBAAzBC,MAAyB;EAAA,IAAzBA,MAAyB,4BAAhB,WAAgB;EAChG,IAAQhC,MAAR,GAA6BwB,UAA7B,CAAQxB,MAAR;EAAA,IAAgBW,QAAhB,GAA6Ba,UAA7B,CAAgBb,QAAhB;EACA,IAAMkQ,YAAY,GAAGlT,6DAAQ,IAAIqC,MAAjC;EACA,IAAMiB,oBAAoB,GAAGrB,iFAAuB,EAApD;EACA,IAAMkR,wBAAwB,GAAG9F,kFAAwB,EAAzD;;EACA,IAAM+F,YAAY,GAAG,SAAfA,YAAe,CAACxQ,YAAD,EAAkB;IACnCN,aAAa,CAAC;MACVtC,QAAQ,EAARA,6DADU;MAEVqC,MAAM,EAAEO,YAAY,CAAC3E,KAFX;MAGV+E,QAAQ,EAAEJ,YAAY,CAAC7E;IAHb,CAAD,CAAb;EAKH,CAND;;EAOAyG,gDAAS,CAAC,YAAM;IACZ2O,wBAAwB,CAAC;MACrBjO,GAAG,EAAER,4FADgB;MAErBU,OAAO,EAAE;QACLf,MAAM,EAANA;MADK;IAFY,CAAD,CAAxB;EAMH,CAPQ,EAON,CAACA,MAAD,CAPM,CAAT;EAQA,OAAO,CAACf,oBAAD,GAAyBzC,sDAAI,CAACgS,4DAAD,EAAe,EAAf,CAA7B,GAAoDhR,uDAAK,CAACC,2CAAD,EAAW;IAAEd,QAAQ,EAAE,CAAC,CAACmD,UAAU,IAAI,CAAC+O,YAAhB,KAAkCrS,sDAAI,CAACoS,mDAAD,EAAa;MAAE5Q,MAAM,EAAEA,MAAV;MAAkBW,QAAQ,EAAEA,QAA5B;MAAsCoQ,YAAY,EAAEA,YAApD;MAAkE/O,MAAM,EAAEA;IAA1E,CAAb,CAAvC,EAA0I6O,YAAY,IAAKrR,uDAAK,CAACC,2CAAD,EAAW;MAAEd,QAAQ,EAAE,CAACmD,UAAU,IAAItD,sDAAI,CAACkS,8DAAD,EAAW,EAAX,CAAnB,EAAmC3O,OAAO,IAAIvD,sDAAI,CAACmS,oDAAD,EAAc;QAAEhT,QAAQ,EAAEA,6DAAZ;QAAsBqC,MAAM,EAAEA;MAA9B,CAAd,CAAlD;IAAZ,CAAX,CAAhK;EAAZ,CAAX,CAAhE;AACH;;AACc,SAASgR,iBAAT,CAA2BhQ,KAA3B,EAAkC;EAC7C,OAAQxC,sDAAI,CAACmB,kFAAD,EAA+B;IAAE/D,KAAK,EAAEmC,iEAAY,IAAI+B,mFAAwB,CAAC/B,iEAAD,CAAjD;IAAiEY,QAAQ,EAAEH,sDAAI,CAACoD,QAAD,oBAAgBZ,KAAhB;EAA/E,CAA/B,CAAZ;AACH;;;;;;;;;;;;;;;;;;;;;;;;AClCD;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACe,SAAS4P,UAAT,OAA+E;EAAA,IAAzD5Q,MAAyD,QAAzDA,MAAyD;EAAA,IAAjDW,QAAiD,QAAjDA,QAAiD;EAAA,IAAvCoQ,YAAuC,QAAvCA,YAAuC;EAAA,uBAAzB/O,MAAyB;EAAA,IAAzBA,MAAyB,4BAAhB,WAAgB;;EAC1F,gBAAwCnC,2DAAQ,EAAhD;EAAA,IAAQmD,MAAR,aAAQA,MAAR;EAAA,IAAgBmO,YAAhB,aAAgBA,YAAhB;EAAA,IAA8BC,KAA9B,aAA8BA,KAA9B;;EACA,4BAA0GF,4EAAyB,CAAClP,MAAD,CAAnI;EAAA,IAAQqP,oBAAR,yBAAQA,oBAAR;EAAA,IAAqCC,WAArC,yBAA8BF,KAA9B;EAAA,IAAkDG,UAAlD,yBAAkDA,UAAlD;EAAA,IAA8DrR,QAA9D,yBAA8DA,QAA9D;EAAA,IAAsFsR,cAAtF,yBAAwEL,YAAxE;;EACA,IAAMvV,KAAK,GAAGoE,MAAM,IAAIW,QAAV,GACR;IACEjF,KAAK,EAAEiF,QADT;IAEE/E,KAAK,EAAEoE;EAFT,CADQ,GAKR,IALN;;EAMA,IAAMyR,iBAAiB,GAAG,SAApBA,iBAAoB,CAACC,MAAD,EAAY;IAClC,IAAI7V,4EAAa,CAAC6V,MAAM,CAAC9V,KAAR,CAAjB,EAAiC;MAC7ByV,oBAAoB,CAACK,MAAM,CAAC9V,KAAR,CAApB,CAAmCqH,IAAnC,CAAwC,iBAAoB;QAAA,IAAjBE,IAAiB,SAAjBA,IAAiB;QAAA,IAAXhE,IAAW,SAAXA,IAAW;QACxD4R,YAAY,CAAC;UACTnV,KAAK,EAAEuH,IADE;UAETzH,KAAK,EAAEyD;QAFE,CAAD,CAAZ;MAIH,CALD;IAMH,CAPD,MAQK;MACD4R,YAAY,CAACW,MAAD,CAAZ;IACH;EACJ,CAZD;;EAaA,OAAOH,UAAU,GAAI/S,sDAAI,CAACgS,4DAAD,EAAe,EAAf,CAAR,GAA8BW,YAAY,IAAIK,cAAhB,GAAkChT,sDAAI,CAACmD,4DAAD,EAAe;IAAEM,MAAM,EAAEkP,YAAY,GAAGA,YAAY,CAAClP,MAAhB,GAAyBuP,cAAc,CAACvP,MAA9D;IAAsE6N,eAAe,EAAE,2BAAM;MACzL,IAAI5P,QAAJ,EAAc;QACVoR,WAAW;MACd,CAFD,MAGK;QACDF,KAAK;MACR;IACJ,CAP+F;IAO7FrB,SAAS,EAAE;MACVC,MAAM,EAAE7U,mDAAE,CAAC,2CAAD,EAA8C,QAA9C,CADA;MAEV+P,OAAO,EAAE/P,mDAAE,CAAC,yDAAD,EAA4D,QAA5D,CAFD;MAGV8U,MAAM,EAAE9U,mDAAE,CAAC,eAAD,EAAkB,QAAlB;IAHA;EAPkF,CAAf,CAAtC,GAWlCqD,sDAAI,CAACyS,qDAAD,EAAe;IAAElD,WAAW,EAAE/K,MAAf;IAAuB3C,QAAQ,EAAE,kBAACqR,MAAD;MAAA,OAAYD,iBAAiB,CAACC,MAAD,CAA7B;IAAA,CAAjC;IAAwE9V,KAAK,EAAEA;EAA/E,CAAf,CAXjB;AAYH;;;;;;;;;;;;;;;;;;;;;AC1CD;AACA;AACA;AACA;AACA;AACe,SAASqV,YAAT,OAAyD;EAAA,IAAjClD,WAAiC,QAAjCA,WAAiC;EAAA,IAApB1N,QAAoB,QAApBA,QAAoB;EAAA,IAAVzE,KAAU,QAAVA,KAAU;EACpE,OAAQ4D,uDAAK,CAACkQ,8DAAD,EAAiB;IAAEnS,UAAU,EAAEA,+DAAd;IAA0BoB,QAAQ,EAAE,CAACH,sDAAI,CAAC,GAAD,EAAM;MAAE,gBAAgB,oBAAlB;MAAwCG,QAAQ,EAAEH,sDAAI,CAAC,GAAD,EAAM;QAAEG,QAAQ,EAAExD,mDAAE,CAAC,6DAAD,EAAgE,QAAhE;MAAd,CAAN;IAAtD,CAAN,CAAL,EAAsKqD,sDAAI,CAACqP,2DAAD,EAAc;MAAEC,WAAW,EAAE3S,mDAAE,CAAC,mBAAD,EAAsB,QAAtB,CAAjB;MAAkDS,KAAK,EAAEA,KAAzD;MAAgEmS,WAAW,EAAEA,WAA7E;MAA0F1N,QAAQ,EAAEA;IAApG,CAAd,CAA1K;EAApC,CAAjB,CAAb;AACH;;;;;;;;;;;;;;;;;;;;;ACPD;AACA;AACA;AACA;AACA;AACe,SAASsQ,WAAT,OAA4C;EAAA,IAArBhT,QAAqB,QAArBA,QAAqB;EAAA,IAAXqC,MAAW,QAAXA,MAAW;EACvD,IAAMiO,OAAO,GAAG5B,6CAAM,CAAC,IAAD,CAAtB;EACA,IAAMwF,KAAK,GAAGD,iEAAa,EAA3B;EACAzP,gDAAS,CAAC,YAAM;IACZ,IAAI,CAAC0P,KAAL,EAAY;MACR;IACH;;IACD,IAAI5D,OAAO,CAACQ,OAAZ,EAAqB;MACjBR,OAAO,CAACQ,OAAR,CAAgBqD,SAAhB,GAA4B,EAA5B;MACA,IAAMC,WAAW,GAAGC,QAAQ,CAACC,aAAT,CAAuB,QAAvB,CAApB;MACAF,WAAW,CAACD,SAAZ,6CAA2DnU,QAA3D,yBAAkFqC,MAAlF,yBAAuGtD,2DAAvG,gBAAmHD,uEAAnH;MACAwR,OAAO,CAACQ,OAAR,CAAgByD,WAAhB,CAA4BH,WAA5B;IACH;EACJ,CAVQ,EAUN,CAAC/R,MAAD,EAASrC,QAAT,EAAmBkU,KAAnB,EAA0B5D,OAA1B,CAVM,CAAT;EAWA,OAAOzP,sDAAI,CAACmT,+DAAD,EAAY;IAAEvC,GAAG,EAAEnB;EAAP,CAAZ,CAAX;AACH;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;ACpBD;AACA;AACA;AACA;AACe,SAASiD,yBAAT,GAAyD;EAAA,IAAtBlP,MAAsB,uEAAb,WAAa;EACpE,IAAMO,KAAK,GAAGD,uFAA6B,EAA3C;EACA,IAAM6P,KAAK,GAAGnH,kFAAwB,EAAtC;;EACA,gBAAkC9I,+CAAQ,CAACE,6DAAD,CAA1C;EAAA;EAAA,IAAOK,SAAP;EAAA,IAAkBC,YAAlB;;EACA,iBAAwCR,+CAAQ,CAAC,IAAD,CAAhD;EAAA;EAAA,IAAOiP,YAAP;EAAA,IAAqBiB,eAArB;;EACA,IAAMf,oBAAoB,GAAG,SAAvBA,oBAAuB,CAACtS,IAAD,EAAU;IACnC2D,YAAY,CAACN,gEAAD,CAAZ;IACA+P,KAAK,CAAC;MACFtP,GAAG,EAAER,kGADH;MAEFU,OAAO,EAAE;QACLhE,IAAI,EAAJA,IADK;QAELiD,MAAM,EAANA;MAFK;IAFP,CAAD,CAAL;IAOA,OAAOO,KAAK,CAAC;MACTM,GAAG,EAAER,4FADI;MAETU,OAAO,EAAEhE;IAFA,CAAD,CAAL,CAIFkE,IAJE,CAIG,UAAAxC,IAAI,EAAI;MACdiC,YAAY,CAACN,6DAAD,CAAZ;MACA,OAAO3B,IAAP;IACH,CAPM,WAQI,UAAA4R,GAAG,EAAI;MACdD,eAAe,CAACC,GAAD,CAAf;MACAF,KAAK,CAAC;QACFtP,GAAG,EAAER,6FADH;QAEFU,OAAO,EAAE;UACLf,MAAM,EAANA;QADK;MAFP,CAAD,CAAL;MAMAU,YAAY,CAACN,+DAAD,CAAZ;IACH,CAjBM,CAAP;EAkBH,CA3BD;;EA4BA,OAAO;IACHmP,UAAU,EAAE9O,SAAS,KAAKL,gEADvB;IAEHlC,QAAQ,EAAEuC,SAAS,KAAKL,+DAFrB;IAGH+O,YAAY,EAAZA,YAHG;IAIHE,oBAAoB,EAApBA,oBAJG;IAKHD,KAAK,EAAE;MAAA,OAAM1O,YAAY,CAACN,6DAAD,CAAlB;IAAA;EALJ,CAAP;AAOH;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AC5CD;AACA;AACA;AACA;AACA;AACe,SAASvC,QAAT,GAAoB;EAC/B,IAAM0C,KAAK,GAAGD,uFAA6B,EAA3C;;EACA,gBAAwCJ,+CAAQ,CAAC,IAAD,CAAhD;EAAA;EAAA,IAAOiP,YAAP;EAAA,IAAqBiB,eAArB;;EACA,IAAMpP,MAAM,GAAGsP,sDAAQ,CAAC,UAACtP,MAAD,EAASmD,QAAT,EAAsB;IAC1C,OAAO5D,KAAK,CAAC;MACTM,GAAG,EAAER,gFADI;MAETU,OAAO,EAAE;QACLC,MAAM,EAANA;MADK;IAFA,CAAD,CAAL,CAMFC,IANE,CAMG,UAAA9C,KAAK,EAAI;MACfgG,QAAQ,8BACDhG,KAAK,CAACW,GAAN,CAAU,UAACL,IAAD;QAAA,OAAW;UACpB/E,KAAK,EAAE+E,IAAI,CAACtB,IADQ;UAEpBvD,KAAK,EAAE6E,IAAI,CAAC0C;QAFQ,CAAX;MAAA,CAAV,CADC,IAKJ1H,0EALI,GAAR;IAOH,CAdM,WAeI,UAAA4H,KAAK,EAAI;MAChB+O,eAAe,CAAC/O,KAAD,CAAf;IACH,CAjBM,CAAP;EAkBH,CAnBsB,EAmBpB,GAnBoB,EAmBf;IAAEkP,QAAQ,EAAE;EAAZ,CAnBe,CAAvB;EAoBA,OAAO;IACHvP,MAAM,EAANA,MADG;IAEHmO,YAAY,EAAZA,YAFG;IAGHC,KAAK,EAAE;MAAA,OAAMgB,eAAe,CAAC,IAAD,CAArB;IAAA;EAHJ,CAAP;AAKH;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;ACjCD;AACA;AACA;AACA;AACA,IAAIK,OAAJ;;AACA,SAASC,eAAT,GAA2B;EACvB,IAAI,CAACD,OAAL,EAAc;IACVA,OAAO,GAAG,IAAIE,OAAJ,CAAY,UAACC,OAAD,EAAUC,MAAV;MAAA,OAAqBL,uDAAA,CAAYjW,gEAAZ,EACtC6J,IADsC,CACjCwM,OADiC,EAEtCG,IAFsC,CAEjCF,MAFiC,CAArB;IAAA,CAAZ,CAAV;EAGH;;EACD,OAAOJ,OAAP;AACH;;AACc,SAASb,aAAT,GAAyB;EACpC,gBAA0B1P,+CAAQ,CAAC,KAAD,CAAlC;EAAA;EAAA,IAAO2P,KAAP;EAAA,IAAcmB,QAAd;;EACA7Q,gDAAS,CAAC,YAAM;IACZuQ,eAAe,GACVzP,IADL,CACU;MAAA,OAAM+P,QAAQ,CAAC,IAAD,CAAd;IAAA,CADV,WAEW,UAAA3P,KAAK;MAAA,OAAIc,mEAAA,CAAuBd,KAAvB,CAAJ;IAAA,CAFhB;EAGH,CAJQ,EAIN,EAJM,CAAT;EAKA,OAAOwO,KAAP;AACH;;;;;;;;;;;;;;;;;;;;;;;;;;;;;ACrBD;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACe,SAASuB,iBAAT,OAAmD;EAAA,IAAtBrC,YAAsB,QAAtBA,YAAsB;EAAA,IAAR1M,GAAQ,QAARA,GAAQ;;EAC9D,mBAA+EJ,8DAAW,EAA1F;EAAA,IAAwBK,QAAxB,gBAAQC,cAAR;EAAA,IAAkCnE,OAAlC,gBAAkCA,OAAlC;EAAA,IAA2CiD,KAA3C,gBAA2CA,KAA3C;EAAA,IAAkDmB,MAAlD,gBAAkDA,MAAlD;EAAA,IAA0DC,eAA1D,gBAA0DA,eAA1D;;EACA,IAAM4O,qBAAqB,GAAGF,sEAAkB,CAAC9O,GAAD,CAAhD;EACA,IAAMK,uBAAuB,GAAGR,8EAA0B,CAACG,GAAD,CAA1D;EACAlC,gDAAS,CAAC,YAAM;IACZ,IAAI,CAACkC,GAAD,IAAQC,QAAQ,CAACW,MAAT,GAAkB,CAA9B,EAAiC;MAC7B8L,YAAY,CAACzM,QAAQ,CAAC,CAAD,CAAR,CAAY1I,KAAb,CAAZ;IACH;EACJ,CAJQ,EAIN,CAAC0I,QAAD,EAAWD,GAAX,EAAgB0M,YAAhB,CAJM,CAAT;;EAKA,IAAMU,iBAAiB,GAAG,SAApBA,iBAAoB,CAACC,MAAD,EAAY;IAClCX,YAAY,CAACW,MAAM,CAAC9V,KAAR,CAAZ;EACH,CAFD;;EAGA,IAAMiJ,qBAAqB,GAAG,SAAxBA,qBAAwB,GAAM;IAChC,OAAOJ,eAAe,GACjBxB,IADE,CACG,YAAM;MACZuB,MAAM;IACT,CAHM,WAII,UAAAnB,KAAK,EAAI;MAChBc,+DAAA,CAAqB,4BAArB,EAAmD;QAC/CY,KAAK,EAAE;UAAE1B,KAAK,EAALA;QAAF;MADwC,CAAnD;IAGH,CARM,CAAP;EASH,CAVD;;EAWA,OAAQ7E,sDAAI,CAACiB,2CAAD,EAAW;IAAEd,QAAQ,EAAEyB,OAAO,GAAI5B,sDAAI,CAACgS,4DAAD,EAAe,EAAf,CAAR,GAA8BnN,KAAK,GAAI7E,sDAAI,CAACmD,4DAAD,EAAe;MAAEM,MAAM,EAAGoB,KAAK,IAAIA,KAAK,CAACpB,MAAhB,IAA2BoB,KAArC;MAA4CyM,eAAe,EAAE;QAAA,OAAMtL,MAAM,EAAZ;MAAA,CAA7D;MAA6EuL,SAAS,EAAE;QAChLC,MAAM,EAAE7U,mDAAE,CAAC,8CAAD,EAAiD,QAAjD,CADsK;QAEhL+P,OAAO,EAAE/P,mDAAE,CAAC,4DAAD,EAA+D,QAA/D,CAFqK;QAGhL8U,MAAM,EAAE9U,mDAAE,CAAC,kBAAD,EAAqB,QAArB;MAHsK;IAAxF,CAAf,CAAR,GAI5DqE,uDAAK,CAACkQ,8DAAD,EAAiB;MAAEa,OAAO,EAAE,gBAAX;MAA6BhT,UAAU,EAAEA,+DAAzC;MAAqDoB,QAAQ,EAAE,CAAC+F,uBAAuB,IAAKlG,sDAAI,CAAC+G,uDAAD,EAAiB;QAAEtD,MAAM,EAAEyC,uBAAV;QAAmCM,iBAAiB,EAAEH;MAAtD,CAAjB,CAAjC,EAAmIP,QAAQ,CAACW,MAAT,GAAkB,CAAlB,IAAwBzG,sDAAI,CAAC0U,wDAAD,EAAkB;QAAE7S,QAAQ,EAAEoR,iBAAZ;QAA+B9V,OAAO,EAAE2I,QAAxC;QAAkD1I,KAAK,EAAEyX;MAAzD,CAAlB,CAA/J;IAA/D,CAAjB;EAJC,CAAX,CAAZ;AAKH;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;ACvCD;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AACA,SAASE,WAAT,OAAgH;EAAA,IAA3ElP,GAA2E,QAAzF7C,UAAyF,CAA3E6C,GAA2E;EAAA,IAApEvC,UAAoE,QAApEA,UAAoE;EAAA,IAAxD7B,aAAwD,QAAxDA,aAAwD;EAAA,wBAAzC8B,OAAyC;EAAA,IAAzCA,OAAyC,6BAA/B,IAA+B;EAAA,uBAAzBC,MAAyB;EAAA,IAAzBA,MAAyB,4BAAhB,WAAgB;EAC5G,IAAMf,oBAAoB,GAAGrB,iFAAuB,EAApD;EACA,IAAMkR,wBAAwB,GAAG9F,kFAAwB,EAAzD;;EACA,IAAM+F,YAAY,GAAG,SAAfA,YAAe,CAAC7L,MAAD,EAAY;IAC7BjF,aAAa,CAAC;MACVoE,GAAG,EAAEa;IADK,CAAD,CAAb;EAGH,CAJD;;EAKA/C,gDAAS,CAAC,YAAM;IACZ2O,wBAAwB,CAAC;MACrBjO,GAAG,EAAER,+FADgB;MAErBU,OAAO,EAAE;QACLf,MAAM,EAANA;MADK;IAFY,CAAD,CAAxB;EAMH,CAPQ,EAON,CAACA,MAAD,CAPM,CAAT;EAQA,OAAO,CAACf,oBAAD,GAAyBzC,sDAAI,CAACgS,4DAAD,EAAe,EAAf,CAA7B,GAAoDhR,uDAAK,CAACC,2CAAD,EAAW;IAAEd,QAAQ,EAAE,CAAC,CAACmD,UAAU,IAAI,CAACuC,GAAhB,KAAyB7F,sDAAI,CAAC4U,0DAAD,EAAoB;MAAE/O,GAAG,EAAEA,GAAP;MAAY0M,YAAY,EAAEA;IAA1B,CAApB,CAA9B,EAA8FhP,OAAO,IAAIsC,GAAX,IAAkB7F,sDAAI,CAAC8U,uDAAD,EAAiB;MAAEjP,GAAG,EAAEA;IAAP,CAAjB,CAApH;EAAZ,CAAX,CAAhE;AACH;;AACc,SAASmP,qBAAT,CAA+BxS,KAA/B,EAAsC;EACjD,OAAQxC,sDAAI,CAACmB,kFAAD,EAA+B;IAAE/D,KAAK,EAAEmC,iEAAY,IAAI+B,mFAAwB,CAAC/B,iEAAD,CAAjD;IAAiEY,QAAQ,EAAEH,sDAAI,CAAC+U,WAAD,oBAAmBvS,KAAnB;EAA/E,CAA/B,CAAZ;AACH;;;;;;;;;;;;;;;;;;;;;;AC7BD;AACA;AACA;AACA;AACA;AACe,SAASkS,eAAT,OAAwD;EAAA,IAA7BvX,OAA6B,QAA7BA,OAA6B;EAAA,IAApB0E,QAAoB,QAApBA,QAAoB;EAAA,IAAVzE,KAAU,QAAVA,KAAU;EACnE,IAAM6X,cAAc,GAAG,CACnB;IACI/X,KAAK,EAAEP,mDAAE,CAAC,cAAD,EAAiB,QAAjB,CADb;IAEIQ,OAAO,EAAPA;EAFJ,CADmB,CAAvB;EAMA,OAAQ6D,uDAAK,CAACC,2CAAD,EAAW;IAAEd,QAAQ,EAAE,CAACH,sDAAI,CAACkS,8DAAD,EAAW,EAAX,CAAL,EAAqBlS,sDAAI,CAAC,GAAD,EAAM;MAAE,gBAAgB,uBAAlB;MAA2CG,QAAQ,EAAEH,sDAAI,CAAC,GAAD,EAAM;QAAEG,QAAQ,EAAExD,mDAAE,CAAC,kCAAD,EAAqC,QAArC;MAAd,CAAN;IAAzD,CAAN,CAAzB,EAAkKqD,sDAAI,CAACqP,2DAAD,EAAc;MAAEG,cAAc,EAAEyF,cAAlB;MAAkCpT,QAAQ,EAAEA,QAA5C;MAAsDyN,WAAW,EAAE3S,mDAAE,CAAC,kBAAD,EAAqB,QAArB,CAArE;MAAqGS,KAAK,EAAEA;IAA5G,CAAd,CAAtK;EAAZ,CAAX,CAAb;AACH;;;;;;;;;;;;;;;;;;;;;ACbD;AACA;AACA;AACA;AACA;AACe,SAAS2J,cAAT,OAAwD;EAAA,IAA9BtD,MAA8B,QAA9BA,MAA8B;EAAA,IAAtB+C,iBAAsB,QAAtBA,iBAAsB;EACnE,IAAMQ,cAAc,GAAGvD,MAAM,KAAKqD,qEAAlC;EACA,IAAMG,SAAS,GAAGD,cAAc,GAC1BrK,mDAAE,CAAC,gCAAD,EAAmC,QAAnC,CADwB,GAE1BA,mDAAE,CAAC,2BAAD,EAA8B,QAA9B,CAFR;EAGA,IAAMuK,YAAY,GAAGF,cAAc,GAC7BrK,mDAAE,CAAC,gEAAD,EAAmE,QAAnE,CAD2B,GAE7BA,mDAAE,CAAC,yGAAD,EAA4G,QAA5G,CAFR;EAGA,OAAQqD,sDAAI,CAACkV,6DAAD,EAAU;IAAEjO,SAAS,EAAEA,SAAb;IAAwBC,YAAY,EAAEA,YAAtC;IAAoD/G,QAAQ,EAAE6G,cAAc,IAAKhH,sDAAI,CAACgR,8DAAD,EAAW;MAAEmE,GAAG,EAAE,UAAP;MAAmBhO,EAAE,EAAE,2BAAvB;MAAoDC,OAAO,EAAEZ,iBAA7D;MAAgFrG,QAAQ,EAAExD,mDAAE,CAAC,kBAAD,EAAqB,QAArB;IAA5F,CAAX;EAArF,CAAV,CAAZ;AACH;;;;;;;;;;;;;;;;;;;;ACdD;AACA;AACA;AACA;AACe,SAASwV,WAAT,OAA8B;EAAA,IAAPtM,GAAO,QAAPA,GAAO;EACzC,IAAMwN,KAAK,GAAG+B,oEAAiB,EAA/B;EACA,IAAM3F,OAAO,GAAG5B,6CAAM,CAAC,IAAD,CAAtB;EACAlK,gDAAS,CAAC,YAAM;IACZ,IAAI,CAAC0P,KAAL,EAAY;MACR;IACH;;IACD,IAAI5D,OAAO,CAACQ,OAAZ,EAAqB;MACjBR,OAAO,CAACQ,OAAR,CAAgBqD,SAAhB,GAA4B,EAA5B;MACA,IAAM+B,SAAS,GAAG7B,QAAQ,CAACC,aAAT,CAAuB,KAAvB,CAAlB;MACA4B,SAAS,CAACjQ,OAAV,CAAkBkQ,GAAlB,aAA2BzP,GAA3B;MACAwP,SAAS,CAACE,SAAV,CAAoBC,GAApB,CAAwB,2BAAxB;MACA/F,OAAO,CAACQ,OAAR,CAAgByD,WAAhB,CAA4B2B,SAA5B;MACA,IAAM9B,WAAW,GAAGC,QAAQ,CAACC,aAAT,CAAuB,QAAvB,CAApB;MACAF,WAAW,CAACD,SAAZ,GACI,sDADJ;MAEA7D,OAAO,CAACQ,OAAR,CAAgByD,WAAhB,CAA4BH,WAA5B;IACH;EACJ,CAfQ,EAeN,CAAC1N,GAAD,EAAMwN,KAAN,EAAa5D,OAAb,CAfM,CAAT;EAgBA,OAAOzP,sDAAI,CAACiB,2CAAD,EAAW;IAAEd,QAAQ,EAAE0F,GAAG,IAAI7F,sDAAI,CAACmT,+DAAD,EAAY;MAAEvC,GAAG,EAAEnB;IAAP,CAAZ;EAAvB,CAAX,CAAX;AACH;;;;;;;;;;;;;;;;ACxBM,IAAMgG,2BAA2B,GAAG,6BAApC;AACA,IAAM3O,6BAA6B,GAAG,+BAAtC;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;ACDP;AACA;AACA;AACA;AACA,IAAI4O,IAAI,GAAG,IAAX;AACe,SAASC,mBAAT,GAA+B;EAC1C,IAAM5R,KAAK,GAAGD,uFAA6B,EAA3C;;EACA,gBAAkCJ,+CAAQ,CAACE,kEAAD,CAA1C;EAAA;EAAA,IAAOK,SAAP;EAAA,IAAkBC,YAAlB;;EACA,iBAA0BR,+CAAQ,CAAC,IAAD,CAAlC;EAAA;EAAA,IAAOmB,KAAP;EAAA,IAAcV,QAAd;;EACA,IAAMyR,UAAU,GAAG,SAAbA,UAAa,GAAM;IACrB,IAAI,CAACF,IAAL,EAAW;MACPxR,YAAY,CAACN,kEAAD,CAAZ;IACH;EACJ,CAJD;;EAKA,IAAMoC,MAAM,GAAG,SAATA,MAAS,GAAM;IACjB0P,IAAI,GAAG,IAAP;IACAxR,YAAY,CAACN,kEAAD,CAAZ;IACAO,QAAQ,CAAC,IAAD,CAAR;EACH,CAJD;;EAKAR,gDAAS,CAAC,YAAM;IACZ,IAAIM,SAAS,KAAKL,kEAAd,IAAqC,CAAC8R,IAA1C,EAAgD;MAC5CxR,YAAY,CAACN,gEAAD,CAAZ;MACAG,KAAK,CAAC;QACFM,GAAG,EAAER,8FAAsC8H;MADzC,CAAD,CAAL,CAGKlH,IAHL,CAGU,UAAAC,IAAI,EAAI;QACdgR,IAAI,GAAGhR,IAAP;QACAR,YAAY,CAACN,6DAAD,CAAZ;MACH,CAND,WAOW,UAAAiQ,GAAG,EAAI;QACd1P,QAAQ,CAAC0P,GAAD,CAAR;QACA3P,YAAY,CAACN,+DAAD,CAAZ;MACH,CAVD;IAWH;EACJ,CAfQ,EAeN,CAACK,SAAD,CAfM,CAAT;EAgBA,OAAO;IAAEyR,IAAI,EAAJA,IAAF;IAAQG,aAAa,EAAE5R,SAAvB;IAAkCY,KAAK,EAALA,KAAlC;IAAyC+Q,UAAU,EAAVA,UAAzC;IAAqD5P,MAAM,EAANA;EAArD,CAAP;AACH;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;ACpCD;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AACA,SAASgQ,qBAAT,CAA+BC,OAA/B,EAAwCC,WAAxC,EAAqDC,YAArD,EAAmE;EAC/D,2CAAyBF,OAAO,CAACG,eAAjC;EAAA,IAAOC,cAAP;;EACA,IAAIlG,MAAM,GAAGxT,mDAAE,CAAC,SAAD,EAAY,QAAZ,CAAf;;EACA,IAAIuZ,WAAW,IACXG,cAAc,KAAKH,WAAW,CAAC/O,EAD/B,IAEAgP,YAAY,CAACE,cAAD,CAFhB,EAEkC;IAC9B,IAAMX,IAAI,GAAGS,YAAY,CAACE,cAAD,CAAzB;IACAlG,MAAM,gBAASuF,IAAI,CAACY,WAAL,CAAiBC,QAA1B,MAAN;EACH;;EACD,OAAOpG,MAAP;AACH;;AACD,SAASqG,iBAAT,CAA2Bd,IAA3B,EAAiC;EAC7B,OAAQA,IAAI,IACRA,IAAI,CAACe,gBADD,IAEJf,IAAI,CAACe,gBAAL,CAAsBC,gBAFlB,IAGJhB,IAAI,CAACe,gBAAL,CAAsBC,gBAAtB,CAAuCC,KAH3C;AAIH;;AACc,SAASlR,WAAT,GAAuB;EAClC,IAAM1B,KAAK,GAAGD,uFAA6B,EAA3C;;EACA,wBAAqGiS,6DAAgB,EAArH;EAAA,IAAQjQ,QAAR,qBAAQA,QAAR;EAAA,IAAkBqQ,YAAlB,qBAAkBA,YAAlB;EAAA,IAAuCS,aAAvC,qBAAgC/R,KAAhC;EAAA,IAAsDgS,iBAAtD,qBAAsDA,iBAAtD;EAAA,IAAiFC,cAAjF,qBAAyE9Q,MAAzE;;EACA,2BAAoF2P,gEAAmB,EAAvG;EAAA,IAAcO,WAAd,wBAAQR,IAAR;EAAA,IAAkCqB,SAAlC,wBAA2BlS,KAA3B;EAAA,IAA6CgR,aAA7C,wBAA6CA,aAA7C;EAAA,IAAoEmB,UAApE,wBAA4DhR,MAA5D;;EACA,IAAMA,MAAM,GAAG8P,kDAAW,CAAC,YAAM;IAC7BkB,UAAU;IACVF,cAAc;EACjB,CAHyB,EAGvB,CAACE,UAAD,EAAaF,cAAb,CAHuB,CAA1B;;EAIA,IAAM7Q,eAAe,GAAG,SAAlBA,eAAkB,GAAM;IAC1B,OAAOlC,KAAK,CAAC;MACTM,GAAG,EAAER,6FAAqC+H;IADjC,CAAD,CAAZ;EAGH,CAJD;;EAKA,OAAO;IACH7F,cAAc,EAAED,QAAQ,CAACxD,GAAT,CAAa,UAAA2U,IAAI;MAAA,OAAK;QAClC/Z,KAAK,EAAE+Z,IAAI,CAACtW,IAAL,IAAaqV,qBAAqB,CAACiB,IAAD,EAAOf,WAAP,EAAoBC,YAApB,CADP;QAElC/Y,KAAK,EAAE6Z,IAAI,CAACC;MAFsB,CAAL;IAAA,CAAjB,CADb;IAKHpR,QAAQ,EAARA,QALG;IAMHqQ,YAAY,EAAZA,YANG;IAOHD,WAAW,EAAXA,WAPG;IAQHrR,KAAK,EAAE+R,aAAa,IAAIG,SARrB;IASHnV,OAAO,EAAEiV,iBAAiB,IAAIjT,gEAArB,IACLiS,aAAa,KAAKjS,gEAVnB;IAWHoC,MAAM,EAANA,MAXG;IAYHC,eAAe,EAAfA;EAZG,CAAP;AAcH;AACM,SAAS0O,kBAAT,CAA4B9O,GAA5B,EAAiC;EACpC,mBAAqCJ,WAAW,EAAhD;EAAA,IAAwBK,QAAxB,gBAAQC,cAAR;;EACA,IAAMmN,MAAM,GAAGpN,QAAQ,CAAC9D,IAAT,CAAc;IAAA,IAAG5E,KAAH,QAAGA,KAAH;IAAA,OAAeA,KAAK,KAAKyI,GAAzB;EAAA,CAAd,CAAf;EACA,OAAOqN,MAAP;AACH;AACM,SAASxN,0BAAT,CAAoCG,GAApC,EAAyC;EAC5C,oBAAgDJ,WAAW,EAA3D;EAAA,IAAQK,QAAR,iBAAQA,QAAR;EAAA,IAAkBqQ,YAAlB,iBAAkBA,YAAlB;EAAA,IAAgCD,WAAhC,iBAAgCA,WAAhC;;EACA,IAAMD,OAAO,GAAGnQ,QAAQ,CAAC9D,IAAT,CAAc,UAAAiV,IAAI;IAAA,OAAIA,IAAI,CAACC,IAAL,KAAcrR,GAAlB;EAAA,CAAlB,CAAhB;EACA,IAAMsR,oBAAoB,GAAGhB,YAAY,CAACiB,MAAb,CAAoB,UAACC,CAAD,EAAIC,CAAJ;IAAA,uCAAgBD,CAAhB,2BAAoBC,CAAC,CAACnQ,EAAtB,EAA2BmQ,CAA3B;EAAA,CAApB,EAAqD,EAArD,CAA7B;;EACA,IAAI,CAACrB,OAAL,EAAc;IACV,OAAO,IAAP;EACH,CAFD,MAGK;IACD,IAAQG,eAAR,GAA4BH,OAA5B,CAAQG,eAAR;;IACA,IAAIF,WAAW,IACXE,eAAe,CAACmB,QAAhB,CAAyBrB,WAAW,CAAC/O,EAArC,CADA,IAEA,CAACqP,iBAAiB,CAACN,WAAD,CAFtB,EAEqC;MACjC,OAAOpP,qEAAP;IACH,CAJD,MAKK,IAAIsP,eAAe,CACnB9T,GADI,CACA,UAAA6E,EAAE;MAAA,OAAIgQ,oBAAoB,CAAChQ,EAAD,CAAxB;IAAA,CADF,EAEJqQ,IAFI,CAEC,UAAC9B,IAAD;MAAA,OAAU,CAACc,iBAAiB,CAACd,IAAD,CAA5B;IAAA,CAFD,CAAJ,EAE0C;MAC3C,OAAOD,mEAAP;IACH,CAJI,MAKA;MACD,OAAO,IAAP;IACH;EACJ;AACJ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;ACjFD;AACA;AACA;AACA;AACA,IAAI3P,QAAQ,GAAG,EAAf;AACA,IAAIqQ,YAAY,GAAG,EAAnB;AACe,SAASJ,gBAAT,GAA4B;EACvC,IAAMhS,KAAK,GAAGD,uFAA6B,EAA3C;;EACA,gBAAkCJ,+CAAQ,CAACE,kEAAD,CAA1C;EAAA;EAAA,IAAOK,SAAP;EAAA,IAAkBC,YAAlB;;EACA,iBAA0BR,+CAAQ,CAAC,IAAD,CAAlC;EAAA;EAAA,IAAOmB,KAAP;EAAA,IAAcV,QAAd;;EACA,IAAM6B,MAAM,GAAG,SAATA,MAAS,GAAM;IACjBF,QAAQ,GAAG,EAAX;IACA3B,QAAQ,CAAC,IAAD,CAAR;IACAD,YAAY,CAACN,kEAAD,CAAZ;EACH,CAJD;;EAKAD,gDAAS,CAAC,YAAM;IACZ,IAAIM,SAAS,KAAKL,kEAAd,IAAqCkC,QAAQ,CAACW,MAAT,KAAoB,CAA7D,EAAgE;MAC5DvC,YAAY,CAACN,gEAAD,CAAZ;MACAG,KAAK,CAAC;QACFM,GAAG,EAAER,2FAAmC4H;MADtC,CAAD,CAAL,CAGKhH,IAHL,CAGU,UAAAC,IAAI,EAAI;QACdR,YAAY,CAACN,+DAAD,CAAZ;QACAkC,QAAQ,GAAGpB,IAAI,IAAIA,IAAI,CAAC+S,YAAxB;QACAtB,YAAY,GAAGzR,IAAI,IAAIA,IAAI,CAACyR,YAA5B;MACH,CAPD,WAQW,UAAArF,CAAC,EAAI;QACZ3M,QAAQ,CAAC2M,CAAD,CAAR;QACA5M,YAAY,CAACN,+DAAD,CAAZ;MACH,CAXD;IAYH;EACJ,CAhBQ,EAgBN,CAACK,SAAD,CAhBM,CAAT;EAiBA,OAAO;IACH6B,QAAQ,EAARA,QADG;IAEHqQ,YAAY,EAAZA,YAFG;IAGHU,iBAAiB,EAAE5S,SAHhB;IAIHY,KAAK,EAALA,KAJG;IAKHmB,MAAM,EAANA;EALG,CAAP;AAOH;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;ACvCD;AACA;AACA;AACA;AACA,IAAIiO,OAAJ;;AACA,SAASyD,kBAAT,GAA8B;EAC1B,IAAI,CAACzD,OAAL,EAAc;IACVA,OAAO,GAAG,IAAIE,OAAJ,CAAY,UAACC,OAAD,EAAUC,MAAV;MAAA,OAAqBL,uDAAA,CAAYhW,mEAAZ,EACtC4J,IADsC,CACjCwM,OADiC,EAEtCG,IAFsC,CAEjCF,MAFiC,CAArB;IAAA,CAAZ,CAAV;EAGH;;EACD,OAAOJ,OAAP;AACH;;AACc,SAASmB,iBAAT,GAA6B;EACxC,gBAA0B1R,+CAAQ,CAAC,KAAD,CAAlC;EAAA;EAAA,IAAO2P,KAAP;EAAA,IAAcmB,QAAd;;EACA7Q,gDAAS,CAAC,YAAM;IACZ+T,kBAAkB,GACbjT,IADL,CACU;MAAA,OAAM+P,QAAQ,CAAC,IAAD,CAAd;IAAA,CADV,WAEW,UAAA3P,KAAK;MAAA,OAAIc,mEAAA,CAAuBd,KAAvB,CAAJ;IAAA,CAFhB;EAGH,CAJQ,EAIN,EAJM,CAAT;EAKA,OAAOwO,KAAP;AACH;;;;;;;;;;;;;;;;;ACrBD;AACA;AAEA,IAAMsE,cAAc,gBAAGlX,sDAAM,OAANA,CAAM;EAAAE;EAAA;EAAAC;AAAA,CAANH,CAAvB;AAmBA,IAAMmX,KAAK,gBAAGnX,sDAAM,KAANA,CAAM;EAAAE;EAAA;EAAAC;AAAA,CAANH,CAAd;AAUA,IAAMoX,OAAO,gBAAGpX,sDAAM,KAANA,CAAM;EAAAE;EAAA;EAAAC;AAAA,CAANH,CAAhB;AAQA,IAAMqX,gBAAgB,gBAAGrX,sDAAM,OAANA,CAAM;EAAAE;EAAA;EAAAC;AAAA,CAANH,CAAzB;AAIe,SAASyU,OAAT,OAAyD;EAAA,IAAtCjO,SAAsC,QAAtCA,SAAsC;EAAA,IAA3BC,YAA2B,QAA3BA,YAA2B;EAAA,IAAb/G,QAAa,QAAbA,QAAa;EACpE,OAAQa,uDAAK,CAAC2W,cAAD,EAAiB;IAAExX,QAAQ,EAAE,CAACa,uDAAK,CAAC8W,gBAAD,EAAmB;MAAE3X,QAAQ,EAAE,CAACH,sDAAI,CAAC4X,KAAD,EAAQ;QAAEzX,QAAQ,EAAE8G;MAAZ,CAAR,CAAL,EAAuCjH,sDAAI,CAAC6X,OAAD,EAAU;QAAE1X,QAAQ,EAAE+G;MAAZ,CAAV,CAA3C;IAAZ,CAAnB,CAAN,EAA2H/G,QAA3H;EAAZ,CAAjB,CAAb;AACJ;;;;;;;;;;;;;;;;;;;AC9CA;AACA;;AAAkD,YAAhC,sBAAgC6N,KAAhC;EAAA,OAGIxL,eAAK;IAAA,OAAKA,KAAK,CAAC2S,GAAN3S,KAAc,UAAdA,GAA2BuV,8CAA3BvV,GAAuCwV,0CAA5C;EAAA,CAHT;AAAA,CAAgC;;AAClD,8EAAevX,sDAAM,UAANA,CAAM;EAAAE;EAAA;EAAAC;EAAAwN;IAAA,cAECJ,KAAuD,EAFxD;EAAA;AAAA,CAANvN,CAAf;;;;;;;;;;;;;;;;;;ACFA;;AAAwC,WACtB,sBADsBqR,IACtB;EAAA,OACFtP,eAAK;IAAA,OAAKA,KAAK,CAACqP,SAANrP,GAAkBA,KAAK,CAACqP,SAAxBrP,GAAoC,SAAzC;EAAA,CADH;AAAA,CADsB;;AACxC,8EAAe/B,sDAAM,OAANA,CAAM;EAAAE;EAAA;EAAAC;EAAAwN;IAAA,cACL0D,IAAwD,EADnD;EAAA;AAAA,CAANrR,CAAf;;;;;;;;;;;;;;;;;;ACDA;AACA,8EAAeA,sDAAM,OAANA,CAAM;EAAAE;EAAA;EAAAC;AAAA,CAANH,CAAf;;;;;;;;;;;;;;;;;;ACDA;AACA,8EAAeA,sDAAM,OAANA,CAAM;EAAAE;EAAA;EAAAC;AAAA,CAANH,CAAf;;;;;;;;;;;;;;;;;;;;ACDA;AACA;AACA;AACA,IAAMyX,YAAY,gBAAGzX,sDAAM,OAANA,CAAM;EAAAE;EAAA;EAAAC;AAAA,CAANH,CAArB;AAUA,IAAM0X,YAAY,gBAAG1X,sDAAM,OAANA,CAAM;EAAAE;EAAA;EAAAC;AAAA,CAANH,CAArB;;AAME,WAlBgB,sBAkBhBqR,IAlBgB;EAAA,OAqBNtP,eAAK;IAAA,OAAIA,KAAK,CAAC4V,KAAV;EAAA,CArBC;AAAA,CAkBhB;;AACF,IAAMC,MAAM,gBAAG5X,sDAAM,UAANA,CAAM;EAAAE;EAAA;EAAAC;EAAAwN;IAAA,cAET0D,IAAoB,EAFX;EAAA;AAAA,CAANrR,CAAf;;AAME,YAzBgB,sBAyBhBuN,KAzBgB;EAAA,OA4BNxL,eAAK;IAAA,OAAIA,KAAK,CAAC4V,KAAV;EAAA,CA5BC;AAAA,CAyBhB;;AACF,IAAME,cAAc,gBAAG7X,sDAAM,UAANA,CAAM;EAAAE;EAAA;EAAAC;EAAAwN;IAAA,cAEjBJ,KAAoB,EAFH;EAAA;AAAA,CAANvN,CAAvB;AA8Be,SAASS,SAAT,OAAkC;EAAA,qBAAb+Q,IAAa;EAAA,IAAbA,IAAa,0BAAN,EAAM;EAC7C,OAAQjS,sDAAI,CAACkY,YAAD,EAAe;IAAE/X,QAAQ,EAAEH,sDAAI,CAACmY,YAAD,EAAe;MAAEhY,QAAQ,EAAEa,uDAAK,CAAC,KAAD,EAAQ;QAAEuX,MAAM,EAAEtG,IAAV;QAAgBlB,KAAK,EAAEkB,IAAvB;QAA6BuG,OAAO,EAAE,WAAtC;QAAmDrY,QAAQ,EAAE,CAACH,sDAAI,CAACqY,MAAD,EAAS;UAAED,KAAK,EAAErK,mDAAT;UAAyB0K,EAAE,EAAE,IAA7B;UAAmCC,EAAE,EAAE,IAAvC;UAA6CC,CAAC,EAAE;QAAhD,CAAT,CAAL,EAAyE3Y,sDAAI,CAACsY,cAAD,EAAiB;UAAEF,KAAK,EAAEH,4CAAT;UAAkBQ,EAAE,EAAE,IAAtB;UAA4BC,EAAE,EAAE,IAAhC;UAAsCC,CAAC,EAAE;QAAzC,CAAjB,CAA7E;MAA7D,CAAR;IAAjB,CAAf;EAAhB,CAAf,CAAZ;AACJ;;;;;;;;;;;;;;;;;;;;;;;;;AC3DO,IAAMV,OAAO,GAAG,SAAhB;AACA,IAAMlK,cAAc,GAAG,SAAvB;AACA,IAAMD,aAAa,GAAG,SAAtB;AACA,IAAMkK,KAAK,GAAG,SAAd;AACA,IAAMY,IAAI,GAAG,SAAb;AACA,IAAMb,SAAS,GAAG,SAAlB;AACA,IAAMc,cAAc,GAAG,SAAvB;AACA,IAAMC,eAAe,GAAG,SAAxB;AACA,IAAMC,QAAQ,GAAG,SAAjB;;;;;;;;;;;;;;;ACRP,IAAMnW,gBAAgB,GAAG;EACrBC,SAAS,EAAE,WADU;EAErBC,YAAY,EAAE;AAFO,CAAzB;AAIA,iEAAeF,gBAAf;;;;;;;;;;;;;;;ACJA,IAAMgB,SAAS,GAAG;EACdI,SAAS,EAAE,WADG;EAEde,OAAO,EAAE,SAFK;EAGdH,MAAM,EAAE,QAHM;EAIdwL,IAAI,EAAE,MAJQ;EAKdtL,MAAM,EAAE;AALM,CAAlB;AAOA,iEAAelB,SAAf;;;;;;;;;;;;;;;;;;;ACPA;AACA;AACO,SAASoV,OAAT,CAAiBC,MAAjB,EAAyB;EAC5BpM,0DAAc;EACdlH,0DAAA,CAAcsT,MAAd;AACH;AACM,SAASE,cAAT,CAAwBF,MAAxB,EAAgC;EACnC,SAASG,IAAT,GAAgB;IACZpF,6CAAC,CAACiF,MAAD,CAAD;EACH;;EACDD,OAAO,CAACI,IAAD,CAAP;AACH;;;;;;;;;;;;;;;;;;ACXD;AACA;AACO,SAASC,iBAAT,CAA2BJ,MAA3B,EAAmC;EACtC,SAASG,IAAT,GAAgB;IACZ,IAAIE,KAAK,CAACC,OAAN,CAAcN,MAAd,CAAJ,EAA2B;MACvBA,MAAM,CAACO,OAAP,CAAe,UAAA7R,QAAQ;QAAA,OAAIA,QAAQ,EAAZ;MAAA,CAAvB;IACH,CAFD,MAGK;MACDsR,MAAM;IACT;EACJ;;EACDD,kDAAO,CAACI,IAAD,CAAP;AACH;AACM,IAAM9X,wBAAwB,GAAG,SAA3BA,wBAA2B,CAAC/B,YAAD,EAAkB;EACtD,IAAIjC,MAAM,CAACmc,mBAAX,EAAgC;IAC5B,OAAOnc,MAAM,CAACmc,mBAAd;EACH;;EACD,cAAwDnc,MAAxD;EAAA,IAAQoc,qBAAR,WAAQA,qBAAR;EAAA,IAA+BC,oBAA/B,WAA+BA,oBAA/B;EACA,IAAMxc,OAAO,GAAG,IAAIwc,oBAAJ,GACXC,SADW,CACDhb,2DADC,EAEXib,WAFW,CAECjc,6DAFD,EAGXkc,eAHW,CAGKva,YAHL,CAAhB;EAIA,IAAMwa,QAAQ,GAAG,IAAIL,qBAAJ,CAA0B,yBAA1B,EAAqDva,6DAArD,EAA+DhB,mEAA/D,EAA+E,YAAM,CAAG,CAAxF,EAA0F4R,UAA1F,CAAqG5S,OAArG,CAAjB;EACA4c,QAAQ,CAACC,QAAT,CAAkBxG,QAAQ,CAACyG,IAA3B,EAAiC,KAAjC;EACAF,QAAQ,CAACG,mBAAT,GAXsD,CAWtB;;EAChC5c,MAAM,CAACmc,mBAAP,GAA6BM,QAA7B;EACA,OAAOzc,MAAM,CAACmc,mBAAd;AACH,CAdM;;;;;;;;;;ACbP,WAAW,mBAAO,CAAC,+CAAS;;AAE5B;AACA;;AAEA;;;;;;;;;;;ACLA,aAAa,mBAAO,CAAC,mDAAW;AAChC,gBAAgB,mBAAO,CAAC,yDAAc;AACtC,qBAAqB,mBAAO,CAAC,mEAAmB;;AAEhD;AACA;AACA;;AAEA;AACA;;AAEA;AACA;AACA;AACA;AACA,WAAW,GAAG;AACd,aAAa,QAAQ;AACrB;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;;;;;;;;;;;AC3BA,sBAAsB,mBAAO,CAAC,qEAAoB;;AAElD;AACA;;AAEA;AACA;AACA;AACA;AACA,WAAW,QAAQ;AACnB,aAAa,QAAQ;AACrB;AACA;AACA;AACA;AACA;AACA;;AAEA;;;;;;;;;;;AClBA;AACA,wBAAwB,qBAAM,gBAAgB,qBAAM,IAAI,qBAAM,sBAAsB,qBAAM;;AAE1F;;;;;;;;;;;ACHA,aAAa,mBAAO,CAAC,mDAAW;;AAEhC;AACA;;AAEA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;;AAEA;AACA;AACA;AACA;AACA,WAAW,GAAG;AACd,aAAa,QAAQ;AACrB;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA,IAAI;;AAEJ;AACA;AACA;AACA;AACA,MAAM;AACN;AACA;AACA;AACA;AACA;;AAEA;;;;;;;;;;;AC7CA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA,WAAW,GAAG;AACd,aAAa,QAAQ;AACrB;AACA;AACA;AACA;;AAEA;;;;;;;;;;;ACrBA,iBAAiB,mBAAO,CAAC,2DAAe;;AAExC;AACA;;AAEA;AACA;;AAEA;;;;;;;;;;;ACRA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA,WAAW,QAAQ;AACnB,aAAa,QAAQ;AACrB;AACA;AACA;;AAEA;AACA;AACA;;AAEA;;;;;;;;;;;AClBA,eAAe,mBAAO,CAAC,qDAAY;AACnC,UAAU,mBAAO,CAAC,2CAAO;AACzB,eAAe,mBAAO,CAAC,qDAAY;;AAEnC;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,WAAW,UAAU;AACrB,WAAW,QAAQ;AACnB,WAAW,QAAQ,WAAW;AAC9B,WAAW,SAAS;AACpB;AACA,WAAW,QAAQ;AACnB;AACA,WAAW,SAAS;AACpB;AACA,aAAa,UAAU;AACvB;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,IAAI;AACJ;AACA;AACA,+CAA+C,iBAAiB;AAChE;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;;;;;;;;;;;AC9LA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,WAAW,GAAG;AACd,aAAa,SAAS;AACtB;AACA;AACA,gBAAgB;AAChB;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;;;;;;;;;;;AC9BA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,WAAW,GAAG;AACd,aAAa,SAAS;AACtB;AACA;AACA,oBAAoB;AACpB;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;;;;;;;;;;;AC5BA,iBAAiB,mBAAO,CAAC,2DAAe;AACxC,mBAAmB,mBAAO,CAAC,6DAAgB;;AAE3C;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,WAAW,GAAG;AACd,aAAa,SAAS;AACtB;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;;;;;;;;;;;AC5BA,WAAW,mBAAO,CAAC,+CAAS;;AAE5B;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,aAAa,QAAQ;AACrB;AACA;AACA;AACA;AACA,IAAI;AACJ;AACA;AACA;AACA;AACA;;AAEA;;;;;;;;;;;ACtBA,eAAe,mBAAO,CAAC,uDAAa;AACpC,eAAe,mBAAO,CAAC,qDAAY;AACnC,eAAe,mBAAO,CAAC,qDAAY;;AAEnC;AACA;;AAEA;AACA;;AAEA;AACA;;AAEA;AACA;;AAEA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,WAAW,GAAG;AACd,aAAa,QAAQ;AACrB;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;;;;;;;;;;;;;AC/DA;;;;;;;;;;;;;ACAA;;;;;;;;;;;;;ACAA;;;;;;;;;;;;;ACAA;;;;;;;;;;;;;ACAA;;;;;;;;;;;;;ACAA;;;;;;;;;;;;;ACAA;;;;;;;;;;;;;ACAA;;;;;;;;;;;;;ACAA;;;;;;;;;;;;;ACAA;;;;;;;;;;;;ACAA;AACA;AACA;AACA;AACA;;AAEa;AACb;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;;AAEA;AACA,kCAAkC;AAClC;AACA;AACA;AACA;;AAEA;AACA;AACA,kBAAkB,QAAQ;AAC1B;AACA;AACA;AACA;AACA,GAAG;AACH;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA,GAAG;AACH,kCAAkC;AAClC;AACA;AACA;;AAEA;AACA,GAAG;AACH;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;;AAEA,iBAAiB,sBAAsB;AACvC;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA,mBAAmB,oBAAoB;AACvC;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;;;;;;;;;;;ACzFA;AACA;AACA;AACA;AACA;AACA;;AAEA;;;;;;;;;;;ACPA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;;AAEA;AACA;;AAEA;AACA,gBAAgB,+CAA+C;;AAE/D;AACA;AACA;AACA;AACA;AACA;AACA;AACA,MAAM;AACN;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;;;;;;;;;;;ACtCA;;AAEA,eAAe,mBAAO,CAAC,wFAA6B;AACpD,gBAAgB,mBAAO,CAAC,gHAAyC;AACjE,uBAAuB,mBAAO,CAAC,iEAAe;;AAE9C,YAAY,mBAAO,CAAC,qDAAS;AAC7B;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA,wBAAwB,2FAA+B;;AAEvD;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA,aAAa,qBAAM,mBAAmB,qBAAM;AAC5C;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA,UAAU;AACV;;AAEA;AACA;AACA;AACA;AACA;AACA;;AAEA;;AAEA;;AAEA;AACA;AACA;AACA,eAAe,QAAQ;AACvB,eAAe,QAAQ;AACvB,gBAAgB;AAChB;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA,UAAU;AACV;AACA;AACA,OAAO;AACP;;AAEA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,OAAO;;AAEP;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA,UAAU;AACV;AACA,MAAM;AACN;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA,UAAU;AACV;AACA,MAAM;AACN;AACA;AACA;;AAEA;;AAEA;AACA;AACA,GAAG;;AAEH;AACA;AACA;AACA;AACA;AACA;AACA,gBAAgB;AAChB;AACA;AACA;AACA;AACA;AACA;AACA,OAAO;AACP;AACA;AACA;;AAEA;;AAEA;AACA;;AAEA;AACA;;AAEA;AACA;AACA,GAAG;;AAEH;AACA;AACA;AACA,eAAe,QAAQ;AACvB;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;;AAEA;AACA;;AAEA;AACA;AACA;AACA,GAAG;;AAEH;AACA;AACA;AACA;AACA,eAAe,QAAQ;AACvB,eAAe,UAAU;AACzB,eAAe,OAAO;AACtB;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA,GAAG;;AAEH;AACA;AACA;AACA,eAAe,QAAQ;AACvB,eAAe,UAAU;AACzB,eAAe,UAAU;AACzB,gBAAgB,UAAU;AAC1B;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA,MAAM;AACN;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA,QAAQ;AACR;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA,GAAG;;AAEH;AACA;AACA;AACA,gBAAgB;AAChB;AACA;AACA;;AAEA;;AAEA;AACA;;AAEA;AACA,GAAG;;AAEH;AACA;AACA;AACA,eAAe,OAAO;AACtB,eAAe,QAAQ;AACvB,gBAAgB;AAChB;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,WAAW;AACX;AACA;AACA;AACA;;AAEA;AACA;;AAEA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,MAAM;AACN;AACA;AACA;AACA;;AAEA;AACA,GAAG;;AAEH;AACA;AACA;AACA,eAAe,QAAQ;AACvB,eAAe,QAAQ;AACvB,gBAAgB;AAChB;AACA;AACA;AACA,mBAAmB;AACnB;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;;AAEA;AACA;AACA;AACA,OAAO;AACP;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,MAAM;AACN;AACA;;AAEA;AACA;AACA;;AAEA;AACA;;AAEA;;AAEA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,SAAS;AACT;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;;AAEA;AACA,GAAG;;AAEH;AACA;AACA;AACA;AACA,OAAO;AACP;AACA;;AAEA;AACA;;AAEA;AACA;AACA,QAAQ;AACR;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA,GAAG;;AAEH;AACA;;AAEA;AACA;AACA;AACA;;AAEA;AACA,GAAG;;AAEH;AACA;AACA;AACA,eAAe,QAAQ;AACvB,gBAAgB;AAChB;AACA;AACA;AACA;;AAEA;AACA,GAAG;;AAEH;AACA;AACA;AACA,eAAe,QAAQ;AACvB,gBAAgB;AAChB;AACA;AACA;;AAEA;AACA,GAAG;;AAEH;AACA;AACA;AACA,eAAe,QAAQ;AACvB,gBAAgB;AAChB;AACA;AACA;;AAEA;AACA,GAAG;;AAEH;AACA;AACA;AACA,gBAAgB;AAChB;AACA;AACA;;AAEA;AACA,GAAG;;AAEH;AACA;AACA;AACA,gBAAgB,QAAQ;AACxB;AACA;AACA;AACA;AACA,GAAG;;AAEH;AACA;AACA;AACA,eAAe,QAAQ;AACvB,gBAAgB;AAChB;AACA;AACA;;AAEA;AACA,GAAG;;AAEH;AACA;AACA;AACA,eAAe,QAAQ;AACvB,gBAAgB;AAChB;AACA;AACA;;AAEA;AACA,GAAG;;AAEH;AACA;AACA;AACA,eAAe,UAAU;AACzB;AACA,gBAAgB;AAChB;AACA;AACA;AACA;AACA;AACA,GAAG;;AAEH;AACA;AACA;AACA,eAAe,UAAU;AACzB;AACA,gBAAgB;AAChB;AACA;AACA;AACA;AACA;AACA,GAAG;;AAEH;AACA;AACA;AACA,eAAe,UAAU;AACzB;AACA,gBAAgB;AAChB;AACA;AACA;AACA;AACA;AACA,GAAG;;AAEH;AACA;AACA;AACA;AACA,eAAe,UAAU;AACzB;AACA;AACA,gBAAgB;AAChB;AACA;AACA;;AAEA;AACA,GAAG;;AAEH;AACA;AACA;AACA,gBAAgB;AAChB;AACA;AACA;AACA,GAAG;;AAEH;AACA;AACA;AACA,gBAAgB;AAChB;AACA;AACA;AACA,GAAG;;AAEH;AACA;AACA;AACA,gBAAgB;AAChB;AACA;AACA,sCAAsC;AACtC;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,GAAG;;AAEH;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA,GAAG;;AAEH;AACA;AACA;AACA;AACA;;AAEA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;;AAEA;AACA;AACA;AACA;AACA,GAAG;;AAEH;AACA;AACA;AACA;AACA;AACA;AACA;AACA,KAAK;AACL,GAAG;;AAEH;AACA;AACA;;AAEA;;AAEA;;AAEA;;AAEA;AACA;AACA;AACA,MAAM;AACN;AACA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA,MAAM;AACN;AACA;AACA;AACA;AACA,QAAQ;AACR;AACA;AACA;AACA,GAAG;;AAEH;AACA;AACA;AACA,iBAAiB;AACjB;AACA;AACA;AACA;AACA;AACA,iCAAiC;AACjC;AACA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,QAAQ;AACR;AACA;;AAEA;AACA;AACA;AACA,OAAO;AACP;AACA,GAAG;;AAEH;AACA;AACA,iBAAiB;AACjB;AACA;AACA;AACA;AACA,+BAA+B;;AAE/B;AACA;AACA;AACA;AACA;AACA;AACA;AACA,QAAQ;AACR;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,OAAO;AACP;AACA,GAAG;;AAEH;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA,KAAK;AACL,GAAG;;AAEH;AACA;AACA;AACA;AACA;AACA;;AAEA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA,wBAAwB,iBAAiB;AACzC;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA,UAAU;AACV;AACA;AACA;AACA;;AAEA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,gBAAgB;AAChB;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA,oBAAoB;AACpB;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,WAAW;AACX;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,gBAAgB;AAChB;AACA;AACA;AACA;AACA,WAAW;AACX;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,SAAS;AACT;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,oBAAoB,yBAAyB;AAC7C;AACA;AACA,GAAG;;AAEH;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;;AAEA;AACA;AACA;AACA;AACA,SAAS,GAAG;AACZ;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA,SAAS;AACT;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA,kBAAkB;AAClB;AACA;;AAEA;AACA;AACA;AACA;AACA,iBAAiB;AACjB;AACA;;AAEA;AACA,4BAA4B,kBAAkB;AAC9C;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA,kBAAkB;AAClB;AACA,cAAc;AACd;AACA;AACA;AACA;;AAEA;AACA;AACA,SAAS;AACT;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,4BAA4B,iBAAiB;AAC7C;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA,cAAc;AACd;AACA;AACA;AACA;AACA,cAAc;AACd;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA,aAAa;;AAEb;AACA;;AAEA;AACA,aAAa;AACb;AACA,SAAS;AACT;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA,QAAQ;AACR;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;AACA,+CAA+C;AAC/C;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,SAAS;AACT;;AAEA;AACA;AACA,OAAO;AACP;AACA,GAAG;;AAEH;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA,GAAG;;AAEH;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA,KAAK;AACL,GAAG;;AAEH;AACA;AACA,cAAc;AACd;;AAEA;AACA;AACA,MAAM;AACN;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA,GAAG;;AAEH;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA,GAAG;;AAEH;AACA;AACA;AACA;AACA;AACA,GAAG;;AAEH;AACA;;AAEA;AACA;AACA;AACA,KAAK;;AAEL;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,GAAG;;AAEH;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,OAAO;;AAEP;AACA;AACA,wBAAwB,iDAAiD;AACzE;AACA;AACA;AACA;AACA;AACA;AACA,GAAG;;AAEH;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA,0CAA0C;AAC1C;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA,GAAG;;AAEH;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;;AAEA;AACA;AACA;AACA;AACA;AACA,oBAAoB;AACpB,MAAM;AACN;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,SAAS;AACT;AACA,OAAO;AACP;AACA;;AAEA;AACA;AACA,GAAG;;AAEH;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;;AAEA;AACA,GAAG;;AAEH;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA,oBAAoB,+BAA+B;AACnD;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA,2BAA2B;AAC3B,sBAAsB,qBAAqB;AAC3C;AACA;AACA;AACA;AACA;AACA;AACA;AACA,GAAG;;AAEH;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA,GAAG;;AAEH;AACA;AACA;AACA,GAAG;;AAEH;AACA;AACA,GAAG;;AAEH;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA,MAAM;AACN;AACA;AACA;;AAEA;AACA,GAAG;;AAEH;AACA;AACA;AACA;AACA;;AAEA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA,0CAA0C;AAC1C,MAAM;AACN;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA,GAAG;;AAEH;AACA;;AAEA;AACA;AACA;AACA;AACA,OAAO;AACP;;AAEA;AACA;AACA;;AAEA;AACA;;AAEA;;AAEA;AACA,0CAA0C;AAC1C,2CAA2C;;AAE3C;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;;AAEA;AACA;;AAEA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA,MAAM;AACN;AACA;AACA,GAAG;;AAEH;AACA;AACA,GAAG;;AAEH;AACA;AACA;;AAEA;;AAEA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;;AAEA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,KAAK;;AAEL;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA,SAAS;AACT;AACA,OAAO;AACP;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;AACA,SAAS;AACT;AACA;AACA;AACA,KAAK;AACL,GAAG;;AAEH;AACA;AACA;;AAEA;AACA;;AAEA;;AAEA;;AAEA;AACA;AACA;AACA;AACA,UAAU;AACV;AACA,UAAU;AACV;AACA;AACA;AACA;AACA;AACA,MAAM;AACN;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA,GAAG;;AAEH;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,GAAG;;AAEH;AACA;AACA;AACA,MAAM;AACN,2EAA2E;AAC3E;AACA;AACA;;AAEA;AACA;AACA;;AAEA;;;;;;;;;;;ACr4DA;AACA;AACA;AACA;AACA;;AAEA,uBAAuB,mBAAO,CAAC,qDAAS;;AAExC;AACA;AACA;AACA;AACA,aAAa,qBAAM,mBAAmB,qBAAM;AAC5C;;AAEA;;AAEA;AACA;AACA;AACA;AACA,YAAY;AACZ;AACA;AACA;AACA;AACA;;AAEA;;AAEA;;;;;;;;;;;AC9BA;AACA;AACA;AACA,aAAa,qBAAM,mBAAmB,qBAAM;;AAE5C;AACA;AACA;;AAEA;AACA;AACA;AACA,YAAY;AACZ;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA,mCAAmC;AACnC;;AAEA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA,oCAAoC;AACpC;AACA;;AAEA;AACA;AACA,wBAAwB;AACxB;AACA,IAAI;AACJ;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;;AAEA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA,IAAI;AACJ;AACA;AACA,kBAAkB,OAAO;AACzB;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA,GAAG;AACH;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA,WAAW,QAAQ;AACnB,WAAW,QAAQ;AACnB;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA,SAAS,SAAS;AAClB;AACA;AACA;AACA;AACA,iDAAiD;AACjD,MAAM;AACN;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA,GAAG;AACH;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,IAAI;AACJ;AACA;AACA;AACA;AACA;AACA,KAAK;AACL;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA,aAAa;AACb;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;;AAEA;AACA;AACA;;AAEA;AACA;;AAEA;AACA;AACA;AACA;AACA,aAAa;AACb;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA,gBAAgB,oBAAoB;AACpC;AACA;AACA;AACA;AACA,cAAc,0BAA0B;AACxC;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA;;AAEA;;AAEA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA;;AAEA;AACA;;AAEA,kCAAkC;AAClC;AACA,kBAAkB,oBAAoB;AACtC;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA,iBAAiB,UAAU;AAC3B;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;;;;;;;;;;AChYA,YAAY,mBAAO,CAAC,6DAAiB;;AAErC;AACA;;AAEA;AACA;AACA;;AAEA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA,aAAa,qBAAM,mBAAmB,qBAAM;;AAE5C;AACA;AACA;;AAEA;AACA;;AAEA;AACA;;AAEA;AACA;;AAEA;AACA;AACA;AACA;AACA,qDAAqD,KAAK;AAC1D,uDAAuD,KAAK;AAC5D;AACA,WAAW,aAAa,YAAY;AACpC;AACA;AACA;AACA,8BAA8B;AAC9B;AACA;AACA,+DAA+D;AAC/D;AACA,+DAA+D;AAC/D;AACA;AACA;AACA;AACA;AACA,oCAAoC;AACpC;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA,eAAe,UAAU;AACzB;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA,eAAe,UAAU;AACzB;AACA;AACA,sCAAsC,QAAQ;AAC9C;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA,eAAe,oBAAoB;AACnC;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,UAAU;AACV;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;;AAEA;AACA;AACA;AACA,eAAe,QAAQ;AACvB,eAAe,QAAQ;AACvB,eAAe,iBAAiB;AAChC;AACA,eAAe,kBAAkB;AACjC;AACA,eAAe,QAAQ;AACvB;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,MAAM;AACN,8BAA8B;;AAE9B;AACA;AACA;AACA;AACA;AACA,MAAM;AACN;AACA;AACA;AACA;AACA;;AAEA;AACA,yBAAyB;AACzB;AACA,YAAY;AACZ;AACA;AACA;AACA;AACA;AACA;;AAEA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA,eAAe,OAAO;AACtB,eAAe,UAAU;AACzB;AACA;AACA;AACA;AACA;AACA;AACA;AACA,gBAAgB;AAChB,QAAQ;AACR;AACA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;AACA,uBAAuB;AACvB;AACA;AACA;AACA;AACA;AACA,KAAK;;AAEL;AACA,gBAAgB;AAChB;AACA;;AAEA;AACA;AACA;AACA;AACA,CAAC;;AAED;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,0BAA0B;;AAE1B;AACA;AACA;AACA,eAAe,OAAO;AACtB,gBAAgB,qBAAqB;AACrC;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA,sCAAsC,OAAO;AAC7C;AACA,qEAAqE;AACrE,iEAAiE;AACjE;AACA;AACA,kCAAkC;AAClC,kCAAkC;AAClC,kCAAkC;AAClC;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,QAAQ;AACR;AACA;AACA;AACA;AACA;AACA;AACA;AACA,QAAQ;AACR;AACA;AACA;AACA;AACA;AACA,2BAA2B;AAC3B,UAAU;AACV;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,QAAQ;AACR;AACA;;AAEA;AACA;AACA;;AAEA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA,eAAe,oBAAoB;AACnC;AACA,eAAe,QAAQ;AACvB,eAAe,iBAAiB;AAChC;AACA,eAAe,SAAS;AACxB;AACA,gBAAgB,SAAS;AACzB;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;AACA,0BAA0B;AAC1B,YAAY;AACZ;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA,MAAM;AACN;AACA;;AAEA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA,QAAQ,0CAA0C;AAClD,eAAe,OAAO;AACtB,gBAAgB,qBAAqB;AACrC;AACA;AACA;AACA;AACA,gBAAgB;AAChB;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA,QAAQ;AACR;AACA;;AAEA;AACA;AACA,qEAAqE;AACrE,UAAU;AACV;;AAEA;AACA;AACA,QAAQ;AACR;AACA;;AAEA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA,eAAe,OAAO;AACtB,eAAe,kBAAkB;AACjC;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA,MAAM;AACN;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA,MAAM;AACN;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;;AAEA;AACA,CAAC;;AAED;;;;;;;;;;;AC9mBA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;;AAEA;AACA,oBAAoB;;AAEpB;AACA,kBAAkB,qBAAqB;AACvC;AACA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA,MAAM;AACN;AACA;;AAEA;AACA;AACA;AACA;AACA;;;;;;;;;;;;ACzEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEa;;AAEb,IAAI,IAAqC;AACzC;AACA;;AAEA,YAAY,mBAAO,CAAC,oBAAO;AAC3B,cAAc,mBAAO,CAAC,4DAAe;;AAErC;AACA;AACA;AACA;AACA;AACA;AACA;AACA,gBAAgB;AAChB;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA,EAAE,gBAAgB;AAClB;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;;AAEA;;AAEA;AACA;AACA;;AAEA;AACA;;AAEA;;AAEA;AACA;AACA,+FAA+F,eAAe;AAC9G;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;AACA,KAAK,GAAG;;AAER,kDAAkD;AAClD;AACA;;AAEA;AACA;AACA;;AAEA;;AAEA,4BAA4B;;AAE5B;AACA;AACA;AACA,IAAI;;;AAGJ;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;;AAEA;AACA;;AAEA;AACA;;AAEA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;;AAEA;AACA;;AAEA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA,YAAY;AACZ;AACA;AACA;AACA;AACA;;AAEA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,uCAAuC;;AAEvC;AACA;AACA;AACA;AACA;AACA,SAAS;;AAET;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,OAAO;AACP;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA,SAAS;;AAET;AACA,uBAAuB;AACvB;AACA,SAAS;AACT,wBAAwB;AACxB;AACA,SAAS;AACT,wBAAwB;AACxB;AACA,SAAS;AACT,yBAAyB;AACzB;AACA,SAAS;AACT,yBAAyB;AACzB;AACA,SAAS;AACT,kCAAkC;AAClC;AACA,SAAS;AACT,4BAA4B;AAC5B;AACA,SAAS;AACT,OAAO;AACP;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,QAAQ;AACR;AACA;AACA;AACA,MAAM;;;AAGN;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;AACA,2DAA2D;;AAE3D;AACA;;AAEA;AACA,yDAAyD;AACzD;;AAEA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA,SAAS;;;AAGT;AACA;AACA;AACA;AACA;AACA;AACA,OAAO;;AAEP;AACA;AACA;AACA;AACA;AACA,UAAU;AACV;AACA;;AAEA;AACA,QAAQ;AACR;AACA;AACA,UAAU;AACV;AACA;;AAEA;AACA;AACA,MAAM;AACN;AACA;AACA,QAAQ;AACR;AACA;;AAEA;AACA;AACA,IAAI;AACJ;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA,aAAa,kBAAkB;AAC/B;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,mBAAmB;AACnB;;AAEA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA,kBAAkB;;;AAGlB;AACA;AACA,cAAc;AACd;;AAEA;AACA;AACA;AACA;AACA,IAAI;AACJ;;AAEA;AACA;AACA;AACA;;AAEA;AACA,IAAI;;;AAGJ;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA,YAAY;AACZ;AACA;AACA;;AAEA;AACA;;AAEA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA,MAAM;AACN;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;AACA,8BAA8B;AAC9B;AACA;;AAEA;AACA;AACA;AACA;AACA,2HAA2H;AAC3H;AACA;AACA;;AAEA;AACA,UAAU;AACV;AACA;;AAEA;AACA;;AAEA,oEAAoE;;AAEpE;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;;AAEA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA,KAAK;AACL;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA,KAAK;AACL;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,WAAW,GAAG;AACd,WAAW,GAAG;AACd,WAAW,GAAG;AACd,WAAW,eAAe;AAC1B,WAAW,GAAG;AACd,WAAW,GAAG;AACd;AACA;AACA;AACA;AACA,WAAW,GAAG;AACd;AACA;AACA;;;AAGA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA,yBAAyB;AACzB;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA,KAAK,GAAG;;AAER;AACA;AACA;AACA;AACA;AACA,KAAK,GAAG;AACR;;AAEA;AACA;AACA;AACA;AACA;AACA,KAAK;;AAEL;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA,WAAW,GAAG;AACd,WAAW,QAAQ;AACnB,WAAW,QAAQ;AACnB;;AAEA;AACA;AACA,kBAAkB;;AAElB;AACA;AACA,oBAAoB;AACpB,2DAA2D,UAAU;AACrE,yBAAyB,UAAU;AACnC;AACA,aAAa,UAAU;AACvB;;AAEA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;AACA,MAAM;;;AAGN;AACA;AACA;AACA;AACA,MAAM;;;AAGN;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA,MAAM;AACN;AACA;AACA;AACA;;AAEA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA,WAAW,SAAS;AACpB,YAAY,SAAS;AACrB;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;;AAGA;;AAEA;AACA;AACA;;AAEA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,WAAW,cAAc;AACzB,WAAW,GAAG;AACd;;;AAGA;AACA;AACA;AACA;AACA;;AAEA;AACA;;AAEA;AACA;AACA;;AAEA,6DAA6D;AAC7D;AACA;;AAEA;;AAEA;AACA;AACA;AACA;;AAEA;;AAEA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,WAAW,WAAW;AACtB,WAAW,GAAG;AACd;;;AAGA;AACA;AACA;AACA;AACA;;AAEA;AACA,sBAAsB,iBAAiB;AACvC;;AAEA;AACA;AACA;AACA;AACA,MAAM;AACN;AACA;AACA;AACA;AACA,MAAM;AACN;;AAEA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,WAAW,cAAc;AACzB;;;AAGA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;;AAEA;AACA;AACA,MAAM;AACN;AACA;AACA;AACA,MAAM;AACN;AACA;;AAEA;AACA;AACA;AACA;AACA,MAAM;AACN,4CAA4C;;AAE5C;;AAEA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,WAAW,cAAc;AACzB;;;AAGA;AACA;AACA;;AAEA,oBAAoB,iBAAiB;AACrC;;AAEA;AACA;;AAEA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;;AAEA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;AACA,8CAA8C;AAC9C;;AAEA;AACA;;AAEA;AACA;AACA;;AAEA;;AAEA;AACA;AACA,QAAQ;AACR;AACA;;AAEA;;AAEA;AACA;AACA,QAAQ;AACR;AACA,QAAQ;AACR;AACA;AACA,QAAQ;AACR;AACA;;AAEA;AACA;;AAEA,0DAA0D;AAC1D;;AAEA;AACA;AACA,MAAM;AACN;AACA;AACA;AACA;;;AAGA;AACA;;AAEA;AACA;AACA;AACA,4BAA4B,qBAAqB;AACjD;AACA;;AAEA;AACA;AACA;AACA,YAAY;AACZ;AACA;AACA,UAAU;AACV;AACA;AACA;AACA;;AAEA;AACA;AACA,MAAM;AACN;AACA;;AAEA;AACA;AACA,EAAE;AACF;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA,sCAAsC;AACtC;;AAEA;;AAEA,WAAW;AACX,YAAY;AACZ,GAAG;AACH;;;;;;;;;;;;ACpsCa;;AAEb,IAAI,KAAqC,EAAE,EAE1C,CAAC;AACF,EAAE,+IAAkE;AACpE;;;;;;;;;;;;ACNA;;;;;;;;;;;ACAA;;;;;;;;;;;ACAA;;;;;;;;;;;ACAA;;;;;;;;;;;;;;;;;;ACAA;AAC+C;AACrB;AACS;AACnC;AACA;AACA;AACA;AACA;AACA;AACA,GAAG;AACH;AACA;AACA;AACA;AACA;AACA,oCAAoC,8DAAS,oBAAoB,SAAS,8DAAS,GAAG,EAAE,8DAAS;AACjG;AACA;AACA;AACA;AACA,KAAK;AACL;AACA;AACA;AACA;AACA,MAAM,IAAqC;AAC3C;AACA;AACA;AACA;AACA;AACA,wCAAwC,YAAY,sBAAsB,cAAc;AACxF;AACA;AACA;AACA;AACA;AACA,QAAQ,IAAqC;AAC7C;AACA;AACA;AACA;AACA;AACA;AACA;AACA,cAAc,wCAAwC;AACtD;AACA;AACA;AACA;AACA;AACA;AACA,iDAAiD,iDAAE,wDAAwD,iDAAE;AAC7G,cAAc,OAAO;AACrB;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,qBAAqB,KAAK,QAAQ,MAAM,EAAE,KAAK;AAC/C;AACA;AACA;AACA;AACA;AACA;AACA,WAAW;AACX;AACA;AACA;AACA;AACA;AACA,eAAe,gDAAmB;AAClC;AACA,aAAa,gDAAmB;AAChC;AACA,mBAAmB,6CAAgB,GAAG,6CAAgB;AACtD;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,qBAAqB,KAAqC;AAC1D;AACA;AACA;AACA,CAAC,IAAI,CAAM;AAGT;AACF;;;;;;;;;;;;;;;;ACpGA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,QAAQ;AACR;AACA;AACA,KAAK;AACL,GAAG;AACH;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AAIE;AACF;;;;;;UCtCA;UACA;;UAEA;UACA;UACA;UACA;UACA;UACA;UACA;UACA;UACA;UACA;UACA;UACA;UACA;;UAEA;UACA;;UAEA;UACA;UACA;;;;;WCtBA;WACA;WACA;WACA;WACA;WACA,iCAAiC,WAAW;WAC5C;WACA;;;;;WCPA;WACA;WACA;WACA;WACA,yCAAyC,wCAAwC;WACjF;WACA;WACA;;;;;WCPA;WACA;WACA;WACA;WACA,GAAG;WACH;WACA;WACA,CAAC;;;;;WCPD;;;;;WCAA;WACA;WACA;WACA,uDAAuD,iBAAiB;WACxE;WACA,gDAAgD,aAAa;WAC7D;;;;;;;;;;;;;;;;ACNA;AACA;AACA;AACA;AACA,IAAMU,wBAAwB,GAAG,GAAjC;AACA,IAAMC,gBAAgB,GAAG,KAAzB;;AACA,IAAMC,wBAAwB,GAAG,SAA3BA,wBAA2B,GAAM;EACnChB,4EAAiB,CAAC,YAAM;IACpB,IAAIiB,UAAJ;IACA,IAAIC,cAAJ;IACA,IAAMC,wBAAwB,GAAG/S,sEAAe,EAChD;IACAnK,MAAM,CAACoK,SAFyC,EAE9B;MACdqB,UAAU,EAAE,cADE;MAEdR,eAAe,EAAE,gCAFH;MAGdG,iBAAiB,EAAE;IAHL,CAF8B,EAM7C,UAACxD,gBAAD,EAAmBC,eAAnB,EAAoClC,QAApC,EAAiD;MAChDqX,UAAU,GAAG,IAAIrV,gFAAJ,CAAuBC,gBAAvB,EAAyCC,eAAzC,EAA0DlC,QAA1D,CAAb;MACAqX,UAAU,CAACpX,MAAX;IACH,CAT+C,EAS7C,YAAM;MACLoX,UAAU,CAAC1S,IAAX;IACH,CAX+C,CAAhD;IAYA,IAAM6S,2BAA2B,GAAGhT,sEAAe,EACnD;IACAnK,MAAM,CAACoK,SAF4C,EAEjC;MACdqB,UAAU,EAAE,iBADE;MAEdR,eAAe,EAAE,mCAFH;MAGdG,iBAAiB,EAAE;IAHL,CAFiC,EAMhD,UAACxD,gBAAD,EAAmBC,eAAnB,EAAoClC,QAApC,EAAiD;MAChDsX,cAAc,GAAG,IAAI/S,sFAAJ,CAA2BtC,gBAA3B,EAA6CC,eAA7C,EAA8DlC,QAA9D,CAAjB;MACAsX,cAAc,CAACrX,MAAf;IACH,CATkD,EAShD,YAAM;MACLqX,cAAc,CAAC3S,IAAf;IACH,CAXkD,CAAnD,CAfoB,CA2BpB;;IACAtK,MAAM,CAACoK,SAAP,CAAiBgT,cAAjB,CAAgC,kBAAhC,EAAoDF,wBAApD,EA5BoB,CA6BpB;;IACAld,MAAM,CAACoK,SAAP,CAAiBgT,cAAjB,CAAgC,qBAAhC,EAAuDD,2BAAvD;EACH,CA/BgB,CAAjB;AAgCH,CAjCD;;AAkCA,IAAME,qBAAqB,GAAGC,WAAW,CAAC,YAAM;EAC5C,IAAMhS,iBAAiB,GAAGtL,MAAM,CAACsL,iBAAjC;;EACA,IAAIA,iBAAJ,EAAuB;IACnByR,wBAAwB;IACxBQ,aAAa,CAACF,qBAAD,CAAb;EACH;AACJ,CANwC,EAMtCR,wBANsC,CAAzC;AAOAW,UAAU,CAAC,YAAM;EACbD,aAAa,CAACF,qBAAD,CAAb;AACH,CAFS,EAEPP,gBAFO,CAAV,C","sources":["webpack://leadin/./node_modules/@emotion/memoize/dist/emotion-memoize.esm.js","webpack://leadin/./node_modules/@linaria/react/node_modules/@emotion/is-prop-valid/dist/emotion-is-prop-valid.esm.js","webpack://leadin/./scripts/constants/defaultFormOptions.ts","webpack://leadin/./scripts/constants/leadinConfig.ts","webpack://leadin/./scripts/elementor/Common/ConnectPluginBanner.tsx","webpack://leadin/./scripts/elementor/Common/ElementorBanner.tsx","webpack://leadin/./scripts/elementor/Common/ElementorButton.tsx","webpack://leadin/./scripts/elementor/FormWidget/ElementorFormSelect.tsx","webpack://leadin/./scripts/elementor/FormWidget/FormControlController.tsx","webpack://leadin/./scripts/elementor/FormWidget/FormWidgetController.tsx","webpack://leadin/./scripts/elementor/FormWidget/hooks/useForms.ts","webpack://leadin/./scripts/elementor/FormWidget/registerFormWidget.ts","webpack://leadin/./scripts/elementor/MeetingWidget/ElementorMeetingSelect.tsx","webpack://leadin/./scripts/elementor/MeetingWidget/ElementorMeetingWarning.tsx","webpack://leadin/./scripts/elementor/MeetingWidget/MeetingControlController.tsx","webpack://leadin/./scripts/elementor/MeetingWidget/MeetingWidgetController.tsx","webpack://leadin/./scripts/elementor/MeetingWidget/registerMeetingWidget.ts","webpack://leadin/./scripts/elementor/elementorWidget.ts","webpack://leadin/./scripts/iframe/integratedMessages/core/CoreMessages.ts","webpack://leadin/./scripts/iframe/integratedMessages/forms/FormsMessages.ts","webpack://leadin/./scripts/iframe/integratedMessages/index.ts","webpack://leadin/./scripts/iframe/integratedMessages/livechat/LiveChatMessages.ts","webpack://leadin/./scripts/iframe/integratedMessages/plugin/PluginMessages.ts","webpack://leadin/./scripts/iframe/integratedMessages/proxy/ProxyMessages.ts","webpack://leadin/./scripts/iframe/useBackgroundApp.ts","webpack://leadin/./scripts/lib/Raven.ts","webpack://leadin/./scripts/shared/Common/AsyncSelect.tsx","webpack://leadin/./scripts/shared/Common/ErrorHandler.tsx","webpack://leadin/./scripts/shared/Common/HubspotWrapper.ts","webpack://leadin/./scripts/shared/Common/LoadingBlock.tsx","webpack://leadin/./scripts/shared/Form/FormEdit.tsx","webpack://leadin/./scripts/shared/Form/FormSelect.tsx","webpack://leadin/./scripts/shared/Form/FormSelector.tsx","webpack://leadin/./scripts/shared/Form/PreviewForm.tsx","webpack://leadin/./scripts/shared/Form/hooks/useCreateFormFromTemplate.ts","webpack://leadin/./scripts/shared/Form/hooks/useForms.ts","webpack://leadin/./scripts/shared/Form/hooks/useFormsScript.ts","webpack://leadin/./scripts/shared/Meeting/MeetingController.tsx","webpack://leadin/./scripts/shared/Meeting/MeetingEdit.tsx","webpack://leadin/./scripts/shared/Meeting/MeetingSelector.tsx","webpack://leadin/./scripts/shared/Meeting/MeetingWarning.tsx","webpack://leadin/./scripts/shared/Meeting/PreviewMeeting.tsx","webpack://leadin/./scripts/shared/Meeting/constants.ts","webpack://leadin/./scripts/shared/Meeting/hooks/useCurrentUserFetch.ts","webpack://leadin/./scripts/shared/Meeting/hooks/useMeetings.ts","webpack://leadin/./scripts/shared/Meeting/hooks/useMeetingsFetch.ts","webpack://leadin/./scripts/shared/Meeting/hooks/useMeetingsScript.ts","webpack://leadin/./scripts/shared/UIComponents/UIAlert.tsx","webpack://leadin/./scripts/shared/UIComponents/UIButton.ts","webpack://leadin/./scripts/shared/UIComponents/UIContainer.ts","webpack://leadin/./scripts/shared/UIComponents/UIOverlay.ts","webpack://leadin/./scripts/shared/UIComponents/UISpacer.ts","webpack://leadin/./scripts/shared/UIComponents/UISpinner.tsx","webpack://leadin/./scripts/shared/UIComponents/colors.ts","webpack://leadin/./scripts/shared/enums/connectionStatus.ts","webpack://leadin/./scripts/shared/enums/loadState.ts","webpack://leadin/./scripts/utils/appUtils.ts","webpack://leadin/./scripts/utils/backgroundAppUtils.ts","webpack://leadin/./node_modules/lodash/_Symbol.js","webpack://leadin/./node_modules/lodash/_baseGetTag.js","webpack://leadin/./node_modules/lodash/_baseTrim.js","webpack://leadin/./node_modules/lodash/_freeGlobal.js","webpack://leadin/./node_modules/lodash/_getRawTag.js","webpack://leadin/./node_modules/lodash/_objectToString.js","webpack://leadin/./node_modules/lodash/_root.js","webpack://leadin/./node_modules/lodash/_trimmedEndIndex.js","webpack://leadin/./node_modules/lodash/debounce.js","webpack://leadin/./node_modules/lodash/isObject.js","webpack://leadin/./node_modules/lodash/isObjectLike.js","webpack://leadin/./node_modules/lodash/isSymbol.js","webpack://leadin/./node_modules/lodash/now.js","webpack://leadin/./node_modules/lodash/toNumber.js","webpack://leadin/./scripts/elementor/Common/ElementorButton.tsx?a429","webpack://leadin/./scripts/elementor/MeetingWidget/ElementorMeetingWarning.tsx?284e","webpack://leadin/./scripts/shared/Common/AsyncSelect.tsx?df11","webpack://leadin/./scripts/shared/Common/HubspotWrapper.ts?a346","webpack://leadin/./scripts/shared/UIComponents/UIAlert.tsx?0f15","webpack://leadin/./scripts/shared/UIComponents/UIButton.ts?d089","webpack://leadin/./scripts/shared/UIComponents/UIContainer.ts?e576","webpack://leadin/./scripts/shared/UIComponents/UIOverlay.ts?c9f9","webpack://leadin/./scripts/shared/UIComponents/UISpacer.ts?8e1e","webpack://leadin/./scripts/shared/UIComponents/UISpinner.tsx?4a02","webpack://leadin/./node_modules/object-assign/index.js","webpack://leadin/./node_modules/raven-js/src/configError.js","webpack://leadin/./node_modules/raven-js/src/console.js","webpack://leadin/./node_modules/raven-js/src/raven.js","webpack://leadin/./node_modules/raven-js/src/singleton.js","webpack://leadin/./node_modules/raven-js/src/utils.js","webpack://leadin/./node_modules/raven-js/vendor/TraceKit/tracekit.js","webpack://leadin/./node_modules/raven-js/vendor/json-stringify-safe/stringify.js","webpack://leadin/./node_modules/react/cjs/react-jsx-runtime.development.js","webpack://leadin/./node_modules/react/jsx-runtime.js","webpack://leadin/external window \"React\"","webpack://leadin/external window \"ReactDOM\"","webpack://leadin/external window \"jQuery\"","webpack://leadin/external window [\"wp\",\"i18n\"]","webpack://leadin/./node_modules/@linaria/react/dist/index.mjs","webpack://leadin/./node_modules/@linaria/react/node_modules/@linaria/core/dist/index.mjs","webpack://leadin/webpack/bootstrap","webpack://leadin/webpack/runtime/compat get default export","webpack://leadin/webpack/runtime/define property getters","webpack://leadin/webpack/runtime/global","webpack://leadin/webpack/runtime/hasOwnProperty shorthand","webpack://leadin/webpack/runtime/make namespace object","webpack://leadin/./scripts/entries/elementor.ts"],"sourcesContent":["function memoize(fn) {\n var cache = Object.create(null);\n return function (arg) {\n if (cache[arg] === undefined) cache[arg] = fn(arg);\n return cache[arg];\n };\n}\n\nexport default memoize;\n","import memoize from '@emotion/memoize';\n\nvar reactPropsRegex = /^((children|dangerouslySetInnerHTML|key|ref|autoFocus|defaultValue|defaultChecked|innerHTML|suppressContentEditableWarning|suppressHydrationWarning|valueLink|abbr|accept|acceptCharset|accessKey|action|allow|allowUserMedia|allowPaymentRequest|allowFullScreen|allowTransparency|alt|async|autoComplete|autoPlay|capture|cellPadding|cellSpacing|challenge|charSet|checked|cite|classID|className|cols|colSpan|content|contentEditable|contextMenu|controls|controlsList|coords|crossOrigin|data|dateTime|decoding|default|defer|dir|disabled|disablePictureInPicture|download|draggable|encType|enterKeyHint|form|formAction|formEncType|formMethod|formNoValidate|formTarget|frameBorder|headers|height|hidden|high|href|hrefLang|htmlFor|httpEquiv|id|inputMode|integrity|is|keyParams|keyType|kind|label|lang|list|loading|loop|low|marginHeight|marginWidth|max|maxLength|media|mediaGroup|method|min|minLength|multiple|muted|name|nonce|noValidate|open|optimum|pattern|placeholder|playsInline|poster|preload|profile|radioGroup|readOnly|referrerPolicy|rel|required|reversed|role|rows|rowSpan|sandbox|scope|scoped|scrolling|seamless|selected|shape|size|sizes|slot|span|spellCheck|src|srcDoc|srcLang|srcSet|start|step|style|summary|tabIndex|target|title|translate|type|useMap|value|width|wmode|wrap|about|datatype|inlist|prefix|property|resource|typeof|vocab|autoCapitalize|autoCorrect|autoSave|color|incremental|fallback|inert|itemProp|itemScope|itemType|itemID|itemRef|on|option|results|security|unselectable|accentHeight|accumulate|additive|alignmentBaseline|allowReorder|alphabetic|amplitude|arabicForm|ascent|attributeName|attributeType|autoReverse|azimuth|baseFrequency|baselineShift|baseProfile|bbox|begin|bias|by|calcMode|capHeight|clip|clipPathUnits|clipPath|clipRule|colorInterpolation|colorInterpolationFilters|colorProfile|colorRendering|contentScriptType|contentStyleType|cursor|cx|cy|d|decelerate|descent|diffuseConstant|direction|display|divisor|dominantBaseline|dur|dx|dy|edgeMode|elevation|enableBackground|end|exponent|externalResourcesRequired|fill|fillOpacity|fillRule|filter|filterRes|filterUnits|floodColor|floodOpacity|focusable|fontFamily|fontSize|fontSizeAdjust|fontStretch|fontStyle|fontVariant|fontWeight|format|from|fr|fx|fy|g1|g2|glyphName|glyphOrientationHorizontal|glyphOrientationVertical|glyphRef|gradientTransform|gradientUnits|hanging|horizAdvX|horizOriginX|ideographic|imageRendering|in|in2|intercept|k|k1|k2|k3|k4|kernelMatrix|kernelUnitLength|kerning|keyPoints|keySplines|keyTimes|lengthAdjust|letterSpacing|lightingColor|limitingConeAngle|local|markerEnd|markerMid|markerStart|markerHeight|markerUnits|markerWidth|mask|maskContentUnits|maskUnits|mathematical|mode|numOctaves|offset|opacity|operator|order|orient|orientation|origin|overflow|overlinePosition|overlineThickness|panose1|paintOrder|pathLength|patternContentUnits|patternTransform|patternUnits|pointerEvents|points|pointsAtX|pointsAtY|pointsAtZ|preserveAlpha|preserveAspectRatio|primitiveUnits|r|radius|refX|refY|renderingIntent|repeatCount|repeatDur|requiredExtensions|requiredFeatures|restart|result|rotate|rx|ry|scale|seed|shapeRendering|slope|spacing|specularConstant|specularExponent|speed|spreadMethod|startOffset|stdDeviation|stemh|stemv|stitchTiles|stopColor|stopOpacity|strikethroughPosition|strikethroughThickness|string|stroke|strokeDasharray|strokeDashoffset|strokeLinecap|strokeLinejoin|strokeMiterlimit|strokeOpacity|strokeWidth|surfaceScale|systemLanguage|tableValues|targetX|targetY|textAnchor|textDecoration|textRendering|textLength|to|transform|u1|u2|underlinePosition|underlineThickness|unicode|unicodeBidi|unicodeRange|unitsPerEm|vAlphabetic|vHanging|vIdeographic|vMathematical|values|vectorEffect|version|vertAdvY|vertOriginX|vertOriginY|viewBox|viewTarget|visibility|widths|wordSpacing|writingMode|x|xHeight|x1|x2|xChannelSelector|xlinkActuate|xlinkArcrole|xlinkHref|xlinkRole|xlinkShow|xlinkTitle|xlinkType|xmlBase|xmlns|xmlnsXlink|xmlLang|xmlSpace|y|y1|y2|yChannelSelector|z|zoomAndPan|for|class|autofocus)|(([Dd][Aa][Tt][Aa]|[Aa][Rr][Ii][Aa]|x)-.*))$/; // https://esbench.com/bench/5bfee68a4cd7e6009ef61d23\n\nvar isPropValid = /* #__PURE__ */memoize(function (prop) {\n return reactPropsRegex.test(prop) || prop.charCodeAt(0) === 111\n /* o */\n && prop.charCodeAt(1) === 110\n /* n */\n && prop.charCodeAt(2) < 91;\n}\n/* Z+1 */\n);\n\nexport default isPropValid;\n","import { __ } from '@wordpress/i18n';\nconst REGISTRATION_FORM = 'REGISTRATION_FORM';\nconst CONTACT_US_FORM = 'CONTACT_US_FORM';\nconst NEWSLETTER_FORM = 'NEWSLETTER_FORM';\nconst SUPPORT_FORM = 'SUPPORT_FORM';\nconst EVENT_FORM = 'EVENT_FORM';\nexport const DEFAULT_OPTIONS = {\n label: __('Templates', 'leadin'),\n options: [\n { label: __('Registration Form', 'leadin'), value: REGISTRATION_FORM },\n { label: __('Contact us Form', 'leadin'), value: CONTACT_US_FORM },\n { label: __('Newsletter sign-up Form', 'leadin'), value: NEWSLETTER_FORM },\n { label: __('Support Form', 'leadin'), value: SUPPORT_FORM },\n { label: __('Event Registration Form', 'leadin'), value: EVENT_FORM },\n ],\n};\nexport function isDefaultForm(value) {\n return (value === REGISTRATION_FORM ||\n value === CONTACT_US_FORM ||\n value === NEWSLETTER_FORM ||\n value === SUPPORT_FORM ||\n value === EVENT_FORM);\n}\n","const { accountName, adminUrl, activationTime, connectionStatus, deviceId, didDisconnect, env, formsScript, meetingsScript, formsScriptPayload, hublet, hubspotBaseUrl, hubspotNonce, iframeUrl, impactLink, lastAuthorizeTime, lastDeauthorizeTime, lastDisconnectTime, leadinPluginVersion, leadinQueryParams, locale, loginUrl, phpVersion, pluginPath, plugins, portalDomain, portalEmail, portalId, redirectNonce, restNonce, restUrl, refreshToken, reviewSkippedDate, theme, trackConsent, wpVersion, contentEmbed, requiresContentEmbedScope, refreshTokenError, } = window.leadinConfig;\nexport { accountName, adminUrl, activationTime, connectionStatus, deviceId, didDisconnect, env, formsScript, meetingsScript, formsScriptPayload, hublet, hubspotBaseUrl, hubspotNonce, iframeUrl, impactLink, lastAuthorizeTime, lastDeauthorizeTime, lastDisconnectTime, leadinPluginVersion, leadinQueryParams, loginUrl, locale, phpVersion, pluginPath, plugins, portalDomain, portalEmail, portalId, redirectNonce, restNonce, restUrl, refreshToken, reviewSkippedDate, theme, trackConsent, wpVersion, contentEmbed, requiresContentEmbedScope, refreshTokenError, };\n","import { jsx as _jsx } from \"react/jsx-runtime\";\nimport ElementorBanner from './ElementorBanner';\nimport { __ } from '@wordpress/i18n';\nexport default function ConnectPluginBanner() {\n return (_jsx(ElementorBanner, { children: _jsx(\"b\", { dangerouslySetInnerHTML: {\n __html: __('The HubSpot plugin is not connected right now To use HubSpot tools on your WordPress site, %1$sconnect the plugin now%2$s')\n .replace('%1$s', '')\n .replace('%2$s', ' '),\n } }) }));\n}\n","import { jsx as _jsx } from \"react/jsx-runtime\";\nexport default function ElementorBanner({ type = 'warning', children, }) {\n return (_jsx(\"div\", { className: \"elementor-control-content\", children: _jsx(\"div\", { className: `elementor-control-raw-html elementor-panel-alert elementor-panel-alert-${type}`, children: children }) }));\n}\n","import { jsx as _jsx } from \"react/jsx-runtime\";\nimport { styled } from '@linaria/react';\nconst Container = styled.div `\n display: flex;\n justify-content: center;\n padding-bottom: 8px;\n`;\nexport default function ElementorButton({ children, ...params }) {\n return (_jsx(Container, { className: \"elementor-button-wrapper\", children: _jsx(\"button\", { className: \"elementor-button elementor-button-default\", type: \"button\", ...params, children: children }) }));\n}\n","import { jsx as _jsx, jsxs as _jsxs } from \"react/jsx-runtime\";\nimport { Fragment } from 'react';\nimport { portalId, refreshToken } from '../../constants/leadinConfig';\nimport ElementorBanner from '../Common/ElementorBanner';\nimport UISpinner from '../../shared/UIComponents/UISpinner';\nimport { __ } from '@wordpress/i18n';\nimport { BackgroudAppContext, useBackgroundAppContext, } from '../../iframe/useBackgroundApp';\nimport useForms from './hooks/useForms';\nimport { getOrCreateBackgroundApp } from '../../utils/backgroundAppUtils';\nfunction ElementorFormSelect({ formId, setAttributes, }) {\n const { hasError, forms, loading } = useForms();\n return loading ? (_jsx(\"div\", { children: _jsx(UISpinner, {}) })) : hasError ? (_jsx(ElementorBanner, { type: \"danger\", children: __('Please refresh your forms or try again in a few minutes', 'leadin') })) : (_jsxs(\"select\", { value: formId, onChange: event => {\n const selectedForm = forms.find(form => form.value === event.target.value);\n if (selectedForm) {\n setAttributes({\n portalId,\n formId: selectedForm.value,\n formName: selectedForm.label,\n });\n }\n }, children: [_jsx(\"option\", { value: \"\", disabled: true, selected: true, children: __('Search for a form', 'leadin') }), forms.map(form => (_jsx(\"option\", { value: form.value, children: form.label }, form.value)))] }));\n}\nfunction ElementorFormSelectWrapper(props) {\n const isBackgroundAppReady = useBackgroundAppContext();\n return (_jsx(Fragment, { children: !isBackgroundAppReady ? (_jsx(\"div\", { children: _jsx(UISpinner, {}) })) : (_jsx(ElementorFormSelect, { ...props })) }));\n}\nexport default function ElementorFormSelectContainer(props) {\n return (_jsx(BackgroudAppContext.Provider, { value: refreshToken && getOrCreateBackgroundApp(refreshToken), children: _jsx(ElementorFormSelectWrapper, { ...props }) }));\n}\n","import { jsx as _jsx } from \"react/jsx-runtime\";\nimport { Fragment } from 'react';\nimport { connectionStatus } from '../../constants/leadinConfig';\nimport ConnectPluginBanner from '../Common/ConnectPluginBanner';\nimport ElementorFormSelect from './ElementorFormSelect';\nconst ConnectionStatus = {\n Connected: 'Connected',\n NotConnected: 'NotConnected',\n};\nexport default function FormControlController(attributes, setValue) {\n return () => {\n const render = () => {\n if (connectionStatus === ConnectionStatus.Connected) {\n return (_jsx(ElementorFormSelect, { formId: attributes.formId, setAttributes: setValue }));\n }\n else {\n return _jsx(ConnectPluginBanner, {});\n }\n };\n return _jsx(Fragment, { children: render() });\n };\n}\n","import { jsx as _jsx } from \"react/jsx-runtime\";\nimport { Fragment } from 'react';\nimport { connectionStatus } from '../../constants/leadinConfig';\nimport ErrorHandler from '../../shared/Common/ErrorHandler';\nimport FormEdit from '../../shared/Form/FormEdit';\nimport ConnectionStatus from '../../shared/enums/connectionStatus';\nexport default function FormWidgetController(attributes, setValue) {\n return () => {\n const render = () => {\n if (connectionStatus === ConnectionStatus.Connected) {\n return (_jsx(FormEdit, { attributes: attributes, isSelected: true, setAttributes: setValue, preview: false, origin: \"elementor\" }));\n }\n else {\n return _jsx(ErrorHandler, { status: 401 });\n }\n };\n return _jsx(Fragment, { children: render() });\n };\n}\n","import { useState, useEffect } from 'react';\nimport LoadState from '../../../shared/enums/loadState';\nimport { ProxyMessages } from '../../../iframe/integratedMessages';\nimport { usePostAsyncBackgroundMessage } from '../../../iframe/useBackgroundApp';\nexport default function useForms() {\n const proxy = usePostAsyncBackgroundMessage();\n const [loadState, setLoadState] = useState(LoadState.NotLoaded);\n const [hasError, setError] = useState(null);\n const [forms, setForms] = useState([]);\n useEffect(() => {\n if (loadState === LoadState.NotLoaded) {\n proxy({\n key: ProxyMessages.FetchForms,\n payload: {\n search: '',\n },\n })\n .then(data => {\n setForms(data.map((form) => ({\n label: form.name,\n value: form.guid,\n })));\n setLoadState(LoadState.Loaded);\n })\n .catch(error => {\n setError(error);\n setLoadState(LoadState.Failed);\n });\n }\n }, [loadState]);\n return { forms, loading: loadState === LoadState.Loading, hasError };\n}\n","import ReactDOM from 'react-dom';\nimport FormControlController from './FormControlController';\nimport FormWidgetController from './FormWidgetController';\nexport default class registerFormWidget {\n widgetContainer;\n attributes;\n controlContainer;\n setValue;\n constructor(controlContainer, widgetContainer, setValue) {\n const attributes = widgetContainer.dataset.attributes\n ? JSON.parse(widgetContainer.dataset.attributes)\n : {};\n this.widgetContainer = widgetContainer;\n this.controlContainer = controlContainer;\n this.setValue = setValue;\n this.attributes = attributes;\n }\n render() {\n ReactDOM.render(FormWidgetController(this.attributes, this.setValue)(), this.widgetContainer);\n ReactDOM.render(FormControlController(this.attributes, this.setValue)(), this.controlContainer);\n }\n done() {\n ReactDOM.unmountComponentAtNode(this.widgetContainer);\n ReactDOM.unmountComponentAtNode(this.controlContainer);\n }\n}\n","import { jsx as _jsx, jsxs as _jsxs } from \"react/jsx-runtime\";\nimport { Fragment, useState } from 'react';\nimport ElementorBanner from '../Common/ElementorBanner';\nimport UISpinner from '../../shared/UIComponents/UISpinner';\nimport ElementorMeetingWarning from './ElementorMeetingWarning';\nimport useMeetings, { useSelectedMeetingCalendar, } from '../../shared/Meeting/hooks/useMeetings';\nimport { __ } from '@wordpress/i18n';\nimport Raven from 'raven-js';\nimport { BackgroudAppContext, useBackgroundAppContext, } from '../../iframe/useBackgroundApp';\nimport { refreshToken } from '../../constants/leadinConfig';\nimport { getOrCreateBackgroundApp } from '../../utils/backgroundAppUtils';\nfunction ElementorMeetingSelect({ url, setAttributes, }) {\n const { mappedMeetings: meetings, loading, error, reload, connectCalendar, } = useMeetings();\n const selectedMeetingCalendar = useSelectedMeetingCalendar(url);\n const [localUrl, setLocalUrl] = useState(url);\n const handleConnectCalendar = () => {\n return connectCalendar()\n .then(() => {\n reload();\n })\n .catch(error => {\n Raven.captureMessage('Unable to connect calendar', {\n extra: { error },\n });\n });\n };\n return (_jsx(Fragment, { children: loading ? (_jsx(\"div\", { children: _jsx(UISpinner, {}) })) : error ? (_jsx(ElementorBanner, { type: \"danger\", children: __('Please refresh your meetings or try again in a few minutes', 'leadin') })) : (_jsxs(Fragment, { children: [selectedMeetingCalendar && (_jsx(ElementorMeetingWarning, { status: selectedMeetingCalendar, onConnectCalendar: connectCalendar })), meetings.length > 1 && (_jsxs(\"select\", { value: localUrl, onChange: event => {\n const newUrl = event.target.value;\n setLocalUrl(newUrl);\n setAttributes({\n url: newUrl,\n });\n }, children: [_jsx(\"option\", { value: \"\", disabled: true, selected: true, children: __('Select a meeting', 'leadin') }), meetings.map(item => (_jsx(\"option\", { value: item.value, children: item.label }, item.value)))] }))] })) }));\n}\nfunction ElementorMeetingSelectWrapper(props) {\n const isBackgroundAppReady = useBackgroundAppContext();\n return (_jsx(Fragment, { children: !isBackgroundAppReady ? (_jsx(\"div\", { children: _jsx(UISpinner, {}) })) : (_jsx(ElementorMeetingSelect, { ...props })) }));\n}\nexport default function ElementorMeetingsSelectContainer(props) {\n return (_jsx(BackgroudAppContext.Provider, { value: refreshToken && getOrCreateBackgroundApp(refreshToken), children: _jsx(ElementorMeetingSelectWrapper, { ...props }) }));\n}\n","import { jsx as _jsx, jsxs as _jsxs } from \"react/jsx-runtime\";\nimport { Fragment } from 'react';\nimport { CURRENT_USER_CALENDAR_MISSING } from '../../shared/Meeting/constants';\nimport ElementorButton from '../Common/ElementorButton';\nimport ElementorBanner from '../Common/ElementorBanner';\nimport { styled } from '@linaria/react';\nimport { __ } from '@wordpress/i18n';\nconst Container = styled.div `\n padding-bottom: 8px;\n`;\nexport default function MeetingWarning({ onConnectCalendar, status, }) {\n const isMeetingOwner = status === CURRENT_USER_CALENDAR_MISSING;\n const titleText = isMeetingOwner\n ? __('Your calendar is not connected', 'leadin')\n : __('Calendar is not connected', 'leadin');\n const titleMessage = isMeetingOwner\n ? __('Please connect your calendar to activate your scheduling pages', 'leadin')\n : __('Make sure that everybody in this meeting has connected their calendar from the Meetings page in HubSpot', 'leadin');\n return (_jsxs(Fragment, { children: [_jsx(Container, { children: _jsxs(ElementorBanner, { type: \"warning\", children: [_jsx(\"b\", { children: titleText }), _jsx(\"br\", {}), titleMessage] }) }), isMeetingOwner && (_jsx(ElementorButton, { id: \"meetings-connect-calendar\", onClick: onConnectCalendar, children: __('Connect calendar', 'leadin') }))] }));\n}\n","import { jsx as _jsx } from \"react/jsx-runtime\";\nimport { Fragment } from 'react';\nimport { connectionStatus } from '../../constants/leadinConfig';\nimport ConnectPluginBanner from '../Common/ConnectPluginBanner';\nimport ElementorMeetingSelect from './ElementorMeetingSelect';\nconst ConnectionStatus = {\n Connected: 'Connected',\n NotConnected: 'NotConnected',\n};\nexport default function MeetingControlController(attributes, setValue) {\n return () => {\n const render = () => {\n if (connectionStatus === ConnectionStatus.Connected) {\n return (_jsx(ElementorMeetingSelect, { url: attributes.url, setAttributes: setValue }));\n }\n else {\n return _jsx(ConnectPluginBanner, {});\n }\n };\n return _jsx(Fragment, { children: render() });\n };\n}\n","import { jsx as _jsx } from \"react/jsx-runtime\";\nimport { Fragment } from 'react';\nimport { connectionStatus } from '../../constants/leadinConfig';\nimport ErrorHandler from '../../shared/Common/ErrorHandler';\nimport MeetingsEdit from '../../shared/Meeting/MeetingEdit';\nconst ConnectionStatus = {\n Connected: 'Connected',\n NotConnected: 'NotConnected',\n};\nexport default function MeetingWidgetController(attributes, setValue) {\n return () => {\n const render = () => {\n if (connectionStatus === ConnectionStatus.Connected) {\n return (_jsx(MeetingsEdit, { attributes: attributes, isSelected: true, setAttributes: setValue, preview: false, origin: \"elementor\" }));\n }\n else {\n return _jsx(ErrorHandler, { status: 401 });\n }\n };\n return _jsx(Fragment, { children: render() });\n };\n}\n","import ReactDOM from 'react-dom';\nimport MeetingControlController from './MeetingControlController';\nimport MeetingWidgetController from './MeetingWidgetController';\nexport default class registerMeetingsWidget {\n widgetContainer;\n controlContainer;\n setValue;\n attributes;\n constructor(controlContainer, widgetContainer, setValue) {\n const attributes = widgetContainer.dataset.attributes\n ? JSON.parse(widgetContainer.dataset.attributes)\n : {};\n this.widgetContainer = widgetContainer;\n this.controlContainer = controlContainer;\n this.setValue = setValue;\n this.attributes = attributes;\n }\n render() {\n ReactDOM.render(MeetingWidgetController(this.attributes, this.setValue)(), this.widgetContainer);\n ReactDOM.render(MeetingControlController(this.attributes, this.setValue)(), this.controlContainer);\n }\n done() {\n ReactDOM.unmountComponentAtNode(this.widgetContainer);\n ReactDOM.unmountComponentAtNode(this.controlContainer);\n }\n}\n","export default function elementorWidget(elementor, options, callback, done = () => { }) {\n return elementor.modules.controls.BaseData.extend({\n onReady() {\n const self = this;\n const controlContainer = this.ui.contentEditable.prevObject[0].querySelector(options.controlSelector);\n let widgetContainer = this.options.element.$el[0].querySelector(options.containerSelector);\n if (widgetContainer) {\n callback(controlContainer, widgetContainer, (args) => self.setValue(args));\n }\n else {\n //@ts-expect-error global\n window.elementorFrontend.hooks.addAction(`frontend/element_ready/${options.widgetName}.default`, (element) => {\n widgetContainer = element[0].querySelector(options.containerSelector);\n callback(controlContainer, widgetContainer, (args) => self.setValue(args));\n });\n }\n },\n saveValue(props) {\n this.setValue(props);\n },\n onBeforeDestroy() {\n //@ts-expect-error global\n window.elementorFrontend.hooks.removeAction(`frontend/element_ready/${options.widgetName}.default`);\n done();\n },\n });\n}\n","export const CoreMessages = {\n HandshakeReceive: 'INTEGRATED_APP_EMBEDDER_HANDSHAKE_RECEIVED',\n SendRefreshToken: 'INTEGRATED_APP_EMBEDDER_SEND_REFRESH_TOKEN',\n ReloadParentFrame: 'INTEGRATED_APP_EMBEDDER_RELOAD_PARENT_FRAME',\n RedirectParentFrame: 'INTEGRATED_APP_EMBEDDER_REDIRECT_PARENT_FRAME',\n SendLocale: 'INTEGRATED_APP_EMBEDDER_SEND_LOCALE',\n SendDeviceId: 'INTEGRATED_APP_EMBEDDER_SEND_DEVICE_ID',\n};\n","export const FormMessages = {\n CreateFormAppNavigation: 'CREATE_FORM_APP_NAVIGATION',\n};\n","export * from './core/CoreMessages';\nexport * from './forms/FormsMessages';\nexport * from './livechat/LiveChatMessages';\nexport * from './plugin/PluginMessages';\nexport * from './proxy/ProxyMessages';\n","export const LiveChatMessages = {\n CreateLiveChatAppNavigation: 'CREATE_LIVE_CHAT_APP_NAVIGATION',\n};\n","export const PluginMessages = {\n PluginSettingsNavigation: 'PLUGIN_SETTINGS_NAVIGATION',\n PluginLeadinConfig: 'PLUGIN_LEADIN_CONFIG',\n TrackConsent: 'INTEGRATED_APP_EMBEDDER_TRACK_CONSENT',\n InternalTrackingFetchRequest: 'INTEGRATED_TRACKING_FETCH_REQUEST',\n InternalTrackingFetchResponse: 'INTEGRATED_TRACKING_FETCH_RESPONSE',\n InternalTrackingFetchError: 'INTEGRATED_TRACKING_FETCH_ERROR',\n InternalTrackingChangeRequest: 'INTEGRATED_TRACKING_CHANGE_REQUEST',\n InternalTrackingChangeError: 'INTEGRATED_TRACKING_CHANGE_ERROR',\n BusinessUnitFetchRequest: 'BUSINESS_UNIT_FETCH_REQUEST',\n BusinessUnitFetchResponse: 'BUSINESS_UNIT_FETCH_FETCH_RESPONSE',\n BusinessUnitFetchError: 'BUSINESS_UNIT_FETCH_FETCH_ERROR',\n BusinessUnitChangeRequest: 'BUSINESS_UNIT_CHANGE_REQUEST',\n BusinessUnitChangeError: 'BUSINESS_UNIT_CHANGE_ERROR',\n SkipReviewRequest: 'SKIP_REVIEW_REQUEST',\n SkipReviewResponse: 'SKIP_REVIEW_RESPONSE',\n SkipReviewError: 'SKIP_REVIEW_ERROR',\n RemoveParentQueryParam: 'REMOVE_PARENT_QUERY_PARAM',\n ContentEmbedInstallRequest: 'CONTENT_EMBED_INSTALL_REQUEST',\n ContentEmbedInstallResponse: 'CONTENT_EMBED_INSTALL_RESPONSE',\n ContentEmbedInstallError: 'CONTENT_EMBED_INSTALL_ERROR',\n ContentEmbedActivationRequest: 'CONTENT_EMBED_ACTIVATION_REQUEST',\n ContentEmbedActivationResponse: 'CONTENT_EMBED_ACTIVATION_RESPONSE',\n ContentEmbedActivationError: 'CONTENT_EMBED_ACTIVATION_ERROR',\n};\n","export const ProxyMessages = {\n FetchForms: 'FETCH_FORMS',\n FetchForm: 'FETCH_FORM',\n CreateFormFromTemplate: 'CREATE_FORM_FROM_TEMPLATE',\n FetchAuth: 'FETCH_AUTH',\n FetchMeetingsAndUsers: 'FETCH_MEETINGS_AND_USERS',\n FetchContactsCreateSinceActivation: 'FETCH_CONTACTS_CREATED_SINCE_ACTIVATION',\n FetchOrCreateMeetingUser: 'FETCH_OR_CREATE_MEETING_USER',\n ConnectMeetingsCalendar: 'CONNECT_MEETINGS_CALENDAR',\n TrackFormPreviewRender: 'TRACK_FORM_PREVIEW_RENDER',\n TrackFormCreatedFromTemplate: 'TRACK_FORM_CREATED_FROM_TEMPLATE',\n TrackFormCreationFailed: 'TRACK_FORM_CREATION_FAILED',\n TrackMeetingPreviewRender: 'TRACK_MEETING_PREVIEW_RENDER',\n TrackSidebarMetaChange: 'TRACK_SIDEBAR_META_CHANGE',\n TrackReviewBannerRender: 'TRACK_REVIEW_BANNER_RENDER',\n TrackReviewBannerInteraction: 'TRACK_REVIEW_BANNER_INTERACTION',\n TrackReviewBannerDismissed: 'TRACK_REVIEW_BANNER_DISMISSED',\n TrackPluginDeactivation: 'TRACK_PLUGIN_DEACTIVATION',\n};\n","import { createContext, useContext } from 'react';\nexport const BackgroudAppContext = createContext(null);\nexport function useBackgroundAppContext() {\n return useContext(BackgroudAppContext);\n}\nexport function usePostBackgroundMessage() {\n const app = useBackgroundAppContext();\n return (message) => {\n app.postMessage(message);\n };\n}\nexport function usePostAsyncBackgroundMessage() {\n const app = useBackgroundAppContext();\n return (message) => app.postAsyncMessage(message);\n}\n","import Raven from 'raven-js';\nimport { hubspotBaseUrl, phpVersion, wpVersion, leadinPluginVersion, portalId, plugins, } from '../constants/leadinConfig';\nexport function configureRaven() {\n if (hubspotBaseUrl.indexOf('app.hubspot.com') === -1) {\n return;\n }\n Raven.config('https://e9b8f382cdd130c0d415cd977d2be56f@exceptions.hubspot.com/1', {\n instrument: {\n tryCatch: false,\n },\n release: leadinPluginVersion,\n }).install();\n Raven.setTagsContext({\n v: leadinPluginVersion,\n php: phpVersion,\n wordpress: wpVersion,\n });\n Raven.setExtraContext({\n hub: portalId,\n plugins: Object.keys(plugins)\n .map(name => `${name}#${plugins[name]}`)\n .join(','),\n });\n}\nexport default Raven;\n","import { jsx as _jsx, jsxs as _jsxs } from \"react/jsx-runtime\";\nimport { useRef, useState, useEffect } from 'react';\nimport { styled } from '@linaria/react';\nimport { CALYPSO, CALYPSO_LIGHT, CALYPSO_MEDIUM, OBSIDIAN, } from '../UIComponents/colors';\nimport UISpinner from '../UIComponents/UISpinner';\nimport LoadState from '../enums/loadState';\nconst Container = styled.div `\n color: ${OBSIDIAN};\n font-family: 'Lexend Deca', Helvetica, Arial, sans-serif;\n font-size: 14px;\n position: relative;\n`;\nconst ControlContainer = styled.div `\n align-items: center;\n background-color: hsl(0, 0%, 100%);\n border-color: hsl(0, 0%, 80%);\n border-radius: 4px;\n border-style: solid;\n border-width: ${props => (props.focused ? '0' : '1px')};\n cursor: default;\n display: flex;\n flex-wrap: wrap;\n justify-content: space-between;\n min-height: 38px;\n outline: 0 !important;\n position: relative;\n transition: all 100ms;\n box-sizing: border-box;\n box-shadow: ${props => props.focused ? `0 0 0 2px ${CALYPSO_MEDIUM}` : 'none'};\n &:hover {\n border-color: hsl(0, 0%, 70%);\n }\n`;\nconst ValueContainer = styled.div `\n align-items: center;\n display: flex;\n flex: 1;\n flex-wrap: wrap;\n padding: 2px 8px;\n position: relative;\n overflow: hidden;\n box-sizing: border-box;\n`;\nconst Placeholder = styled.div `\n color: hsl(0, 0%, 50%);\n margin-left: 2px;\n margin-right: 2px;\n position: absolute;\n top: 50%;\n transform: translateY(-50%);\n box-sizing: border-box;\n font-size: 16px;\n`;\nconst SingleValue = styled.div `\n color: hsl(0, 0%, 20%);\n margin-left: 2px;\n margin-right: 2px;\n max-width: calc(100% - 8px);\n overflow: hidden;\n position: absolute;\n text-overflow: ellipsis;\n white-space: nowrap;\n top: 50%;\n transform: translateY(-50%);\n box-sizing: border-box;\n`;\nconst IndicatorContainer = styled.div `\n align-items: center;\n align-self: stretch;\n display: flex;\n flex-shrink: 0;\n box-sizing: border-box;\n`;\nconst DropdownIndicator = styled.div `\n border-top: 8px solid ${CALYPSO};\n border-left: 6px solid transparent;\n border-right: 6px solid transparent;\n width: 0px;\n height: 0px;\n margin: 10px;\n`;\nconst InputContainer = styled.div `\n margin: 2px;\n padding-bottom: 2px;\n padding-top: 2px;\n visibility: visible;\n color: hsl(0, 0%, 20%);\n box-sizing: border-box;\n`;\nconst Input = styled.input `\n box-sizing: content-box;\n background: rgba(0, 0, 0, 0) none repeat scroll 0px center;\n border: 0px none;\n font-size: inherit;\n opacity: 1;\n outline: currentcolor none 0px;\n padding: 0px;\n color: inherit;\n font-family: inherit;\n`;\nconst InputShadow = styled.div `\n position: absolute;\n opacity: 0;\n font-size: inherit;\n`;\nconst MenuContainer = styled.div `\n position: absolute;\n top: 100%;\n background-color: #fff;\n border-radius: 4px;\n margin-bottom: 8px;\n margin-top: 8px;\n z-index: 9999;\n box-shadow: 0 0 0 1px hsla(0, 0%, 0%, 0.1), 0 4px 11px hsla(0, 0%, 0%, 0.1);\n width: 100%;\n`;\nconst MenuList = styled.div `\n max-height: 300px;\n overflow-y: auto;\n padding-bottom: 4px;\n padding-top: 4px;\n position: relative;\n`;\nconst MenuGroup = styled.div `\n padding-bottom: 8px;\n padding-top: 8px;\n`;\nconst MenuGroupHeader = styled.div `\n color: #999;\n cursor: default;\n font-size: 75%;\n font-weight: 500;\n margin-bottom: 0.25em;\n text-transform: uppercase;\n padding-left: 12px;\n padding-left: 12px;\n`;\nconst MenuItem = styled.div `\n display: block;\n background-color: ${props => props.selected ? CALYPSO_MEDIUM : 'transparent'};\n color: ${props => (props.selected ? '#fff' : 'inherit')};\n cursor: default;\n font-size: inherit;\n width: 100%;\n padding: 8px 12px;\n &:hover {\n background-color: ${props => props.selected ? CALYPSO_MEDIUM : CALYPSO_LIGHT};\n }\n`;\nexport default function AsyncSelect({ placeholder, value, loadOptions, onChange, defaultOptions, }) {\n const inputEl = useRef(null);\n const inputShadowEl = useRef(null);\n const [isFocused, setFocus] = useState(false);\n const [loadState, setLoadState] = useState(LoadState.NotLoaded);\n const [localValue, setLocalValue] = useState('');\n const [options, setOptions] = useState(defaultOptions);\n const inputSize = `${inputShadowEl.current ? inputShadowEl.current.clientWidth + 10 : 2}px`;\n useEffect(() => {\n if (loadOptions && loadState === LoadState.NotLoaded) {\n loadOptions('', (result) => {\n setOptions(result);\n setLoadState(LoadState.Idle);\n });\n }\n }, [loadOptions, loadState]);\n const renderItems = (items = [], parentKey) => {\n return items.map((item, index) => {\n if (item.options) {\n return (_jsxs(MenuGroup, { children: [_jsx(MenuGroupHeader, { id: `${index}-heading`, children: item.label }), _jsx(\"div\", { children: renderItems(item.options, index) })] }, `async-select-item-${index}`));\n }\n else {\n const key = `async-select-item-${parentKey !== undefined ? `${parentKey}-${index}` : index}`;\n return (_jsx(MenuItem, { id: key, selected: value && item.value === value.value, onClick: () => {\n onChange(item);\n setFocus(false);\n }, children: item.label }, key));\n }\n });\n };\n return (_jsxs(Container, { children: [_jsxs(ControlContainer, { id: \"leadin-async-selector\", focused: isFocused, onClick: () => {\n if (isFocused) {\n if (inputEl.current) {\n inputEl.current.blur();\n }\n setFocus(false);\n setLocalValue('');\n }\n else {\n if (inputEl.current) {\n inputEl.current.focus();\n }\n setFocus(true);\n }\n }, children: [_jsxs(ValueContainer, { children: [localValue === '' &&\n (!value ? (_jsx(Placeholder, { children: placeholder })) : (_jsx(SingleValue, { children: value.label }))), _jsxs(InputContainer, { children: [_jsx(Input, { ref: inputEl, onFocus: () => {\n setFocus(true);\n }, onChange: e => {\n setLocalValue(e.target.value);\n setLoadState(LoadState.Loading);\n loadOptions &&\n loadOptions(e.target.value, (result) => {\n setOptions(result);\n setLoadState(LoadState.Idle);\n });\n }, value: localValue, width: inputSize, id: \"asycn-select-input\" }), _jsx(InputShadow, { ref: inputShadowEl, children: localValue })] })] }), _jsxs(IndicatorContainer, { children: [loadState === LoadState.Loading && _jsx(UISpinner, {}), _jsx(DropdownIndicator, {})] })] }), isFocused && (_jsx(MenuContainer, { children: _jsx(MenuList, { children: renderItems(options) }) }))] }));\n}\n","import { jsx as _jsx, jsxs as _jsxs } from \"react/jsx-runtime\";\nimport UIButton from '../UIComponents/UIButton';\nimport UIContainer from '../UIComponents/UIContainer';\nimport HubspotWrapper from './HubspotWrapper';\nimport { adminUrl, redirectNonce } from '../../constants/leadinConfig';\nimport { pluginPath } from '../../constants/leadinConfig';\nimport { __ } from '@wordpress/i18n';\nfunction redirectToPlugin() {\n window.location.href = `${adminUrl}admin.php?page=leadin&leadin_expired=${redirectNonce}`;\n}\nexport default function ErrorHandler({ status, resetErrorState, errorInfo = { header: '', message: '', action: '' }, }) {\n const isUnauthorized = status === 401 || status === 403;\n const errorHeader = isUnauthorized\n ? __(\"Your plugin isn't authorized\", 'leadin')\n : errorInfo.header;\n const errorMessage = isUnauthorized\n ? __('Reauthorize your plugin to access your free HubSpot tools', 'leadin')\n : errorInfo.message;\n return (_jsx(HubspotWrapper, { pluginPath: pluginPath, children: _jsxs(UIContainer, { textAlign: \"center\", children: [_jsx(\"h4\", { children: errorHeader }), _jsx(\"p\", { children: _jsx(\"b\", { children: errorMessage }) }), isUnauthorized ? (_jsx(UIButton, { \"data-test-id\": \"authorize-button\", onClick: redirectToPlugin, children: __('Go to plugin', 'leadin') })) : (_jsx(UIButton, { \"data-test-id\": \"retry-button\", onClick: resetErrorState, children: errorInfo.action }))] }) }));\n}\n","import { styled } from '@linaria/react';\nexport default styled.div `\n background-image: ${props => `url(${props.pluginPath}/public/assets/images/hubspot.svg)`};\n background-color: #f5f8fa;\n background-repeat: no-repeat;\n background-position: center 25px;\n background-size: 120px;\n color: #33475b;\n font-family: 'Lexend Deca', Helvetica, Arial, sans-serif;\n font-size: 14px;\n\n padding: ${(props) => props.padding || '90px 20% 25px'};\n\n p {\n font-size: inherit !important;\n line-height: 24px;\n margin: 4px 0;\n }\n`;\n","import { jsx as _jsx } from \"react/jsx-runtime\";\nimport HubspotWrapper from './HubspotWrapper';\nimport UISpinner from '../UIComponents/UISpinner';\nimport { pluginPath } from '../../constants/leadinConfig';\nexport default function LoadingBlock() {\n return (_jsx(HubspotWrapper, { pluginPath: pluginPath, children: _jsx(UISpinner, { size: 50 }) }));\n}\n","import { jsx as _jsx, jsxs as _jsxs } from \"react/jsx-runtime\";\nimport { Fragment, useEffect } from 'react';\nimport { portalId, refreshToken } from '../../constants/leadinConfig';\nimport UISpacer from '../UIComponents/UISpacer';\nimport PreviewForm from './PreviewForm';\nimport FormSelect from './FormSelect';\nimport { usePostBackgroundMessage, BackgroudAppContext, useBackgroundAppContext, } from '../../iframe/useBackgroundApp';\nimport { ProxyMessages } from '../../iframe/integratedMessages';\nimport LoadingBlock from '../Common/LoadingBlock';\nimport { getOrCreateBackgroundApp } from '../../utils/backgroundAppUtils';\nfunction FormEdit({ attributes, isSelected, setAttributes, preview = true, origin = 'gutenberg', }) {\n const { formId, formName } = attributes;\n const formSelected = portalId && formId;\n const isBackgroundAppReady = useBackgroundAppContext();\n const monitorFormPreviewRender = usePostBackgroundMessage();\n const handleChange = (selectedForm) => {\n setAttributes({\n portalId,\n formId: selectedForm.value,\n formName: selectedForm.label,\n });\n };\n useEffect(() => {\n monitorFormPreviewRender({\n key: ProxyMessages.TrackFormPreviewRender,\n payload: {\n origin,\n },\n });\n }, [origin]);\n return !isBackgroundAppReady ? (_jsx(LoadingBlock, {})) : (_jsxs(Fragment, { children: [(isSelected || !formSelected) && (_jsx(FormSelect, { formId: formId, formName: formName, handleChange: handleChange, origin: origin })), formSelected && (_jsxs(Fragment, { children: [isSelected && _jsx(UISpacer, {}), preview && _jsx(PreviewForm, { portalId: portalId, formId: formId })] }))] }));\n}\nexport default function FormEditContainer(props) {\n return (_jsx(BackgroudAppContext.Provider, { value: refreshToken && getOrCreateBackgroundApp(refreshToken), children: _jsx(FormEdit, { ...props }) }));\n}\n","import { jsx as _jsx } from \"react/jsx-runtime\";\nimport FormSelector from './FormSelector';\nimport LoadingBlock from '../Common/LoadingBlock';\nimport { __ } from '@wordpress/i18n';\nimport useForms from './hooks/useForms';\nimport useCreateFormFromTemplate from './hooks/useCreateFormFromTemplate';\nimport { isDefaultForm } from '../../constants/defaultFormOptions';\nimport ErrorHandler from '../Common/ErrorHandler';\nexport default function FormSelect({ formId, formName, handleChange, origin = 'gutenberg', }) {\n const { search, formApiError, reset } = useForms();\n const { createFormByTemplate, reset: createReset, isCreating, hasError, formApiError: createApiError, } = useCreateFormFromTemplate(origin);\n const value = formId && formName\n ? {\n label: formName,\n value: formId,\n }\n : null;\n const handleLocalChange = (option) => {\n if (isDefaultForm(option.value)) {\n createFormByTemplate(option.value).then(({ guid, name }) => {\n handleChange({\n value: guid,\n label: name,\n });\n });\n }\n else {\n handleChange(option);\n }\n };\n return isCreating ? (_jsx(LoadingBlock, {})) : formApiError || createApiError ? (_jsx(ErrorHandler, { status: formApiError ? formApiError.status : createApiError.status, resetErrorState: () => {\n if (hasError) {\n createReset();\n }\n else {\n reset();\n }\n }, errorInfo: {\n header: __('There was a problem retrieving your forms', 'leadin'),\n message: __('Please refresh your forms or try again in a few minutes', 'leadin'),\n action: __('Refresh forms', 'leadin'),\n } })) : (_jsx(FormSelector, { loadOptions: search, onChange: (option) => handleLocalChange(option), value: value }));\n}\n","import { jsx as _jsx, jsxs as _jsxs } from \"react/jsx-runtime\";\nimport HubspotWrapper from '../Common/HubspotWrapper';\nimport { pluginPath } from '../../constants/leadinConfig';\nimport AsyncSelect from '../Common/AsyncSelect';\nimport { __ } from '@wordpress/i18n';\nexport default function FormSelector({ loadOptions, onChange, value, }) {\n return (_jsxs(HubspotWrapper, { pluginPath: pluginPath, children: [_jsx(\"p\", { \"data-test-id\": \"leadin-form-select\", children: _jsx(\"b\", { children: __('Select an existing form or create a new one from a template', 'leadin') }) }), _jsx(AsyncSelect, { placeholder: __('Search for a form', 'leadin'), value: value, loadOptions: loadOptions, onChange: onChange })] }));\n}\n","import { jsx as _jsx } from \"react/jsx-runtime\";\nimport { useEffect, useRef } from 'react';\nimport UIOverlay from '../UIComponents/UIOverlay';\nimport { formsScriptPayload, hublet } from '../../constants/leadinConfig';\nimport useFormScript from './hooks/useFormsScript';\nexport default function PreviewForm({ portalId, formId, }) {\n const inputEl = useRef(null);\n const ready = useFormScript();\n useEffect(() => {\n if (!ready) {\n return;\n }\n if (inputEl.current) {\n inputEl.current.innerHTML = '';\n const embedScript = document.createElement('script');\n embedScript.innerHTML = `hbspt.forms.create({ portalId: '${portalId}', formId: '${formId}', region: '${hublet}', ${formsScriptPayload} });`;\n inputEl.current.appendChild(embedScript);\n }\n }, [formId, portalId, ready, inputEl]);\n return _jsx(UIOverlay, { ref: inputEl });\n}\n","import { useState } from 'react';\nimport { usePostAsyncBackgroundMessage, usePostBackgroundMessage, } from '../../../iframe/useBackgroundApp';\nimport LoadState from '../../enums/loadState';\nimport { ProxyMessages } from '../../../iframe/integratedMessages';\nexport default function useCreateFormFromTemplate(origin = 'gutenberg') {\n const proxy = usePostAsyncBackgroundMessage();\n const track = usePostBackgroundMessage();\n const [loadState, setLoadState] = useState(LoadState.Idle);\n const [formApiError, setFormApiError] = useState(null);\n const createFormByTemplate = (type) => {\n setLoadState(LoadState.Loading);\n track({\n key: ProxyMessages.TrackFormCreatedFromTemplate,\n payload: {\n type,\n origin,\n },\n });\n return proxy({\n key: ProxyMessages.CreateFormFromTemplate,\n payload: type,\n })\n .then(form => {\n setLoadState(LoadState.Idle);\n return form;\n })\n .catch(err => {\n setFormApiError(err);\n track({\n key: ProxyMessages.TrackFormCreationFailed,\n payload: {\n origin,\n },\n });\n setLoadState(LoadState.Failed);\n });\n };\n return {\n isCreating: loadState === LoadState.Loading,\n hasError: loadState === LoadState.Failed,\n formApiError,\n createFormByTemplate,\n reset: () => setLoadState(LoadState.Idle),\n };\n}\n","import { useState } from 'react';\nimport debounce from 'lodash/debounce';\nimport { usePostAsyncBackgroundMessage } from '../../../iframe/useBackgroundApp';\nimport { DEFAULT_OPTIONS } from '../../../constants/defaultFormOptions';\nimport { ProxyMessages } from '../../../iframe/integratedMessages';\nexport default function useForms() {\n const proxy = usePostAsyncBackgroundMessage();\n const [formApiError, setFormApiError] = useState(null);\n const search = debounce((search, callback) => {\n return proxy({\n key: ProxyMessages.FetchForms,\n payload: {\n search,\n },\n })\n .then(forms => {\n callback([\n ...forms.map((form) => ({\n label: form.name,\n value: form.guid,\n })),\n DEFAULT_OPTIONS,\n ]);\n })\n .catch(error => {\n setFormApiError(error);\n });\n }, 300, { trailing: true });\n return {\n search,\n formApiError,\n reset: () => setFormApiError(null),\n };\n}\n","import $ from 'jquery';\nimport { useEffect, useState } from 'react';\nimport { formsScript } from '../../../constants/leadinConfig';\nimport Raven from '../../../lib/Raven';\nlet promise;\nfunction loadFormsScript() {\n if (!promise) {\n promise = new Promise((resolve, reject) => $.getScript(formsScript)\n .done(resolve)\n .fail(reject));\n }\n return promise;\n}\nexport default function useFormScript() {\n const [ready, setReady] = useState(false);\n useEffect(() => {\n loadFormsScript()\n .then(() => setReady(true))\n .catch(error => Raven.captureException(error));\n }, []);\n return ready;\n}\n","import { jsx as _jsx, jsxs as _jsxs } from \"react/jsx-runtime\";\nimport { Fragment, useEffect } from 'react';\nimport LoadingBlock from '../Common/LoadingBlock';\nimport MeetingSelector from './MeetingSelector';\nimport MeetingWarning from './MeetingWarning';\nimport useMeetings, { useSelectedMeeting, useSelectedMeetingCalendar, } from './hooks/useMeetings';\nimport HubspotWrapper from '../Common/HubspotWrapper';\nimport ErrorHandler from '../Common/ErrorHandler';\nimport { pluginPath } from '../../constants/leadinConfig';\nimport { __ } from '@wordpress/i18n';\nimport Raven from 'raven-js';\nexport default function MeetingController({ handleChange, url, }) {\n const { mappedMeetings: meetings, loading, error, reload, connectCalendar, } = useMeetings();\n const selectedMeetingOption = useSelectedMeeting(url);\n const selectedMeetingCalendar = useSelectedMeetingCalendar(url);\n useEffect(() => {\n if (!url && meetings.length > 0) {\n handleChange(meetings[0].value);\n }\n }, [meetings, url, handleChange]);\n const handleLocalChange = (option) => {\n handleChange(option.value);\n };\n const handleConnectCalendar = () => {\n return connectCalendar()\n .then(() => {\n reload();\n })\n .catch(error => {\n Raven.captureMessage('Unable to connect calendar', {\n extra: { error },\n });\n });\n };\n return (_jsx(Fragment, { children: loading ? (_jsx(LoadingBlock, {})) : error ? (_jsx(ErrorHandler, { status: (error && error.status) || error, resetErrorState: () => reload(), errorInfo: {\n header: __('There was a problem retrieving your meetings', 'leadin'),\n message: __('Please refresh your meetings or try again in a few minutes', 'leadin'),\n action: __('Refresh meetings', 'leadin'),\n } })) : (_jsxs(HubspotWrapper, { padding: \"90px 32px 24px\", pluginPath: pluginPath, children: [selectedMeetingCalendar && (_jsx(MeetingWarning, { status: selectedMeetingCalendar, onConnectCalendar: handleConnectCalendar })), meetings.length > 1 && (_jsx(MeetingSelector, { onChange: handleLocalChange, options: meetings, value: selectedMeetingOption }))] })) }));\n}\n","import { jsx as _jsx, jsxs as _jsxs } from \"react/jsx-runtime\";\nimport { Fragment, useEffect } from 'react';\nimport MeetingController from './MeetingController';\nimport PreviewMeeting from './PreviewMeeting';\nimport { BackgroudAppContext, useBackgroundAppContext, usePostBackgroundMessage, } from '../../iframe/useBackgroundApp';\nimport { refreshToken } from '../../constants/leadinConfig';\nimport { ProxyMessages } from '../../iframe/integratedMessages';\nimport LoadingBlock from '../Common/LoadingBlock';\nimport { getOrCreateBackgroundApp } from '../../utils/backgroundAppUtils';\nfunction MeetingEdit({ attributes: { url }, isSelected, setAttributes, preview = true, origin = 'gutenberg', }) {\n const isBackgroundAppReady = useBackgroundAppContext();\n const monitorFormPreviewRender = usePostBackgroundMessage();\n const handleChange = (newUrl) => {\n setAttributes({\n url: newUrl,\n });\n };\n useEffect(() => {\n monitorFormPreviewRender({\n key: ProxyMessages.TrackMeetingPreviewRender,\n payload: {\n origin,\n },\n });\n }, [origin]);\n return !isBackgroundAppReady ? (_jsx(LoadingBlock, {})) : (_jsxs(Fragment, { children: [(isSelected || !url) && (_jsx(MeetingController, { url: url, handleChange: handleChange })), preview && url && _jsx(PreviewMeeting, { url: url })] }));\n}\nexport default function MeetingsEditContainer(props) {\n return (_jsx(BackgroudAppContext.Provider, { value: refreshToken && getOrCreateBackgroundApp(refreshToken), children: _jsx(MeetingEdit, { ...props }) }));\n}\n","import { jsx as _jsx, jsxs as _jsxs } from \"react/jsx-runtime\";\nimport { Fragment } from 'react';\nimport AsyncSelect from '../Common/AsyncSelect';\nimport UISpacer from '../UIComponents/UISpacer';\nimport { __ } from '@wordpress/i18n';\nexport default function MeetingSelector({ options, onChange, value, }) {\n const optionsWrapper = [\n {\n label: __('Meeting name', 'leadin'),\n options,\n },\n ];\n return (_jsxs(Fragment, { children: [_jsx(UISpacer, {}), _jsx(\"p\", { \"data-test-id\": \"leadin-meeting-select\", children: _jsx(\"b\", { children: __('Select a meeting scheduling page', 'leadin') }) }), _jsx(AsyncSelect, { defaultOptions: optionsWrapper, onChange: onChange, placeholder: __('Select a meeting', 'leadin'), value: value })] }));\n}\n","import { jsx as _jsx } from \"react/jsx-runtime\";\nimport UIAlert from '../UIComponents/UIAlert';\nimport UIButton from '../UIComponents/UIButton';\nimport { CURRENT_USER_CALENDAR_MISSING } from './constants';\nimport { __ } from '@wordpress/i18n';\nexport default function MeetingWarning({ status, onConnectCalendar, }) {\n const isMeetingOwner = status === CURRENT_USER_CALENDAR_MISSING;\n const titleText = isMeetingOwner\n ? __('Your calendar is not connected', 'leadin')\n : __('Calendar is not connected', 'leadin');\n const titleMessage = isMeetingOwner\n ? __('Please connect your calendar to activate your scheduling pages', 'leadin')\n : __('Make sure that everybody in this meeting has connected their calendar from the Meetings page in HubSpot', 'leadin');\n return (_jsx(UIAlert, { titleText: titleText, titleMessage: titleMessage, children: isMeetingOwner && (_jsx(UIButton, { use: \"tertiary\", id: \"meetings-connect-calendar\", onClick: onConnectCalendar, children: __('Connect calendar', 'leadin') })) }));\n}\n","import { jsx as _jsx } from \"react/jsx-runtime\";\nimport { Fragment, useEffect, useRef } from 'react';\nimport UIOverlay from '../UIComponents/UIOverlay';\nimport useMeetingsScript from './hooks/useMeetingsScript';\nexport default function PreviewForm({ url }) {\n const ready = useMeetingsScript();\n const inputEl = useRef(null);\n useEffect(() => {\n if (!ready) {\n return;\n }\n if (inputEl.current) {\n inputEl.current.innerHTML = '';\n const container = document.createElement('div');\n container.dataset.src = `${url}?embed=true`;\n container.classList.add('meetings-iframe-container');\n inputEl.current.appendChild(container);\n const embedScript = document.createElement('script');\n embedScript.innerHTML =\n 'hbspt.meetings.create(\".meetings-iframe-container\");';\n inputEl.current.appendChild(embedScript);\n }\n }, [url, ready, inputEl]);\n return _jsx(Fragment, { children: url && _jsx(UIOverlay, { ref: inputEl }) });\n}\n","export const OTHER_USER_CALENDAR_MISSING = 'OTHER_USER_CALENDAR_MISSING';\nexport const CURRENT_USER_CALENDAR_MISSING = 'CURRENT_USER_CALENDAR_MISSING';\n","import { useEffect, useState } from 'react';\nimport { usePostAsyncBackgroundMessage } from '../../../iframe/useBackgroundApp';\nimport LoadState from '../../enums/loadState';\nimport { ProxyMessages } from '../../../iframe/integratedMessages';\nlet user = null;\nexport default function useCurrentUserFetch() {\n const proxy = usePostAsyncBackgroundMessage();\n const [loadState, setLoadState] = useState(LoadState.NotLoaded);\n const [error, setError] = useState(null);\n const createUser = () => {\n if (!user) {\n setLoadState(LoadState.NotLoaded);\n }\n };\n const reload = () => {\n user = null;\n setLoadState(LoadState.NotLoaded);\n setError(null);\n };\n useEffect(() => {\n if (loadState === LoadState.NotLoaded && !user) {\n setLoadState(LoadState.Loading);\n proxy({\n key: ProxyMessages.FetchOrCreateMeetingUser,\n })\n .then(data => {\n user = data;\n setLoadState(LoadState.Idle);\n })\n .catch(err => {\n setError(err);\n setLoadState(LoadState.Failed);\n });\n }\n }, [loadState]);\n return { user, loadUserState: loadState, error, createUser, reload };\n}\n","import { useCallback } from 'react';\nimport { __ } from '@wordpress/i18n';\nimport { CURRENT_USER_CALENDAR_MISSING, OTHER_USER_CALENDAR_MISSING, } from '../constants';\nimport useMeetingsFetch from './useMeetingsFetch';\nimport useCurrentUserFetch from './useCurrentUserFetch';\nimport LoadState from '../../enums/loadState';\nimport { usePostAsyncBackgroundMessage } from '../../../iframe/useBackgroundApp';\nimport { ProxyMessages } from '../../../iframe/integratedMessages';\nfunction getDefaultMeetingName(meeting, currentUser, meetingUsers) {\n const [meetingOwnerId] = meeting.meetingsUserIds;\n let result = __('Default', 'leadin');\n if (currentUser &&\n meetingOwnerId !== currentUser.id &&\n meetingUsers[meetingOwnerId]) {\n const user = meetingUsers[meetingOwnerId];\n result += ` (${user.userProfile.fullName})`;\n }\n return result;\n}\nfunction hasCalendarObject(user) {\n return (user &&\n user.meetingsUserBlob &&\n user.meetingsUserBlob.calendarSettings &&\n user.meetingsUserBlob.calendarSettings.email);\n}\nexport default function useMeetings() {\n const proxy = usePostAsyncBackgroundMessage();\n const { meetings, meetingUsers, error: meetingsError, loadMeetingsState, reload: reloadMeetings, } = useMeetingsFetch();\n const { user: currentUser, error: userError, loadUserState, reload: reloadUser, } = useCurrentUserFetch();\n const reload = useCallback(() => {\n reloadUser();\n reloadMeetings();\n }, [reloadUser, reloadMeetings]);\n const connectCalendar = () => {\n return proxy({\n key: ProxyMessages.ConnectMeetingsCalendar,\n });\n };\n return {\n mappedMeetings: meetings.map(meet => ({\n label: meet.name || getDefaultMeetingName(meet, currentUser, meetingUsers),\n value: meet.link,\n })),\n meetings,\n meetingUsers,\n currentUser,\n error: meetingsError || userError,\n loading: loadMeetingsState == LoadState.Loading ||\n loadUserState === LoadState.Loading,\n reload,\n connectCalendar,\n };\n}\nexport function useSelectedMeeting(url) {\n const { mappedMeetings: meetings } = useMeetings();\n const option = meetings.find(({ value }) => value === url);\n return option;\n}\nexport function useSelectedMeetingCalendar(url) {\n const { meetings, meetingUsers, currentUser } = useMeetings();\n const meeting = meetings.find(meet => meet.link === url);\n const mappedMeetingUsersId = meetingUsers.reduce((p, c) => ({ ...p, [c.id]: c }), {});\n if (!meeting) {\n return null;\n }\n else {\n const { meetingsUserIds } = meeting;\n if (currentUser &&\n meetingsUserIds.includes(currentUser.id) &&\n !hasCalendarObject(currentUser)) {\n return CURRENT_USER_CALENDAR_MISSING;\n }\n else if (meetingsUserIds\n .map(id => mappedMeetingUsersId[id])\n .some((user) => !hasCalendarObject(user))) {\n return OTHER_USER_CALENDAR_MISSING;\n }\n else {\n return null;\n }\n }\n}\n","import { useEffect, useState } from 'react';\nimport { usePostAsyncBackgroundMessage } from '../../../iframe/useBackgroundApp';\nimport LoadState from '../../enums/loadState';\nimport { ProxyMessages } from '../../../iframe/integratedMessages';\nlet meetings = [];\nlet meetingUsers = [];\nexport default function useMeetingsFetch() {\n const proxy = usePostAsyncBackgroundMessage();\n const [loadState, setLoadState] = useState(LoadState.NotLoaded);\n const [error, setError] = useState(null);\n const reload = () => {\n meetings = [];\n setError(null);\n setLoadState(LoadState.NotLoaded);\n };\n useEffect(() => {\n if (loadState === LoadState.NotLoaded && meetings.length === 0) {\n setLoadState(LoadState.Loading);\n proxy({\n key: ProxyMessages.FetchMeetingsAndUsers,\n })\n .then(data => {\n setLoadState(LoadState.Loaded);\n meetings = data && data.meetingLinks;\n meetingUsers = data && data.meetingUsers;\n })\n .catch(e => {\n setError(e);\n setLoadState(LoadState.Failed);\n });\n }\n }, [loadState]);\n return {\n meetings,\n meetingUsers,\n loadMeetingsState: loadState,\n error,\n reload,\n };\n}\n","import $ from 'jquery';\nimport { useState, useEffect } from 'react';\nimport { meetingsScript } from '../../../constants/leadinConfig';\nimport Raven from '../../../lib/Raven';\nlet promise;\nfunction loadMeetingsScript() {\n if (!promise) {\n promise = new Promise((resolve, reject) => $.getScript(meetingsScript)\n .done(resolve)\n .fail(reject));\n }\n return promise;\n}\nexport default function useMeetingsScript() {\n const [ready, setReady] = useState(false);\n useEffect(() => {\n loadMeetingsScript()\n .then(() => setReady(true))\n .catch(error => Raven.captureException(error));\n }, []);\n return ready;\n}\n","import { jsx as _jsx, jsxs as _jsxs } from \"react/jsx-runtime\";\nimport { styled } from '@linaria/react';\nimport { MARIGOLD_LIGHT, MARIGOLD_MEDIUM, OBSIDIAN } from './colors';\nconst AlertContainer = styled.div `\n background-color: ${MARIGOLD_LIGHT};\n border-color: ${MARIGOLD_MEDIUM};\n color: ${OBSIDIAN};\n font-size: 14px;\n align-items: center;\n justify-content: space-between;\n display: flex;\n border-style: solid;\n border-top-style: solid;\n border-right-style: solid;\n border-bottom-style: solid;\n border-left-style: solid;\n border-width: 1px;\n min-height: 60px;\n padding: 8px 20px;\n position: relative;\n text-align: left;\n`;\nconst Title = styled.p `\n font-family: 'Lexend Deca';\n font-style: normal;\n font-weight: 700;\n font-size: 16px;\n line-height: 19px;\n color: ${OBSIDIAN};\n margin: 0;\n padding: 0;\n`;\nconst Message = styled.p `\n font-family: 'Lexend Deca';\n font-style: normal;\n font-weight: 400;\n font-size: 14px;\n margin: 0;\n padding: 0;\n`;\nconst MessageContainer = styled.div `\n display: flex;\n flex-direction: column;\n`;\nexport default function UIAlert({ titleText, titleMessage, children, }) {\n return (_jsxs(AlertContainer, { children: [_jsxs(MessageContainer, { children: [_jsx(Title, { children: titleText }), _jsx(Message, { children: titleMessage })] }), children] }));\n}\n","import { styled } from '@linaria/react';\nimport { HEFFALUMP, LORAX, OLAF } from './colors';\nexport default styled.button `\n background-color:${props => (props.use === 'tertiary' ? HEFFALUMP : LORAX)};\n border: 3px solid ${props => (props.use === 'tertiary' ? HEFFALUMP : LORAX)};\n color: ${OLAF}\n border-radius: 3px;\n font-size: 14px;\n line-height: 14px;\n padding: 12px 24px;\n font-family: 'Lexend Deca', Helvetica, Arial, sans-serif;\n font-weight: 500;\n white-space: nowrap;\n`;\n","import { styled } from '@linaria/react';\nexport default styled.div `\n text-align: ${props => (props.textAlign ? props.textAlign : 'inherit')};\n`;\n","import { styled } from '@linaria/react';\nexport default styled.div `\n position: relative;\n\n &:after {\n content: '';\n position: absolute;\n top: 0;\n bottom: 0;\n right: 0;\n left: 0;\n }\n`;\n","import { styled } from '@linaria/react';\nexport default styled.div `\n height: 30px;\n`;\n","import { jsx as _jsx, jsxs as _jsxs } from \"react/jsx-runtime\";\nimport { styled } from '@linaria/react';\nimport { CALYPSO_MEDIUM, CALYPSO } from './colors';\nconst SpinnerOuter = styled.div `\n align-items: center;\n color: #00a4bd;\n display: flex;\n flex-direction: column;\n justify-content: center;\n width: 100%;\n height: 100%;\n margin: '2px';\n`;\nconst SpinnerInner = styled.div `\n align-items: center;\n display: flex;\n justify-content: center;\n width: 100%;\n height: 100%;\n`;\nconst Circle = styled.circle `\n fill: none;\n stroke: ${props => props.color};\n stroke-width: 5;\n stroke-linecap: round;\n transform-origin: center;\n`;\nconst AnimatedCircle = styled.circle `\n fill: none;\n stroke: ${props => props.color};\n stroke-width: 5;\n stroke-linecap: round;\n transform-origin: center;\n animation: dashAnimation 2s ease-in-out infinite,\n spinAnimation 2s linear infinite;\n\n @keyframes dashAnimation {\n 0% {\n stroke-dasharray: 1, 150;\n stroke-dashoffset: 0;\n }\n\n 50% {\n stroke-dasharray: 90, 150;\n stroke-dashoffset: -50;\n }\n\n 100% {\n stroke-dasharray: 90, 150;\n stroke-dashoffset: -140;\n }\n }\n\n @keyframes spinAnimation {\n transform: rotate(360deg);\n }\n`;\nexport default function UISpinner({ size = 20 }) {\n return (_jsx(SpinnerOuter, { children: _jsx(SpinnerInner, { children: _jsxs(\"svg\", { height: size, width: size, viewBox: \"0 0 50 50\", children: [_jsx(Circle, { color: CALYPSO_MEDIUM, cx: \"25\", cy: \"25\", r: \"22.5\" }), _jsx(AnimatedCircle, { color: CALYPSO, cx: \"25\", cy: \"25\", r: \"22.5\" })] }) }) }));\n}\n","export const CALYPSO = '#00a4bd';\nexport const CALYPSO_MEDIUM = '#7fd1de';\nexport const CALYPSO_LIGHT = '#e5f5f8';\nexport const LORAX = '#ff7a59';\nexport const OLAF = '#ffffff';\nexport const HEFFALUMP = '#425b76';\nexport const MARIGOLD_LIGHT = '#fef8f0';\nexport const MARIGOLD_MEDIUM = '#fae0b5';\nexport const OBSIDIAN = '#33475b';\n","const ConnectionStatus = {\n Connected: 'Connected',\n NotConnected: 'NotConnected',\n};\nexport default ConnectionStatus;\n","const LoadState = {\n NotLoaded: 'NotLoaded',\n Loading: 'Loading',\n Loaded: 'Loaded',\n Idle: 'Idle',\n Failed: 'Failed',\n};\nexport default LoadState;\n","import $ from 'jquery';\nimport Raven, { configureRaven } from '../lib/Raven';\nexport function initApp(initFn) {\n configureRaven();\n Raven.context(initFn);\n}\nexport function initAppOnReady(initFn) {\n function main() {\n $(initFn);\n }\n initApp(main);\n}\n","import { deviceId, hubspotBaseUrl, locale, portalId, } from '../constants/leadinConfig';\nimport { initApp } from './appUtils';\nexport function initBackgroundApp(initFn) {\n function main() {\n if (Array.isArray(initFn)) {\n initFn.forEach(callback => callback());\n }\n else {\n initFn();\n }\n }\n initApp(main);\n}\nexport const getOrCreateBackgroundApp = (refreshToken) => {\n if (window.LeadinBackgroundApp) {\n return window.LeadinBackgroundApp;\n }\n const { IntegratedAppEmbedder, IntegratedAppOptions } = window;\n const options = new IntegratedAppOptions()\n .setLocale(locale)\n .setDeviceId(deviceId)\n .setRefreshToken(refreshToken);\n const embedder = new IntegratedAppEmbedder('integrated-plugin-proxy', portalId, hubspotBaseUrl, () => { }).setOptions(options);\n embedder.attachTo(document.body, false);\n embedder.postStartAppMessage(); // lets the app know all all data has been passed to it\n window.LeadinBackgroundApp = embedder;\n return window.LeadinBackgroundApp;\n};\n","var root = require('./_root');\n\n/** Built-in value references. */\nvar Symbol = root.Symbol;\n\nmodule.exports = Symbol;\n","var Symbol = require('./_Symbol'),\n getRawTag = require('./_getRawTag'),\n objectToString = require('./_objectToString');\n\n/** `Object#toString` result references. */\nvar nullTag = '[object Null]',\n undefinedTag = '[object Undefined]';\n\n/** Built-in value references. */\nvar symToStringTag = Symbol ? Symbol.toStringTag : undefined;\n\n/**\n * The base implementation of `getTag` without fallbacks for buggy environments.\n *\n * @private\n * @param {*} value The value to query.\n * @returns {string} Returns the `toStringTag`.\n */\nfunction baseGetTag(value) {\n if (value == null) {\n return value === undefined ? undefinedTag : nullTag;\n }\n return (symToStringTag && symToStringTag in Object(value))\n ? getRawTag(value)\n : objectToString(value);\n}\n\nmodule.exports = baseGetTag;\n","var trimmedEndIndex = require('./_trimmedEndIndex');\n\n/** Used to match leading whitespace. */\nvar reTrimStart = /^\\s+/;\n\n/**\n * The base implementation of `_.trim`.\n *\n * @private\n * @param {string} string The string to trim.\n * @returns {string} Returns the trimmed string.\n */\nfunction baseTrim(string) {\n return string\n ? string.slice(0, trimmedEndIndex(string) + 1).replace(reTrimStart, '')\n : string;\n}\n\nmodule.exports = baseTrim;\n","/** Detect free variable `global` from Node.js. */\nvar freeGlobal = typeof global == 'object' && global && global.Object === Object && global;\n\nmodule.exports = freeGlobal;\n","var Symbol = require('./_Symbol');\n\n/** Used for built-in method references. */\nvar objectProto = Object.prototype;\n\n/** Used to check objects for own properties. */\nvar hasOwnProperty = objectProto.hasOwnProperty;\n\n/**\n * Used to resolve the\n * [`toStringTag`](http://ecma-international.org/ecma-262/7.0/#sec-object.prototype.tostring)\n * of values.\n */\nvar nativeObjectToString = objectProto.toString;\n\n/** Built-in value references. */\nvar symToStringTag = Symbol ? Symbol.toStringTag : undefined;\n\n/**\n * A specialized version of `baseGetTag` which ignores `Symbol.toStringTag` values.\n *\n * @private\n * @param {*} value The value to query.\n * @returns {string} Returns the raw `toStringTag`.\n */\nfunction getRawTag(value) {\n var isOwn = hasOwnProperty.call(value, symToStringTag),\n tag = value[symToStringTag];\n\n try {\n value[symToStringTag] = undefined;\n var unmasked = true;\n } catch (e) {}\n\n var result = nativeObjectToString.call(value);\n if (unmasked) {\n if (isOwn) {\n value[symToStringTag] = tag;\n } else {\n delete value[symToStringTag];\n }\n }\n return result;\n}\n\nmodule.exports = getRawTag;\n","/** Used for built-in method references. */\nvar objectProto = Object.prototype;\n\n/**\n * Used to resolve the\n * [`toStringTag`](http://ecma-international.org/ecma-262/7.0/#sec-object.prototype.tostring)\n * of values.\n */\nvar nativeObjectToString = objectProto.toString;\n\n/**\n * Converts `value` to a string using `Object.prototype.toString`.\n *\n * @private\n * @param {*} value The value to convert.\n * @returns {string} Returns the converted string.\n */\nfunction objectToString(value) {\n return nativeObjectToString.call(value);\n}\n\nmodule.exports = objectToString;\n","var freeGlobal = require('./_freeGlobal');\n\n/** Detect free variable `self`. */\nvar freeSelf = typeof self == 'object' && self && self.Object === Object && self;\n\n/** Used as a reference to the global object. */\nvar root = freeGlobal || freeSelf || Function('return this')();\n\nmodule.exports = root;\n","/** Used to match a single whitespace character. */\nvar reWhitespace = /\\s/;\n\n/**\n * Used by `_.trim` and `_.trimEnd` to get the index of the last non-whitespace\n * character of `string`.\n *\n * @private\n * @param {string} string The string to inspect.\n * @returns {number} Returns the index of the last non-whitespace character.\n */\nfunction trimmedEndIndex(string) {\n var index = string.length;\n\n while (index-- && reWhitespace.test(string.charAt(index))) {}\n return index;\n}\n\nmodule.exports = trimmedEndIndex;\n","var isObject = require('./isObject'),\n now = require('./now'),\n toNumber = require('./toNumber');\n\n/** Error message constants. */\nvar FUNC_ERROR_TEXT = 'Expected a function';\n\n/* Built-in method references for those with the same name as other `lodash` methods. */\nvar nativeMax = Math.max,\n nativeMin = Math.min;\n\n/**\n * Creates a debounced function that delays invoking `func` until after `wait`\n * milliseconds have elapsed since the last time the debounced function was\n * invoked. The debounced function comes with a `cancel` method to cancel\n * delayed `func` invocations and a `flush` method to immediately invoke them.\n * Provide `options` to indicate whether `func` should be invoked on the\n * leading and/or trailing edge of the `wait` timeout. The `func` is invoked\n * with the last arguments provided to the debounced function. Subsequent\n * calls to the debounced function return the result of the last `func`\n * invocation.\n *\n * **Note:** If `leading` and `trailing` options are `true`, `func` is\n * invoked on the trailing edge of the timeout only if the debounced function\n * is invoked more than once during the `wait` timeout.\n *\n * If `wait` is `0` and `leading` is `false`, `func` invocation is deferred\n * until to the next tick, similar to `setTimeout` with a timeout of `0`.\n *\n * See [David Corbacho's article](https://css-tricks.com/debouncing-throttling-explained-examples/)\n * for details over the differences between `_.debounce` and `_.throttle`.\n *\n * @static\n * @memberOf _\n * @since 0.1.0\n * @category Function\n * @param {Function} func The function to debounce.\n * @param {number} [wait=0] The number of milliseconds to delay.\n * @param {Object} [options={}] The options object.\n * @param {boolean} [options.leading=false]\n * Specify invoking on the leading edge of the timeout.\n * @param {number} [options.maxWait]\n * The maximum time `func` is allowed to be delayed before it's invoked.\n * @param {boolean} [options.trailing=true]\n * Specify invoking on the trailing edge of the timeout.\n * @returns {Function} Returns the new debounced function.\n * @example\n *\n * // Avoid costly calculations while the window size is in flux.\n * jQuery(window).on('resize', _.debounce(calculateLayout, 150));\n *\n * // Invoke `sendMail` when clicked, debouncing subsequent calls.\n * jQuery(element).on('click', _.debounce(sendMail, 300, {\n * 'leading': true,\n * 'trailing': false\n * }));\n *\n * // Ensure `batchLog` is invoked once after 1 second of debounced calls.\n * var debounced = _.debounce(batchLog, 250, { 'maxWait': 1000 });\n * var source = new EventSource('/stream');\n * jQuery(source).on('message', debounced);\n *\n * // Cancel the trailing debounced invocation.\n * jQuery(window).on('popstate', debounced.cancel);\n */\nfunction debounce(func, wait, options) {\n var lastArgs,\n lastThis,\n maxWait,\n result,\n timerId,\n lastCallTime,\n lastInvokeTime = 0,\n leading = false,\n maxing = false,\n trailing = true;\n\n if (typeof func != 'function') {\n throw new TypeError(FUNC_ERROR_TEXT);\n }\n wait = toNumber(wait) || 0;\n if (isObject(options)) {\n leading = !!options.leading;\n maxing = 'maxWait' in options;\n maxWait = maxing ? nativeMax(toNumber(options.maxWait) || 0, wait) : maxWait;\n trailing = 'trailing' in options ? !!options.trailing : trailing;\n }\n\n function invokeFunc(time) {\n var args = lastArgs,\n thisArg = lastThis;\n\n lastArgs = lastThis = undefined;\n lastInvokeTime = time;\n result = func.apply(thisArg, args);\n return result;\n }\n\n function leadingEdge(time) {\n // Reset any `maxWait` timer.\n lastInvokeTime = time;\n // Start the timer for the trailing edge.\n timerId = setTimeout(timerExpired, wait);\n // Invoke the leading edge.\n return leading ? invokeFunc(time) : result;\n }\n\n function remainingWait(time) {\n var timeSinceLastCall = time - lastCallTime,\n timeSinceLastInvoke = time - lastInvokeTime,\n timeWaiting = wait - timeSinceLastCall;\n\n return maxing\n ? nativeMin(timeWaiting, maxWait - timeSinceLastInvoke)\n : timeWaiting;\n }\n\n function shouldInvoke(time) {\n var timeSinceLastCall = time - lastCallTime,\n timeSinceLastInvoke = time - lastInvokeTime;\n\n // Either this is the first call, activity has stopped and we're at the\n // trailing edge, the system time has gone backwards and we're treating\n // it as the trailing edge, or we've hit the `maxWait` limit.\n return (lastCallTime === undefined || (timeSinceLastCall >= wait) ||\n (timeSinceLastCall < 0) || (maxing && timeSinceLastInvoke >= maxWait));\n }\n\n function timerExpired() {\n var time = now();\n if (shouldInvoke(time)) {\n return trailingEdge(time);\n }\n // Restart the timer.\n timerId = setTimeout(timerExpired, remainingWait(time));\n }\n\n function trailingEdge(time) {\n timerId = undefined;\n\n // Only invoke if we have `lastArgs` which means `func` has been\n // debounced at least once.\n if (trailing && lastArgs) {\n return invokeFunc(time);\n }\n lastArgs = lastThis = undefined;\n return result;\n }\n\n function cancel() {\n if (timerId !== undefined) {\n clearTimeout(timerId);\n }\n lastInvokeTime = 0;\n lastArgs = lastCallTime = lastThis = timerId = undefined;\n }\n\n function flush() {\n return timerId === undefined ? result : trailingEdge(now());\n }\n\n function debounced() {\n var time = now(),\n isInvoking = shouldInvoke(time);\n\n lastArgs = arguments;\n lastThis = this;\n lastCallTime = time;\n\n if (isInvoking) {\n if (timerId === undefined) {\n return leadingEdge(lastCallTime);\n }\n if (maxing) {\n // Handle invocations in a tight loop.\n clearTimeout(timerId);\n timerId = setTimeout(timerExpired, wait);\n return invokeFunc(lastCallTime);\n }\n }\n if (timerId === undefined) {\n timerId = setTimeout(timerExpired, wait);\n }\n return result;\n }\n debounced.cancel = cancel;\n debounced.flush = flush;\n return debounced;\n}\n\nmodule.exports = debounce;\n","/**\n * Checks if `value` is the\n * [language type](http://www.ecma-international.org/ecma-262/7.0/#sec-ecmascript-language-types)\n * of `Object`. (e.g. arrays, functions, objects, regexes, `new Number(0)`, and `new String('')`)\n *\n * @static\n * @memberOf _\n * @since 0.1.0\n * @category Lang\n * @param {*} value The value to check.\n * @returns {boolean} Returns `true` if `value` is an object, else `false`.\n * @example\n *\n * _.isObject({});\n * // => true\n *\n * _.isObject([1, 2, 3]);\n * // => true\n *\n * _.isObject(_.noop);\n * // => true\n *\n * _.isObject(null);\n * // => false\n */\nfunction isObject(value) {\n var type = typeof value;\n return value != null && (type == 'object' || type == 'function');\n}\n\nmodule.exports = isObject;\n","/**\n * Checks if `value` is object-like. A value is object-like if it's not `null`\n * and has a `typeof` result of \"object\".\n *\n * @static\n * @memberOf _\n * @since 4.0.0\n * @category Lang\n * @param {*} value The value to check.\n * @returns {boolean} Returns `true` if `value` is object-like, else `false`.\n * @example\n *\n * _.isObjectLike({});\n * // => true\n *\n * _.isObjectLike([1, 2, 3]);\n * // => true\n *\n * _.isObjectLike(_.noop);\n * // => false\n *\n * _.isObjectLike(null);\n * // => false\n */\nfunction isObjectLike(value) {\n return value != null && typeof value == 'object';\n}\n\nmodule.exports = isObjectLike;\n","var baseGetTag = require('./_baseGetTag'),\n isObjectLike = require('./isObjectLike');\n\n/** `Object#toString` result references. */\nvar symbolTag = '[object Symbol]';\n\n/**\n * Checks if `value` is classified as a `Symbol` primitive or object.\n *\n * @static\n * @memberOf _\n * @since 4.0.0\n * @category Lang\n * @param {*} value The value to check.\n * @returns {boolean} Returns `true` if `value` is a symbol, else `false`.\n * @example\n *\n * _.isSymbol(Symbol.iterator);\n * // => true\n *\n * _.isSymbol('abc');\n * // => false\n */\nfunction isSymbol(value) {\n return typeof value == 'symbol' ||\n (isObjectLike(value) && baseGetTag(value) == symbolTag);\n}\n\nmodule.exports = isSymbol;\n","var root = require('./_root');\n\n/**\n * Gets the timestamp of the number of milliseconds that have elapsed since\n * the Unix epoch (1 January 1970 00:00:00 UTC).\n *\n * @static\n * @memberOf _\n * @since 2.4.0\n * @category Date\n * @returns {number} Returns the timestamp.\n * @example\n *\n * _.defer(function(stamp) {\n * console.log(_.now() - stamp);\n * }, _.now());\n * // => Logs the number of milliseconds it took for the deferred invocation.\n */\nvar now = function() {\n return root.Date.now();\n};\n\nmodule.exports = now;\n","var baseTrim = require('./_baseTrim'),\n isObject = require('./isObject'),\n isSymbol = require('./isSymbol');\n\n/** Used as references for various `Number` constants. */\nvar NAN = 0 / 0;\n\n/** Used to detect bad signed hexadecimal string values. */\nvar reIsBadHex = /^[-+]0x[0-9a-f]+$/i;\n\n/** Used to detect binary string values. */\nvar reIsBinary = /^0b[01]+$/i;\n\n/** Used to detect octal string values. */\nvar reIsOctal = /^0o[0-7]+$/i;\n\n/** Built-in method references without a dependency on `root`. */\nvar freeParseInt = parseInt;\n\n/**\n * Converts `value` to a number.\n *\n * @static\n * @memberOf _\n * @since 4.0.0\n * @category Lang\n * @param {*} value The value to process.\n * @returns {number} Returns the number.\n * @example\n *\n * _.toNumber(3.2);\n * // => 3.2\n *\n * _.toNumber(Number.MIN_VALUE);\n * // => 5e-324\n *\n * _.toNumber(Infinity);\n * // => Infinity\n *\n * _.toNumber('3.2');\n * // => 3.2\n */\nfunction toNumber(value) {\n if (typeof value == 'number') {\n return value;\n }\n if (isSymbol(value)) {\n return NAN;\n }\n if (isObject(value)) {\n var other = typeof value.valueOf == 'function' ? value.valueOf() : value;\n value = isObject(other) ? (other + '') : other;\n }\n if (typeof value != 'string') {\n return value === 0 ? value : +value;\n }\n value = baseTrim(value);\n var isBinary = reIsBinary.test(value);\n return (isBinary || reIsOctal.test(value))\n ? freeParseInt(value.slice(2), isBinary ? 2 : 8)\n : (reIsBadHex.test(value) ? NAN : +value);\n}\n\nmodule.exports = toNumber;\n","// extracted by mini-css-extract-plugin\nexport {};","// extracted by mini-css-extract-plugin\nexport {};","// extracted by mini-css-extract-plugin\nexport {};","// extracted by mini-css-extract-plugin\nexport {};","// extracted by mini-css-extract-plugin\nexport {};","// extracted by mini-css-extract-plugin\nexport {};","// extracted by mini-css-extract-plugin\nexport {};","// extracted by mini-css-extract-plugin\nexport {};","// extracted by mini-css-extract-plugin\nexport {};","// extracted by mini-css-extract-plugin\nexport {};","/*\nobject-assign\n(c) Sindre Sorhus\n@license MIT\n*/\n\n'use strict';\n/* eslint-disable no-unused-vars */\nvar getOwnPropertySymbols = Object.getOwnPropertySymbols;\nvar hasOwnProperty = Object.prototype.hasOwnProperty;\nvar propIsEnumerable = Object.prototype.propertyIsEnumerable;\n\nfunction toObject(val) {\n\tif (val === null || val === undefined) {\n\t\tthrow new TypeError('Object.assign cannot be called with null or undefined');\n\t}\n\n\treturn Object(val);\n}\n\nfunction shouldUseNative() {\n\ttry {\n\t\tif (!Object.assign) {\n\t\t\treturn false;\n\t\t}\n\n\t\t// Detect buggy property enumeration order in older V8 versions.\n\n\t\t// https://bugs.chromium.org/p/v8/issues/detail?id=4118\n\t\tvar test1 = new String('abc'); // eslint-disable-line no-new-wrappers\n\t\ttest1[5] = 'de';\n\t\tif (Object.getOwnPropertyNames(test1)[0] === '5') {\n\t\t\treturn false;\n\t\t}\n\n\t\t// https://bugs.chromium.org/p/v8/issues/detail?id=3056\n\t\tvar test2 = {};\n\t\tfor (var i = 0; i < 10; i++) {\n\t\t\ttest2['_' + String.fromCharCode(i)] = i;\n\t\t}\n\t\tvar order2 = Object.getOwnPropertyNames(test2).map(function (n) {\n\t\t\treturn test2[n];\n\t\t});\n\t\tif (order2.join('') !== '0123456789') {\n\t\t\treturn false;\n\t\t}\n\n\t\t// https://bugs.chromium.org/p/v8/issues/detail?id=3056\n\t\tvar test3 = {};\n\t\t'abcdefghijklmnopqrst'.split('').forEach(function (letter) {\n\t\t\ttest3[letter] = letter;\n\t\t});\n\t\tif (Object.keys(Object.assign({}, test3)).join('') !==\n\t\t\t\t'abcdefghijklmnopqrst') {\n\t\t\treturn false;\n\t\t}\n\n\t\treturn true;\n\t} catch (err) {\n\t\t// We don't expect any of the above to throw, but better to be safe.\n\t\treturn false;\n\t}\n}\n\nmodule.exports = shouldUseNative() ? Object.assign : function (target, source) {\n\tvar from;\n\tvar to = toObject(target);\n\tvar symbols;\n\n\tfor (var s = 1; s < arguments.length; s++) {\n\t\tfrom = Object(arguments[s]);\n\n\t\tfor (var key in from) {\n\t\t\tif (hasOwnProperty.call(from, key)) {\n\t\t\t\tto[key] = from[key];\n\t\t\t}\n\t\t}\n\n\t\tif (getOwnPropertySymbols) {\n\t\t\tsymbols = getOwnPropertySymbols(from);\n\t\t\tfor (var i = 0; i < symbols.length; i++) {\n\t\t\t\tif (propIsEnumerable.call(from, symbols[i])) {\n\t\t\t\t\tto[symbols[i]] = from[symbols[i]];\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\treturn to;\n};\n","function RavenConfigError(message) {\n this.name = 'RavenConfigError';\n this.message = message;\n}\nRavenConfigError.prototype = new Error();\nRavenConfigError.prototype.constructor = RavenConfigError;\n\nmodule.exports = RavenConfigError;\n","var wrapMethod = function(console, level, callback) {\n var originalConsoleLevel = console[level];\n var originalConsole = console;\n\n if (!(level in console)) {\n return;\n }\n\n var sentryLevel = level === 'warn' ? 'warning' : level;\n\n console[level] = function() {\n var args = [].slice.call(arguments);\n\n var msg = '' + args.join(' ');\n var data = {level: sentryLevel, logger: 'console', extra: {arguments: args}};\n\n if (level === 'assert') {\n if (args[0] === false) {\n // Default browsers message\n msg = 'Assertion failed: ' + (args.slice(1).join(' ') || 'console.assert');\n data.extra.arguments = args.slice(1);\n callback && callback(msg, data);\n }\n } else {\n callback && callback(msg, data);\n }\n\n // this fails for some browsers. :(\n if (originalConsoleLevel) {\n // IE9 doesn't allow calling apply on console functions directly\n // See: https://stackoverflow.com/questions/5472938/does-ie9-support-console-log-and-is-it-a-real-function#answer-5473193\n Function.prototype.apply.call(originalConsoleLevel, originalConsole, args);\n }\n };\n};\n\nmodule.exports = {\n wrapMethod: wrapMethod\n};\n","/*global XDomainRequest:false */\n\nvar TraceKit = require('../vendor/TraceKit/tracekit');\nvar stringify = require('../vendor/json-stringify-safe/stringify');\nvar RavenConfigError = require('./configError');\n\nvar utils = require('./utils');\nvar isError = utils.isError;\nvar isObject = utils.isObject;\nvar isObject = utils.isObject;\nvar isErrorEvent = utils.isErrorEvent;\nvar isUndefined = utils.isUndefined;\nvar isFunction = utils.isFunction;\nvar isString = utils.isString;\nvar isEmptyObject = utils.isEmptyObject;\nvar each = utils.each;\nvar objectMerge = utils.objectMerge;\nvar truncate = utils.truncate;\nvar objectFrozen = utils.objectFrozen;\nvar hasKey = utils.hasKey;\nvar joinRegExp = utils.joinRegExp;\nvar urlencode = utils.urlencode;\nvar uuid4 = utils.uuid4;\nvar htmlTreeAsString = utils.htmlTreeAsString;\nvar isSameException = utils.isSameException;\nvar isSameStacktrace = utils.isSameStacktrace;\nvar parseUrl = utils.parseUrl;\nvar fill = utils.fill;\n\nvar wrapConsoleMethod = require('./console').wrapMethod;\n\nvar dsnKeys = 'source protocol user pass host port path'.split(' '),\n dsnPattern = /^(?:(\\w+):)?\\/\\/(?:(\\w+)(:\\w+)?@)?([\\w\\.-]+)(?::(\\d+))?(\\/.*)/;\n\nfunction now() {\n return +new Date();\n}\n\n// This is to be defensive in environments where window does not exist (see https://github.com/getsentry/raven-js/pull/785)\nvar _window =\n typeof window !== 'undefined'\n ? window\n : typeof global !== 'undefined' ? global : typeof self !== 'undefined' ? self : {};\nvar _document = _window.document;\nvar _navigator = _window.navigator;\n\nfunction keepOriginalCallback(original, callback) {\n return isFunction(callback)\n ? function(data) {\n return callback(data, original);\n }\n : callback;\n}\n\n// First, check for JSON support\n// If there is no JSON, we no-op the core features of Raven\n// since JSON is required to encode the payload\nfunction Raven() {\n this._hasJSON = !!(typeof JSON === 'object' && JSON.stringify);\n // Raven can run in contexts where there's no document (react-native)\n this._hasDocument = !isUndefined(_document);\n this._hasNavigator = !isUndefined(_navigator);\n this._lastCapturedException = null;\n this._lastData = null;\n this._lastEventId = null;\n this._globalServer = null;\n this._globalKey = null;\n this._globalProject = null;\n this._globalContext = {};\n this._globalOptions = {\n logger: 'javascript',\n ignoreErrors: [],\n ignoreUrls: [],\n whitelistUrls: [],\n includePaths: [],\n collectWindowErrors: true,\n maxMessageLength: 0,\n\n // By default, truncates URL values to 250 chars\n maxUrlLength: 250,\n stackTraceLimit: 50,\n autoBreadcrumbs: true,\n instrument: true,\n sampleRate: 1\n };\n this._ignoreOnError = 0;\n this._isRavenInstalled = false;\n this._originalErrorStackTraceLimit = Error.stackTraceLimit;\n // capture references to window.console *and* all its methods first\n // before the console plugin has a chance to monkey patch\n this._originalConsole = _window.console || {};\n this._originalConsoleMethods = {};\n this._plugins = [];\n this._startTime = now();\n this._wrappedBuiltIns = [];\n this._breadcrumbs = [];\n this._lastCapturedEvent = null;\n this._keypressTimeout;\n this._location = _window.location;\n this._lastHref = this._location && this._location.href;\n this._resetBackoff();\n\n // eslint-disable-next-line guard-for-in\n for (var method in this._originalConsole) {\n this._originalConsoleMethods[method] = this._originalConsole[method];\n }\n}\n\n/*\n * The core Raven singleton\n *\n * @this {Raven}\n */\n\nRaven.prototype = {\n // Hardcode version string so that raven source can be loaded directly via\n // webpack (using a build step causes webpack #1617). Grunt verifies that\n // this value matches package.json during build.\n // See: https://github.com/getsentry/raven-js/issues/465\n VERSION: '3.19.1',\n\n debug: false,\n\n TraceKit: TraceKit, // alias to TraceKit\n\n /*\n * Configure Raven with a DSN and extra options\n *\n * @param {string} dsn The public Sentry DSN\n * @param {object} options Set of global options [optional]\n * @return {Raven}\n */\n config: function(dsn, options) {\n var self = this;\n\n if (self._globalServer) {\n this._logDebug('error', 'Error: Raven has already been configured');\n return self;\n }\n if (!dsn) return self;\n\n var globalOptions = self._globalOptions;\n\n // merge in options\n if (options) {\n each(options, function(key, value) {\n // tags and extra are special and need to be put into context\n if (key === 'tags' || key === 'extra' || key === 'user') {\n self._globalContext[key] = value;\n } else {\n globalOptions[key] = value;\n }\n });\n }\n\n self.setDSN(dsn);\n\n // \"Script error.\" is hard coded into browsers for errors that it can't read.\n // this is the result of a script being pulled in from an external domain and CORS.\n globalOptions.ignoreErrors.push(/^Script error\\.?$/);\n globalOptions.ignoreErrors.push(/^Javascript error: Script error\\.? on line 0$/);\n\n // join regexp rules into one big rule\n globalOptions.ignoreErrors = joinRegExp(globalOptions.ignoreErrors);\n globalOptions.ignoreUrls = globalOptions.ignoreUrls.length\n ? joinRegExp(globalOptions.ignoreUrls)\n : false;\n globalOptions.whitelistUrls = globalOptions.whitelistUrls.length\n ? joinRegExp(globalOptions.whitelistUrls)\n : false;\n globalOptions.includePaths = joinRegExp(globalOptions.includePaths);\n globalOptions.maxBreadcrumbs = Math.max(\n 0,\n Math.min(globalOptions.maxBreadcrumbs || 100, 100)\n ); // default and hard limit is 100\n\n var autoBreadcrumbDefaults = {\n xhr: true,\n console: true,\n dom: true,\n location: true\n };\n\n var autoBreadcrumbs = globalOptions.autoBreadcrumbs;\n if ({}.toString.call(autoBreadcrumbs) === '[object Object]') {\n autoBreadcrumbs = objectMerge(autoBreadcrumbDefaults, autoBreadcrumbs);\n } else if (autoBreadcrumbs !== false) {\n autoBreadcrumbs = autoBreadcrumbDefaults;\n }\n globalOptions.autoBreadcrumbs = autoBreadcrumbs;\n\n var instrumentDefaults = {\n tryCatch: true\n };\n\n var instrument = globalOptions.instrument;\n if ({}.toString.call(instrument) === '[object Object]') {\n instrument = objectMerge(instrumentDefaults, instrument);\n } else if (instrument !== false) {\n instrument = instrumentDefaults;\n }\n globalOptions.instrument = instrument;\n\n TraceKit.collectWindowErrors = !!globalOptions.collectWindowErrors;\n\n // return for chaining\n return self;\n },\n\n /*\n * Installs a global window.onerror error handler\n * to capture and report uncaught exceptions.\n * At this point, install() is required to be called due\n * to the way TraceKit is set up.\n *\n * @return {Raven}\n */\n install: function() {\n var self = this;\n if (self.isSetup() && !self._isRavenInstalled) {\n TraceKit.report.subscribe(function() {\n self._handleOnErrorStackInfo.apply(self, arguments);\n });\n if (self._globalOptions.instrument && self._globalOptions.instrument.tryCatch) {\n self._instrumentTryCatch();\n }\n\n if (self._globalOptions.autoBreadcrumbs) self._instrumentBreadcrumbs();\n\n // Install all of the plugins\n self._drainPlugins();\n\n self._isRavenInstalled = true;\n }\n\n Error.stackTraceLimit = self._globalOptions.stackTraceLimit;\n return this;\n },\n\n /*\n * Set the DSN (can be called multiple time unlike config)\n *\n * @param {string} dsn The public Sentry DSN\n */\n setDSN: function(dsn) {\n var self = this,\n uri = self._parseDSN(dsn),\n lastSlash = uri.path.lastIndexOf('/'),\n path = uri.path.substr(1, lastSlash);\n\n self._dsn = dsn;\n self._globalKey = uri.user;\n self._globalSecret = uri.pass && uri.pass.substr(1);\n self._globalProject = uri.path.substr(lastSlash + 1);\n\n self._globalServer = self._getGlobalServer(uri);\n\n self._globalEndpoint =\n self._globalServer + '/' + path + 'api/' + self._globalProject + '/store/';\n\n // Reset backoff state since we may be pointing at a\n // new project/server\n this._resetBackoff();\n },\n\n /*\n * Wrap code within a context so Raven can capture errors\n * reliably across domains that is executed immediately.\n *\n * @param {object} options A specific set of options for this context [optional]\n * @param {function} func The callback to be immediately executed within the context\n * @param {array} args An array of arguments to be called with the callback [optional]\n */\n context: function(options, func, args) {\n if (isFunction(options)) {\n args = func || [];\n func = options;\n options = undefined;\n }\n\n return this.wrap(options, func).apply(this, args);\n },\n\n /*\n * Wrap code within a context and returns back a new function to be executed\n *\n * @param {object} options A specific set of options for this context [optional]\n * @param {function} func The function to be wrapped in a new context\n * @param {function} func A function to call before the try/catch wrapper [optional, private]\n * @return {function} The newly wrapped functions with a context\n */\n wrap: function(options, func, _before) {\n var self = this;\n // 1 argument has been passed, and it's not a function\n // so just return it\n if (isUndefined(func) && !isFunction(options)) {\n return options;\n }\n\n // options is optional\n if (isFunction(options)) {\n func = options;\n options = undefined;\n }\n\n // At this point, we've passed along 2 arguments, and the second one\n // is not a function either, so we'll just return the second argument.\n if (!isFunction(func)) {\n return func;\n }\n\n // We don't wanna wrap it twice!\n try {\n if (func.__raven__) {\n return func;\n }\n\n // If this has already been wrapped in the past, return that\n if (func.__raven_wrapper__) {\n return func.__raven_wrapper__;\n }\n } catch (e) {\n // Just accessing custom props in some Selenium environments\n // can cause a \"Permission denied\" exception (see raven-js#495).\n // Bail on wrapping and return the function as-is (defers to window.onerror).\n return func;\n }\n\n function wrapped() {\n var args = [],\n i = arguments.length,\n deep = !options || (options && options.deep !== false);\n\n if (_before && isFunction(_before)) {\n _before.apply(this, arguments);\n }\n\n // Recursively wrap all of a function's arguments that are\n // functions themselves.\n while (i--) args[i] = deep ? self.wrap(options, arguments[i]) : arguments[i];\n\n try {\n // Attempt to invoke user-land function\n // NOTE: If you are a Sentry user, and you are seeing this stack frame, it\n // means Raven caught an error invoking your application code. This is\n // expected behavior and NOT indicative of a bug with Raven.js.\n return func.apply(this, args);\n } catch (e) {\n self._ignoreNextOnError();\n self.captureException(e, options);\n throw e;\n }\n }\n\n // copy over properties of the old function\n for (var property in func) {\n if (hasKey(func, property)) {\n wrapped[property] = func[property];\n }\n }\n wrapped.prototype = func.prototype;\n\n func.__raven_wrapper__ = wrapped;\n // Signal that this function has been wrapped already\n // for both debugging and to prevent it to being wrapped twice\n wrapped.__raven__ = true;\n wrapped.__inner__ = func;\n\n return wrapped;\n },\n\n /*\n * Uninstalls the global error handler.\n *\n * @return {Raven}\n */\n uninstall: function() {\n TraceKit.report.uninstall();\n\n this._restoreBuiltIns();\n\n Error.stackTraceLimit = this._originalErrorStackTraceLimit;\n this._isRavenInstalled = false;\n\n return this;\n },\n\n /*\n * Manually capture an exception and send it over to Sentry\n *\n * @param {error} ex An exception to be logged\n * @param {object} options A specific set of options for this error [optional]\n * @return {Raven}\n */\n captureException: function(ex, options) {\n // Cases for sending ex as a message, rather than an exception\n var isNotError = !isError(ex);\n var isNotErrorEvent = !isErrorEvent(ex);\n var isErrorEventWithoutError = isErrorEvent(ex) && !ex.error;\n\n if ((isNotError && isNotErrorEvent) || isErrorEventWithoutError) {\n return this.captureMessage(\n ex,\n objectMerge(\n {\n trimHeadFrames: 1,\n stacktrace: true // if we fall back to captureMessage, default to attempting a new trace\n },\n options\n )\n );\n }\n\n // Get actual Error from ErrorEvent\n if (isErrorEvent(ex)) ex = ex.error;\n\n // Store the raw exception object for potential debugging and introspection\n this._lastCapturedException = ex;\n\n // TraceKit.report will re-raise any exception passed to it,\n // which means you have to wrap it in try/catch. Instead, we\n // can wrap it here and only re-raise if TraceKit.report\n // raises an exception different from the one we asked to\n // report on.\n try {\n var stack = TraceKit.computeStackTrace(ex);\n this._handleStackInfo(stack, options);\n } catch (ex1) {\n if (ex !== ex1) {\n throw ex1;\n }\n }\n\n return this;\n },\n\n /*\n * Manually send a message to Sentry\n *\n * @param {string} msg A plain message to be captured in Sentry\n * @param {object} options A specific set of options for this message [optional]\n * @return {Raven}\n */\n captureMessage: function(msg, options) {\n // config() automagically converts ignoreErrors from a list to a RegExp so we need to test for an\n // early call; we'll error on the side of logging anything called before configuration since it's\n // probably something you should see:\n if (\n !!this._globalOptions.ignoreErrors.test &&\n this._globalOptions.ignoreErrors.test(msg)\n ) {\n return;\n }\n\n options = options || {};\n\n var data = objectMerge(\n {\n message: msg + '' // Make sure it's actually a string\n },\n options\n );\n\n var ex;\n // Generate a \"synthetic\" stack trace from this point.\n // NOTE: If you are a Sentry user, and you are seeing this stack frame, it is NOT indicative\n // of a bug with Raven.js. Sentry generates synthetic traces either by configuration,\n // or if it catches a thrown object without a \"stack\" property.\n try {\n throw new Error(msg);\n } catch (ex1) {\n ex = ex1;\n }\n\n // null exception name so `Error` isn't prefixed to msg\n ex.name = null;\n var stack = TraceKit.computeStackTrace(ex);\n\n // stack[0] is `throw new Error(msg)` call itself, we are interested in the frame that was just before that, stack[1]\n var initialCall = stack.stack[1];\n\n var fileurl = (initialCall && initialCall.url) || '';\n\n if (\n !!this._globalOptions.ignoreUrls.test &&\n this._globalOptions.ignoreUrls.test(fileurl)\n ) {\n return;\n }\n\n if (\n !!this._globalOptions.whitelistUrls.test &&\n !this._globalOptions.whitelistUrls.test(fileurl)\n ) {\n return;\n }\n\n if (this._globalOptions.stacktrace || (options && options.stacktrace)) {\n options = objectMerge(\n {\n // fingerprint on msg, not stack trace (legacy behavior, could be\n // revisited)\n fingerprint: msg,\n // since we know this is a synthetic trace, the top N-most frames\n // MUST be from Raven.js, so mark them as in_app later by setting\n // trimHeadFrames\n trimHeadFrames: (options.trimHeadFrames || 0) + 1\n },\n options\n );\n\n var frames = this._prepareFrames(stack, options);\n data.stacktrace = {\n // Sentry expects frames oldest to newest\n frames: frames.reverse()\n };\n }\n\n // Fire away!\n this._send(data);\n\n return this;\n },\n\n captureBreadcrumb: function(obj) {\n var crumb = objectMerge(\n {\n timestamp: now() / 1000\n },\n obj\n );\n\n if (isFunction(this._globalOptions.breadcrumbCallback)) {\n var result = this._globalOptions.breadcrumbCallback(crumb);\n\n if (isObject(result) && !isEmptyObject(result)) {\n crumb = result;\n } else if (result === false) {\n return this;\n }\n }\n\n this._breadcrumbs.push(crumb);\n if (this._breadcrumbs.length > this._globalOptions.maxBreadcrumbs) {\n this._breadcrumbs.shift();\n }\n return this;\n },\n\n addPlugin: function(plugin /*arg1, arg2, ... argN*/) {\n var pluginArgs = [].slice.call(arguments, 1);\n\n this._plugins.push([plugin, pluginArgs]);\n if (this._isRavenInstalled) {\n this._drainPlugins();\n }\n\n return this;\n },\n\n /*\n * Set/clear a user to be sent along with the payload.\n *\n * @param {object} user An object representing user data [optional]\n * @return {Raven}\n */\n setUserContext: function(user) {\n // Intentionally do not merge here since that's an unexpected behavior.\n this._globalContext.user = user;\n\n return this;\n },\n\n /*\n * Merge extra attributes to be sent along with the payload.\n *\n * @param {object} extra An object representing extra data [optional]\n * @return {Raven}\n */\n setExtraContext: function(extra) {\n this._mergeContext('extra', extra);\n\n return this;\n },\n\n /*\n * Merge tags to be sent along with the payload.\n *\n * @param {object} tags An object representing tags [optional]\n * @return {Raven}\n */\n setTagsContext: function(tags) {\n this._mergeContext('tags', tags);\n\n return this;\n },\n\n /*\n * Clear all of the context.\n *\n * @return {Raven}\n */\n clearContext: function() {\n this._globalContext = {};\n\n return this;\n },\n\n /*\n * Get a copy of the current context. This cannot be mutated.\n *\n * @return {object} copy of context\n */\n getContext: function() {\n // lol javascript\n return JSON.parse(stringify(this._globalContext));\n },\n\n /*\n * Set environment of application\n *\n * @param {string} environment Typically something like 'production'.\n * @return {Raven}\n */\n setEnvironment: function(environment) {\n this._globalOptions.environment = environment;\n\n return this;\n },\n\n /*\n * Set release version of application\n *\n * @param {string} release Typically something like a git SHA to identify version\n * @return {Raven}\n */\n setRelease: function(release) {\n this._globalOptions.release = release;\n\n return this;\n },\n\n /*\n * Set the dataCallback option\n *\n * @param {function} callback The callback to run which allows the\n * data blob to be mutated before sending\n * @return {Raven}\n */\n setDataCallback: function(callback) {\n var original = this._globalOptions.dataCallback;\n this._globalOptions.dataCallback = keepOriginalCallback(original, callback);\n return this;\n },\n\n /*\n * Set the breadcrumbCallback option\n *\n * @param {function} callback The callback to run which allows filtering\n * or mutating breadcrumbs\n * @return {Raven}\n */\n setBreadcrumbCallback: function(callback) {\n var original = this._globalOptions.breadcrumbCallback;\n this._globalOptions.breadcrumbCallback = keepOriginalCallback(original, callback);\n return this;\n },\n\n /*\n * Set the shouldSendCallback option\n *\n * @param {function} callback The callback to run which allows\n * introspecting the blob before sending\n * @return {Raven}\n */\n setShouldSendCallback: function(callback) {\n var original = this._globalOptions.shouldSendCallback;\n this._globalOptions.shouldSendCallback = keepOriginalCallback(original, callback);\n return this;\n },\n\n /**\n * Override the default HTTP transport mechanism that transmits data\n * to the Sentry server.\n *\n * @param {function} transport Function invoked instead of the default\n * `makeRequest` handler.\n *\n * @return {Raven}\n */\n setTransport: function(transport) {\n this._globalOptions.transport = transport;\n\n return this;\n },\n\n /*\n * Get the latest raw exception that was captured by Raven.\n *\n * @return {error}\n */\n lastException: function() {\n return this._lastCapturedException;\n },\n\n /*\n * Get the last event id\n *\n * @return {string}\n */\n lastEventId: function() {\n return this._lastEventId;\n },\n\n /*\n * Determine if Raven is setup and ready to go.\n *\n * @return {boolean}\n */\n isSetup: function() {\n if (!this._hasJSON) return false; // needs JSON support\n if (!this._globalServer) {\n if (!this.ravenNotConfiguredError) {\n this.ravenNotConfiguredError = true;\n this._logDebug('error', 'Error: Raven has not been configured.');\n }\n return false;\n }\n return true;\n },\n\n afterLoad: function() {\n // TODO: remove window dependence?\n\n // Attempt to initialize Raven on load\n var RavenConfig = _window.RavenConfig;\n if (RavenConfig) {\n this.config(RavenConfig.dsn, RavenConfig.config).install();\n }\n },\n\n showReportDialog: function(options) {\n if (\n !_document // doesn't work without a document (React native)\n )\n return;\n\n options = options || {};\n\n var lastEventId = options.eventId || this.lastEventId();\n if (!lastEventId) {\n throw new RavenConfigError('Missing eventId');\n }\n\n var dsn = options.dsn || this._dsn;\n if (!dsn) {\n throw new RavenConfigError('Missing DSN');\n }\n\n var encode = encodeURIComponent;\n var qs = '';\n qs += '?eventId=' + encode(lastEventId);\n qs += '&dsn=' + encode(dsn);\n\n var user = options.user || this._globalContext.user;\n if (user) {\n if (user.name) qs += '&name=' + encode(user.name);\n if (user.email) qs += '&email=' + encode(user.email);\n }\n\n var globalServer = this._getGlobalServer(this._parseDSN(dsn));\n\n var script = _document.createElement('script');\n script.async = true;\n script.src = globalServer + '/api/embed/error-page/' + qs;\n (_document.head || _document.body).appendChild(script);\n },\n\n /**** Private functions ****/\n _ignoreNextOnError: function() {\n var self = this;\n this._ignoreOnError += 1;\n setTimeout(function() {\n // onerror should trigger before setTimeout\n self._ignoreOnError -= 1;\n });\n },\n\n _triggerEvent: function(eventType, options) {\n // NOTE: `event` is a native browser thing, so let's avoid conflicting wiht it\n var evt, key;\n\n if (!this._hasDocument) return;\n\n options = options || {};\n\n eventType = 'raven' + eventType.substr(0, 1).toUpperCase() + eventType.substr(1);\n\n if (_document.createEvent) {\n evt = _document.createEvent('HTMLEvents');\n evt.initEvent(eventType, true, true);\n } else {\n evt = _document.createEventObject();\n evt.eventType = eventType;\n }\n\n for (key in options)\n if (hasKey(options, key)) {\n evt[key] = options[key];\n }\n\n if (_document.createEvent) {\n // IE9 if standards\n _document.dispatchEvent(evt);\n } else {\n // IE8 regardless of Quirks or Standards\n // IE9 if quirks\n try {\n _document.fireEvent('on' + evt.eventType.toLowerCase(), evt);\n } catch (e) {\n // Do nothing\n }\n }\n },\n\n /**\n * Wraps addEventListener to capture UI breadcrumbs\n * @param evtName the event name (e.g. \"click\")\n * @returns {Function}\n * @private\n */\n _breadcrumbEventHandler: function(evtName) {\n var self = this;\n return function(evt) {\n // reset keypress timeout; e.g. triggering a 'click' after\n // a 'keypress' will reset the keypress debounce so that a new\n // set of keypresses can be recorded\n self._keypressTimeout = null;\n\n // It's possible this handler might trigger multiple times for the same\n // event (e.g. event propagation through node ancestors). Ignore if we've\n // already captured the event.\n if (self._lastCapturedEvent === evt) return;\n\n self._lastCapturedEvent = evt;\n\n // try/catch both:\n // - accessing evt.target (see getsentry/raven-js#838, #768)\n // - `htmlTreeAsString` because it's complex, and just accessing the DOM incorrectly\n // can throw an exception in some circumstances.\n var target;\n try {\n target = htmlTreeAsString(evt.target);\n } catch (e) {\n target = '';\n }\n\n self.captureBreadcrumb({\n category: 'ui.' + evtName, // e.g. ui.click, ui.input\n message: target\n });\n };\n },\n\n /**\n * Wraps addEventListener to capture keypress UI events\n * @returns {Function}\n * @private\n */\n _keypressEventHandler: function() {\n var self = this,\n debounceDuration = 1000; // milliseconds\n\n // TODO: if somehow user switches keypress target before\n // debounce timeout is triggered, we will only capture\n // a single breadcrumb from the FIRST target (acceptable?)\n return function(evt) {\n var target;\n try {\n target = evt.target;\n } catch (e) {\n // just accessing event properties can throw an exception in some rare circumstances\n // see: https://github.com/getsentry/raven-js/issues/838\n return;\n }\n var tagName = target && target.tagName;\n\n // only consider keypress events on actual input elements\n // this will disregard keypresses targeting body (e.g. tabbing\n // through elements, hotkeys, etc)\n if (\n !tagName ||\n (tagName !== 'INPUT' && tagName !== 'TEXTAREA' && !target.isContentEditable)\n )\n return;\n\n // record first keypress in a series, but ignore subsequent\n // keypresses until debounce clears\n var timeout = self._keypressTimeout;\n if (!timeout) {\n self._breadcrumbEventHandler('input')(evt);\n }\n clearTimeout(timeout);\n self._keypressTimeout = setTimeout(function() {\n self._keypressTimeout = null;\n }, debounceDuration);\n };\n },\n\n /**\n * Captures a breadcrumb of type \"navigation\", normalizing input URLs\n * @param to the originating URL\n * @param from the target URL\n * @private\n */\n _captureUrlChange: function(from, to) {\n var parsedLoc = parseUrl(this._location.href);\n var parsedTo = parseUrl(to);\n var parsedFrom = parseUrl(from);\n\n // because onpopstate only tells you the \"new\" (to) value of location.href, and\n // not the previous (from) value, we need to track the value of the current URL\n // state ourselves\n this._lastHref = to;\n\n // Use only the path component of the URL if the URL matches the current\n // document (almost all the time when using pushState)\n if (parsedLoc.protocol === parsedTo.protocol && parsedLoc.host === parsedTo.host)\n to = parsedTo.relative;\n if (parsedLoc.protocol === parsedFrom.protocol && parsedLoc.host === parsedFrom.host)\n from = parsedFrom.relative;\n\n this.captureBreadcrumb({\n category: 'navigation',\n data: {\n to: to,\n from: from\n }\n });\n },\n\n /**\n * Wrap timer functions and event targets to catch errors and provide\n * better metadata.\n */\n _instrumentTryCatch: function() {\n var self = this;\n\n var wrappedBuiltIns = self._wrappedBuiltIns;\n\n function wrapTimeFn(orig) {\n return function(fn, t) {\n // preserve arity\n // Make a copy of the arguments to prevent deoptimization\n // https://github.com/petkaantonov/bluebird/wiki/Optimization-killers#32-leaking-arguments\n var args = new Array(arguments.length);\n for (var i = 0; i < args.length; ++i) {\n args[i] = arguments[i];\n }\n var originalCallback = args[0];\n if (isFunction(originalCallback)) {\n args[0] = self.wrap(originalCallback);\n }\n\n // IE < 9 doesn't support .call/.apply on setInterval/setTimeout, but it\n // also supports only two arguments and doesn't care what this is, so we\n // can just call the original function directly.\n if (orig.apply) {\n return orig.apply(this, args);\n } else {\n return orig(args[0], args[1]);\n }\n };\n }\n\n var autoBreadcrumbs = this._globalOptions.autoBreadcrumbs;\n\n function wrapEventTarget(global) {\n var proto = _window[global] && _window[global].prototype;\n if (proto && proto.hasOwnProperty && proto.hasOwnProperty('addEventListener')) {\n fill(\n proto,\n 'addEventListener',\n function(orig) {\n return function(evtName, fn, capture, secure) {\n // preserve arity\n try {\n if (fn && fn.handleEvent) {\n fn.handleEvent = self.wrap(fn.handleEvent);\n }\n } catch (err) {\n // can sometimes get 'Permission denied to access property \"handle Event'\n }\n\n // More breadcrumb DOM capture ... done here and not in `_instrumentBreadcrumbs`\n // so that we don't have more than one wrapper function\n var before, clickHandler, keypressHandler;\n\n if (\n autoBreadcrumbs &&\n autoBreadcrumbs.dom &&\n (global === 'EventTarget' || global === 'Node')\n ) {\n // NOTE: generating multiple handlers per addEventListener invocation, should\n // revisit and verify we can just use one (almost certainly)\n clickHandler = self._breadcrumbEventHandler('click');\n keypressHandler = self._keypressEventHandler();\n before = function(evt) {\n // need to intercept every DOM event in `before` argument, in case that\n // same wrapped method is re-used for different events (e.g. mousemove THEN click)\n // see #724\n if (!evt) return;\n\n var eventType;\n try {\n eventType = evt.type;\n } catch (e) {\n // just accessing event properties can throw an exception in some rare circumstances\n // see: https://github.com/getsentry/raven-js/issues/838\n return;\n }\n if (eventType === 'click') return clickHandler(evt);\n else if (eventType === 'keypress') return keypressHandler(evt);\n };\n }\n return orig.call(\n this,\n evtName,\n self.wrap(fn, undefined, before),\n capture,\n secure\n );\n };\n },\n wrappedBuiltIns\n );\n fill(\n proto,\n 'removeEventListener',\n function(orig) {\n return function(evt, fn, capture, secure) {\n try {\n fn = fn && (fn.__raven_wrapper__ ? fn.__raven_wrapper__ : fn);\n } catch (e) {\n // ignore, accessing __raven_wrapper__ will throw in some Selenium environments\n }\n return orig.call(this, evt, fn, capture, secure);\n };\n },\n wrappedBuiltIns\n );\n }\n }\n\n fill(_window, 'setTimeout', wrapTimeFn, wrappedBuiltIns);\n fill(_window, 'setInterval', wrapTimeFn, wrappedBuiltIns);\n if (_window.requestAnimationFrame) {\n fill(\n _window,\n 'requestAnimationFrame',\n function(orig) {\n return function(cb) {\n return orig(self.wrap(cb));\n };\n },\n wrappedBuiltIns\n );\n }\n\n // event targets borrowed from bugsnag-js:\n // https://github.com/bugsnag/bugsnag-js/blob/master/src/bugsnag.js#L666\n var eventTargets = [\n 'EventTarget',\n 'Window',\n 'Node',\n 'ApplicationCache',\n 'AudioTrackList',\n 'ChannelMergerNode',\n 'CryptoOperation',\n 'EventSource',\n 'FileReader',\n 'HTMLUnknownElement',\n 'IDBDatabase',\n 'IDBRequest',\n 'IDBTransaction',\n 'KeyOperation',\n 'MediaController',\n 'MessagePort',\n 'ModalWindow',\n 'Notification',\n 'SVGElementInstance',\n 'Screen',\n 'TextTrack',\n 'TextTrackCue',\n 'TextTrackList',\n 'WebSocket',\n 'WebSocketWorker',\n 'Worker',\n 'XMLHttpRequest',\n 'XMLHttpRequestEventTarget',\n 'XMLHttpRequestUpload'\n ];\n for (var i = 0; i < eventTargets.length; i++) {\n wrapEventTarget(eventTargets[i]);\n }\n },\n\n /**\n * Instrument browser built-ins w/ breadcrumb capturing\n * - XMLHttpRequests\n * - DOM interactions (click/typing)\n * - window.location changes\n * - console\n *\n * Can be disabled or individually configured via the `autoBreadcrumbs` config option\n */\n _instrumentBreadcrumbs: function() {\n var self = this;\n var autoBreadcrumbs = this._globalOptions.autoBreadcrumbs;\n\n var wrappedBuiltIns = self._wrappedBuiltIns;\n\n function wrapProp(prop, xhr) {\n if (prop in xhr && isFunction(xhr[prop])) {\n fill(xhr, prop, function(orig) {\n return self.wrap(orig);\n }); // intentionally don't track filled methods on XHR instances\n }\n }\n\n if (autoBreadcrumbs.xhr && 'XMLHttpRequest' in _window) {\n var xhrproto = XMLHttpRequest.prototype;\n fill(\n xhrproto,\n 'open',\n function(origOpen) {\n return function(method, url) {\n // preserve arity\n\n // if Sentry key appears in URL, don't capture\n if (isString(url) && url.indexOf(self._globalKey) === -1) {\n this.__raven_xhr = {\n method: method,\n url: url,\n status_code: null\n };\n }\n\n return origOpen.apply(this, arguments);\n };\n },\n wrappedBuiltIns\n );\n\n fill(\n xhrproto,\n 'send',\n function(origSend) {\n return function(data) {\n // preserve arity\n var xhr = this;\n\n function onreadystatechangeHandler() {\n if (xhr.__raven_xhr && xhr.readyState === 4) {\n try {\n // touching statusCode in some platforms throws\n // an exception\n xhr.__raven_xhr.status_code = xhr.status;\n } catch (e) {\n /* do nothing */\n }\n\n self.captureBreadcrumb({\n type: 'http',\n category: 'xhr',\n data: xhr.__raven_xhr\n });\n }\n }\n\n var props = ['onload', 'onerror', 'onprogress'];\n for (var j = 0; j < props.length; j++) {\n wrapProp(props[j], xhr);\n }\n\n if ('onreadystatechange' in xhr && isFunction(xhr.onreadystatechange)) {\n fill(\n xhr,\n 'onreadystatechange',\n function(orig) {\n return self.wrap(orig, undefined, onreadystatechangeHandler);\n } /* intentionally don't track this instrumentation */\n );\n } else {\n // if onreadystatechange wasn't actually set by the page on this xhr, we\n // are free to set our own and capture the breadcrumb\n xhr.onreadystatechange = onreadystatechangeHandler;\n }\n\n return origSend.apply(this, arguments);\n };\n },\n wrappedBuiltIns\n );\n }\n\n if (autoBreadcrumbs.xhr && 'fetch' in _window) {\n fill(\n _window,\n 'fetch',\n function(origFetch) {\n return function(fn, t) {\n // preserve arity\n // Make a copy of the arguments to prevent deoptimization\n // https://github.com/petkaantonov/bluebird/wiki/Optimization-killers#32-leaking-arguments\n var args = new Array(arguments.length);\n for (var i = 0; i < args.length; ++i) {\n args[i] = arguments[i];\n }\n\n var fetchInput = args[0];\n var method = 'GET';\n var url;\n\n if (typeof fetchInput === 'string') {\n url = fetchInput;\n } else if ('Request' in _window && fetchInput instanceof _window.Request) {\n url = fetchInput.url;\n if (fetchInput.method) {\n method = fetchInput.method;\n }\n } else {\n url = '' + fetchInput;\n }\n\n if (args[1] && args[1].method) {\n method = args[1].method;\n }\n\n var fetchData = {\n method: method,\n url: url,\n status_code: null\n };\n\n self.captureBreadcrumb({\n type: 'http',\n category: 'fetch',\n data: fetchData\n });\n\n return origFetch.apply(this, args).then(function(response) {\n fetchData.status_code = response.status;\n\n return response;\n });\n };\n },\n wrappedBuiltIns\n );\n }\n\n // Capture breadcrumbs from any click that is unhandled / bubbled up all the way\n // to the document. Do this before we instrument addEventListener.\n if (autoBreadcrumbs.dom && this._hasDocument) {\n if (_document.addEventListener) {\n _document.addEventListener('click', self._breadcrumbEventHandler('click'), false);\n _document.addEventListener('keypress', self._keypressEventHandler(), false);\n } else {\n // IE8 Compatibility\n _document.attachEvent('onclick', self._breadcrumbEventHandler('click'));\n _document.attachEvent('onkeypress', self._keypressEventHandler());\n }\n }\n\n // record navigation (URL) changes\n // NOTE: in Chrome App environment, touching history.pushState, *even inside\n // a try/catch block*, will cause Chrome to output an error to console.error\n // borrowed from: https://github.com/angular/angular.js/pull/13945/files\n var chrome = _window.chrome;\n var isChromePackagedApp = chrome && chrome.app && chrome.app.runtime;\n var hasPushAndReplaceState =\n !isChromePackagedApp &&\n _window.history &&\n history.pushState &&\n history.replaceState;\n if (autoBreadcrumbs.location && hasPushAndReplaceState) {\n // TODO: remove onpopstate handler on uninstall()\n var oldOnPopState = _window.onpopstate;\n _window.onpopstate = function() {\n var currentHref = self._location.href;\n self._captureUrlChange(self._lastHref, currentHref);\n\n if (oldOnPopState) {\n return oldOnPopState.apply(this, arguments);\n }\n };\n\n var historyReplacementFunction = function(origHistFunction) {\n // note history.pushState.length is 0; intentionally not declaring\n // params to preserve 0 arity\n return function(/* state, title, url */) {\n var url = arguments.length > 2 ? arguments[2] : undefined;\n\n // url argument is optional\n if (url) {\n // coerce to string (this is what pushState does)\n self._captureUrlChange(self._lastHref, url + '');\n }\n\n return origHistFunction.apply(this, arguments);\n };\n };\n\n fill(history, 'pushState', historyReplacementFunction, wrappedBuiltIns);\n fill(history, 'replaceState', historyReplacementFunction, wrappedBuiltIns);\n }\n\n if (autoBreadcrumbs.console && 'console' in _window && console.log) {\n // console\n var consoleMethodCallback = function(msg, data) {\n self.captureBreadcrumb({\n message: msg,\n level: data.level,\n category: 'console'\n });\n };\n\n each(['debug', 'info', 'warn', 'error', 'log'], function(_, level) {\n wrapConsoleMethod(console, level, consoleMethodCallback);\n });\n }\n },\n\n _restoreBuiltIns: function() {\n // restore any wrapped builtins\n var builtin;\n while (this._wrappedBuiltIns.length) {\n builtin = this._wrappedBuiltIns.shift();\n\n var obj = builtin[0],\n name = builtin[1],\n orig = builtin[2];\n\n obj[name] = orig;\n }\n },\n\n _drainPlugins: function() {\n var self = this;\n\n // FIX ME TODO\n each(this._plugins, function(_, plugin) {\n var installer = plugin[0];\n var args = plugin[1];\n installer.apply(self, [self].concat(args));\n });\n },\n\n _parseDSN: function(str) {\n var m = dsnPattern.exec(str),\n dsn = {},\n i = 7;\n\n try {\n while (i--) dsn[dsnKeys[i]] = m[i] || '';\n } catch (e) {\n throw new RavenConfigError('Invalid DSN: ' + str);\n }\n\n if (dsn.pass && !this._globalOptions.allowSecretKey) {\n throw new RavenConfigError(\n 'Do not specify your secret key in the DSN. See: http://bit.ly/raven-secret-key'\n );\n }\n\n return dsn;\n },\n\n _getGlobalServer: function(uri) {\n // assemble the endpoint from the uri pieces\n var globalServer = '//' + uri.host + (uri.port ? ':' + uri.port : '');\n\n if (uri.protocol) {\n globalServer = uri.protocol + ':' + globalServer;\n }\n return globalServer;\n },\n\n _handleOnErrorStackInfo: function() {\n // if we are intentionally ignoring errors via onerror, bail out\n if (!this._ignoreOnError) {\n this._handleStackInfo.apply(this, arguments);\n }\n },\n\n _handleStackInfo: function(stackInfo, options) {\n var frames = this._prepareFrames(stackInfo, options);\n\n this._triggerEvent('handle', {\n stackInfo: stackInfo,\n options: options\n });\n\n this._processException(\n stackInfo.name,\n stackInfo.message,\n stackInfo.url,\n stackInfo.lineno,\n frames,\n options\n );\n },\n\n _prepareFrames: function(stackInfo, options) {\n var self = this;\n var frames = [];\n if (stackInfo.stack && stackInfo.stack.length) {\n each(stackInfo.stack, function(i, stack) {\n var frame = self._normalizeFrame(stack, stackInfo.url);\n if (frame) {\n frames.push(frame);\n }\n });\n\n // e.g. frames captured via captureMessage throw\n if (options && options.trimHeadFrames) {\n for (var j = 0; j < options.trimHeadFrames && j < frames.length; j++) {\n frames[j].in_app = false;\n }\n }\n }\n frames = frames.slice(0, this._globalOptions.stackTraceLimit);\n return frames;\n },\n\n _normalizeFrame: function(frame, stackInfoUrl) {\n // normalize the frames data\n var normalized = {\n filename: frame.url,\n lineno: frame.line,\n colno: frame.column,\n function: frame.func || '?'\n };\n\n // Case when we don't have any information about the error\n // E.g. throwing a string or raw object, instead of an `Error` in Firefox\n // Generating synthetic error doesn't add any value here\n //\n // We should probably somehow let a user know that they should fix their code\n if (!frame.url) {\n normalized.filename = stackInfoUrl; // fallback to whole stacks url from onerror handler\n }\n\n normalized.in_app = !// determine if an exception came from outside of our app\n // first we check the global includePaths list.\n (\n (!!this._globalOptions.includePaths.test &&\n !this._globalOptions.includePaths.test(normalized.filename)) ||\n // Now we check for fun, if the function name is Raven or TraceKit\n /(Raven|TraceKit)\\./.test(normalized['function']) ||\n // finally, we do a last ditch effort and check for raven.min.js\n /raven\\.(min\\.)?js$/.test(normalized.filename)\n );\n\n return normalized;\n },\n\n _processException: function(type, message, fileurl, lineno, frames, options) {\n var prefixedMessage = (type ? type + ': ' : '') + (message || '');\n if (\n !!this._globalOptions.ignoreErrors.test &&\n (this._globalOptions.ignoreErrors.test(message) ||\n this._globalOptions.ignoreErrors.test(prefixedMessage))\n ) {\n return;\n }\n\n var stacktrace;\n\n if (frames && frames.length) {\n fileurl = frames[0].filename || fileurl;\n // Sentry expects frames oldest to newest\n // and JS sends them as newest to oldest\n frames.reverse();\n stacktrace = {frames: frames};\n } else if (fileurl) {\n stacktrace = {\n frames: [\n {\n filename: fileurl,\n lineno: lineno,\n in_app: true\n }\n ]\n };\n }\n\n if (\n !!this._globalOptions.ignoreUrls.test &&\n this._globalOptions.ignoreUrls.test(fileurl)\n ) {\n return;\n }\n\n if (\n !!this._globalOptions.whitelistUrls.test &&\n !this._globalOptions.whitelistUrls.test(fileurl)\n ) {\n return;\n }\n\n var data = objectMerge(\n {\n // sentry.interfaces.Exception\n exception: {\n values: [\n {\n type: type,\n value: message,\n stacktrace: stacktrace\n }\n ]\n },\n culprit: fileurl\n },\n options\n );\n\n // Fire away!\n this._send(data);\n },\n\n _trimPacket: function(data) {\n // For now, we only want to truncate the two different messages\n // but this could/should be expanded to just trim everything\n var max = this._globalOptions.maxMessageLength;\n if (data.message) {\n data.message = truncate(data.message, max);\n }\n if (data.exception) {\n var exception = data.exception.values[0];\n exception.value = truncate(exception.value, max);\n }\n\n var request = data.request;\n if (request) {\n if (request.url) {\n request.url = truncate(request.url, this._globalOptions.maxUrlLength);\n }\n if (request.Referer) {\n request.Referer = truncate(request.Referer, this._globalOptions.maxUrlLength);\n }\n }\n\n if (data.breadcrumbs && data.breadcrumbs.values)\n this._trimBreadcrumbs(data.breadcrumbs);\n\n return data;\n },\n\n /**\n * Truncate breadcrumb values (right now just URLs)\n */\n _trimBreadcrumbs: function(breadcrumbs) {\n // known breadcrumb properties with urls\n // TODO: also consider arbitrary prop values that start with (https?)?://\n var urlProps = ['to', 'from', 'url'],\n urlProp,\n crumb,\n data;\n\n for (var i = 0; i < breadcrumbs.values.length; ++i) {\n crumb = breadcrumbs.values[i];\n if (\n !crumb.hasOwnProperty('data') ||\n !isObject(crumb.data) ||\n objectFrozen(crumb.data)\n )\n continue;\n\n data = objectMerge({}, crumb.data);\n for (var j = 0; j < urlProps.length; ++j) {\n urlProp = urlProps[j];\n if (data.hasOwnProperty(urlProp) && data[urlProp]) {\n data[urlProp] = truncate(data[urlProp], this._globalOptions.maxUrlLength);\n }\n }\n breadcrumbs.values[i].data = data;\n }\n },\n\n _getHttpData: function() {\n if (!this._hasNavigator && !this._hasDocument) return;\n var httpData = {};\n\n if (this._hasNavigator && _navigator.userAgent) {\n httpData.headers = {\n 'User-Agent': navigator.userAgent\n };\n }\n\n if (this._hasDocument) {\n if (_document.location && _document.location.href) {\n httpData.url = _document.location.href;\n }\n if (_document.referrer) {\n if (!httpData.headers) httpData.headers = {};\n httpData.headers.Referer = _document.referrer;\n }\n }\n\n return httpData;\n },\n\n _resetBackoff: function() {\n this._backoffDuration = 0;\n this._backoffStart = null;\n },\n\n _shouldBackoff: function() {\n return this._backoffDuration && now() - this._backoffStart < this._backoffDuration;\n },\n\n /**\n * Returns true if the in-process data payload matches the signature\n * of the previously-sent data\n *\n * NOTE: This has to be done at this level because TraceKit can generate\n * data from window.onerror WITHOUT an exception object (IE8, IE9,\n * other old browsers). This can take the form of an \"exception\"\n * data object with a single frame (derived from the onerror args).\n */\n _isRepeatData: function(current) {\n var last = this._lastData;\n\n if (\n !last ||\n current.message !== last.message || // defined for captureMessage\n current.culprit !== last.culprit // defined for captureException/onerror\n )\n return false;\n\n // Stacktrace interface (i.e. from captureMessage)\n if (current.stacktrace || last.stacktrace) {\n return isSameStacktrace(current.stacktrace, last.stacktrace);\n } else if (current.exception || last.exception) {\n // Exception interface (i.e. from captureException/onerror)\n return isSameException(current.exception, last.exception);\n }\n\n return true;\n },\n\n _setBackoffState: function(request) {\n // If we are already in a backoff state, don't change anything\n if (this._shouldBackoff()) {\n return;\n }\n\n var status = request.status;\n\n // 400 - project_id doesn't exist or some other fatal\n // 401 - invalid/revoked dsn\n // 429 - too many requests\n if (!(status === 400 || status === 401 || status === 429)) return;\n\n var retry;\n try {\n // If Retry-After is not in Access-Control-Expose-Headers, most\n // browsers will throw an exception trying to access it\n retry = request.getResponseHeader('Retry-After');\n retry = parseInt(retry, 10) * 1000; // Retry-After is returned in seconds\n } catch (e) {\n /* eslint no-empty:0 */\n }\n\n this._backoffDuration = retry\n ? // If Sentry server returned a Retry-After value, use it\n retry\n : // Otherwise, double the last backoff duration (starts at 1 sec)\n this._backoffDuration * 2 || 1000;\n\n this._backoffStart = now();\n },\n\n _send: function(data) {\n var globalOptions = this._globalOptions;\n\n var baseData = {\n project: this._globalProject,\n logger: globalOptions.logger,\n platform: 'javascript'\n },\n httpData = this._getHttpData();\n\n if (httpData) {\n baseData.request = httpData;\n }\n\n // HACK: delete `trimHeadFrames` to prevent from appearing in outbound payload\n if (data.trimHeadFrames) delete data.trimHeadFrames;\n\n data = objectMerge(baseData, data);\n\n // Merge in the tags and extra separately since objectMerge doesn't handle a deep merge\n data.tags = objectMerge(objectMerge({}, this._globalContext.tags), data.tags);\n data.extra = objectMerge(objectMerge({}, this._globalContext.extra), data.extra);\n\n // Send along our own collected metadata with extra\n data.extra['session:duration'] = now() - this._startTime;\n\n if (this._breadcrumbs && this._breadcrumbs.length > 0) {\n // intentionally make shallow copy so that additions\n // to breadcrumbs aren't accidentally sent in this request\n data.breadcrumbs = {\n values: [].slice.call(this._breadcrumbs, 0)\n };\n }\n\n // If there are no tags/extra, strip the key from the payload alltogther.\n if (isEmptyObject(data.tags)) delete data.tags;\n\n if (this._globalContext.user) {\n // sentry.interfaces.User\n data.user = this._globalContext.user;\n }\n\n // Include the environment if it's defined in globalOptions\n if (globalOptions.environment) data.environment = globalOptions.environment;\n\n // Include the release if it's defined in globalOptions\n if (globalOptions.release) data.release = globalOptions.release;\n\n // Include server_name if it's defined in globalOptions\n if (globalOptions.serverName) data.server_name = globalOptions.serverName;\n\n if (isFunction(globalOptions.dataCallback)) {\n data = globalOptions.dataCallback(data) || data;\n }\n\n // Why??????????\n if (!data || isEmptyObject(data)) {\n return;\n }\n\n // Check if the request should be filtered or not\n if (\n isFunction(globalOptions.shouldSendCallback) &&\n !globalOptions.shouldSendCallback(data)\n ) {\n return;\n }\n\n // Backoff state: Sentry server previously responded w/ an error (e.g. 429 - too many requests),\n // so drop requests until \"cool-off\" period has elapsed.\n if (this._shouldBackoff()) {\n this._logDebug('warn', 'Raven dropped error due to backoff: ', data);\n return;\n }\n\n if (typeof globalOptions.sampleRate === 'number') {\n if (Math.random() < globalOptions.sampleRate) {\n this._sendProcessedPayload(data);\n }\n } else {\n this._sendProcessedPayload(data);\n }\n },\n\n _getUuid: function() {\n return uuid4();\n },\n\n _sendProcessedPayload: function(data, callback) {\n var self = this;\n var globalOptions = this._globalOptions;\n\n if (!this.isSetup()) return;\n\n // Try and clean up the packet before sending by truncating long values\n data = this._trimPacket(data);\n\n // ideally duplicate error testing should occur *before* dataCallback/shouldSendCallback,\n // but this would require copying an un-truncated copy of the data packet, which can be\n // arbitrarily deep (extra_data) -- could be worthwhile? will revisit\n if (!this._globalOptions.allowDuplicates && this._isRepeatData(data)) {\n this._logDebug('warn', 'Raven dropped repeat event: ', data);\n return;\n }\n\n // Send along an event_id if not explicitly passed.\n // This event_id can be used to reference the error within Sentry itself.\n // Set lastEventId after we know the error should actually be sent\n this._lastEventId = data.event_id || (data.event_id = this._getUuid());\n\n // Store outbound payload after trim\n this._lastData = data;\n\n this._logDebug('debug', 'Raven about to send:', data);\n\n var auth = {\n sentry_version: '7',\n sentry_client: 'raven-js/' + this.VERSION,\n sentry_key: this._globalKey\n };\n\n if (this._globalSecret) {\n auth.sentry_secret = this._globalSecret;\n }\n\n var exception = data.exception && data.exception.values[0];\n this.captureBreadcrumb({\n category: 'sentry',\n message: exception\n ? (exception.type ? exception.type + ': ' : '') + exception.value\n : data.message,\n event_id: data.event_id,\n level: data.level || 'error' // presume error unless specified\n });\n\n var url = this._globalEndpoint;\n (globalOptions.transport || this._makeRequest).call(this, {\n url: url,\n auth: auth,\n data: data,\n options: globalOptions,\n onSuccess: function success() {\n self._resetBackoff();\n\n self._triggerEvent('success', {\n data: data,\n src: url\n });\n callback && callback();\n },\n onError: function failure(error) {\n self._logDebug('error', 'Raven transport failed to send: ', error);\n\n if (error.request) {\n self._setBackoffState(error.request);\n }\n\n self._triggerEvent('failure', {\n data: data,\n src: url\n });\n error = error || new Error('Raven send failed (no additional details provided)');\n callback && callback(error);\n }\n });\n },\n\n _makeRequest: function(opts) {\n var request = _window.XMLHttpRequest && new _window.XMLHttpRequest();\n if (!request) return;\n\n // if browser doesn't support CORS (e.g. IE7), we are out of luck\n var hasCORS = 'withCredentials' in request || typeof XDomainRequest !== 'undefined';\n\n if (!hasCORS) return;\n\n var url = opts.url;\n\n if ('withCredentials' in request) {\n request.onreadystatechange = function() {\n if (request.readyState !== 4) {\n return;\n } else if (request.status === 200) {\n opts.onSuccess && opts.onSuccess();\n } else if (opts.onError) {\n var err = new Error('Sentry error code: ' + request.status);\n err.request = request;\n opts.onError(err);\n }\n };\n } else {\n request = new XDomainRequest();\n // xdomainrequest cannot go http -> https (or vice versa),\n // so always use protocol relative\n url = url.replace(/^https?:/, '');\n\n // onreadystatechange not supported by XDomainRequest\n if (opts.onSuccess) {\n request.onload = opts.onSuccess;\n }\n if (opts.onError) {\n request.onerror = function() {\n var err = new Error('Sentry error code: XDomainRequest');\n err.request = request;\n opts.onError(err);\n };\n }\n }\n\n // NOTE: auth is intentionally sent as part of query string (NOT as custom\n // HTTP header) so as to avoid preflight CORS requests\n request.open('POST', url + '?' + urlencode(opts.auth));\n request.send(stringify(opts.data));\n },\n\n _logDebug: function(level) {\n if (this._originalConsoleMethods[level] && this.debug) {\n // In IE<10 console methods do not have their own 'apply' method\n Function.prototype.apply.call(\n this._originalConsoleMethods[level],\n this._originalConsole,\n [].slice.call(arguments, 1)\n );\n }\n },\n\n _mergeContext: function(key, context) {\n if (isUndefined(context)) {\n delete this._globalContext[key];\n } else {\n this._globalContext[key] = objectMerge(this._globalContext[key] || {}, context);\n }\n }\n};\n\n// Deprecations\nRaven.prototype.setUser = Raven.prototype.setUserContext;\nRaven.prototype.setReleaseContext = Raven.prototype.setRelease;\n\nmodule.exports = Raven;\n","/**\n * Enforces a single instance of the Raven client, and the\n * main entry point for Raven. If you are a consumer of the\n * Raven library, you SHOULD load this file (vs raven.js).\n **/\n\nvar RavenConstructor = require('./raven');\n\n// This is to be defensive in environments where window does not exist (see https://github.com/getsentry/raven-js/pull/785)\nvar _window =\n typeof window !== 'undefined'\n ? window\n : typeof global !== 'undefined' ? global : typeof self !== 'undefined' ? self : {};\nvar _Raven = _window.Raven;\n\nvar Raven = new RavenConstructor();\n\n/*\n * Allow multiple versions of Raven to be installed.\n * Strip Raven from the global context and returns the instance.\n *\n * @return {Raven}\n */\nRaven.noConflict = function() {\n _window.Raven = _Raven;\n return Raven;\n};\n\nRaven.afterLoad();\n\nmodule.exports = Raven;\n","var _window =\n typeof window !== 'undefined'\n ? window\n : typeof global !== 'undefined' ? global : typeof self !== 'undefined' ? self : {};\n\nfunction isObject(what) {\n return typeof what === 'object' && what !== null;\n}\n\n// Yanked from https://git.io/vS8DV re-used under CC0\n// with some tiny modifications\nfunction isError(value) {\n switch ({}.toString.call(value)) {\n case '[object Error]':\n return true;\n case '[object Exception]':\n return true;\n case '[object DOMException]':\n return true;\n default:\n return value instanceof Error;\n }\n}\n\nfunction isErrorEvent(value) {\n return supportsErrorEvent() && {}.toString.call(value) === '[object ErrorEvent]';\n}\n\nfunction isUndefined(what) {\n return what === void 0;\n}\n\nfunction isFunction(what) {\n return typeof what === 'function';\n}\n\nfunction isString(what) {\n return Object.prototype.toString.call(what) === '[object String]';\n}\n\nfunction isEmptyObject(what) {\n for (var _ in what) return false; // eslint-disable-line guard-for-in, no-unused-vars\n return true;\n}\n\nfunction supportsErrorEvent() {\n try {\n new ErrorEvent(''); // eslint-disable-line no-new\n return true;\n } catch (e) {\n return false;\n }\n}\n\nfunction wrappedCallback(callback) {\n function dataCallback(data, original) {\n var normalizedData = callback(data) || data;\n if (original) {\n return original(normalizedData) || normalizedData;\n }\n return normalizedData;\n }\n\n return dataCallback;\n}\n\nfunction each(obj, callback) {\n var i, j;\n\n if (isUndefined(obj.length)) {\n for (i in obj) {\n if (hasKey(obj, i)) {\n callback.call(null, i, obj[i]);\n }\n }\n } else {\n j = obj.length;\n if (j) {\n for (i = 0; i < j; i++) {\n callback.call(null, i, obj[i]);\n }\n }\n }\n}\n\nfunction objectMerge(obj1, obj2) {\n if (!obj2) {\n return obj1;\n }\n each(obj2, function(key, value) {\n obj1[key] = value;\n });\n return obj1;\n}\n\n/**\n * This function is only used for react-native.\n * react-native freezes object that have already been sent over the\n * js bridge. We need this function in order to check if the object is frozen.\n * So it's ok that objectFrozen returns false if Object.isFrozen is not\n * supported because it's not relevant for other \"platforms\". See related issue:\n * https://github.com/getsentry/react-native-sentry/issues/57\n */\nfunction objectFrozen(obj) {\n if (!Object.isFrozen) {\n return false;\n }\n return Object.isFrozen(obj);\n}\n\nfunction truncate(str, max) {\n return !max || str.length <= max ? str : str.substr(0, max) + '\\u2026';\n}\n\n/**\n * hasKey, a better form of hasOwnProperty\n * Example: hasKey(MainHostObject, property) === true/false\n *\n * @param {Object} host object to check property\n * @param {string} key to check\n */\nfunction hasKey(object, key) {\n return Object.prototype.hasOwnProperty.call(object, key);\n}\n\nfunction joinRegExp(patterns) {\n // Combine an array of regular expressions and strings into one large regexp\n // Be mad.\n var sources = [],\n i = 0,\n len = patterns.length,\n pattern;\n\n for (; i < len; i++) {\n pattern = patterns[i];\n if (isString(pattern)) {\n // If it's a string, we need to escape it\n // Taken from: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Guide/Regular_Expressions\n sources.push(pattern.replace(/([.*+?^=!:${}()|\\[\\]\\/\\\\])/g, '\\\\$1'));\n } else if (pattern && pattern.source) {\n // If it's a regexp already, we want to extract the source\n sources.push(pattern.source);\n }\n // Intentionally skip other cases\n }\n return new RegExp(sources.join('|'), 'i');\n}\n\nfunction urlencode(o) {\n var pairs = [];\n each(o, function(key, value) {\n pairs.push(encodeURIComponent(key) + '=' + encodeURIComponent(value));\n });\n return pairs.join('&');\n}\n\n// borrowed from https://tools.ietf.org/html/rfc3986#appendix-B\n// intentionally using regex and not href parsing trick because React Native and other\n// environments where DOM might not be available\nfunction parseUrl(url) {\n var match = url.match(/^(([^:\\/?#]+):)?(\\/\\/([^\\/?#]*))?([^?#]*)(\\?([^#]*))?(#(.*))?$/);\n if (!match) return {};\n\n // coerce to undefined values to empty string so we don't get 'undefined'\n var query = match[6] || '';\n var fragment = match[8] || '';\n return {\n protocol: match[2],\n host: match[4],\n path: match[5],\n relative: match[5] + query + fragment // everything minus origin\n };\n}\nfunction uuid4() {\n var crypto = _window.crypto || _window.msCrypto;\n\n if (!isUndefined(crypto) && crypto.getRandomValues) {\n // Use window.crypto API if available\n // eslint-disable-next-line no-undef\n var arr = new Uint16Array(8);\n crypto.getRandomValues(arr);\n\n // set 4 in byte 7\n arr[3] = (arr[3] & 0xfff) | 0x4000;\n // set 2 most significant bits of byte 9 to '10'\n arr[4] = (arr[4] & 0x3fff) | 0x8000;\n\n var pad = function(num) {\n var v = num.toString(16);\n while (v.length < 4) {\n v = '0' + v;\n }\n return v;\n };\n\n return (\n pad(arr[0]) +\n pad(arr[1]) +\n pad(arr[2]) +\n pad(arr[3]) +\n pad(arr[4]) +\n pad(arr[5]) +\n pad(arr[6]) +\n pad(arr[7])\n );\n } else {\n // http://stackoverflow.com/questions/105034/how-to-create-a-guid-uuid-in-javascript/2117523#2117523\n return 'xxxxxxxxxxxx4xxxyxxxxxxxxxxxxxxx'.replace(/[xy]/g, function(c) {\n var r = (Math.random() * 16) | 0,\n v = c === 'x' ? r : (r & 0x3) | 0x8;\n return v.toString(16);\n });\n }\n}\n\n/**\n * Given a child DOM element, returns a query-selector statement describing that\n * and its ancestors\n * e.g. [HTMLElement] => body > div > input#foo.btn[name=baz]\n * @param elem\n * @returns {string}\n */\nfunction htmlTreeAsString(elem) {\n /* eslint no-extra-parens:0*/\n var MAX_TRAVERSE_HEIGHT = 5,\n MAX_OUTPUT_LEN = 80,\n out = [],\n height = 0,\n len = 0,\n separator = ' > ',\n sepLength = separator.length,\n nextStr;\n\n while (elem && height++ < MAX_TRAVERSE_HEIGHT) {\n nextStr = htmlElementAsString(elem);\n // bail out if\n // - nextStr is the 'html' element\n // - the length of the string that would be created exceeds MAX_OUTPUT_LEN\n // (ignore this limit if we are on the first iteration)\n if (\n nextStr === 'html' ||\n (height > 1 && len + out.length * sepLength + nextStr.length >= MAX_OUTPUT_LEN)\n ) {\n break;\n }\n\n out.push(nextStr);\n\n len += nextStr.length;\n elem = elem.parentNode;\n }\n\n return out.reverse().join(separator);\n}\n\n/**\n * Returns a simple, query-selector representation of a DOM element\n * e.g. [HTMLElement] => input#foo.btn[name=baz]\n * @param HTMLElement\n * @returns {string}\n */\nfunction htmlElementAsString(elem) {\n var out = [],\n className,\n classes,\n key,\n attr,\n i;\n\n if (!elem || !elem.tagName) {\n return '';\n }\n\n out.push(elem.tagName.toLowerCase());\n if (elem.id) {\n out.push('#' + elem.id);\n }\n\n className = elem.className;\n if (className && isString(className)) {\n classes = className.split(/\\s+/);\n for (i = 0; i < classes.length; i++) {\n out.push('.' + classes[i]);\n }\n }\n var attrWhitelist = ['type', 'name', 'title', 'alt'];\n for (i = 0; i < attrWhitelist.length; i++) {\n key = attrWhitelist[i];\n attr = elem.getAttribute(key);\n if (attr) {\n out.push('[' + key + '=\"' + attr + '\"]');\n }\n }\n return out.join('');\n}\n\n/**\n * Returns true if either a OR b is truthy, but not both\n */\nfunction isOnlyOneTruthy(a, b) {\n return !!(!!a ^ !!b);\n}\n\n/**\n * Returns true if the two input exception interfaces have the same content\n */\nfunction isSameException(ex1, ex2) {\n if (isOnlyOneTruthy(ex1, ex2)) return false;\n\n ex1 = ex1.values[0];\n ex2 = ex2.values[0];\n\n if (ex1.type !== ex2.type || ex1.value !== ex2.value) return false;\n\n return isSameStacktrace(ex1.stacktrace, ex2.stacktrace);\n}\n\n/**\n * Returns true if the two input stack trace interfaces have the same content\n */\nfunction isSameStacktrace(stack1, stack2) {\n if (isOnlyOneTruthy(stack1, stack2)) return false;\n\n var frames1 = stack1.frames;\n var frames2 = stack2.frames;\n\n // Exit early if frame count differs\n if (frames1.length !== frames2.length) return false;\n\n // Iterate through every frame; bail out if anything differs\n var a, b;\n for (var i = 0; i < frames1.length; i++) {\n a = frames1[i];\n b = frames2[i];\n if (\n a.filename !== b.filename ||\n a.lineno !== b.lineno ||\n a.colno !== b.colno ||\n a['function'] !== b['function']\n )\n return false;\n }\n return true;\n}\n\n/**\n * Polyfill a method\n * @param obj object e.g. `document`\n * @param name method name present on object e.g. `addEventListener`\n * @param replacement replacement function\n * @param track {optional} record instrumentation to an array\n */\nfunction fill(obj, name, replacement, track) {\n var orig = obj[name];\n obj[name] = replacement(orig);\n if (track) {\n track.push([obj, name, orig]);\n }\n}\n\nmodule.exports = {\n isObject: isObject,\n isError: isError,\n isErrorEvent: isErrorEvent,\n isUndefined: isUndefined,\n isFunction: isFunction,\n isString: isString,\n isEmptyObject: isEmptyObject,\n supportsErrorEvent: supportsErrorEvent,\n wrappedCallback: wrappedCallback,\n each: each,\n objectMerge: objectMerge,\n truncate: truncate,\n objectFrozen: objectFrozen,\n hasKey: hasKey,\n joinRegExp: joinRegExp,\n urlencode: urlencode,\n uuid4: uuid4,\n htmlTreeAsString: htmlTreeAsString,\n htmlElementAsString: htmlElementAsString,\n isSameException: isSameException,\n isSameStacktrace: isSameStacktrace,\n parseUrl: parseUrl,\n fill: fill\n};\n","var utils = require('../../src/utils');\n\n/*\n TraceKit - Cross brower stack traces\n\n This was originally forked from github.com/occ/TraceKit, but has since been\n largely re-written and is now maintained as part of raven-js. Tests for\n this are in test/vendor.\n\n MIT license\n*/\n\nvar TraceKit = {\n collectWindowErrors: true,\n debug: false\n};\n\n// This is to be defensive in environments where window does not exist (see https://github.com/getsentry/raven-js/pull/785)\nvar _window =\n typeof window !== 'undefined'\n ? window\n : typeof global !== 'undefined' ? global : typeof self !== 'undefined' ? self : {};\n\n// global reference to slice\nvar _slice = [].slice;\nvar UNKNOWN_FUNCTION = '?';\n\n// https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Error#Error_types\nvar ERROR_TYPES_RE = /^(?:[Uu]ncaught (?:exception: )?)?(?:((?:Eval|Internal|Range|Reference|Syntax|Type|URI|)Error): )?(.*)$/;\n\nfunction getLocationHref() {\n if (typeof document === 'undefined' || document.location == null) return '';\n\n return document.location.href;\n}\n\n/**\n * TraceKit.report: cross-browser processing of unhandled exceptions\n *\n * Syntax:\n * TraceKit.report.subscribe(function(stackInfo) { ... })\n * TraceKit.report.unsubscribe(function(stackInfo) { ... })\n * TraceKit.report(exception)\n * try { ...code... } catch(ex) { TraceKit.report(ex); }\n *\n * Supports:\n * - Firefox: full stack trace with line numbers, plus column number\n * on top frame; column number is not guaranteed\n * - Opera: full stack trace with line and column numbers\n * - Chrome: full stack trace with line and column numbers\n * - Safari: line and column number for the top frame only; some frames\n * may be missing, and column number is not guaranteed\n * - IE: line and column number for the top frame only; some frames\n * may be missing, and column number is not guaranteed\n *\n * In theory, TraceKit should work on all of the following versions:\n * - IE5.5+ (only 8.0 tested)\n * - Firefox 0.9+ (only 3.5+ tested)\n * - Opera 7+ (only 10.50 tested; versions 9 and earlier may require\n * Exceptions Have Stacktrace to be enabled in opera:config)\n * - Safari 3+ (only 4+ tested)\n * - Chrome 1+ (only 5+ tested)\n * - Konqueror 3.5+ (untested)\n *\n * Requires TraceKit.computeStackTrace.\n *\n * Tries to catch all unhandled exceptions and report them to the\n * subscribed handlers. Please note that TraceKit.report will rethrow the\n * exception. This is REQUIRED in order to get a useful stack trace in IE.\n * If the exception does not reach the top of the browser, you will only\n * get a stack trace from the point where TraceKit.report was called.\n *\n * Handlers receive a stackInfo object as described in the\n * TraceKit.computeStackTrace docs.\n */\nTraceKit.report = (function reportModuleWrapper() {\n var handlers = [],\n lastArgs = null,\n lastException = null,\n lastExceptionStack = null;\n\n /**\n * Add a crash handler.\n * @param {Function} handler\n */\n function subscribe(handler) {\n installGlobalHandler();\n handlers.push(handler);\n }\n\n /**\n * Remove a crash handler.\n * @param {Function} handler\n */\n function unsubscribe(handler) {\n for (var i = handlers.length - 1; i >= 0; --i) {\n if (handlers[i] === handler) {\n handlers.splice(i, 1);\n }\n }\n }\n\n /**\n * Remove all crash handlers.\n */\n function unsubscribeAll() {\n uninstallGlobalHandler();\n handlers = [];\n }\n\n /**\n * Dispatch stack information to all handlers.\n * @param {Object.} stack\n */\n function notifyHandlers(stack, isWindowError) {\n var exception = null;\n if (isWindowError && !TraceKit.collectWindowErrors) {\n return;\n }\n for (var i in handlers) {\n if (handlers.hasOwnProperty(i)) {\n try {\n handlers[i].apply(null, [stack].concat(_slice.call(arguments, 2)));\n } catch (inner) {\n exception = inner;\n }\n }\n }\n\n if (exception) {\n throw exception;\n }\n }\n\n var _oldOnerrorHandler, _onErrorHandlerInstalled;\n\n /**\n * Ensures all global unhandled exceptions are recorded.\n * Supported by Gecko and IE.\n * @param {string} message Error message.\n * @param {string} url URL of script that generated the exception.\n * @param {(number|string)} lineNo The line number at which the error\n * occurred.\n * @param {?(number|string)} colNo The column number at which the error\n * occurred.\n * @param {?Error} ex The actual Error object.\n */\n function traceKitWindowOnError(message, url, lineNo, colNo, ex) {\n var stack = null;\n\n if (lastExceptionStack) {\n TraceKit.computeStackTrace.augmentStackTraceWithInitialElement(\n lastExceptionStack,\n url,\n lineNo,\n message\n );\n processLastException();\n } else if (ex && utils.isError(ex)) {\n // non-string `ex` arg; attempt to extract stack trace\n\n // New chrome and blink send along a real error object\n // Let's just report that like a normal error.\n // See: https://mikewest.org/2013/08/debugging-runtime-errors-with-window-onerror\n stack = TraceKit.computeStackTrace(ex);\n notifyHandlers(stack, true);\n } else {\n var location = {\n url: url,\n line: lineNo,\n column: colNo\n };\n\n var name = undefined;\n var msg = message; // must be new var or will modify original `arguments`\n var groups;\n if ({}.toString.call(message) === '[object String]') {\n var groups = message.match(ERROR_TYPES_RE);\n if (groups) {\n name = groups[1];\n msg = groups[2];\n }\n }\n\n location.func = UNKNOWN_FUNCTION;\n\n stack = {\n name: name,\n message: msg,\n url: getLocationHref(),\n stack: [location]\n };\n notifyHandlers(stack, true);\n }\n\n if (_oldOnerrorHandler) {\n return _oldOnerrorHandler.apply(this, arguments);\n }\n\n return false;\n }\n\n function installGlobalHandler() {\n if (_onErrorHandlerInstalled) {\n return;\n }\n _oldOnerrorHandler = _window.onerror;\n _window.onerror = traceKitWindowOnError;\n _onErrorHandlerInstalled = true;\n }\n\n function uninstallGlobalHandler() {\n if (!_onErrorHandlerInstalled) {\n return;\n }\n _window.onerror = _oldOnerrorHandler;\n _onErrorHandlerInstalled = false;\n _oldOnerrorHandler = undefined;\n }\n\n function processLastException() {\n var _lastExceptionStack = lastExceptionStack,\n _lastArgs = lastArgs;\n lastArgs = null;\n lastExceptionStack = null;\n lastException = null;\n notifyHandlers.apply(null, [_lastExceptionStack, false].concat(_lastArgs));\n }\n\n /**\n * Reports an unhandled Error to TraceKit.\n * @param {Error} ex\n * @param {?boolean} rethrow If false, do not re-throw the exception.\n * Only used for window.onerror to not cause an infinite loop of\n * rethrowing.\n */\n function report(ex, rethrow) {\n var args = _slice.call(arguments, 1);\n if (lastExceptionStack) {\n if (lastException === ex) {\n return; // already caught by an inner catch block, ignore\n } else {\n processLastException();\n }\n }\n\n var stack = TraceKit.computeStackTrace(ex);\n lastExceptionStack = stack;\n lastException = ex;\n lastArgs = args;\n\n // If the stack trace is incomplete, wait for 2 seconds for\n // slow slow IE to see if onerror occurs or not before reporting\n // this exception; otherwise, we will end up with an incomplete\n // stack trace\n setTimeout(function() {\n if (lastException === ex) {\n processLastException();\n }\n }, stack.incomplete ? 2000 : 0);\n\n if (rethrow !== false) {\n throw ex; // re-throw to propagate to the top level (and cause window.onerror)\n }\n }\n\n report.subscribe = subscribe;\n report.unsubscribe = unsubscribe;\n report.uninstall = unsubscribeAll;\n return report;\n})();\n\n/**\n * TraceKit.computeStackTrace: cross-browser stack traces in JavaScript\n *\n * Syntax:\n * s = TraceKit.computeStackTrace(exception) // consider using TraceKit.report instead (see below)\n * Returns:\n * s.name - exception name\n * s.message - exception message\n * s.stack[i].url - JavaScript or HTML file URL\n * s.stack[i].func - function name, or empty for anonymous functions (if guessing did not work)\n * s.stack[i].args - arguments passed to the function, if known\n * s.stack[i].line - line number, if known\n * s.stack[i].column - column number, if known\n *\n * Supports:\n * - Firefox: full stack trace with line numbers and unreliable column\n * number on top frame\n * - Opera 10: full stack trace with line and column numbers\n * - Opera 9-: full stack trace with line numbers\n * - Chrome: full stack trace with line and column numbers\n * - Safari: line and column number for the topmost stacktrace element\n * only\n * - IE: no line numbers whatsoever\n *\n * Tries to guess names of anonymous functions by looking for assignments\n * in the source code. In IE and Safari, we have to guess source file names\n * by searching for function bodies inside all page scripts. This will not\n * work for scripts that are loaded cross-domain.\n * Here be dragons: some function names may be guessed incorrectly, and\n * duplicate functions may be mismatched.\n *\n * TraceKit.computeStackTrace should only be used for tracing purposes.\n * Logging of unhandled exceptions should be done with TraceKit.report,\n * which builds on top of TraceKit.computeStackTrace and provides better\n * IE support by utilizing the window.onerror event to retrieve information\n * about the top of the stack.\n *\n * Note: In IE and Safari, no stack trace is recorded on the Error object,\n * so computeStackTrace instead walks its *own* chain of callers.\n * This means that:\n * * in Safari, some methods may be missing from the stack trace;\n * * in IE, the topmost function in the stack trace will always be the\n * caller of computeStackTrace.\n *\n * This is okay for tracing (because you are likely to be calling\n * computeStackTrace from the function you want to be the topmost element\n * of the stack trace anyway), but not okay for logging unhandled\n * exceptions (because your catch block will likely be far away from the\n * inner function that actually caused the exception).\n *\n */\nTraceKit.computeStackTrace = (function computeStackTraceWrapper() {\n // Contents of Exception in various browsers.\n //\n // SAFARI:\n // ex.message = Can't find variable: qq\n // ex.line = 59\n // ex.sourceId = 580238192\n // ex.sourceURL = http://...\n // ex.expressionBeginOffset = 96\n // ex.expressionCaretOffset = 98\n // ex.expressionEndOffset = 98\n // ex.name = ReferenceError\n //\n // FIREFOX:\n // ex.message = qq is not defined\n // ex.fileName = http://...\n // ex.lineNumber = 59\n // ex.columnNumber = 69\n // ex.stack = ...stack trace... (see the example below)\n // ex.name = ReferenceError\n //\n // CHROME:\n // ex.message = qq is not defined\n // ex.name = ReferenceError\n // ex.type = not_defined\n // ex.arguments = ['aa']\n // ex.stack = ...stack trace...\n //\n // INTERNET EXPLORER:\n // ex.message = ...\n // ex.name = ReferenceError\n //\n // OPERA:\n // ex.message = ...message... (see the example below)\n // ex.name = ReferenceError\n // ex.opera#sourceloc = 11 (pretty much useless, duplicates the info in ex.message)\n // ex.stacktrace = n/a; see 'opera:config#UserPrefs|Exceptions Have Stacktrace'\n\n /**\n * Computes stack trace information from the stack property.\n * Chrome and Gecko use this property.\n * @param {Error} ex\n * @return {?Object.} Stack trace information.\n */\n function computeStackTraceFromStackProp(ex) {\n if (typeof ex.stack === 'undefined' || !ex.stack) return;\n\n var chrome = /^\\s*at (.*?) ?\\(((?:file|https?|blob|chrome-extension|native|eval|webpack||[a-z]:|\\/).*?)(?::(\\d+))?(?::(\\d+))?\\)?\\s*$/i,\n gecko = /^\\s*(.*?)(?:\\((.*?)\\))?(?:^|@)((?:file|https?|blob|chrome|webpack|resource|\\[native).*?|[^@]*bundle)(?::(\\d+))?(?::(\\d+))?\\s*$/i,\n winjs = /^\\s*at (?:((?:\\[object object\\])?.+) )?\\(?((?:file|ms-appx|https?|webpack|blob):.*?):(\\d+)(?::(\\d+))?\\)?\\s*$/i,\n // Used to additionally parse URL/line/column from eval frames\n geckoEval = /(\\S+) line (\\d+)(?: > eval line \\d+)* > eval/i,\n chromeEval = /\\((\\S*)(?::(\\d+))(?::(\\d+))\\)/,\n lines = ex.stack.split('\\n'),\n stack = [],\n submatch,\n parts,\n element,\n reference = /^(.*) is undefined$/.exec(ex.message);\n\n for (var i = 0, j = lines.length; i < j; ++i) {\n if ((parts = chrome.exec(lines[i]))) {\n var isNative = parts[2] && parts[2].indexOf('native') === 0; // start of line\n var isEval = parts[2] && parts[2].indexOf('eval') === 0; // start of line\n if (isEval && (submatch = chromeEval.exec(parts[2]))) {\n // throw out eval line/column and use top-most line/column number\n parts[2] = submatch[1]; // url\n parts[3] = submatch[2]; // line\n parts[4] = submatch[3]; // column\n }\n element = {\n url: !isNative ? parts[2] : null,\n func: parts[1] || UNKNOWN_FUNCTION,\n args: isNative ? [parts[2]] : [],\n line: parts[3] ? +parts[3] : null,\n column: parts[4] ? +parts[4] : null\n };\n } else if ((parts = winjs.exec(lines[i]))) {\n element = {\n url: parts[2],\n func: parts[1] || UNKNOWN_FUNCTION,\n args: [],\n line: +parts[3],\n column: parts[4] ? +parts[4] : null\n };\n } else if ((parts = gecko.exec(lines[i]))) {\n var isEval = parts[3] && parts[3].indexOf(' > eval') > -1;\n if (isEval && (submatch = geckoEval.exec(parts[3]))) {\n // throw out eval line/column and use top-most line number\n parts[3] = submatch[1];\n parts[4] = submatch[2];\n parts[5] = null; // no column when eval\n } else if (i === 0 && !parts[5] && typeof ex.columnNumber !== 'undefined') {\n // FireFox uses this awesome columnNumber property for its top frame\n // Also note, Firefox's column number is 0-based and everything else expects 1-based,\n // so adding 1\n // NOTE: this hack doesn't work if top-most frame is eval\n stack[0].column = ex.columnNumber + 1;\n }\n element = {\n url: parts[3],\n func: parts[1] || UNKNOWN_FUNCTION,\n args: parts[2] ? parts[2].split(',') : [],\n line: parts[4] ? +parts[4] : null,\n column: parts[5] ? +parts[5] : null\n };\n } else {\n continue;\n }\n\n if (!element.func && element.line) {\n element.func = UNKNOWN_FUNCTION;\n }\n\n stack.push(element);\n }\n\n if (!stack.length) {\n return null;\n }\n\n return {\n name: ex.name,\n message: ex.message,\n url: getLocationHref(),\n stack: stack\n };\n }\n\n /**\n * Adds information about the first frame to incomplete stack traces.\n * Safari and IE require this to get complete data on the first frame.\n * @param {Object.} stackInfo Stack trace information from\n * one of the compute* methods.\n * @param {string} url The URL of the script that caused an error.\n * @param {(number|string)} lineNo The line number of the script that\n * caused an error.\n * @param {string=} message The error generated by the browser, which\n * hopefully contains the name of the object that caused the error.\n * @return {boolean} Whether or not the stack information was\n * augmented.\n */\n function augmentStackTraceWithInitialElement(stackInfo, url, lineNo, message) {\n var initial = {\n url: url,\n line: lineNo\n };\n\n if (initial.url && initial.line) {\n stackInfo.incomplete = false;\n\n if (!initial.func) {\n initial.func = UNKNOWN_FUNCTION;\n }\n\n if (stackInfo.stack.length > 0) {\n if (stackInfo.stack[0].url === initial.url) {\n if (stackInfo.stack[0].line === initial.line) {\n return false; // already in stack trace\n } else if (\n !stackInfo.stack[0].line &&\n stackInfo.stack[0].func === initial.func\n ) {\n stackInfo.stack[0].line = initial.line;\n return false;\n }\n }\n }\n\n stackInfo.stack.unshift(initial);\n stackInfo.partial = true;\n return true;\n } else {\n stackInfo.incomplete = true;\n }\n\n return false;\n }\n\n /**\n * Computes stack trace information by walking the arguments.caller\n * chain at the time the exception occurred. This will cause earlier\n * frames to be missed but is the only way to get any stack trace in\n * Safari and IE. The top frame is restored by\n * {@link augmentStackTraceWithInitialElement}.\n * @param {Error} ex\n * @return {?Object.} Stack trace information.\n */\n function computeStackTraceByWalkingCallerChain(ex, depth) {\n var functionName = /function\\s+([_$a-zA-Z\\xA0-\\uFFFF][_$a-zA-Z0-9\\xA0-\\uFFFF]*)?\\s*\\(/i,\n stack = [],\n funcs = {},\n recursion = false,\n parts,\n item,\n source;\n\n for (\n var curr = computeStackTraceByWalkingCallerChain.caller;\n curr && !recursion;\n curr = curr.caller\n ) {\n if (curr === computeStackTrace || curr === TraceKit.report) {\n // console.log('skipping internal function');\n continue;\n }\n\n item = {\n url: null,\n func: UNKNOWN_FUNCTION,\n line: null,\n column: null\n };\n\n if (curr.name) {\n item.func = curr.name;\n } else if ((parts = functionName.exec(curr.toString()))) {\n item.func = parts[1];\n }\n\n if (typeof item.func === 'undefined') {\n try {\n item.func = parts.input.substring(0, parts.input.indexOf('{'));\n } catch (e) {}\n }\n\n if (funcs['' + curr]) {\n recursion = true;\n } else {\n funcs['' + curr] = true;\n }\n\n stack.push(item);\n }\n\n if (depth) {\n // console.log('depth is ' + depth);\n // console.log('stack is ' + stack.length);\n stack.splice(0, depth);\n }\n\n var result = {\n name: ex.name,\n message: ex.message,\n url: getLocationHref(),\n stack: stack\n };\n augmentStackTraceWithInitialElement(\n result,\n ex.sourceURL || ex.fileName,\n ex.line || ex.lineNumber,\n ex.message || ex.description\n );\n return result;\n }\n\n /**\n * Computes a stack trace for an exception.\n * @param {Error} ex\n * @param {(string|number)=} depth\n */\n function computeStackTrace(ex, depth) {\n var stack = null;\n depth = depth == null ? 0 : +depth;\n\n try {\n stack = computeStackTraceFromStackProp(ex);\n if (stack) {\n return stack;\n }\n } catch (e) {\n if (TraceKit.debug) {\n throw e;\n }\n }\n\n try {\n stack = computeStackTraceByWalkingCallerChain(ex, depth + 1);\n if (stack) {\n return stack;\n }\n } catch (e) {\n if (TraceKit.debug) {\n throw e;\n }\n }\n return {\n name: ex.name,\n message: ex.message,\n url: getLocationHref()\n };\n }\n\n computeStackTrace.augmentStackTraceWithInitialElement = augmentStackTraceWithInitialElement;\n computeStackTrace.computeStackTraceFromStackProp = computeStackTraceFromStackProp;\n\n return computeStackTrace;\n})();\n\nmodule.exports = TraceKit;\n","/*\n json-stringify-safe\n Like JSON.stringify, but doesn't throw on circular references.\n\n Originally forked from https://github.com/isaacs/json-stringify-safe\n version 5.0.1 on 3/8/2017 and modified to handle Errors serialization\n and IE8 compatibility. Tests for this are in test/vendor.\n\n ISC license: https://github.com/isaacs/json-stringify-safe/blob/master/LICENSE\n*/\n\nexports = module.exports = stringify;\nexports.getSerialize = serializer;\n\nfunction indexOf(haystack, needle) {\n for (var i = 0; i < haystack.length; ++i) {\n if (haystack[i] === needle) return i;\n }\n return -1;\n}\n\nfunction stringify(obj, replacer, spaces, cycleReplacer) {\n return JSON.stringify(obj, serializer(replacer, cycleReplacer), spaces);\n}\n\n// https://github.com/ftlabs/js-abbreviate/blob/fa709e5f139e7770a71827b1893f22418097fbda/index.js#L95-L106\nfunction stringifyError(value) {\n var err = {\n // These properties are implemented as magical getters and don't show up in for in\n stack: value.stack,\n message: value.message,\n name: value.name\n };\n\n for (var i in value) {\n if (Object.prototype.hasOwnProperty.call(value, i)) {\n err[i] = value[i];\n }\n }\n\n return err;\n}\n\nfunction serializer(replacer, cycleReplacer) {\n var stack = [];\n var keys = [];\n\n if (cycleReplacer == null) {\n cycleReplacer = function(key, value) {\n if (stack[0] === value) {\n return '[Circular ~]';\n }\n return '[Circular ~.' + keys.slice(0, indexOf(stack, value)).join('.') + ']';\n };\n }\n\n return function(key, value) {\n if (stack.length > 0) {\n var thisPos = indexOf(stack, this);\n ~thisPos ? stack.splice(thisPos + 1) : stack.push(this);\n ~thisPos ? keys.splice(thisPos, Infinity, key) : keys.push(key);\n\n if (~indexOf(stack, value)) {\n value = cycleReplacer.call(this, key, value);\n }\n } else {\n stack.push(value);\n }\n\n return replacer == null\n ? value instanceof Error ? stringifyError(value) : value\n : replacer.call(this, key, value);\n };\n}\n","/** @license React v17.0.2\n * react-jsx-runtime.development.js\n *\n * Copyright (c) Facebook, Inc. and its affiliates.\n *\n * This source code is licensed under the MIT license found in the\n * LICENSE file in the root directory of this source tree.\n */\n\n'use strict';\n\nif (process.env.NODE_ENV !== \"production\") {\n (function() {\n'use strict';\n\nvar React = require('react');\nvar _assign = require('object-assign');\n\n// ATTENTION\n// When adding new symbols to this file,\n// Please consider also adding to 'react-devtools-shared/src/backend/ReactSymbols'\n// The Symbol used to tag the ReactElement-like types. If there is no native Symbol\n// nor polyfill, then a plain number is used for performance.\nvar REACT_ELEMENT_TYPE = 0xeac7;\nvar REACT_PORTAL_TYPE = 0xeaca;\nexports.Fragment = 0xeacb;\nvar REACT_STRICT_MODE_TYPE = 0xeacc;\nvar REACT_PROFILER_TYPE = 0xead2;\nvar REACT_PROVIDER_TYPE = 0xeacd;\nvar REACT_CONTEXT_TYPE = 0xeace;\nvar REACT_FORWARD_REF_TYPE = 0xead0;\nvar REACT_SUSPENSE_TYPE = 0xead1;\nvar REACT_SUSPENSE_LIST_TYPE = 0xead8;\nvar REACT_MEMO_TYPE = 0xead3;\nvar REACT_LAZY_TYPE = 0xead4;\nvar REACT_BLOCK_TYPE = 0xead9;\nvar REACT_SERVER_BLOCK_TYPE = 0xeada;\nvar REACT_FUNDAMENTAL_TYPE = 0xead5;\nvar REACT_SCOPE_TYPE = 0xead7;\nvar REACT_OPAQUE_ID_TYPE = 0xeae0;\nvar REACT_DEBUG_TRACING_MODE_TYPE = 0xeae1;\nvar REACT_OFFSCREEN_TYPE = 0xeae2;\nvar REACT_LEGACY_HIDDEN_TYPE = 0xeae3;\n\nif (typeof Symbol === 'function' && Symbol.for) {\n var symbolFor = Symbol.for;\n REACT_ELEMENT_TYPE = symbolFor('react.element');\n REACT_PORTAL_TYPE = symbolFor('react.portal');\n exports.Fragment = symbolFor('react.fragment');\n REACT_STRICT_MODE_TYPE = symbolFor('react.strict_mode');\n REACT_PROFILER_TYPE = symbolFor('react.profiler');\n REACT_PROVIDER_TYPE = symbolFor('react.provider');\n REACT_CONTEXT_TYPE = symbolFor('react.context');\n REACT_FORWARD_REF_TYPE = symbolFor('react.forward_ref');\n REACT_SUSPENSE_TYPE = symbolFor('react.suspense');\n REACT_SUSPENSE_LIST_TYPE = symbolFor('react.suspense_list');\n REACT_MEMO_TYPE = symbolFor('react.memo');\n REACT_LAZY_TYPE = symbolFor('react.lazy');\n REACT_BLOCK_TYPE = symbolFor('react.block');\n REACT_SERVER_BLOCK_TYPE = symbolFor('react.server.block');\n REACT_FUNDAMENTAL_TYPE = symbolFor('react.fundamental');\n REACT_SCOPE_TYPE = symbolFor('react.scope');\n REACT_OPAQUE_ID_TYPE = symbolFor('react.opaque.id');\n REACT_DEBUG_TRACING_MODE_TYPE = symbolFor('react.debug_trace_mode');\n REACT_OFFSCREEN_TYPE = symbolFor('react.offscreen');\n REACT_LEGACY_HIDDEN_TYPE = symbolFor('react.legacy_hidden');\n}\n\nvar MAYBE_ITERATOR_SYMBOL = typeof Symbol === 'function' && Symbol.iterator;\nvar FAUX_ITERATOR_SYMBOL = '@@iterator';\nfunction getIteratorFn(maybeIterable) {\n if (maybeIterable === null || typeof maybeIterable !== 'object') {\n return null;\n }\n\n var maybeIterator = MAYBE_ITERATOR_SYMBOL && maybeIterable[MAYBE_ITERATOR_SYMBOL] || maybeIterable[FAUX_ITERATOR_SYMBOL];\n\n if (typeof maybeIterator === 'function') {\n return maybeIterator;\n }\n\n return null;\n}\n\nvar ReactSharedInternals = React.__SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED;\n\nfunction error(format) {\n {\n for (var _len2 = arguments.length, args = new Array(_len2 > 1 ? _len2 - 1 : 0), _key2 = 1; _key2 < _len2; _key2++) {\n args[_key2 - 1] = arguments[_key2];\n }\n\n printWarning('error', format, args);\n }\n}\n\nfunction printWarning(level, format, args) {\n // When changing this logic, you might want to also\n // update consoleWithStackDev.www.js as well.\n {\n var ReactDebugCurrentFrame = ReactSharedInternals.ReactDebugCurrentFrame;\n var stack = ReactDebugCurrentFrame.getStackAddendum();\n\n if (stack !== '') {\n format += '%s';\n args = args.concat([stack]);\n }\n\n var argsWithFormat = args.map(function (item) {\n return '' + item;\n }); // Careful: RN currently depends on this prefix\n\n argsWithFormat.unshift('Warning: ' + format); // We intentionally don't use spread (or .apply) directly because it\n // breaks IE9: https://github.com/facebook/react/issues/13610\n // eslint-disable-next-line react-internal/no-production-logging\n\n Function.prototype.apply.call(console[level], console, argsWithFormat);\n }\n}\n\n// Filter certain DOM attributes (e.g. src, href) if their values are empty strings.\n\nvar enableScopeAPI = false; // Experimental Create Event Handle API.\n\nfunction isValidElementType(type) {\n if (typeof type === 'string' || typeof type === 'function') {\n return true;\n } // Note: typeof might be other than 'symbol' or 'number' (e.g. if it's a polyfill).\n\n\n if (type === exports.Fragment || type === REACT_PROFILER_TYPE || type === REACT_DEBUG_TRACING_MODE_TYPE || type === REACT_STRICT_MODE_TYPE || type === REACT_SUSPENSE_TYPE || type === REACT_SUSPENSE_LIST_TYPE || type === REACT_LEGACY_HIDDEN_TYPE || enableScopeAPI ) {\n return true;\n }\n\n if (typeof type === 'object' && type !== null) {\n if (type.$$typeof === REACT_LAZY_TYPE || type.$$typeof === REACT_MEMO_TYPE || type.$$typeof === REACT_PROVIDER_TYPE || type.$$typeof === REACT_CONTEXT_TYPE || type.$$typeof === REACT_FORWARD_REF_TYPE || type.$$typeof === REACT_FUNDAMENTAL_TYPE || type.$$typeof === REACT_BLOCK_TYPE || type[0] === REACT_SERVER_BLOCK_TYPE) {\n return true;\n }\n }\n\n return false;\n}\n\nfunction getWrappedName(outerType, innerType, wrapperName) {\n var functionName = innerType.displayName || innerType.name || '';\n return outerType.displayName || (functionName !== '' ? wrapperName + \"(\" + functionName + \")\" : wrapperName);\n}\n\nfunction getContextName(type) {\n return type.displayName || 'Context';\n}\n\nfunction getComponentName(type) {\n if (type == null) {\n // Host root, text node or just invalid type.\n return null;\n }\n\n {\n if (typeof type.tag === 'number') {\n error('Received an unexpected object in getComponentName(). ' + 'This is likely a bug in React. Please file an issue.');\n }\n }\n\n if (typeof type === 'function') {\n return type.displayName || type.name || null;\n }\n\n if (typeof type === 'string') {\n return type;\n }\n\n switch (type) {\n case exports.Fragment:\n return 'Fragment';\n\n case REACT_PORTAL_TYPE:\n return 'Portal';\n\n case REACT_PROFILER_TYPE:\n return 'Profiler';\n\n case REACT_STRICT_MODE_TYPE:\n return 'StrictMode';\n\n case REACT_SUSPENSE_TYPE:\n return 'Suspense';\n\n case REACT_SUSPENSE_LIST_TYPE:\n return 'SuspenseList';\n }\n\n if (typeof type === 'object') {\n switch (type.$$typeof) {\n case REACT_CONTEXT_TYPE:\n var context = type;\n return getContextName(context) + '.Consumer';\n\n case REACT_PROVIDER_TYPE:\n var provider = type;\n return getContextName(provider._context) + '.Provider';\n\n case REACT_FORWARD_REF_TYPE:\n return getWrappedName(type, type.render, 'ForwardRef');\n\n case REACT_MEMO_TYPE:\n return getComponentName(type.type);\n\n case REACT_BLOCK_TYPE:\n return getComponentName(type._render);\n\n case REACT_LAZY_TYPE:\n {\n var lazyComponent = type;\n var payload = lazyComponent._payload;\n var init = lazyComponent._init;\n\n try {\n return getComponentName(init(payload));\n } catch (x) {\n return null;\n }\n }\n }\n }\n\n return null;\n}\n\n// Helpers to patch console.logs to avoid logging during side-effect free\n// replaying on render function. This currently only patches the object\n// lazily which won't cover if the log function was extracted eagerly.\n// We could also eagerly patch the method.\nvar disabledDepth = 0;\nvar prevLog;\nvar prevInfo;\nvar prevWarn;\nvar prevError;\nvar prevGroup;\nvar prevGroupCollapsed;\nvar prevGroupEnd;\n\nfunction disabledLog() {}\n\ndisabledLog.__reactDisabledLog = true;\nfunction disableLogs() {\n {\n if (disabledDepth === 0) {\n /* eslint-disable react-internal/no-production-logging */\n prevLog = console.log;\n prevInfo = console.info;\n prevWarn = console.warn;\n prevError = console.error;\n prevGroup = console.group;\n prevGroupCollapsed = console.groupCollapsed;\n prevGroupEnd = console.groupEnd; // https://github.com/facebook/react/issues/19099\n\n var props = {\n configurable: true,\n enumerable: true,\n value: disabledLog,\n writable: true\n }; // $FlowFixMe Flow thinks console is immutable.\n\n Object.defineProperties(console, {\n info: props,\n log: props,\n warn: props,\n error: props,\n group: props,\n groupCollapsed: props,\n groupEnd: props\n });\n /* eslint-enable react-internal/no-production-logging */\n }\n\n disabledDepth++;\n }\n}\nfunction reenableLogs() {\n {\n disabledDepth--;\n\n if (disabledDepth === 0) {\n /* eslint-disable react-internal/no-production-logging */\n var props = {\n configurable: true,\n enumerable: true,\n writable: true\n }; // $FlowFixMe Flow thinks console is immutable.\n\n Object.defineProperties(console, {\n log: _assign({}, props, {\n value: prevLog\n }),\n info: _assign({}, props, {\n value: prevInfo\n }),\n warn: _assign({}, props, {\n value: prevWarn\n }),\n error: _assign({}, props, {\n value: prevError\n }),\n group: _assign({}, props, {\n value: prevGroup\n }),\n groupCollapsed: _assign({}, props, {\n value: prevGroupCollapsed\n }),\n groupEnd: _assign({}, props, {\n value: prevGroupEnd\n })\n });\n /* eslint-enable react-internal/no-production-logging */\n }\n\n if (disabledDepth < 0) {\n error('disabledDepth fell below zero. ' + 'This is a bug in React. Please file an issue.');\n }\n }\n}\n\nvar ReactCurrentDispatcher = ReactSharedInternals.ReactCurrentDispatcher;\nvar prefix;\nfunction describeBuiltInComponentFrame(name, source, ownerFn) {\n {\n if (prefix === undefined) {\n // Extract the VM specific prefix used by each line.\n try {\n throw Error();\n } catch (x) {\n var match = x.stack.trim().match(/\\n( *(at )?)/);\n prefix = match && match[1] || '';\n }\n } // We use the prefix to ensure our stacks line up with native stack frames.\n\n\n return '\\n' + prefix + name;\n }\n}\nvar reentry = false;\nvar componentFrameCache;\n\n{\n var PossiblyWeakMap = typeof WeakMap === 'function' ? WeakMap : Map;\n componentFrameCache = new PossiblyWeakMap();\n}\n\nfunction describeNativeComponentFrame(fn, construct) {\n // If something asked for a stack inside a fake render, it should get ignored.\n if (!fn || reentry) {\n return '';\n }\n\n {\n var frame = componentFrameCache.get(fn);\n\n if (frame !== undefined) {\n return frame;\n }\n }\n\n var control;\n reentry = true;\n var previousPrepareStackTrace = Error.prepareStackTrace; // $FlowFixMe It does accept undefined.\n\n Error.prepareStackTrace = undefined;\n var previousDispatcher;\n\n {\n previousDispatcher = ReactCurrentDispatcher.current; // Set the dispatcher in DEV because this might be call in the render function\n // for warnings.\n\n ReactCurrentDispatcher.current = null;\n disableLogs();\n }\n\n try {\n // This should throw.\n if (construct) {\n // Something should be setting the props in the constructor.\n var Fake = function () {\n throw Error();\n }; // $FlowFixMe\n\n\n Object.defineProperty(Fake.prototype, 'props', {\n set: function () {\n // We use a throwing setter instead of frozen or non-writable props\n // because that won't throw in a non-strict mode function.\n throw Error();\n }\n });\n\n if (typeof Reflect === 'object' && Reflect.construct) {\n // We construct a different control for this case to include any extra\n // frames added by the construct call.\n try {\n Reflect.construct(Fake, []);\n } catch (x) {\n control = x;\n }\n\n Reflect.construct(fn, [], Fake);\n } else {\n try {\n Fake.call();\n } catch (x) {\n control = x;\n }\n\n fn.call(Fake.prototype);\n }\n } else {\n try {\n throw Error();\n } catch (x) {\n control = x;\n }\n\n fn();\n }\n } catch (sample) {\n // This is inlined manually because closure doesn't do it for us.\n if (sample && control && typeof sample.stack === 'string') {\n // This extracts the first frame from the sample that isn't also in the control.\n // Skipping one frame that we assume is the frame that calls the two.\n var sampleLines = sample.stack.split('\\n');\n var controlLines = control.stack.split('\\n');\n var s = sampleLines.length - 1;\n var c = controlLines.length - 1;\n\n while (s >= 1 && c >= 0 && sampleLines[s] !== controlLines[c]) {\n // We expect at least one stack frame to be shared.\n // Typically this will be the root most one. However, stack frames may be\n // cut off due to maximum stack limits. In this case, one maybe cut off\n // earlier than the other. We assume that the sample is longer or the same\n // and there for cut off earlier. So we should find the root most frame in\n // the sample somewhere in the control.\n c--;\n }\n\n for (; s >= 1 && c >= 0; s--, c--) {\n // Next we find the first one that isn't the same which should be the\n // frame that called our sample function and the control.\n if (sampleLines[s] !== controlLines[c]) {\n // In V8, the first line is describing the message but other VMs don't.\n // If we're about to return the first line, and the control is also on the same\n // line, that's a pretty good indicator that our sample threw at same line as\n // the control. I.e. before we entered the sample frame. So we ignore this result.\n // This can happen if you passed a class to function component, or non-function.\n if (s !== 1 || c !== 1) {\n do {\n s--;\n c--; // We may still have similar intermediate frames from the construct call.\n // The next one that isn't the same should be our match though.\n\n if (c < 0 || sampleLines[s] !== controlLines[c]) {\n // V8 adds a \"new\" prefix for native classes. Let's remove it to make it prettier.\n var _frame = '\\n' + sampleLines[s].replace(' at new ', ' at ');\n\n {\n if (typeof fn === 'function') {\n componentFrameCache.set(fn, _frame);\n }\n } // Return the line we found.\n\n\n return _frame;\n }\n } while (s >= 1 && c >= 0);\n }\n\n break;\n }\n }\n }\n } finally {\n reentry = false;\n\n {\n ReactCurrentDispatcher.current = previousDispatcher;\n reenableLogs();\n }\n\n Error.prepareStackTrace = previousPrepareStackTrace;\n } // Fallback to just using the name if we couldn't make it throw.\n\n\n var name = fn ? fn.displayName || fn.name : '';\n var syntheticFrame = name ? describeBuiltInComponentFrame(name) : '';\n\n {\n if (typeof fn === 'function') {\n componentFrameCache.set(fn, syntheticFrame);\n }\n }\n\n return syntheticFrame;\n}\nfunction describeFunctionComponentFrame(fn, source, ownerFn) {\n {\n return describeNativeComponentFrame(fn, false);\n }\n}\n\nfunction shouldConstruct(Component) {\n var prototype = Component.prototype;\n return !!(prototype && prototype.isReactComponent);\n}\n\nfunction describeUnknownElementTypeFrameInDEV(type, source, ownerFn) {\n\n if (type == null) {\n return '';\n }\n\n if (typeof type === 'function') {\n {\n return describeNativeComponentFrame(type, shouldConstruct(type));\n }\n }\n\n if (typeof type === 'string') {\n return describeBuiltInComponentFrame(type);\n }\n\n switch (type) {\n case REACT_SUSPENSE_TYPE:\n return describeBuiltInComponentFrame('Suspense');\n\n case REACT_SUSPENSE_LIST_TYPE:\n return describeBuiltInComponentFrame('SuspenseList');\n }\n\n if (typeof type === 'object') {\n switch (type.$$typeof) {\n case REACT_FORWARD_REF_TYPE:\n return describeFunctionComponentFrame(type.render);\n\n case REACT_MEMO_TYPE:\n // Memo may contain any component type so we recursively resolve it.\n return describeUnknownElementTypeFrameInDEV(type.type, source, ownerFn);\n\n case REACT_BLOCK_TYPE:\n return describeFunctionComponentFrame(type._render);\n\n case REACT_LAZY_TYPE:\n {\n var lazyComponent = type;\n var payload = lazyComponent._payload;\n var init = lazyComponent._init;\n\n try {\n // Lazy may contain any component type so we recursively resolve it.\n return describeUnknownElementTypeFrameInDEV(init(payload), source, ownerFn);\n } catch (x) {}\n }\n }\n }\n\n return '';\n}\n\nvar loggedTypeFailures = {};\nvar ReactDebugCurrentFrame = ReactSharedInternals.ReactDebugCurrentFrame;\n\nfunction setCurrentlyValidatingElement(element) {\n {\n if (element) {\n var owner = element._owner;\n var stack = describeUnknownElementTypeFrameInDEV(element.type, element._source, owner ? owner.type : null);\n ReactDebugCurrentFrame.setExtraStackFrame(stack);\n } else {\n ReactDebugCurrentFrame.setExtraStackFrame(null);\n }\n }\n}\n\nfunction checkPropTypes(typeSpecs, values, location, componentName, element) {\n {\n // $FlowFixMe This is okay but Flow doesn't know it.\n var has = Function.call.bind(Object.prototype.hasOwnProperty);\n\n for (var typeSpecName in typeSpecs) {\n if (has(typeSpecs, typeSpecName)) {\n var error$1 = void 0; // Prop type validation may throw. In case they do, we don't want to\n // fail the render phase where it didn't fail before. So we log it.\n // After these have been cleaned up, we'll let them throw.\n\n try {\n // This is intentionally an invariant that gets caught. It's the same\n // behavior as without this statement except with a better message.\n if (typeof typeSpecs[typeSpecName] !== 'function') {\n var err = Error((componentName || 'React class') + ': ' + location + ' type `' + typeSpecName + '` is invalid; ' + 'it must be a function, usually from the `prop-types` package, but received `' + typeof typeSpecs[typeSpecName] + '`.' + 'This often happens because of typos such as `PropTypes.function` instead of `PropTypes.func`.');\n err.name = 'Invariant Violation';\n throw err;\n }\n\n error$1 = typeSpecs[typeSpecName](values, typeSpecName, componentName, location, null, 'SECRET_DO_NOT_PASS_THIS_OR_YOU_WILL_BE_FIRED');\n } catch (ex) {\n error$1 = ex;\n }\n\n if (error$1 && !(error$1 instanceof Error)) {\n setCurrentlyValidatingElement(element);\n\n error('%s: type specification of %s' + ' `%s` is invalid; the type checker ' + 'function must return `null` or an `Error` but returned a %s. ' + 'You may have forgotten to pass an argument to the type checker ' + 'creator (arrayOf, instanceOf, objectOf, oneOf, oneOfType, and ' + 'shape all require an argument).', componentName || 'React class', location, typeSpecName, typeof error$1);\n\n setCurrentlyValidatingElement(null);\n }\n\n if (error$1 instanceof Error && !(error$1.message in loggedTypeFailures)) {\n // Only monitor this failure once because there tends to be a lot of the\n // same error.\n loggedTypeFailures[error$1.message] = true;\n setCurrentlyValidatingElement(element);\n\n error('Failed %s type: %s', location, error$1.message);\n\n setCurrentlyValidatingElement(null);\n }\n }\n }\n }\n}\n\nvar ReactCurrentOwner = ReactSharedInternals.ReactCurrentOwner;\nvar hasOwnProperty = Object.prototype.hasOwnProperty;\nvar RESERVED_PROPS = {\n key: true,\n ref: true,\n __self: true,\n __source: true\n};\nvar specialPropKeyWarningShown;\nvar specialPropRefWarningShown;\nvar didWarnAboutStringRefs;\n\n{\n didWarnAboutStringRefs = {};\n}\n\nfunction hasValidRef(config) {\n {\n if (hasOwnProperty.call(config, 'ref')) {\n var getter = Object.getOwnPropertyDescriptor(config, 'ref').get;\n\n if (getter && getter.isReactWarning) {\n return false;\n }\n }\n }\n\n return config.ref !== undefined;\n}\n\nfunction hasValidKey(config) {\n {\n if (hasOwnProperty.call(config, 'key')) {\n var getter = Object.getOwnPropertyDescriptor(config, 'key').get;\n\n if (getter && getter.isReactWarning) {\n return false;\n }\n }\n }\n\n return config.key !== undefined;\n}\n\nfunction warnIfStringRefCannotBeAutoConverted(config, self) {\n {\n if (typeof config.ref === 'string' && ReactCurrentOwner.current && self && ReactCurrentOwner.current.stateNode !== self) {\n var componentName = getComponentName(ReactCurrentOwner.current.type);\n\n if (!didWarnAboutStringRefs[componentName]) {\n error('Component \"%s\" contains the string ref \"%s\". ' + 'Support for string refs will be removed in a future major release. ' + 'This case cannot be automatically converted to an arrow function. ' + 'We ask you to manually fix this case by using useRef() or createRef() instead. ' + 'Learn more about using refs safely here: ' + 'https://reactjs.org/link/strict-mode-string-ref', getComponentName(ReactCurrentOwner.current.type), config.ref);\n\n didWarnAboutStringRefs[componentName] = true;\n }\n }\n }\n}\n\nfunction defineKeyPropWarningGetter(props, displayName) {\n {\n var warnAboutAccessingKey = function () {\n if (!specialPropKeyWarningShown) {\n specialPropKeyWarningShown = true;\n\n error('%s: `key` is not a prop. Trying to access it will result ' + 'in `undefined` being returned. If you need to access the same ' + 'value within the child component, you should pass it as a different ' + 'prop. (https://reactjs.org/link/special-props)', displayName);\n }\n };\n\n warnAboutAccessingKey.isReactWarning = true;\n Object.defineProperty(props, 'key', {\n get: warnAboutAccessingKey,\n configurable: true\n });\n }\n}\n\nfunction defineRefPropWarningGetter(props, displayName) {\n {\n var warnAboutAccessingRef = function () {\n if (!specialPropRefWarningShown) {\n specialPropRefWarningShown = true;\n\n error('%s: `ref` is not a prop. Trying to access it will result ' + 'in `undefined` being returned. If you need to access the same ' + 'value within the child component, you should pass it as a different ' + 'prop. (https://reactjs.org/link/special-props)', displayName);\n }\n };\n\n warnAboutAccessingRef.isReactWarning = true;\n Object.defineProperty(props, 'ref', {\n get: warnAboutAccessingRef,\n configurable: true\n });\n }\n}\n/**\n * Factory method to create a new React element. This no longer adheres to\n * the class pattern, so do not use new to call it. Also, instanceof check\n * will not work. Instead test $$typeof field against Symbol.for('react.element') to check\n * if something is a React Element.\n *\n * @param {*} type\n * @param {*} props\n * @param {*} key\n * @param {string|object} ref\n * @param {*} owner\n * @param {*} self A *temporary* helper to detect places where `this` is\n * different from the `owner` when React.createElement is called, so that we\n * can warn. We want to get rid of owner and replace string `ref`s with arrow\n * functions, and as long as `this` and owner are the same, there will be no\n * change in behavior.\n * @param {*} source An annotation object (added by a transpiler or otherwise)\n * indicating filename, line number, and/or other information.\n * @internal\n */\n\n\nvar ReactElement = function (type, key, ref, self, source, owner, props) {\n var element = {\n // This tag allows us to uniquely identify this as a React Element\n $$typeof: REACT_ELEMENT_TYPE,\n // Built-in properties that belong on the element\n type: type,\n key: key,\n ref: ref,\n props: props,\n // Record the component responsible for creating this element.\n _owner: owner\n };\n\n {\n // The validation flag is currently mutative. We put it on\n // an external backing store so that we can freeze the whole object.\n // This can be replaced with a WeakMap once they are implemented in\n // commonly used development environments.\n element._store = {}; // To make comparing ReactElements easier for testing purposes, we make\n // the validation flag non-enumerable (where possible, which should\n // include every environment we run tests in), so the test framework\n // ignores it.\n\n Object.defineProperty(element._store, 'validated', {\n configurable: false,\n enumerable: false,\n writable: true,\n value: false\n }); // self and source are DEV only properties.\n\n Object.defineProperty(element, '_self', {\n configurable: false,\n enumerable: false,\n writable: false,\n value: self\n }); // Two elements created in two different places should be considered\n // equal for testing purposes and therefore we hide it from enumeration.\n\n Object.defineProperty(element, '_source', {\n configurable: false,\n enumerable: false,\n writable: false,\n value: source\n });\n\n if (Object.freeze) {\n Object.freeze(element.props);\n Object.freeze(element);\n }\n }\n\n return element;\n};\n/**\n * https://github.com/reactjs/rfcs/pull/107\n * @param {*} type\n * @param {object} props\n * @param {string} key\n */\n\nfunction jsxDEV(type, config, maybeKey, source, self) {\n {\n var propName; // Reserved names are extracted\n\n var props = {};\n var key = null;\n var ref = null; // Currently, key can be spread in as a prop. This causes a potential\n // issue if key is also explicitly declared (ie.
\n // or
). We want to deprecate key spread,\n // but as an intermediary step, we will use jsxDEV for everything except\n //
, because we aren't currently able to tell if\n // key is explicitly declared to be undefined or not.\n\n if (maybeKey !== undefined) {\n key = '' + maybeKey;\n }\n\n if (hasValidKey(config)) {\n key = '' + config.key;\n }\n\n if (hasValidRef(config)) {\n ref = config.ref;\n warnIfStringRefCannotBeAutoConverted(config, self);\n } // Remaining properties are added to a new props object\n\n\n for (propName in config) {\n if (hasOwnProperty.call(config, propName) && !RESERVED_PROPS.hasOwnProperty(propName)) {\n props[propName] = config[propName];\n }\n } // Resolve default props\n\n\n if (type && type.defaultProps) {\n var defaultProps = type.defaultProps;\n\n for (propName in defaultProps) {\n if (props[propName] === undefined) {\n props[propName] = defaultProps[propName];\n }\n }\n }\n\n if (key || ref) {\n var displayName = typeof type === 'function' ? type.displayName || type.name || 'Unknown' : type;\n\n if (key) {\n defineKeyPropWarningGetter(props, displayName);\n }\n\n if (ref) {\n defineRefPropWarningGetter(props, displayName);\n }\n }\n\n return ReactElement(type, key, ref, self, source, ReactCurrentOwner.current, props);\n }\n}\n\nvar ReactCurrentOwner$1 = ReactSharedInternals.ReactCurrentOwner;\nvar ReactDebugCurrentFrame$1 = ReactSharedInternals.ReactDebugCurrentFrame;\n\nfunction setCurrentlyValidatingElement$1(element) {\n {\n if (element) {\n var owner = element._owner;\n var stack = describeUnknownElementTypeFrameInDEV(element.type, element._source, owner ? owner.type : null);\n ReactDebugCurrentFrame$1.setExtraStackFrame(stack);\n } else {\n ReactDebugCurrentFrame$1.setExtraStackFrame(null);\n }\n }\n}\n\nvar propTypesMisspellWarningShown;\n\n{\n propTypesMisspellWarningShown = false;\n}\n/**\n * Verifies the object is a ReactElement.\n * See https://reactjs.org/docs/react-api.html#isvalidelement\n * @param {?object} object\n * @return {boolean} True if `object` is a ReactElement.\n * @final\n */\n\nfunction isValidElement(object) {\n {\n return typeof object === 'object' && object !== null && object.$$typeof === REACT_ELEMENT_TYPE;\n }\n}\n\nfunction getDeclarationErrorAddendum() {\n {\n if (ReactCurrentOwner$1.current) {\n var name = getComponentName(ReactCurrentOwner$1.current.type);\n\n if (name) {\n return '\\n\\nCheck the render method of `' + name + '`.';\n }\n }\n\n return '';\n }\n}\n\nfunction getSourceInfoErrorAddendum(source) {\n {\n if (source !== undefined) {\n var fileName = source.fileName.replace(/^.*[\\\\\\/]/, '');\n var lineNumber = source.lineNumber;\n return '\\n\\nCheck your code at ' + fileName + ':' + lineNumber + '.';\n }\n\n return '';\n }\n}\n/**\n * Warn if there's no key explicitly set on dynamic arrays of children or\n * object keys are not valid. This allows us to keep track of children between\n * updates.\n */\n\n\nvar ownerHasKeyUseWarning = {};\n\nfunction getCurrentComponentErrorInfo(parentType) {\n {\n var info = getDeclarationErrorAddendum();\n\n if (!info) {\n var parentName = typeof parentType === 'string' ? parentType : parentType.displayName || parentType.name;\n\n if (parentName) {\n info = \"\\n\\nCheck the top-level render call using <\" + parentName + \">.\";\n }\n }\n\n return info;\n }\n}\n/**\n * Warn if the element doesn't have an explicit key assigned to it.\n * This element is in an array. The array could grow and shrink or be\n * reordered. All children that haven't already been validated are required to\n * have a \"key\" property assigned to it. Error statuses are cached so a warning\n * will only be shown once.\n *\n * @internal\n * @param {ReactElement} element Element that requires a key.\n * @param {*} parentType element's parent's type.\n */\n\n\nfunction validateExplicitKey(element, parentType) {\n {\n if (!element._store || element._store.validated || element.key != null) {\n return;\n }\n\n element._store.validated = true;\n var currentComponentErrorInfo = getCurrentComponentErrorInfo(parentType);\n\n if (ownerHasKeyUseWarning[currentComponentErrorInfo]) {\n return;\n }\n\n ownerHasKeyUseWarning[currentComponentErrorInfo] = true; // Usually the current owner is the offender, but if it accepts children as a\n // property, it may be the creator of the child that's responsible for\n // assigning it a key.\n\n var childOwner = '';\n\n if (element && element._owner && element._owner !== ReactCurrentOwner$1.current) {\n // Give the component that originally created this child.\n childOwner = \" It was passed a child from \" + getComponentName(element._owner.type) + \".\";\n }\n\n setCurrentlyValidatingElement$1(element);\n\n error('Each child in a list should have a unique \"key\" prop.' + '%s%s See https://reactjs.org/link/warning-keys for more information.', currentComponentErrorInfo, childOwner);\n\n setCurrentlyValidatingElement$1(null);\n }\n}\n/**\n * Ensure that every element either is passed in a static location, in an\n * array with an explicit keys property defined, or in an object literal\n * with valid key property.\n *\n * @internal\n * @param {ReactNode} node Statically passed child of any type.\n * @param {*} parentType node's parent's type.\n */\n\n\nfunction validateChildKeys(node, parentType) {\n {\n if (typeof node !== 'object') {\n return;\n }\n\n if (Array.isArray(node)) {\n for (var i = 0; i < node.length; i++) {\n var child = node[i];\n\n if (isValidElement(child)) {\n validateExplicitKey(child, parentType);\n }\n }\n } else if (isValidElement(node)) {\n // This element was passed in a valid location.\n if (node._store) {\n node._store.validated = true;\n }\n } else if (node) {\n var iteratorFn = getIteratorFn(node);\n\n if (typeof iteratorFn === 'function') {\n // Entry iterators used to provide implicit keys,\n // but now we print a separate warning for them later.\n if (iteratorFn !== node.entries) {\n var iterator = iteratorFn.call(node);\n var step;\n\n while (!(step = iterator.next()).done) {\n if (isValidElement(step.value)) {\n validateExplicitKey(step.value, parentType);\n }\n }\n }\n }\n }\n }\n}\n/**\n * Given an element, validate that its props follow the propTypes definition,\n * provided by the type.\n *\n * @param {ReactElement} element\n */\n\n\nfunction validatePropTypes(element) {\n {\n var type = element.type;\n\n if (type === null || type === undefined || typeof type === 'string') {\n return;\n }\n\n var propTypes;\n\n if (typeof type === 'function') {\n propTypes = type.propTypes;\n } else if (typeof type === 'object' && (type.$$typeof === REACT_FORWARD_REF_TYPE || // Note: Memo only checks outer props here.\n // Inner props are checked in the reconciler.\n type.$$typeof === REACT_MEMO_TYPE)) {\n propTypes = type.propTypes;\n } else {\n return;\n }\n\n if (propTypes) {\n // Intentionally inside to avoid triggering lazy initializers:\n var name = getComponentName(type);\n checkPropTypes(propTypes, element.props, 'prop', name, element);\n } else if (type.PropTypes !== undefined && !propTypesMisspellWarningShown) {\n propTypesMisspellWarningShown = true; // Intentionally inside to avoid triggering lazy initializers:\n\n var _name = getComponentName(type);\n\n error('Component %s declared `PropTypes` instead of `propTypes`. Did you misspell the property assignment?', _name || 'Unknown');\n }\n\n if (typeof type.getDefaultProps === 'function' && !type.getDefaultProps.isReactClassApproved) {\n error('getDefaultProps is only used on classic React.createClass ' + 'definitions. Use a static property named `defaultProps` instead.');\n }\n }\n}\n/**\n * Given a fragment, validate that it can only be provided with fragment props\n * @param {ReactElement} fragment\n */\n\n\nfunction validateFragmentProps(fragment) {\n {\n var keys = Object.keys(fragment.props);\n\n for (var i = 0; i < keys.length; i++) {\n var key = keys[i];\n\n if (key !== 'children' && key !== 'key') {\n setCurrentlyValidatingElement$1(fragment);\n\n error('Invalid prop `%s` supplied to `React.Fragment`. ' + 'React.Fragment can only have `key` and `children` props.', key);\n\n setCurrentlyValidatingElement$1(null);\n break;\n }\n }\n\n if (fragment.ref !== null) {\n setCurrentlyValidatingElement$1(fragment);\n\n error('Invalid attribute `ref` supplied to `React.Fragment`.');\n\n setCurrentlyValidatingElement$1(null);\n }\n }\n}\n\nfunction jsxWithValidation(type, props, key, isStaticChildren, source, self) {\n {\n var validType = isValidElementType(type); // We warn in this case but don't throw. We expect the element creation to\n // succeed and there will likely be errors in render.\n\n if (!validType) {\n var info = '';\n\n if (type === undefined || typeof type === 'object' && type !== null && Object.keys(type).length === 0) {\n info += ' You likely forgot to export your component from the file ' + \"it's defined in, or you might have mixed up default and named imports.\";\n }\n\n var sourceInfo = getSourceInfoErrorAddendum(source);\n\n if (sourceInfo) {\n info += sourceInfo;\n } else {\n info += getDeclarationErrorAddendum();\n }\n\n var typeString;\n\n if (type === null) {\n typeString = 'null';\n } else if (Array.isArray(type)) {\n typeString = 'array';\n } else if (type !== undefined && type.$$typeof === REACT_ELEMENT_TYPE) {\n typeString = \"<\" + (getComponentName(type.type) || 'Unknown') + \" />\";\n info = ' Did you accidentally export a JSX literal instead of a component?';\n } else {\n typeString = typeof type;\n }\n\n error('React.jsx: type is invalid -- expected a string (for ' + 'built-in components) or a class/function (for composite ' + 'components) but got: %s.%s', typeString, info);\n }\n\n var element = jsxDEV(type, props, key, source, self); // The result can be nullish if a mock or a custom function is used.\n // TODO: Drop this when these are no longer allowed as the type argument.\n\n if (element == null) {\n return element;\n } // Skip key warning if the type isn't valid since our key validation logic\n // doesn't expect a non-string/function type and can throw confusing errors.\n // We don't want exception behavior to differ between dev and prod.\n // (Rendering will throw with a helpful message and as soon as the type is\n // fixed, the key warnings will appear.)\n\n\n if (validType) {\n var children = props.children;\n\n if (children !== undefined) {\n if (isStaticChildren) {\n if (Array.isArray(children)) {\n for (var i = 0; i < children.length; i++) {\n validateChildKeys(children[i], type);\n }\n\n if (Object.freeze) {\n Object.freeze(children);\n }\n } else {\n error('React.jsx: Static children should always be an array. ' + 'You are likely explicitly calling React.jsxs or React.jsxDEV. ' + 'Use the Babel transform instead.');\n }\n } else {\n validateChildKeys(children, type);\n }\n }\n }\n\n if (type === exports.Fragment) {\n validateFragmentProps(element);\n } else {\n validatePropTypes(element);\n }\n\n return element;\n }\n} // These two functions exist to still get child warnings in dev\n// even with the prod transform. This means that jsxDEV is purely\n// opt-in behavior for better messages but that we won't stop\n// giving you warnings if you use production apis.\n\nfunction jsxWithValidationStatic(type, props, key) {\n {\n return jsxWithValidation(type, props, key, true);\n }\n}\nfunction jsxWithValidationDynamic(type, props, key) {\n {\n return jsxWithValidation(type, props, key, false);\n }\n}\n\nvar jsx = jsxWithValidationDynamic ; // we may want to special case jsxs internally to take advantage of static children.\n// for now we can ship identical prod functions\n\nvar jsxs = jsxWithValidationStatic ;\n\nexports.jsx = jsx;\nexports.jsxs = jsxs;\n })();\n}\n","'use strict';\n\nif (process.env.NODE_ENV === 'production') {\n module.exports = require('./cjs/react-jsx-runtime.production.min.js');\n} else {\n module.exports = require('./cjs/react-jsx-runtime.development.js');\n}\n","module.exports = window[\"React\"];","module.exports = window[\"ReactDOM\"];","module.exports = window[\"jQuery\"];","module.exports = window[\"wp\"][\"i18n\"];","// src/styled.ts\nimport validAttr from \"@emotion/is-prop-valid\";\nimport React from \"react\";\nimport { cx } from \"@linaria/core\";\nvar isCapital = (ch) => ch.toUpperCase() === ch;\nvar filterKey = (keys) => (key) => keys.indexOf(key) === -1;\nvar omit = (obj, keys) => {\n const res = {};\n Object.keys(obj).filter(filterKey(keys)).forEach((key) => {\n res[key] = obj[key];\n });\n return res;\n};\nfunction filterProps(asIs, props, omitKeys) {\n const filteredProps = omit(props, omitKeys);\n if (!asIs) {\n const interopValidAttr = typeof validAttr === \"function\" ? { default: validAttr } : validAttr;\n Object.keys(filteredProps).forEach((key) => {\n if (!interopValidAttr.default(key)) {\n delete filteredProps[key];\n }\n });\n }\n return filteredProps;\n}\nvar warnIfInvalid = (value, componentName) => {\n if (process.env.NODE_ENV !== \"production\") {\n if (typeof value === \"string\" || typeof value === \"number\" && isFinite(value)) {\n return;\n }\n const stringified = typeof value === \"object\" ? JSON.stringify(value) : String(value);\n console.warn(\n `An interpolation evaluated to '${stringified}' in the component '${componentName}', which is probably a mistake. You should explicitly cast or transform the value to a string.`\n );\n }\n};\nfunction styled(tag) {\n return (options) => {\n if (process.env.NODE_ENV !== \"production\") {\n if (Array.isArray(options)) {\n throw new Error(\n 'Using the \"styled\" tag in runtime is not supported. Make sure you have set up the Babel plugin correctly. See https://github.com/callstack/linaria#setup'\n );\n }\n }\n const render = (props, ref) => {\n const { as: component = tag, class: className } = props;\n const shouldKeepProps = options.propsAsIs === void 0 ? !(typeof component === \"string\" && component.indexOf(\"-\") === -1 && !isCapital(component[0])) : options.propsAsIs;\n const filteredProps = filterProps(shouldKeepProps, props, [\n \"as\",\n \"class\"\n ]);\n filteredProps.ref = ref;\n filteredProps.className = options.atomic ? cx(options.class, filteredProps.className || className) : cx(filteredProps.className || className, options.class);\n const { vars } = options;\n if (vars) {\n const style = {};\n for (const name in vars) {\n const variable = vars[name];\n const result = variable[0];\n const unit = variable[1] || \"\";\n const value = typeof result === \"function\" ? result(props) : result;\n warnIfInvalid(value, options.name);\n style[`--${name}`] = `${value}${unit}`;\n }\n const ownStyle = filteredProps.style || {};\n const keys = Object.keys(ownStyle);\n if (keys.length > 0) {\n keys.forEach((key) => {\n style[key] = ownStyle[key];\n });\n }\n filteredProps.style = style;\n }\n if (tag.__linaria && tag !== component) {\n filteredProps.as = component;\n return React.createElement(tag, filteredProps);\n }\n return React.createElement(component, filteredProps);\n };\n const Result = React.forwardRef ? React.forwardRef(render) : (props) => {\n const rest = omit(props, [\"innerRef\"]);\n return render(rest, props.innerRef);\n };\n Result.displayName = options.name;\n Result.__linaria = {\n className: options.class,\n extends: tag\n };\n return Result;\n };\n}\nvar styled_default = process.env.NODE_ENV !== \"production\" ? new Proxy(styled, {\n get(o, prop) {\n return o(prop);\n }\n}) : styled;\nexport {\n styled_default as styled\n};\n//# sourceMappingURL=index.mjs.map","// src/css.ts\nvar css = () => {\n throw new Error(\n 'Using the \"css\" tag in runtime is not supported. Make sure you have set up the Babel plugin correctly.'\n );\n};\nvar css_default = css;\n\n// src/cx.ts\nvar cx = function cx2() {\n const presentClassNames = Array.prototype.slice.call(arguments).filter(Boolean);\n const atomicClasses = {};\n const nonAtomicClasses = [];\n presentClassNames.forEach((arg) => {\n const individualClassNames = arg ? arg.split(\" \") : [];\n individualClassNames.forEach((className) => {\n if (className.startsWith(\"atm_\")) {\n const [, keyHash] = className.split(\"_\");\n atomicClasses[keyHash] = className;\n } else {\n nonAtomicClasses.push(className);\n }\n });\n });\n const result = [];\n for (const keyHash in atomicClasses) {\n if (Object.prototype.hasOwnProperty.call(atomicClasses, keyHash)) {\n result.push(atomicClasses[keyHash]);\n }\n }\n result.push(...nonAtomicClasses);\n return result.join(\" \");\n};\nvar cx_default = cx;\nexport {\n css_default as css,\n cx_default as cx\n};\n//# sourceMappingURL=index.mjs.map","// The module cache\nvar __webpack_module_cache__ = {};\n\n// The require function\nfunction __webpack_require__(moduleId) {\n\t// Check if module is in cache\n\tvar cachedModule = __webpack_module_cache__[moduleId];\n\tif (cachedModule !== undefined) {\n\t\treturn cachedModule.exports;\n\t}\n\t// Create a new module (and put it into the cache)\n\tvar module = __webpack_module_cache__[moduleId] = {\n\t\t// no module.id needed\n\t\t// no module.loaded needed\n\t\texports: {}\n\t};\n\n\t// Execute the module function\n\t__webpack_modules__[moduleId](module, module.exports, __webpack_require__);\n\n\t// Return the exports of the module\n\treturn module.exports;\n}\n\n","// getDefaultExport function for compatibility with non-harmony modules\n__webpack_require__.n = (module) => {\n\tvar getter = module && module.__esModule ?\n\t\t() => (module['default']) :\n\t\t() => (module);\n\t__webpack_require__.d(getter, { a: getter });\n\treturn getter;\n};","// define getter functions for harmony exports\n__webpack_require__.d = (exports, definition) => {\n\tfor(var key in definition) {\n\t\tif(__webpack_require__.o(definition, key) && !__webpack_require__.o(exports, key)) {\n\t\t\tObject.defineProperty(exports, key, { enumerable: true, get: definition[key] });\n\t\t}\n\t}\n};","__webpack_require__.g = (function() {\n\tif (typeof globalThis === 'object') return globalThis;\n\ttry {\n\t\treturn this || new Function('return this')();\n\t} catch (e) {\n\t\tif (typeof window === 'object') return window;\n\t}\n})();","__webpack_require__.o = (obj, prop) => (Object.prototype.hasOwnProperty.call(obj, prop))","// define __esModule on exports\n__webpack_require__.r = (exports) => {\n\tif(typeof Symbol !== 'undefined' && Symbol.toStringTag) {\n\t\tObject.defineProperty(exports, Symbol.toStringTag, { value: 'Module' });\n\t}\n\tObject.defineProperty(exports, '__esModule', { value: true });\n};","import elementorWidget from '../elementor/elementorWidget';\nimport registerFormWidget from '../elementor/FormWidget/registerFormWidget';\nimport { initBackgroundApp } from '../utils/backgroundAppUtils';\nimport registerMeetingsWidget from '../elementor/MeetingWidget/registerMeetingWidget';\nconst ELEMENTOR_READY_INTERVAL = 500;\nconst MAX_POLL_TIMEOUT = 30000;\nconst registerElementorWidgets = () => {\n initBackgroundApp(() => {\n let FormWidget;\n let MeetingsWidget;\n const leadinSelectFormItemView = elementorWidget(\n //@ts-expect-error global\n window.elementor, {\n widgetName: 'hubspot-form',\n controlSelector: '.elementor-hbspt-form-selector',\n containerSelector: '.hubspot-form-edit-mode',\n }, (controlContainer, widgetContainer, setValue) => {\n FormWidget = new registerFormWidget(controlContainer, widgetContainer, setValue);\n FormWidget.render();\n }, () => {\n FormWidget.done();\n });\n const leadinSelectMeetingItemView = elementorWidget(\n //@ts-expect-error global\n window.elementor, {\n widgetName: 'hubspot-meeting',\n controlSelector: '.elementor-hbspt-meeting-selector',\n containerSelector: '.hubspot-meeting-edit-mode',\n }, (controlContainer, widgetContainer, setValue) => {\n MeetingsWidget = new registerMeetingsWidget(controlContainer, widgetContainer, setValue);\n MeetingsWidget.render();\n }, () => {\n MeetingsWidget.done();\n });\n //@ts-expect-error global\n window.elementor.addControlView('leadinformselect', leadinSelectFormItemView);\n //@ts-expect-error global\n window.elementor.addControlView('leadinmeetingselect', leadinSelectMeetingItemView);\n });\n};\nconst pollForElementorReady = setInterval(() => {\n const elementorFrontend = window.elementorFrontend;\n if (elementorFrontend) {\n registerElementorWidgets();\n clearInterval(pollForElementorReady);\n }\n}, ELEMENTOR_READY_INTERVAL);\nsetTimeout(() => {\n clearInterval(pollForElementorReady);\n}, MAX_POLL_TIMEOUT);\n"],"names":["__","REGISTRATION_FORM","CONTACT_US_FORM","NEWSLETTER_FORM","SUPPORT_FORM","EVENT_FORM","DEFAULT_OPTIONS","label","options","value","isDefaultForm","window","leadinConfig","accountName","adminUrl","activationTime","connectionStatus","deviceId","didDisconnect","env","formsScript","meetingsScript","formsScriptPayload","hublet","hubspotBaseUrl","hubspotNonce","iframeUrl","impactLink","lastAuthorizeTime","lastDeauthorizeTime","lastDisconnectTime","leadinPluginVersion","leadinQueryParams","locale","loginUrl","phpVersion","pluginPath","plugins","portalDomain","portalEmail","portalId","redirectNonce","restNonce","restUrl","refreshToken","reviewSkippedDate","theme","trackConsent","wpVersion","contentEmbed","requiresContentEmbedScope","refreshTokenError","jsx","_jsx","ElementorBanner","ConnectPluginBanner","children","dangerouslySetInnerHTML","__html","replace","type","className","styled","Container","name","propsAsIs","ElementorButton","params","jsxs","_jsxs","Fragment","UISpinner","BackgroudAppContext","useBackgroundAppContext","useForms","getOrCreateBackgroundApp","ElementorFormSelect","formId","setAttributes","hasError","forms","loading","onChange","event","selectedForm","find","form","target","formName","disabled","selected","map","ElementorFormSelectWrapper","props","isBackgroundAppReady","ElementorFormSelectContainer","Provider","ConnectionStatus","Connected","NotConnected","FormControlController","attributes","setValue","render","ErrorHandler","FormEdit","FormWidgetController","isSelected","preview","origin","status","useState","useEffect","LoadState","ProxyMessages","usePostAsyncBackgroundMessage","proxy","NotLoaded","loadState","setLoadState","setError","setForms","key","FetchForms","payload","search","then","data","guid","Loaded","error","Failed","Loading","ReactDOM","registerFormWidget","controlContainer","widgetContainer","dataset","JSON","parse","unmountComponentAtNode","ElementorMeetingWarning","useMeetings","useSelectedMeetingCalendar","Raven","ElementorMeetingSelect","url","meetings","mappedMeetings","reload","connectCalendar","selectedMeetingCalendar","localUrl","setLocalUrl","handleConnectCalendar","captureMessage","extra","onConnectCalendar","length","newUrl","item","ElementorMeetingSelectWrapper","ElementorMeetingsSelectContainer","CURRENT_USER_CALENDAR_MISSING","MeetingWarning","isMeetingOwner","titleText","titleMessage","id","onClick","MeetingControlController","MeetingsEdit","MeetingWidgetController","registerMeetingsWidget","elementorWidget","elementor","callback","done","modules","controls","BaseData","extend","onReady","self","ui","contentEditable","prevObject","querySelector","controlSelector","element","$el","containerSelector","args","elementorFrontend","hooks","addAction","widgetName","saveValue","onBeforeDestroy","removeAction","CoreMessages","HandshakeReceive","SendRefreshToken","ReloadParentFrame","RedirectParentFrame","SendLocale","SendDeviceId","FormMessages","CreateFormAppNavigation","LiveChatMessages","CreateLiveChatAppNavigation","PluginMessages","PluginSettingsNavigation","PluginLeadinConfig","TrackConsent","InternalTrackingFetchRequest","InternalTrackingFetchResponse","InternalTrackingFetchError","InternalTrackingChangeRequest","InternalTrackingChangeError","BusinessUnitFetchRequest","BusinessUnitFetchResponse","BusinessUnitFetchError","BusinessUnitChangeRequest","BusinessUnitChangeError","SkipReviewRequest","SkipReviewResponse","SkipReviewError","RemoveParentQueryParam","ContentEmbedInstallRequest","ContentEmbedInstallResponse","ContentEmbedInstallError","ContentEmbedActivationRequest","ContentEmbedActivationResponse","ContentEmbedActivationError","FetchForm","CreateFormFromTemplate","FetchAuth","FetchMeetingsAndUsers","FetchContactsCreateSinceActivation","FetchOrCreateMeetingUser","ConnectMeetingsCalendar","TrackFormPreviewRender","TrackFormCreatedFromTemplate","TrackFormCreationFailed","TrackMeetingPreviewRender","TrackSidebarMetaChange","TrackReviewBannerRender","TrackReviewBannerInteraction","TrackReviewBannerDismissed","TrackPluginDeactivation","createContext","useContext","usePostBackgroundMessage","app","message","postMessage","postAsyncMessage","configureRaven","indexOf","config","instrument","tryCatch","release","install","setTagsContext","v","php","wordpress","setExtraContext","hub","Object","keys","join","useRef","CALYPSO_LIGHT","CALYPSO_MEDIUM","_exp2","focused","_exp3","ControlContainer","vars","ValueContainer","Placeholder","SingleValue","IndicatorContainer","DropdownIndicator","InputContainer","Input","InputShadow","MenuContainer","MenuList","MenuGroup","MenuGroupHeader","_exp5","_exp6","_exp7","MenuItem","AsyncSelect","placeholder","loadOptions","defaultOptions","inputEl","inputShadowEl","isFocused","setFocus","localValue","setLocalValue","setOptions","inputSize","current","clientWidth","result","Idle","renderItems","items","parentKey","index","undefined","blur","focus","ref","onFocus","e","width","UIButton","UIContainer","HubspotWrapper","redirectToPlugin","location","href","resetErrorState","errorInfo","header","action","isUnauthorized","errorHeader","errorMessage","textAlign","_exp","padding","LoadingBlock","size","UISpacer","PreviewForm","FormSelect","formSelected","monitorFormPreviewRender","handleChange","FormEditContainer","FormSelector","useCreateFormFromTemplate","formApiError","reset","createFormByTemplate","createReset","isCreating","createApiError","handleLocalChange","option","UIOverlay","useFormScript","ready","innerHTML","embedScript","document","createElement","appendChild","track","setFormApiError","err","debounce","trailing","$","promise","loadFormsScript","Promise","resolve","reject","getScript","fail","setReady","captureException","MeetingSelector","useSelectedMeeting","MeetingController","selectedMeetingOption","PreviewMeeting","MeetingEdit","MeetingsEditContainer","optionsWrapper","UIAlert","use","useMeetingsScript","container","src","classList","add","OTHER_USER_CALENDAR_MISSING","user","useCurrentUserFetch","createUser","loadUserState","useCallback","useMeetingsFetch","getDefaultMeetingName","meeting","currentUser","meetingUsers","meetingsUserIds","meetingOwnerId","userProfile","fullName","hasCalendarObject","meetingsUserBlob","calendarSettings","email","meetingsError","loadMeetingsState","reloadMeetings","userError","reloadUser","meet","link","mappedMeetingUsersId","reduce","p","c","includes","some","meetingLinks","loadMeetingsScript","AlertContainer","Title","Message","MessageContainer","HEFFALUMP","LORAX","CALYPSO","SpinnerOuter","SpinnerInner","color","Circle","AnimatedCircle","height","viewBox","cx","cy","r","OLAF","MARIGOLD_LIGHT","MARIGOLD_MEDIUM","OBSIDIAN","initApp","initFn","context","initAppOnReady","main","initBackgroundApp","Array","isArray","forEach","LeadinBackgroundApp","IntegratedAppEmbedder","IntegratedAppOptions","setLocale","setDeviceId","setRefreshToken","embedder","attachTo","body","postStartAppMessage","ELEMENTOR_READY_INTERVAL","MAX_POLL_TIMEOUT","registerElementorWidgets","FormWidget","MeetingsWidget","leadinSelectFormItemView","leadinSelectMeetingItemView","addControlView","pollForElementorReady","setInterval","clearInterval","setTimeout"],"sourceRoot":""}
\ No newline at end of file
diff --git a/wp/wp-content/plugins/leadin/build/feedback.asset.php b/wp/wp-content/plugins/leadin/build/feedback.asset.php
new file mode 100644
index 00000000..b2b4b65f
--- /dev/null
+++ b/wp/wp-content/plugins/leadin/build/feedback.asset.php
@@ -0,0 +1 @@
+ array('jquery'), 'version' => '9ee21da01ecaa4dcb32f');
diff --git a/wp/wp-content/plugins/leadin/build/feedback.js b/wp/wp-content/plugins/leadin/build/feedback.js
new file mode 100644
index 00000000..14b5af10
--- /dev/null
+++ b/wp/wp-content/plugins/leadin/build/feedback.js
@@ -0,0 +1,3839 @@
+/******/ (() => { // webpackBootstrap
+/******/ var __webpack_modules__ = ({
+
+/***/ "./scripts/constants/leadinConfig.ts":
+/*!*******************************************!*\
+ !*** ./scripts/constants/leadinConfig.ts ***!
+ \*******************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "accountName": () => (/* binding */ accountName),
+/* harmony export */ "activationTime": () => (/* binding */ activationTime),
+/* harmony export */ "adminUrl": () => (/* binding */ adminUrl),
+/* harmony export */ "connectionStatus": () => (/* binding */ connectionStatus),
+/* harmony export */ "contentEmbed": () => (/* binding */ contentEmbed),
+/* harmony export */ "deviceId": () => (/* binding */ deviceId),
+/* harmony export */ "didDisconnect": () => (/* binding */ didDisconnect),
+/* harmony export */ "env": () => (/* binding */ env),
+/* harmony export */ "formsScript": () => (/* binding */ formsScript),
+/* harmony export */ "formsScriptPayload": () => (/* binding */ formsScriptPayload),
+/* harmony export */ "hublet": () => (/* binding */ hublet),
+/* harmony export */ "hubspotBaseUrl": () => (/* binding */ hubspotBaseUrl),
+/* harmony export */ "hubspotNonce": () => (/* binding */ hubspotNonce),
+/* harmony export */ "iframeUrl": () => (/* binding */ iframeUrl),
+/* harmony export */ "impactLink": () => (/* binding */ impactLink),
+/* harmony export */ "lastAuthorizeTime": () => (/* binding */ lastAuthorizeTime),
+/* harmony export */ "lastDeauthorizeTime": () => (/* binding */ lastDeauthorizeTime),
+/* harmony export */ "lastDisconnectTime": () => (/* binding */ lastDisconnectTime),
+/* harmony export */ "leadinPluginVersion": () => (/* binding */ leadinPluginVersion),
+/* harmony export */ "leadinQueryParams": () => (/* binding */ leadinQueryParams),
+/* harmony export */ "locale": () => (/* binding */ locale),
+/* harmony export */ "loginUrl": () => (/* binding */ loginUrl),
+/* harmony export */ "meetingsScript": () => (/* binding */ meetingsScript),
+/* harmony export */ "phpVersion": () => (/* binding */ phpVersion),
+/* harmony export */ "pluginPath": () => (/* binding */ pluginPath),
+/* harmony export */ "plugins": () => (/* binding */ plugins),
+/* harmony export */ "portalDomain": () => (/* binding */ portalDomain),
+/* harmony export */ "portalEmail": () => (/* binding */ portalEmail),
+/* harmony export */ "portalId": () => (/* binding */ portalId),
+/* harmony export */ "redirectNonce": () => (/* binding */ redirectNonce),
+/* harmony export */ "refreshToken": () => (/* binding */ refreshToken),
+/* harmony export */ "refreshTokenError": () => (/* binding */ refreshTokenError),
+/* harmony export */ "requiresContentEmbedScope": () => (/* binding */ requiresContentEmbedScope),
+/* harmony export */ "restNonce": () => (/* binding */ restNonce),
+/* harmony export */ "restUrl": () => (/* binding */ restUrl),
+/* harmony export */ "reviewSkippedDate": () => (/* binding */ reviewSkippedDate),
+/* harmony export */ "theme": () => (/* binding */ theme),
+/* harmony export */ "trackConsent": () => (/* binding */ trackConsent),
+/* harmony export */ "wpVersion": () => (/* binding */ wpVersion)
+/* harmony export */ });
+var _window$leadinConfig = window.leadinConfig,
+ accountName = _window$leadinConfig.accountName,
+ adminUrl = _window$leadinConfig.adminUrl,
+ activationTime = _window$leadinConfig.activationTime,
+ connectionStatus = _window$leadinConfig.connectionStatus,
+ deviceId = _window$leadinConfig.deviceId,
+ didDisconnect = _window$leadinConfig.didDisconnect,
+ env = _window$leadinConfig.env,
+ formsScript = _window$leadinConfig.formsScript,
+ meetingsScript = _window$leadinConfig.meetingsScript,
+ formsScriptPayload = _window$leadinConfig.formsScriptPayload,
+ hublet = _window$leadinConfig.hublet,
+ hubspotBaseUrl = _window$leadinConfig.hubspotBaseUrl,
+ hubspotNonce = _window$leadinConfig.hubspotNonce,
+ iframeUrl = _window$leadinConfig.iframeUrl,
+ impactLink = _window$leadinConfig.impactLink,
+ lastAuthorizeTime = _window$leadinConfig.lastAuthorizeTime,
+ lastDeauthorizeTime = _window$leadinConfig.lastDeauthorizeTime,
+ lastDisconnectTime = _window$leadinConfig.lastDisconnectTime,
+ leadinPluginVersion = _window$leadinConfig.leadinPluginVersion,
+ leadinQueryParams = _window$leadinConfig.leadinQueryParams,
+ locale = _window$leadinConfig.locale,
+ loginUrl = _window$leadinConfig.loginUrl,
+ phpVersion = _window$leadinConfig.phpVersion,
+ pluginPath = _window$leadinConfig.pluginPath,
+ plugins = _window$leadinConfig.plugins,
+ portalDomain = _window$leadinConfig.portalDomain,
+ portalEmail = _window$leadinConfig.portalEmail,
+ portalId = _window$leadinConfig.portalId,
+ redirectNonce = _window$leadinConfig.redirectNonce,
+ restNonce = _window$leadinConfig.restNonce,
+ restUrl = _window$leadinConfig.restUrl,
+ refreshToken = _window$leadinConfig.refreshToken,
+ reviewSkippedDate = _window$leadinConfig.reviewSkippedDate,
+ theme = _window$leadinConfig.theme,
+ trackConsent = _window$leadinConfig.trackConsent,
+ wpVersion = _window$leadinConfig.wpVersion,
+ contentEmbed = _window$leadinConfig.contentEmbed,
+ requiresContentEmbedScope = _window$leadinConfig.requiresContentEmbedScope,
+ refreshTokenError = _window$leadinConfig.refreshTokenError;
+
+
+/***/ }),
+
+/***/ "./scripts/constants/selectors.ts":
+/*!****************************************!*\
+ !*** ./scripts/constants/selectors.ts ***!
+ \****************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "domElements": () => (/* binding */ domElements)
+/* harmony export */ });
+var domElements = {
+ iframe: '#leadin-iframe',
+ subMenu: '.toplevel_page_leadin > ul',
+ subMenuLinks: '.toplevel_page_leadin > ul a',
+ subMenuButtons: '.toplevel_page_leadin > ul > li',
+ deactivatePluginButton: '[data-slug="leadin"] .deactivate a',
+ deactivateFeedbackForm: 'form.leadin-deactivate-form',
+ deactivateFeedbackSubmit: 'button#leadin-feedback-submit',
+ deactivateFeedbackSkip: 'button#leadin-feedback-skip',
+ thickboxModalClose: '.leadin-modal-close',
+ thickboxModalWindow: 'div#TB_window.thickbox-loading',
+ thickboxModalContent: 'div#TB_ajaxContent.TB_modal',
+ reviewBannerContainer: '#leadin-review-banner',
+ reviewBannerLeaveReviewLink: 'a#leave-review-button',
+ reviewBannerDismissButton: 'a#dismiss-review-banner-button',
+ leadinIframeContainer: 'leadin-iframe-container',
+ leadinIframe: 'leadin-iframe',
+ leadinIframeFallbackContainer: 'leadin-iframe-fallback-container'
+};
+
+/***/ }),
+
+/***/ "./scripts/feedback/ThickBoxModal.ts":
+/*!*******************************************!*\
+ !*** ./scripts/feedback/ThickBoxModal.ts ***!
+ \*******************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ ThickBoxModal)
+/* harmony export */ });
+/* harmony import */ var jquery__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! jquery */ "jquery");
+/* harmony import */ var jquery__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(jquery__WEBPACK_IMPORTED_MODULE_0__);
+/* harmony import */ var _constants_selectors__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! ../constants/selectors */ "./scripts/constants/selectors.ts");
+function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
+
+function _defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } }
+
+function _createClass(Constructor, protoProps, staticProps) { if (protoProps) _defineProperties(Constructor.prototype, protoProps); if (staticProps) _defineProperties(Constructor, staticProps); Object.defineProperty(Constructor, "prototype", { writable: false }); return Constructor; }
+
+function _defineProperty(obj, key, value) { if (key in obj) { Object.defineProperty(obj, key, { value: value, enumerable: true, configurable: true, writable: true }); } else { obj[key] = value; } return obj; }
+
+
+
+
+var ThickBoxModal = /*#__PURE__*/function () {
+ function ThickBoxModal(openTriggerSelector, inlineContentId, windowCssClass, contentCssClass) {
+ _classCallCheck(this, ThickBoxModal);
+
+ _defineProperty(this, "openTriggerSelector", void 0);
+
+ _defineProperty(this, "inlineContentId", void 0);
+
+ _defineProperty(this, "windowCssClass", void 0);
+
+ _defineProperty(this, "contentCssClass", void 0);
+
+ this.openTriggerSelector = openTriggerSelector;
+ this.inlineContentId = inlineContentId;
+ this.windowCssClass = windowCssClass;
+ this.contentCssClass = contentCssClass;
+ jquery__WEBPACK_IMPORTED_MODULE_0___default()(openTriggerSelector).on('click', this.init.bind(this));
+ }
+
+ _createClass(ThickBoxModal, [{
+ key: "close",
+ value: function close() {
+ //@ts-expect-error global
+ window.tb_remove();
+ }
+ }, {
+ key: "init",
+ value: function init(e) {
+ //@ts-expect-error global
+ window.tb_show('', "#TB_inline?inlineId=".concat(this.inlineContentId, "&modal=true")); // thickbox doesn't respect the width and height url parameters https://core.trac.wordpress.org/ticket/17249
+ // We override thickboxes css with !important in the css
+
+ jquery__WEBPACK_IMPORTED_MODULE_0___default()(_constants_selectors__WEBPACK_IMPORTED_MODULE_1__.domElements.thickboxModalWindow).addClass(this.windowCssClass); // have to modify the css of the thickbox content container as well
+
+ jquery__WEBPACK_IMPORTED_MODULE_0___default()(_constants_selectors__WEBPACK_IMPORTED_MODULE_1__.domElements.thickboxModalContent).addClass(this.contentCssClass); // we unbind previous handlers because a thickbox modal is a single global object.
+ // Everytime it is re-opened, it still has old handlers bound
+
+ jquery__WEBPACK_IMPORTED_MODULE_0___default()(_constants_selectors__WEBPACK_IMPORTED_MODULE_1__.domElements.thickboxModalClose).off('click').on('click', this.close);
+ e.preventDefault();
+ }
+ }]);
+
+ return ThickBoxModal;
+}();
+
+
+
+/***/ }),
+
+/***/ "./scripts/feedback/feedbackFormApi.ts":
+/*!*********************************************!*\
+ !*** ./scripts/feedback/feedbackFormApi.ts ***!
+ \*********************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "submitFeedbackForm": () => (/* binding */ submitFeedbackForm)
+/* harmony export */ });
+/* harmony import */ var jquery__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! jquery */ "jquery");
+/* harmony import */ var jquery__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(jquery__WEBPACK_IMPORTED_MODULE_0__);
+
+var portalId = '6275621';
+var formId = '0e8807f8-2ac3-4664-b742-44552bfa09e2';
+var formSubmissionUrl = "https://api.hsforms.com/submissions/v3/integration/submit/".concat(portalId, "/").concat(formId);
+function submitFeedbackForm(formSelector) {
+ var formSubmissionPayload = {
+ fields: jquery__WEBPACK_IMPORTED_MODULE_0___default()(formSelector).serializeArray(),
+ skipValidation: true
+ };
+ return new Promise(function (resolve, reject) {
+ jquery__WEBPACK_IMPORTED_MODULE_0___default().ajax({
+ type: 'POST',
+ url: formSubmissionUrl,
+ contentType: 'application/json',
+ data: JSON.stringify(formSubmissionPayload),
+ success: resolve,
+ error: reject
+ });
+ });
+}
+
+/***/ }),
+
+/***/ "./scripts/iframe/integratedMessages/core/CoreMessages.ts":
+/*!****************************************************************!*\
+ !*** ./scripts/iframe/integratedMessages/core/CoreMessages.ts ***!
+ \****************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "CoreMessages": () => (/* binding */ CoreMessages)
+/* harmony export */ });
+var CoreMessages = {
+ HandshakeReceive: 'INTEGRATED_APP_EMBEDDER_HANDSHAKE_RECEIVED',
+ SendRefreshToken: 'INTEGRATED_APP_EMBEDDER_SEND_REFRESH_TOKEN',
+ ReloadParentFrame: 'INTEGRATED_APP_EMBEDDER_RELOAD_PARENT_FRAME',
+ RedirectParentFrame: 'INTEGRATED_APP_EMBEDDER_REDIRECT_PARENT_FRAME',
+ SendLocale: 'INTEGRATED_APP_EMBEDDER_SEND_LOCALE',
+ SendDeviceId: 'INTEGRATED_APP_EMBEDDER_SEND_DEVICE_ID'
+};
+
+/***/ }),
+
+/***/ "./scripts/iframe/integratedMessages/forms/FormsMessages.ts":
+/*!******************************************************************!*\
+ !*** ./scripts/iframe/integratedMessages/forms/FormsMessages.ts ***!
+ \******************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "FormMessages": () => (/* binding */ FormMessages)
+/* harmony export */ });
+var FormMessages = {
+ CreateFormAppNavigation: 'CREATE_FORM_APP_NAVIGATION'
+};
+
+/***/ }),
+
+/***/ "./scripts/iframe/integratedMessages/index.ts":
+/*!****************************************************!*\
+ !*** ./scripts/iframe/integratedMessages/index.ts ***!
+ \****************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "CoreMessages": () => (/* reexport safe */ _core_CoreMessages__WEBPACK_IMPORTED_MODULE_0__.CoreMessages),
+/* harmony export */ "FormMessages": () => (/* reexport safe */ _forms_FormsMessages__WEBPACK_IMPORTED_MODULE_1__.FormMessages),
+/* harmony export */ "LiveChatMessages": () => (/* reexport safe */ _livechat_LiveChatMessages__WEBPACK_IMPORTED_MODULE_2__.LiveChatMessages),
+/* harmony export */ "PluginMessages": () => (/* reexport safe */ _plugin_PluginMessages__WEBPACK_IMPORTED_MODULE_3__.PluginMessages),
+/* harmony export */ "ProxyMessages": () => (/* reexport safe */ _proxy_ProxyMessages__WEBPACK_IMPORTED_MODULE_4__.ProxyMessages)
+/* harmony export */ });
+/* harmony import */ var _core_CoreMessages__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! ./core/CoreMessages */ "./scripts/iframe/integratedMessages/core/CoreMessages.ts");
+/* harmony import */ var _forms_FormsMessages__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! ./forms/FormsMessages */ "./scripts/iframe/integratedMessages/forms/FormsMessages.ts");
+/* harmony import */ var _livechat_LiveChatMessages__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ./livechat/LiveChatMessages */ "./scripts/iframe/integratedMessages/livechat/LiveChatMessages.ts");
+/* harmony import */ var _plugin_PluginMessages__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ./plugin/PluginMessages */ "./scripts/iframe/integratedMessages/plugin/PluginMessages.ts");
+/* harmony import */ var _proxy_ProxyMessages__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__(/*! ./proxy/ProxyMessages */ "./scripts/iframe/integratedMessages/proxy/ProxyMessages.ts");
+
+
+
+
+
+
+/***/ }),
+
+/***/ "./scripts/iframe/integratedMessages/livechat/LiveChatMessages.ts":
+/*!************************************************************************!*\
+ !*** ./scripts/iframe/integratedMessages/livechat/LiveChatMessages.ts ***!
+ \************************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "LiveChatMessages": () => (/* binding */ LiveChatMessages)
+/* harmony export */ });
+var LiveChatMessages = {
+ CreateLiveChatAppNavigation: 'CREATE_LIVE_CHAT_APP_NAVIGATION'
+};
+
+/***/ }),
+
+/***/ "./scripts/iframe/integratedMessages/plugin/PluginMessages.ts":
+/*!********************************************************************!*\
+ !*** ./scripts/iframe/integratedMessages/plugin/PluginMessages.ts ***!
+ \********************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "PluginMessages": () => (/* binding */ PluginMessages)
+/* harmony export */ });
+var PluginMessages = {
+ PluginSettingsNavigation: 'PLUGIN_SETTINGS_NAVIGATION',
+ PluginLeadinConfig: 'PLUGIN_LEADIN_CONFIG',
+ TrackConsent: 'INTEGRATED_APP_EMBEDDER_TRACK_CONSENT',
+ InternalTrackingFetchRequest: 'INTEGRATED_TRACKING_FETCH_REQUEST',
+ InternalTrackingFetchResponse: 'INTEGRATED_TRACKING_FETCH_RESPONSE',
+ InternalTrackingFetchError: 'INTEGRATED_TRACKING_FETCH_ERROR',
+ InternalTrackingChangeRequest: 'INTEGRATED_TRACKING_CHANGE_REQUEST',
+ InternalTrackingChangeError: 'INTEGRATED_TRACKING_CHANGE_ERROR',
+ BusinessUnitFetchRequest: 'BUSINESS_UNIT_FETCH_REQUEST',
+ BusinessUnitFetchResponse: 'BUSINESS_UNIT_FETCH_FETCH_RESPONSE',
+ BusinessUnitFetchError: 'BUSINESS_UNIT_FETCH_FETCH_ERROR',
+ BusinessUnitChangeRequest: 'BUSINESS_UNIT_CHANGE_REQUEST',
+ BusinessUnitChangeError: 'BUSINESS_UNIT_CHANGE_ERROR',
+ SkipReviewRequest: 'SKIP_REVIEW_REQUEST',
+ SkipReviewResponse: 'SKIP_REVIEW_RESPONSE',
+ SkipReviewError: 'SKIP_REVIEW_ERROR',
+ RemoveParentQueryParam: 'REMOVE_PARENT_QUERY_PARAM',
+ ContentEmbedInstallRequest: 'CONTENT_EMBED_INSTALL_REQUEST',
+ ContentEmbedInstallResponse: 'CONTENT_EMBED_INSTALL_RESPONSE',
+ ContentEmbedInstallError: 'CONTENT_EMBED_INSTALL_ERROR',
+ ContentEmbedActivationRequest: 'CONTENT_EMBED_ACTIVATION_REQUEST',
+ ContentEmbedActivationResponse: 'CONTENT_EMBED_ACTIVATION_RESPONSE',
+ ContentEmbedActivationError: 'CONTENT_EMBED_ACTIVATION_ERROR'
+};
+
+/***/ }),
+
+/***/ "./scripts/iframe/integratedMessages/proxy/ProxyMessages.ts":
+/*!******************************************************************!*\
+ !*** ./scripts/iframe/integratedMessages/proxy/ProxyMessages.ts ***!
+ \******************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "ProxyMessages": () => (/* binding */ ProxyMessages)
+/* harmony export */ });
+var ProxyMessages = {
+ FetchForms: 'FETCH_FORMS',
+ FetchForm: 'FETCH_FORM',
+ CreateFormFromTemplate: 'CREATE_FORM_FROM_TEMPLATE',
+ FetchAuth: 'FETCH_AUTH',
+ FetchMeetingsAndUsers: 'FETCH_MEETINGS_AND_USERS',
+ FetchContactsCreateSinceActivation: 'FETCH_CONTACTS_CREATED_SINCE_ACTIVATION',
+ FetchOrCreateMeetingUser: 'FETCH_OR_CREATE_MEETING_USER',
+ ConnectMeetingsCalendar: 'CONNECT_MEETINGS_CALENDAR',
+ TrackFormPreviewRender: 'TRACK_FORM_PREVIEW_RENDER',
+ TrackFormCreatedFromTemplate: 'TRACK_FORM_CREATED_FROM_TEMPLATE',
+ TrackFormCreationFailed: 'TRACK_FORM_CREATION_FAILED',
+ TrackMeetingPreviewRender: 'TRACK_MEETING_PREVIEW_RENDER',
+ TrackSidebarMetaChange: 'TRACK_SIDEBAR_META_CHANGE',
+ TrackReviewBannerRender: 'TRACK_REVIEW_BANNER_RENDER',
+ TrackReviewBannerInteraction: 'TRACK_REVIEW_BANNER_INTERACTION',
+ TrackReviewBannerDismissed: 'TRACK_REVIEW_BANNER_DISMISSED',
+ TrackPluginDeactivation: 'TRACK_PLUGIN_DEACTIVATION'
+};
+
+/***/ }),
+
+/***/ "./scripts/lib/Raven.ts":
+/*!******************************!*\
+ !*** ./scripts/lib/Raven.ts ***!
+ \******************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "configureRaven": () => (/* binding */ configureRaven),
+/* harmony export */ "default": () => (__WEBPACK_DEFAULT_EXPORT__)
+/* harmony export */ });
+/* harmony import */ var raven_js__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! raven-js */ "./node_modules/raven-js/src/singleton.js");
+/* harmony import */ var raven_js__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(raven_js__WEBPACK_IMPORTED_MODULE_0__);
+/* harmony import */ var _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! ../constants/leadinConfig */ "./scripts/constants/leadinConfig.ts");
+
+
+function configureRaven() {
+ if (_constants_leadinConfig__WEBPACK_IMPORTED_MODULE_1__.hubspotBaseUrl.indexOf('app.hubspot.com') === -1) {
+ return;
+ }
+
+ raven_js__WEBPACK_IMPORTED_MODULE_0___default().config('https://e9b8f382cdd130c0d415cd977d2be56f@exceptions.hubspot.com/1', {
+ instrument: {
+ tryCatch: false
+ },
+ release: _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_1__.leadinPluginVersion
+ }).install();
+ raven_js__WEBPACK_IMPORTED_MODULE_0___default().setTagsContext({
+ v: _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_1__.leadinPluginVersion,
+ php: _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_1__.phpVersion,
+ wordpress: _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_1__.wpVersion
+ });
+ raven_js__WEBPACK_IMPORTED_MODULE_0___default().setExtraContext({
+ hub: _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_1__.portalId,
+ plugins: Object.keys(_constants_leadinConfig__WEBPACK_IMPORTED_MODULE_1__.plugins).map(function (name) {
+ return "".concat(name, "#").concat(_constants_leadinConfig__WEBPACK_IMPORTED_MODULE_1__.plugins[name]);
+ }).join(',')
+ });
+}
+/* harmony default export */ const __WEBPACK_DEFAULT_EXPORT__ = ((raven_js__WEBPACK_IMPORTED_MODULE_0___default()));
+
+/***/ }),
+
+/***/ "./scripts/utils/appUtils.ts":
+/*!***********************************!*\
+ !*** ./scripts/utils/appUtils.ts ***!
+ \***********************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "initApp": () => (/* binding */ initApp),
+/* harmony export */ "initAppOnReady": () => (/* binding */ initAppOnReady)
+/* harmony export */ });
+/* harmony import */ var jquery__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! jquery */ "jquery");
+/* harmony import */ var jquery__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(jquery__WEBPACK_IMPORTED_MODULE_0__);
+/* harmony import */ var _lib_Raven__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! ../lib/Raven */ "./scripts/lib/Raven.ts");
+
+
+function initApp(initFn) {
+ (0,_lib_Raven__WEBPACK_IMPORTED_MODULE_1__.configureRaven)();
+ _lib_Raven__WEBPACK_IMPORTED_MODULE_1__["default"].context(initFn);
+}
+function initAppOnReady(initFn) {
+ function main() {
+ jquery__WEBPACK_IMPORTED_MODULE_0___default()(initFn);
+ }
+
+ initApp(main);
+}
+
+/***/ }),
+
+/***/ "./scripts/utils/backgroundAppUtils.ts":
+/*!*********************************************!*\
+ !*** ./scripts/utils/backgroundAppUtils.ts ***!
+ \*********************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "getOrCreateBackgroundApp": () => (/* binding */ getOrCreateBackgroundApp),
+/* harmony export */ "initBackgroundApp": () => (/* binding */ initBackgroundApp)
+/* harmony export */ });
+/* harmony import */ var _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! ../constants/leadinConfig */ "./scripts/constants/leadinConfig.ts");
+/* harmony import */ var _appUtils__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! ./appUtils */ "./scripts/utils/appUtils.ts");
+
+
+function initBackgroundApp(initFn) {
+ function main() {
+ if (Array.isArray(initFn)) {
+ initFn.forEach(function (callback) {
+ return callback();
+ });
+ } else {
+ initFn();
+ }
+ }
+
+ (0,_appUtils__WEBPACK_IMPORTED_MODULE_1__.initApp)(main);
+}
+var getOrCreateBackgroundApp = function getOrCreateBackgroundApp(refreshToken) {
+ if (window.LeadinBackgroundApp) {
+ return window.LeadinBackgroundApp;
+ }
+
+ var _window = window,
+ IntegratedAppEmbedder = _window.IntegratedAppEmbedder,
+ IntegratedAppOptions = _window.IntegratedAppOptions;
+ var options = new IntegratedAppOptions().setLocale(_constants_leadinConfig__WEBPACK_IMPORTED_MODULE_0__.locale).setDeviceId(_constants_leadinConfig__WEBPACK_IMPORTED_MODULE_0__.deviceId).setRefreshToken(refreshToken);
+ var embedder = new IntegratedAppEmbedder('integrated-plugin-proxy', _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_0__.portalId, _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_0__.hubspotBaseUrl, function () {}).setOptions(options);
+ embedder.attachTo(document.body, false);
+ embedder.postStartAppMessage(); // lets the app know all all data has been passed to it
+
+ window.LeadinBackgroundApp = embedder;
+ return window.LeadinBackgroundApp;
+};
+
+/***/ }),
+
+/***/ "./node_modules/raven-js/src/configError.js":
+/*!**************************************************!*\
+ !*** ./node_modules/raven-js/src/configError.js ***!
+ \**************************************************/
+/***/ ((module) => {
+
+function RavenConfigError(message) {
+ this.name = 'RavenConfigError';
+ this.message = message;
+}
+RavenConfigError.prototype = new Error();
+RavenConfigError.prototype.constructor = RavenConfigError;
+
+module.exports = RavenConfigError;
+
+
+/***/ }),
+
+/***/ "./node_modules/raven-js/src/console.js":
+/*!**********************************************!*\
+ !*** ./node_modules/raven-js/src/console.js ***!
+ \**********************************************/
+/***/ ((module) => {
+
+var wrapMethod = function(console, level, callback) {
+ var originalConsoleLevel = console[level];
+ var originalConsole = console;
+
+ if (!(level in console)) {
+ return;
+ }
+
+ var sentryLevel = level === 'warn' ? 'warning' : level;
+
+ console[level] = function() {
+ var args = [].slice.call(arguments);
+
+ var msg = '' + args.join(' ');
+ var data = {level: sentryLevel, logger: 'console', extra: {arguments: args}};
+
+ if (level === 'assert') {
+ if (args[0] === false) {
+ // Default browsers message
+ msg = 'Assertion failed: ' + (args.slice(1).join(' ') || 'console.assert');
+ data.extra.arguments = args.slice(1);
+ callback && callback(msg, data);
+ }
+ } else {
+ callback && callback(msg, data);
+ }
+
+ // this fails for some browsers. :(
+ if (originalConsoleLevel) {
+ // IE9 doesn't allow calling apply on console functions directly
+ // See: https://stackoverflow.com/questions/5472938/does-ie9-support-console-log-and-is-it-a-real-function#answer-5473193
+ Function.prototype.apply.call(originalConsoleLevel, originalConsole, args);
+ }
+ };
+};
+
+module.exports = {
+ wrapMethod: wrapMethod
+};
+
+
+/***/ }),
+
+/***/ "./node_modules/raven-js/src/raven.js":
+/*!********************************************!*\
+ !*** ./node_modules/raven-js/src/raven.js ***!
+ \********************************************/
+/***/ ((module, __unused_webpack_exports, __webpack_require__) => {
+
+/*global XDomainRequest:false */
+
+var TraceKit = __webpack_require__(/*! ../vendor/TraceKit/tracekit */ "./node_modules/raven-js/vendor/TraceKit/tracekit.js");
+var stringify = __webpack_require__(/*! ../vendor/json-stringify-safe/stringify */ "./node_modules/raven-js/vendor/json-stringify-safe/stringify.js");
+var RavenConfigError = __webpack_require__(/*! ./configError */ "./node_modules/raven-js/src/configError.js");
+
+var utils = __webpack_require__(/*! ./utils */ "./node_modules/raven-js/src/utils.js");
+var isError = utils.isError;
+var isObject = utils.isObject;
+var isObject = utils.isObject;
+var isErrorEvent = utils.isErrorEvent;
+var isUndefined = utils.isUndefined;
+var isFunction = utils.isFunction;
+var isString = utils.isString;
+var isEmptyObject = utils.isEmptyObject;
+var each = utils.each;
+var objectMerge = utils.objectMerge;
+var truncate = utils.truncate;
+var objectFrozen = utils.objectFrozen;
+var hasKey = utils.hasKey;
+var joinRegExp = utils.joinRegExp;
+var urlencode = utils.urlencode;
+var uuid4 = utils.uuid4;
+var htmlTreeAsString = utils.htmlTreeAsString;
+var isSameException = utils.isSameException;
+var isSameStacktrace = utils.isSameStacktrace;
+var parseUrl = utils.parseUrl;
+var fill = utils.fill;
+
+var wrapConsoleMethod = (__webpack_require__(/*! ./console */ "./node_modules/raven-js/src/console.js").wrapMethod);
+
+var dsnKeys = 'source protocol user pass host port path'.split(' '),
+ dsnPattern = /^(?:(\w+):)?\/\/(?:(\w+)(:\w+)?@)?([\w\.-]+)(?::(\d+))?(\/.*)/;
+
+function now() {
+ return +new Date();
+}
+
+// This is to be defensive in environments where window does not exist (see https://github.com/getsentry/raven-js/pull/785)
+var _window =
+ typeof window !== 'undefined'
+ ? window
+ : typeof __webpack_require__.g !== 'undefined' ? __webpack_require__.g : typeof self !== 'undefined' ? self : {};
+var _document = _window.document;
+var _navigator = _window.navigator;
+
+function keepOriginalCallback(original, callback) {
+ return isFunction(callback)
+ ? function(data) {
+ return callback(data, original);
+ }
+ : callback;
+}
+
+// First, check for JSON support
+// If there is no JSON, we no-op the core features of Raven
+// since JSON is required to encode the payload
+function Raven() {
+ this._hasJSON = !!(typeof JSON === 'object' && JSON.stringify);
+ // Raven can run in contexts where there's no document (react-native)
+ this._hasDocument = !isUndefined(_document);
+ this._hasNavigator = !isUndefined(_navigator);
+ this._lastCapturedException = null;
+ this._lastData = null;
+ this._lastEventId = null;
+ this._globalServer = null;
+ this._globalKey = null;
+ this._globalProject = null;
+ this._globalContext = {};
+ this._globalOptions = {
+ logger: 'javascript',
+ ignoreErrors: [],
+ ignoreUrls: [],
+ whitelistUrls: [],
+ includePaths: [],
+ collectWindowErrors: true,
+ maxMessageLength: 0,
+
+ // By default, truncates URL values to 250 chars
+ maxUrlLength: 250,
+ stackTraceLimit: 50,
+ autoBreadcrumbs: true,
+ instrument: true,
+ sampleRate: 1
+ };
+ this._ignoreOnError = 0;
+ this._isRavenInstalled = false;
+ this._originalErrorStackTraceLimit = Error.stackTraceLimit;
+ // capture references to window.console *and* all its methods first
+ // before the console plugin has a chance to monkey patch
+ this._originalConsole = _window.console || {};
+ this._originalConsoleMethods = {};
+ this._plugins = [];
+ this._startTime = now();
+ this._wrappedBuiltIns = [];
+ this._breadcrumbs = [];
+ this._lastCapturedEvent = null;
+ this._keypressTimeout;
+ this._location = _window.location;
+ this._lastHref = this._location && this._location.href;
+ this._resetBackoff();
+
+ // eslint-disable-next-line guard-for-in
+ for (var method in this._originalConsole) {
+ this._originalConsoleMethods[method] = this._originalConsole[method];
+ }
+}
+
+/*
+ * The core Raven singleton
+ *
+ * @this {Raven}
+ */
+
+Raven.prototype = {
+ // Hardcode version string so that raven source can be loaded directly via
+ // webpack (using a build step causes webpack #1617). Grunt verifies that
+ // this value matches package.json during build.
+ // See: https://github.com/getsentry/raven-js/issues/465
+ VERSION: '3.19.1',
+
+ debug: false,
+
+ TraceKit: TraceKit, // alias to TraceKit
+
+ /*
+ * Configure Raven with a DSN and extra options
+ *
+ * @param {string} dsn The public Sentry DSN
+ * @param {object} options Set of global options [optional]
+ * @return {Raven}
+ */
+ config: function(dsn, options) {
+ var self = this;
+
+ if (self._globalServer) {
+ this._logDebug('error', 'Error: Raven has already been configured');
+ return self;
+ }
+ if (!dsn) return self;
+
+ var globalOptions = self._globalOptions;
+
+ // merge in options
+ if (options) {
+ each(options, function(key, value) {
+ // tags and extra are special and need to be put into context
+ if (key === 'tags' || key === 'extra' || key === 'user') {
+ self._globalContext[key] = value;
+ } else {
+ globalOptions[key] = value;
+ }
+ });
+ }
+
+ self.setDSN(dsn);
+
+ // "Script error." is hard coded into browsers for errors that it can't read.
+ // this is the result of a script being pulled in from an external domain and CORS.
+ globalOptions.ignoreErrors.push(/^Script error\.?$/);
+ globalOptions.ignoreErrors.push(/^Javascript error: Script error\.? on line 0$/);
+
+ // join regexp rules into one big rule
+ globalOptions.ignoreErrors = joinRegExp(globalOptions.ignoreErrors);
+ globalOptions.ignoreUrls = globalOptions.ignoreUrls.length
+ ? joinRegExp(globalOptions.ignoreUrls)
+ : false;
+ globalOptions.whitelistUrls = globalOptions.whitelistUrls.length
+ ? joinRegExp(globalOptions.whitelistUrls)
+ : false;
+ globalOptions.includePaths = joinRegExp(globalOptions.includePaths);
+ globalOptions.maxBreadcrumbs = Math.max(
+ 0,
+ Math.min(globalOptions.maxBreadcrumbs || 100, 100)
+ ); // default and hard limit is 100
+
+ var autoBreadcrumbDefaults = {
+ xhr: true,
+ console: true,
+ dom: true,
+ location: true
+ };
+
+ var autoBreadcrumbs = globalOptions.autoBreadcrumbs;
+ if ({}.toString.call(autoBreadcrumbs) === '[object Object]') {
+ autoBreadcrumbs = objectMerge(autoBreadcrumbDefaults, autoBreadcrumbs);
+ } else if (autoBreadcrumbs !== false) {
+ autoBreadcrumbs = autoBreadcrumbDefaults;
+ }
+ globalOptions.autoBreadcrumbs = autoBreadcrumbs;
+
+ var instrumentDefaults = {
+ tryCatch: true
+ };
+
+ var instrument = globalOptions.instrument;
+ if ({}.toString.call(instrument) === '[object Object]') {
+ instrument = objectMerge(instrumentDefaults, instrument);
+ } else if (instrument !== false) {
+ instrument = instrumentDefaults;
+ }
+ globalOptions.instrument = instrument;
+
+ TraceKit.collectWindowErrors = !!globalOptions.collectWindowErrors;
+
+ // return for chaining
+ return self;
+ },
+
+ /*
+ * Installs a global window.onerror error handler
+ * to capture and report uncaught exceptions.
+ * At this point, install() is required to be called due
+ * to the way TraceKit is set up.
+ *
+ * @return {Raven}
+ */
+ install: function() {
+ var self = this;
+ if (self.isSetup() && !self._isRavenInstalled) {
+ TraceKit.report.subscribe(function() {
+ self._handleOnErrorStackInfo.apply(self, arguments);
+ });
+ if (self._globalOptions.instrument && self._globalOptions.instrument.tryCatch) {
+ self._instrumentTryCatch();
+ }
+
+ if (self._globalOptions.autoBreadcrumbs) self._instrumentBreadcrumbs();
+
+ // Install all of the plugins
+ self._drainPlugins();
+
+ self._isRavenInstalled = true;
+ }
+
+ Error.stackTraceLimit = self._globalOptions.stackTraceLimit;
+ return this;
+ },
+
+ /*
+ * Set the DSN (can be called multiple time unlike config)
+ *
+ * @param {string} dsn The public Sentry DSN
+ */
+ setDSN: function(dsn) {
+ var self = this,
+ uri = self._parseDSN(dsn),
+ lastSlash = uri.path.lastIndexOf('/'),
+ path = uri.path.substr(1, lastSlash);
+
+ self._dsn = dsn;
+ self._globalKey = uri.user;
+ self._globalSecret = uri.pass && uri.pass.substr(1);
+ self._globalProject = uri.path.substr(lastSlash + 1);
+
+ self._globalServer = self._getGlobalServer(uri);
+
+ self._globalEndpoint =
+ self._globalServer + '/' + path + 'api/' + self._globalProject + '/store/';
+
+ // Reset backoff state since we may be pointing at a
+ // new project/server
+ this._resetBackoff();
+ },
+
+ /*
+ * Wrap code within a context so Raven can capture errors
+ * reliably across domains that is executed immediately.
+ *
+ * @param {object} options A specific set of options for this context [optional]
+ * @param {function} func The callback to be immediately executed within the context
+ * @param {array} args An array of arguments to be called with the callback [optional]
+ */
+ context: function(options, func, args) {
+ if (isFunction(options)) {
+ args = func || [];
+ func = options;
+ options = undefined;
+ }
+
+ return this.wrap(options, func).apply(this, args);
+ },
+
+ /*
+ * Wrap code within a context and returns back a new function to be executed
+ *
+ * @param {object} options A specific set of options for this context [optional]
+ * @param {function} func The function to be wrapped in a new context
+ * @param {function} func A function to call before the try/catch wrapper [optional, private]
+ * @return {function} The newly wrapped functions with a context
+ */
+ wrap: function(options, func, _before) {
+ var self = this;
+ // 1 argument has been passed, and it's not a function
+ // so just return it
+ if (isUndefined(func) && !isFunction(options)) {
+ return options;
+ }
+
+ // options is optional
+ if (isFunction(options)) {
+ func = options;
+ options = undefined;
+ }
+
+ // At this point, we've passed along 2 arguments, and the second one
+ // is not a function either, so we'll just return the second argument.
+ if (!isFunction(func)) {
+ return func;
+ }
+
+ // We don't wanna wrap it twice!
+ try {
+ if (func.__raven__) {
+ return func;
+ }
+
+ // If this has already been wrapped in the past, return that
+ if (func.__raven_wrapper__) {
+ return func.__raven_wrapper__;
+ }
+ } catch (e) {
+ // Just accessing custom props in some Selenium environments
+ // can cause a "Permission denied" exception (see raven-js#495).
+ // Bail on wrapping and return the function as-is (defers to window.onerror).
+ return func;
+ }
+
+ function wrapped() {
+ var args = [],
+ i = arguments.length,
+ deep = !options || (options && options.deep !== false);
+
+ if (_before && isFunction(_before)) {
+ _before.apply(this, arguments);
+ }
+
+ // Recursively wrap all of a function's arguments that are
+ // functions themselves.
+ while (i--) args[i] = deep ? self.wrap(options, arguments[i]) : arguments[i];
+
+ try {
+ // Attempt to invoke user-land function
+ // NOTE: If you are a Sentry user, and you are seeing this stack frame, it
+ // means Raven caught an error invoking your application code. This is
+ // expected behavior and NOT indicative of a bug with Raven.js.
+ return func.apply(this, args);
+ } catch (e) {
+ self._ignoreNextOnError();
+ self.captureException(e, options);
+ throw e;
+ }
+ }
+
+ // copy over properties of the old function
+ for (var property in func) {
+ if (hasKey(func, property)) {
+ wrapped[property] = func[property];
+ }
+ }
+ wrapped.prototype = func.prototype;
+
+ func.__raven_wrapper__ = wrapped;
+ // Signal that this function has been wrapped already
+ // for both debugging and to prevent it to being wrapped twice
+ wrapped.__raven__ = true;
+ wrapped.__inner__ = func;
+
+ return wrapped;
+ },
+
+ /*
+ * Uninstalls the global error handler.
+ *
+ * @return {Raven}
+ */
+ uninstall: function() {
+ TraceKit.report.uninstall();
+
+ this._restoreBuiltIns();
+
+ Error.stackTraceLimit = this._originalErrorStackTraceLimit;
+ this._isRavenInstalled = false;
+
+ return this;
+ },
+
+ /*
+ * Manually capture an exception and send it over to Sentry
+ *
+ * @param {error} ex An exception to be logged
+ * @param {object} options A specific set of options for this error [optional]
+ * @return {Raven}
+ */
+ captureException: function(ex, options) {
+ // Cases for sending ex as a message, rather than an exception
+ var isNotError = !isError(ex);
+ var isNotErrorEvent = !isErrorEvent(ex);
+ var isErrorEventWithoutError = isErrorEvent(ex) && !ex.error;
+
+ if ((isNotError && isNotErrorEvent) || isErrorEventWithoutError) {
+ return this.captureMessage(
+ ex,
+ objectMerge(
+ {
+ trimHeadFrames: 1,
+ stacktrace: true // if we fall back to captureMessage, default to attempting a new trace
+ },
+ options
+ )
+ );
+ }
+
+ // Get actual Error from ErrorEvent
+ if (isErrorEvent(ex)) ex = ex.error;
+
+ // Store the raw exception object for potential debugging and introspection
+ this._lastCapturedException = ex;
+
+ // TraceKit.report will re-raise any exception passed to it,
+ // which means you have to wrap it in try/catch. Instead, we
+ // can wrap it here and only re-raise if TraceKit.report
+ // raises an exception different from the one we asked to
+ // report on.
+ try {
+ var stack = TraceKit.computeStackTrace(ex);
+ this._handleStackInfo(stack, options);
+ } catch (ex1) {
+ if (ex !== ex1) {
+ throw ex1;
+ }
+ }
+
+ return this;
+ },
+
+ /*
+ * Manually send a message to Sentry
+ *
+ * @param {string} msg A plain message to be captured in Sentry
+ * @param {object} options A specific set of options for this message [optional]
+ * @return {Raven}
+ */
+ captureMessage: function(msg, options) {
+ // config() automagically converts ignoreErrors from a list to a RegExp so we need to test for an
+ // early call; we'll error on the side of logging anything called before configuration since it's
+ // probably something you should see:
+ if (
+ !!this._globalOptions.ignoreErrors.test &&
+ this._globalOptions.ignoreErrors.test(msg)
+ ) {
+ return;
+ }
+
+ options = options || {};
+
+ var data = objectMerge(
+ {
+ message: msg + '' // Make sure it's actually a string
+ },
+ options
+ );
+
+ var ex;
+ // Generate a "synthetic" stack trace from this point.
+ // NOTE: If you are a Sentry user, and you are seeing this stack frame, it is NOT indicative
+ // of a bug with Raven.js. Sentry generates synthetic traces either by configuration,
+ // or if it catches a thrown object without a "stack" property.
+ try {
+ throw new Error(msg);
+ } catch (ex1) {
+ ex = ex1;
+ }
+
+ // null exception name so `Error` isn't prefixed to msg
+ ex.name = null;
+ var stack = TraceKit.computeStackTrace(ex);
+
+ // stack[0] is `throw new Error(msg)` call itself, we are interested in the frame that was just before that, stack[1]
+ var initialCall = stack.stack[1];
+
+ var fileurl = (initialCall && initialCall.url) || '';
+
+ if (
+ !!this._globalOptions.ignoreUrls.test &&
+ this._globalOptions.ignoreUrls.test(fileurl)
+ ) {
+ return;
+ }
+
+ if (
+ !!this._globalOptions.whitelistUrls.test &&
+ !this._globalOptions.whitelistUrls.test(fileurl)
+ ) {
+ return;
+ }
+
+ if (this._globalOptions.stacktrace || (options && options.stacktrace)) {
+ options = objectMerge(
+ {
+ // fingerprint on msg, not stack trace (legacy behavior, could be
+ // revisited)
+ fingerprint: msg,
+ // since we know this is a synthetic trace, the top N-most frames
+ // MUST be from Raven.js, so mark them as in_app later by setting
+ // trimHeadFrames
+ trimHeadFrames: (options.trimHeadFrames || 0) + 1
+ },
+ options
+ );
+
+ var frames = this._prepareFrames(stack, options);
+ data.stacktrace = {
+ // Sentry expects frames oldest to newest
+ frames: frames.reverse()
+ };
+ }
+
+ // Fire away!
+ this._send(data);
+
+ return this;
+ },
+
+ captureBreadcrumb: function(obj) {
+ var crumb = objectMerge(
+ {
+ timestamp: now() / 1000
+ },
+ obj
+ );
+
+ if (isFunction(this._globalOptions.breadcrumbCallback)) {
+ var result = this._globalOptions.breadcrumbCallback(crumb);
+
+ if (isObject(result) && !isEmptyObject(result)) {
+ crumb = result;
+ } else if (result === false) {
+ return this;
+ }
+ }
+
+ this._breadcrumbs.push(crumb);
+ if (this._breadcrumbs.length > this._globalOptions.maxBreadcrumbs) {
+ this._breadcrumbs.shift();
+ }
+ return this;
+ },
+
+ addPlugin: function(plugin /*arg1, arg2, ... argN*/) {
+ var pluginArgs = [].slice.call(arguments, 1);
+
+ this._plugins.push([plugin, pluginArgs]);
+ if (this._isRavenInstalled) {
+ this._drainPlugins();
+ }
+
+ return this;
+ },
+
+ /*
+ * Set/clear a user to be sent along with the payload.
+ *
+ * @param {object} user An object representing user data [optional]
+ * @return {Raven}
+ */
+ setUserContext: function(user) {
+ // Intentionally do not merge here since that's an unexpected behavior.
+ this._globalContext.user = user;
+
+ return this;
+ },
+
+ /*
+ * Merge extra attributes to be sent along with the payload.
+ *
+ * @param {object} extra An object representing extra data [optional]
+ * @return {Raven}
+ */
+ setExtraContext: function(extra) {
+ this._mergeContext('extra', extra);
+
+ return this;
+ },
+
+ /*
+ * Merge tags to be sent along with the payload.
+ *
+ * @param {object} tags An object representing tags [optional]
+ * @return {Raven}
+ */
+ setTagsContext: function(tags) {
+ this._mergeContext('tags', tags);
+
+ return this;
+ },
+
+ /*
+ * Clear all of the context.
+ *
+ * @return {Raven}
+ */
+ clearContext: function() {
+ this._globalContext = {};
+
+ return this;
+ },
+
+ /*
+ * Get a copy of the current context. This cannot be mutated.
+ *
+ * @return {object} copy of context
+ */
+ getContext: function() {
+ // lol javascript
+ return JSON.parse(stringify(this._globalContext));
+ },
+
+ /*
+ * Set environment of application
+ *
+ * @param {string} environment Typically something like 'production'.
+ * @return {Raven}
+ */
+ setEnvironment: function(environment) {
+ this._globalOptions.environment = environment;
+
+ return this;
+ },
+
+ /*
+ * Set release version of application
+ *
+ * @param {string} release Typically something like a git SHA to identify version
+ * @return {Raven}
+ */
+ setRelease: function(release) {
+ this._globalOptions.release = release;
+
+ return this;
+ },
+
+ /*
+ * Set the dataCallback option
+ *
+ * @param {function} callback The callback to run which allows the
+ * data blob to be mutated before sending
+ * @return {Raven}
+ */
+ setDataCallback: function(callback) {
+ var original = this._globalOptions.dataCallback;
+ this._globalOptions.dataCallback = keepOriginalCallback(original, callback);
+ return this;
+ },
+
+ /*
+ * Set the breadcrumbCallback option
+ *
+ * @param {function} callback The callback to run which allows filtering
+ * or mutating breadcrumbs
+ * @return {Raven}
+ */
+ setBreadcrumbCallback: function(callback) {
+ var original = this._globalOptions.breadcrumbCallback;
+ this._globalOptions.breadcrumbCallback = keepOriginalCallback(original, callback);
+ return this;
+ },
+
+ /*
+ * Set the shouldSendCallback option
+ *
+ * @param {function} callback The callback to run which allows
+ * introspecting the blob before sending
+ * @return {Raven}
+ */
+ setShouldSendCallback: function(callback) {
+ var original = this._globalOptions.shouldSendCallback;
+ this._globalOptions.shouldSendCallback = keepOriginalCallback(original, callback);
+ return this;
+ },
+
+ /**
+ * Override the default HTTP transport mechanism that transmits data
+ * to the Sentry server.
+ *
+ * @param {function} transport Function invoked instead of the default
+ * `makeRequest` handler.
+ *
+ * @return {Raven}
+ */
+ setTransport: function(transport) {
+ this._globalOptions.transport = transport;
+
+ return this;
+ },
+
+ /*
+ * Get the latest raw exception that was captured by Raven.
+ *
+ * @return {error}
+ */
+ lastException: function() {
+ return this._lastCapturedException;
+ },
+
+ /*
+ * Get the last event id
+ *
+ * @return {string}
+ */
+ lastEventId: function() {
+ return this._lastEventId;
+ },
+
+ /*
+ * Determine if Raven is setup and ready to go.
+ *
+ * @return {boolean}
+ */
+ isSetup: function() {
+ if (!this._hasJSON) return false; // needs JSON support
+ if (!this._globalServer) {
+ if (!this.ravenNotConfiguredError) {
+ this.ravenNotConfiguredError = true;
+ this._logDebug('error', 'Error: Raven has not been configured.');
+ }
+ return false;
+ }
+ return true;
+ },
+
+ afterLoad: function() {
+ // TODO: remove window dependence?
+
+ // Attempt to initialize Raven on load
+ var RavenConfig = _window.RavenConfig;
+ if (RavenConfig) {
+ this.config(RavenConfig.dsn, RavenConfig.config).install();
+ }
+ },
+
+ showReportDialog: function(options) {
+ if (
+ !_document // doesn't work without a document (React native)
+ )
+ return;
+
+ options = options || {};
+
+ var lastEventId = options.eventId || this.lastEventId();
+ if (!lastEventId) {
+ throw new RavenConfigError('Missing eventId');
+ }
+
+ var dsn = options.dsn || this._dsn;
+ if (!dsn) {
+ throw new RavenConfigError('Missing DSN');
+ }
+
+ var encode = encodeURIComponent;
+ var qs = '';
+ qs += '?eventId=' + encode(lastEventId);
+ qs += '&dsn=' + encode(dsn);
+
+ var user = options.user || this._globalContext.user;
+ if (user) {
+ if (user.name) qs += '&name=' + encode(user.name);
+ if (user.email) qs += '&email=' + encode(user.email);
+ }
+
+ var globalServer = this._getGlobalServer(this._parseDSN(dsn));
+
+ var script = _document.createElement('script');
+ script.async = true;
+ script.src = globalServer + '/api/embed/error-page/' + qs;
+ (_document.head || _document.body).appendChild(script);
+ },
+
+ /**** Private functions ****/
+ _ignoreNextOnError: function() {
+ var self = this;
+ this._ignoreOnError += 1;
+ setTimeout(function() {
+ // onerror should trigger before setTimeout
+ self._ignoreOnError -= 1;
+ });
+ },
+
+ _triggerEvent: function(eventType, options) {
+ // NOTE: `event` is a native browser thing, so let's avoid conflicting wiht it
+ var evt, key;
+
+ if (!this._hasDocument) return;
+
+ options = options || {};
+
+ eventType = 'raven' + eventType.substr(0, 1).toUpperCase() + eventType.substr(1);
+
+ if (_document.createEvent) {
+ evt = _document.createEvent('HTMLEvents');
+ evt.initEvent(eventType, true, true);
+ } else {
+ evt = _document.createEventObject();
+ evt.eventType = eventType;
+ }
+
+ for (key in options)
+ if (hasKey(options, key)) {
+ evt[key] = options[key];
+ }
+
+ if (_document.createEvent) {
+ // IE9 if standards
+ _document.dispatchEvent(evt);
+ } else {
+ // IE8 regardless of Quirks or Standards
+ // IE9 if quirks
+ try {
+ _document.fireEvent('on' + evt.eventType.toLowerCase(), evt);
+ } catch (e) {
+ // Do nothing
+ }
+ }
+ },
+
+ /**
+ * Wraps addEventListener to capture UI breadcrumbs
+ * @param evtName the event name (e.g. "click")
+ * @returns {Function}
+ * @private
+ */
+ _breadcrumbEventHandler: function(evtName) {
+ var self = this;
+ return function(evt) {
+ // reset keypress timeout; e.g. triggering a 'click' after
+ // a 'keypress' will reset the keypress debounce so that a new
+ // set of keypresses can be recorded
+ self._keypressTimeout = null;
+
+ // It's possible this handler might trigger multiple times for the same
+ // event (e.g. event propagation through node ancestors). Ignore if we've
+ // already captured the event.
+ if (self._lastCapturedEvent === evt) return;
+
+ self._lastCapturedEvent = evt;
+
+ // try/catch both:
+ // - accessing evt.target (see getsentry/raven-js#838, #768)
+ // - `htmlTreeAsString` because it's complex, and just accessing the DOM incorrectly
+ // can throw an exception in some circumstances.
+ var target;
+ try {
+ target = htmlTreeAsString(evt.target);
+ } catch (e) {
+ target = '';
+ }
+
+ self.captureBreadcrumb({
+ category: 'ui.' + evtName, // e.g. ui.click, ui.input
+ message: target
+ });
+ };
+ },
+
+ /**
+ * Wraps addEventListener to capture keypress UI events
+ * @returns {Function}
+ * @private
+ */
+ _keypressEventHandler: function() {
+ var self = this,
+ debounceDuration = 1000; // milliseconds
+
+ // TODO: if somehow user switches keypress target before
+ // debounce timeout is triggered, we will only capture
+ // a single breadcrumb from the FIRST target (acceptable?)
+ return function(evt) {
+ var target;
+ try {
+ target = evt.target;
+ } catch (e) {
+ // just accessing event properties can throw an exception in some rare circumstances
+ // see: https://github.com/getsentry/raven-js/issues/838
+ return;
+ }
+ var tagName = target && target.tagName;
+
+ // only consider keypress events on actual input elements
+ // this will disregard keypresses targeting body (e.g. tabbing
+ // through elements, hotkeys, etc)
+ if (
+ !tagName ||
+ (tagName !== 'INPUT' && tagName !== 'TEXTAREA' && !target.isContentEditable)
+ )
+ return;
+
+ // record first keypress in a series, but ignore subsequent
+ // keypresses until debounce clears
+ var timeout = self._keypressTimeout;
+ if (!timeout) {
+ self._breadcrumbEventHandler('input')(evt);
+ }
+ clearTimeout(timeout);
+ self._keypressTimeout = setTimeout(function() {
+ self._keypressTimeout = null;
+ }, debounceDuration);
+ };
+ },
+
+ /**
+ * Captures a breadcrumb of type "navigation", normalizing input URLs
+ * @param to the originating URL
+ * @param from the target URL
+ * @private
+ */
+ _captureUrlChange: function(from, to) {
+ var parsedLoc = parseUrl(this._location.href);
+ var parsedTo = parseUrl(to);
+ var parsedFrom = parseUrl(from);
+
+ // because onpopstate only tells you the "new" (to) value of location.href, and
+ // not the previous (from) value, we need to track the value of the current URL
+ // state ourselves
+ this._lastHref = to;
+
+ // Use only the path component of the URL if the URL matches the current
+ // document (almost all the time when using pushState)
+ if (parsedLoc.protocol === parsedTo.protocol && parsedLoc.host === parsedTo.host)
+ to = parsedTo.relative;
+ if (parsedLoc.protocol === parsedFrom.protocol && parsedLoc.host === parsedFrom.host)
+ from = parsedFrom.relative;
+
+ this.captureBreadcrumb({
+ category: 'navigation',
+ data: {
+ to: to,
+ from: from
+ }
+ });
+ },
+
+ /**
+ * Wrap timer functions and event targets to catch errors and provide
+ * better metadata.
+ */
+ _instrumentTryCatch: function() {
+ var self = this;
+
+ var wrappedBuiltIns = self._wrappedBuiltIns;
+
+ function wrapTimeFn(orig) {
+ return function(fn, t) {
+ // preserve arity
+ // Make a copy of the arguments to prevent deoptimization
+ // https://github.com/petkaantonov/bluebird/wiki/Optimization-killers#32-leaking-arguments
+ var args = new Array(arguments.length);
+ for (var i = 0; i < args.length; ++i) {
+ args[i] = arguments[i];
+ }
+ var originalCallback = args[0];
+ if (isFunction(originalCallback)) {
+ args[0] = self.wrap(originalCallback);
+ }
+
+ // IE < 9 doesn't support .call/.apply on setInterval/setTimeout, but it
+ // also supports only two arguments and doesn't care what this is, so we
+ // can just call the original function directly.
+ if (orig.apply) {
+ return orig.apply(this, args);
+ } else {
+ return orig(args[0], args[1]);
+ }
+ };
+ }
+
+ var autoBreadcrumbs = this._globalOptions.autoBreadcrumbs;
+
+ function wrapEventTarget(global) {
+ var proto = _window[global] && _window[global].prototype;
+ if (proto && proto.hasOwnProperty && proto.hasOwnProperty('addEventListener')) {
+ fill(
+ proto,
+ 'addEventListener',
+ function(orig) {
+ return function(evtName, fn, capture, secure) {
+ // preserve arity
+ try {
+ if (fn && fn.handleEvent) {
+ fn.handleEvent = self.wrap(fn.handleEvent);
+ }
+ } catch (err) {
+ // can sometimes get 'Permission denied to access property "handle Event'
+ }
+
+ // More breadcrumb DOM capture ... done here and not in `_instrumentBreadcrumbs`
+ // so that we don't have more than one wrapper function
+ var before, clickHandler, keypressHandler;
+
+ if (
+ autoBreadcrumbs &&
+ autoBreadcrumbs.dom &&
+ (global === 'EventTarget' || global === 'Node')
+ ) {
+ // NOTE: generating multiple handlers per addEventListener invocation, should
+ // revisit and verify we can just use one (almost certainly)
+ clickHandler = self._breadcrumbEventHandler('click');
+ keypressHandler = self._keypressEventHandler();
+ before = function(evt) {
+ // need to intercept every DOM event in `before` argument, in case that
+ // same wrapped method is re-used for different events (e.g. mousemove THEN click)
+ // see #724
+ if (!evt) return;
+
+ var eventType;
+ try {
+ eventType = evt.type;
+ } catch (e) {
+ // just accessing event properties can throw an exception in some rare circumstances
+ // see: https://github.com/getsentry/raven-js/issues/838
+ return;
+ }
+ if (eventType === 'click') return clickHandler(evt);
+ else if (eventType === 'keypress') return keypressHandler(evt);
+ };
+ }
+ return orig.call(
+ this,
+ evtName,
+ self.wrap(fn, undefined, before),
+ capture,
+ secure
+ );
+ };
+ },
+ wrappedBuiltIns
+ );
+ fill(
+ proto,
+ 'removeEventListener',
+ function(orig) {
+ return function(evt, fn, capture, secure) {
+ try {
+ fn = fn && (fn.__raven_wrapper__ ? fn.__raven_wrapper__ : fn);
+ } catch (e) {
+ // ignore, accessing __raven_wrapper__ will throw in some Selenium environments
+ }
+ return orig.call(this, evt, fn, capture, secure);
+ };
+ },
+ wrappedBuiltIns
+ );
+ }
+ }
+
+ fill(_window, 'setTimeout', wrapTimeFn, wrappedBuiltIns);
+ fill(_window, 'setInterval', wrapTimeFn, wrappedBuiltIns);
+ if (_window.requestAnimationFrame) {
+ fill(
+ _window,
+ 'requestAnimationFrame',
+ function(orig) {
+ return function(cb) {
+ return orig(self.wrap(cb));
+ };
+ },
+ wrappedBuiltIns
+ );
+ }
+
+ // event targets borrowed from bugsnag-js:
+ // https://github.com/bugsnag/bugsnag-js/blob/master/src/bugsnag.js#L666
+ var eventTargets = [
+ 'EventTarget',
+ 'Window',
+ 'Node',
+ 'ApplicationCache',
+ 'AudioTrackList',
+ 'ChannelMergerNode',
+ 'CryptoOperation',
+ 'EventSource',
+ 'FileReader',
+ 'HTMLUnknownElement',
+ 'IDBDatabase',
+ 'IDBRequest',
+ 'IDBTransaction',
+ 'KeyOperation',
+ 'MediaController',
+ 'MessagePort',
+ 'ModalWindow',
+ 'Notification',
+ 'SVGElementInstance',
+ 'Screen',
+ 'TextTrack',
+ 'TextTrackCue',
+ 'TextTrackList',
+ 'WebSocket',
+ 'WebSocketWorker',
+ 'Worker',
+ 'XMLHttpRequest',
+ 'XMLHttpRequestEventTarget',
+ 'XMLHttpRequestUpload'
+ ];
+ for (var i = 0; i < eventTargets.length; i++) {
+ wrapEventTarget(eventTargets[i]);
+ }
+ },
+
+ /**
+ * Instrument browser built-ins w/ breadcrumb capturing
+ * - XMLHttpRequests
+ * - DOM interactions (click/typing)
+ * - window.location changes
+ * - console
+ *
+ * Can be disabled or individually configured via the `autoBreadcrumbs` config option
+ */
+ _instrumentBreadcrumbs: function() {
+ var self = this;
+ var autoBreadcrumbs = this._globalOptions.autoBreadcrumbs;
+
+ var wrappedBuiltIns = self._wrappedBuiltIns;
+
+ function wrapProp(prop, xhr) {
+ if (prop in xhr && isFunction(xhr[prop])) {
+ fill(xhr, prop, function(orig) {
+ return self.wrap(orig);
+ }); // intentionally don't track filled methods on XHR instances
+ }
+ }
+
+ if (autoBreadcrumbs.xhr && 'XMLHttpRequest' in _window) {
+ var xhrproto = XMLHttpRequest.prototype;
+ fill(
+ xhrproto,
+ 'open',
+ function(origOpen) {
+ return function(method, url) {
+ // preserve arity
+
+ // if Sentry key appears in URL, don't capture
+ if (isString(url) && url.indexOf(self._globalKey) === -1) {
+ this.__raven_xhr = {
+ method: method,
+ url: url,
+ status_code: null
+ };
+ }
+
+ return origOpen.apply(this, arguments);
+ };
+ },
+ wrappedBuiltIns
+ );
+
+ fill(
+ xhrproto,
+ 'send',
+ function(origSend) {
+ return function(data) {
+ // preserve arity
+ var xhr = this;
+
+ function onreadystatechangeHandler() {
+ if (xhr.__raven_xhr && xhr.readyState === 4) {
+ try {
+ // touching statusCode in some platforms throws
+ // an exception
+ xhr.__raven_xhr.status_code = xhr.status;
+ } catch (e) {
+ /* do nothing */
+ }
+
+ self.captureBreadcrumb({
+ type: 'http',
+ category: 'xhr',
+ data: xhr.__raven_xhr
+ });
+ }
+ }
+
+ var props = ['onload', 'onerror', 'onprogress'];
+ for (var j = 0; j < props.length; j++) {
+ wrapProp(props[j], xhr);
+ }
+
+ if ('onreadystatechange' in xhr && isFunction(xhr.onreadystatechange)) {
+ fill(
+ xhr,
+ 'onreadystatechange',
+ function(orig) {
+ return self.wrap(orig, undefined, onreadystatechangeHandler);
+ } /* intentionally don't track this instrumentation */
+ );
+ } else {
+ // if onreadystatechange wasn't actually set by the page on this xhr, we
+ // are free to set our own and capture the breadcrumb
+ xhr.onreadystatechange = onreadystatechangeHandler;
+ }
+
+ return origSend.apply(this, arguments);
+ };
+ },
+ wrappedBuiltIns
+ );
+ }
+
+ if (autoBreadcrumbs.xhr && 'fetch' in _window) {
+ fill(
+ _window,
+ 'fetch',
+ function(origFetch) {
+ return function(fn, t) {
+ // preserve arity
+ // Make a copy of the arguments to prevent deoptimization
+ // https://github.com/petkaantonov/bluebird/wiki/Optimization-killers#32-leaking-arguments
+ var args = new Array(arguments.length);
+ for (var i = 0; i < args.length; ++i) {
+ args[i] = arguments[i];
+ }
+
+ var fetchInput = args[0];
+ var method = 'GET';
+ var url;
+
+ if (typeof fetchInput === 'string') {
+ url = fetchInput;
+ } else if ('Request' in _window && fetchInput instanceof _window.Request) {
+ url = fetchInput.url;
+ if (fetchInput.method) {
+ method = fetchInput.method;
+ }
+ } else {
+ url = '' + fetchInput;
+ }
+
+ if (args[1] && args[1].method) {
+ method = args[1].method;
+ }
+
+ var fetchData = {
+ method: method,
+ url: url,
+ status_code: null
+ };
+
+ self.captureBreadcrumb({
+ type: 'http',
+ category: 'fetch',
+ data: fetchData
+ });
+
+ return origFetch.apply(this, args).then(function(response) {
+ fetchData.status_code = response.status;
+
+ return response;
+ });
+ };
+ },
+ wrappedBuiltIns
+ );
+ }
+
+ // Capture breadcrumbs from any click that is unhandled / bubbled up all the way
+ // to the document. Do this before we instrument addEventListener.
+ if (autoBreadcrumbs.dom && this._hasDocument) {
+ if (_document.addEventListener) {
+ _document.addEventListener('click', self._breadcrumbEventHandler('click'), false);
+ _document.addEventListener('keypress', self._keypressEventHandler(), false);
+ } else {
+ // IE8 Compatibility
+ _document.attachEvent('onclick', self._breadcrumbEventHandler('click'));
+ _document.attachEvent('onkeypress', self._keypressEventHandler());
+ }
+ }
+
+ // record navigation (URL) changes
+ // NOTE: in Chrome App environment, touching history.pushState, *even inside
+ // a try/catch block*, will cause Chrome to output an error to console.error
+ // borrowed from: https://github.com/angular/angular.js/pull/13945/files
+ var chrome = _window.chrome;
+ var isChromePackagedApp = chrome && chrome.app && chrome.app.runtime;
+ var hasPushAndReplaceState =
+ !isChromePackagedApp &&
+ _window.history &&
+ history.pushState &&
+ history.replaceState;
+ if (autoBreadcrumbs.location && hasPushAndReplaceState) {
+ // TODO: remove onpopstate handler on uninstall()
+ var oldOnPopState = _window.onpopstate;
+ _window.onpopstate = function() {
+ var currentHref = self._location.href;
+ self._captureUrlChange(self._lastHref, currentHref);
+
+ if (oldOnPopState) {
+ return oldOnPopState.apply(this, arguments);
+ }
+ };
+
+ var historyReplacementFunction = function(origHistFunction) {
+ // note history.pushState.length is 0; intentionally not declaring
+ // params to preserve 0 arity
+ return function(/* state, title, url */) {
+ var url = arguments.length > 2 ? arguments[2] : undefined;
+
+ // url argument is optional
+ if (url) {
+ // coerce to string (this is what pushState does)
+ self._captureUrlChange(self._lastHref, url + '');
+ }
+
+ return origHistFunction.apply(this, arguments);
+ };
+ };
+
+ fill(history, 'pushState', historyReplacementFunction, wrappedBuiltIns);
+ fill(history, 'replaceState', historyReplacementFunction, wrappedBuiltIns);
+ }
+
+ if (autoBreadcrumbs.console && 'console' in _window && console.log) {
+ // console
+ var consoleMethodCallback = function(msg, data) {
+ self.captureBreadcrumb({
+ message: msg,
+ level: data.level,
+ category: 'console'
+ });
+ };
+
+ each(['debug', 'info', 'warn', 'error', 'log'], function(_, level) {
+ wrapConsoleMethod(console, level, consoleMethodCallback);
+ });
+ }
+ },
+
+ _restoreBuiltIns: function() {
+ // restore any wrapped builtins
+ var builtin;
+ while (this._wrappedBuiltIns.length) {
+ builtin = this._wrappedBuiltIns.shift();
+
+ var obj = builtin[0],
+ name = builtin[1],
+ orig = builtin[2];
+
+ obj[name] = orig;
+ }
+ },
+
+ _drainPlugins: function() {
+ var self = this;
+
+ // FIX ME TODO
+ each(this._plugins, function(_, plugin) {
+ var installer = plugin[0];
+ var args = plugin[1];
+ installer.apply(self, [self].concat(args));
+ });
+ },
+
+ _parseDSN: function(str) {
+ var m = dsnPattern.exec(str),
+ dsn = {},
+ i = 7;
+
+ try {
+ while (i--) dsn[dsnKeys[i]] = m[i] || '';
+ } catch (e) {
+ throw new RavenConfigError('Invalid DSN: ' + str);
+ }
+
+ if (dsn.pass && !this._globalOptions.allowSecretKey) {
+ throw new RavenConfigError(
+ 'Do not specify your secret key in the DSN. See: http://bit.ly/raven-secret-key'
+ );
+ }
+
+ return dsn;
+ },
+
+ _getGlobalServer: function(uri) {
+ // assemble the endpoint from the uri pieces
+ var globalServer = '//' + uri.host + (uri.port ? ':' + uri.port : '');
+
+ if (uri.protocol) {
+ globalServer = uri.protocol + ':' + globalServer;
+ }
+ return globalServer;
+ },
+
+ _handleOnErrorStackInfo: function() {
+ // if we are intentionally ignoring errors via onerror, bail out
+ if (!this._ignoreOnError) {
+ this._handleStackInfo.apply(this, arguments);
+ }
+ },
+
+ _handleStackInfo: function(stackInfo, options) {
+ var frames = this._prepareFrames(stackInfo, options);
+
+ this._triggerEvent('handle', {
+ stackInfo: stackInfo,
+ options: options
+ });
+
+ this._processException(
+ stackInfo.name,
+ stackInfo.message,
+ stackInfo.url,
+ stackInfo.lineno,
+ frames,
+ options
+ );
+ },
+
+ _prepareFrames: function(stackInfo, options) {
+ var self = this;
+ var frames = [];
+ if (stackInfo.stack && stackInfo.stack.length) {
+ each(stackInfo.stack, function(i, stack) {
+ var frame = self._normalizeFrame(stack, stackInfo.url);
+ if (frame) {
+ frames.push(frame);
+ }
+ });
+
+ // e.g. frames captured via captureMessage throw
+ if (options && options.trimHeadFrames) {
+ for (var j = 0; j < options.trimHeadFrames && j < frames.length; j++) {
+ frames[j].in_app = false;
+ }
+ }
+ }
+ frames = frames.slice(0, this._globalOptions.stackTraceLimit);
+ return frames;
+ },
+
+ _normalizeFrame: function(frame, stackInfoUrl) {
+ // normalize the frames data
+ var normalized = {
+ filename: frame.url,
+ lineno: frame.line,
+ colno: frame.column,
+ function: frame.func || '?'
+ };
+
+ // Case when we don't have any information about the error
+ // E.g. throwing a string or raw object, instead of an `Error` in Firefox
+ // Generating synthetic error doesn't add any value here
+ //
+ // We should probably somehow let a user know that they should fix their code
+ if (!frame.url) {
+ normalized.filename = stackInfoUrl; // fallback to whole stacks url from onerror handler
+ }
+
+ normalized.in_app = !// determine if an exception came from outside of our app
+ // first we check the global includePaths list.
+ (
+ (!!this._globalOptions.includePaths.test &&
+ !this._globalOptions.includePaths.test(normalized.filename)) ||
+ // Now we check for fun, if the function name is Raven or TraceKit
+ /(Raven|TraceKit)\./.test(normalized['function']) ||
+ // finally, we do a last ditch effort and check for raven.min.js
+ /raven\.(min\.)?js$/.test(normalized.filename)
+ );
+
+ return normalized;
+ },
+
+ _processException: function(type, message, fileurl, lineno, frames, options) {
+ var prefixedMessage = (type ? type + ': ' : '') + (message || '');
+ if (
+ !!this._globalOptions.ignoreErrors.test &&
+ (this._globalOptions.ignoreErrors.test(message) ||
+ this._globalOptions.ignoreErrors.test(prefixedMessage))
+ ) {
+ return;
+ }
+
+ var stacktrace;
+
+ if (frames && frames.length) {
+ fileurl = frames[0].filename || fileurl;
+ // Sentry expects frames oldest to newest
+ // and JS sends them as newest to oldest
+ frames.reverse();
+ stacktrace = {frames: frames};
+ } else if (fileurl) {
+ stacktrace = {
+ frames: [
+ {
+ filename: fileurl,
+ lineno: lineno,
+ in_app: true
+ }
+ ]
+ };
+ }
+
+ if (
+ !!this._globalOptions.ignoreUrls.test &&
+ this._globalOptions.ignoreUrls.test(fileurl)
+ ) {
+ return;
+ }
+
+ if (
+ !!this._globalOptions.whitelistUrls.test &&
+ !this._globalOptions.whitelistUrls.test(fileurl)
+ ) {
+ return;
+ }
+
+ var data = objectMerge(
+ {
+ // sentry.interfaces.Exception
+ exception: {
+ values: [
+ {
+ type: type,
+ value: message,
+ stacktrace: stacktrace
+ }
+ ]
+ },
+ culprit: fileurl
+ },
+ options
+ );
+
+ // Fire away!
+ this._send(data);
+ },
+
+ _trimPacket: function(data) {
+ // For now, we only want to truncate the two different messages
+ // but this could/should be expanded to just trim everything
+ var max = this._globalOptions.maxMessageLength;
+ if (data.message) {
+ data.message = truncate(data.message, max);
+ }
+ if (data.exception) {
+ var exception = data.exception.values[0];
+ exception.value = truncate(exception.value, max);
+ }
+
+ var request = data.request;
+ if (request) {
+ if (request.url) {
+ request.url = truncate(request.url, this._globalOptions.maxUrlLength);
+ }
+ if (request.Referer) {
+ request.Referer = truncate(request.Referer, this._globalOptions.maxUrlLength);
+ }
+ }
+
+ if (data.breadcrumbs && data.breadcrumbs.values)
+ this._trimBreadcrumbs(data.breadcrumbs);
+
+ return data;
+ },
+
+ /**
+ * Truncate breadcrumb values (right now just URLs)
+ */
+ _trimBreadcrumbs: function(breadcrumbs) {
+ // known breadcrumb properties with urls
+ // TODO: also consider arbitrary prop values that start with (https?)?://
+ var urlProps = ['to', 'from', 'url'],
+ urlProp,
+ crumb,
+ data;
+
+ for (var i = 0; i < breadcrumbs.values.length; ++i) {
+ crumb = breadcrumbs.values[i];
+ if (
+ !crumb.hasOwnProperty('data') ||
+ !isObject(crumb.data) ||
+ objectFrozen(crumb.data)
+ )
+ continue;
+
+ data = objectMerge({}, crumb.data);
+ for (var j = 0; j < urlProps.length; ++j) {
+ urlProp = urlProps[j];
+ if (data.hasOwnProperty(urlProp) && data[urlProp]) {
+ data[urlProp] = truncate(data[urlProp], this._globalOptions.maxUrlLength);
+ }
+ }
+ breadcrumbs.values[i].data = data;
+ }
+ },
+
+ _getHttpData: function() {
+ if (!this._hasNavigator && !this._hasDocument) return;
+ var httpData = {};
+
+ if (this._hasNavigator && _navigator.userAgent) {
+ httpData.headers = {
+ 'User-Agent': navigator.userAgent
+ };
+ }
+
+ if (this._hasDocument) {
+ if (_document.location && _document.location.href) {
+ httpData.url = _document.location.href;
+ }
+ if (_document.referrer) {
+ if (!httpData.headers) httpData.headers = {};
+ httpData.headers.Referer = _document.referrer;
+ }
+ }
+
+ return httpData;
+ },
+
+ _resetBackoff: function() {
+ this._backoffDuration = 0;
+ this._backoffStart = null;
+ },
+
+ _shouldBackoff: function() {
+ return this._backoffDuration && now() - this._backoffStart < this._backoffDuration;
+ },
+
+ /**
+ * Returns true if the in-process data payload matches the signature
+ * of the previously-sent data
+ *
+ * NOTE: This has to be done at this level because TraceKit can generate
+ * data from window.onerror WITHOUT an exception object (IE8, IE9,
+ * other old browsers). This can take the form of an "exception"
+ * data object with a single frame (derived from the onerror args).
+ */
+ _isRepeatData: function(current) {
+ var last = this._lastData;
+
+ if (
+ !last ||
+ current.message !== last.message || // defined for captureMessage
+ current.culprit !== last.culprit // defined for captureException/onerror
+ )
+ return false;
+
+ // Stacktrace interface (i.e. from captureMessage)
+ if (current.stacktrace || last.stacktrace) {
+ return isSameStacktrace(current.stacktrace, last.stacktrace);
+ } else if (current.exception || last.exception) {
+ // Exception interface (i.e. from captureException/onerror)
+ return isSameException(current.exception, last.exception);
+ }
+
+ return true;
+ },
+
+ _setBackoffState: function(request) {
+ // If we are already in a backoff state, don't change anything
+ if (this._shouldBackoff()) {
+ return;
+ }
+
+ var status = request.status;
+
+ // 400 - project_id doesn't exist or some other fatal
+ // 401 - invalid/revoked dsn
+ // 429 - too many requests
+ if (!(status === 400 || status === 401 || status === 429)) return;
+
+ var retry;
+ try {
+ // If Retry-After is not in Access-Control-Expose-Headers, most
+ // browsers will throw an exception trying to access it
+ retry = request.getResponseHeader('Retry-After');
+ retry = parseInt(retry, 10) * 1000; // Retry-After is returned in seconds
+ } catch (e) {
+ /* eslint no-empty:0 */
+ }
+
+ this._backoffDuration = retry
+ ? // If Sentry server returned a Retry-After value, use it
+ retry
+ : // Otherwise, double the last backoff duration (starts at 1 sec)
+ this._backoffDuration * 2 || 1000;
+
+ this._backoffStart = now();
+ },
+
+ _send: function(data) {
+ var globalOptions = this._globalOptions;
+
+ var baseData = {
+ project: this._globalProject,
+ logger: globalOptions.logger,
+ platform: 'javascript'
+ },
+ httpData = this._getHttpData();
+
+ if (httpData) {
+ baseData.request = httpData;
+ }
+
+ // HACK: delete `trimHeadFrames` to prevent from appearing in outbound payload
+ if (data.trimHeadFrames) delete data.trimHeadFrames;
+
+ data = objectMerge(baseData, data);
+
+ // Merge in the tags and extra separately since objectMerge doesn't handle a deep merge
+ data.tags = objectMerge(objectMerge({}, this._globalContext.tags), data.tags);
+ data.extra = objectMerge(objectMerge({}, this._globalContext.extra), data.extra);
+
+ // Send along our own collected metadata with extra
+ data.extra['session:duration'] = now() - this._startTime;
+
+ if (this._breadcrumbs && this._breadcrumbs.length > 0) {
+ // intentionally make shallow copy so that additions
+ // to breadcrumbs aren't accidentally sent in this request
+ data.breadcrumbs = {
+ values: [].slice.call(this._breadcrumbs, 0)
+ };
+ }
+
+ // If there are no tags/extra, strip the key from the payload alltogther.
+ if (isEmptyObject(data.tags)) delete data.tags;
+
+ if (this._globalContext.user) {
+ // sentry.interfaces.User
+ data.user = this._globalContext.user;
+ }
+
+ // Include the environment if it's defined in globalOptions
+ if (globalOptions.environment) data.environment = globalOptions.environment;
+
+ // Include the release if it's defined in globalOptions
+ if (globalOptions.release) data.release = globalOptions.release;
+
+ // Include server_name if it's defined in globalOptions
+ if (globalOptions.serverName) data.server_name = globalOptions.serverName;
+
+ if (isFunction(globalOptions.dataCallback)) {
+ data = globalOptions.dataCallback(data) || data;
+ }
+
+ // Why??????????
+ if (!data || isEmptyObject(data)) {
+ return;
+ }
+
+ // Check if the request should be filtered or not
+ if (
+ isFunction(globalOptions.shouldSendCallback) &&
+ !globalOptions.shouldSendCallback(data)
+ ) {
+ return;
+ }
+
+ // Backoff state: Sentry server previously responded w/ an error (e.g. 429 - too many requests),
+ // so drop requests until "cool-off" period has elapsed.
+ if (this._shouldBackoff()) {
+ this._logDebug('warn', 'Raven dropped error due to backoff: ', data);
+ return;
+ }
+
+ if (typeof globalOptions.sampleRate === 'number') {
+ if (Math.random() < globalOptions.sampleRate) {
+ this._sendProcessedPayload(data);
+ }
+ } else {
+ this._sendProcessedPayload(data);
+ }
+ },
+
+ _getUuid: function() {
+ return uuid4();
+ },
+
+ _sendProcessedPayload: function(data, callback) {
+ var self = this;
+ var globalOptions = this._globalOptions;
+
+ if (!this.isSetup()) return;
+
+ // Try and clean up the packet before sending by truncating long values
+ data = this._trimPacket(data);
+
+ // ideally duplicate error testing should occur *before* dataCallback/shouldSendCallback,
+ // but this would require copying an un-truncated copy of the data packet, which can be
+ // arbitrarily deep (extra_data) -- could be worthwhile? will revisit
+ if (!this._globalOptions.allowDuplicates && this._isRepeatData(data)) {
+ this._logDebug('warn', 'Raven dropped repeat event: ', data);
+ return;
+ }
+
+ // Send along an event_id if not explicitly passed.
+ // This event_id can be used to reference the error within Sentry itself.
+ // Set lastEventId after we know the error should actually be sent
+ this._lastEventId = data.event_id || (data.event_id = this._getUuid());
+
+ // Store outbound payload after trim
+ this._lastData = data;
+
+ this._logDebug('debug', 'Raven about to send:', data);
+
+ var auth = {
+ sentry_version: '7',
+ sentry_client: 'raven-js/' + this.VERSION,
+ sentry_key: this._globalKey
+ };
+
+ if (this._globalSecret) {
+ auth.sentry_secret = this._globalSecret;
+ }
+
+ var exception = data.exception && data.exception.values[0];
+ this.captureBreadcrumb({
+ category: 'sentry',
+ message: exception
+ ? (exception.type ? exception.type + ': ' : '') + exception.value
+ : data.message,
+ event_id: data.event_id,
+ level: data.level || 'error' // presume error unless specified
+ });
+
+ var url = this._globalEndpoint;
+ (globalOptions.transport || this._makeRequest).call(this, {
+ url: url,
+ auth: auth,
+ data: data,
+ options: globalOptions,
+ onSuccess: function success() {
+ self._resetBackoff();
+
+ self._triggerEvent('success', {
+ data: data,
+ src: url
+ });
+ callback && callback();
+ },
+ onError: function failure(error) {
+ self._logDebug('error', 'Raven transport failed to send: ', error);
+
+ if (error.request) {
+ self._setBackoffState(error.request);
+ }
+
+ self._triggerEvent('failure', {
+ data: data,
+ src: url
+ });
+ error = error || new Error('Raven send failed (no additional details provided)');
+ callback && callback(error);
+ }
+ });
+ },
+
+ _makeRequest: function(opts) {
+ var request = _window.XMLHttpRequest && new _window.XMLHttpRequest();
+ if (!request) return;
+
+ // if browser doesn't support CORS (e.g. IE7), we are out of luck
+ var hasCORS = 'withCredentials' in request || typeof XDomainRequest !== 'undefined';
+
+ if (!hasCORS) return;
+
+ var url = opts.url;
+
+ if ('withCredentials' in request) {
+ request.onreadystatechange = function() {
+ if (request.readyState !== 4) {
+ return;
+ } else if (request.status === 200) {
+ opts.onSuccess && opts.onSuccess();
+ } else if (opts.onError) {
+ var err = new Error('Sentry error code: ' + request.status);
+ err.request = request;
+ opts.onError(err);
+ }
+ };
+ } else {
+ request = new XDomainRequest();
+ // xdomainrequest cannot go http -> https (or vice versa),
+ // so always use protocol relative
+ url = url.replace(/^https?:/, '');
+
+ // onreadystatechange not supported by XDomainRequest
+ if (opts.onSuccess) {
+ request.onload = opts.onSuccess;
+ }
+ if (opts.onError) {
+ request.onerror = function() {
+ var err = new Error('Sentry error code: XDomainRequest');
+ err.request = request;
+ opts.onError(err);
+ };
+ }
+ }
+
+ // NOTE: auth is intentionally sent as part of query string (NOT as custom
+ // HTTP header) so as to avoid preflight CORS requests
+ request.open('POST', url + '?' + urlencode(opts.auth));
+ request.send(stringify(opts.data));
+ },
+
+ _logDebug: function(level) {
+ if (this._originalConsoleMethods[level] && this.debug) {
+ // In IE<10 console methods do not have their own 'apply' method
+ Function.prototype.apply.call(
+ this._originalConsoleMethods[level],
+ this._originalConsole,
+ [].slice.call(arguments, 1)
+ );
+ }
+ },
+
+ _mergeContext: function(key, context) {
+ if (isUndefined(context)) {
+ delete this._globalContext[key];
+ } else {
+ this._globalContext[key] = objectMerge(this._globalContext[key] || {}, context);
+ }
+ }
+};
+
+// Deprecations
+Raven.prototype.setUser = Raven.prototype.setUserContext;
+Raven.prototype.setReleaseContext = Raven.prototype.setRelease;
+
+module.exports = Raven;
+
+
+/***/ }),
+
+/***/ "./node_modules/raven-js/src/singleton.js":
+/*!************************************************!*\
+ !*** ./node_modules/raven-js/src/singleton.js ***!
+ \************************************************/
+/***/ ((module, __unused_webpack_exports, __webpack_require__) => {
+
+/**
+ * Enforces a single instance of the Raven client, and the
+ * main entry point for Raven. If you are a consumer of the
+ * Raven library, you SHOULD load this file (vs raven.js).
+ **/
+
+var RavenConstructor = __webpack_require__(/*! ./raven */ "./node_modules/raven-js/src/raven.js");
+
+// This is to be defensive in environments where window does not exist (see https://github.com/getsentry/raven-js/pull/785)
+var _window =
+ typeof window !== 'undefined'
+ ? window
+ : typeof __webpack_require__.g !== 'undefined' ? __webpack_require__.g : typeof self !== 'undefined' ? self : {};
+var _Raven = _window.Raven;
+
+var Raven = new RavenConstructor();
+
+/*
+ * Allow multiple versions of Raven to be installed.
+ * Strip Raven from the global context and returns the instance.
+ *
+ * @return {Raven}
+ */
+Raven.noConflict = function() {
+ _window.Raven = _Raven;
+ return Raven;
+};
+
+Raven.afterLoad();
+
+module.exports = Raven;
+
+
+/***/ }),
+
+/***/ "./node_modules/raven-js/src/utils.js":
+/*!********************************************!*\
+ !*** ./node_modules/raven-js/src/utils.js ***!
+ \********************************************/
+/***/ ((module, __unused_webpack_exports, __webpack_require__) => {
+
+var _window =
+ typeof window !== 'undefined'
+ ? window
+ : typeof __webpack_require__.g !== 'undefined' ? __webpack_require__.g : typeof self !== 'undefined' ? self : {};
+
+function isObject(what) {
+ return typeof what === 'object' && what !== null;
+}
+
+// Yanked from https://git.io/vS8DV re-used under CC0
+// with some tiny modifications
+function isError(value) {
+ switch ({}.toString.call(value)) {
+ case '[object Error]':
+ return true;
+ case '[object Exception]':
+ return true;
+ case '[object DOMException]':
+ return true;
+ default:
+ return value instanceof Error;
+ }
+}
+
+function isErrorEvent(value) {
+ return supportsErrorEvent() && {}.toString.call(value) === '[object ErrorEvent]';
+}
+
+function isUndefined(what) {
+ return what === void 0;
+}
+
+function isFunction(what) {
+ return typeof what === 'function';
+}
+
+function isString(what) {
+ return Object.prototype.toString.call(what) === '[object String]';
+}
+
+function isEmptyObject(what) {
+ for (var _ in what) return false; // eslint-disable-line guard-for-in, no-unused-vars
+ return true;
+}
+
+function supportsErrorEvent() {
+ try {
+ new ErrorEvent(''); // eslint-disable-line no-new
+ return true;
+ } catch (e) {
+ return false;
+ }
+}
+
+function wrappedCallback(callback) {
+ function dataCallback(data, original) {
+ var normalizedData = callback(data) || data;
+ if (original) {
+ return original(normalizedData) || normalizedData;
+ }
+ return normalizedData;
+ }
+
+ return dataCallback;
+}
+
+function each(obj, callback) {
+ var i, j;
+
+ if (isUndefined(obj.length)) {
+ for (i in obj) {
+ if (hasKey(obj, i)) {
+ callback.call(null, i, obj[i]);
+ }
+ }
+ } else {
+ j = obj.length;
+ if (j) {
+ for (i = 0; i < j; i++) {
+ callback.call(null, i, obj[i]);
+ }
+ }
+ }
+}
+
+function objectMerge(obj1, obj2) {
+ if (!obj2) {
+ return obj1;
+ }
+ each(obj2, function(key, value) {
+ obj1[key] = value;
+ });
+ return obj1;
+}
+
+/**
+ * This function is only used for react-native.
+ * react-native freezes object that have already been sent over the
+ * js bridge. We need this function in order to check if the object is frozen.
+ * So it's ok that objectFrozen returns false if Object.isFrozen is not
+ * supported because it's not relevant for other "platforms". See related issue:
+ * https://github.com/getsentry/react-native-sentry/issues/57
+ */
+function objectFrozen(obj) {
+ if (!Object.isFrozen) {
+ return false;
+ }
+ return Object.isFrozen(obj);
+}
+
+function truncate(str, max) {
+ return !max || str.length <= max ? str : str.substr(0, max) + '\u2026';
+}
+
+/**
+ * hasKey, a better form of hasOwnProperty
+ * Example: hasKey(MainHostObject, property) === true/false
+ *
+ * @param {Object} host object to check property
+ * @param {string} key to check
+ */
+function hasKey(object, key) {
+ return Object.prototype.hasOwnProperty.call(object, key);
+}
+
+function joinRegExp(patterns) {
+ // Combine an array of regular expressions and strings into one large regexp
+ // Be mad.
+ var sources = [],
+ i = 0,
+ len = patterns.length,
+ pattern;
+
+ for (; i < len; i++) {
+ pattern = patterns[i];
+ if (isString(pattern)) {
+ // If it's a string, we need to escape it
+ // Taken from: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Guide/Regular_Expressions
+ sources.push(pattern.replace(/([.*+?^=!:${}()|\[\]\/\\])/g, '\\$1'));
+ } else if (pattern && pattern.source) {
+ // If it's a regexp already, we want to extract the source
+ sources.push(pattern.source);
+ }
+ // Intentionally skip other cases
+ }
+ return new RegExp(sources.join('|'), 'i');
+}
+
+function urlencode(o) {
+ var pairs = [];
+ each(o, function(key, value) {
+ pairs.push(encodeURIComponent(key) + '=' + encodeURIComponent(value));
+ });
+ return pairs.join('&');
+}
+
+// borrowed from https://tools.ietf.org/html/rfc3986#appendix-B
+// intentionally using regex and not href parsing trick because React Native and other
+// environments where DOM might not be available
+function parseUrl(url) {
+ var match = url.match(/^(([^:\/?#]+):)?(\/\/([^\/?#]*))?([^?#]*)(\?([^#]*))?(#(.*))?$/);
+ if (!match) return {};
+
+ // coerce to undefined values to empty string so we don't get 'undefined'
+ var query = match[6] || '';
+ var fragment = match[8] || '';
+ return {
+ protocol: match[2],
+ host: match[4],
+ path: match[5],
+ relative: match[5] + query + fragment // everything minus origin
+ };
+}
+function uuid4() {
+ var crypto = _window.crypto || _window.msCrypto;
+
+ if (!isUndefined(crypto) && crypto.getRandomValues) {
+ // Use window.crypto API if available
+ // eslint-disable-next-line no-undef
+ var arr = new Uint16Array(8);
+ crypto.getRandomValues(arr);
+
+ // set 4 in byte 7
+ arr[3] = (arr[3] & 0xfff) | 0x4000;
+ // set 2 most significant bits of byte 9 to '10'
+ arr[4] = (arr[4] & 0x3fff) | 0x8000;
+
+ var pad = function(num) {
+ var v = num.toString(16);
+ while (v.length < 4) {
+ v = '0' + v;
+ }
+ return v;
+ };
+
+ return (
+ pad(arr[0]) +
+ pad(arr[1]) +
+ pad(arr[2]) +
+ pad(arr[3]) +
+ pad(arr[4]) +
+ pad(arr[5]) +
+ pad(arr[6]) +
+ pad(arr[7])
+ );
+ } else {
+ // http://stackoverflow.com/questions/105034/how-to-create-a-guid-uuid-in-javascript/2117523#2117523
+ return 'xxxxxxxxxxxx4xxxyxxxxxxxxxxxxxxx'.replace(/[xy]/g, function(c) {
+ var r = (Math.random() * 16) | 0,
+ v = c === 'x' ? r : (r & 0x3) | 0x8;
+ return v.toString(16);
+ });
+ }
+}
+
+/**
+ * Given a child DOM element, returns a query-selector statement describing that
+ * and its ancestors
+ * e.g. [HTMLElement] => body > div > input#foo.btn[name=baz]
+ * @param elem
+ * @returns {string}
+ */
+function htmlTreeAsString(elem) {
+ /* eslint no-extra-parens:0*/
+ var MAX_TRAVERSE_HEIGHT = 5,
+ MAX_OUTPUT_LEN = 80,
+ out = [],
+ height = 0,
+ len = 0,
+ separator = ' > ',
+ sepLength = separator.length,
+ nextStr;
+
+ while (elem && height++ < MAX_TRAVERSE_HEIGHT) {
+ nextStr = htmlElementAsString(elem);
+ // bail out if
+ // - nextStr is the 'html' element
+ // - the length of the string that would be created exceeds MAX_OUTPUT_LEN
+ // (ignore this limit if we are on the first iteration)
+ if (
+ nextStr === 'html' ||
+ (height > 1 && len + out.length * sepLength + nextStr.length >= MAX_OUTPUT_LEN)
+ ) {
+ break;
+ }
+
+ out.push(nextStr);
+
+ len += nextStr.length;
+ elem = elem.parentNode;
+ }
+
+ return out.reverse().join(separator);
+}
+
+/**
+ * Returns a simple, query-selector representation of a DOM element
+ * e.g. [HTMLElement] => input#foo.btn[name=baz]
+ * @param HTMLElement
+ * @returns {string}
+ */
+function htmlElementAsString(elem) {
+ var out = [],
+ className,
+ classes,
+ key,
+ attr,
+ i;
+
+ if (!elem || !elem.tagName) {
+ return '';
+ }
+
+ out.push(elem.tagName.toLowerCase());
+ if (elem.id) {
+ out.push('#' + elem.id);
+ }
+
+ className = elem.className;
+ if (className && isString(className)) {
+ classes = className.split(/\s+/);
+ for (i = 0; i < classes.length; i++) {
+ out.push('.' + classes[i]);
+ }
+ }
+ var attrWhitelist = ['type', 'name', 'title', 'alt'];
+ for (i = 0; i < attrWhitelist.length; i++) {
+ key = attrWhitelist[i];
+ attr = elem.getAttribute(key);
+ if (attr) {
+ out.push('[' + key + '="' + attr + '"]');
+ }
+ }
+ return out.join('');
+}
+
+/**
+ * Returns true if either a OR b is truthy, but not both
+ */
+function isOnlyOneTruthy(a, b) {
+ return !!(!!a ^ !!b);
+}
+
+/**
+ * Returns true if the two input exception interfaces have the same content
+ */
+function isSameException(ex1, ex2) {
+ if (isOnlyOneTruthy(ex1, ex2)) return false;
+
+ ex1 = ex1.values[0];
+ ex2 = ex2.values[0];
+
+ if (ex1.type !== ex2.type || ex1.value !== ex2.value) return false;
+
+ return isSameStacktrace(ex1.stacktrace, ex2.stacktrace);
+}
+
+/**
+ * Returns true if the two input stack trace interfaces have the same content
+ */
+function isSameStacktrace(stack1, stack2) {
+ if (isOnlyOneTruthy(stack1, stack2)) return false;
+
+ var frames1 = stack1.frames;
+ var frames2 = stack2.frames;
+
+ // Exit early if frame count differs
+ if (frames1.length !== frames2.length) return false;
+
+ // Iterate through every frame; bail out if anything differs
+ var a, b;
+ for (var i = 0; i < frames1.length; i++) {
+ a = frames1[i];
+ b = frames2[i];
+ if (
+ a.filename !== b.filename ||
+ a.lineno !== b.lineno ||
+ a.colno !== b.colno ||
+ a['function'] !== b['function']
+ )
+ return false;
+ }
+ return true;
+}
+
+/**
+ * Polyfill a method
+ * @param obj object e.g. `document`
+ * @param name method name present on object e.g. `addEventListener`
+ * @param replacement replacement function
+ * @param track {optional} record instrumentation to an array
+ */
+function fill(obj, name, replacement, track) {
+ var orig = obj[name];
+ obj[name] = replacement(orig);
+ if (track) {
+ track.push([obj, name, orig]);
+ }
+}
+
+module.exports = {
+ isObject: isObject,
+ isError: isError,
+ isErrorEvent: isErrorEvent,
+ isUndefined: isUndefined,
+ isFunction: isFunction,
+ isString: isString,
+ isEmptyObject: isEmptyObject,
+ supportsErrorEvent: supportsErrorEvent,
+ wrappedCallback: wrappedCallback,
+ each: each,
+ objectMerge: objectMerge,
+ truncate: truncate,
+ objectFrozen: objectFrozen,
+ hasKey: hasKey,
+ joinRegExp: joinRegExp,
+ urlencode: urlencode,
+ uuid4: uuid4,
+ htmlTreeAsString: htmlTreeAsString,
+ htmlElementAsString: htmlElementAsString,
+ isSameException: isSameException,
+ isSameStacktrace: isSameStacktrace,
+ parseUrl: parseUrl,
+ fill: fill
+};
+
+
+/***/ }),
+
+/***/ "./node_modules/raven-js/vendor/TraceKit/tracekit.js":
+/*!***********************************************************!*\
+ !*** ./node_modules/raven-js/vendor/TraceKit/tracekit.js ***!
+ \***********************************************************/
+/***/ ((module, __unused_webpack_exports, __webpack_require__) => {
+
+var utils = __webpack_require__(/*! ../../src/utils */ "./node_modules/raven-js/src/utils.js");
+
+/*
+ TraceKit - Cross brower stack traces
+
+ This was originally forked from github.com/occ/TraceKit, but has since been
+ largely re-written and is now maintained as part of raven-js. Tests for
+ this are in test/vendor.
+
+ MIT license
+*/
+
+var TraceKit = {
+ collectWindowErrors: true,
+ debug: false
+};
+
+// This is to be defensive in environments where window does not exist (see https://github.com/getsentry/raven-js/pull/785)
+var _window =
+ typeof window !== 'undefined'
+ ? window
+ : typeof __webpack_require__.g !== 'undefined' ? __webpack_require__.g : typeof self !== 'undefined' ? self : {};
+
+// global reference to slice
+var _slice = [].slice;
+var UNKNOWN_FUNCTION = '?';
+
+// https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Error#Error_types
+var ERROR_TYPES_RE = /^(?:[Uu]ncaught (?:exception: )?)?(?:((?:Eval|Internal|Range|Reference|Syntax|Type|URI|)Error): )?(.*)$/;
+
+function getLocationHref() {
+ if (typeof document === 'undefined' || document.location == null) return '';
+
+ return document.location.href;
+}
+
+/**
+ * TraceKit.report: cross-browser processing of unhandled exceptions
+ *
+ * Syntax:
+ * TraceKit.report.subscribe(function(stackInfo) { ... })
+ * TraceKit.report.unsubscribe(function(stackInfo) { ... })
+ * TraceKit.report(exception)
+ * try { ...code... } catch(ex) { TraceKit.report(ex); }
+ *
+ * Supports:
+ * - Firefox: full stack trace with line numbers, plus column number
+ * on top frame; column number is not guaranteed
+ * - Opera: full stack trace with line and column numbers
+ * - Chrome: full stack trace with line and column numbers
+ * - Safari: line and column number for the top frame only; some frames
+ * may be missing, and column number is not guaranteed
+ * - IE: line and column number for the top frame only; some frames
+ * may be missing, and column number is not guaranteed
+ *
+ * In theory, TraceKit should work on all of the following versions:
+ * - IE5.5+ (only 8.0 tested)
+ * - Firefox 0.9+ (only 3.5+ tested)
+ * - Opera 7+ (only 10.50 tested; versions 9 and earlier may require
+ * Exceptions Have Stacktrace to be enabled in opera:config)
+ * - Safari 3+ (only 4+ tested)
+ * - Chrome 1+ (only 5+ tested)
+ * - Konqueror 3.5+ (untested)
+ *
+ * Requires TraceKit.computeStackTrace.
+ *
+ * Tries to catch all unhandled exceptions and report them to the
+ * subscribed handlers. Please note that TraceKit.report will rethrow the
+ * exception. This is REQUIRED in order to get a useful stack trace in IE.
+ * If the exception does not reach the top of the browser, you will only
+ * get a stack trace from the point where TraceKit.report was called.
+ *
+ * Handlers receive a stackInfo object as described in the
+ * TraceKit.computeStackTrace docs.
+ */
+TraceKit.report = (function reportModuleWrapper() {
+ var handlers = [],
+ lastArgs = null,
+ lastException = null,
+ lastExceptionStack = null;
+
+ /**
+ * Add a crash handler.
+ * @param {Function} handler
+ */
+ function subscribe(handler) {
+ installGlobalHandler();
+ handlers.push(handler);
+ }
+
+ /**
+ * Remove a crash handler.
+ * @param {Function} handler
+ */
+ function unsubscribe(handler) {
+ for (var i = handlers.length - 1; i >= 0; --i) {
+ if (handlers[i] === handler) {
+ handlers.splice(i, 1);
+ }
+ }
+ }
+
+ /**
+ * Remove all crash handlers.
+ */
+ function unsubscribeAll() {
+ uninstallGlobalHandler();
+ handlers = [];
+ }
+
+ /**
+ * Dispatch stack information to all handlers.
+ * @param {Object.} stack
+ */
+ function notifyHandlers(stack, isWindowError) {
+ var exception = null;
+ if (isWindowError && !TraceKit.collectWindowErrors) {
+ return;
+ }
+ for (var i in handlers) {
+ if (handlers.hasOwnProperty(i)) {
+ try {
+ handlers[i].apply(null, [stack].concat(_slice.call(arguments, 2)));
+ } catch (inner) {
+ exception = inner;
+ }
+ }
+ }
+
+ if (exception) {
+ throw exception;
+ }
+ }
+
+ var _oldOnerrorHandler, _onErrorHandlerInstalled;
+
+ /**
+ * Ensures all global unhandled exceptions are recorded.
+ * Supported by Gecko and IE.
+ * @param {string} message Error message.
+ * @param {string} url URL of script that generated the exception.
+ * @param {(number|string)} lineNo The line number at which the error
+ * occurred.
+ * @param {?(number|string)} colNo The column number at which the error
+ * occurred.
+ * @param {?Error} ex The actual Error object.
+ */
+ function traceKitWindowOnError(message, url, lineNo, colNo, ex) {
+ var stack = null;
+
+ if (lastExceptionStack) {
+ TraceKit.computeStackTrace.augmentStackTraceWithInitialElement(
+ lastExceptionStack,
+ url,
+ lineNo,
+ message
+ );
+ processLastException();
+ } else if (ex && utils.isError(ex)) {
+ // non-string `ex` arg; attempt to extract stack trace
+
+ // New chrome and blink send along a real error object
+ // Let's just report that like a normal error.
+ // See: https://mikewest.org/2013/08/debugging-runtime-errors-with-window-onerror
+ stack = TraceKit.computeStackTrace(ex);
+ notifyHandlers(stack, true);
+ } else {
+ var location = {
+ url: url,
+ line: lineNo,
+ column: colNo
+ };
+
+ var name = undefined;
+ var msg = message; // must be new var or will modify original `arguments`
+ var groups;
+ if ({}.toString.call(message) === '[object String]') {
+ var groups = message.match(ERROR_TYPES_RE);
+ if (groups) {
+ name = groups[1];
+ msg = groups[2];
+ }
+ }
+
+ location.func = UNKNOWN_FUNCTION;
+
+ stack = {
+ name: name,
+ message: msg,
+ url: getLocationHref(),
+ stack: [location]
+ };
+ notifyHandlers(stack, true);
+ }
+
+ if (_oldOnerrorHandler) {
+ return _oldOnerrorHandler.apply(this, arguments);
+ }
+
+ return false;
+ }
+
+ function installGlobalHandler() {
+ if (_onErrorHandlerInstalled) {
+ return;
+ }
+ _oldOnerrorHandler = _window.onerror;
+ _window.onerror = traceKitWindowOnError;
+ _onErrorHandlerInstalled = true;
+ }
+
+ function uninstallGlobalHandler() {
+ if (!_onErrorHandlerInstalled) {
+ return;
+ }
+ _window.onerror = _oldOnerrorHandler;
+ _onErrorHandlerInstalled = false;
+ _oldOnerrorHandler = undefined;
+ }
+
+ function processLastException() {
+ var _lastExceptionStack = lastExceptionStack,
+ _lastArgs = lastArgs;
+ lastArgs = null;
+ lastExceptionStack = null;
+ lastException = null;
+ notifyHandlers.apply(null, [_lastExceptionStack, false].concat(_lastArgs));
+ }
+
+ /**
+ * Reports an unhandled Error to TraceKit.
+ * @param {Error} ex
+ * @param {?boolean} rethrow If false, do not re-throw the exception.
+ * Only used for window.onerror to not cause an infinite loop of
+ * rethrowing.
+ */
+ function report(ex, rethrow) {
+ var args = _slice.call(arguments, 1);
+ if (lastExceptionStack) {
+ if (lastException === ex) {
+ return; // already caught by an inner catch block, ignore
+ } else {
+ processLastException();
+ }
+ }
+
+ var stack = TraceKit.computeStackTrace(ex);
+ lastExceptionStack = stack;
+ lastException = ex;
+ lastArgs = args;
+
+ // If the stack trace is incomplete, wait for 2 seconds for
+ // slow slow IE to see if onerror occurs or not before reporting
+ // this exception; otherwise, we will end up with an incomplete
+ // stack trace
+ setTimeout(function() {
+ if (lastException === ex) {
+ processLastException();
+ }
+ }, stack.incomplete ? 2000 : 0);
+
+ if (rethrow !== false) {
+ throw ex; // re-throw to propagate to the top level (and cause window.onerror)
+ }
+ }
+
+ report.subscribe = subscribe;
+ report.unsubscribe = unsubscribe;
+ report.uninstall = unsubscribeAll;
+ return report;
+})();
+
+/**
+ * TraceKit.computeStackTrace: cross-browser stack traces in JavaScript
+ *
+ * Syntax:
+ * s = TraceKit.computeStackTrace(exception) // consider using TraceKit.report instead (see below)
+ * Returns:
+ * s.name - exception name
+ * s.message - exception message
+ * s.stack[i].url - JavaScript or HTML file URL
+ * s.stack[i].func - function name, or empty for anonymous functions (if guessing did not work)
+ * s.stack[i].args - arguments passed to the function, if known
+ * s.stack[i].line - line number, if known
+ * s.stack[i].column - column number, if known
+ *
+ * Supports:
+ * - Firefox: full stack trace with line numbers and unreliable column
+ * number on top frame
+ * - Opera 10: full stack trace with line and column numbers
+ * - Opera 9-: full stack trace with line numbers
+ * - Chrome: full stack trace with line and column numbers
+ * - Safari: line and column number for the topmost stacktrace element
+ * only
+ * - IE: no line numbers whatsoever
+ *
+ * Tries to guess names of anonymous functions by looking for assignments
+ * in the source code. In IE and Safari, we have to guess source file names
+ * by searching for function bodies inside all page scripts. This will not
+ * work for scripts that are loaded cross-domain.
+ * Here be dragons: some function names may be guessed incorrectly, and
+ * duplicate functions may be mismatched.
+ *
+ * TraceKit.computeStackTrace should only be used for tracing purposes.
+ * Logging of unhandled exceptions should be done with TraceKit.report,
+ * which builds on top of TraceKit.computeStackTrace and provides better
+ * IE support by utilizing the window.onerror event to retrieve information
+ * about the top of the stack.
+ *
+ * Note: In IE and Safari, no stack trace is recorded on the Error object,
+ * so computeStackTrace instead walks its *own* chain of callers.
+ * This means that:
+ * * in Safari, some methods may be missing from the stack trace;
+ * * in IE, the topmost function in the stack trace will always be the
+ * caller of computeStackTrace.
+ *
+ * This is okay for tracing (because you are likely to be calling
+ * computeStackTrace from the function you want to be the topmost element
+ * of the stack trace anyway), but not okay for logging unhandled
+ * exceptions (because your catch block will likely be far away from the
+ * inner function that actually caused the exception).
+ *
+ */
+TraceKit.computeStackTrace = (function computeStackTraceWrapper() {
+ // Contents of Exception in various browsers.
+ //
+ // SAFARI:
+ // ex.message = Can't find variable: qq
+ // ex.line = 59
+ // ex.sourceId = 580238192
+ // ex.sourceURL = http://...
+ // ex.expressionBeginOffset = 96
+ // ex.expressionCaretOffset = 98
+ // ex.expressionEndOffset = 98
+ // ex.name = ReferenceError
+ //
+ // FIREFOX:
+ // ex.message = qq is not defined
+ // ex.fileName = http://...
+ // ex.lineNumber = 59
+ // ex.columnNumber = 69
+ // ex.stack = ...stack trace... (see the example below)
+ // ex.name = ReferenceError
+ //
+ // CHROME:
+ // ex.message = qq is not defined
+ // ex.name = ReferenceError
+ // ex.type = not_defined
+ // ex.arguments = ['aa']
+ // ex.stack = ...stack trace...
+ //
+ // INTERNET EXPLORER:
+ // ex.message = ...
+ // ex.name = ReferenceError
+ //
+ // OPERA:
+ // ex.message = ...message... (see the example below)
+ // ex.name = ReferenceError
+ // ex.opera#sourceloc = 11 (pretty much useless, duplicates the info in ex.message)
+ // ex.stacktrace = n/a; see 'opera:config#UserPrefs|Exceptions Have Stacktrace'
+
+ /**
+ * Computes stack trace information from the stack property.
+ * Chrome and Gecko use this property.
+ * @param {Error} ex
+ * @return {?Object.} Stack trace information.
+ */
+ function computeStackTraceFromStackProp(ex) {
+ if (typeof ex.stack === 'undefined' || !ex.stack) return;
+
+ var chrome = /^\s*at (.*?) ?\(((?:file|https?|blob|chrome-extension|native|eval|webpack||[a-z]:|\/).*?)(?::(\d+))?(?::(\d+))?\)?\s*$/i,
+ gecko = /^\s*(.*?)(?:\((.*?)\))?(?:^|@)((?:file|https?|blob|chrome|webpack|resource|\[native).*?|[^@]*bundle)(?::(\d+))?(?::(\d+))?\s*$/i,
+ winjs = /^\s*at (?:((?:\[object object\])?.+) )?\(?((?:file|ms-appx|https?|webpack|blob):.*?):(\d+)(?::(\d+))?\)?\s*$/i,
+ // Used to additionally parse URL/line/column from eval frames
+ geckoEval = /(\S+) line (\d+)(?: > eval line \d+)* > eval/i,
+ chromeEval = /\((\S*)(?::(\d+))(?::(\d+))\)/,
+ lines = ex.stack.split('\n'),
+ stack = [],
+ submatch,
+ parts,
+ element,
+ reference = /^(.*) is undefined$/.exec(ex.message);
+
+ for (var i = 0, j = lines.length; i < j; ++i) {
+ if ((parts = chrome.exec(lines[i]))) {
+ var isNative = parts[2] && parts[2].indexOf('native') === 0; // start of line
+ var isEval = parts[2] && parts[2].indexOf('eval') === 0; // start of line
+ if (isEval && (submatch = chromeEval.exec(parts[2]))) {
+ // throw out eval line/column and use top-most line/column number
+ parts[2] = submatch[1]; // url
+ parts[3] = submatch[2]; // line
+ parts[4] = submatch[3]; // column
+ }
+ element = {
+ url: !isNative ? parts[2] : null,
+ func: parts[1] || UNKNOWN_FUNCTION,
+ args: isNative ? [parts[2]] : [],
+ line: parts[3] ? +parts[3] : null,
+ column: parts[4] ? +parts[4] : null
+ };
+ } else if ((parts = winjs.exec(lines[i]))) {
+ element = {
+ url: parts[2],
+ func: parts[1] || UNKNOWN_FUNCTION,
+ args: [],
+ line: +parts[3],
+ column: parts[4] ? +parts[4] : null
+ };
+ } else if ((parts = gecko.exec(lines[i]))) {
+ var isEval = parts[3] && parts[3].indexOf(' > eval') > -1;
+ if (isEval && (submatch = geckoEval.exec(parts[3]))) {
+ // throw out eval line/column and use top-most line number
+ parts[3] = submatch[1];
+ parts[4] = submatch[2];
+ parts[5] = null; // no column when eval
+ } else if (i === 0 && !parts[5] && typeof ex.columnNumber !== 'undefined') {
+ // FireFox uses this awesome columnNumber property for its top frame
+ // Also note, Firefox's column number is 0-based and everything else expects 1-based,
+ // so adding 1
+ // NOTE: this hack doesn't work if top-most frame is eval
+ stack[0].column = ex.columnNumber + 1;
+ }
+ element = {
+ url: parts[3],
+ func: parts[1] || UNKNOWN_FUNCTION,
+ args: parts[2] ? parts[2].split(',') : [],
+ line: parts[4] ? +parts[4] : null,
+ column: parts[5] ? +parts[5] : null
+ };
+ } else {
+ continue;
+ }
+
+ if (!element.func && element.line) {
+ element.func = UNKNOWN_FUNCTION;
+ }
+
+ stack.push(element);
+ }
+
+ if (!stack.length) {
+ return null;
+ }
+
+ return {
+ name: ex.name,
+ message: ex.message,
+ url: getLocationHref(),
+ stack: stack
+ };
+ }
+
+ /**
+ * Adds information about the first frame to incomplete stack traces.
+ * Safari and IE require this to get complete data on the first frame.
+ * @param {Object.} stackInfo Stack trace information from
+ * one of the compute* methods.
+ * @param {string} url The URL of the script that caused an error.
+ * @param {(number|string)} lineNo The line number of the script that
+ * caused an error.
+ * @param {string=} message The error generated by the browser, which
+ * hopefully contains the name of the object that caused the error.
+ * @return {boolean} Whether or not the stack information was
+ * augmented.
+ */
+ function augmentStackTraceWithInitialElement(stackInfo, url, lineNo, message) {
+ var initial = {
+ url: url,
+ line: lineNo
+ };
+
+ if (initial.url && initial.line) {
+ stackInfo.incomplete = false;
+
+ if (!initial.func) {
+ initial.func = UNKNOWN_FUNCTION;
+ }
+
+ if (stackInfo.stack.length > 0) {
+ if (stackInfo.stack[0].url === initial.url) {
+ if (stackInfo.stack[0].line === initial.line) {
+ return false; // already in stack trace
+ } else if (
+ !stackInfo.stack[0].line &&
+ stackInfo.stack[0].func === initial.func
+ ) {
+ stackInfo.stack[0].line = initial.line;
+ return false;
+ }
+ }
+ }
+
+ stackInfo.stack.unshift(initial);
+ stackInfo.partial = true;
+ return true;
+ } else {
+ stackInfo.incomplete = true;
+ }
+
+ return false;
+ }
+
+ /**
+ * Computes stack trace information by walking the arguments.caller
+ * chain at the time the exception occurred. This will cause earlier
+ * frames to be missed but is the only way to get any stack trace in
+ * Safari and IE. The top frame is restored by
+ * {@link augmentStackTraceWithInitialElement}.
+ * @param {Error} ex
+ * @return {?Object.} Stack trace information.
+ */
+ function computeStackTraceByWalkingCallerChain(ex, depth) {
+ var functionName = /function\s+([_$a-zA-Z\xA0-\uFFFF][_$a-zA-Z0-9\xA0-\uFFFF]*)?\s*\(/i,
+ stack = [],
+ funcs = {},
+ recursion = false,
+ parts,
+ item,
+ source;
+
+ for (
+ var curr = computeStackTraceByWalkingCallerChain.caller;
+ curr && !recursion;
+ curr = curr.caller
+ ) {
+ if (curr === computeStackTrace || curr === TraceKit.report) {
+ // console.log('skipping internal function');
+ continue;
+ }
+
+ item = {
+ url: null,
+ func: UNKNOWN_FUNCTION,
+ line: null,
+ column: null
+ };
+
+ if (curr.name) {
+ item.func = curr.name;
+ } else if ((parts = functionName.exec(curr.toString()))) {
+ item.func = parts[1];
+ }
+
+ if (typeof item.func === 'undefined') {
+ try {
+ item.func = parts.input.substring(0, parts.input.indexOf('{'));
+ } catch (e) {}
+ }
+
+ if (funcs['' + curr]) {
+ recursion = true;
+ } else {
+ funcs['' + curr] = true;
+ }
+
+ stack.push(item);
+ }
+
+ if (depth) {
+ // console.log('depth is ' + depth);
+ // console.log('stack is ' + stack.length);
+ stack.splice(0, depth);
+ }
+
+ var result = {
+ name: ex.name,
+ message: ex.message,
+ url: getLocationHref(),
+ stack: stack
+ };
+ augmentStackTraceWithInitialElement(
+ result,
+ ex.sourceURL || ex.fileName,
+ ex.line || ex.lineNumber,
+ ex.message || ex.description
+ );
+ return result;
+ }
+
+ /**
+ * Computes a stack trace for an exception.
+ * @param {Error} ex
+ * @param {(string|number)=} depth
+ */
+ function computeStackTrace(ex, depth) {
+ var stack = null;
+ depth = depth == null ? 0 : +depth;
+
+ try {
+ stack = computeStackTraceFromStackProp(ex);
+ if (stack) {
+ return stack;
+ }
+ } catch (e) {
+ if (TraceKit.debug) {
+ throw e;
+ }
+ }
+
+ try {
+ stack = computeStackTraceByWalkingCallerChain(ex, depth + 1);
+ if (stack) {
+ return stack;
+ }
+ } catch (e) {
+ if (TraceKit.debug) {
+ throw e;
+ }
+ }
+ return {
+ name: ex.name,
+ message: ex.message,
+ url: getLocationHref()
+ };
+ }
+
+ computeStackTrace.augmentStackTraceWithInitialElement = augmentStackTraceWithInitialElement;
+ computeStackTrace.computeStackTraceFromStackProp = computeStackTraceFromStackProp;
+
+ return computeStackTrace;
+})();
+
+module.exports = TraceKit;
+
+
+/***/ }),
+
+/***/ "./node_modules/raven-js/vendor/json-stringify-safe/stringify.js":
+/*!***********************************************************************!*\
+ !*** ./node_modules/raven-js/vendor/json-stringify-safe/stringify.js ***!
+ \***********************************************************************/
+/***/ ((module, exports) => {
+
+/*
+ json-stringify-safe
+ Like JSON.stringify, but doesn't throw on circular references.
+
+ Originally forked from https://github.com/isaacs/json-stringify-safe
+ version 5.0.1 on 3/8/2017 and modified to handle Errors serialization
+ and IE8 compatibility. Tests for this are in test/vendor.
+
+ ISC license: https://github.com/isaacs/json-stringify-safe/blob/master/LICENSE
+*/
+
+exports = module.exports = stringify;
+exports.getSerialize = serializer;
+
+function indexOf(haystack, needle) {
+ for (var i = 0; i < haystack.length; ++i) {
+ if (haystack[i] === needle) return i;
+ }
+ return -1;
+}
+
+function stringify(obj, replacer, spaces, cycleReplacer) {
+ return JSON.stringify(obj, serializer(replacer, cycleReplacer), spaces);
+}
+
+// https://github.com/ftlabs/js-abbreviate/blob/fa709e5f139e7770a71827b1893f22418097fbda/index.js#L95-L106
+function stringifyError(value) {
+ var err = {
+ // These properties are implemented as magical getters and don't show up in for in
+ stack: value.stack,
+ message: value.message,
+ name: value.name
+ };
+
+ for (var i in value) {
+ if (Object.prototype.hasOwnProperty.call(value, i)) {
+ err[i] = value[i];
+ }
+ }
+
+ return err;
+}
+
+function serializer(replacer, cycleReplacer) {
+ var stack = [];
+ var keys = [];
+
+ if (cycleReplacer == null) {
+ cycleReplacer = function(key, value) {
+ if (stack[0] === value) {
+ return '[Circular ~]';
+ }
+ return '[Circular ~.' + keys.slice(0, indexOf(stack, value)).join('.') + ']';
+ };
+ }
+
+ return function(key, value) {
+ if (stack.length > 0) {
+ var thisPos = indexOf(stack, this);
+ ~thisPos ? stack.splice(thisPos + 1) : stack.push(this);
+ ~thisPos ? keys.splice(thisPos, Infinity, key) : keys.push(key);
+
+ if (~indexOf(stack, value)) {
+ value = cycleReplacer.call(this, key, value);
+ }
+ } else {
+ stack.push(value);
+ }
+
+ return replacer == null
+ ? value instanceof Error ? stringifyError(value) : value
+ : replacer.call(this, key, value);
+ };
+}
+
+
+/***/ }),
+
+/***/ "jquery":
+/*!*************************!*\
+ !*** external "jQuery" ***!
+ \*************************/
+/***/ ((module) => {
+
+"use strict";
+module.exports = window["jQuery"];
+
+/***/ })
+
+/******/ });
+/************************************************************************/
+/******/ // The module cache
+/******/ var __webpack_module_cache__ = {};
+/******/
+/******/ // The require function
+/******/ function __webpack_require__(moduleId) {
+/******/ // Check if module is in cache
+/******/ var cachedModule = __webpack_module_cache__[moduleId];
+/******/ if (cachedModule !== undefined) {
+/******/ return cachedModule.exports;
+/******/ }
+/******/ // Create a new module (and put it into the cache)
+/******/ var module = __webpack_module_cache__[moduleId] = {
+/******/ // no module.id needed
+/******/ // no module.loaded needed
+/******/ exports: {}
+/******/ };
+/******/
+/******/ // Execute the module function
+/******/ __webpack_modules__[moduleId](module, module.exports, __webpack_require__);
+/******/
+/******/ // Return the exports of the module
+/******/ return module.exports;
+/******/ }
+/******/
+/************************************************************************/
+/******/ /* webpack/runtime/compat get default export */
+/******/ (() => {
+/******/ // getDefaultExport function for compatibility with non-harmony modules
+/******/ __webpack_require__.n = (module) => {
+/******/ var getter = module && module.__esModule ?
+/******/ () => (module['default']) :
+/******/ () => (module);
+/******/ __webpack_require__.d(getter, { a: getter });
+/******/ return getter;
+/******/ };
+/******/ })();
+/******/
+/******/ /* webpack/runtime/define property getters */
+/******/ (() => {
+/******/ // define getter functions for harmony exports
+/******/ __webpack_require__.d = (exports, definition) => {
+/******/ for(var key in definition) {
+/******/ if(__webpack_require__.o(definition, key) && !__webpack_require__.o(exports, key)) {
+/******/ Object.defineProperty(exports, key, { enumerable: true, get: definition[key] });
+/******/ }
+/******/ }
+/******/ };
+/******/ })();
+/******/
+/******/ /* webpack/runtime/global */
+/******/ (() => {
+/******/ __webpack_require__.g = (function() {
+/******/ if (typeof globalThis === 'object') return globalThis;
+/******/ try {
+/******/ return this || new Function('return this')();
+/******/ } catch (e) {
+/******/ if (typeof window === 'object') return window;
+/******/ }
+/******/ })();
+/******/ })();
+/******/
+/******/ /* webpack/runtime/hasOwnProperty shorthand */
+/******/ (() => {
+/******/ __webpack_require__.o = (obj, prop) => (Object.prototype.hasOwnProperty.call(obj, prop))
+/******/ })();
+/******/
+/******/ /* webpack/runtime/make namespace object */
+/******/ (() => {
+/******/ // define __esModule on exports
+/******/ __webpack_require__.r = (exports) => {
+/******/ if(typeof Symbol !== 'undefined' && Symbol.toStringTag) {
+/******/ Object.defineProperty(exports, Symbol.toStringTag, { value: 'Module' });
+/******/ }
+/******/ Object.defineProperty(exports, '__esModule', { value: true });
+/******/ };
+/******/ })();
+/******/
+/************************************************************************/
+var __webpack_exports__ = {};
+// This entry need to be wrapped in an IIFE because it need to be in strict mode.
+(() => {
+"use strict";
+/*!*************************************!*\
+ !*** ./scripts/entries/feedback.ts ***!
+ \*************************************/
+__webpack_require__.r(__webpack_exports__);
+/* harmony import */ var jquery__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! jquery */ "jquery");
+/* harmony import */ var jquery__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(jquery__WEBPACK_IMPORTED_MODULE_0__);
+/* harmony import */ var _lib_Raven__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! ../lib/Raven */ "./scripts/lib/Raven.ts");
+/* harmony import */ var _constants_selectors__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ../constants/selectors */ "./scripts/constants/selectors.ts");
+/* harmony import */ var _feedback_ThickBoxModal__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ../feedback/ThickBoxModal */ "./scripts/feedback/ThickBoxModal.ts");
+/* harmony import */ var _feedback_feedbackFormApi__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__(/*! ../feedback/feedbackFormApi */ "./scripts/feedback/feedbackFormApi.ts");
+/* harmony import */ var _utils_backgroundAppUtils__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__(/*! ../utils/backgroundAppUtils */ "./scripts/utils/backgroundAppUtils.ts");
+/* harmony import */ var _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_6__ = __webpack_require__(/*! ../constants/leadinConfig */ "./scripts/constants/leadinConfig.ts");
+/* harmony import */ var _iframe_integratedMessages__WEBPACK_IMPORTED_MODULE_7__ = __webpack_require__(/*! ../iframe/integratedMessages */ "./scripts/iframe/integratedMessages/index.ts");
+
+
+
+
+
+
+
+
+
+function deactivatePlugin() {
+ var href = jquery__WEBPACK_IMPORTED_MODULE_0___default()(_constants_selectors__WEBPACK_IMPORTED_MODULE_2__.domElements.deactivatePluginButton).attr('href');
+
+ if (href) {
+ window.location.href = href;
+ }
+}
+
+function setLoadingState() {
+ jquery__WEBPACK_IMPORTED_MODULE_0___default()(_constants_selectors__WEBPACK_IMPORTED_MODULE_2__.domElements.deactivateFeedbackSubmit).addClass('loading');
+}
+
+function submitAndDeactivate(e) {
+ e.preventDefault();
+ setLoadingState();
+ var feedback = jquery__WEBPACK_IMPORTED_MODULE_0___default()(_constants_selectors__WEBPACK_IMPORTED_MODULE_2__.domElements.deactivateFeedbackForm).serializeArray().find(function (field) {
+ return field.name === 'feedback';
+ });
+ (0,_feedback_feedbackFormApi__WEBPACK_IMPORTED_MODULE_4__.submitFeedbackForm)(_constants_selectors__WEBPACK_IMPORTED_MODULE_2__.domElements.deactivateFeedbackForm).then(function () {
+ if (feedback && _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_6__.refreshToken) {
+ var embedder = (0,_utils_backgroundAppUtils__WEBPACK_IMPORTED_MODULE_5__.getOrCreateBackgroundApp)(_constants_leadinConfig__WEBPACK_IMPORTED_MODULE_6__.refreshToken);
+ embedder.postMessage({
+ key: _iframe_integratedMessages__WEBPACK_IMPORTED_MODULE_7__.ProxyMessages.TrackPluginDeactivation,
+ payload: {
+ type: feedback.value.trim().replace(/[\s']+/g, '_')
+ }
+ });
+ }
+ })["catch"](function (err) {
+ _lib_Raven__WEBPACK_IMPORTED_MODULE_1__["default"].captureException(err);
+ })["finally"](function () {
+ deactivatePlugin();
+ });
+}
+
+function init() {
+ // eslint-disable-next-line no-new
+ new _feedback_ThickBoxModal__WEBPACK_IMPORTED_MODULE_3__["default"](_constants_selectors__WEBPACK_IMPORTED_MODULE_2__.domElements.deactivatePluginButton, 'leadin-feedback-container', 'leadin-feedback-window', 'leadin-feedback-content');
+ jquery__WEBPACK_IMPORTED_MODULE_0___default()(_constants_selectors__WEBPACK_IMPORTED_MODULE_2__.domElements.deactivateFeedbackForm).off('submit').on('submit', submitAndDeactivate);
+ jquery__WEBPACK_IMPORTED_MODULE_0___default()(_constants_selectors__WEBPACK_IMPORTED_MODULE_2__.domElements.deactivateFeedbackSkip).off('click').on('click', deactivatePlugin);
+}
+
+(0,_utils_backgroundAppUtils__WEBPACK_IMPORTED_MODULE_5__.initBackgroundApp)(init);
+})();
+
+/******/ })()
+;
+//# sourceMappingURL=feedback.js.map
\ No newline at end of file
diff --git a/wp/wp-content/plugins/leadin/build/feedback.js.map b/wp/wp-content/plugins/leadin/build/feedback.js.map
new file mode 100644
index 00000000..b2e12d56
--- /dev/null
+++ b/wp/wp-content/plugins/leadin/build/feedback.js.map
@@ -0,0 +1 @@
+{"version":3,"file":"feedback.js","mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AAAA,2BAA6iBA,MAAM,CAACC,YAApjB;AAAA,IAAQC,WAAR,wBAAQA,WAAR;AAAA,IAAqBC,QAArB,wBAAqBA,QAArB;AAAA,IAA+BC,cAA/B,wBAA+BA,cAA/B;AAAA,IAA+CC,gBAA/C,wBAA+CA,gBAA/C;AAAA,IAAiEC,QAAjE,wBAAiEA,QAAjE;AAAA,IAA2EC,aAA3E,wBAA2EA,aAA3E;AAAA,IAA0FC,GAA1F,wBAA0FA,GAA1F;AAAA,IAA+FC,WAA/F,wBAA+FA,WAA/F;AAAA,IAA4GC,cAA5G,wBAA4GA,cAA5G;AAAA,IAA4HC,kBAA5H,wBAA4HA,kBAA5H;AAAA,IAAgJC,MAAhJ,wBAAgJA,MAAhJ;AAAA,IAAwJC,cAAxJ,wBAAwJA,cAAxJ;AAAA,IAAwKC,YAAxK,wBAAwKA,YAAxK;AAAA,IAAsLC,SAAtL,wBAAsLA,SAAtL;AAAA,IAAiMC,UAAjM,wBAAiMA,UAAjM;AAAA,IAA6MC,iBAA7M,wBAA6MA,iBAA7M;AAAA,IAAgOC,mBAAhO,wBAAgOA,mBAAhO;AAAA,IAAqPC,kBAArP,wBAAqPA,kBAArP;AAAA,IAAyQC,mBAAzQ,wBAAyQA,mBAAzQ;AAAA,IAA8RC,iBAA9R,wBAA8RA,iBAA9R;AAAA,IAAiTC,MAAjT,wBAAiTA,MAAjT;AAAA,IAAyTC,QAAzT,wBAAyTA,QAAzT;AAAA,IAAmUC,UAAnU,wBAAmUA,UAAnU;AAAA,IAA+UC,UAA/U,wBAA+UA,UAA/U;AAAA,IAA2VC,OAA3V,wBAA2VA,OAA3V;AAAA,IAAoWC,YAApW,wBAAoWA,YAApW;AAAA,IAAkXC,WAAlX,wBAAkXA,WAAlX;AAAA,IAA+XC,QAA/X,wBAA+XA,QAA/X;AAAA,IAAyYC,aAAzY,wBAAyYA,aAAzY;AAAA,IAAwZC,SAAxZ,wBAAwZA,SAAxZ;AAAA,IAAmaC,OAAna,wBAAmaA,OAAna;AAAA,IAA4aC,YAA5a,wBAA4aA,YAA5a;AAAA,IAA0bC,iBAA1b,wBAA0bA,iBAA1b;AAAA,IAA6cC,KAA7c,wBAA6cA,KAA7c;AAAA,IAAodC,YAApd,wBAAodA,YAApd;AAAA,IAAkeC,SAAle,wBAAkeA,SAAle;AAAA,IAA6eC,YAA7e,wBAA6eA,YAA7e;AAAA,IAA2fC,yBAA3f,wBAA2fA,yBAA3f;AAAA,IAAshBC,iBAAthB,wBAAshBA,iBAAthB;;;;;;;;;;;;;;;;ACAO,IAAMC,WAAW,GAAG;EACvBC,MAAM,EAAE,gBADe;EAEvBC,OAAO,EAAE,4BAFc;EAGvBC,YAAY,EAAE,8BAHS;EAIvBC,cAAc,EAAE,iCAJO;EAKvBC,sBAAsB,EAAE,oCALD;EAMvBC,sBAAsB,EAAE,6BAND;EAOvBC,wBAAwB,EAAE,+BAPH;EAQvBC,sBAAsB,EAAE,6BARD;EASvBC,kBAAkB,EAAE,qBATG;EAUvBC,mBAAmB,EAAE,gCAVE;EAWvBC,oBAAoB,EAAE,6BAXC;EAYvBC,qBAAqB,EAAE,uBAZA;EAavBC,2BAA2B,EAAE,uBAbN;EAcvBC,yBAAyB,EAAE,gCAdJ;EAevBC,qBAAqB,EAAE,yBAfA;EAgBvBC,YAAY,EAAE,eAhBS;EAiBvBC,6BAA6B,EAAE;AAjBR,CAApB;;;;;;;;;;;;;;;;;;;;;;;;;;ACAP;AACA;;IACqBE;EAKjB,uBAAYC,mBAAZ,EAAiCC,eAAjC,EAAkDC,cAAlD,EAAkEC,eAAlE,EAAmF;IAAA;;IAAA;;IAAA;;IAAA;;IAAA;;IAC/E,KAAKH,mBAAL,GAA2BA,mBAA3B;IACA,KAAKC,eAAL,GAAuBA,eAAvB;IACA,KAAKC,cAAL,GAAsBA,cAAtB;IACA,KAAKC,eAAL,GAAuBA,eAAvB;IACAL,6CAAC,CAACE,mBAAD,CAAD,CAAuBI,EAAvB,CAA0B,OAA1B,EAAmC,KAAKC,IAAL,CAAUC,IAAV,CAAe,IAAf,CAAnC;EACH;;;;WACD,iBAAQ;MACJ;MACAnE,MAAM,CAACoE,SAAP;IACH;;;WACD,cAAKC,CAAL,EAAQ;MACJ;MACArE,MAAM,CAACsE,OAAP,CAAe,EAAf,gCAA0C,KAAKR,eAA/C,kBAFI,CAGJ;MACA;;MACAH,6CAAC,CAAClB,iFAAD,CAAD,CAAmC8B,QAAnC,CAA4C,KAAKR,cAAjD,EALI,CAMJ;;MACAJ,6CAAC,CAAClB,kFAAD,CAAD,CAAoC8B,QAApC,CAA6C,KAAKP,eAAlD,EAPI,CAQJ;MACA;;MACAL,6CAAC,CAAClB,gFAAD,CAAD,CACK+B,GADL,CACS,OADT,EAEKP,EAFL,CAEQ,OAFR,EAEiB,KAAKQ,KAFtB;MAGAJ,CAAC,CAACK,cAAF;IACH;;;;;;;;;;;;;;;;;;;;;;;AChCL;AACA,IAAM7C,QAAQ,GAAG,SAAjB;AACA,IAAM8C,MAAM,GAAG,sCAAf;AACA,IAAMC,iBAAiB,uEAAgE/C,QAAhE,cAA4E8C,MAA5E,CAAvB;AACO,SAASE,kBAAT,CAA4BC,YAA5B,EAA0C;EAC7C,IAAMC,qBAAqB,GAAG;IAC1BC,MAAM,EAAErB,6CAAC,CAACmB,YAAD,CAAD,CAAgBG,cAAhB,EADkB;IAE1BC,cAAc,EAAE;EAFU,CAA9B;EAIA,OAAO,IAAIC,OAAJ,CAAY,UAACC,OAAD,EAAUC,MAAV,EAAqB;IACpC1B,kDAAA,CAAO;MACH4B,IAAI,EAAE,MADH;MAEHC,GAAG,EAAEZ,iBAFF;MAGHa,WAAW,EAAE,kBAHV;MAIHC,IAAI,EAAEC,IAAI,CAACC,SAAL,CAAeb,qBAAf,CAJH;MAKHc,OAAO,EAAET,OALN;MAMHU,KAAK,EAAET;IANJ,CAAP;EAQH,CATM,CAAP;AAUH;;;;;;;;;;;;;;;ACnBM,IAAMU,YAAY,GAAG;EACxBC,gBAAgB,EAAE,4CADM;EAExBC,gBAAgB,EAAE,4CAFM;EAGxBC,iBAAiB,EAAE,6CAHK;EAIxBC,mBAAmB,EAAE,+CAJG;EAKxBC,UAAU,EAAE,qCALY;EAMxBC,YAAY,EAAE;AANU,CAArB;;;;;;;;;;;;;;;ACAA,IAAMC,YAAY,GAAG;EACxBC,uBAAuB,EAAE;AADD,CAArB;;;;;;;;;;;;;;;;;;;;;;;;ACAP;AACA;AACA;AACA;;;;;;;;;;;;;;;;ACHO,IAAMC,gBAAgB,GAAG;EAC5BC,2BAA2B,EAAE;AADD,CAAzB;;;;;;;;;;;;;;;ACAA,IAAMC,cAAc,GAAG;EAC1BC,wBAAwB,EAAE,4BADA;EAE1BC,kBAAkB,EAAE,sBAFM;EAG1BC,YAAY,EAAE,uCAHY;EAI1BC,4BAA4B,EAAE,mCAJJ;EAK1BC,6BAA6B,EAAE,oCALL;EAM1BC,0BAA0B,EAAE,iCANF;EAO1BC,6BAA6B,EAAE,oCAPL;EAQ1BC,2BAA2B,EAAE,kCARH;EAS1BC,wBAAwB,EAAE,6BATA;EAU1BC,yBAAyB,EAAE,oCAVD;EAW1BC,sBAAsB,EAAE,iCAXE;EAY1BC,yBAAyB,EAAE,8BAZD;EAa1BC,uBAAuB,EAAE,4BAbC;EAc1BC,iBAAiB,EAAE,qBAdO;EAe1BC,kBAAkB,EAAE,sBAfM;EAgB1BC,eAAe,EAAE,mBAhBS;EAiB1BC,sBAAsB,EAAE,2BAjBE;EAkB1BC,0BAA0B,EAAE,+BAlBF;EAmB1BC,2BAA2B,EAAE,gCAnBH;EAoB1BC,wBAAwB,EAAE,6BApBA;EAqB1BC,6BAA6B,EAAE,kCArBL;EAsB1BC,8BAA8B,EAAE,mCAtBN;EAuB1BC,2BAA2B,EAAE;AAvBH,CAAvB;;;;;;;;;;;;;;;ACAA,IAAMC,aAAa,GAAG;EACzBC,UAAU,EAAE,aADa;EAEzBC,SAAS,EAAE,YAFc;EAGzBC,sBAAsB,EAAE,2BAHC;EAIzBC,SAAS,EAAE,YAJc;EAKzBC,qBAAqB,EAAE,0BALE;EAMzBC,kCAAkC,EAAE,yCANX;EAOzBC,wBAAwB,EAAE,8BAPD;EAQzBC,uBAAuB,EAAE,2BARA;EASzBC,sBAAsB,EAAE,2BATC;EAUzBC,4BAA4B,EAAE,kCAVL;EAWzBC,uBAAuB,EAAE,4BAXA;EAYzBC,yBAAyB,EAAE,8BAZF;EAazBC,sBAAsB,EAAE,2BAbC;EAczBC,uBAAuB,EAAE,4BAdA;EAezBC,4BAA4B,EAAE,iCAfL;EAgBzBC,0BAA0B,EAAE,+BAhBH;EAiBzBC,uBAAuB,EAAE;AAjBA,CAAtB;;;;;;;;;;;;;;;;;;;ACAP;AACA;AACO,SAASE,cAAT,GAA0B;EAC7B,IAAIxI,2EAAA,CAAuB,iBAAvB,MAA8C,CAAC,CAAnD,EAAsD;IAClD;EACH;;EACDuI,sDAAA,CAAa,mEAAb,EAAkF;IAC9EI,UAAU,EAAE;MACRC,QAAQ,EAAE;IADF,CADkE;IAI9EC,OAAO,EAAEtI,wEAAmBA;EAJkD,CAAlF,EAKGuI,OALH;EAMAP,8DAAA,CAAqB;IACjBS,CAAC,EAAEzI,wEADc;IAEjB0I,GAAG,EAAEtI,+DAFY;IAGjBuI,SAAS,EAAE1H,8DAASA;EAHH,CAArB;EAKA+G,+DAAA,CAAsB;IAClBa,GAAG,EAAEpI,6DADa;IAElBH,OAAO,EAAEwI,MAAM,CAACC,IAAP,CAAYzI,4DAAZ,EACJ0I,GADI,CACA,UAAAC,IAAI;MAAA,iBAAOA,IAAP,cAAe3I,4DAAO,CAAC2I,IAAD,CAAtB;IAAA,CADJ,EAEJC,IAFI,CAEC,GAFD;EAFS,CAAtB;AAMH;AACD,iEAAelB,iDAAf;;;;;;;;;;;;;;;;;;;ACxBA;AACA;AACO,SAASmB,OAAT,CAAiBC,MAAjB,EAAyB;EAC5BnB,0DAAc;EACdD,0DAAA,CAAcoB,MAAd;AACH;AACM,SAASE,cAAT,CAAwBF,MAAxB,EAAgC;EACnC,SAASG,IAAT,GAAgB;IACZhH,6CAAC,CAAC6G,MAAD,CAAD;EACH;;EACDD,OAAO,CAACI,IAAD,CAAP;AACH;;;;;;;;;;;;;;;;;;ACXD;AACA;AACO,SAASC,iBAAT,CAA2BJ,MAA3B,EAAmC;EACtC,SAASG,IAAT,GAAgB;IACZ,IAAIE,KAAK,CAACC,OAAN,CAAcN,MAAd,CAAJ,EAA2B;MACvBA,MAAM,CAACO,OAAP,CAAe,UAAAC,QAAQ;QAAA,OAAIA,QAAQ,EAAZ;MAAA,CAAvB;IACH,CAFD,MAGK;MACDR,MAAM;IACT;EACJ;;EACDD,kDAAO,CAACI,IAAD,CAAP;AACH;AACM,IAAMM,wBAAwB,GAAG,SAA3BA,wBAA2B,CAAChJ,YAAD,EAAkB;EACtD,IAAIjC,MAAM,CAACkL,mBAAX,EAAgC;IAC5B,OAAOlL,MAAM,CAACkL,mBAAd;EACH;;EACD,cAAwDlL,MAAxD;EAAA,IAAQmL,qBAAR,WAAQA,qBAAR;EAAA,IAA+BC,oBAA/B,WAA+BA,oBAA/B;EACA,IAAMC,OAAO,GAAG,IAAID,oBAAJ,GACXE,SADW,CACDhK,2DADC,EAEXiK,WAFW,CAECjL,6DAFD,EAGXkL,eAHW,CAGKvJ,YAHL,CAAhB;EAIA,IAAMwJ,QAAQ,GAAG,IAAIN,qBAAJ,CAA0B,yBAA1B,EAAqDtJ,6DAArD,EAA+DhB,mEAA/D,EAA+E,YAAM,CAAG,CAAxF,EAA0F6K,UAA1F,CAAqGL,OAArG,CAAjB;EACAI,QAAQ,CAACE,QAAT,CAAkBC,QAAQ,CAACC,IAA3B,EAAiC,KAAjC;EACAJ,QAAQ,CAACK,mBAAT,GAXsD,CAWtB;;EAChC9L,MAAM,CAACkL,mBAAP,GAA6BO,QAA7B;EACA,OAAOzL,MAAM,CAACkL,mBAAd;AACH,CAdM;;;;;;;;;;ACbP;AACA;AACA;AACA;AACA;AACA;;AAEA;;;;;;;;;;;ACPA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;;AAEA;AACA;;AAEA;AACA,gBAAgB,+CAA+C;;AAE/D;AACA;AACA;AACA;AACA;AACA;AACA;AACA,MAAM;AACN;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;;;;;;;;;;;ACtCA;;AAEA,eAAe,mBAAO,CAAC,wFAA6B;AACpD,gBAAgB,mBAAO,CAAC,gHAAyC;AACjE,uBAAuB,mBAAO,CAAC,iEAAe;;AAE9C,YAAY,mBAAO,CAAC,qDAAS;AAC7B;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA,wBAAwB,2FAA+B;;AAEvD;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA,aAAa,qBAAM,mBAAmB,qBAAM;AAC5C;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA,UAAU;AACV;;AAEA;AACA;AACA;AACA;AACA;AACA;;AAEA;;AAEA;;AAEA;AACA;AACA;AACA,eAAe,QAAQ;AACvB,eAAe,QAAQ;AACvB,gBAAgB;AAChB;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA,UAAU;AACV;AACA;AACA,OAAO;AACP;;AAEA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,OAAO;;AAEP;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA,UAAU;AACV;AACA,MAAM;AACN;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA,UAAU;AACV;AACA,MAAM;AACN;AACA;AACA;;AAEA;;AAEA;AACA;AACA,GAAG;;AAEH;AACA;AACA;AACA;AACA;AACA;AACA,gBAAgB;AAChB;AACA;AACA;AACA;AACA;AACA;AACA,OAAO;AACP;AACA;AACA;;AAEA;;AAEA;AACA;;AAEA;AACA;;AAEA;AACA;AACA,GAAG;;AAEH;AACA;AACA;AACA,eAAe,QAAQ;AACvB;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;;AAEA;AACA;;AAEA;AACA;AACA;AACA,GAAG;;AAEH;AACA;AACA;AACA;AACA,eAAe,QAAQ;AACvB,eAAe,UAAU;AACzB,eAAe,OAAO;AACtB;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA,GAAG;;AAEH;AACA;AACA;AACA,eAAe,QAAQ;AACvB,eAAe,UAAU;AACzB,eAAe,UAAU;AACzB,gBAAgB,UAAU;AAC1B;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA,MAAM;AACN;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA,QAAQ;AACR;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA,GAAG;;AAEH;AACA;AACA;AACA,gBAAgB;AAChB;AACA;AACA;;AAEA;;AAEA;AACA;;AAEA;AACA,GAAG;;AAEH;AACA;AACA;AACA,eAAe,OAAO;AACtB,eAAe,QAAQ;AACvB,gBAAgB;AAChB;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,WAAW;AACX;AACA;AACA;AACA;;AAEA;AACA;;AAEA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,MAAM;AACN;AACA;AACA;AACA;;AAEA;AACA,GAAG;;AAEH;AACA;AACA;AACA,eAAe,QAAQ;AACvB,eAAe,QAAQ;AACvB,gBAAgB;AAChB;AACA;AACA;AACA,mBAAmB;AACnB;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;;AAEA;AACA;AACA;AACA,OAAO;AACP;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,MAAM;AACN;AACA;;AAEA;AACA;AACA;;AAEA;AACA;;AAEA;;AAEA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,SAAS;AACT;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;;AAEA;AACA,GAAG;;AAEH;AACA;AACA;AACA;AACA,OAAO;AACP;AACA;;AAEA;AACA;;AAEA;AACA;AACA,QAAQ;AACR;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA,GAAG;;AAEH;AACA;;AAEA;AACA;AACA;AACA;;AAEA;AACA,GAAG;;AAEH;AACA;AACA;AACA,eAAe,QAAQ;AACvB,gBAAgB;AAChB;AACA;AACA;AACA;;AAEA;AACA,GAAG;;AAEH;AACA;AACA;AACA,eAAe,QAAQ;AACvB,gBAAgB;AAChB;AACA;AACA;;AAEA;AACA,GAAG;;AAEH;AACA;AACA;AACA,eAAe,QAAQ;AACvB,gBAAgB;AAChB;AACA;AACA;;AAEA;AACA,GAAG;;AAEH;AACA;AACA;AACA,gBAAgB;AAChB;AACA;AACA;;AAEA;AACA,GAAG;;AAEH;AACA;AACA;AACA,gBAAgB,QAAQ;AACxB;AACA;AACA;AACA;AACA,GAAG;;AAEH;AACA;AACA;AACA,eAAe,QAAQ;AACvB,gBAAgB;AAChB;AACA;AACA;;AAEA;AACA,GAAG;;AAEH;AACA;AACA;AACA,eAAe,QAAQ;AACvB,gBAAgB;AAChB;AACA;AACA;;AAEA;AACA,GAAG;;AAEH;AACA;AACA;AACA,eAAe,UAAU;AACzB;AACA,gBAAgB;AAChB;AACA;AACA;AACA;AACA;AACA,GAAG;;AAEH;AACA;AACA;AACA,eAAe,UAAU;AACzB;AACA,gBAAgB;AAChB;AACA;AACA;AACA;AACA;AACA,GAAG;;AAEH;AACA;AACA;AACA,eAAe,UAAU;AACzB;AACA,gBAAgB;AAChB;AACA;AACA;AACA;AACA;AACA,GAAG;;AAEH;AACA;AACA;AACA;AACA,eAAe,UAAU;AACzB;AACA;AACA,gBAAgB;AAChB;AACA;AACA;;AAEA;AACA,GAAG;;AAEH;AACA;AACA;AACA,gBAAgB;AAChB;AACA;AACA;AACA,GAAG;;AAEH;AACA;AACA;AACA,gBAAgB;AAChB;AACA;AACA;AACA,GAAG;;AAEH;AACA;AACA;AACA,gBAAgB;AAChB;AACA;AACA,sCAAsC;AACtC;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,GAAG;;AAEH;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA,GAAG;;AAEH;AACA;AACA;AACA;AACA;;AAEA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;;AAEA;AACA;AACA;AACA;AACA,GAAG;;AAEH;AACA;AACA;AACA;AACA;AACA;AACA;AACA,KAAK;AACL,GAAG;;AAEH;AACA;AACA;;AAEA;;AAEA;;AAEA;;AAEA;AACA;AACA;AACA,MAAM;AACN;AACA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA,MAAM;AACN;AACA;AACA;AACA;AACA,QAAQ;AACR;AACA;AACA;AACA,GAAG;;AAEH;AACA;AACA;AACA,iBAAiB;AACjB;AACA;AACA;AACA;AACA;AACA,iCAAiC;AACjC;AACA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,QAAQ;AACR;AACA;;AAEA;AACA;AACA;AACA,OAAO;AACP;AACA,GAAG;;AAEH;AACA;AACA,iBAAiB;AACjB;AACA;AACA;AACA;AACA,+BAA+B;;AAE/B;AACA;AACA;AACA;AACA;AACA;AACA;AACA,QAAQ;AACR;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,OAAO;AACP;AACA,GAAG;;AAEH;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA,KAAK;AACL,GAAG;;AAEH;AACA;AACA;AACA;AACA;AACA;;AAEA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA,wBAAwB,iBAAiB;AACzC;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA,UAAU;AACV;AACA;AACA;AACA;;AAEA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,gBAAgB;AAChB;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA,oBAAoB;AACpB;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,WAAW;AACX;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,gBAAgB;AAChB;AACA;AACA;AACA;AACA,WAAW;AACX;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,SAAS;AACT;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,oBAAoB,yBAAyB;AAC7C;AACA;AACA,GAAG;;AAEH;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;;AAEA;AACA;AACA;AACA;AACA,SAAS,GAAG;AACZ;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA,SAAS;AACT;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA,kBAAkB;AAClB;AACA;;AAEA;AACA;AACA;AACA;AACA,iBAAiB;AACjB;AACA;;AAEA;AACA,4BAA4B,kBAAkB;AAC9C;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA,kBAAkB;AAClB;AACA,cAAc;AACd;AACA;AACA;AACA;;AAEA;AACA;AACA,SAAS;AACT;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,4BAA4B,iBAAiB;AAC7C;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA,cAAc;AACd;AACA;AACA;AACA;AACA,cAAc;AACd;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA,aAAa;;AAEb;AACA;;AAEA;AACA,aAAa;AACb;AACA,SAAS;AACT;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA,QAAQ;AACR;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;AACA,+CAA+C;AAC/C;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,SAAS;AACT;;AAEA;AACA;AACA,OAAO;AACP;AACA,GAAG;;AAEH;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA,GAAG;;AAEH;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA,KAAK;AACL,GAAG;;AAEH;AACA;AACA,cAAc;AACd;;AAEA;AACA;AACA,MAAM;AACN;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA,GAAG;;AAEH;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA,GAAG;;AAEH;AACA;AACA;AACA;AACA;AACA,GAAG;;AAEH;AACA;;AAEA;AACA;AACA;AACA,KAAK;;AAEL;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,GAAG;;AAEH;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,OAAO;;AAEP;AACA;AACA,wBAAwB,iDAAiD;AACzE;AACA;AACA;AACA;AACA;AACA;AACA,GAAG;;AAEH;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA,0CAA0C;AAC1C;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA,GAAG;;AAEH;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;;AAEA;AACA;AACA;AACA;AACA;AACA,oBAAoB;AACpB,MAAM;AACN;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,SAAS;AACT;AACA,OAAO;AACP;AACA;;AAEA;AACA;AACA,GAAG;;AAEH;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;;AAEA;AACA,GAAG;;AAEH;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA,oBAAoB,+BAA+B;AACnD;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA,2BAA2B;AAC3B,sBAAsB,qBAAqB;AAC3C;AACA;AACA;AACA;AACA;AACA;AACA;AACA,GAAG;;AAEH;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA,GAAG;;AAEH;AACA;AACA;AACA,GAAG;;AAEH;AACA;AACA,GAAG;;AAEH;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA,MAAM;AACN;AACA;AACA;;AAEA;AACA,GAAG;;AAEH;AACA;AACA;AACA;AACA;;AAEA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA,0CAA0C;AAC1C,MAAM;AACN;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA,GAAG;;AAEH;AACA;;AAEA;AACA;AACA;AACA;AACA,OAAO;AACP;;AAEA;AACA;AACA;;AAEA;AACA;;AAEA;;AAEA;AACA,0CAA0C;AAC1C,2CAA2C;;AAE3C;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;;AAEA;AACA;;AAEA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA,MAAM;AACN;AACA;AACA,GAAG;;AAEH;AACA;AACA,GAAG;;AAEH;AACA;AACA;;AAEA;;AAEA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;;AAEA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,KAAK;;AAEL;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA,SAAS;AACT;AACA,OAAO;AACP;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;AACA,SAAS;AACT;AACA;AACA;AACA,KAAK;AACL,GAAG;;AAEH;AACA;AACA;;AAEA;AACA;;AAEA;;AAEA;;AAEA;AACA;AACA;AACA;AACA,UAAU;AACV;AACA,UAAU;AACV;AACA;AACA;AACA;AACA;AACA,MAAM;AACN;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA,GAAG;;AAEH;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,GAAG;;AAEH;AACA;AACA;AACA,MAAM;AACN,2EAA2E;AAC3E;AACA;AACA;;AAEA;AACA;AACA;;AAEA;;;;;;;;;;;ACr4DA;AACA;AACA;AACA;AACA;;AAEA,uBAAuB,mBAAO,CAAC,qDAAS;;AAExC;AACA;AACA;AACA;AACA,aAAa,qBAAM,mBAAmB,qBAAM;AAC5C;;AAEA;;AAEA;AACA;AACA;AACA;AACA,YAAY;AACZ;AACA;AACA;AACA;AACA;;AAEA;;AAEA;;;;;;;;;;;AC9BA;AACA;AACA;AACA,aAAa,qBAAM,mBAAmB,qBAAM;;AAE5C;AACA;AACA;;AAEA;AACA;AACA;AACA,YAAY;AACZ;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA,mCAAmC;AACnC;;AAEA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA,oCAAoC;AACpC;AACA;;AAEA;AACA;AACA,wBAAwB;AACxB;AACA,IAAI;AACJ;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;;AAEA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA,IAAI;AACJ;AACA;AACA,kBAAkB,OAAO;AACzB;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA,GAAG;AACH;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA,WAAW,QAAQ;AACnB,WAAW,QAAQ;AACnB;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA,SAAS,SAAS;AAClB;AACA;AACA;AACA;AACA,iDAAiD;AACjD,MAAM;AACN;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA,GAAG;AACH;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,IAAI;AACJ;AACA;AACA;AACA;AACA;AACA,KAAK;AACL;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA,aAAa;AACb;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;;AAEA;AACA;AACA;;AAEA;AACA;;AAEA;AACA;AACA;AACA;AACA,aAAa;AACb;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA,gBAAgB,oBAAoB;AACpC;AACA;AACA;AACA;AACA,cAAc,0BAA0B;AACxC;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA;;AAEA;;AAEA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA;;AAEA;AACA;;AAEA,kCAAkC;AAClC;AACA,kBAAkB,oBAAoB;AACtC;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA,iBAAiB,UAAU;AAC3B;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;;;;;;;;;;AChYA,YAAY,mBAAO,CAAC,6DAAiB;;AAErC;AACA;;AAEA;AACA;AACA;;AAEA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA,aAAa,qBAAM,mBAAmB,qBAAM;;AAE5C;AACA;AACA;;AAEA;AACA;;AAEA;AACA;;AAEA;AACA;;AAEA;AACA;AACA;AACA;AACA,qDAAqD,KAAK;AAC1D,uDAAuD,KAAK;AAC5D;AACA,WAAW,aAAa,YAAY;AACpC;AACA;AACA;AACA,8BAA8B;AAC9B;AACA;AACA,+DAA+D;AAC/D;AACA,+DAA+D;AAC/D;AACA;AACA;AACA;AACA;AACA,oCAAoC;AACpC;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA,eAAe,UAAU;AACzB;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA,eAAe,UAAU;AACzB;AACA;AACA,sCAAsC,QAAQ;AAC9C;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA,eAAe,oBAAoB;AACnC;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,UAAU;AACV;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;;AAEA;AACA;AACA;AACA,eAAe,QAAQ;AACvB,eAAe,QAAQ;AACvB,eAAe,iBAAiB;AAChC;AACA,eAAe,kBAAkB;AACjC;AACA,eAAe,QAAQ;AACvB;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,MAAM;AACN,8BAA8B;;AAE9B;AACA;AACA;AACA;AACA;AACA,MAAM;AACN;AACA;AACA;AACA;AACA;;AAEA;AACA,yBAAyB;AACzB;AACA,YAAY;AACZ;AACA;AACA;AACA;AACA;AACA;;AAEA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA,eAAe,OAAO;AACtB,eAAe,UAAU;AACzB;AACA;AACA;AACA;AACA;AACA;AACA;AACA,gBAAgB;AAChB,QAAQ;AACR;AACA;AACA;;AAEA;AACA;AACA;AACA;;AAEA;AACA;AACA,uBAAuB;AACvB;AACA;AACA;AACA;AACA;AACA,KAAK;;AAEL;AACA,gBAAgB;AAChB;AACA;;AAEA;AACA;AACA;AACA;AACA,CAAC;;AAED;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,0BAA0B;;AAE1B;AACA;AACA;AACA,eAAe,OAAO;AACtB,gBAAgB,qBAAqB;AACrC;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA,sCAAsC,OAAO;AAC7C;AACA,qEAAqE;AACrE,iEAAiE;AACjE;AACA;AACA,kCAAkC;AAClC,kCAAkC;AAClC,kCAAkC;AAClC;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,QAAQ;AACR;AACA;AACA;AACA;AACA;AACA;AACA;AACA,QAAQ;AACR;AACA;AACA;AACA;AACA;AACA,2BAA2B;AAC3B,UAAU;AACV;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,QAAQ;AACR;AACA;;AAEA;AACA;AACA;;AAEA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA,eAAe,oBAAoB;AACnC;AACA,eAAe,QAAQ;AACvB,eAAe,iBAAiB;AAChC;AACA,eAAe,SAAS;AACxB;AACA,gBAAgB,SAAS;AACzB;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;AACA,0BAA0B;AAC1B,YAAY;AACZ;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA,MAAM;AACN;AACA;;AAEA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA,QAAQ,0CAA0C;AAClD,eAAe,OAAO;AACtB,gBAAgB,qBAAqB;AACrC;AACA;AACA;AACA;AACA,gBAAgB;AAChB;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA,QAAQ;AACR;AACA;;AAEA;AACA;AACA,qEAAqE;AACrE,UAAU;AACV;;AAEA;AACA;AACA,QAAQ;AACR;AACA;;AAEA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA,eAAe,OAAO;AACtB,eAAe,kBAAkB;AACjC;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA,MAAM;AACN;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA,MAAM;AACN;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;;AAEA;AACA,CAAC;;AAED;;;;;;;;;;;AC9mBA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;;AAEA;AACA,oBAAoB;;AAEpB;AACA,kBAAkB,qBAAqB;AACvC;AACA;AACA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA;AACA;;AAEA;AACA;AACA;AACA,MAAM;AACN;AACA;;AAEA;AACA;AACA;AACA;AACA;;;;;;;;;;;;ACzEA;;;;;;UCAA;UACA;;UAEA;UACA;UACA;UACA;UACA;UACA;UACA;UACA;UACA;UACA;UACA;UACA;UACA;;UAEA;UACA;;UAEA;UACA;UACA;;;;;WCtBA;WACA;WACA;WACA;WACA;WACA,iCAAiC,WAAW;WAC5C;WACA;;;;;WCPA;WACA;WACA;WACA;WACA,yCAAyC,wCAAwC;WACjF;WACA;WACA;;;;;WCPA;WACA;WACA;WACA;WACA,GAAG;WACH;WACA;WACA,CAAC;;;;;WCPD;;;;;WCAA;WACA;WACA;WACA,uDAAuD,iBAAiB;WACxE;WACA,gDAAgD,aAAa;WAC7D;;;;;;;;;;;;;;;;;;;;;ACNA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AACA,SAASa,gBAAT,GAA4B;EACxB,IAAMC,IAAI,GAAGrI,6CAAC,CAAClB,oFAAD,CAAD,CAAsCwJ,IAAtC,CAA2C,MAA3C,CAAb;;EACA,IAAID,IAAJ,EAAU;IACNhM,MAAM,CAACkM,QAAP,CAAgBF,IAAhB,GAAuBA,IAAvB;EACH;AACJ;;AACD,SAASG,eAAT,GAA2B;EACvBxI,6CAAC,CAAClB,sFAAD,CAAD,CAAwC8B,QAAxC,CAAiD,SAAjD;AACH;;AACD,SAAS6H,mBAAT,CAA6B/H,CAA7B,EAAgC;EAC5BA,CAAC,CAACK,cAAF;EACAyH,eAAe;EACf,IAAME,QAAQ,GAAG1I,6CAAC,CAAClB,oFAAD,CAAD,CACZwC,cADY,GAEZqH,IAFY,CAEP,UAAAC,KAAK;IAAA,OAAIA,KAAK,CAAClC,IAAN,KAAe,UAAnB;EAAA,CAFE,CAAjB;EAGAxF,6EAAkB,CAACpC,oFAAD,CAAlB,CACK+J,IADL,CACU,YAAM;IACZ,IAAIH,QAAQ,IAAIpK,iEAAhB,EAA8B;MAC1B,IAAMwJ,QAAQ,GAAGR,mFAAwB,CAAChJ,iEAAD,CAAzC;MACAwJ,QAAQ,CAACgB,WAAT,CAAqB;QACjBC,GAAG,EAAExE,6FADY;QAEjByE,OAAO,EAAE;UACLpH,IAAI,EAAE8G,QAAQ,CAACO,KAAT,CAAeC,IAAf,GAAsBC,OAAtB,CAA8B,SAA9B,EAAyC,GAAzC;QADD;MAFQ,CAArB;IAMH;EACJ,CAXD,WAYW,UAACC,GAAD,EAAS;IAChB3D,mEAAA,CAAuB2D,GAAvB;EACH,CAdD,aAea,YAAM;IACfhB,gBAAgB;EACnB,CAjBD;AAkBH;;AACD,SAAS7H,IAAT,GAAgB;EACZ;EACA,IAAIN,+DAAJ,CAAkBnB,oFAAlB,EAAsD,2BAAtD,EAAmF,wBAAnF,EAA6G,yBAA7G;EACAkB,6CAAC,CAAClB,oFAAD,CAAD,CACK+B,GADL,CACS,QADT,EAEKP,EAFL,CAEQ,QAFR,EAEkBmI,mBAFlB;EAGAzI,6CAAC,CAAClB,oFAAD,CAAD,CACK+B,GADL,CACS,OADT,EAEKP,EAFL,CAEQ,OAFR,EAEiB8H,gBAFjB;AAGH;;AACDnB,4EAAiB,CAAC1G,IAAD,CAAjB,C","sources":["webpack://leadin/./scripts/constants/leadinConfig.ts","webpack://leadin/./scripts/constants/selectors.ts","webpack://leadin/./scripts/feedback/ThickBoxModal.ts","webpack://leadin/./scripts/feedback/feedbackFormApi.ts","webpack://leadin/./scripts/iframe/integratedMessages/core/CoreMessages.ts","webpack://leadin/./scripts/iframe/integratedMessages/forms/FormsMessages.ts","webpack://leadin/./scripts/iframe/integratedMessages/index.ts","webpack://leadin/./scripts/iframe/integratedMessages/livechat/LiveChatMessages.ts","webpack://leadin/./scripts/iframe/integratedMessages/plugin/PluginMessages.ts","webpack://leadin/./scripts/iframe/integratedMessages/proxy/ProxyMessages.ts","webpack://leadin/./scripts/lib/Raven.ts","webpack://leadin/./scripts/utils/appUtils.ts","webpack://leadin/./scripts/utils/backgroundAppUtils.ts","webpack://leadin/./node_modules/raven-js/src/configError.js","webpack://leadin/./node_modules/raven-js/src/console.js","webpack://leadin/./node_modules/raven-js/src/raven.js","webpack://leadin/./node_modules/raven-js/src/singleton.js","webpack://leadin/./node_modules/raven-js/src/utils.js","webpack://leadin/./node_modules/raven-js/vendor/TraceKit/tracekit.js","webpack://leadin/./node_modules/raven-js/vendor/json-stringify-safe/stringify.js","webpack://leadin/external window \"jQuery\"","webpack://leadin/webpack/bootstrap","webpack://leadin/webpack/runtime/compat get default export","webpack://leadin/webpack/runtime/define property getters","webpack://leadin/webpack/runtime/global","webpack://leadin/webpack/runtime/hasOwnProperty shorthand","webpack://leadin/webpack/runtime/make namespace object","webpack://leadin/./scripts/entries/feedback.ts"],"sourcesContent":["const { accountName, adminUrl, activationTime, connectionStatus, deviceId, didDisconnect, env, formsScript, meetingsScript, formsScriptPayload, hublet, hubspotBaseUrl, hubspotNonce, iframeUrl, impactLink, lastAuthorizeTime, lastDeauthorizeTime, lastDisconnectTime, leadinPluginVersion, leadinQueryParams, locale, loginUrl, phpVersion, pluginPath, plugins, portalDomain, portalEmail, portalId, redirectNonce, restNonce, restUrl, refreshToken, reviewSkippedDate, theme, trackConsent, wpVersion, contentEmbed, requiresContentEmbedScope, refreshTokenError, } = window.leadinConfig;\nexport { accountName, adminUrl, activationTime, connectionStatus, deviceId, didDisconnect, env, formsScript, meetingsScript, formsScriptPayload, hublet, hubspotBaseUrl, hubspotNonce, iframeUrl, impactLink, lastAuthorizeTime, lastDeauthorizeTime, lastDisconnectTime, leadinPluginVersion, leadinQueryParams, loginUrl, locale, phpVersion, pluginPath, plugins, portalDomain, portalEmail, portalId, redirectNonce, restNonce, restUrl, refreshToken, reviewSkippedDate, theme, trackConsent, wpVersion, contentEmbed, requiresContentEmbedScope, refreshTokenError, };\n","export const domElements = {\n iframe: '#leadin-iframe',\n subMenu: '.toplevel_page_leadin > ul',\n subMenuLinks: '.toplevel_page_leadin > ul a',\n subMenuButtons: '.toplevel_page_leadin > ul > li',\n deactivatePluginButton: '[data-slug=\"leadin\"] .deactivate a',\n deactivateFeedbackForm: 'form.leadin-deactivate-form',\n deactivateFeedbackSubmit: 'button#leadin-feedback-submit',\n deactivateFeedbackSkip: 'button#leadin-feedback-skip',\n thickboxModalClose: '.leadin-modal-close',\n thickboxModalWindow: 'div#TB_window.thickbox-loading',\n thickboxModalContent: 'div#TB_ajaxContent.TB_modal',\n reviewBannerContainer: '#leadin-review-banner',\n reviewBannerLeaveReviewLink: 'a#leave-review-button',\n reviewBannerDismissButton: 'a#dismiss-review-banner-button',\n leadinIframeContainer: 'leadin-iframe-container',\n leadinIframe: 'leadin-iframe',\n leadinIframeFallbackContainer: 'leadin-iframe-fallback-container',\n};\n","import $ from 'jquery';\nimport { domElements } from '../constants/selectors';\nexport default class ThickBoxModal {\n openTriggerSelector;\n inlineContentId;\n windowCssClass;\n contentCssClass;\n constructor(openTriggerSelector, inlineContentId, windowCssClass, contentCssClass) {\n this.openTriggerSelector = openTriggerSelector;\n this.inlineContentId = inlineContentId;\n this.windowCssClass = windowCssClass;\n this.contentCssClass = contentCssClass;\n $(openTriggerSelector).on('click', this.init.bind(this));\n }\n close() {\n //@ts-expect-error global\n window.tb_remove();\n }\n init(e) {\n //@ts-expect-error global\n window.tb_show('', `#TB_inline?inlineId=${this.inlineContentId}&modal=true`);\n // thickbox doesn't respect the width and height url parameters https://core.trac.wordpress.org/ticket/17249\n // We override thickboxes css with !important in the css\n $(domElements.thickboxModalWindow).addClass(this.windowCssClass);\n // have to modify the css of the thickbox content container as well\n $(domElements.thickboxModalContent).addClass(this.contentCssClass);\n // we unbind previous handlers because a thickbox modal is a single global object.\n // Everytime it is re-opened, it still has old handlers bound\n $(domElements.thickboxModalClose)\n .off('click')\n .on('click', this.close);\n e.preventDefault();\n }\n}\n","import $ from 'jquery';\nconst portalId = '6275621';\nconst formId = '0e8807f8-2ac3-4664-b742-44552bfa09e2';\nconst formSubmissionUrl = `https://api.hsforms.com/submissions/v3/integration/submit/${portalId}/${formId}`;\nexport function submitFeedbackForm(formSelector) {\n const formSubmissionPayload = {\n fields: $(formSelector).serializeArray(),\n skipValidation: true,\n };\n return new Promise((resolve, reject) => {\n $.ajax({\n type: 'POST',\n url: formSubmissionUrl,\n contentType: 'application/json',\n data: JSON.stringify(formSubmissionPayload),\n success: resolve,\n error: reject,\n });\n });\n}\n","export const CoreMessages = {\n HandshakeReceive: 'INTEGRATED_APP_EMBEDDER_HANDSHAKE_RECEIVED',\n SendRefreshToken: 'INTEGRATED_APP_EMBEDDER_SEND_REFRESH_TOKEN',\n ReloadParentFrame: 'INTEGRATED_APP_EMBEDDER_RELOAD_PARENT_FRAME',\n RedirectParentFrame: 'INTEGRATED_APP_EMBEDDER_REDIRECT_PARENT_FRAME',\n SendLocale: 'INTEGRATED_APP_EMBEDDER_SEND_LOCALE',\n SendDeviceId: 'INTEGRATED_APP_EMBEDDER_SEND_DEVICE_ID',\n};\n","export const FormMessages = {\n CreateFormAppNavigation: 'CREATE_FORM_APP_NAVIGATION',\n};\n","export * from './core/CoreMessages';\nexport * from './forms/FormsMessages';\nexport * from './livechat/LiveChatMessages';\nexport * from './plugin/PluginMessages';\nexport * from './proxy/ProxyMessages';\n","export const LiveChatMessages = {\n CreateLiveChatAppNavigation: 'CREATE_LIVE_CHAT_APP_NAVIGATION',\n};\n","export const PluginMessages = {\n PluginSettingsNavigation: 'PLUGIN_SETTINGS_NAVIGATION',\n PluginLeadinConfig: 'PLUGIN_LEADIN_CONFIG',\n TrackConsent: 'INTEGRATED_APP_EMBEDDER_TRACK_CONSENT',\n InternalTrackingFetchRequest: 'INTEGRATED_TRACKING_FETCH_REQUEST',\n InternalTrackingFetchResponse: 'INTEGRATED_TRACKING_FETCH_RESPONSE',\n InternalTrackingFetchError: 'INTEGRATED_TRACKING_FETCH_ERROR',\n InternalTrackingChangeRequest: 'INTEGRATED_TRACKING_CHANGE_REQUEST',\n InternalTrackingChangeError: 'INTEGRATED_TRACKING_CHANGE_ERROR',\n BusinessUnitFetchRequest: 'BUSINESS_UNIT_FETCH_REQUEST',\n BusinessUnitFetchResponse: 'BUSINESS_UNIT_FETCH_FETCH_RESPONSE',\n BusinessUnitFetchError: 'BUSINESS_UNIT_FETCH_FETCH_ERROR',\n BusinessUnitChangeRequest: 'BUSINESS_UNIT_CHANGE_REQUEST',\n BusinessUnitChangeError: 'BUSINESS_UNIT_CHANGE_ERROR',\n SkipReviewRequest: 'SKIP_REVIEW_REQUEST',\n SkipReviewResponse: 'SKIP_REVIEW_RESPONSE',\n SkipReviewError: 'SKIP_REVIEW_ERROR',\n RemoveParentQueryParam: 'REMOVE_PARENT_QUERY_PARAM',\n ContentEmbedInstallRequest: 'CONTENT_EMBED_INSTALL_REQUEST',\n ContentEmbedInstallResponse: 'CONTENT_EMBED_INSTALL_RESPONSE',\n ContentEmbedInstallError: 'CONTENT_EMBED_INSTALL_ERROR',\n ContentEmbedActivationRequest: 'CONTENT_EMBED_ACTIVATION_REQUEST',\n ContentEmbedActivationResponse: 'CONTENT_EMBED_ACTIVATION_RESPONSE',\n ContentEmbedActivationError: 'CONTENT_EMBED_ACTIVATION_ERROR',\n};\n","export const ProxyMessages = {\n FetchForms: 'FETCH_FORMS',\n FetchForm: 'FETCH_FORM',\n CreateFormFromTemplate: 'CREATE_FORM_FROM_TEMPLATE',\n FetchAuth: 'FETCH_AUTH',\n FetchMeetingsAndUsers: 'FETCH_MEETINGS_AND_USERS',\n FetchContactsCreateSinceActivation: 'FETCH_CONTACTS_CREATED_SINCE_ACTIVATION',\n FetchOrCreateMeetingUser: 'FETCH_OR_CREATE_MEETING_USER',\n ConnectMeetingsCalendar: 'CONNECT_MEETINGS_CALENDAR',\n TrackFormPreviewRender: 'TRACK_FORM_PREVIEW_RENDER',\n TrackFormCreatedFromTemplate: 'TRACK_FORM_CREATED_FROM_TEMPLATE',\n TrackFormCreationFailed: 'TRACK_FORM_CREATION_FAILED',\n TrackMeetingPreviewRender: 'TRACK_MEETING_PREVIEW_RENDER',\n TrackSidebarMetaChange: 'TRACK_SIDEBAR_META_CHANGE',\n TrackReviewBannerRender: 'TRACK_REVIEW_BANNER_RENDER',\n TrackReviewBannerInteraction: 'TRACK_REVIEW_BANNER_INTERACTION',\n TrackReviewBannerDismissed: 'TRACK_REVIEW_BANNER_DISMISSED',\n TrackPluginDeactivation: 'TRACK_PLUGIN_DEACTIVATION',\n};\n","import Raven from 'raven-js';\nimport { hubspotBaseUrl, phpVersion, wpVersion, leadinPluginVersion, portalId, plugins, } from '../constants/leadinConfig';\nexport function configureRaven() {\n if (hubspotBaseUrl.indexOf('app.hubspot.com') === -1) {\n return;\n }\n Raven.config('https://e9b8f382cdd130c0d415cd977d2be56f@exceptions.hubspot.com/1', {\n instrument: {\n tryCatch: false,\n },\n release: leadinPluginVersion,\n }).install();\n Raven.setTagsContext({\n v: leadinPluginVersion,\n php: phpVersion,\n wordpress: wpVersion,\n });\n Raven.setExtraContext({\n hub: portalId,\n plugins: Object.keys(plugins)\n .map(name => `${name}#${plugins[name]}`)\n .join(','),\n });\n}\nexport default Raven;\n","import $ from 'jquery';\nimport Raven, { configureRaven } from '../lib/Raven';\nexport function initApp(initFn) {\n configureRaven();\n Raven.context(initFn);\n}\nexport function initAppOnReady(initFn) {\n function main() {\n $(initFn);\n }\n initApp(main);\n}\n","import { deviceId, hubspotBaseUrl, locale, portalId, } from '../constants/leadinConfig';\nimport { initApp } from './appUtils';\nexport function initBackgroundApp(initFn) {\n function main() {\n if (Array.isArray(initFn)) {\n initFn.forEach(callback => callback());\n }\n else {\n initFn();\n }\n }\n initApp(main);\n}\nexport const getOrCreateBackgroundApp = (refreshToken) => {\n if (window.LeadinBackgroundApp) {\n return window.LeadinBackgroundApp;\n }\n const { IntegratedAppEmbedder, IntegratedAppOptions } = window;\n const options = new IntegratedAppOptions()\n .setLocale(locale)\n .setDeviceId(deviceId)\n .setRefreshToken(refreshToken);\n const embedder = new IntegratedAppEmbedder('integrated-plugin-proxy', portalId, hubspotBaseUrl, () => { }).setOptions(options);\n embedder.attachTo(document.body, false);\n embedder.postStartAppMessage(); // lets the app know all all data has been passed to it\n window.LeadinBackgroundApp = embedder;\n return window.LeadinBackgroundApp;\n};\n","function RavenConfigError(message) {\n this.name = 'RavenConfigError';\n this.message = message;\n}\nRavenConfigError.prototype = new Error();\nRavenConfigError.prototype.constructor = RavenConfigError;\n\nmodule.exports = RavenConfigError;\n","var wrapMethod = function(console, level, callback) {\n var originalConsoleLevel = console[level];\n var originalConsole = console;\n\n if (!(level in console)) {\n return;\n }\n\n var sentryLevel = level === 'warn' ? 'warning' : level;\n\n console[level] = function() {\n var args = [].slice.call(arguments);\n\n var msg = '' + args.join(' ');\n var data = {level: sentryLevel, logger: 'console', extra: {arguments: args}};\n\n if (level === 'assert') {\n if (args[0] === false) {\n // Default browsers message\n msg = 'Assertion failed: ' + (args.slice(1).join(' ') || 'console.assert');\n data.extra.arguments = args.slice(1);\n callback && callback(msg, data);\n }\n } else {\n callback && callback(msg, data);\n }\n\n // this fails for some browsers. :(\n if (originalConsoleLevel) {\n // IE9 doesn't allow calling apply on console functions directly\n // See: https://stackoverflow.com/questions/5472938/does-ie9-support-console-log-and-is-it-a-real-function#answer-5473193\n Function.prototype.apply.call(originalConsoleLevel, originalConsole, args);\n }\n };\n};\n\nmodule.exports = {\n wrapMethod: wrapMethod\n};\n","/*global XDomainRequest:false */\n\nvar TraceKit = require('../vendor/TraceKit/tracekit');\nvar stringify = require('../vendor/json-stringify-safe/stringify');\nvar RavenConfigError = require('./configError');\n\nvar utils = require('./utils');\nvar isError = utils.isError;\nvar isObject = utils.isObject;\nvar isObject = utils.isObject;\nvar isErrorEvent = utils.isErrorEvent;\nvar isUndefined = utils.isUndefined;\nvar isFunction = utils.isFunction;\nvar isString = utils.isString;\nvar isEmptyObject = utils.isEmptyObject;\nvar each = utils.each;\nvar objectMerge = utils.objectMerge;\nvar truncate = utils.truncate;\nvar objectFrozen = utils.objectFrozen;\nvar hasKey = utils.hasKey;\nvar joinRegExp = utils.joinRegExp;\nvar urlencode = utils.urlencode;\nvar uuid4 = utils.uuid4;\nvar htmlTreeAsString = utils.htmlTreeAsString;\nvar isSameException = utils.isSameException;\nvar isSameStacktrace = utils.isSameStacktrace;\nvar parseUrl = utils.parseUrl;\nvar fill = utils.fill;\n\nvar wrapConsoleMethod = require('./console').wrapMethod;\n\nvar dsnKeys = 'source protocol user pass host port path'.split(' '),\n dsnPattern = /^(?:(\\w+):)?\\/\\/(?:(\\w+)(:\\w+)?@)?([\\w\\.-]+)(?::(\\d+))?(\\/.*)/;\n\nfunction now() {\n return +new Date();\n}\n\n// This is to be defensive in environments where window does not exist (see https://github.com/getsentry/raven-js/pull/785)\nvar _window =\n typeof window !== 'undefined'\n ? window\n : typeof global !== 'undefined' ? global : typeof self !== 'undefined' ? self : {};\nvar _document = _window.document;\nvar _navigator = _window.navigator;\n\nfunction keepOriginalCallback(original, callback) {\n return isFunction(callback)\n ? function(data) {\n return callback(data, original);\n }\n : callback;\n}\n\n// First, check for JSON support\n// If there is no JSON, we no-op the core features of Raven\n// since JSON is required to encode the payload\nfunction Raven() {\n this._hasJSON = !!(typeof JSON === 'object' && JSON.stringify);\n // Raven can run in contexts where there's no document (react-native)\n this._hasDocument = !isUndefined(_document);\n this._hasNavigator = !isUndefined(_navigator);\n this._lastCapturedException = null;\n this._lastData = null;\n this._lastEventId = null;\n this._globalServer = null;\n this._globalKey = null;\n this._globalProject = null;\n this._globalContext = {};\n this._globalOptions = {\n logger: 'javascript',\n ignoreErrors: [],\n ignoreUrls: [],\n whitelistUrls: [],\n includePaths: [],\n collectWindowErrors: true,\n maxMessageLength: 0,\n\n // By default, truncates URL values to 250 chars\n maxUrlLength: 250,\n stackTraceLimit: 50,\n autoBreadcrumbs: true,\n instrument: true,\n sampleRate: 1\n };\n this._ignoreOnError = 0;\n this._isRavenInstalled = false;\n this._originalErrorStackTraceLimit = Error.stackTraceLimit;\n // capture references to window.console *and* all its methods first\n // before the console plugin has a chance to monkey patch\n this._originalConsole = _window.console || {};\n this._originalConsoleMethods = {};\n this._plugins = [];\n this._startTime = now();\n this._wrappedBuiltIns = [];\n this._breadcrumbs = [];\n this._lastCapturedEvent = null;\n this._keypressTimeout;\n this._location = _window.location;\n this._lastHref = this._location && this._location.href;\n this._resetBackoff();\n\n // eslint-disable-next-line guard-for-in\n for (var method in this._originalConsole) {\n this._originalConsoleMethods[method] = this._originalConsole[method];\n }\n}\n\n/*\n * The core Raven singleton\n *\n * @this {Raven}\n */\n\nRaven.prototype = {\n // Hardcode version string so that raven source can be loaded directly via\n // webpack (using a build step causes webpack #1617). Grunt verifies that\n // this value matches package.json during build.\n // See: https://github.com/getsentry/raven-js/issues/465\n VERSION: '3.19.1',\n\n debug: false,\n\n TraceKit: TraceKit, // alias to TraceKit\n\n /*\n * Configure Raven with a DSN and extra options\n *\n * @param {string} dsn The public Sentry DSN\n * @param {object} options Set of global options [optional]\n * @return {Raven}\n */\n config: function(dsn, options) {\n var self = this;\n\n if (self._globalServer) {\n this._logDebug('error', 'Error: Raven has already been configured');\n return self;\n }\n if (!dsn) return self;\n\n var globalOptions = self._globalOptions;\n\n // merge in options\n if (options) {\n each(options, function(key, value) {\n // tags and extra are special and need to be put into context\n if (key === 'tags' || key === 'extra' || key === 'user') {\n self._globalContext[key] = value;\n } else {\n globalOptions[key] = value;\n }\n });\n }\n\n self.setDSN(dsn);\n\n // \"Script error.\" is hard coded into browsers for errors that it can't read.\n // this is the result of a script being pulled in from an external domain and CORS.\n globalOptions.ignoreErrors.push(/^Script error\\.?$/);\n globalOptions.ignoreErrors.push(/^Javascript error: Script error\\.? on line 0$/);\n\n // join regexp rules into one big rule\n globalOptions.ignoreErrors = joinRegExp(globalOptions.ignoreErrors);\n globalOptions.ignoreUrls = globalOptions.ignoreUrls.length\n ? joinRegExp(globalOptions.ignoreUrls)\n : false;\n globalOptions.whitelistUrls = globalOptions.whitelistUrls.length\n ? joinRegExp(globalOptions.whitelistUrls)\n : false;\n globalOptions.includePaths = joinRegExp(globalOptions.includePaths);\n globalOptions.maxBreadcrumbs = Math.max(\n 0,\n Math.min(globalOptions.maxBreadcrumbs || 100, 100)\n ); // default and hard limit is 100\n\n var autoBreadcrumbDefaults = {\n xhr: true,\n console: true,\n dom: true,\n location: true\n };\n\n var autoBreadcrumbs = globalOptions.autoBreadcrumbs;\n if ({}.toString.call(autoBreadcrumbs) === '[object Object]') {\n autoBreadcrumbs = objectMerge(autoBreadcrumbDefaults, autoBreadcrumbs);\n } else if (autoBreadcrumbs !== false) {\n autoBreadcrumbs = autoBreadcrumbDefaults;\n }\n globalOptions.autoBreadcrumbs = autoBreadcrumbs;\n\n var instrumentDefaults = {\n tryCatch: true\n };\n\n var instrument = globalOptions.instrument;\n if ({}.toString.call(instrument) === '[object Object]') {\n instrument = objectMerge(instrumentDefaults, instrument);\n } else if (instrument !== false) {\n instrument = instrumentDefaults;\n }\n globalOptions.instrument = instrument;\n\n TraceKit.collectWindowErrors = !!globalOptions.collectWindowErrors;\n\n // return for chaining\n return self;\n },\n\n /*\n * Installs a global window.onerror error handler\n * to capture and report uncaught exceptions.\n * At this point, install() is required to be called due\n * to the way TraceKit is set up.\n *\n * @return {Raven}\n */\n install: function() {\n var self = this;\n if (self.isSetup() && !self._isRavenInstalled) {\n TraceKit.report.subscribe(function() {\n self._handleOnErrorStackInfo.apply(self, arguments);\n });\n if (self._globalOptions.instrument && self._globalOptions.instrument.tryCatch) {\n self._instrumentTryCatch();\n }\n\n if (self._globalOptions.autoBreadcrumbs) self._instrumentBreadcrumbs();\n\n // Install all of the plugins\n self._drainPlugins();\n\n self._isRavenInstalled = true;\n }\n\n Error.stackTraceLimit = self._globalOptions.stackTraceLimit;\n return this;\n },\n\n /*\n * Set the DSN (can be called multiple time unlike config)\n *\n * @param {string} dsn The public Sentry DSN\n */\n setDSN: function(dsn) {\n var self = this,\n uri = self._parseDSN(dsn),\n lastSlash = uri.path.lastIndexOf('/'),\n path = uri.path.substr(1, lastSlash);\n\n self._dsn = dsn;\n self._globalKey = uri.user;\n self._globalSecret = uri.pass && uri.pass.substr(1);\n self._globalProject = uri.path.substr(lastSlash + 1);\n\n self._globalServer = self._getGlobalServer(uri);\n\n self._globalEndpoint =\n self._globalServer + '/' + path + 'api/' + self._globalProject + '/store/';\n\n // Reset backoff state since we may be pointing at a\n // new project/server\n this._resetBackoff();\n },\n\n /*\n * Wrap code within a context so Raven can capture errors\n * reliably across domains that is executed immediately.\n *\n * @param {object} options A specific set of options for this context [optional]\n * @param {function} func The callback to be immediately executed within the context\n * @param {array} args An array of arguments to be called with the callback [optional]\n */\n context: function(options, func, args) {\n if (isFunction(options)) {\n args = func || [];\n func = options;\n options = undefined;\n }\n\n return this.wrap(options, func).apply(this, args);\n },\n\n /*\n * Wrap code within a context and returns back a new function to be executed\n *\n * @param {object} options A specific set of options for this context [optional]\n * @param {function} func The function to be wrapped in a new context\n * @param {function} func A function to call before the try/catch wrapper [optional, private]\n * @return {function} The newly wrapped functions with a context\n */\n wrap: function(options, func, _before) {\n var self = this;\n // 1 argument has been passed, and it's not a function\n // so just return it\n if (isUndefined(func) && !isFunction(options)) {\n return options;\n }\n\n // options is optional\n if (isFunction(options)) {\n func = options;\n options = undefined;\n }\n\n // At this point, we've passed along 2 arguments, and the second one\n // is not a function either, so we'll just return the second argument.\n if (!isFunction(func)) {\n return func;\n }\n\n // We don't wanna wrap it twice!\n try {\n if (func.__raven__) {\n return func;\n }\n\n // If this has already been wrapped in the past, return that\n if (func.__raven_wrapper__) {\n return func.__raven_wrapper__;\n }\n } catch (e) {\n // Just accessing custom props in some Selenium environments\n // can cause a \"Permission denied\" exception (see raven-js#495).\n // Bail on wrapping and return the function as-is (defers to window.onerror).\n return func;\n }\n\n function wrapped() {\n var args = [],\n i = arguments.length,\n deep = !options || (options && options.deep !== false);\n\n if (_before && isFunction(_before)) {\n _before.apply(this, arguments);\n }\n\n // Recursively wrap all of a function's arguments that are\n // functions themselves.\n while (i--) args[i] = deep ? self.wrap(options, arguments[i]) : arguments[i];\n\n try {\n // Attempt to invoke user-land function\n // NOTE: If you are a Sentry user, and you are seeing this stack frame, it\n // means Raven caught an error invoking your application code. This is\n // expected behavior and NOT indicative of a bug with Raven.js.\n return func.apply(this, args);\n } catch (e) {\n self._ignoreNextOnError();\n self.captureException(e, options);\n throw e;\n }\n }\n\n // copy over properties of the old function\n for (var property in func) {\n if (hasKey(func, property)) {\n wrapped[property] = func[property];\n }\n }\n wrapped.prototype = func.prototype;\n\n func.__raven_wrapper__ = wrapped;\n // Signal that this function has been wrapped already\n // for both debugging and to prevent it to being wrapped twice\n wrapped.__raven__ = true;\n wrapped.__inner__ = func;\n\n return wrapped;\n },\n\n /*\n * Uninstalls the global error handler.\n *\n * @return {Raven}\n */\n uninstall: function() {\n TraceKit.report.uninstall();\n\n this._restoreBuiltIns();\n\n Error.stackTraceLimit = this._originalErrorStackTraceLimit;\n this._isRavenInstalled = false;\n\n return this;\n },\n\n /*\n * Manually capture an exception and send it over to Sentry\n *\n * @param {error} ex An exception to be logged\n * @param {object} options A specific set of options for this error [optional]\n * @return {Raven}\n */\n captureException: function(ex, options) {\n // Cases for sending ex as a message, rather than an exception\n var isNotError = !isError(ex);\n var isNotErrorEvent = !isErrorEvent(ex);\n var isErrorEventWithoutError = isErrorEvent(ex) && !ex.error;\n\n if ((isNotError && isNotErrorEvent) || isErrorEventWithoutError) {\n return this.captureMessage(\n ex,\n objectMerge(\n {\n trimHeadFrames: 1,\n stacktrace: true // if we fall back to captureMessage, default to attempting a new trace\n },\n options\n )\n );\n }\n\n // Get actual Error from ErrorEvent\n if (isErrorEvent(ex)) ex = ex.error;\n\n // Store the raw exception object for potential debugging and introspection\n this._lastCapturedException = ex;\n\n // TraceKit.report will re-raise any exception passed to it,\n // which means you have to wrap it in try/catch. Instead, we\n // can wrap it here and only re-raise if TraceKit.report\n // raises an exception different from the one we asked to\n // report on.\n try {\n var stack = TraceKit.computeStackTrace(ex);\n this._handleStackInfo(stack, options);\n } catch (ex1) {\n if (ex !== ex1) {\n throw ex1;\n }\n }\n\n return this;\n },\n\n /*\n * Manually send a message to Sentry\n *\n * @param {string} msg A plain message to be captured in Sentry\n * @param {object} options A specific set of options for this message [optional]\n * @return {Raven}\n */\n captureMessage: function(msg, options) {\n // config() automagically converts ignoreErrors from a list to a RegExp so we need to test for an\n // early call; we'll error on the side of logging anything called before configuration since it's\n // probably something you should see:\n if (\n !!this._globalOptions.ignoreErrors.test &&\n this._globalOptions.ignoreErrors.test(msg)\n ) {\n return;\n }\n\n options = options || {};\n\n var data = objectMerge(\n {\n message: msg + '' // Make sure it's actually a string\n },\n options\n );\n\n var ex;\n // Generate a \"synthetic\" stack trace from this point.\n // NOTE: If you are a Sentry user, and you are seeing this stack frame, it is NOT indicative\n // of a bug with Raven.js. Sentry generates synthetic traces either by configuration,\n // or if it catches a thrown object without a \"stack\" property.\n try {\n throw new Error(msg);\n } catch (ex1) {\n ex = ex1;\n }\n\n // null exception name so `Error` isn't prefixed to msg\n ex.name = null;\n var stack = TraceKit.computeStackTrace(ex);\n\n // stack[0] is `throw new Error(msg)` call itself, we are interested in the frame that was just before that, stack[1]\n var initialCall = stack.stack[1];\n\n var fileurl = (initialCall && initialCall.url) || '';\n\n if (\n !!this._globalOptions.ignoreUrls.test &&\n this._globalOptions.ignoreUrls.test(fileurl)\n ) {\n return;\n }\n\n if (\n !!this._globalOptions.whitelistUrls.test &&\n !this._globalOptions.whitelistUrls.test(fileurl)\n ) {\n return;\n }\n\n if (this._globalOptions.stacktrace || (options && options.stacktrace)) {\n options = objectMerge(\n {\n // fingerprint on msg, not stack trace (legacy behavior, could be\n // revisited)\n fingerprint: msg,\n // since we know this is a synthetic trace, the top N-most frames\n // MUST be from Raven.js, so mark them as in_app later by setting\n // trimHeadFrames\n trimHeadFrames: (options.trimHeadFrames || 0) + 1\n },\n options\n );\n\n var frames = this._prepareFrames(stack, options);\n data.stacktrace = {\n // Sentry expects frames oldest to newest\n frames: frames.reverse()\n };\n }\n\n // Fire away!\n this._send(data);\n\n return this;\n },\n\n captureBreadcrumb: function(obj) {\n var crumb = objectMerge(\n {\n timestamp: now() / 1000\n },\n obj\n );\n\n if (isFunction(this._globalOptions.breadcrumbCallback)) {\n var result = this._globalOptions.breadcrumbCallback(crumb);\n\n if (isObject(result) && !isEmptyObject(result)) {\n crumb = result;\n } else if (result === false) {\n return this;\n }\n }\n\n this._breadcrumbs.push(crumb);\n if (this._breadcrumbs.length > this._globalOptions.maxBreadcrumbs) {\n this._breadcrumbs.shift();\n }\n return this;\n },\n\n addPlugin: function(plugin /*arg1, arg2, ... argN*/) {\n var pluginArgs = [].slice.call(arguments, 1);\n\n this._plugins.push([plugin, pluginArgs]);\n if (this._isRavenInstalled) {\n this._drainPlugins();\n }\n\n return this;\n },\n\n /*\n * Set/clear a user to be sent along with the payload.\n *\n * @param {object} user An object representing user data [optional]\n * @return {Raven}\n */\n setUserContext: function(user) {\n // Intentionally do not merge here since that's an unexpected behavior.\n this._globalContext.user = user;\n\n return this;\n },\n\n /*\n * Merge extra attributes to be sent along with the payload.\n *\n * @param {object} extra An object representing extra data [optional]\n * @return {Raven}\n */\n setExtraContext: function(extra) {\n this._mergeContext('extra', extra);\n\n return this;\n },\n\n /*\n * Merge tags to be sent along with the payload.\n *\n * @param {object} tags An object representing tags [optional]\n * @return {Raven}\n */\n setTagsContext: function(tags) {\n this._mergeContext('tags', tags);\n\n return this;\n },\n\n /*\n * Clear all of the context.\n *\n * @return {Raven}\n */\n clearContext: function() {\n this._globalContext = {};\n\n return this;\n },\n\n /*\n * Get a copy of the current context. This cannot be mutated.\n *\n * @return {object} copy of context\n */\n getContext: function() {\n // lol javascript\n return JSON.parse(stringify(this._globalContext));\n },\n\n /*\n * Set environment of application\n *\n * @param {string} environment Typically something like 'production'.\n * @return {Raven}\n */\n setEnvironment: function(environment) {\n this._globalOptions.environment = environment;\n\n return this;\n },\n\n /*\n * Set release version of application\n *\n * @param {string} release Typically something like a git SHA to identify version\n * @return {Raven}\n */\n setRelease: function(release) {\n this._globalOptions.release = release;\n\n return this;\n },\n\n /*\n * Set the dataCallback option\n *\n * @param {function} callback The callback to run which allows the\n * data blob to be mutated before sending\n * @return {Raven}\n */\n setDataCallback: function(callback) {\n var original = this._globalOptions.dataCallback;\n this._globalOptions.dataCallback = keepOriginalCallback(original, callback);\n return this;\n },\n\n /*\n * Set the breadcrumbCallback option\n *\n * @param {function} callback The callback to run which allows filtering\n * or mutating breadcrumbs\n * @return {Raven}\n */\n setBreadcrumbCallback: function(callback) {\n var original = this._globalOptions.breadcrumbCallback;\n this._globalOptions.breadcrumbCallback = keepOriginalCallback(original, callback);\n return this;\n },\n\n /*\n * Set the shouldSendCallback option\n *\n * @param {function} callback The callback to run which allows\n * introspecting the blob before sending\n * @return {Raven}\n */\n setShouldSendCallback: function(callback) {\n var original = this._globalOptions.shouldSendCallback;\n this._globalOptions.shouldSendCallback = keepOriginalCallback(original, callback);\n return this;\n },\n\n /**\n * Override the default HTTP transport mechanism that transmits data\n * to the Sentry server.\n *\n * @param {function} transport Function invoked instead of the default\n * `makeRequest` handler.\n *\n * @return {Raven}\n */\n setTransport: function(transport) {\n this._globalOptions.transport = transport;\n\n return this;\n },\n\n /*\n * Get the latest raw exception that was captured by Raven.\n *\n * @return {error}\n */\n lastException: function() {\n return this._lastCapturedException;\n },\n\n /*\n * Get the last event id\n *\n * @return {string}\n */\n lastEventId: function() {\n return this._lastEventId;\n },\n\n /*\n * Determine if Raven is setup and ready to go.\n *\n * @return {boolean}\n */\n isSetup: function() {\n if (!this._hasJSON) return false; // needs JSON support\n if (!this._globalServer) {\n if (!this.ravenNotConfiguredError) {\n this.ravenNotConfiguredError = true;\n this._logDebug('error', 'Error: Raven has not been configured.');\n }\n return false;\n }\n return true;\n },\n\n afterLoad: function() {\n // TODO: remove window dependence?\n\n // Attempt to initialize Raven on load\n var RavenConfig = _window.RavenConfig;\n if (RavenConfig) {\n this.config(RavenConfig.dsn, RavenConfig.config).install();\n }\n },\n\n showReportDialog: function(options) {\n if (\n !_document // doesn't work without a document (React native)\n )\n return;\n\n options = options || {};\n\n var lastEventId = options.eventId || this.lastEventId();\n if (!lastEventId) {\n throw new RavenConfigError('Missing eventId');\n }\n\n var dsn = options.dsn || this._dsn;\n if (!dsn) {\n throw new RavenConfigError('Missing DSN');\n }\n\n var encode = encodeURIComponent;\n var qs = '';\n qs += '?eventId=' + encode(lastEventId);\n qs += '&dsn=' + encode(dsn);\n\n var user = options.user || this._globalContext.user;\n if (user) {\n if (user.name) qs += '&name=' + encode(user.name);\n if (user.email) qs += '&email=' + encode(user.email);\n }\n\n var globalServer = this._getGlobalServer(this._parseDSN(dsn));\n\n var script = _document.createElement('script');\n script.async = true;\n script.src = globalServer + '/api/embed/error-page/' + qs;\n (_document.head || _document.body).appendChild(script);\n },\n\n /**** Private functions ****/\n _ignoreNextOnError: function() {\n var self = this;\n this._ignoreOnError += 1;\n setTimeout(function() {\n // onerror should trigger before setTimeout\n self._ignoreOnError -= 1;\n });\n },\n\n _triggerEvent: function(eventType, options) {\n // NOTE: `event` is a native browser thing, so let's avoid conflicting wiht it\n var evt, key;\n\n if (!this._hasDocument) return;\n\n options = options || {};\n\n eventType = 'raven' + eventType.substr(0, 1).toUpperCase() + eventType.substr(1);\n\n if (_document.createEvent) {\n evt = _document.createEvent('HTMLEvents');\n evt.initEvent(eventType, true, true);\n } else {\n evt = _document.createEventObject();\n evt.eventType = eventType;\n }\n\n for (key in options)\n if (hasKey(options, key)) {\n evt[key] = options[key];\n }\n\n if (_document.createEvent) {\n // IE9 if standards\n _document.dispatchEvent(evt);\n } else {\n // IE8 regardless of Quirks or Standards\n // IE9 if quirks\n try {\n _document.fireEvent('on' + evt.eventType.toLowerCase(), evt);\n } catch (e) {\n // Do nothing\n }\n }\n },\n\n /**\n * Wraps addEventListener to capture UI breadcrumbs\n * @param evtName the event name (e.g. \"click\")\n * @returns {Function}\n * @private\n */\n _breadcrumbEventHandler: function(evtName) {\n var self = this;\n return function(evt) {\n // reset keypress timeout; e.g. triggering a 'click' after\n // a 'keypress' will reset the keypress debounce so that a new\n // set of keypresses can be recorded\n self._keypressTimeout = null;\n\n // It's possible this handler might trigger multiple times for the same\n // event (e.g. event propagation through node ancestors). Ignore if we've\n // already captured the event.\n if (self._lastCapturedEvent === evt) return;\n\n self._lastCapturedEvent = evt;\n\n // try/catch both:\n // - accessing evt.target (see getsentry/raven-js#838, #768)\n // - `htmlTreeAsString` because it's complex, and just accessing the DOM incorrectly\n // can throw an exception in some circumstances.\n var target;\n try {\n target = htmlTreeAsString(evt.target);\n } catch (e) {\n target = '';\n }\n\n self.captureBreadcrumb({\n category: 'ui.' + evtName, // e.g. ui.click, ui.input\n message: target\n });\n };\n },\n\n /**\n * Wraps addEventListener to capture keypress UI events\n * @returns {Function}\n * @private\n */\n _keypressEventHandler: function() {\n var self = this,\n debounceDuration = 1000; // milliseconds\n\n // TODO: if somehow user switches keypress target before\n // debounce timeout is triggered, we will only capture\n // a single breadcrumb from the FIRST target (acceptable?)\n return function(evt) {\n var target;\n try {\n target = evt.target;\n } catch (e) {\n // just accessing event properties can throw an exception in some rare circumstances\n // see: https://github.com/getsentry/raven-js/issues/838\n return;\n }\n var tagName = target && target.tagName;\n\n // only consider keypress events on actual input elements\n // this will disregard keypresses targeting body (e.g. tabbing\n // through elements, hotkeys, etc)\n if (\n !tagName ||\n (tagName !== 'INPUT' && tagName !== 'TEXTAREA' && !target.isContentEditable)\n )\n return;\n\n // record first keypress in a series, but ignore subsequent\n // keypresses until debounce clears\n var timeout = self._keypressTimeout;\n if (!timeout) {\n self._breadcrumbEventHandler('input')(evt);\n }\n clearTimeout(timeout);\n self._keypressTimeout = setTimeout(function() {\n self._keypressTimeout = null;\n }, debounceDuration);\n };\n },\n\n /**\n * Captures a breadcrumb of type \"navigation\", normalizing input URLs\n * @param to the originating URL\n * @param from the target URL\n * @private\n */\n _captureUrlChange: function(from, to) {\n var parsedLoc = parseUrl(this._location.href);\n var parsedTo = parseUrl(to);\n var parsedFrom = parseUrl(from);\n\n // because onpopstate only tells you the \"new\" (to) value of location.href, and\n // not the previous (from) value, we need to track the value of the current URL\n // state ourselves\n this._lastHref = to;\n\n // Use only the path component of the URL if the URL matches the current\n // document (almost all the time when using pushState)\n if (parsedLoc.protocol === parsedTo.protocol && parsedLoc.host === parsedTo.host)\n to = parsedTo.relative;\n if (parsedLoc.protocol === parsedFrom.protocol && parsedLoc.host === parsedFrom.host)\n from = parsedFrom.relative;\n\n this.captureBreadcrumb({\n category: 'navigation',\n data: {\n to: to,\n from: from\n }\n });\n },\n\n /**\n * Wrap timer functions and event targets to catch errors and provide\n * better metadata.\n */\n _instrumentTryCatch: function() {\n var self = this;\n\n var wrappedBuiltIns = self._wrappedBuiltIns;\n\n function wrapTimeFn(orig) {\n return function(fn, t) {\n // preserve arity\n // Make a copy of the arguments to prevent deoptimization\n // https://github.com/petkaantonov/bluebird/wiki/Optimization-killers#32-leaking-arguments\n var args = new Array(arguments.length);\n for (var i = 0; i < args.length; ++i) {\n args[i] = arguments[i];\n }\n var originalCallback = args[0];\n if (isFunction(originalCallback)) {\n args[0] = self.wrap(originalCallback);\n }\n\n // IE < 9 doesn't support .call/.apply on setInterval/setTimeout, but it\n // also supports only two arguments and doesn't care what this is, so we\n // can just call the original function directly.\n if (orig.apply) {\n return orig.apply(this, args);\n } else {\n return orig(args[0], args[1]);\n }\n };\n }\n\n var autoBreadcrumbs = this._globalOptions.autoBreadcrumbs;\n\n function wrapEventTarget(global) {\n var proto = _window[global] && _window[global].prototype;\n if (proto && proto.hasOwnProperty && proto.hasOwnProperty('addEventListener')) {\n fill(\n proto,\n 'addEventListener',\n function(orig) {\n return function(evtName, fn, capture, secure) {\n // preserve arity\n try {\n if (fn && fn.handleEvent) {\n fn.handleEvent = self.wrap(fn.handleEvent);\n }\n } catch (err) {\n // can sometimes get 'Permission denied to access property \"handle Event'\n }\n\n // More breadcrumb DOM capture ... done here and not in `_instrumentBreadcrumbs`\n // so that we don't have more than one wrapper function\n var before, clickHandler, keypressHandler;\n\n if (\n autoBreadcrumbs &&\n autoBreadcrumbs.dom &&\n (global === 'EventTarget' || global === 'Node')\n ) {\n // NOTE: generating multiple handlers per addEventListener invocation, should\n // revisit and verify we can just use one (almost certainly)\n clickHandler = self._breadcrumbEventHandler('click');\n keypressHandler = self._keypressEventHandler();\n before = function(evt) {\n // need to intercept every DOM event in `before` argument, in case that\n // same wrapped method is re-used for different events (e.g. mousemove THEN click)\n // see #724\n if (!evt) return;\n\n var eventType;\n try {\n eventType = evt.type;\n } catch (e) {\n // just accessing event properties can throw an exception in some rare circumstances\n // see: https://github.com/getsentry/raven-js/issues/838\n return;\n }\n if (eventType === 'click') return clickHandler(evt);\n else if (eventType === 'keypress') return keypressHandler(evt);\n };\n }\n return orig.call(\n this,\n evtName,\n self.wrap(fn, undefined, before),\n capture,\n secure\n );\n };\n },\n wrappedBuiltIns\n );\n fill(\n proto,\n 'removeEventListener',\n function(orig) {\n return function(evt, fn, capture, secure) {\n try {\n fn = fn && (fn.__raven_wrapper__ ? fn.__raven_wrapper__ : fn);\n } catch (e) {\n // ignore, accessing __raven_wrapper__ will throw in some Selenium environments\n }\n return orig.call(this, evt, fn, capture, secure);\n };\n },\n wrappedBuiltIns\n );\n }\n }\n\n fill(_window, 'setTimeout', wrapTimeFn, wrappedBuiltIns);\n fill(_window, 'setInterval', wrapTimeFn, wrappedBuiltIns);\n if (_window.requestAnimationFrame) {\n fill(\n _window,\n 'requestAnimationFrame',\n function(orig) {\n return function(cb) {\n return orig(self.wrap(cb));\n };\n },\n wrappedBuiltIns\n );\n }\n\n // event targets borrowed from bugsnag-js:\n // https://github.com/bugsnag/bugsnag-js/blob/master/src/bugsnag.js#L666\n var eventTargets = [\n 'EventTarget',\n 'Window',\n 'Node',\n 'ApplicationCache',\n 'AudioTrackList',\n 'ChannelMergerNode',\n 'CryptoOperation',\n 'EventSource',\n 'FileReader',\n 'HTMLUnknownElement',\n 'IDBDatabase',\n 'IDBRequest',\n 'IDBTransaction',\n 'KeyOperation',\n 'MediaController',\n 'MessagePort',\n 'ModalWindow',\n 'Notification',\n 'SVGElementInstance',\n 'Screen',\n 'TextTrack',\n 'TextTrackCue',\n 'TextTrackList',\n 'WebSocket',\n 'WebSocketWorker',\n 'Worker',\n 'XMLHttpRequest',\n 'XMLHttpRequestEventTarget',\n 'XMLHttpRequestUpload'\n ];\n for (var i = 0; i < eventTargets.length; i++) {\n wrapEventTarget(eventTargets[i]);\n }\n },\n\n /**\n * Instrument browser built-ins w/ breadcrumb capturing\n * - XMLHttpRequests\n * - DOM interactions (click/typing)\n * - window.location changes\n * - console\n *\n * Can be disabled or individually configured via the `autoBreadcrumbs` config option\n */\n _instrumentBreadcrumbs: function() {\n var self = this;\n var autoBreadcrumbs = this._globalOptions.autoBreadcrumbs;\n\n var wrappedBuiltIns = self._wrappedBuiltIns;\n\n function wrapProp(prop, xhr) {\n if (prop in xhr && isFunction(xhr[prop])) {\n fill(xhr, prop, function(orig) {\n return self.wrap(orig);\n }); // intentionally don't track filled methods on XHR instances\n }\n }\n\n if (autoBreadcrumbs.xhr && 'XMLHttpRequest' in _window) {\n var xhrproto = XMLHttpRequest.prototype;\n fill(\n xhrproto,\n 'open',\n function(origOpen) {\n return function(method, url) {\n // preserve arity\n\n // if Sentry key appears in URL, don't capture\n if (isString(url) && url.indexOf(self._globalKey) === -1) {\n this.__raven_xhr = {\n method: method,\n url: url,\n status_code: null\n };\n }\n\n return origOpen.apply(this, arguments);\n };\n },\n wrappedBuiltIns\n );\n\n fill(\n xhrproto,\n 'send',\n function(origSend) {\n return function(data) {\n // preserve arity\n var xhr = this;\n\n function onreadystatechangeHandler() {\n if (xhr.__raven_xhr && xhr.readyState === 4) {\n try {\n // touching statusCode in some platforms throws\n // an exception\n xhr.__raven_xhr.status_code = xhr.status;\n } catch (e) {\n /* do nothing */\n }\n\n self.captureBreadcrumb({\n type: 'http',\n category: 'xhr',\n data: xhr.__raven_xhr\n });\n }\n }\n\n var props = ['onload', 'onerror', 'onprogress'];\n for (var j = 0; j < props.length; j++) {\n wrapProp(props[j], xhr);\n }\n\n if ('onreadystatechange' in xhr && isFunction(xhr.onreadystatechange)) {\n fill(\n xhr,\n 'onreadystatechange',\n function(orig) {\n return self.wrap(orig, undefined, onreadystatechangeHandler);\n } /* intentionally don't track this instrumentation */\n );\n } else {\n // if onreadystatechange wasn't actually set by the page on this xhr, we\n // are free to set our own and capture the breadcrumb\n xhr.onreadystatechange = onreadystatechangeHandler;\n }\n\n return origSend.apply(this, arguments);\n };\n },\n wrappedBuiltIns\n );\n }\n\n if (autoBreadcrumbs.xhr && 'fetch' in _window) {\n fill(\n _window,\n 'fetch',\n function(origFetch) {\n return function(fn, t) {\n // preserve arity\n // Make a copy of the arguments to prevent deoptimization\n // https://github.com/petkaantonov/bluebird/wiki/Optimization-killers#32-leaking-arguments\n var args = new Array(arguments.length);\n for (var i = 0; i < args.length; ++i) {\n args[i] = arguments[i];\n }\n\n var fetchInput = args[0];\n var method = 'GET';\n var url;\n\n if (typeof fetchInput === 'string') {\n url = fetchInput;\n } else if ('Request' in _window && fetchInput instanceof _window.Request) {\n url = fetchInput.url;\n if (fetchInput.method) {\n method = fetchInput.method;\n }\n } else {\n url = '' + fetchInput;\n }\n\n if (args[1] && args[1].method) {\n method = args[1].method;\n }\n\n var fetchData = {\n method: method,\n url: url,\n status_code: null\n };\n\n self.captureBreadcrumb({\n type: 'http',\n category: 'fetch',\n data: fetchData\n });\n\n return origFetch.apply(this, args).then(function(response) {\n fetchData.status_code = response.status;\n\n return response;\n });\n };\n },\n wrappedBuiltIns\n );\n }\n\n // Capture breadcrumbs from any click that is unhandled / bubbled up all the way\n // to the document. Do this before we instrument addEventListener.\n if (autoBreadcrumbs.dom && this._hasDocument) {\n if (_document.addEventListener) {\n _document.addEventListener('click', self._breadcrumbEventHandler('click'), false);\n _document.addEventListener('keypress', self._keypressEventHandler(), false);\n } else {\n // IE8 Compatibility\n _document.attachEvent('onclick', self._breadcrumbEventHandler('click'));\n _document.attachEvent('onkeypress', self._keypressEventHandler());\n }\n }\n\n // record navigation (URL) changes\n // NOTE: in Chrome App environment, touching history.pushState, *even inside\n // a try/catch block*, will cause Chrome to output an error to console.error\n // borrowed from: https://github.com/angular/angular.js/pull/13945/files\n var chrome = _window.chrome;\n var isChromePackagedApp = chrome && chrome.app && chrome.app.runtime;\n var hasPushAndReplaceState =\n !isChromePackagedApp &&\n _window.history &&\n history.pushState &&\n history.replaceState;\n if (autoBreadcrumbs.location && hasPushAndReplaceState) {\n // TODO: remove onpopstate handler on uninstall()\n var oldOnPopState = _window.onpopstate;\n _window.onpopstate = function() {\n var currentHref = self._location.href;\n self._captureUrlChange(self._lastHref, currentHref);\n\n if (oldOnPopState) {\n return oldOnPopState.apply(this, arguments);\n }\n };\n\n var historyReplacementFunction = function(origHistFunction) {\n // note history.pushState.length is 0; intentionally not declaring\n // params to preserve 0 arity\n return function(/* state, title, url */) {\n var url = arguments.length > 2 ? arguments[2] : undefined;\n\n // url argument is optional\n if (url) {\n // coerce to string (this is what pushState does)\n self._captureUrlChange(self._lastHref, url + '');\n }\n\n return origHistFunction.apply(this, arguments);\n };\n };\n\n fill(history, 'pushState', historyReplacementFunction, wrappedBuiltIns);\n fill(history, 'replaceState', historyReplacementFunction, wrappedBuiltIns);\n }\n\n if (autoBreadcrumbs.console && 'console' in _window && console.log) {\n // console\n var consoleMethodCallback = function(msg, data) {\n self.captureBreadcrumb({\n message: msg,\n level: data.level,\n category: 'console'\n });\n };\n\n each(['debug', 'info', 'warn', 'error', 'log'], function(_, level) {\n wrapConsoleMethod(console, level, consoleMethodCallback);\n });\n }\n },\n\n _restoreBuiltIns: function() {\n // restore any wrapped builtins\n var builtin;\n while (this._wrappedBuiltIns.length) {\n builtin = this._wrappedBuiltIns.shift();\n\n var obj = builtin[0],\n name = builtin[1],\n orig = builtin[2];\n\n obj[name] = orig;\n }\n },\n\n _drainPlugins: function() {\n var self = this;\n\n // FIX ME TODO\n each(this._plugins, function(_, plugin) {\n var installer = plugin[0];\n var args = plugin[1];\n installer.apply(self, [self].concat(args));\n });\n },\n\n _parseDSN: function(str) {\n var m = dsnPattern.exec(str),\n dsn = {},\n i = 7;\n\n try {\n while (i--) dsn[dsnKeys[i]] = m[i] || '';\n } catch (e) {\n throw new RavenConfigError('Invalid DSN: ' + str);\n }\n\n if (dsn.pass && !this._globalOptions.allowSecretKey) {\n throw new RavenConfigError(\n 'Do not specify your secret key in the DSN. See: http://bit.ly/raven-secret-key'\n );\n }\n\n return dsn;\n },\n\n _getGlobalServer: function(uri) {\n // assemble the endpoint from the uri pieces\n var globalServer = '//' + uri.host + (uri.port ? ':' + uri.port : '');\n\n if (uri.protocol) {\n globalServer = uri.protocol + ':' + globalServer;\n }\n return globalServer;\n },\n\n _handleOnErrorStackInfo: function() {\n // if we are intentionally ignoring errors via onerror, bail out\n if (!this._ignoreOnError) {\n this._handleStackInfo.apply(this, arguments);\n }\n },\n\n _handleStackInfo: function(stackInfo, options) {\n var frames = this._prepareFrames(stackInfo, options);\n\n this._triggerEvent('handle', {\n stackInfo: stackInfo,\n options: options\n });\n\n this._processException(\n stackInfo.name,\n stackInfo.message,\n stackInfo.url,\n stackInfo.lineno,\n frames,\n options\n );\n },\n\n _prepareFrames: function(stackInfo, options) {\n var self = this;\n var frames = [];\n if (stackInfo.stack && stackInfo.stack.length) {\n each(stackInfo.stack, function(i, stack) {\n var frame = self._normalizeFrame(stack, stackInfo.url);\n if (frame) {\n frames.push(frame);\n }\n });\n\n // e.g. frames captured via captureMessage throw\n if (options && options.trimHeadFrames) {\n for (var j = 0; j < options.trimHeadFrames && j < frames.length; j++) {\n frames[j].in_app = false;\n }\n }\n }\n frames = frames.slice(0, this._globalOptions.stackTraceLimit);\n return frames;\n },\n\n _normalizeFrame: function(frame, stackInfoUrl) {\n // normalize the frames data\n var normalized = {\n filename: frame.url,\n lineno: frame.line,\n colno: frame.column,\n function: frame.func || '?'\n };\n\n // Case when we don't have any information about the error\n // E.g. throwing a string or raw object, instead of an `Error` in Firefox\n // Generating synthetic error doesn't add any value here\n //\n // We should probably somehow let a user know that they should fix their code\n if (!frame.url) {\n normalized.filename = stackInfoUrl; // fallback to whole stacks url from onerror handler\n }\n\n normalized.in_app = !// determine if an exception came from outside of our app\n // first we check the global includePaths list.\n (\n (!!this._globalOptions.includePaths.test &&\n !this._globalOptions.includePaths.test(normalized.filename)) ||\n // Now we check for fun, if the function name is Raven or TraceKit\n /(Raven|TraceKit)\\./.test(normalized['function']) ||\n // finally, we do a last ditch effort and check for raven.min.js\n /raven\\.(min\\.)?js$/.test(normalized.filename)\n );\n\n return normalized;\n },\n\n _processException: function(type, message, fileurl, lineno, frames, options) {\n var prefixedMessage = (type ? type + ': ' : '') + (message || '');\n if (\n !!this._globalOptions.ignoreErrors.test &&\n (this._globalOptions.ignoreErrors.test(message) ||\n this._globalOptions.ignoreErrors.test(prefixedMessage))\n ) {\n return;\n }\n\n var stacktrace;\n\n if (frames && frames.length) {\n fileurl = frames[0].filename || fileurl;\n // Sentry expects frames oldest to newest\n // and JS sends them as newest to oldest\n frames.reverse();\n stacktrace = {frames: frames};\n } else if (fileurl) {\n stacktrace = {\n frames: [\n {\n filename: fileurl,\n lineno: lineno,\n in_app: true\n }\n ]\n };\n }\n\n if (\n !!this._globalOptions.ignoreUrls.test &&\n this._globalOptions.ignoreUrls.test(fileurl)\n ) {\n return;\n }\n\n if (\n !!this._globalOptions.whitelistUrls.test &&\n !this._globalOptions.whitelistUrls.test(fileurl)\n ) {\n return;\n }\n\n var data = objectMerge(\n {\n // sentry.interfaces.Exception\n exception: {\n values: [\n {\n type: type,\n value: message,\n stacktrace: stacktrace\n }\n ]\n },\n culprit: fileurl\n },\n options\n );\n\n // Fire away!\n this._send(data);\n },\n\n _trimPacket: function(data) {\n // For now, we only want to truncate the two different messages\n // but this could/should be expanded to just trim everything\n var max = this._globalOptions.maxMessageLength;\n if (data.message) {\n data.message = truncate(data.message, max);\n }\n if (data.exception) {\n var exception = data.exception.values[0];\n exception.value = truncate(exception.value, max);\n }\n\n var request = data.request;\n if (request) {\n if (request.url) {\n request.url = truncate(request.url, this._globalOptions.maxUrlLength);\n }\n if (request.Referer) {\n request.Referer = truncate(request.Referer, this._globalOptions.maxUrlLength);\n }\n }\n\n if (data.breadcrumbs && data.breadcrumbs.values)\n this._trimBreadcrumbs(data.breadcrumbs);\n\n return data;\n },\n\n /**\n * Truncate breadcrumb values (right now just URLs)\n */\n _trimBreadcrumbs: function(breadcrumbs) {\n // known breadcrumb properties with urls\n // TODO: also consider arbitrary prop values that start with (https?)?://\n var urlProps = ['to', 'from', 'url'],\n urlProp,\n crumb,\n data;\n\n for (var i = 0; i < breadcrumbs.values.length; ++i) {\n crumb = breadcrumbs.values[i];\n if (\n !crumb.hasOwnProperty('data') ||\n !isObject(crumb.data) ||\n objectFrozen(crumb.data)\n )\n continue;\n\n data = objectMerge({}, crumb.data);\n for (var j = 0; j < urlProps.length; ++j) {\n urlProp = urlProps[j];\n if (data.hasOwnProperty(urlProp) && data[urlProp]) {\n data[urlProp] = truncate(data[urlProp], this._globalOptions.maxUrlLength);\n }\n }\n breadcrumbs.values[i].data = data;\n }\n },\n\n _getHttpData: function() {\n if (!this._hasNavigator && !this._hasDocument) return;\n var httpData = {};\n\n if (this._hasNavigator && _navigator.userAgent) {\n httpData.headers = {\n 'User-Agent': navigator.userAgent\n };\n }\n\n if (this._hasDocument) {\n if (_document.location && _document.location.href) {\n httpData.url = _document.location.href;\n }\n if (_document.referrer) {\n if (!httpData.headers) httpData.headers = {};\n httpData.headers.Referer = _document.referrer;\n }\n }\n\n return httpData;\n },\n\n _resetBackoff: function() {\n this._backoffDuration = 0;\n this._backoffStart = null;\n },\n\n _shouldBackoff: function() {\n return this._backoffDuration && now() - this._backoffStart < this._backoffDuration;\n },\n\n /**\n * Returns true if the in-process data payload matches the signature\n * of the previously-sent data\n *\n * NOTE: This has to be done at this level because TraceKit can generate\n * data from window.onerror WITHOUT an exception object (IE8, IE9,\n * other old browsers). This can take the form of an \"exception\"\n * data object with a single frame (derived from the onerror args).\n */\n _isRepeatData: function(current) {\n var last = this._lastData;\n\n if (\n !last ||\n current.message !== last.message || // defined for captureMessage\n current.culprit !== last.culprit // defined for captureException/onerror\n )\n return false;\n\n // Stacktrace interface (i.e. from captureMessage)\n if (current.stacktrace || last.stacktrace) {\n return isSameStacktrace(current.stacktrace, last.stacktrace);\n } else if (current.exception || last.exception) {\n // Exception interface (i.e. from captureException/onerror)\n return isSameException(current.exception, last.exception);\n }\n\n return true;\n },\n\n _setBackoffState: function(request) {\n // If we are already in a backoff state, don't change anything\n if (this._shouldBackoff()) {\n return;\n }\n\n var status = request.status;\n\n // 400 - project_id doesn't exist or some other fatal\n // 401 - invalid/revoked dsn\n // 429 - too many requests\n if (!(status === 400 || status === 401 || status === 429)) return;\n\n var retry;\n try {\n // If Retry-After is not in Access-Control-Expose-Headers, most\n // browsers will throw an exception trying to access it\n retry = request.getResponseHeader('Retry-After');\n retry = parseInt(retry, 10) * 1000; // Retry-After is returned in seconds\n } catch (e) {\n /* eslint no-empty:0 */\n }\n\n this._backoffDuration = retry\n ? // If Sentry server returned a Retry-After value, use it\n retry\n : // Otherwise, double the last backoff duration (starts at 1 sec)\n this._backoffDuration * 2 || 1000;\n\n this._backoffStart = now();\n },\n\n _send: function(data) {\n var globalOptions = this._globalOptions;\n\n var baseData = {\n project: this._globalProject,\n logger: globalOptions.logger,\n platform: 'javascript'\n },\n httpData = this._getHttpData();\n\n if (httpData) {\n baseData.request = httpData;\n }\n\n // HACK: delete `trimHeadFrames` to prevent from appearing in outbound payload\n if (data.trimHeadFrames) delete data.trimHeadFrames;\n\n data = objectMerge(baseData, data);\n\n // Merge in the tags and extra separately since objectMerge doesn't handle a deep merge\n data.tags = objectMerge(objectMerge({}, this._globalContext.tags), data.tags);\n data.extra = objectMerge(objectMerge({}, this._globalContext.extra), data.extra);\n\n // Send along our own collected metadata with extra\n data.extra['session:duration'] = now() - this._startTime;\n\n if (this._breadcrumbs && this._breadcrumbs.length > 0) {\n // intentionally make shallow copy so that additions\n // to breadcrumbs aren't accidentally sent in this request\n data.breadcrumbs = {\n values: [].slice.call(this._breadcrumbs, 0)\n };\n }\n\n // If there are no tags/extra, strip the key from the payload alltogther.\n if (isEmptyObject(data.tags)) delete data.tags;\n\n if (this._globalContext.user) {\n // sentry.interfaces.User\n data.user = this._globalContext.user;\n }\n\n // Include the environment if it's defined in globalOptions\n if (globalOptions.environment) data.environment = globalOptions.environment;\n\n // Include the release if it's defined in globalOptions\n if (globalOptions.release) data.release = globalOptions.release;\n\n // Include server_name if it's defined in globalOptions\n if (globalOptions.serverName) data.server_name = globalOptions.serverName;\n\n if (isFunction(globalOptions.dataCallback)) {\n data = globalOptions.dataCallback(data) || data;\n }\n\n // Why??????????\n if (!data || isEmptyObject(data)) {\n return;\n }\n\n // Check if the request should be filtered or not\n if (\n isFunction(globalOptions.shouldSendCallback) &&\n !globalOptions.shouldSendCallback(data)\n ) {\n return;\n }\n\n // Backoff state: Sentry server previously responded w/ an error (e.g. 429 - too many requests),\n // so drop requests until \"cool-off\" period has elapsed.\n if (this._shouldBackoff()) {\n this._logDebug('warn', 'Raven dropped error due to backoff: ', data);\n return;\n }\n\n if (typeof globalOptions.sampleRate === 'number') {\n if (Math.random() < globalOptions.sampleRate) {\n this._sendProcessedPayload(data);\n }\n } else {\n this._sendProcessedPayload(data);\n }\n },\n\n _getUuid: function() {\n return uuid4();\n },\n\n _sendProcessedPayload: function(data, callback) {\n var self = this;\n var globalOptions = this._globalOptions;\n\n if (!this.isSetup()) return;\n\n // Try and clean up the packet before sending by truncating long values\n data = this._trimPacket(data);\n\n // ideally duplicate error testing should occur *before* dataCallback/shouldSendCallback,\n // but this would require copying an un-truncated copy of the data packet, which can be\n // arbitrarily deep (extra_data) -- could be worthwhile? will revisit\n if (!this._globalOptions.allowDuplicates && this._isRepeatData(data)) {\n this._logDebug('warn', 'Raven dropped repeat event: ', data);\n return;\n }\n\n // Send along an event_id if not explicitly passed.\n // This event_id can be used to reference the error within Sentry itself.\n // Set lastEventId after we know the error should actually be sent\n this._lastEventId = data.event_id || (data.event_id = this._getUuid());\n\n // Store outbound payload after trim\n this._lastData = data;\n\n this._logDebug('debug', 'Raven about to send:', data);\n\n var auth = {\n sentry_version: '7',\n sentry_client: 'raven-js/' + this.VERSION,\n sentry_key: this._globalKey\n };\n\n if (this._globalSecret) {\n auth.sentry_secret = this._globalSecret;\n }\n\n var exception = data.exception && data.exception.values[0];\n this.captureBreadcrumb({\n category: 'sentry',\n message: exception\n ? (exception.type ? exception.type + ': ' : '') + exception.value\n : data.message,\n event_id: data.event_id,\n level: data.level || 'error' // presume error unless specified\n });\n\n var url = this._globalEndpoint;\n (globalOptions.transport || this._makeRequest).call(this, {\n url: url,\n auth: auth,\n data: data,\n options: globalOptions,\n onSuccess: function success() {\n self._resetBackoff();\n\n self._triggerEvent('success', {\n data: data,\n src: url\n });\n callback && callback();\n },\n onError: function failure(error) {\n self._logDebug('error', 'Raven transport failed to send: ', error);\n\n if (error.request) {\n self._setBackoffState(error.request);\n }\n\n self._triggerEvent('failure', {\n data: data,\n src: url\n });\n error = error || new Error('Raven send failed (no additional details provided)');\n callback && callback(error);\n }\n });\n },\n\n _makeRequest: function(opts) {\n var request = _window.XMLHttpRequest && new _window.XMLHttpRequest();\n if (!request) return;\n\n // if browser doesn't support CORS (e.g. IE7), we are out of luck\n var hasCORS = 'withCredentials' in request || typeof XDomainRequest !== 'undefined';\n\n if (!hasCORS) return;\n\n var url = opts.url;\n\n if ('withCredentials' in request) {\n request.onreadystatechange = function() {\n if (request.readyState !== 4) {\n return;\n } else if (request.status === 200) {\n opts.onSuccess && opts.onSuccess();\n } else if (opts.onError) {\n var err = new Error('Sentry error code: ' + request.status);\n err.request = request;\n opts.onError(err);\n }\n };\n } else {\n request = new XDomainRequest();\n // xdomainrequest cannot go http -> https (or vice versa),\n // so always use protocol relative\n url = url.replace(/^https?:/, '');\n\n // onreadystatechange not supported by XDomainRequest\n if (opts.onSuccess) {\n request.onload = opts.onSuccess;\n }\n if (opts.onError) {\n request.onerror = function() {\n var err = new Error('Sentry error code: XDomainRequest');\n err.request = request;\n opts.onError(err);\n };\n }\n }\n\n // NOTE: auth is intentionally sent as part of query string (NOT as custom\n // HTTP header) so as to avoid preflight CORS requests\n request.open('POST', url + '?' + urlencode(opts.auth));\n request.send(stringify(opts.data));\n },\n\n _logDebug: function(level) {\n if (this._originalConsoleMethods[level] && this.debug) {\n // In IE<10 console methods do not have their own 'apply' method\n Function.prototype.apply.call(\n this._originalConsoleMethods[level],\n this._originalConsole,\n [].slice.call(arguments, 1)\n );\n }\n },\n\n _mergeContext: function(key, context) {\n if (isUndefined(context)) {\n delete this._globalContext[key];\n } else {\n this._globalContext[key] = objectMerge(this._globalContext[key] || {}, context);\n }\n }\n};\n\n// Deprecations\nRaven.prototype.setUser = Raven.prototype.setUserContext;\nRaven.prototype.setReleaseContext = Raven.prototype.setRelease;\n\nmodule.exports = Raven;\n","/**\n * Enforces a single instance of the Raven client, and the\n * main entry point for Raven. If you are a consumer of the\n * Raven library, you SHOULD load this file (vs raven.js).\n **/\n\nvar RavenConstructor = require('./raven');\n\n// This is to be defensive in environments where window does not exist (see https://github.com/getsentry/raven-js/pull/785)\nvar _window =\n typeof window !== 'undefined'\n ? window\n : typeof global !== 'undefined' ? global : typeof self !== 'undefined' ? self : {};\nvar _Raven = _window.Raven;\n\nvar Raven = new RavenConstructor();\n\n/*\n * Allow multiple versions of Raven to be installed.\n * Strip Raven from the global context and returns the instance.\n *\n * @return {Raven}\n */\nRaven.noConflict = function() {\n _window.Raven = _Raven;\n return Raven;\n};\n\nRaven.afterLoad();\n\nmodule.exports = Raven;\n","var _window =\n typeof window !== 'undefined'\n ? window\n : typeof global !== 'undefined' ? global : typeof self !== 'undefined' ? self : {};\n\nfunction isObject(what) {\n return typeof what === 'object' && what !== null;\n}\n\n// Yanked from https://git.io/vS8DV re-used under CC0\n// with some tiny modifications\nfunction isError(value) {\n switch ({}.toString.call(value)) {\n case '[object Error]':\n return true;\n case '[object Exception]':\n return true;\n case '[object DOMException]':\n return true;\n default:\n return value instanceof Error;\n }\n}\n\nfunction isErrorEvent(value) {\n return supportsErrorEvent() && {}.toString.call(value) === '[object ErrorEvent]';\n}\n\nfunction isUndefined(what) {\n return what === void 0;\n}\n\nfunction isFunction(what) {\n return typeof what === 'function';\n}\n\nfunction isString(what) {\n return Object.prototype.toString.call(what) === '[object String]';\n}\n\nfunction isEmptyObject(what) {\n for (var _ in what) return false; // eslint-disable-line guard-for-in, no-unused-vars\n return true;\n}\n\nfunction supportsErrorEvent() {\n try {\n new ErrorEvent(''); // eslint-disable-line no-new\n return true;\n } catch (e) {\n return false;\n }\n}\n\nfunction wrappedCallback(callback) {\n function dataCallback(data, original) {\n var normalizedData = callback(data) || data;\n if (original) {\n return original(normalizedData) || normalizedData;\n }\n return normalizedData;\n }\n\n return dataCallback;\n}\n\nfunction each(obj, callback) {\n var i, j;\n\n if (isUndefined(obj.length)) {\n for (i in obj) {\n if (hasKey(obj, i)) {\n callback.call(null, i, obj[i]);\n }\n }\n } else {\n j = obj.length;\n if (j) {\n for (i = 0; i < j; i++) {\n callback.call(null, i, obj[i]);\n }\n }\n }\n}\n\nfunction objectMerge(obj1, obj2) {\n if (!obj2) {\n return obj1;\n }\n each(obj2, function(key, value) {\n obj1[key] = value;\n });\n return obj1;\n}\n\n/**\n * This function is only used for react-native.\n * react-native freezes object that have already been sent over the\n * js bridge. We need this function in order to check if the object is frozen.\n * So it's ok that objectFrozen returns false if Object.isFrozen is not\n * supported because it's not relevant for other \"platforms\". See related issue:\n * https://github.com/getsentry/react-native-sentry/issues/57\n */\nfunction objectFrozen(obj) {\n if (!Object.isFrozen) {\n return false;\n }\n return Object.isFrozen(obj);\n}\n\nfunction truncate(str, max) {\n return !max || str.length <= max ? str : str.substr(0, max) + '\\u2026';\n}\n\n/**\n * hasKey, a better form of hasOwnProperty\n * Example: hasKey(MainHostObject, property) === true/false\n *\n * @param {Object} host object to check property\n * @param {string} key to check\n */\nfunction hasKey(object, key) {\n return Object.prototype.hasOwnProperty.call(object, key);\n}\n\nfunction joinRegExp(patterns) {\n // Combine an array of regular expressions and strings into one large regexp\n // Be mad.\n var sources = [],\n i = 0,\n len = patterns.length,\n pattern;\n\n for (; i < len; i++) {\n pattern = patterns[i];\n if (isString(pattern)) {\n // If it's a string, we need to escape it\n // Taken from: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Guide/Regular_Expressions\n sources.push(pattern.replace(/([.*+?^=!:${}()|\\[\\]\\/\\\\])/g, '\\\\$1'));\n } else if (pattern && pattern.source) {\n // If it's a regexp already, we want to extract the source\n sources.push(pattern.source);\n }\n // Intentionally skip other cases\n }\n return new RegExp(sources.join('|'), 'i');\n}\n\nfunction urlencode(o) {\n var pairs = [];\n each(o, function(key, value) {\n pairs.push(encodeURIComponent(key) + '=' + encodeURIComponent(value));\n });\n return pairs.join('&');\n}\n\n// borrowed from https://tools.ietf.org/html/rfc3986#appendix-B\n// intentionally using regex and not href parsing trick because React Native and other\n// environments where DOM might not be available\nfunction parseUrl(url) {\n var match = url.match(/^(([^:\\/?#]+):)?(\\/\\/([^\\/?#]*))?([^?#]*)(\\?([^#]*))?(#(.*))?$/);\n if (!match) return {};\n\n // coerce to undefined values to empty string so we don't get 'undefined'\n var query = match[6] || '';\n var fragment = match[8] || '';\n return {\n protocol: match[2],\n host: match[4],\n path: match[5],\n relative: match[5] + query + fragment // everything minus origin\n };\n}\nfunction uuid4() {\n var crypto = _window.crypto || _window.msCrypto;\n\n if (!isUndefined(crypto) && crypto.getRandomValues) {\n // Use window.crypto API if available\n // eslint-disable-next-line no-undef\n var arr = new Uint16Array(8);\n crypto.getRandomValues(arr);\n\n // set 4 in byte 7\n arr[3] = (arr[3] & 0xfff) | 0x4000;\n // set 2 most significant bits of byte 9 to '10'\n arr[4] = (arr[4] & 0x3fff) | 0x8000;\n\n var pad = function(num) {\n var v = num.toString(16);\n while (v.length < 4) {\n v = '0' + v;\n }\n return v;\n };\n\n return (\n pad(arr[0]) +\n pad(arr[1]) +\n pad(arr[2]) +\n pad(arr[3]) +\n pad(arr[4]) +\n pad(arr[5]) +\n pad(arr[6]) +\n pad(arr[7])\n );\n } else {\n // http://stackoverflow.com/questions/105034/how-to-create-a-guid-uuid-in-javascript/2117523#2117523\n return 'xxxxxxxxxxxx4xxxyxxxxxxxxxxxxxxx'.replace(/[xy]/g, function(c) {\n var r = (Math.random() * 16) | 0,\n v = c === 'x' ? r : (r & 0x3) | 0x8;\n return v.toString(16);\n });\n }\n}\n\n/**\n * Given a child DOM element, returns a query-selector statement describing that\n * and its ancestors\n * e.g. [HTMLElement] => body > div > input#foo.btn[name=baz]\n * @param elem\n * @returns {string}\n */\nfunction htmlTreeAsString(elem) {\n /* eslint no-extra-parens:0*/\n var MAX_TRAVERSE_HEIGHT = 5,\n MAX_OUTPUT_LEN = 80,\n out = [],\n height = 0,\n len = 0,\n separator = ' > ',\n sepLength = separator.length,\n nextStr;\n\n while (elem && height++ < MAX_TRAVERSE_HEIGHT) {\n nextStr = htmlElementAsString(elem);\n // bail out if\n // - nextStr is the 'html' element\n // - the length of the string that would be created exceeds MAX_OUTPUT_LEN\n // (ignore this limit if we are on the first iteration)\n if (\n nextStr === 'html' ||\n (height > 1 && len + out.length * sepLength + nextStr.length >= MAX_OUTPUT_LEN)\n ) {\n break;\n }\n\n out.push(nextStr);\n\n len += nextStr.length;\n elem = elem.parentNode;\n }\n\n return out.reverse().join(separator);\n}\n\n/**\n * Returns a simple, query-selector representation of a DOM element\n * e.g. [HTMLElement] => input#foo.btn[name=baz]\n * @param HTMLElement\n * @returns {string}\n */\nfunction htmlElementAsString(elem) {\n var out = [],\n className,\n classes,\n key,\n attr,\n i;\n\n if (!elem || !elem.tagName) {\n return '';\n }\n\n out.push(elem.tagName.toLowerCase());\n if (elem.id) {\n out.push('#' + elem.id);\n }\n\n className = elem.className;\n if (className && isString(className)) {\n classes = className.split(/\\s+/);\n for (i = 0; i < classes.length; i++) {\n out.push('.' + classes[i]);\n }\n }\n var attrWhitelist = ['type', 'name', 'title', 'alt'];\n for (i = 0; i < attrWhitelist.length; i++) {\n key = attrWhitelist[i];\n attr = elem.getAttribute(key);\n if (attr) {\n out.push('[' + key + '=\"' + attr + '\"]');\n }\n }\n return out.join('');\n}\n\n/**\n * Returns true if either a OR b is truthy, but not both\n */\nfunction isOnlyOneTruthy(a, b) {\n return !!(!!a ^ !!b);\n}\n\n/**\n * Returns true if the two input exception interfaces have the same content\n */\nfunction isSameException(ex1, ex2) {\n if (isOnlyOneTruthy(ex1, ex2)) return false;\n\n ex1 = ex1.values[0];\n ex2 = ex2.values[0];\n\n if (ex1.type !== ex2.type || ex1.value !== ex2.value) return false;\n\n return isSameStacktrace(ex1.stacktrace, ex2.stacktrace);\n}\n\n/**\n * Returns true if the two input stack trace interfaces have the same content\n */\nfunction isSameStacktrace(stack1, stack2) {\n if (isOnlyOneTruthy(stack1, stack2)) return false;\n\n var frames1 = stack1.frames;\n var frames2 = stack2.frames;\n\n // Exit early if frame count differs\n if (frames1.length !== frames2.length) return false;\n\n // Iterate through every frame; bail out if anything differs\n var a, b;\n for (var i = 0; i < frames1.length; i++) {\n a = frames1[i];\n b = frames2[i];\n if (\n a.filename !== b.filename ||\n a.lineno !== b.lineno ||\n a.colno !== b.colno ||\n a['function'] !== b['function']\n )\n return false;\n }\n return true;\n}\n\n/**\n * Polyfill a method\n * @param obj object e.g. `document`\n * @param name method name present on object e.g. `addEventListener`\n * @param replacement replacement function\n * @param track {optional} record instrumentation to an array\n */\nfunction fill(obj, name, replacement, track) {\n var orig = obj[name];\n obj[name] = replacement(orig);\n if (track) {\n track.push([obj, name, orig]);\n }\n}\n\nmodule.exports = {\n isObject: isObject,\n isError: isError,\n isErrorEvent: isErrorEvent,\n isUndefined: isUndefined,\n isFunction: isFunction,\n isString: isString,\n isEmptyObject: isEmptyObject,\n supportsErrorEvent: supportsErrorEvent,\n wrappedCallback: wrappedCallback,\n each: each,\n objectMerge: objectMerge,\n truncate: truncate,\n objectFrozen: objectFrozen,\n hasKey: hasKey,\n joinRegExp: joinRegExp,\n urlencode: urlencode,\n uuid4: uuid4,\n htmlTreeAsString: htmlTreeAsString,\n htmlElementAsString: htmlElementAsString,\n isSameException: isSameException,\n isSameStacktrace: isSameStacktrace,\n parseUrl: parseUrl,\n fill: fill\n};\n","var utils = require('../../src/utils');\n\n/*\n TraceKit - Cross brower stack traces\n\n This was originally forked from github.com/occ/TraceKit, but has since been\n largely re-written and is now maintained as part of raven-js. Tests for\n this are in test/vendor.\n\n MIT license\n*/\n\nvar TraceKit = {\n collectWindowErrors: true,\n debug: false\n};\n\n// This is to be defensive in environments where window does not exist (see https://github.com/getsentry/raven-js/pull/785)\nvar _window =\n typeof window !== 'undefined'\n ? window\n : typeof global !== 'undefined' ? global : typeof self !== 'undefined' ? self : {};\n\n// global reference to slice\nvar _slice = [].slice;\nvar UNKNOWN_FUNCTION = '?';\n\n// https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Error#Error_types\nvar ERROR_TYPES_RE = /^(?:[Uu]ncaught (?:exception: )?)?(?:((?:Eval|Internal|Range|Reference|Syntax|Type|URI|)Error): )?(.*)$/;\n\nfunction getLocationHref() {\n if (typeof document === 'undefined' || document.location == null) return '';\n\n return document.location.href;\n}\n\n/**\n * TraceKit.report: cross-browser processing of unhandled exceptions\n *\n * Syntax:\n * TraceKit.report.subscribe(function(stackInfo) { ... })\n * TraceKit.report.unsubscribe(function(stackInfo) { ... })\n * TraceKit.report(exception)\n * try { ...code... } catch(ex) { TraceKit.report(ex); }\n *\n * Supports:\n * - Firefox: full stack trace with line numbers, plus column number\n * on top frame; column number is not guaranteed\n * - Opera: full stack trace with line and column numbers\n * - Chrome: full stack trace with line and column numbers\n * - Safari: line and column number for the top frame only; some frames\n * may be missing, and column number is not guaranteed\n * - IE: line and column number for the top frame only; some frames\n * may be missing, and column number is not guaranteed\n *\n * In theory, TraceKit should work on all of the following versions:\n * - IE5.5+ (only 8.0 tested)\n * - Firefox 0.9+ (only 3.5+ tested)\n * - Opera 7+ (only 10.50 tested; versions 9 and earlier may require\n * Exceptions Have Stacktrace to be enabled in opera:config)\n * - Safari 3+ (only 4+ tested)\n * - Chrome 1+ (only 5+ tested)\n * - Konqueror 3.5+ (untested)\n *\n * Requires TraceKit.computeStackTrace.\n *\n * Tries to catch all unhandled exceptions and report them to the\n * subscribed handlers. Please note that TraceKit.report will rethrow the\n * exception. This is REQUIRED in order to get a useful stack trace in IE.\n * If the exception does not reach the top of the browser, you will only\n * get a stack trace from the point where TraceKit.report was called.\n *\n * Handlers receive a stackInfo object as described in the\n * TraceKit.computeStackTrace docs.\n */\nTraceKit.report = (function reportModuleWrapper() {\n var handlers = [],\n lastArgs = null,\n lastException = null,\n lastExceptionStack = null;\n\n /**\n * Add a crash handler.\n * @param {Function} handler\n */\n function subscribe(handler) {\n installGlobalHandler();\n handlers.push(handler);\n }\n\n /**\n * Remove a crash handler.\n * @param {Function} handler\n */\n function unsubscribe(handler) {\n for (var i = handlers.length - 1; i >= 0; --i) {\n if (handlers[i] === handler) {\n handlers.splice(i, 1);\n }\n }\n }\n\n /**\n * Remove all crash handlers.\n */\n function unsubscribeAll() {\n uninstallGlobalHandler();\n handlers = [];\n }\n\n /**\n * Dispatch stack information to all handlers.\n * @param {Object.} stack\n */\n function notifyHandlers(stack, isWindowError) {\n var exception = null;\n if (isWindowError && !TraceKit.collectWindowErrors) {\n return;\n }\n for (var i in handlers) {\n if (handlers.hasOwnProperty(i)) {\n try {\n handlers[i].apply(null, [stack].concat(_slice.call(arguments, 2)));\n } catch (inner) {\n exception = inner;\n }\n }\n }\n\n if (exception) {\n throw exception;\n }\n }\n\n var _oldOnerrorHandler, _onErrorHandlerInstalled;\n\n /**\n * Ensures all global unhandled exceptions are recorded.\n * Supported by Gecko and IE.\n * @param {string} message Error message.\n * @param {string} url URL of script that generated the exception.\n * @param {(number|string)} lineNo The line number at which the error\n * occurred.\n * @param {?(number|string)} colNo The column number at which the error\n * occurred.\n * @param {?Error} ex The actual Error object.\n */\n function traceKitWindowOnError(message, url, lineNo, colNo, ex) {\n var stack = null;\n\n if (lastExceptionStack) {\n TraceKit.computeStackTrace.augmentStackTraceWithInitialElement(\n lastExceptionStack,\n url,\n lineNo,\n message\n );\n processLastException();\n } else if (ex && utils.isError(ex)) {\n // non-string `ex` arg; attempt to extract stack trace\n\n // New chrome and blink send along a real error object\n // Let's just report that like a normal error.\n // See: https://mikewest.org/2013/08/debugging-runtime-errors-with-window-onerror\n stack = TraceKit.computeStackTrace(ex);\n notifyHandlers(stack, true);\n } else {\n var location = {\n url: url,\n line: lineNo,\n column: colNo\n };\n\n var name = undefined;\n var msg = message; // must be new var or will modify original `arguments`\n var groups;\n if ({}.toString.call(message) === '[object String]') {\n var groups = message.match(ERROR_TYPES_RE);\n if (groups) {\n name = groups[1];\n msg = groups[2];\n }\n }\n\n location.func = UNKNOWN_FUNCTION;\n\n stack = {\n name: name,\n message: msg,\n url: getLocationHref(),\n stack: [location]\n };\n notifyHandlers(stack, true);\n }\n\n if (_oldOnerrorHandler) {\n return _oldOnerrorHandler.apply(this, arguments);\n }\n\n return false;\n }\n\n function installGlobalHandler() {\n if (_onErrorHandlerInstalled) {\n return;\n }\n _oldOnerrorHandler = _window.onerror;\n _window.onerror = traceKitWindowOnError;\n _onErrorHandlerInstalled = true;\n }\n\n function uninstallGlobalHandler() {\n if (!_onErrorHandlerInstalled) {\n return;\n }\n _window.onerror = _oldOnerrorHandler;\n _onErrorHandlerInstalled = false;\n _oldOnerrorHandler = undefined;\n }\n\n function processLastException() {\n var _lastExceptionStack = lastExceptionStack,\n _lastArgs = lastArgs;\n lastArgs = null;\n lastExceptionStack = null;\n lastException = null;\n notifyHandlers.apply(null, [_lastExceptionStack, false].concat(_lastArgs));\n }\n\n /**\n * Reports an unhandled Error to TraceKit.\n * @param {Error} ex\n * @param {?boolean} rethrow If false, do not re-throw the exception.\n * Only used for window.onerror to not cause an infinite loop of\n * rethrowing.\n */\n function report(ex, rethrow) {\n var args = _slice.call(arguments, 1);\n if (lastExceptionStack) {\n if (lastException === ex) {\n return; // already caught by an inner catch block, ignore\n } else {\n processLastException();\n }\n }\n\n var stack = TraceKit.computeStackTrace(ex);\n lastExceptionStack = stack;\n lastException = ex;\n lastArgs = args;\n\n // If the stack trace is incomplete, wait for 2 seconds for\n // slow slow IE to see if onerror occurs or not before reporting\n // this exception; otherwise, we will end up with an incomplete\n // stack trace\n setTimeout(function() {\n if (lastException === ex) {\n processLastException();\n }\n }, stack.incomplete ? 2000 : 0);\n\n if (rethrow !== false) {\n throw ex; // re-throw to propagate to the top level (and cause window.onerror)\n }\n }\n\n report.subscribe = subscribe;\n report.unsubscribe = unsubscribe;\n report.uninstall = unsubscribeAll;\n return report;\n})();\n\n/**\n * TraceKit.computeStackTrace: cross-browser stack traces in JavaScript\n *\n * Syntax:\n * s = TraceKit.computeStackTrace(exception) // consider using TraceKit.report instead (see below)\n * Returns:\n * s.name - exception name\n * s.message - exception message\n * s.stack[i].url - JavaScript or HTML file URL\n * s.stack[i].func - function name, or empty for anonymous functions (if guessing did not work)\n * s.stack[i].args - arguments passed to the function, if known\n * s.stack[i].line - line number, if known\n * s.stack[i].column - column number, if known\n *\n * Supports:\n * - Firefox: full stack trace with line numbers and unreliable column\n * number on top frame\n * - Opera 10: full stack trace with line and column numbers\n * - Opera 9-: full stack trace with line numbers\n * - Chrome: full stack trace with line and column numbers\n * - Safari: line and column number for the topmost stacktrace element\n * only\n * - IE: no line numbers whatsoever\n *\n * Tries to guess names of anonymous functions by looking for assignments\n * in the source code. In IE and Safari, we have to guess source file names\n * by searching for function bodies inside all page scripts. This will not\n * work for scripts that are loaded cross-domain.\n * Here be dragons: some function names may be guessed incorrectly, and\n * duplicate functions may be mismatched.\n *\n * TraceKit.computeStackTrace should only be used for tracing purposes.\n * Logging of unhandled exceptions should be done with TraceKit.report,\n * which builds on top of TraceKit.computeStackTrace and provides better\n * IE support by utilizing the window.onerror event to retrieve information\n * about the top of the stack.\n *\n * Note: In IE and Safari, no stack trace is recorded on the Error object,\n * so computeStackTrace instead walks its *own* chain of callers.\n * This means that:\n * * in Safari, some methods may be missing from the stack trace;\n * * in IE, the topmost function in the stack trace will always be the\n * caller of computeStackTrace.\n *\n * This is okay for tracing (because you are likely to be calling\n * computeStackTrace from the function you want to be the topmost element\n * of the stack trace anyway), but not okay for logging unhandled\n * exceptions (because your catch block will likely be far away from the\n * inner function that actually caused the exception).\n *\n */\nTraceKit.computeStackTrace = (function computeStackTraceWrapper() {\n // Contents of Exception in various browsers.\n //\n // SAFARI:\n // ex.message = Can't find variable: qq\n // ex.line = 59\n // ex.sourceId = 580238192\n // ex.sourceURL = http://...\n // ex.expressionBeginOffset = 96\n // ex.expressionCaretOffset = 98\n // ex.expressionEndOffset = 98\n // ex.name = ReferenceError\n //\n // FIREFOX:\n // ex.message = qq is not defined\n // ex.fileName = http://...\n // ex.lineNumber = 59\n // ex.columnNumber = 69\n // ex.stack = ...stack trace... (see the example below)\n // ex.name = ReferenceError\n //\n // CHROME:\n // ex.message = qq is not defined\n // ex.name = ReferenceError\n // ex.type = not_defined\n // ex.arguments = ['aa']\n // ex.stack = ...stack trace...\n //\n // INTERNET EXPLORER:\n // ex.message = ...\n // ex.name = ReferenceError\n //\n // OPERA:\n // ex.message = ...message... (see the example below)\n // ex.name = ReferenceError\n // ex.opera#sourceloc = 11 (pretty much useless, duplicates the info in ex.message)\n // ex.stacktrace = n/a; see 'opera:config#UserPrefs|Exceptions Have Stacktrace'\n\n /**\n * Computes stack trace information from the stack property.\n * Chrome and Gecko use this property.\n * @param {Error} ex\n * @return {?Object.} Stack trace information.\n */\n function computeStackTraceFromStackProp(ex) {\n if (typeof ex.stack === 'undefined' || !ex.stack) return;\n\n var chrome = /^\\s*at (.*?) ?\\(((?:file|https?|blob|chrome-extension|native|eval|webpack||[a-z]:|\\/).*?)(?::(\\d+))?(?::(\\d+))?\\)?\\s*$/i,\n gecko = /^\\s*(.*?)(?:\\((.*?)\\))?(?:^|@)((?:file|https?|blob|chrome|webpack|resource|\\[native).*?|[^@]*bundle)(?::(\\d+))?(?::(\\d+))?\\s*$/i,\n winjs = /^\\s*at (?:((?:\\[object object\\])?.+) )?\\(?((?:file|ms-appx|https?|webpack|blob):.*?):(\\d+)(?::(\\d+))?\\)?\\s*$/i,\n // Used to additionally parse URL/line/column from eval frames\n geckoEval = /(\\S+) line (\\d+)(?: > eval line \\d+)* > eval/i,\n chromeEval = /\\((\\S*)(?::(\\d+))(?::(\\d+))\\)/,\n lines = ex.stack.split('\\n'),\n stack = [],\n submatch,\n parts,\n element,\n reference = /^(.*) is undefined$/.exec(ex.message);\n\n for (var i = 0, j = lines.length; i < j; ++i) {\n if ((parts = chrome.exec(lines[i]))) {\n var isNative = parts[2] && parts[2].indexOf('native') === 0; // start of line\n var isEval = parts[2] && parts[2].indexOf('eval') === 0; // start of line\n if (isEval && (submatch = chromeEval.exec(parts[2]))) {\n // throw out eval line/column and use top-most line/column number\n parts[2] = submatch[1]; // url\n parts[3] = submatch[2]; // line\n parts[4] = submatch[3]; // column\n }\n element = {\n url: !isNative ? parts[2] : null,\n func: parts[1] || UNKNOWN_FUNCTION,\n args: isNative ? [parts[2]] : [],\n line: parts[3] ? +parts[3] : null,\n column: parts[4] ? +parts[4] : null\n };\n } else if ((parts = winjs.exec(lines[i]))) {\n element = {\n url: parts[2],\n func: parts[1] || UNKNOWN_FUNCTION,\n args: [],\n line: +parts[3],\n column: parts[4] ? +parts[4] : null\n };\n } else if ((parts = gecko.exec(lines[i]))) {\n var isEval = parts[3] && parts[3].indexOf(' > eval') > -1;\n if (isEval && (submatch = geckoEval.exec(parts[3]))) {\n // throw out eval line/column and use top-most line number\n parts[3] = submatch[1];\n parts[4] = submatch[2];\n parts[5] = null; // no column when eval\n } else if (i === 0 && !parts[5] && typeof ex.columnNumber !== 'undefined') {\n // FireFox uses this awesome columnNumber property for its top frame\n // Also note, Firefox's column number is 0-based and everything else expects 1-based,\n // so adding 1\n // NOTE: this hack doesn't work if top-most frame is eval\n stack[0].column = ex.columnNumber + 1;\n }\n element = {\n url: parts[3],\n func: parts[1] || UNKNOWN_FUNCTION,\n args: parts[2] ? parts[2].split(',') : [],\n line: parts[4] ? +parts[4] : null,\n column: parts[5] ? +parts[5] : null\n };\n } else {\n continue;\n }\n\n if (!element.func && element.line) {\n element.func = UNKNOWN_FUNCTION;\n }\n\n stack.push(element);\n }\n\n if (!stack.length) {\n return null;\n }\n\n return {\n name: ex.name,\n message: ex.message,\n url: getLocationHref(),\n stack: stack\n };\n }\n\n /**\n * Adds information about the first frame to incomplete stack traces.\n * Safari and IE require this to get complete data on the first frame.\n * @param {Object.} stackInfo Stack trace information from\n * one of the compute* methods.\n * @param {string} url The URL of the script that caused an error.\n * @param {(number|string)} lineNo The line number of the script that\n * caused an error.\n * @param {string=} message The error generated by the browser, which\n * hopefully contains the name of the object that caused the error.\n * @return {boolean} Whether or not the stack information was\n * augmented.\n */\n function augmentStackTraceWithInitialElement(stackInfo, url, lineNo, message) {\n var initial = {\n url: url,\n line: lineNo\n };\n\n if (initial.url && initial.line) {\n stackInfo.incomplete = false;\n\n if (!initial.func) {\n initial.func = UNKNOWN_FUNCTION;\n }\n\n if (stackInfo.stack.length > 0) {\n if (stackInfo.stack[0].url === initial.url) {\n if (stackInfo.stack[0].line === initial.line) {\n return false; // already in stack trace\n } else if (\n !stackInfo.stack[0].line &&\n stackInfo.stack[0].func === initial.func\n ) {\n stackInfo.stack[0].line = initial.line;\n return false;\n }\n }\n }\n\n stackInfo.stack.unshift(initial);\n stackInfo.partial = true;\n return true;\n } else {\n stackInfo.incomplete = true;\n }\n\n return false;\n }\n\n /**\n * Computes stack trace information by walking the arguments.caller\n * chain at the time the exception occurred. This will cause earlier\n * frames to be missed but is the only way to get any stack trace in\n * Safari and IE. The top frame is restored by\n * {@link augmentStackTraceWithInitialElement}.\n * @param {Error} ex\n * @return {?Object.} Stack trace information.\n */\n function computeStackTraceByWalkingCallerChain(ex, depth) {\n var functionName = /function\\s+([_$a-zA-Z\\xA0-\\uFFFF][_$a-zA-Z0-9\\xA0-\\uFFFF]*)?\\s*\\(/i,\n stack = [],\n funcs = {},\n recursion = false,\n parts,\n item,\n source;\n\n for (\n var curr = computeStackTraceByWalkingCallerChain.caller;\n curr && !recursion;\n curr = curr.caller\n ) {\n if (curr === computeStackTrace || curr === TraceKit.report) {\n // console.log('skipping internal function');\n continue;\n }\n\n item = {\n url: null,\n func: UNKNOWN_FUNCTION,\n line: null,\n column: null\n };\n\n if (curr.name) {\n item.func = curr.name;\n } else if ((parts = functionName.exec(curr.toString()))) {\n item.func = parts[1];\n }\n\n if (typeof item.func === 'undefined') {\n try {\n item.func = parts.input.substring(0, parts.input.indexOf('{'));\n } catch (e) {}\n }\n\n if (funcs['' + curr]) {\n recursion = true;\n } else {\n funcs['' + curr] = true;\n }\n\n stack.push(item);\n }\n\n if (depth) {\n // console.log('depth is ' + depth);\n // console.log('stack is ' + stack.length);\n stack.splice(0, depth);\n }\n\n var result = {\n name: ex.name,\n message: ex.message,\n url: getLocationHref(),\n stack: stack\n };\n augmentStackTraceWithInitialElement(\n result,\n ex.sourceURL || ex.fileName,\n ex.line || ex.lineNumber,\n ex.message || ex.description\n );\n return result;\n }\n\n /**\n * Computes a stack trace for an exception.\n * @param {Error} ex\n * @param {(string|number)=} depth\n */\n function computeStackTrace(ex, depth) {\n var stack = null;\n depth = depth == null ? 0 : +depth;\n\n try {\n stack = computeStackTraceFromStackProp(ex);\n if (stack) {\n return stack;\n }\n } catch (e) {\n if (TraceKit.debug) {\n throw e;\n }\n }\n\n try {\n stack = computeStackTraceByWalkingCallerChain(ex, depth + 1);\n if (stack) {\n return stack;\n }\n } catch (e) {\n if (TraceKit.debug) {\n throw e;\n }\n }\n return {\n name: ex.name,\n message: ex.message,\n url: getLocationHref()\n };\n }\n\n computeStackTrace.augmentStackTraceWithInitialElement = augmentStackTraceWithInitialElement;\n computeStackTrace.computeStackTraceFromStackProp = computeStackTraceFromStackProp;\n\n return computeStackTrace;\n})();\n\nmodule.exports = TraceKit;\n","/*\n json-stringify-safe\n Like JSON.stringify, but doesn't throw on circular references.\n\n Originally forked from https://github.com/isaacs/json-stringify-safe\n version 5.0.1 on 3/8/2017 and modified to handle Errors serialization\n and IE8 compatibility. Tests for this are in test/vendor.\n\n ISC license: https://github.com/isaacs/json-stringify-safe/blob/master/LICENSE\n*/\n\nexports = module.exports = stringify;\nexports.getSerialize = serializer;\n\nfunction indexOf(haystack, needle) {\n for (var i = 0; i < haystack.length; ++i) {\n if (haystack[i] === needle) return i;\n }\n return -1;\n}\n\nfunction stringify(obj, replacer, spaces, cycleReplacer) {\n return JSON.stringify(obj, serializer(replacer, cycleReplacer), spaces);\n}\n\n// https://github.com/ftlabs/js-abbreviate/blob/fa709e5f139e7770a71827b1893f22418097fbda/index.js#L95-L106\nfunction stringifyError(value) {\n var err = {\n // These properties are implemented as magical getters and don't show up in for in\n stack: value.stack,\n message: value.message,\n name: value.name\n };\n\n for (var i in value) {\n if (Object.prototype.hasOwnProperty.call(value, i)) {\n err[i] = value[i];\n }\n }\n\n return err;\n}\n\nfunction serializer(replacer, cycleReplacer) {\n var stack = [];\n var keys = [];\n\n if (cycleReplacer == null) {\n cycleReplacer = function(key, value) {\n if (stack[0] === value) {\n return '[Circular ~]';\n }\n return '[Circular ~.' + keys.slice(0, indexOf(stack, value)).join('.') + ']';\n };\n }\n\n return function(key, value) {\n if (stack.length > 0) {\n var thisPos = indexOf(stack, this);\n ~thisPos ? stack.splice(thisPos + 1) : stack.push(this);\n ~thisPos ? keys.splice(thisPos, Infinity, key) : keys.push(key);\n\n if (~indexOf(stack, value)) {\n value = cycleReplacer.call(this, key, value);\n }\n } else {\n stack.push(value);\n }\n\n return replacer == null\n ? value instanceof Error ? stringifyError(value) : value\n : replacer.call(this, key, value);\n };\n}\n","module.exports = window[\"jQuery\"];","// The module cache\nvar __webpack_module_cache__ = {};\n\n// The require function\nfunction __webpack_require__(moduleId) {\n\t// Check if module is in cache\n\tvar cachedModule = __webpack_module_cache__[moduleId];\n\tif (cachedModule !== undefined) {\n\t\treturn cachedModule.exports;\n\t}\n\t// Create a new module (and put it into the cache)\n\tvar module = __webpack_module_cache__[moduleId] = {\n\t\t// no module.id needed\n\t\t// no module.loaded needed\n\t\texports: {}\n\t};\n\n\t// Execute the module function\n\t__webpack_modules__[moduleId](module, module.exports, __webpack_require__);\n\n\t// Return the exports of the module\n\treturn module.exports;\n}\n\n","// getDefaultExport function for compatibility with non-harmony modules\n__webpack_require__.n = (module) => {\n\tvar getter = module && module.__esModule ?\n\t\t() => (module['default']) :\n\t\t() => (module);\n\t__webpack_require__.d(getter, { a: getter });\n\treturn getter;\n};","// define getter functions for harmony exports\n__webpack_require__.d = (exports, definition) => {\n\tfor(var key in definition) {\n\t\tif(__webpack_require__.o(definition, key) && !__webpack_require__.o(exports, key)) {\n\t\t\tObject.defineProperty(exports, key, { enumerable: true, get: definition[key] });\n\t\t}\n\t}\n};","__webpack_require__.g = (function() {\n\tif (typeof globalThis === 'object') return globalThis;\n\ttry {\n\t\treturn this || new Function('return this')();\n\t} catch (e) {\n\t\tif (typeof window === 'object') return window;\n\t}\n})();","__webpack_require__.o = (obj, prop) => (Object.prototype.hasOwnProperty.call(obj, prop))","// define __esModule on exports\n__webpack_require__.r = (exports) => {\n\tif(typeof Symbol !== 'undefined' && Symbol.toStringTag) {\n\t\tObject.defineProperty(exports, Symbol.toStringTag, { value: 'Module' });\n\t}\n\tObject.defineProperty(exports, '__esModule', { value: true });\n};","import $ from 'jquery';\nimport Raven from '../lib/Raven';\nimport { domElements } from '../constants/selectors';\nimport ThickBoxModal from '../feedback/ThickBoxModal';\nimport { submitFeedbackForm } from '../feedback/feedbackFormApi';\nimport { getOrCreateBackgroundApp, initBackgroundApp, } from '../utils/backgroundAppUtils';\nimport { refreshToken } from '../constants/leadinConfig';\nimport { ProxyMessages } from '../iframe/integratedMessages';\nfunction deactivatePlugin() {\n const href = $(domElements.deactivatePluginButton).attr('href');\n if (href) {\n window.location.href = href;\n }\n}\nfunction setLoadingState() {\n $(domElements.deactivateFeedbackSubmit).addClass('loading');\n}\nfunction submitAndDeactivate(e) {\n e.preventDefault();\n setLoadingState();\n const feedback = $(domElements.deactivateFeedbackForm)\n .serializeArray()\n .find(field => field.name === 'feedback');\n submitFeedbackForm(domElements.deactivateFeedbackForm)\n .then(() => {\n if (feedback && refreshToken) {\n const embedder = getOrCreateBackgroundApp(refreshToken);\n embedder.postMessage({\n key: ProxyMessages.TrackPluginDeactivation,\n payload: {\n type: feedback.value.trim().replace(/[\\s']+/g, '_'),\n },\n });\n }\n })\n .catch((err) => {\n Raven.captureException(err);\n })\n .finally(() => {\n deactivatePlugin();\n });\n}\nfunction init() {\n // eslint-disable-next-line no-new\n new ThickBoxModal(domElements.deactivatePluginButton, 'leadin-feedback-container', 'leadin-feedback-window', 'leadin-feedback-content');\n $(domElements.deactivateFeedbackForm)\n .off('submit')\n .on('submit', submitAndDeactivate);\n $(domElements.deactivateFeedbackSkip)\n .off('click')\n .on('click', deactivatePlugin);\n}\ninitBackgroundApp(init);\n"],"names":["window","leadinConfig","accountName","adminUrl","activationTime","connectionStatus","deviceId","didDisconnect","env","formsScript","meetingsScript","formsScriptPayload","hublet","hubspotBaseUrl","hubspotNonce","iframeUrl","impactLink","lastAuthorizeTime","lastDeauthorizeTime","lastDisconnectTime","leadinPluginVersion","leadinQueryParams","locale","loginUrl","phpVersion","pluginPath","plugins","portalDomain","portalEmail","portalId","redirectNonce","restNonce","restUrl","refreshToken","reviewSkippedDate","theme","trackConsent","wpVersion","contentEmbed","requiresContentEmbedScope","refreshTokenError","domElements","iframe","subMenu","subMenuLinks","subMenuButtons","deactivatePluginButton","deactivateFeedbackForm","deactivateFeedbackSubmit","deactivateFeedbackSkip","thickboxModalClose","thickboxModalWindow","thickboxModalContent","reviewBannerContainer","reviewBannerLeaveReviewLink","reviewBannerDismissButton","leadinIframeContainer","leadinIframe","leadinIframeFallbackContainer","$","ThickBoxModal","openTriggerSelector","inlineContentId","windowCssClass","contentCssClass","on","init","bind","tb_remove","e","tb_show","addClass","off","close","preventDefault","formId","formSubmissionUrl","submitFeedbackForm","formSelector","formSubmissionPayload","fields","serializeArray","skipValidation","Promise","resolve","reject","ajax","type","url","contentType","data","JSON","stringify","success","error","CoreMessages","HandshakeReceive","SendRefreshToken","ReloadParentFrame","RedirectParentFrame","SendLocale","SendDeviceId","FormMessages","CreateFormAppNavigation","LiveChatMessages","CreateLiveChatAppNavigation","PluginMessages","PluginSettingsNavigation","PluginLeadinConfig","TrackConsent","InternalTrackingFetchRequest","InternalTrackingFetchResponse","InternalTrackingFetchError","InternalTrackingChangeRequest","InternalTrackingChangeError","BusinessUnitFetchRequest","BusinessUnitFetchResponse","BusinessUnitFetchError","BusinessUnitChangeRequest","BusinessUnitChangeError","SkipReviewRequest","SkipReviewResponse","SkipReviewError","RemoveParentQueryParam","ContentEmbedInstallRequest","ContentEmbedInstallResponse","ContentEmbedInstallError","ContentEmbedActivationRequest","ContentEmbedActivationResponse","ContentEmbedActivationError","ProxyMessages","FetchForms","FetchForm","CreateFormFromTemplate","FetchAuth","FetchMeetingsAndUsers","FetchContactsCreateSinceActivation","FetchOrCreateMeetingUser","ConnectMeetingsCalendar","TrackFormPreviewRender","TrackFormCreatedFromTemplate","TrackFormCreationFailed","TrackMeetingPreviewRender","TrackSidebarMetaChange","TrackReviewBannerRender","TrackReviewBannerInteraction","TrackReviewBannerDismissed","TrackPluginDeactivation","Raven","configureRaven","indexOf","config","instrument","tryCatch","release","install","setTagsContext","v","php","wordpress","setExtraContext","hub","Object","keys","map","name","join","initApp","initFn","context","initAppOnReady","main","initBackgroundApp","Array","isArray","forEach","callback","getOrCreateBackgroundApp","LeadinBackgroundApp","IntegratedAppEmbedder","IntegratedAppOptions","options","setLocale","setDeviceId","setRefreshToken","embedder","setOptions","attachTo","document","body","postStartAppMessage","deactivatePlugin","href","attr","location","setLoadingState","submitAndDeactivate","feedback","find","field","then","postMessage","key","payload","value","trim","replace","err","captureException"],"sourceRoot":""}
\ No newline at end of file
diff --git a/wp/wp-content/plugins/leadin/build/gutenberg.asset.php b/wp/wp-content/plugins/leadin/build/gutenberg.asset.php
new file mode 100644
index 00000000..b0b7a670
--- /dev/null
+++ b/wp/wp-content/plugins/leadin/build/gutenberg.asset.php
@@ -0,0 +1 @@
+ array('jquery', 'react', 'wp-blocks', 'wp-components', 'wp-data', 'wp-edit-post', 'wp-element', 'wp-i18n', 'wp-plugins'), 'version' => '2129d49ff2651d26d477');
diff --git a/wp/wp-content/plugins/leadin/build/gutenberg.css b/wp/wp-content/plugins/leadin/build/gutenberg.css
new file mode 100644
index 00000000..e796fb33
--- /dev/null
+++ b/wp/wp-content/plugins/leadin/build/gutenberg.css
@@ -0,0 +1,67 @@
+/*!***************************************************************************************************************************************************************************!*\
+ !*** css ./node_modules/css-loader/dist/cjs.js!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/gutenberg/UIComponents/UIImage.ts ***!
+ \***************************************************************************************************************************************************************************/
+.ump7xqy{height:var(--ump7xqy-0);width:var(--ump7xqy-1);}
+/*# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIi91c3Ivc2hhcmUvaHVic3BvdC9idWlsZC93b3Jrc3BhY2UvTGVhZGluV29yZFByZXNzUGx1Z2luL2xlYWRpbi9zY3JpcHRzL2d1dGVuYmVyZy9VSUNvbXBvbmVudHMvVUlJbWFnZS50cyJdLCJuYW1lcyI6WyIudW1wN3hxeSJdLCJtYXBwaW5ncyI6IkFBQ2VBIiwiZmlsZSI6Ii91c3Ivc2hhcmUvaHVic3BvdC9idWlsZC93b3Jrc3BhY2UvTGVhZGluV29yZFByZXNzUGx1Z2luL2xlYWRpbi9zY3JpcHRzL2d1dGVuYmVyZy9VSUNvbXBvbmVudHMvVUlJbWFnZS50cyIsInNvdXJjZXNDb250ZW50IjpbImltcG9ydCB7IHN0eWxlZCB9IGZyb20gJ0BsaW5hcmlhL3JlYWN0JztcbmV4cG9ydCBkZWZhdWx0IHN0eWxlZC5pbWcgYFxuICBoZWlnaHQ6ICR7cHJvcHMgPT4gKHByb3BzLmhlaWdodCA/IHByb3BzLmhlaWdodCA6ICdhdXRvJyl9O1xuICB3aWR0aDogJHtwcm9wcyA9PiAocHJvcHMud2lkdGggPyBwcm9wcy53aWR0aCA6ICdhdXRvJyl9O1xuYDtcbiJdfQ==*/
+/*!*************************************************************************************************************************************************************************!*\
+ !*** css ./node_modules/css-loader/dist/cjs.js!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/UIComponents/UIButton.ts ***!
+ \*************************************************************************************************************************************************************************/
+.ug152ch{background-color:var(--ug152ch-0);border:3px solid var(--ug152ch-0);color:#ffffff;border-radius:3px;font-size:14px;line-height:14px;padding:12px 24px;font-family:'Lexend Deca',Helvetica,Arial,sans-serif;font-weight:500;white-space:nowrap;}
+/*# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIi91c3Ivc2hhcmUvaHVic3BvdC9idWlsZC93b3Jrc3BhY2UvTGVhZGluV29yZFByZXNzUGx1Z2luL2xlYWRpbi9zY3JpcHRzL3NoYXJlZC9VSUNvbXBvbmVudHMvVUlCdXR0b24udHMiXSwibmFtZXMiOlsiLnVnMTUyY2giXSwibWFwcGluZ3MiOiJBQUVlQSIsImZpbGUiOiIvdXNyL3NoYXJlL2h1YnNwb3QvYnVpbGQvd29ya3NwYWNlL0xlYWRpbldvcmRQcmVzc1BsdWdpbi9sZWFkaW4vc2NyaXB0cy9zaGFyZWQvVUlDb21wb25lbnRzL1VJQnV0dG9uLnRzIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsgc3R5bGVkIH0gZnJvbSAnQGxpbmFyaWEvcmVhY3QnO1xuaW1wb3J0IHsgSEVGRkFMVU1QLCBMT1JBWCwgT0xBRiB9IGZyb20gJy4vY29sb3JzJztcbmV4cG9ydCBkZWZhdWx0IHN0eWxlZC5idXR0b24gYFxuICBiYWNrZ3JvdW5kLWNvbG9yOiR7cHJvcHMgPT4gKHByb3BzLnVzZSA9PT0gJ3RlcnRpYXJ5JyA/IEhFRkZBTFVNUCA6IExPUkFYKX07XG4gIGJvcmRlcjogM3B4IHNvbGlkICR7cHJvcHMgPT4gKHByb3BzLnVzZSA9PT0gJ3RlcnRpYXJ5JyA/IEhFRkZBTFVNUCA6IExPUkFYKX07XG4gIGNvbG9yOiAke09MQUZ9XG4gIGJvcmRlci1yYWRpdXM6IDNweDtcbiAgZm9udC1zaXplOiAxNHB4O1xuICBsaW5lLWhlaWdodDogMTRweDtcbiAgcGFkZGluZzogMTJweCAyNHB4O1xuICBmb250LWZhbWlseTogJ0xleGVuZCBEZWNhJywgSGVsdmV0aWNhLCBBcmlhbCwgc2Fucy1zZXJpZjtcbiAgZm9udC13ZWlnaHQ6IDUwMDtcbiAgd2hpdGUtc3BhY2U6IG5vd3JhcDtcbmA7XG4iXX0=*/
+/*!****************************************************************************************************************************************************************************!*\
+ !*** css ./node_modules/css-loader/dist/cjs.js!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/UIComponents/UIContainer.ts ***!
+ \****************************************************************************************************************************************************************************/
+.ua13n1c{text-align:var(--ua13n1c-0);}
+/*# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIi91c3Ivc2hhcmUvaHVic3BvdC9idWlsZC93b3Jrc3BhY2UvTGVhZGluV29yZFByZXNzUGx1Z2luL2xlYWRpbi9zY3JpcHRzL3NoYXJlZC9VSUNvbXBvbmVudHMvVUlDb250YWluZXIudHMiXSwibmFtZXMiOlsiLnVhMTNuMWMiXSwibWFwcGluZ3MiOiJBQUNlQSIsImZpbGUiOiIvdXNyL3NoYXJlL2h1YnNwb3QvYnVpbGQvd29ya3NwYWNlL0xlYWRpbldvcmRQcmVzc1BsdWdpbi9sZWFkaW4vc2NyaXB0cy9zaGFyZWQvVUlDb21wb25lbnRzL1VJQ29udGFpbmVyLnRzIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsgc3R5bGVkIH0gZnJvbSAnQGxpbmFyaWEvcmVhY3QnO1xuZXhwb3J0IGRlZmF1bHQgc3R5bGVkLmRpdiBgXG4gIHRleHQtYWxpZ246ICR7cHJvcHMgPT4gKHByb3BzLnRleHRBbGlnbiA/IHByb3BzLnRleHRBbGlnbiA6ICdpbmhlcml0Jyl9O1xuYDtcbiJdfQ==*/
+/*!*************************************************************************************************************************************************************************!*\
+ !*** css ./node_modules/css-loader/dist/cjs.js!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/Common/HubspotWrapper.ts ***!
+ \*************************************************************************************************************************************************************************/
+.h1q5v5ee{background-image:var(--h1q5v5ee-0);background-color:#f5f8fa;background-repeat:no-repeat;background-position:center 25px;background-size:120px;color:#33475b;font-family:'Lexend Deca',Helvetica,Arial,sans-serif;font-size:14px;padding:var(--h1q5v5ee-1);}.h1q5v5ee p{font-size:inherit !important;line-height:24px;margin:4px 0;}
+/*# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIi91c3Ivc2hhcmUvaHVic3BvdC9idWlsZC93b3Jrc3BhY2UvTGVhZGluV29yZFByZXNzUGx1Z2luL2xlYWRpbi9zY3JpcHRzL3NoYXJlZC9Db21tb24vSHVic3BvdFdyYXBwZXIudHMiXSwibmFtZXMiOlsiLmgxcTV2NWVlIl0sIm1hcHBpbmdzIjoiQUFDZUEiLCJmaWxlIjoiL3Vzci9zaGFyZS9odWJzcG90L2J1aWxkL3dvcmtzcGFjZS9MZWFkaW5Xb3JkUHJlc3NQbHVnaW4vbGVhZGluL3NjcmlwdHMvc2hhcmVkL0NvbW1vbi9IdWJzcG90V3JhcHBlci50cyIsInNvdXJjZXNDb250ZW50IjpbImltcG9ydCB7IHN0eWxlZCB9IGZyb20gJ0BsaW5hcmlhL3JlYWN0JztcbmV4cG9ydCBkZWZhdWx0IHN0eWxlZC5kaXYgYFxuICBiYWNrZ3JvdW5kLWltYWdlOiAke3Byb3BzID0+IGB1cmwoJHtwcm9wcy5wbHVnaW5QYXRofS9wdWJsaWMvYXNzZXRzL2ltYWdlcy9odWJzcG90LnN2ZylgfTtcbiAgYmFja2dyb3VuZC1jb2xvcjogI2Y1ZjhmYTtcbiAgYmFja2dyb3VuZC1yZXBlYXQ6IG5vLXJlcGVhdDtcbiAgYmFja2dyb3VuZC1wb3NpdGlvbjogY2VudGVyIDI1cHg7XG4gIGJhY2tncm91bmQtc2l6ZTogMTIwcHg7XG4gIGNvbG9yOiAjMzM0NzViO1xuICBmb250LWZhbWlseTogJ0xleGVuZCBEZWNhJywgSGVsdmV0aWNhLCBBcmlhbCwgc2Fucy1zZXJpZjtcbiAgZm9udC1zaXplOiAxNHB4O1xuXG4gIHBhZGRpbmc6ICR7KHByb3BzKSA9PiBwcm9wcy5wYWRkaW5nIHx8ICc5MHB4IDIwJSAyNXB4J307XG5cbiAgcCB7XG4gICAgZm9udC1zaXplOiBpbmhlcml0ICFpbXBvcnRhbnQ7XG4gICAgbGluZS1oZWlnaHQ6IDI0cHg7XG4gICAgbWFyZ2luOiA0cHggMDtcbiAgfVxuYDtcbiJdfQ==*/
+/*!*************************************************************************************************************************************************************************!*\
+ !*** css ./node_modules/css-loader/dist/cjs.js!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/UIComponents/UISpacer.ts ***!
+ \*************************************************************************************************************************************************************************/
+.u3qxofx{height:30px;}
+/*# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIi91c3Ivc2hhcmUvaHVic3BvdC9idWlsZC93b3Jrc3BhY2UvTGVhZGluV29yZFByZXNzUGx1Z2luL2xlYWRpbi9zY3JpcHRzL3NoYXJlZC9VSUNvbXBvbmVudHMvVUlTcGFjZXIudHMiXSwibmFtZXMiOlsiLnUzcXhvZngiXSwibWFwcGluZ3MiOiJBQUNlQSIsImZpbGUiOiIvdXNyL3NoYXJlL2h1YnNwb3QvYnVpbGQvd29ya3NwYWNlL0xlYWRpbldvcmRQcmVzc1BsdWdpbi9sZWFkaW4vc2NyaXB0cy9zaGFyZWQvVUlDb21wb25lbnRzL1VJU3BhY2VyLnRzIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsgc3R5bGVkIH0gZnJvbSAnQGxpbmFyaWEvcmVhY3QnO1xuZXhwb3J0IGRlZmF1bHQgc3R5bGVkLmRpdiBgXG4gIGhlaWdodDogMzBweDtcbmA7XG4iXX0=*/
+/*!**************************************************************************************************************************************************************************!*\
+ !*** css ./node_modules/css-loader/dist/cjs.js!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/UIComponents/UIOverlay.ts ***!
+ \**************************************************************************************************************************************************************************/
+.u1q7a48k{position:relative;}.u1q7a48k:after{content:'';position:absolute;top:0;bottom:0;right:0;left:0;}
+/*# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIi91c3Ivc2hhcmUvaHVic3BvdC9idWlsZC93b3Jrc3BhY2UvTGVhZGluV29yZFByZXNzUGx1Z2luL2xlYWRpbi9zY3JpcHRzL3NoYXJlZC9VSUNvbXBvbmVudHMvVUlPdmVybGF5LnRzIl0sIm5hbWVzIjpbIi51MXE3YTQ4ayJdLCJtYXBwaW5ncyI6IkFBQ2VBIiwiZmlsZSI6Ii91c3Ivc2hhcmUvaHVic3BvdC9idWlsZC93b3Jrc3BhY2UvTGVhZGluV29yZFByZXNzUGx1Z2luL2xlYWRpbi9zY3JpcHRzL3NoYXJlZC9VSUNvbXBvbmVudHMvVUlPdmVybGF5LnRzIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsgc3R5bGVkIH0gZnJvbSAnQGxpbmFyaWEvcmVhY3QnO1xuZXhwb3J0IGRlZmF1bHQgc3R5bGVkLmRpdiBgXG4gIHBvc2l0aW9uOiByZWxhdGl2ZTtcblxuICAmOmFmdGVyIHtcbiAgICBjb250ZW50OiAnJztcbiAgICBwb3NpdGlvbjogYWJzb2x1dGU7XG4gICAgdG9wOiAwO1xuICAgIGJvdHRvbTogMDtcbiAgICByaWdodDogMDtcbiAgICBsZWZ0OiAwO1xuICB9XG5gO1xuIl19*/
+/*!***************************************************************************************************************************************************************************!*\
+ !*** css ./node_modules/css-loader/dist/cjs.js!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/UIComponents/UISpinner.tsx ***!
+ \***************************************************************************************************************************************************************************/
+.sxa9zrc{-webkit-align-items:center;-webkit-box-align:center;-ms-flex-align:center;align-items:center;color:#00a4bd;display:-webkit-box;display:-webkit-flex;display:-ms-flexbox;display:flex;-webkit-flex-direction:column;-ms-flex-direction:column;flex-direction:column;-webkit-box-pack:center;-webkit-justify-content:center;-ms-flex-pack:center;justify-content:center;width:100%;height:100%;margin:'2px';}
+.s14430wa{-webkit-align-items:center;-webkit-box-align:center;-ms-flex-align:center;align-items:center;display:-webkit-box;display:-webkit-flex;display:-ms-flexbox;display:flex;-webkit-box-pack:center;-webkit-justify-content:center;-ms-flex-pack:center;justify-content:center;width:100%;height:100%;}
+.ct87ghk{fill:none;stroke:var(--ct87ghk-0);stroke-width:5;stroke-linecap:round;-webkit-transform-origin:center;-ms-transform-origin:center;transform-origin:center;}
+.avili0h{fill:none;stroke:var(--avili0h-0);stroke-width:5;stroke-linecap:round;-webkit-transform-origin:center;-ms-transform-origin:center;transform-origin:center;-webkit-animation:dashAnimation-avili0h 2s ease-in-out infinite,spinAnimation-avili0h 2s linear infinite;animation:dashAnimation-avili0h 2s ease-in-out infinite,spinAnimation-avili0h 2s linear infinite;}@-webkit-keyframes dashAnimation-avili0h{0%{stroke-dasharray:1,150;stroke-dashoffset:0;}50%{stroke-dasharray:90,150;stroke-dashoffset:-50;}100%{stroke-dasharray:90,150;stroke-dashoffset:-140;}}@keyframes dashAnimation-avili0h{0%{stroke-dasharray:1,150;stroke-dashoffset:0;}50%{stroke-dasharray:90,150;stroke-dashoffset:-50;}100%{stroke-dasharray:90,150;stroke-dashoffset:-140;}}@-webkit-keyframes spinAnimation-avili0h{{-webkit-transform:rotate(360deg);-ms-transform:rotate(360deg);transform:rotate(360deg);}}@keyframes spinAnimation-avili0h{{-webkit-transform:rotate(360deg);-ms-transform:rotate(360deg);transform:rotate(360deg);}}
+/*# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIi91c3Ivc2hhcmUvaHVic3BvdC9idWlsZC93b3Jrc3BhY2UvTGVhZGluV29yZFByZXNzUGx1Z2luL2xlYWRpbi9zY3JpcHRzL3NoYXJlZC9VSUNvbXBvbmVudHMvVUlTcGlubmVyLnRzeCJdLCJuYW1lcyI6WyIuc3hhOXpyYyIsIi5zMTQ0MzB3YSIsIi5jdDg3Z2hrIiwiLmF2aWxpMGgiXSwibWFwcGluZ3MiOiJBQUdxQkE7QUFVQUM7QUFPTkM7QUFPUUMiLCJmaWxlIjoiL3Vzci9zaGFyZS9odWJzcG90L2J1aWxkL3dvcmtzcGFjZS9MZWFkaW5Xb3JkUHJlc3NQbHVnaW4vbGVhZGluL3NjcmlwdHMvc2hhcmVkL1VJQ29tcG9uZW50cy9VSVNwaW5uZXIudHN4Iiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsganN4IGFzIF9qc3gsIGpzeHMgYXMgX2pzeHMgfSBmcm9tIFwicmVhY3QvanN4LXJ1bnRpbWVcIjtcbmltcG9ydCB7IHN0eWxlZCB9IGZyb20gJ0BsaW5hcmlhL3JlYWN0JztcbmltcG9ydCB7IENBTFlQU09fTUVESVVNLCBDQUxZUFNPIH0gZnJvbSAnLi9jb2xvcnMnO1xuY29uc3QgU3Bpbm5lck91dGVyID0gc3R5bGVkLmRpdiBgXG4gIGFsaWduLWl0ZW1zOiBjZW50ZXI7XG4gIGNvbG9yOiAjMDBhNGJkO1xuICBkaXNwbGF5OiBmbGV4O1xuICBmbGV4LWRpcmVjdGlvbjogY29sdW1uO1xuICBqdXN0aWZ5LWNvbnRlbnQ6IGNlbnRlcjtcbiAgd2lkdGg6IDEwMCU7XG4gIGhlaWdodDogMTAwJTtcbiAgbWFyZ2luOiAnMnB4JztcbmA7XG5jb25zdCBTcGlubmVySW5uZXIgPSBzdHlsZWQuZGl2IGBcbiAgYWxpZ24taXRlbXM6IGNlbnRlcjtcbiAgZGlzcGxheTogZmxleDtcbiAganVzdGlmeS1jb250ZW50OiBjZW50ZXI7XG4gIHdpZHRoOiAxMDAlO1xuICBoZWlnaHQ6IDEwMCU7XG5gO1xuY29uc3QgQ2lyY2xlID0gc3R5bGVkLmNpcmNsZSBgXG4gIGZpbGw6IG5vbmU7XG4gIHN0cm9rZTogJHtwcm9wcyA9PiBwcm9wcy5jb2xvcn07XG4gIHN0cm9rZS13aWR0aDogNTtcbiAgc3Ryb2tlLWxpbmVjYXA6IHJvdW5kO1xuICB0cmFuc2Zvcm0tb3JpZ2luOiBjZW50ZXI7XG5gO1xuY29uc3QgQW5pbWF0ZWRDaXJjbGUgPSBzdHlsZWQuY2lyY2xlIGBcbiAgZmlsbDogbm9uZTtcbiAgc3Ryb2tlOiAke3Byb3BzID0+IHByb3BzLmNvbG9yfTtcbiAgc3Ryb2tlLXdpZHRoOiA1O1xuICBzdHJva2UtbGluZWNhcDogcm91bmQ7XG4gIHRyYW5zZm9ybS1vcmlnaW46IGNlbnRlcjtcbiAgYW5pbWF0aW9uOiBkYXNoQW5pbWF0aW9uIDJzIGVhc2UtaW4tb3V0IGluZmluaXRlLFxuICAgIHNwaW5BbmltYXRpb24gMnMgbGluZWFyIGluZmluaXRlO1xuXG4gIEBrZXlmcmFtZXMgZGFzaEFuaW1hdGlvbiB7XG4gICAgMCUge1xuICAgICAgc3Ryb2tlLWRhc2hhcnJheTogMSwgMTUwO1xuICAgICAgc3Ryb2tlLWRhc2hvZmZzZXQ6IDA7XG4gICAgfVxuXG4gICAgNTAlIHtcbiAgICAgIHN0cm9rZS1kYXNoYXJyYXk6IDkwLCAxNTA7XG4gICAgICBzdHJva2UtZGFzaG9mZnNldDogLTUwO1xuICAgIH1cblxuICAgIDEwMCUge1xuICAgICAgc3Ryb2tlLWRhc2hhcnJheTogOTAsIDE1MDtcbiAgICAgIHN0cm9rZS1kYXNob2Zmc2V0OiAtMTQwO1xuICAgIH1cbiAgfVxuXG4gIEBrZXlmcmFtZXMgc3BpbkFuaW1hdGlvbiB7XG4gICAgdHJhbnNmb3JtOiByb3RhdGUoMzYwZGVnKTtcbiAgfVxuYDtcbmV4cG9ydCBkZWZhdWx0IGZ1bmN0aW9uIFVJU3Bpbm5lcih7IHNpemUgPSAyMCB9KSB7XG4gICAgcmV0dXJuIChfanN4KFNwaW5uZXJPdXRlciwgeyBjaGlsZHJlbjogX2pzeChTcGlubmVySW5uZXIsIHsgY2hpbGRyZW46IF9qc3hzKFwic3ZnXCIsIHsgaGVpZ2h0OiBzaXplLCB3aWR0aDogc2l6ZSwgdmlld0JveDogXCIwIDAgNTAgNTBcIiwgY2hpbGRyZW46IFtfanN4KENpcmNsZSwgeyBjb2xvcjogQ0FMWVBTT19NRURJVU0sIGN4OiBcIjI1XCIsIGN5OiBcIjI1XCIsIHI6IFwiMjIuNVwiIH0pLCBfanN4KEFuaW1hdGVkQ2lyY2xlLCB7IGNvbG9yOiBDQUxZUFNPLCBjeDogXCIyNVwiLCBjeTogXCIyNVwiLCByOiBcIjIyLjVcIiB9KV0gfSkgfSkgfSkpO1xufVxuIl19*/
+/*!***********************************************************************************************************************************************************************!*\
+ !*** css ./node_modules/css-loader/dist/cjs.js!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/Common/AsyncSelect.tsx ***!
+ \***********************************************************************************************************************************************************************/
+.c1wxx7eu{color:#33475b;font-family:'Lexend Deca',Helvetica,Arial,sans-serif;font-size:14px;position:relative;}
+.c1rgwbep{-webkit-align-items:center;-webkit-box-align:center;-ms-flex-align:center;align-items:center;background-color:hsl(0,0%,100%);border-color:hsl(0,0%,80%);border-radius:4px;border-style:solid;border-width:var(--c1rgwbep-0);cursor:default;display:-webkit-box;display:-webkit-flex;display:-ms-flexbox;display:flex;-webkit-flex-wrap:wrap;-ms-flex-wrap:wrap;flex-wrap:wrap;-webkit-box-pack:justify;-webkit-justify-content:space-between;-ms-flex-pack:justify;justify-content:space-between;min-height:38px;outline:0 !important;position:relative;-webkit-transition:all 100ms;transition:all 100ms;box-sizing:border-box;box-shadow:var(--c1rgwbep-1);}.c1rgwbep:hover{border-color:hsl(0,0%,70%);}
+.v1mdmbaj{-webkit-align-items:center;-webkit-box-align:center;-ms-flex-align:center;align-items:center;display:-webkit-box;display:-webkit-flex;display:-ms-flexbox;display:flex;-webkit-flex:1;-ms-flex:1;flex:1;-webkit-flex-wrap:wrap;-ms-flex-wrap:wrap;flex-wrap:wrap;padding:2px 8px;position:relative;overflow:hidden;box-sizing:border-box;}
+.p1gwkvxy{color:hsl(0,0%,50%);margin-left:2px;margin-right:2px;position:absolute;top:50%;-webkit-transform:translateY(-50%);-ms-transform:translateY(-50%);transform:translateY(-50%);box-sizing:border-box;font-size:16px;}
+.s1bwlafs{color:hsl(0,0%,20%);margin-left:2px;margin-right:2px;max-width:calc(100% - 8px);overflow:hidden;position:absolute;text-overflow:ellipsis;white-space:nowrap;top:50%;-webkit-transform:translateY(-50%);-ms-transform:translateY(-50%);transform:translateY(-50%);box-sizing:border-box;}
+.i196z9y5{-webkit-align-items:center;-webkit-box-align:center;-ms-flex-align:center;align-items:center;-webkit-align-self:stretch;-ms-flex-item-align:stretch;align-self:stretch;display:-webkit-box;display:-webkit-flex;display:-ms-flexbox;display:flex;-webkit-flex-shrink:0;-ms-flex-negative:0;flex-shrink:0;box-sizing:border-box;}
+.d1dfo5ow{border-top:8px solid #00a4bd;border-left:6px solid transparent;border-right:6px solid transparent;width:0px;height:0px;margin:10px;}
+.if3lze{margin:2px;padding-bottom:2px;padding-top:2px;visibility:visible;color:hsl(0,0%,20%);box-sizing:border-box;}
+.i9kxf50{box-sizing:content-box;background:rgba(0,0,0,0) none repeat scroll 0px center;border:0px none;font-size:inherit;opacity:1;outline:currentcolor none 0px;padding:0px;color:inherit;font-family:inherit;}
+.igjr3uc{position:absolute;opacity:0;font-size:inherit;}
+.mhb9if7{position:absolute;top:100%;background-color:#fff;border-radius:4px;margin-bottom:8px;margin-top:8px;z-index:9999;box-shadow:0 0 0 1px hsla(0,0%,0%,0.1),0 4px 11px hsla(0,0%,0%,0.1);width:100%;}
+.mxaof7s{max-height:300px;overflow-y:auto;padding-bottom:4px;padding-top:4px;position:relative;}
+.mw50s5v{padding-bottom:8px;padding-top:8px;}
+.m11rzvjw{color:#999;cursor:default;font-size:75%;font-weight:500;margin-bottom:0.25em;text-transform:uppercase;padding-left:12px;padding-left:12px;}
+.m1jcdsjv{display:block;background-color:var(--m1jcdsjv-0);color:var(--m1jcdsjv-1);cursor:default;font-size:inherit;width:100%;padding:8px 12px;}.m1jcdsjv:hover{background-color:var(--m1jcdsjv-2);}
+/*# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIi91c3Ivc2hhcmUvaHVic3BvdC9idWlsZC93b3Jrc3BhY2UvTGVhZGluV29yZFByZXNzUGx1Z2luL2xlYWRpbi9zY3JpcHRzL3NoYXJlZC9Db21tb24vQXN5bmNTZWxlY3QudHN4Il0sIm5hbWVzIjpbIi5jMXd4eDdldSIsIi5jMXJnd2JlcCIsIi52MW1kbWJhaiIsIi5wMWd3a3Z4eSIsIi5zMWJ3bGFmcyIsIi5pMTk2ejl5NSIsIi5kMWRmbzVvdyIsIi5pZjNsemUiLCIuaTlreGY1MCIsIi5pZ2pyM3VjIiwiLm1oYjlpZjciLCIubXhhb2Y3cyIsIi5tdzUwczV2IiwiLm0xMXJ6dmp3IiwiLm0xamNkc2p2Il0sIm1hcHBpbmdzIjoiQUFNa0JBO0FBTU9DO0FBcUJGQztBQVVIQztBQVVBQztBQWFPQztBQU9EQztBQVFIQztBQVFUQztBQVdNQztBQUtFQztBQVdMQztBQU9DQztBQUlNQztBQVVQQyIsImZpbGUiOiIvdXNyL3NoYXJlL2h1YnNwb3QvYnVpbGQvd29ya3NwYWNlL0xlYWRpbldvcmRQcmVzc1BsdWdpbi9sZWFkaW4vc2NyaXB0cy9zaGFyZWQvQ29tbW9uL0FzeW5jU2VsZWN0LnRzeCIsInNvdXJjZXNDb250ZW50IjpbImltcG9ydCB7IGpzeCBhcyBfanN4LCBqc3hzIGFzIF9qc3hzIH0gZnJvbSBcInJlYWN0L2pzeC1ydW50aW1lXCI7XG5pbXBvcnQgeyB1c2VSZWYsIHVzZVN0YXRlLCB1c2VFZmZlY3QgfSBmcm9tICdyZWFjdCc7XG5pbXBvcnQgeyBzdHlsZWQgfSBmcm9tICdAbGluYXJpYS9yZWFjdCc7XG5pbXBvcnQgeyBDQUxZUFNPLCBDQUxZUFNPX0xJR0hULCBDQUxZUFNPX01FRElVTSwgT0JTSURJQU4sIH0gZnJvbSAnLi4vVUlDb21wb25lbnRzL2NvbG9ycyc7XG5pbXBvcnQgVUlTcGlubmVyIGZyb20gJy4uL1VJQ29tcG9uZW50cy9VSVNwaW5uZXInO1xuaW1wb3J0IExvYWRTdGF0ZSBmcm9tICcuLi9lbnVtcy9sb2FkU3RhdGUnO1xuY29uc3QgQ29udGFpbmVyID0gc3R5bGVkLmRpdiBgXG4gIGNvbG9yOiAke09CU0lESUFOfTtcbiAgZm9udC1mYW1pbHk6ICdMZXhlbmQgRGVjYScsIEhlbHZldGljYSwgQXJpYWwsIHNhbnMtc2VyaWY7XG4gIGZvbnQtc2l6ZTogMTRweDtcbiAgcG9zaXRpb246IHJlbGF0aXZlO1xuYDtcbmNvbnN0IENvbnRyb2xDb250YWluZXIgPSBzdHlsZWQuZGl2IGBcbiAgYWxpZ24taXRlbXM6IGNlbnRlcjtcbiAgYmFja2dyb3VuZC1jb2xvcjogaHNsKDAsIDAlLCAxMDAlKTtcbiAgYm9yZGVyLWNvbG9yOiBoc2woMCwgMCUsIDgwJSk7XG4gIGJvcmRlci1yYWRpdXM6IDRweDtcbiAgYm9yZGVyLXN0eWxlOiBzb2xpZDtcbiAgYm9yZGVyLXdpZHRoOiAke3Byb3BzID0+IChwcm9wcy5mb2N1c2VkID8gJzAnIDogJzFweCcpfTtcbiAgY3Vyc29yOiBkZWZhdWx0O1xuICBkaXNwbGF5OiBmbGV4O1xuICBmbGV4LXdyYXA6IHdyYXA7XG4gIGp1c3RpZnktY29udGVudDogc3BhY2UtYmV0d2VlbjtcbiAgbWluLWhlaWdodDogMzhweDtcbiAgb3V0bGluZTogMCAhaW1wb3J0YW50O1xuICBwb3NpdGlvbjogcmVsYXRpdmU7XG4gIHRyYW5zaXRpb246IGFsbCAxMDBtcztcbiAgYm94LXNpemluZzogYm9yZGVyLWJveDtcbiAgYm94LXNoYWRvdzogJHtwcm9wcyA9PiBwcm9wcy5mb2N1c2VkID8gYDAgMCAwIDJweCAke0NBTFlQU09fTUVESVVNfWAgOiAnbm9uZSd9O1xuICAmOmhvdmVyIHtcbiAgICBib3JkZXItY29sb3I6IGhzbCgwLCAwJSwgNzAlKTtcbiAgfVxuYDtcbmNvbnN0IFZhbHVlQ29udGFpbmVyID0gc3R5bGVkLmRpdiBgXG4gIGFsaWduLWl0ZW1zOiBjZW50ZXI7XG4gIGRpc3BsYXk6IGZsZXg7XG4gIGZsZXg6IDE7XG4gIGZsZXgtd3JhcDogd3JhcDtcbiAgcGFkZGluZzogMnB4IDhweDtcbiAgcG9zaXRpb246IHJlbGF0aXZlO1xuICBvdmVyZmxvdzogaGlkZGVuO1xuICBib3gtc2l6aW5nOiBib3JkZXItYm94O1xuYDtcbmNvbnN0IFBsYWNlaG9sZGVyID0gc3R5bGVkLmRpdiBgXG4gIGNvbG9yOiBoc2woMCwgMCUsIDUwJSk7XG4gIG1hcmdpbi1sZWZ0OiAycHg7XG4gIG1hcmdpbi1yaWdodDogMnB4O1xuICBwb3NpdGlvbjogYWJzb2x1dGU7XG4gIHRvcDogNTAlO1xuICB0cmFuc2Zvcm06IHRyYW5zbGF0ZVkoLTUwJSk7XG4gIGJveC1zaXppbmc6IGJvcmRlci1ib3g7XG4gIGZvbnQtc2l6ZTogMTZweDtcbmA7XG5jb25zdCBTaW5nbGVWYWx1ZSA9IHN0eWxlZC5kaXYgYFxuICBjb2xvcjogaHNsKDAsIDAlLCAyMCUpO1xuICBtYXJnaW4tbGVmdDogMnB4O1xuICBtYXJnaW4tcmlnaHQ6IDJweDtcbiAgbWF4LXdpZHRoOiBjYWxjKDEwMCUgLSA4cHgpO1xuICBvdmVyZmxvdzogaGlkZGVuO1xuICBwb3NpdGlvbjogYWJzb2x1dGU7XG4gIHRleHQtb3ZlcmZsb3c6IGVsbGlwc2lzO1xuICB3aGl0ZS1zcGFjZTogbm93cmFwO1xuICB0b3A6IDUwJTtcbiAgdHJhbnNmb3JtOiB0cmFuc2xhdGVZKC01MCUpO1xuICBib3gtc2l6aW5nOiBib3JkZXItYm94O1xuYDtcbmNvbnN0IEluZGljYXRvckNvbnRhaW5lciA9IHN0eWxlZC5kaXYgYFxuICBhbGlnbi1pdGVtczogY2VudGVyO1xuICBhbGlnbi1zZWxmOiBzdHJldGNoO1xuICBkaXNwbGF5OiBmbGV4O1xuICBmbGV4LXNocmluazogMDtcbiAgYm94LXNpemluZzogYm9yZGVyLWJveDtcbmA7XG5jb25zdCBEcm9wZG93bkluZGljYXRvciA9IHN0eWxlZC5kaXYgYFxuICBib3JkZXItdG9wOiA4cHggc29saWQgJHtDQUxZUFNPfTtcbiAgYm9yZGVyLWxlZnQ6IDZweCBzb2xpZCB0cmFuc3BhcmVudDtcbiAgYm9yZGVyLXJpZ2h0OiA2cHggc29saWQgdHJhbnNwYXJlbnQ7XG4gIHdpZHRoOiAwcHg7XG4gIGhlaWdodDogMHB4O1xuICBtYXJnaW46IDEwcHg7XG5gO1xuY29uc3QgSW5wdXRDb250YWluZXIgPSBzdHlsZWQuZGl2IGBcbiAgbWFyZ2luOiAycHg7XG4gIHBhZGRpbmctYm90dG9tOiAycHg7XG4gIHBhZGRpbmctdG9wOiAycHg7XG4gIHZpc2liaWxpdHk6IHZpc2libGU7XG4gIGNvbG9yOiBoc2woMCwgMCUsIDIwJSk7XG4gIGJveC1zaXppbmc6IGJvcmRlci1ib3g7XG5gO1xuY29uc3QgSW5wdXQgPSBzdHlsZWQuaW5wdXQgYFxuICBib3gtc2l6aW5nOiBjb250ZW50LWJveDtcbiAgYmFja2dyb3VuZDogcmdiYSgwLCAwLCAwLCAwKSBub25lIHJlcGVhdCBzY3JvbGwgMHB4IGNlbnRlcjtcbiAgYm9yZGVyOiAwcHggbm9uZTtcbiAgZm9udC1zaXplOiBpbmhlcml0O1xuICBvcGFjaXR5OiAxO1xuICBvdXRsaW5lOiBjdXJyZW50Y29sb3Igbm9uZSAwcHg7XG4gIHBhZGRpbmc6IDBweDtcbiAgY29sb3I6IGluaGVyaXQ7XG4gIGZvbnQtZmFtaWx5OiBpbmhlcml0O1xuYDtcbmNvbnN0IElucHV0U2hhZG93ID0gc3R5bGVkLmRpdiBgXG4gIHBvc2l0aW9uOiBhYnNvbHV0ZTtcbiAgb3BhY2l0eTogMDtcbiAgZm9udC1zaXplOiBpbmhlcml0O1xuYDtcbmNvbnN0IE1lbnVDb250YWluZXIgPSBzdHlsZWQuZGl2IGBcbiAgcG9zaXRpb246IGFic29sdXRlO1xuICB0b3A6IDEwMCU7XG4gIGJhY2tncm91bmQtY29sb3I6ICNmZmY7XG4gIGJvcmRlci1yYWRpdXM6IDRweDtcbiAgbWFyZ2luLWJvdHRvbTogOHB4O1xuICBtYXJnaW4tdG9wOiA4cHg7XG4gIHotaW5kZXg6IDk5OTk7XG4gIGJveC1zaGFkb3c6IDAgMCAwIDFweCBoc2xhKDAsIDAlLCAwJSwgMC4xKSwgMCA0cHggMTFweCBoc2xhKDAsIDAlLCAwJSwgMC4xKTtcbiAgd2lkdGg6IDEwMCU7XG5gO1xuY29uc3QgTWVudUxpc3QgPSBzdHlsZWQuZGl2IGBcbiAgbWF4LWhlaWdodDogMzAwcHg7XG4gIG92ZXJmbG93LXk6IGF1dG87XG4gIHBhZGRpbmctYm90dG9tOiA0cHg7XG4gIHBhZGRpbmctdG9wOiA0cHg7XG4gIHBvc2l0aW9uOiByZWxhdGl2ZTtcbmA7XG5jb25zdCBNZW51R3JvdXAgPSBzdHlsZWQuZGl2IGBcbiAgcGFkZGluZy1ib3R0b206IDhweDtcbiAgcGFkZGluZy10b3A6IDhweDtcbmA7XG5jb25zdCBNZW51R3JvdXBIZWFkZXIgPSBzdHlsZWQuZGl2IGBcbiAgY29sb3I6ICM5OTk7XG4gIGN1cnNvcjogZGVmYXVsdDtcbiAgZm9udC1zaXplOiA3NSU7XG4gIGZvbnQtd2VpZ2h0OiA1MDA7XG4gIG1hcmdpbi1ib3R0b206IDAuMjVlbTtcbiAgdGV4dC10cmFuc2Zvcm06IHVwcGVyY2FzZTtcbiAgcGFkZGluZy1sZWZ0OiAxMnB4O1xuICBwYWRkaW5nLWxlZnQ6IDEycHg7XG5gO1xuY29uc3QgTWVudUl0ZW0gPSBzdHlsZWQuZGl2IGBcbiAgZGlzcGxheTogYmxvY2s7XG4gIGJhY2tncm91bmQtY29sb3I6ICR7cHJvcHMgPT4gcHJvcHMuc2VsZWN0ZWQgPyBDQUxZUFNPX01FRElVTSA6ICd0cmFuc3BhcmVudCd9O1xuICBjb2xvcjogJHtwcm9wcyA9PiAocHJvcHMuc2VsZWN0ZWQgPyAnI2ZmZicgOiAnaW5oZXJpdCcpfTtcbiAgY3Vyc29yOiBkZWZhdWx0O1xuICBmb250LXNpemU6IGluaGVyaXQ7XG4gIHdpZHRoOiAxMDAlO1xuICBwYWRkaW5nOiA4cHggMTJweDtcbiAgJjpob3ZlciB7XG4gICAgYmFja2dyb3VuZC1jb2xvcjogJHtwcm9wcyA9PiBwcm9wcy5zZWxlY3RlZCA/IENBTFlQU09fTUVESVVNIDogQ0FMWVBTT19MSUdIVH07XG4gIH1cbmA7XG5leHBvcnQgZGVmYXVsdCBmdW5jdGlvbiBBc3luY1NlbGVjdCh7IHBsYWNlaG9sZGVyLCB2YWx1ZSwgbG9hZE9wdGlvbnMsIG9uQ2hhbmdlLCBkZWZhdWx0T3B0aW9ucywgfSkge1xuICAgIGNvbnN0IGlucHV0RWwgPSB1c2VSZWYobnVsbCk7XG4gICAgY29uc3QgaW5wdXRTaGFkb3dFbCA9IHVzZVJlZihudWxsKTtcbiAgICBjb25zdCBbaXNGb2N1c2VkLCBzZXRGb2N1c10gPSB1c2VTdGF0ZShmYWxzZSk7XG4gICAgY29uc3QgW2xvYWRTdGF0ZSwgc2V0TG9hZFN0YXRlXSA9IHVzZVN0YXRlKExvYWRTdGF0ZS5Ob3RMb2FkZWQpO1xuICAgIGNvbnN0IFtsb2NhbFZhbHVlLCBzZXRMb2NhbFZhbHVlXSA9IHVzZVN0YXRlKCcnKTtcbiAgICBjb25zdCBbb3B0aW9ucywgc2V0T3B0aW9uc10gPSB1c2VTdGF0ZShkZWZhdWx0T3B0aW9ucyk7XG4gICAgY29uc3QgaW5wdXRTaXplID0gYCR7aW5wdXRTaGFkb3dFbC5jdXJyZW50ID8gaW5wdXRTaGFkb3dFbC5jdXJyZW50LmNsaWVudFdpZHRoICsgMTAgOiAyfXB4YDtcbiAgICB1c2VFZmZlY3QoKCkgPT4ge1xuICAgICAgICBpZiAobG9hZE9wdGlvbnMgJiYgbG9hZFN0YXRlID09PSBMb2FkU3RhdGUuTm90TG9hZGVkKSB7XG4gICAgICAgICAgICBsb2FkT3B0aW9ucygnJywgKHJlc3VsdCkgPT4ge1xuICAgICAgICAgICAgICAgIHNldE9wdGlvbnMocmVzdWx0KTtcbiAgICAgICAgICAgICAgICBzZXRMb2FkU3RhdGUoTG9hZFN0YXRlLklkbGUpO1xuICAgICAgICAgICAgfSk7XG4gICAgICAgIH1cbiAgICB9LCBbbG9hZE9wdGlvbnMsIGxvYWRTdGF0ZV0pO1xuICAgIGNvbnN0IHJlbmRlckl0ZW1zID0gKGl0ZW1zID0gW10sIHBhcmVudEtleSkgPT4ge1xuICAgICAgICByZXR1cm4gaXRlbXMubWFwKChpdGVtLCBpbmRleCkgPT4ge1xuICAgICAgICAgICAgaWYgKGl0ZW0ub3B0aW9ucykge1xuICAgICAgICAgICAgICAgIHJldHVybiAoX2pzeHMoTWVudUdyb3VwLCB7IGNoaWxkcmVuOiBbX2pzeChNZW51R3JvdXBIZWFkZXIsIHsgaWQ6IGAke2luZGV4fS1oZWFkaW5nYCwgY2hpbGRyZW46IGl0ZW0ubGFiZWwgfSksIF9qc3goXCJkaXZcIiwgeyBjaGlsZHJlbjogcmVuZGVySXRlbXMoaXRlbS5vcHRpb25zLCBpbmRleCkgfSldIH0sIGBhc3luYy1zZWxlY3QtaXRlbS0ke2luZGV4fWApKTtcbiAgICAgICAgICAgIH1cbiAgICAgICAgICAgIGVsc2Uge1xuICAgICAgICAgICAgICAgIGNvbnN0IGtleSA9IGBhc3luYy1zZWxlY3QtaXRlbS0ke3BhcmVudEtleSAhPT0gdW5kZWZpbmVkID8gYCR7cGFyZW50S2V5fS0ke2luZGV4fWAgOiBpbmRleH1gO1xuICAgICAgICAgICAgICAgIHJldHVybiAoX2pzeChNZW51SXRlbSwgeyBpZDoga2V5LCBzZWxlY3RlZDogdmFsdWUgJiYgaXRlbS52YWx1ZSA9PT0gdmFsdWUudmFsdWUsIG9uQ2xpY2s6ICgpID0+IHtcbiAgICAgICAgICAgICAgICAgICAgICAgIG9uQ2hhbmdlKGl0ZW0pO1xuICAgICAgICAgICAgICAgICAgICAgICAgc2V0Rm9jdXMoZmFsc2UpO1xuICAgICAgICAgICAgICAgICAgICB9LCBjaGlsZHJlbjogaXRlbS5sYWJlbCB9LCBrZXkpKTtcbiAgICAgICAgICAgIH1cbiAgICAgICAgfSk7XG4gICAgfTtcbiAgICByZXR1cm4gKF9qc3hzKENvbnRhaW5lciwgeyBjaGlsZHJlbjogW19qc3hzKENvbnRyb2xDb250YWluZXIsIHsgaWQ6IFwibGVhZGluLWFzeW5jLXNlbGVjdG9yXCIsIGZvY3VzZWQ6IGlzRm9jdXNlZCwgb25DbGljazogKCkgPT4ge1xuICAgICAgICAgICAgICAgICAgICBpZiAoaXNGb2N1c2VkKSB7XG4gICAgICAgICAgICAgICAgICAgICAgICBpZiAoaW5wdXRFbC5jdXJyZW50KSB7XG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgaW5wdXRFbC5jdXJyZW50LmJsdXIoKTtcbiAgICAgICAgICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgICAgICAgICAgICAgIHNldEZvY3VzKGZhbHNlKTtcbiAgICAgICAgICAgICAgICAgICAgICAgIHNldExvY2FsVmFsdWUoJycpO1xuICAgICAgICAgICAgICAgICAgICB9XG4gICAgICAgICAgICAgICAgICAgIGVsc2Uge1xuICAgICAgICAgICAgICAgICAgICAgICAgaWYgKGlucHV0RWwuY3VycmVudCkge1xuICAgICAgICAgICAgICAgICAgICAgICAgICAgIGlucHV0RWwuY3VycmVudC5mb2N1cygpO1xuICAgICAgICAgICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgICAgICAgICAgICAgc2V0Rm9jdXModHJ1ZSk7XG4gICAgICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgICAgICB9LCBjaGlsZHJlbjogW19qc3hzKFZhbHVlQ29udGFpbmVyLCB7IGNoaWxkcmVuOiBbbG9jYWxWYWx1ZSA9PT0gJycgJiZcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgKCF2YWx1ZSA/IChfanN4KFBsYWNlaG9sZGVyLCB7IGNoaWxkcmVuOiBwbGFjZWhvbGRlciB9KSkgOiAoX2pzeChTaW5nbGVWYWx1ZSwgeyBjaGlsZHJlbjogdmFsdWUubGFiZWwgfSkpKSwgX2pzeHMoSW5wdXRDb250YWluZXIsIHsgY2hpbGRyZW46IFtfanN4KElucHV0LCB7IHJlZjogaW5wdXRFbCwgb25Gb2N1czogKCkgPT4ge1xuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBzZXRGb2N1cyh0cnVlKTtcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB9LCBvbkNoYW5nZTogZSA9PiB7XG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHNldExvY2FsVmFsdWUoZS50YXJnZXQudmFsdWUpO1xuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBzZXRMb2FkU3RhdGUoTG9hZFN0YXRlLkxvYWRpbmcpO1xuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBsb2FkT3B0aW9ucyAmJlxuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgbG9hZE9wdGlvbnMoZS50YXJnZXQudmFsdWUsIChyZXN1bHQpID0+IHtcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBzZXRPcHRpb25zKHJlc3VsdCk7XG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgc2V0TG9hZFN0YXRlKExvYWRTdGF0ZS5JZGxlKTtcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIH0pO1xuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIH0sIHZhbHVlOiBsb2NhbFZhbHVlLCB3aWR0aDogaW5wdXRTaXplLCBpZDogXCJhc3ljbi1zZWxlY3QtaW5wdXRcIiB9KSwgX2pzeChJbnB1dFNoYWRvdywgeyByZWY6IGlucHV0U2hhZG93RWwsIGNoaWxkcmVuOiBsb2NhbFZhbHVlIH0pXSB9KV0gfSksIF9qc3hzKEluZGljYXRvckNvbnRhaW5lciwgeyBjaGlsZHJlbjogW2xvYWRTdGF0ZSA9PT0gTG9hZFN0YXRlLkxvYWRpbmcgJiYgX2pzeChVSVNwaW5uZXIsIHt9KSwgX2pzeChEcm9wZG93bkluZGljYXRvciwge30pXSB9KV0gfSksIGlzRm9jdXNlZCAmJiAoX2pzeChNZW51Q29udGFpbmVyLCB7IGNoaWxkcmVuOiBfanN4KE1lbnVMaXN0LCB7IGNoaWxkcmVuOiByZW5kZXJJdGVtcyhvcHRpb25zKSB9KSB9KSldIH0pKTtcbn1cbiJdfQ==*/
+/*!*************************************************************************************************************************************************************************!*\
+ !*** css ./node_modules/css-loader/dist/cjs.js!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/UIComponents/UIAlert.tsx ***!
+ \*************************************************************************************************************************************************************************/
+.a1h8m4fo{background-color:#fef8f0;border-color:#fae0b5;color:#33475b;font-size:14px;-webkit-align-items:center;-webkit-box-align:center;-ms-flex-align:center;align-items:center;-webkit-box-pack:justify;-webkit-justify-content:space-between;-ms-flex-pack:justify;justify-content:space-between;display:-webkit-box;display:-webkit-flex;display:-ms-flexbox;display:flex;border-style:solid;border-top-style:solid;border-right-style:solid;border-bottom-style:solid;border-left-style:solid;border-width:1px;min-height:60px;padding:8px 20px;position:relative;text-align:left;}
+.tyndzxk{font-family:'Lexend Deca';font-style:normal;font-weight:700;font-size:16px;line-height:19px;color:#33475b;margin:0;padding:0;}
+.m1m9sbk4{font-family:'Lexend Deca';font-style:normal;font-weight:400;font-size:14px;margin:0;padding:0;}
+.mg5o421{display:-webkit-box;display:-webkit-flex;display:-ms-flexbox;display:flex;-webkit-flex-direction:column;-ms-flex-direction:column;flex-direction:column;}
+/*# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIi91c3Ivc2hhcmUvaHVic3BvdC9idWlsZC93b3Jrc3BhY2UvTGVhZGluV29yZFByZXNzUGx1Z2luL2xlYWRpbi9zY3JpcHRzL3NoYXJlZC9VSUNvbXBvbmVudHMvVUlBbGVydC50c3giXSwibmFtZXMiOlsiLmExaDhtNGZvIiwiLnR5bmR6eGsiLCIubTFtOXNiazQiLCIubWc1bzQyMSJdLCJtYXBwaW5ncyI6IkFBR3VCQTtBQW1CVEM7QUFVRUM7QUFRU0MiLCJmaWxlIjoiL3Vzci9zaGFyZS9odWJzcG90L2J1aWxkL3dvcmtzcGFjZS9MZWFkaW5Xb3JkUHJlc3NQbHVnaW4vbGVhZGluL3NjcmlwdHMvc2hhcmVkL1VJQ29tcG9uZW50cy9VSUFsZXJ0LnRzeCIsInNvdXJjZXNDb250ZW50IjpbImltcG9ydCB7IGpzeCBhcyBfanN4LCBqc3hzIGFzIF9qc3hzIH0gZnJvbSBcInJlYWN0L2pzeC1ydW50aW1lXCI7XG5pbXBvcnQgeyBzdHlsZWQgfSBmcm9tICdAbGluYXJpYS9yZWFjdCc7XG5pbXBvcnQgeyBNQVJJR09MRF9MSUdIVCwgTUFSSUdPTERfTUVESVVNLCBPQlNJRElBTiB9IGZyb20gJy4vY29sb3JzJztcbmNvbnN0IEFsZXJ0Q29udGFpbmVyID0gc3R5bGVkLmRpdiBgXG4gIGJhY2tncm91bmQtY29sb3I6ICR7TUFSSUdPTERfTElHSFR9O1xuICBib3JkZXItY29sb3I6ICR7TUFSSUdPTERfTUVESVVNfTtcbiAgY29sb3I6ICR7T0JTSURJQU59O1xuICBmb250LXNpemU6IDE0cHg7XG4gIGFsaWduLWl0ZW1zOiBjZW50ZXI7XG4gIGp1c3RpZnktY29udGVudDogc3BhY2UtYmV0d2VlbjtcbiAgZGlzcGxheTogZmxleDtcbiAgYm9yZGVyLXN0eWxlOiBzb2xpZDtcbiAgYm9yZGVyLXRvcC1zdHlsZTogc29saWQ7XG4gIGJvcmRlci1yaWdodC1zdHlsZTogc29saWQ7XG4gIGJvcmRlci1ib3R0b20tc3R5bGU6IHNvbGlkO1xuICBib3JkZXItbGVmdC1zdHlsZTogc29saWQ7XG4gIGJvcmRlci13aWR0aDogMXB4O1xuICBtaW4taGVpZ2h0OiA2MHB4O1xuICBwYWRkaW5nOiA4cHggMjBweDtcbiAgcG9zaXRpb246IHJlbGF0aXZlO1xuICB0ZXh0LWFsaWduOiBsZWZ0O1xuYDtcbmNvbnN0IFRpdGxlID0gc3R5bGVkLnAgYFxuICBmb250LWZhbWlseTogJ0xleGVuZCBEZWNhJztcbiAgZm9udC1zdHlsZTogbm9ybWFsO1xuICBmb250LXdlaWdodDogNzAwO1xuICBmb250LXNpemU6IDE2cHg7XG4gIGxpbmUtaGVpZ2h0OiAxOXB4O1xuICBjb2xvcjogJHtPQlNJRElBTn07XG4gIG1hcmdpbjogMDtcbiAgcGFkZGluZzogMDtcbmA7XG5jb25zdCBNZXNzYWdlID0gc3R5bGVkLnAgYFxuICBmb250LWZhbWlseTogJ0xleGVuZCBEZWNhJztcbiAgZm9udC1zdHlsZTogbm9ybWFsO1xuICBmb250LXdlaWdodDogNDAwO1xuICBmb250LXNpemU6IDE0cHg7XG4gIG1hcmdpbjogMDtcbiAgcGFkZGluZzogMDtcbmA7XG5jb25zdCBNZXNzYWdlQ29udGFpbmVyID0gc3R5bGVkLmRpdiBgXG4gIGRpc3BsYXk6IGZsZXg7XG4gIGZsZXgtZGlyZWN0aW9uOiBjb2x1bW47XG5gO1xuZXhwb3J0IGRlZmF1bHQgZnVuY3Rpb24gVUlBbGVydCh7IHRpdGxlVGV4dCwgdGl0bGVNZXNzYWdlLCBjaGlsZHJlbiwgfSkge1xuICAgIHJldHVybiAoX2pzeHMoQWxlcnRDb250YWluZXIsIHsgY2hpbGRyZW46IFtfanN4cyhNZXNzYWdlQ29udGFpbmVyLCB7IGNoaWxkcmVuOiBbX2pzeChUaXRsZSwgeyBjaGlsZHJlbjogdGl0bGVUZXh0IH0pLCBfanN4KE1lc3NhZ2UsIHsgY2hpbGRyZW46IHRpdGxlTWVzc2FnZSB9KV0gfSksIGNoaWxkcmVuXSB9KSk7XG59XG4iXX0=*/
+
+/*# sourceMappingURL=gutenberg.css.map*/
\ No newline at end of file
diff --git a/wp/wp-content/plugins/leadin/build/gutenberg.css.map b/wp/wp-content/plugins/leadin/build/gutenberg.css.map
new file mode 100644
index 00000000..3d4d7b5b
--- /dev/null
+++ b/wp/wp-content/plugins/leadin/build/gutenberg.css.map
@@ -0,0 +1 @@
+{"version":3,"file":"gutenberg.css","mappings":";;;AACeA,SAAAA,uBAAAA,CAAAA,sBAAAA,CAAAA;ACAf,2tBAA2tB,C;;;;ACC5sBC,SAAAA,iCAAAA,CAAAA,iCAAAA,CAAAA,aAAAA,CAAAA,iBAAAA,CAAAA,cAAAA,CAAAA,gBAAAA,CAAAA,iBAAAA,CAAAA,oDAAAA,CAAAA,eAAAA,CAAAA,kBAAAA,CAAAA;ACDf,2mCAA2mC,C;;;;ACA5lCC,SAAAA,2BAAAA,CAAAA;ACAf,+pBAA+pB,C;;;;ACAhpBC,UAAAA,kCAAAA,CAAAA,wBAAAA,CAAAA,2BAAAA,CAAAA,+BAAAA,CAAAA,qBAAAA,CAAAA,aAAAA,CAAAA,oDAAAA,CAAAA,cAAAA,CAAAA,yBAAAA,CAAAA,CAAAA,YAAAA,4BAAAA,CAAAA,gBAAAA,CAAAA,YAAAA,CAAAA;ACAf,+qCAA+qC,C;;;;ACAhqCC,SAAAA,WAAAA,CAAAA;ACAf,ukBAAukB,C;;;;ACAxjBC,UAAAA,iBAAAA,CAAAA,CAAAA,gBAAAA,UAAAA,CAAAA,iBAAAA,CAAAA,KAAAA,CAAAA,QAAAA,CAAAA,OAAAA,CAAAA,MAAAA,CAAAA;ACAf,mvBAAmvB,C;;;;ACE9tBC,SAAAA,0BAAAA,CAAAA,wBAAAA,CAAAA,qBAAAA,CAAAA,kBAAAA,CAAAA,aAAAA,CAAAA,mBAAAA,CAAAA,oBAAAA,CAAAA,mBAAAA,CAAAA,YAAAA,CAAAA,6BAAAA,CAAAA,yBAAAA,CAAAA,qBAAAA,CAAAA,uBAAAA,CAAAA,8BAAAA,CAAAA,oBAAAA,CAAAA,sBAAAA,CAAAA,UAAAA,CAAAA,WAAAA,CAAAA,YAAAA,CAAAA;AAUAC,UAAAA,0BAAAA,CAAAA,wBAAAA,CAAAA,qBAAAA,CAAAA,kBAAAA,CAAAA,mBAAAA,CAAAA,oBAAAA,CAAAA,mBAAAA,CAAAA,YAAAA,CAAAA,uBAAAA,CAAAA,8BAAAA,CAAAA,oBAAAA,CAAAA,sBAAAA,CAAAA,UAAAA,CAAAA,WAAAA,CAAAA;AAONC,SAAAA,SAAAA,CAAAA,uBAAAA,CAAAA,cAAAA,CAAAA,oBAAAA,CAAAA,+BAAAA,CAAAA,2BAAAA,CAAAA,uBAAAA,CAAAA;AAOQC,SAAAA,SAAAA,CAAAA,uBAAAA,CAAAA,cAAAA,CAAAA,oBAAAA,CAAAA,+BAAAA,CAAAA,2BAAAA,CAAAA,uBAAAA,CAAAA,wGAAAA,CAAAA,gGAAAA,CAAAA,CAAAA,yCAAAA,GAAAA,sBAAAA,CAAAA,mBAAAA,CAAAA,CAAAA,IAAAA,uBAAAA,CAAAA,qBAAAA,CAAAA,CAAAA,KAAAA,uBAAAA,CAAAA,sBAAAA,CAAAA,CAAAA,CAAAA,iCAAAA,GAAAA,sBAAAA,CAAAA,mBAAAA,CAAAA,CAAAA,IAAAA,uBAAAA,CAAAA,qBAAAA,CAAAA,CAAAA,KAAAA,uBAAAA,CAAAA,sBAAAA,CAAAA,CAAAA,CAAAA,yCAAAA,CAAAA,gCAAAA,CAAAA,4BAAAA,CAAAA,wBAAAA,CAAAA,CAAAA,CAAAA,iCAAAA,CAAAA,gCAAAA,CAAAA,4BAAAA,CAAAA,wBAAAA,CAAAA,CAAAA;ACvBvB,usFAAusF,C;;;;ACErrFC,UAAAA,aAAAA,CAAAA,oDAAAA,CAAAA,cAAAA,CAAAA,iBAAAA,CAAAA;AAMOC,UAAAA,0BAAAA,CAAAA,wBAAAA,CAAAA,qBAAAA,CAAAA,kBAAAA,CAAAA,+BAAAA,CAAAA,0BAAAA,CAAAA,iBAAAA,CAAAA,kBAAAA,CAAAA,8BAAAA,CAAAA,cAAAA,CAAAA,mBAAAA,CAAAA,oBAAAA,CAAAA,mBAAAA,CAAAA,YAAAA,CAAAA,sBAAAA,CAAAA,kBAAAA,CAAAA,cAAAA,CAAAA,wBAAAA,CAAAA,qCAAAA,CAAAA,qBAAAA,CAAAA,6BAAAA,CAAAA,eAAAA,CAAAA,oBAAAA,CAAAA,iBAAAA,CAAAA,4BAAAA,CAAAA,oBAAAA,CAAAA,qBAAAA,CAAAA,4BAAAA,CAAAA,CAAAA,gBAAAA,0BAAAA,CAAAA;AAqBFC,UAAAA,0BAAAA,CAAAA,wBAAAA,CAAAA,qBAAAA,CAAAA,kBAAAA,CAAAA,mBAAAA,CAAAA,oBAAAA,CAAAA,mBAAAA,CAAAA,YAAAA,CAAAA,cAAAA,CAAAA,UAAAA,CAAAA,MAAAA,CAAAA,sBAAAA,CAAAA,kBAAAA,CAAAA,cAAAA,CAAAA,eAAAA,CAAAA,iBAAAA,CAAAA,eAAAA,CAAAA,qBAAAA,CAAAA;AAUHC,UAAAA,mBAAAA,CAAAA,eAAAA,CAAAA,gBAAAA,CAAAA,iBAAAA,CAAAA,OAAAA,CAAAA,kCAAAA,CAAAA,8BAAAA,CAAAA,0BAAAA,CAAAA,qBAAAA,CAAAA,cAAAA,CAAAA;AAUAC,UAAAA,mBAAAA,CAAAA,eAAAA,CAAAA,gBAAAA,CAAAA,0BAAAA,CAAAA,eAAAA,CAAAA,iBAAAA,CAAAA,sBAAAA,CAAAA,kBAAAA,CAAAA,OAAAA,CAAAA,kCAAAA,CAAAA,8BAAAA,CAAAA,0BAAAA,CAAAA,qBAAAA,CAAAA;AAaOC,UAAAA,0BAAAA,CAAAA,wBAAAA,CAAAA,qBAAAA,CAAAA,kBAAAA,CAAAA,0BAAAA,CAAAA,2BAAAA,CAAAA,kBAAAA,CAAAA,mBAAAA,CAAAA,oBAAAA,CAAAA,mBAAAA,CAAAA,YAAAA,CAAAA,qBAAAA,CAAAA,mBAAAA,CAAAA,aAAAA,CAAAA,qBAAAA,CAAAA;AAODC,UAAAA,4BAAAA,CAAAA,iCAAAA,CAAAA,kCAAAA,CAAAA,SAAAA,CAAAA,UAAAA,CAAAA,WAAAA,CAAAA;AAQHC,QAAAA,UAAAA,CAAAA,kBAAAA,CAAAA,eAAAA,CAAAA,kBAAAA,CAAAA,mBAAAA,CAAAA,qBAAAA,CAAAA;AAQTC,SAAAA,sBAAAA,CAAAA,sDAAAA,CAAAA,eAAAA,CAAAA,iBAAAA,CAAAA,SAAAA,CAAAA,6BAAAA,CAAAA,WAAAA,CAAAA,aAAAA,CAAAA,mBAAAA,CAAAA;AAWMC,SAAAA,iBAAAA,CAAAA,SAAAA,CAAAA,iBAAAA,CAAAA;AAKEC,SAAAA,iBAAAA,CAAAA,QAAAA,CAAAA,qBAAAA,CAAAA,iBAAAA,CAAAA,iBAAAA,CAAAA,cAAAA,CAAAA,YAAAA,CAAAA,mEAAAA,CAAAA,UAAAA,CAAAA;AAWLC,SAAAA,gBAAAA,CAAAA,eAAAA,CAAAA,kBAAAA,CAAAA,eAAAA,CAAAA,iBAAAA,CAAAA;AAOCC,SAAAA,kBAAAA,CAAAA,eAAAA,CAAAA;AAIMC,UAAAA,UAAAA,CAAAA,cAAAA,CAAAA,aAAAA,CAAAA,eAAAA,CAAAA,oBAAAA,CAAAA,wBAAAA,CAAAA,iBAAAA,CAAAA,iBAAAA,CAAAA;AAUPC,UAAAA,aAAAA,CAAAA,kCAAAA,CAAAA,uBAAAA,CAAAA,cAAAA,CAAAA,iBAAAA,CAAAA,UAAAA,CAAAA,gBAAAA,CAAAA,CAAAA,gBAAAA,kCAAAA,CAAAA;AC1HjB,ugVAAugV,C;;;;ACZh/UC,UAAAA,wBAAAA,CAAAA,oBAAAA,CAAAA,aAAAA,CAAAA,cAAAA,CAAAA,0BAAAA,CAAAA,wBAAAA,CAAAA,qBAAAA,CAAAA,kBAAAA,CAAAA,wBAAAA,CAAAA,qCAAAA,CAAAA,qBAAAA,CAAAA,6BAAAA,CAAAA,mBAAAA,CAAAA,oBAAAA,CAAAA,mBAAAA,CAAAA,YAAAA,CAAAA,kBAAAA,CAAAA,sBAAAA,CAAAA,wBAAAA,CAAAA,yBAAAA,CAAAA,uBAAAA,CAAAA,gBAAAA,CAAAA,eAAAA,CAAAA,gBAAAA,CAAAA,iBAAAA,CAAAA,eAAAA,CAAAA;AAmBTC,SAAAA,yBAAAA,CAAAA,iBAAAA,CAAAA,eAAAA,CAAAA,cAAAA,CAAAA,gBAAAA,CAAAA,aAAAA,CAAAA,QAAAA,CAAAA,SAAAA,CAAAA;AAUEC,UAAAA,yBAAAA,CAAAA,iBAAAA,CAAAA,eAAAA,CAAAA,cAAAA,CAAAA,QAAAA,CAAAA,SAAAA,CAAAA;AAQSC,SAAAA,mBAAAA,CAAAA,oBAAAA,CAAAA,mBAAAA,CAAAA,YAAAA,CAAAA,6BAAAA,CAAAA,yBAAAA,CAAAA,qBAAAA,CAAAA;ACpCzB,+zEAA+zE,C","sources":["webpack://leadin/./scripts/gutenberg/UIComponents/UIImage.ts","webpack://leadin/./scripts/gutenberg/UIComponents/UIImage.ts","webpack://leadin/./scripts/shared/UIComponents/UIButton.ts","webpack://leadin/./scripts/shared/UIComponents/UIButton.ts","webpack://leadin/./scripts/shared/UIComponents/UIContainer.ts","webpack://leadin/./scripts/shared/UIComponents/UIContainer.ts","webpack://leadin/./scripts/shared/Common/HubspotWrapper.ts","webpack://leadin/./scripts/shared/Common/HubspotWrapper.ts","webpack://leadin/./scripts/shared/UIComponents/UISpacer.ts","webpack://leadin/./scripts/shared/UIComponents/UISpacer.ts","webpack://leadin/./scripts/shared/UIComponents/UIOverlay.ts","webpack://leadin/./scripts/shared/UIComponents/UIOverlay.ts","webpack://leadin/./scripts/shared/UIComponents/UISpinner.tsx","webpack://leadin/./scripts/shared/UIComponents/UISpinner.tsx","webpack://leadin/./scripts/shared/Common/AsyncSelect.tsx","webpack://leadin/./scripts/shared/Common/AsyncSelect.tsx","webpack://leadin/./scripts/shared/UIComponents/UIAlert.tsx","webpack://leadin/./scripts/shared/UIComponents/UIAlert.tsx"],"sourcesContent":["import { styled } from '@linaria/react';\nexport default styled.img `\n height: ${props => (props.height ? props.height : 'auto')};\n width: ${props => (props.width ? props.width : 'auto')};\n`;\n",".ump7xqy{height:var(--ump7xqy-0);width:var(--ump7xqy-1);}\n/*# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIi91c3Ivc2hhcmUvaHVic3BvdC9idWlsZC93b3Jrc3BhY2UvTGVhZGluV29yZFByZXNzUGx1Z2luL2xlYWRpbi9zY3JpcHRzL2d1dGVuYmVyZy9VSUNvbXBvbmVudHMvVUlJbWFnZS50cyJdLCJuYW1lcyI6WyIudW1wN3hxeSJdLCJtYXBwaW5ncyI6IkFBQ2VBIiwiZmlsZSI6Ii91c3Ivc2hhcmUvaHVic3BvdC9idWlsZC93b3Jrc3BhY2UvTGVhZGluV29yZFByZXNzUGx1Z2luL2xlYWRpbi9zY3JpcHRzL2d1dGVuYmVyZy9VSUNvbXBvbmVudHMvVUlJbWFnZS50cyIsInNvdXJjZXNDb250ZW50IjpbImltcG9ydCB7IHN0eWxlZCB9IGZyb20gJ0BsaW5hcmlhL3JlYWN0JztcbmV4cG9ydCBkZWZhdWx0IHN0eWxlZC5pbWcgYFxuICBoZWlnaHQ6ICR7cHJvcHMgPT4gKHByb3BzLmhlaWdodCA/IHByb3BzLmhlaWdodCA6ICdhdXRvJyl9O1xuICB3aWR0aDogJHtwcm9wcyA9PiAocHJvcHMud2lkdGggPyBwcm9wcy53aWR0aCA6ICdhdXRvJyl9O1xuYDtcbiJdfQ==*/","import { styled } from '@linaria/react';\nimport { HEFFALUMP, LORAX, OLAF } from './colors';\nexport default styled.button `\n background-color:${props => (props.use === 'tertiary' ? HEFFALUMP : LORAX)};\n border: 3px solid ${props => (props.use === 'tertiary' ? HEFFALUMP : LORAX)};\n color: ${OLAF}\n border-radius: 3px;\n font-size: 14px;\n line-height: 14px;\n padding: 12px 24px;\n font-family: 'Lexend Deca', Helvetica, Arial, sans-serif;\n font-weight: 500;\n white-space: nowrap;\n`;\n",".ug152ch{background-color:var(--ug152ch-0);border:3px solid var(--ug152ch-0);color:#ffffff;border-radius:3px;font-size:14px;line-height:14px;padding:12px 24px;font-family:'Lexend Deca',Helvetica,Arial,sans-serif;font-weight:500;white-space:nowrap;}\n/*# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIi91c3Ivc2hhcmUvaHVic3BvdC9idWlsZC93b3Jrc3BhY2UvTGVhZGluV29yZFByZXNzUGx1Z2luL2xlYWRpbi9zY3JpcHRzL3NoYXJlZC9VSUNvbXBvbmVudHMvVUlCdXR0b24udHMiXSwibmFtZXMiOlsiLnVnMTUyY2giXSwibWFwcGluZ3MiOiJBQUVlQSIsImZpbGUiOiIvdXNyL3NoYXJlL2h1YnNwb3QvYnVpbGQvd29ya3NwYWNlL0xlYWRpbldvcmRQcmVzc1BsdWdpbi9sZWFkaW4vc2NyaXB0cy9zaGFyZWQvVUlDb21wb25lbnRzL1VJQnV0dG9uLnRzIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsgc3R5bGVkIH0gZnJvbSAnQGxpbmFyaWEvcmVhY3QnO1xuaW1wb3J0IHsgSEVGRkFMVU1QLCBMT1JBWCwgT0xBRiB9IGZyb20gJy4vY29sb3JzJztcbmV4cG9ydCBkZWZhdWx0IHN0eWxlZC5idXR0b24gYFxuICBiYWNrZ3JvdW5kLWNvbG9yOiR7cHJvcHMgPT4gKHByb3BzLnVzZSA9PT0gJ3RlcnRpYXJ5JyA/IEhFRkZBTFVNUCA6IExPUkFYKX07XG4gIGJvcmRlcjogM3B4IHNvbGlkICR7cHJvcHMgPT4gKHByb3BzLnVzZSA9PT0gJ3RlcnRpYXJ5JyA/IEhFRkZBTFVNUCA6IExPUkFYKX07XG4gIGNvbG9yOiAke09MQUZ9XG4gIGJvcmRlci1yYWRpdXM6IDNweDtcbiAgZm9udC1zaXplOiAxNHB4O1xuICBsaW5lLWhlaWdodDogMTRweDtcbiAgcGFkZGluZzogMTJweCAyNHB4O1xuICBmb250LWZhbWlseTogJ0xleGVuZCBEZWNhJywgSGVsdmV0aWNhLCBBcmlhbCwgc2Fucy1zZXJpZjtcbiAgZm9udC13ZWlnaHQ6IDUwMDtcbiAgd2hpdGUtc3BhY2U6IG5vd3JhcDtcbmA7XG4iXX0=*/","import { styled } from '@linaria/react';\nexport default styled.div `\n text-align: ${props => (props.textAlign ? props.textAlign : 'inherit')};\n`;\n",".ua13n1c{text-align:var(--ua13n1c-0);}\n/*# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIi91c3Ivc2hhcmUvaHVic3BvdC9idWlsZC93b3Jrc3BhY2UvTGVhZGluV29yZFByZXNzUGx1Z2luL2xlYWRpbi9zY3JpcHRzL3NoYXJlZC9VSUNvbXBvbmVudHMvVUlDb250YWluZXIudHMiXSwibmFtZXMiOlsiLnVhMTNuMWMiXSwibWFwcGluZ3MiOiJBQUNlQSIsImZpbGUiOiIvdXNyL3NoYXJlL2h1YnNwb3QvYnVpbGQvd29ya3NwYWNlL0xlYWRpbldvcmRQcmVzc1BsdWdpbi9sZWFkaW4vc2NyaXB0cy9zaGFyZWQvVUlDb21wb25lbnRzL1VJQ29udGFpbmVyLnRzIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsgc3R5bGVkIH0gZnJvbSAnQGxpbmFyaWEvcmVhY3QnO1xuZXhwb3J0IGRlZmF1bHQgc3R5bGVkLmRpdiBgXG4gIHRleHQtYWxpZ246ICR7cHJvcHMgPT4gKHByb3BzLnRleHRBbGlnbiA/IHByb3BzLnRleHRBbGlnbiA6ICdpbmhlcml0Jyl9O1xuYDtcbiJdfQ==*/","import { styled } from '@linaria/react';\nexport default styled.div `\n background-image: ${props => `url(${props.pluginPath}/public/assets/images/hubspot.svg)`};\n background-color: #f5f8fa;\n background-repeat: no-repeat;\n background-position: center 25px;\n background-size: 120px;\n color: #33475b;\n font-family: 'Lexend Deca', Helvetica, Arial, sans-serif;\n font-size: 14px;\n\n padding: ${(props) => props.padding || '90px 20% 25px'};\n\n p {\n font-size: inherit !important;\n line-height: 24px;\n margin: 4px 0;\n }\n`;\n",".h1q5v5ee{background-image:var(--h1q5v5ee-0);background-color:#f5f8fa;background-repeat:no-repeat;background-position:center 25px;background-size:120px;color:#33475b;font-family:'Lexend Deca',Helvetica,Arial,sans-serif;font-size:14px;padding:var(--h1q5v5ee-1);}.h1q5v5ee p{font-size:inherit !important;line-height:24px;margin:4px 0;}\n/*# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIi91c3Ivc2hhcmUvaHVic3BvdC9idWlsZC93b3Jrc3BhY2UvTGVhZGluV29yZFByZXNzUGx1Z2luL2xlYWRpbi9zY3JpcHRzL3NoYXJlZC9Db21tb24vSHVic3BvdFdyYXBwZXIudHMiXSwibmFtZXMiOlsiLmgxcTV2NWVlIl0sIm1hcHBpbmdzIjoiQUFDZUEiLCJmaWxlIjoiL3Vzci9zaGFyZS9odWJzcG90L2J1aWxkL3dvcmtzcGFjZS9MZWFkaW5Xb3JkUHJlc3NQbHVnaW4vbGVhZGluL3NjcmlwdHMvc2hhcmVkL0NvbW1vbi9IdWJzcG90V3JhcHBlci50cyIsInNvdXJjZXNDb250ZW50IjpbImltcG9ydCB7IHN0eWxlZCB9IGZyb20gJ0BsaW5hcmlhL3JlYWN0JztcbmV4cG9ydCBkZWZhdWx0IHN0eWxlZC5kaXYgYFxuICBiYWNrZ3JvdW5kLWltYWdlOiAke3Byb3BzID0+IGB1cmwoJHtwcm9wcy5wbHVnaW5QYXRofS9wdWJsaWMvYXNzZXRzL2ltYWdlcy9odWJzcG90LnN2ZylgfTtcbiAgYmFja2dyb3VuZC1jb2xvcjogI2Y1ZjhmYTtcbiAgYmFja2dyb3VuZC1yZXBlYXQ6IG5vLXJlcGVhdDtcbiAgYmFja2dyb3VuZC1wb3NpdGlvbjogY2VudGVyIDI1cHg7XG4gIGJhY2tncm91bmQtc2l6ZTogMTIwcHg7XG4gIGNvbG9yOiAjMzM0NzViO1xuICBmb250LWZhbWlseTogJ0xleGVuZCBEZWNhJywgSGVsdmV0aWNhLCBBcmlhbCwgc2Fucy1zZXJpZjtcbiAgZm9udC1zaXplOiAxNHB4O1xuXG4gIHBhZGRpbmc6ICR7KHByb3BzKSA9PiBwcm9wcy5wYWRkaW5nIHx8ICc5MHB4IDIwJSAyNXB4J307XG5cbiAgcCB7XG4gICAgZm9udC1zaXplOiBpbmhlcml0ICFpbXBvcnRhbnQ7XG4gICAgbGluZS1oZWlnaHQ6IDI0cHg7XG4gICAgbWFyZ2luOiA0cHggMDtcbiAgfVxuYDtcbiJdfQ==*/","import { styled } from '@linaria/react';\nexport default styled.div `\n height: 30px;\n`;\n",".u3qxofx{height:30px;}\n/*# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIi91c3Ivc2hhcmUvaHVic3BvdC9idWlsZC93b3Jrc3BhY2UvTGVhZGluV29yZFByZXNzUGx1Z2luL2xlYWRpbi9zY3JpcHRzL3NoYXJlZC9VSUNvbXBvbmVudHMvVUlTcGFjZXIudHMiXSwibmFtZXMiOlsiLnUzcXhvZngiXSwibWFwcGluZ3MiOiJBQUNlQSIsImZpbGUiOiIvdXNyL3NoYXJlL2h1YnNwb3QvYnVpbGQvd29ya3NwYWNlL0xlYWRpbldvcmRQcmVzc1BsdWdpbi9sZWFkaW4vc2NyaXB0cy9zaGFyZWQvVUlDb21wb25lbnRzL1VJU3BhY2VyLnRzIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsgc3R5bGVkIH0gZnJvbSAnQGxpbmFyaWEvcmVhY3QnO1xuZXhwb3J0IGRlZmF1bHQgc3R5bGVkLmRpdiBgXG4gIGhlaWdodDogMzBweDtcbmA7XG4iXX0=*/","import { styled } from '@linaria/react';\nexport default styled.div `\n position: relative;\n\n &:after {\n content: '';\n position: absolute;\n top: 0;\n bottom: 0;\n right: 0;\n left: 0;\n }\n`;\n",".u1q7a48k{position:relative;}.u1q7a48k:after{content:'';position:absolute;top:0;bottom:0;right:0;left:0;}\n/*# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIi91c3Ivc2hhcmUvaHVic3BvdC9idWlsZC93b3Jrc3BhY2UvTGVhZGluV29yZFByZXNzUGx1Z2luL2xlYWRpbi9zY3JpcHRzL3NoYXJlZC9VSUNvbXBvbmVudHMvVUlPdmVybGF5LnRzIl0sIm5hbWVzIjpbIi51MXE3YTQ4ayJdLCJtYXBwaW5ncyI6IkFBQ2VBIiwiZmlsZSI6Ii91c3Ivc2hhcmUvaHVic3BvdC9idWlsZC93b3Jrc3BhY2UvTGVhZGluV29yZFByZXNzUGx1Z2luL2xlYWRpbi9zY3JpcHRzL3NoYXJlZC9VSUNvbXBvbmVudHMvVUlPdmVybGF5LnRzIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsgc3R5bGVkIH0gZnJvbSAnQGxpbmFyaWEvcmVhY3QnO1xuZXhwb3J0IGRlZmF1bHQgc3R5bGVkLmRpdiBgXG4gIHBvc2l0aW9uOiByZWxhdGl2ZTtcblxuICAmOmFmdGVyIHtcbiAgICBjb250ZW50OiAnJztcbiAgICBwb3NpdGlvbjogYWJzb2x1dGU7XG4gICAgdG9wOiAwO1xuICAgIGJvdHRvbTogMDtcbiAgICByaWdodDogMDtcbiAgICBsZWZ0OiAwO1xuICB9XG5gO1xuIl19*/","import { jsx as _jsx, jsxs as _jsxs } from \"react/jsx-runtime\";\nimport { styled } from '@linaria/react';\nimport { CALYPSO_MEDIUM, CALYPSO } from './colors';\nconst SpinnerOuter = styled.div `\n align-items: center;\n color: #00a4bd;\n display: flex;\n flex-direction: column;\n justify-content: center;\n width: 100%;\n height: 100%;\n margin: '2px';\n`;\nconst SpinnerInner = styled.div `\n align-items: center;\n display: flex;\n justify-content: center;\n width: 100%;\n height: 100%;\n`;\nconst Circle = styled.circle `\n fill: none;\n stroke: ${props => props.color};\n stroke-width: 5;\n stroke-linecap: round;\n transform-origin: center;\n`;\nconst AnimatedCircle = styled.circle `\n fill: none;\n stroke: ${props => props.color};\n stroke-width: 5;\n stroke-linecap: round;\n transform-origin: center;\n animation: dashAnimation 2s ease-in-out infinite,\n spinAnimation 2s linear infinite;\n\n @keyframes dashAnimation {\n 0% {\n stroke-dasharray: 1, 150;\n stroke-dashoffset: 0;\n }\n\n 50% {\n stroke-dasharray: 90, 150;\n stroke-dashoffset: -50;\n }\n\n 100% {\n stroke-dasharray: 90, 150;\n stroke-dashoffset: -140;\n }\n }\n\n @keyframes spinAnimation {\n transform: rotate(360deg);\n }\n`;\nexport default function UISpinner({ size = 20 }) {\n return (_jsx(SpinnerOuter, { children: _jsx(SpinnerInner, { children: _jsxs(\"svg\", { height: size, width: size, viewBox: \"0 0 50 50\", children: [_jsx(Circle, { color: CALYPSO_MEDIUM, cx: \"25\", cy: \"25\", r: \"22.5\" }), _jsx(AnimatedCircle, { color: CALYPSO, cx: \"25\", cy: \"25\", r: \"22.5\" })] }) }) }));\n}\n",".sxa9zrc{-webkit-align-items:center;-webkit-box-align:center;-ms-flex-align:center;align-items:center;color:#00a4bd;display:-webkit-box;display:-webkit-flex;display:-ms-flexbox;display:flex;-webkit-flex-direction:column;-ms-flex-direction:column;flex-direction:column;-webkit-box-pack:center;-webkit-justify-content:center;-ms-flex-pack:center;justify-content:center;width:100%;height:100%;margin:'2px';}\n.s14430wa{-webkit-align-items:center;-webkit-box-align:center;-ms-flex-align:center;align-items:center;display:-webkit-box;display:-webkit-flex;display:-ms-flexbox;display:flex;-webkit-box-pack:center;-webkit-justify-content:center;-ms-flex-pack:center;justify-content:center;width:100%;height:100%;}\n.ct87ghk{fill:none;stroke:var(--ct87ghk-0);stroke-width:5;stroke-linecap:round;-webkit-transform-origin:center;-ms-transform-origin:center;transform-origin:center;}\n.avili0h{fill:none;stroke:var(--avili0h-0);stroke-width:5;stroke-linecap:round;-webkit-transform-origin:center;-ms-transform-origin:center;transform-origin:center;-webkit-animation:dashAnimation-avili0h 2s ease-in-out infinite,spinAnimation-avili0h 2s linear infinite;animation:dashAnimation-avili0h 2s ease-in-out infinite,spinAnimation-avili0h 2s linear infinite;}@-webkit-keyframes dashAnimation-avili0h{0%{stroke-dasharray:1,150;stroke-dashoffset:0;}50%{stroke-dasharray:90,150;stroke-dashoffset:-50;}100%{stroke-dasharray:90,150;stroke-dashoffset:-140;}}@keyframes dashAnimation-avili0h{0%{stroke-dasharray:1,150;stroke-dashoffset:0;}50%{stroke-dasharray:90,150;stroke-dashoffset:-50;}100%{stroke-dasharray:90,150;stroke-dashoffset:-140;}}@-webkit-keyframes spinAnimation-avili0h{{-webkit-transform:rotate(360deg);-ms-transform:rotate(360deg);transform:rotate(360deg);}}@keyframes spinAnimation-avili0h{{-webkit-transform:rotate(360deg);-ms-transform:rotate(360deg);transform:rotate(360deg);}}\n/*# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIi91c3Ivc2hhcmUvaHVic3BvdC9idWlsZC93b3Jrc3BhY2UvTGVhZGluV29yZFByZXNzUGx1Z2luL2xlYWRpbi9zY3JpcHRzL3NoYXJlZC9VSUNvbXBvbmVudHMvVUlTcGlubmVyLnRzeCJdLCJuYW1lcyI6WyIuc3hhOXpyYyIsIi5zMTQ0MzB3YSIsIi5jdDg3Z2hrIiwiLmF2aWxpMGgiXSwibWFwcGluZ3MiOiJBQUdxQkE7QUFVQUM7QUFPTkM7QUFPUUMiLCJmaWxlIjoiL3Vzci9zaGFyZS9odWJzcG90L2J1aWxkL3dvcmtzcGFjZS9MZWFkaW5Xb3JkUHJlc3NQbHVnaW4vbGVhZGluL3NjcmlwdHMvc2hhcmVkL1VJQ29tcG9uZW50cy9VSVNwaW5uZXIudHN4Iiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsganN4IGFzIF9qc3gsIGpzeHMgYXMgX2pzeHMgfSBmcm9tIFwicmVhY3QvanN4LXJ1bnRpbWVcIjtcbmltcG9ydCB7IHN0eWxlZCB9IGZyb20gJ0BsaW5hcmlhL3JlYWN0JztcbmltcG9ydCB7IENBTFlQU09fTUVESVVNLCBDQUxZUFNPIH0gZnJvbSAnLi9jb2xvcnMnO1xuY29uc3QgU3Bpbm5lck91dGVyID0gc3R5bGVkLmRpdiBgXG4gIGFsaWduLWl0ZW1zOiBjZW50ZXI7XG4gIGNvbG9yOiAjMDBhNGJkO1xuICBkaXNwbGF5OiBmbGV4O1xuICBmbGV4LWRpcmVjdGlvbjogY29sdW1uO1xuICBqdXN0aWZ5LWNvbnRlbnQ6IGNlbnRlcjtcbiAgd2lkdGg6IDEwMCU7XG4gIGhlaWdodDogMTAwJTtcbiAgbWFyZ2luOiAnMnB4JztcbmA7XG5jb25zdCBTcGlubmVySW5uZXIgPSBzdHlsZWQuZGl2IGBcbiAgYWxpZ24taXRlbXM6IGNlbnRlcjtcbiAgZGlzcGxheTogZmxleDtcbiAganVzdGlmeS1jb250ZW50OiBjZW50ZXI7XG4gIHdpZHRoOiAxMDAlO1xuICBoZWlnaHQ6IDEwMCU7XG5gO1xuY29uc3QgQ2lyY2xlID0gc3R5bGVkLmNpcmNsZSBgXG4gIGZpbGw6IG5vbmU7XG4gIHN0cm9rZTogJHtwcm9wcyA9PiBwcm9wcy5jb2xvcn07XG4gIHN0cm9rZS13aWR0aDogNTtcbiAgc3Ryb2tlLWxpbmVjYXA6IHJvdW5kO1xuICB0cmFuc2Zvcm0tb3JpZ2luOiBjZW50ZXI7XG5gO1xuY29uc3QgQW5pbWF0ZWRDaXJjbGUgPSBzdHlsZWQuY2lyY2xlIGBcbiAgZmlsbDogbm9uZTtcbiAgc3Ryb2tlOiAke3Byb3BzID0+IHByb3BzLmNvbG9yfTtcbiAgc3Ryb2tlLXdpZHRoOiA1O1xuICBzdHJva2UtbGluZWNhcDogcm91bmQ7XG4gIHRyYW5zZm9ybS1vcmlnaW46IGNlbnRlcjtcbiAgYW5pbWF0aW9uOiBkYXNoQW5pbWF0aW9uIDJzIGVhc2UtaW4tb3V0IGluZmluaXRlLFxuICAgIHNwaW5BbmltYXRpb24gMnMgbGluZWFyIGluZmluaXRlO1xuXG4gIEBrZXlmcmFtZXMgZGFzaEFuaW1hdGlvbiB7XG4gICAgMCUge1xuICAgICAgc3Ryb2tlLWRhc2hhcnJheTogMSwgMTUwO1xuICAgICAgc3Ryb2tlLWRhc2hvZmZzZXQ6IDA7XG4gICAgfVxuXG4gICAgNTAlIHtcbiAgICAgIHN0cm9rZS1kYXNoYXJyYXk6IDkwLCAxNTA7XG4gICAgICBzdHJva2UtZGFzaG9mZnNldDogLTUwO1xuICAgIH1cblxuICAgIDEwMCUge1xuICAgICAgc3Ryb2tlLWRhc2hhcnJheTogOTAsIDE1MDtcbiAgICAgIHN0cm9rZS1kYXNob2Zmc2V0OiAtMTQwO1xuICAgIH1cbiAgfVxuXG4gIEBrZXlmcmFtZXMgc3BpbkFuaW1hdGlvbiB7XG4gICAgdHJhbnNmb3JtOiByb3RhdGUoMzYwZGVnKTtcbiAgfVxuYDtcbmV4cG9ydCBkZWZhdWx0IGZ1bmN0aW9uIFVJU3Bpbm5lcih7IHNpemUgPSAyMCB9KSB7XG4gICAgcmV0dXJuIChfanN4KFNwaW5uZXJPdXRlciwgeyBjaGlsZHJlbjogX2pzeChTcGlubmVySW5uZXIsIHsgY2hpbGRyZW46IF9qc3hzKFwic3ZnXCIsIHsgaGVpZ2h0OiBzaXplLCB3aWR0aDogc2l6ZSwgdmlld0JveDogXCIwIDAgNTAgNTBcIiwgY2hpbGRyZW46IFtfanN4KENpcmNsZSwgeyBjb2xvcjogQ0FMWVBTT19NRURJVU0sIGN4OiBcIjI1XCIsIGN5OiBcIjI1XCIsIHI6IFwiMjIuNVwiIH0pLCBfanN4KEFuaW1hdGVkQ2lyY2xlLCB7IGNvbG9yOiBDQUxZUFNPLCBjeDogXCIyNVwiLCBjeTogXCIyNVwiLCByOiBcIjIyLjVcIiB9KV0gfSkgfSkgfSkpO1xufVxuIl19*/","import { jsx as _jsx, jsxs as _jsxs } from \"react/jsx-runtime\";\nimport { useRef, useState, useEffect } from 'react';\nimport { styled } from '@linaria/react';\nimport { CALYPSO, CALYPSO_LIGHT, CALYPSO_MEDIUM, OBSIDIAN, } from '../UIComponents/colors';\nimport UISpinner from '../UIComponents/UISpinner';\nimport LoadState from '../enums/loadState';\nconst Container = styled.div `\n color: ${OBSIDIAN};\n font-family: 'Lexend Deca', Helvetica, Arial, sans-serif;\n font-size: 14px;\n position: relative;\n`;\nconst ControlContainer = styled.div `\n align-items: center;\n background-color: hsl(0, 0%, 100%);\n border-color: hsl(0, 0%, 80%);\n border-radius: 4px;\n border-style: solid;\n border-width: ${props => (props.focused ? '0' : '1px')};\n cursor: default;\n display: flex;\n flex-wrap: wrap;\n justify-content: space-between;\n min-height: 38px;\n outline: 0 !important;\n position: relative;\n transition: all 100ms;\n box-sizing: border-box;\n box-shadow: ${props => props.focused ? `0 0 0 2px ${CALYPSO_MEDIUM}` : 'none'};\n &:hover {\n border-color: hsl(0, 0%, 70%);\n }\n`;\nconst ValueContainer = styled.div `\n align-items: center;\n display: flex;\n flex: 1;\n flex-wrap: wrap;\n padding: 2px 8px;\n position: relative;\n overflow: hidden;\n box-sizing: border-box;\n`;\nconst Placeholder = styled.div `\n color: hsl(0, 0%, 50%);\n margin-left: 2px;\n margin-right: 2px;\n position: absolute;\n top: 50%;\n transform: translateY(-50%);\n box-sizing: border-box;\n font-size: 16px;\n`;\nconst SingleValue = styled.div `\n color: hsl(0, 0%, 20%);\n margin-left: 2px;\n margin-right: 2px;\n max-width: calc(100% - 8px);\n overflow: hidden;\n position: absolute;\n text-overflow: ellipsis;\n white-space: nowrap;\n top: 50%;\n transform: translateY(-50%);\n box-sizing: border-box;\n`;\nconst IndicatorContainer = styled.div `\n align-items: center;\n align-self: stretch;\n display: flex;\n flex-shrink: 0;\n box-sizing: border-box;\n`;\nconst DropdownIndicator = styled.div `\n border-top: 8px solid ${CALYPSO};\n border-left: 6px solid transparent;\n border-right: 6px solid transparent;\n width: 0px;\n height: 0px;\n margin: 10px;\n`;\nconst InputContainer = styled.div `\n margin: 2px;\n padding-bottom: 2px;\n padding-top: 2px;\n visibility: visible;\n color: hsl(0, 0%, 20%);\n box-sizing: border-box;\n`;\nconst Input = styled.input `\n box-sizing: content-box;\n background: rgba(0, 0, 0, 0) none repeat scroll 0px center;\n border: 0px none;\n font-size: inherit;\n opacity: 1;\n outline: currentcolor none 0px;\n padding: 0px;\n color: inherit;\n font-family: inherit;\n`;\nconst InputShadow = styled.div `\n position: absolute;\n opacity: 0;\n font-size: inherit;\n`;\nconst MenuContainer = styled.div `\n position: absolute;\n top: 100%;\n background-color: #fff;\n border-radius: 4px;\n margin-bottom: 8px;\n margin-top: 8px;\n z-index: 9999;\n box-shadow: 0 0 0 1px hsla(0, 0%, 0%, 0.1), 0 4px 11px hsla(0, 0%, 0%, 0.1);\n width: 100%;\n`;\nconst MenuList = styled.div `\n max-height: 300px;\n overflow-y: auto;\n padding-bottom: 4px;\n padding-top: 4px;\n position: relative;\n`;\nconst MenuGroup = styled.div `\n padding-bottom: 8px;\n padding-top: 8px;\n`;\nconst MenuGroupHeader = styled.div `\n color: #999;\n cursor: default;\n font-size: 75%;\n font-weight: 500;\n margin-bottom: 0.25em;\n text-transform: uppercase;\n padding-left: 12px;\n padding-left: 12px;\n`;\nconst MenuItem = styled.div `\n display: block;\n background-color: ${props => props.selected ? CALYPSO_MEDIUM : 'transparent'};\n color: ${props => (props.selected ? '#fff' : 'inherit')};\n cursor: default;\n font-size: inherit;\n width: 100%;\n padding: 8px 12px;\n &:hover {\n background-color: ${props => props.selected ? CALYPSO_MEDIUM : CALYPSO_LIGHT};\n }\n`;\nexport default function AsyncSelect({ placeholder, value, loadOptions, onChange, defaultOptions, }) {\n const inputEl = useRef(null);\n const inputShadowEl = useRef(null);\n const [isFocused, setFocus] = useState(false);\n const [loadState, setLoadState] = useState(LoadState.NotLoaded);\n const [localValue, setLocalValue] = useState('');\n const [options, setOptions] = useState(defaultOptions);\n const inputSize = `${inputShadowEl.current ? inputShadowEl.current.clientWidth + 10 : 2}px`;\n useEffect(() => {\n if (loadOptions && loadState === LoadState.NotLoaded) {\n loadOptions('', (result) => {\n setOptions(result);\n setLoadState(LoadState.Idle);\n });\n }\n }, [loadOptions, loadState]);\n const renderItems = (items = [], parentKey) => {\n return items.map((item, index) => {\n if (item.options) {\n return (_jsxs(MenuGroup, { children: [_jsx(MenuGroupHeader, { id: `${index}-heading`, children: item.label }), _jsx(\"div\", { children: renderItems(item.options, index) })] }, `async-select-item-${index}`));\n }\n else {\n const key = `async-select-item-${parentKey !== undefined ? `${parentKey}-${index}` : index}`;\n return (_jsx(MenuItem, { id: key, selected: value && item.value === value.value, onClick: () => {\n onChange(item);\n setFocus(false);\n }, children: item.label }, key));\n }\n });\n };\n return (_jsxs(Container, { children: [_jsxs(ControlContainer, { id: \"leadin-async-selector\", focused: isFocused, onClick: () => {\n if (isFocused) {\n if (inputEl.current) {\n inputEl.current.blur();\n }\n setFocus(false);\n setLocalValue('');\n }\n else {\n if (inputEl.current) {\n inputEl.current.focus();\n }\n setFocus(true);\n }\n }, children: [_jsxs(ValueContainer, { children: [localValue === '' &&\n (!value ? (_jsx(Placeholder, { children: placeholder })) : (_jsx(SingleValue, { children: value.label }))), _jsxs(InputContainer, { children: [_jsx(Input, { ref: inputEl, onFocus: () => {\n setFocus(true);\n }, onChange: e => {\n setLocalValue(e.target.value);\n setLoadState(LoadState.Loading);\n loadOptions &&\n loadOptions(e.target.value, (result) => {\n setOptions(result);\n setLoadState(LoadState.Idle);\n });\n }, value: localValue, width: inputSize, id: \"asycn-select-input\" }), _jsx(InputShadow, { ref: inputShadowEl, children: localValue })] })] }), _jsxs(IndicatorContainer, { children: [loadState === LoadState.Loading && _jsx(UISpinner, {}), _jsx(DropdownIndicator, {})] })] }), isFocused && (_jsx(MenuContainer, { children: _jsx(MenuList, { children: renderItems(options) }) }))] }));\n}\n",".c1wxx7eu{color:#33475b;font-family:'Lexend Deca',Helvetica,Arial,sans-serif;font-size:14px;position:relative;}\n.c1rgwbep{-webkit-align-items:center;-webkit-box-align:center;-ms-flex-align:center;align-items:center;background-color:hsl(0,0%,100%);border-color:hsl(0,0%,80%);border-radius:4px;border-style:solid;border-width:var(--c1rgwbep-0);cursor:default;display:-webkit-box;display:-webkit-flex;display:-ms-flexbox;display:flex;-webkit-flex-wrap:wrap;-ms-flex-wrap:wrap;flex-wrap:wrap;-webkit-box-pack:justify;-webkit-justify-content:space-between;-ms-flex-pack:justify;justify-content:space-between;min-height:38px;outline:0 !important;position:relative;-webkit-transition:all 100ms;transition:all 100ms;box-sizing:border-box;box-shadow:var(--c1rgwbep-1);}.c1rgwbep:hover{border-color:hsl(0,0%,70%);}\n.v1mdmbaj{-webkit-align-items:center;-webkit-box-align:center;-ms-flex-align:center;align-items:center;display:-webkit-box;display:-webkit-flex;display:-ms-flexbox;display:flex;-webkit-flex:1;-ms-flex:1;flex:1;-webkit-flex-wrap:wrap;-ms-flex-wrap:wrap;flex-wrap:wrap;padding:2px 8px;position:relative;overflow:hidden;box-sizing:border-box;}\n.p1gwkvxy{color:hsl(0,0%,50%);margin-left:2px;margin-right:2px;position:absolute;top:50%;-webkit-transform:translateY(-50%);-ms-transform:translateY(-50%);transform:translateY(-50%);box-sizing:border-box;font-size:16px;}\n.s1bwlafs{color:hsl(0,0%,20%);margin-left:2px;margin-right:2px;max-width:calc(100% - 8px);overflow:hidden;position:absolute;text-overflow:ellipsis;white-space:nowrap;top:50%;-webkit-transform:translateY(-50%);-ms-transform:translateY(-50%);transform:translateY(-50%);box-sizing:border-box;}\n.i196z9y5{-webkit-align-items:center;-webkit-box-align:center;-ms-flex-align:center;align-items:center;-webkit-align-self:stretch;-ms-flex-item-align:stretch;align-self:stretch;display:-webkit-box;display:-webkit-flex;display:-ms-flexbox;display:flex;-webkit-flex-shrink:0;-ms-flex-negative:0;flex-shrink:0;box-sizing:border-box;}\n.d1dfo5ow{border-top:8px solid #00a4bd;border-left:6px solid transparent;border-right:6px solid transparent;width:0px;height:0px;margin:10px;}\n.if3lze{margin:2px;padding-bottom:2px;padding-top:2px;visibility:visible;color:hsl(0,0%,20%);box-sizing:border-box;}\n.i9kxf50{box-sizing:content-box;background:rgba(0,0,0,0) none repeat scroll 0px center;border:0px none;font-size:inherit;opacity:1;outline:currentcolor none 0px;padding:0px;color:inherit;font-family:inherit;}\n.igjr3uc{position:absolute;opacity:0;font-size:inherit;}\n.mhb9if7{position:absolute;top:100%;background-color:#fff;border-radius:4px;margin-bottom:8px;margin-top:8px;z-index:9999;box-shadow:0 0 0 1px hsla(0,0%,0%,0.1),0 4px 11px hsla(0,0%,0%,0.1);width:100%;}\n.mxaof7s{max-height:300px;overflow-y:auto;padding-bottom:4px;padding-top:4px;position:relative;}\n.mw50s5v{padding-bottom:8px;padding-top:8px;}\n.m11rzvjw{color:#999;cursor:default;font-size:75%;font-weight:500;margin-bottom:0.25em;text-transform:uppercase;padding-left:12px;padding-left:12px;}\n.m1jcdsjv{display:block;background-color:var(--m1jcdsjv-0);color:var(--m1jcdsjv-1);cursor:default;font-size:inherit;width:100%;padding:8px 12px;}.m1jcdsjv:hover{background-color:var(--m1jcdsjv-2);}\n/*# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIi91c3Ivc2hhcmUvaHVic3BvdC9idWlsZC93b3Jrc3BhY2UvTGVhZGluV29yZFByZXNzUGx1Z2luL2xlYWRpbi9zY3JpcHRzL3NoYXJlZC9Db21tb24vQXN5bmNTZWxlY3QudHN4Il0sIm5hbWVzIjpbIi5jMXd4eDdldSIsIi5jMXJnd2JlcCIsIi52MW1kbWJhaiIsIi5wMWd3a3Z4eSIsIi5zMWJ3bGFmcyIsIi5pMTk2ejl5NSIsIi5kMWRmbzVvdyIsIi5pZjNsemUiLCIuaTlreGY1MCIsIi5pZ2pyM3VjIiwiLm1oYjlpZjciLCIubXhhb2Y3cyIsIi5tdzUwczV2IiwiLm0xMXJ6dmp3IiwiLm0xamNkc2p2Il0sIm1hcHBpbmdzIjoiQUFNa0JBO0FBTU9DO0FBcUJGQztBQVVIQztBQVVBQztBQWFPQztBQU9EQztBQVFIQztBQVFUQztBQVdNQztBQUtFQztBQVdMQztBQU9DQztBQUlNQztBQVVQQyIsImZpbGUiOiIvdXNyL3NoYXJlL2h1YnNwb3QvYnVpbGQvd29ya3NwYWNlL0xlYWRpbldvcmRQcmVzc1BsdWdpbi9sZWFkaW4vc2NyaXB0cy9zaGFyZWQvQ29tbW9uL0FzeW5jU2VsZWN0LnRzeCIsInNvdXJjZXNDb250ZW50IjpbImltcG9ydCB7IGpzeCBhcyBfanN4LCBqc3hzIGFzIF9qc3hzIH0gZnJvbSBcInJlYWN0L2pzeC1ydW50aW1lXCI7XG5pbXBvcnQgeyB1c2VSZWYsIHVzZVN0YXRlLCB1c2VFZmZlY3QgfSBmcm9tICdyZWFjdCc7XG5pbXBvcnQgeyBzdHlsZWQgfSBmcm9tICdAbGluYXJpYS9yZWFjdCc7XG5pbXBvcnQgeyBDQUxZUFNPLCBDQUxZUFNPX0xJR0hULCBDQUxZUFNPX01FRElVTSwgT0JTSURJQU4sIH0gZnJvbSAnLi4vVUlDb21wb25lbnRzL2NvbG9ycyc7XG5pbXBvcnQgVUlTcGlubmVyIGZyb20gJy4uL1VJQ29tcG9uZW50cy9VSVNwaW5uZXInO1xuaW1wb3J0IExvYWRTdGF0ZSBmcm9tICcuLi9lbnVtcy9sb2FkU3RhdGUnO1xuY29uc3QgQ29udGFpbmVyID0gc3R5bGVkLmRpdiBgXG4gIGNvbG9yOiAke09CU0lESUFOfTtcbiAgZm9udC1mYW1pbHk6ICdMZXhlbmQgRGVjYScsIEhlbHZldGljYSwgQXJpYWwsIHNhbnMtc2VyaWY7XG4gIGZvbnQtc2l6ZTogMTRweDtcbiAgcG9zaXRpb246IHJlbGF0aXZlO1xuYDtcbmNvbnN0IENvbnRyb2xDb250YWluZXIgPSBzdHlsZWQuZGl2IGBcbiAgYWxpZ24taXRlbXM6IGNlbnRlcjtcbiAgYmFja2dyb3VuZC1jb2xvcjogaHNsKDAsIDAlLCAxMDAlKTtcbiAgYm9yZGVyLWNvbG9yOiBoc2woMCwgMCUsIDgwJSk7XG4gIGJvcmRlci1yYWRpdXM6IDRweDtcbiAgYm9yZGVyLXN0eWxlOiBzb2xpZDtcbiAgYm9yZGVyLXdpZHRoOiAke3Byb3BzID0+IChwcm9wcy5mb2N1c2VkID8gJzAnIDogJzFweCcpfTtcbiAgY3Vyc29yOiBkZWZhdWx0O1xuICBkaXNwbGF5OiBmbGV4O1xuICBmbGV4LXdyYXA6IHdyYXA7XG4gIGp1c3RpZnktY29udGVudDogc3BhY2UtYmV0d2VlbjtcbiAgbWluLWhlaWdodDogMzhweDtcbiAgb3V0bGluZTogMCAhaW1wb3J0YW50O1xuICBwb3NpdGlvbjogcmVsYXRpdmU7XG4gIHRyYW5zaXRpb246IGFsbCAxMDBtcztcbiAgYm94LXNpemluZzogYm9yZGVyLWJveDtcbiAgYm94LXNoYWRvdzogJHtwcm9wcyA9PiBwcm9wcy5mb2N1c2VkID8gYDAgMCAwIDJweCAke0NBTFlQU09fTUVESVVNfWAgOiAnbm9uZSd9O1xuICAmOmhvdmVyIHtcbiAgICBib3JkZXItY29sb3I6IGhzbCgwLCAwJSwgNzAlKTtcbiAgfVxuYDtcbmNvbnN0IFZhbHVlQ29udGFpbmVyID0gc3R5bGVkLmRpdiBgXG4gIGFsaWduLWl0ZW1zOiBjZW50ZXI7XG4gIGRpc3BsYXk6IGZsZXg7XG4gIGZsZXg6IDE7XG4gIGZsZXgtd3JhcDogd3JhcDtcbiAgcGFkZGluZzogMnB4IDhweDtcbiAgcG9zaXRpb246IHJlbGF0aXZlO1xuICBvdmVyZmxvdzogaGlkZGVuO1xuICBib3gtc2l6aW5nOiBib3JkZXItYm94O1xuYDtcbmNvbnN0IFBsYWNlaG9sZGVyID0gc3R5bGVkLmRpdiBgXG4gIGNvbG9yOiBoc2woMCwgMCUsIDUwJSk7XG4gIG1hcmdpbi1sZWZ0OiAycHg7XG4gIG1hcmdpbi1yaWdodDogMnB4O1xuICBwb3NpdGlvbjogYWJzb2x1dGU7XG4gIHRvcDogNTAlO1xuICB0cmFuc2Zvcm06IHRyYW5zbGF0ZVkoLTUwJSk7XG4gIGJveC1zaXppbmc6IGJvcmRlci1ib3g7XG4gIGZvbnQtc2l6ZTogMTZweDtcbmA7XG5jb25zdCBTaW5nbGVWYWx1ZSA9IHN0eWxlZC5kaXYgYFxuICBjb2xvcjogaHNsKDAsIDAlLCAyMCUpO1xuICBtYXJnaW4tbGVmdDogMnB4O1xuICBtYXJnaW4tcmlnaHQ6IDJweDtcbiAgbWF4LXdpZHRoOiBjYWxjKDEwMCUgLSA4cHgpO1xuICBvdmVyZmxvdzogaGlkZGVuO1xuICBwb3NpdGlvbjogYWJzb2x1dGU7XG4gIHRleHQtb3ZlcmZsb3c6IGVsbGlwc2lzO1xuICB3aGl0ZS1zcGFjZTogbm93cmFwO1xuICB0b3A6IDUwJTtcbiAgdHJhbnNmb3JtOiB0cmFuc2xhdGVZKC01MCUpO1xuICBib3gtc2l6aW5nOiBib3JkZXItYm94O1xuYDtcbmNvbnN0IEluZGljYXRvckNvbnRhaW5lciA9IHN0eWxlZC5kaXYgYFxuICBhbGlnbi1pdGVtczogY2VudGVyO1xuICBhbGlnbi1zZWxmOiBzdHJldGNoO1xuICBkaXNwbGF5OiBmbGV4O1xuICBmbGV4LXNocmluazogMDtcbiAgYm94LXNpemluZzogYm9yZGVyLWJveDtcbmA7XG5jb25zdCBEcm9wZG93bkluZGljYXRvciA9IHN0eWxlZC5kaXYgYFxuICBib3JkZXItdG9wOiA4cHggc29saWQgJHtDQUxZUFNPfTtcbiAgYm9yZGVyLWxlZnQ6IDZweCBzb2xpZCB0cmFuc3BhcmVudDtcbiAgYm9yZGVyLXJpZ2h0OiA2cHggc29saWQgdHJhbnNwYXJlbnQ7XG4gIHdpZHRoOiAwcHg7XG4gIGhlaWdodDogMHB4O1xuICBtYXJnaW46IDEwcHg7XG5gO1xuY29uc3QgSW5wdXRDb250YWluZXIgPSBzdHlsZWQuZGl2IGBcbiAgbWFyZ2luOiAycHg7XG4gIHBhZGRpbmctYm90dG9tOiAycHg7XG4gIHBhZGRpbmctdG9wOiAycHg7XG4gIHZpc2liaWxpdHk6IHZpc2libGU7XG4gIGNvbG9yOiBoc2woMCwgMCUsIDIwJSk7XG4gIGJveC1zaXppbmc6IGJvcmRlci1ib3g7XG5gO1xuY29uc3QgSW5wdXQgPSBzdHlsZWQuaW5wdXQgYFxuICBib3gtc2l6aW5nOiBjb250ZW50LWJveDtcbiAgYmFja2dyb3VuZDogcmdiYSgwLCAwLCAwLCAwKSBub25lIHJlcGVhdCBzY3JvbGwgMHB4IGNlbnRlcjtcbiAgYm9yZGVyOiAwcHggbm9uZTtcbiAgZm9udC1zaXplOiBpbmhlcml0O1xuICBvcGFjaXR5OiAxO1xuICBvdXRsaW5lOiBjdXJyZW50Y29sb3Igbm9uZSAwcHg7XG4gIHBhZGRpbmc6IDBweDtcbiAgY29sb3I6IGluaGVyaXQ7XG4gIGZvbnQtZmFtaWx5OiBpbmhlcml0O1xuYDtcbmNvbnN0IElucHV0U2hhZG93ID0gc3R5bGVkLmRpdiBgXG4gIHBvc2l0aW9uOiBhYnNvbHV0ZTtcbiAgb3BhY2l0eTogMDtcbiAgZm9udC1zaXplOiBpbmhlcml0O1xuYDtcbmNvbnN0IE1lbnVDb250YWluZXIgPSBzdHlsZWQuZGl2IGBcbiAgcG9zaXRpb246IGFic29sdXRlO1xuICB0b3A6IDEwMCU7XG4gIGJhY2tncm91bmQtY29sb3I6ICNmZmY7XG4gIGJvcmRlci1yYWRpdXM6IDRweDtcbiAgbWFyZ2luLWJvdHRvbTogOHB4O1xuICBtYXJnaW4tdG9wOiA4cHg7XG4gIHotaW5kZXg6IDk5OTk7XG4gIGJveC1zaGFkb3c6IDAgMCAwIDFweCBoc2xhKDAsIDAlLCAwJSwgMC4xKSwgMCA0cHggMTFweCBoc2xhKDAsIDAlLCAwJSwgMC4xKTtcbiAgd2lkdGg6IDEwMCU7XG5gO1xuY29uc3QgTWVudUxpc3QgPSBzdHlsZWQuZGl2IGBcbiAgbWF4LWhlaWdodDogMzAwcHg7XG4gIG92ZXJmbG93LXk6IGF1dG87XG4gIHBhZGRpbmctYm90dG9tOiA0cHg7XG4gIHBhZGRpbmctdG9wOiA0cHg7XG4gIHBvc2l0aW9uOiByZWxhdGl2ZTtcbmA7XG5jb25zdCBNZW51R3JvdXAgPSBzdHlsZWQuZGl2IGBcbiAgcGFkZGluZy1ib3R0b206IDhweDtcbiAgcGFkZGluZy10b3A6IDhweDtcbmA7XG5jb25zdCBNZW51R3JvdXBIZWFkZXIgPSBzdHlsZWQuZGl2IGBcbiAgY29sb3I6ICM5OTk7XG4gIGN1cnNvcjogZGVmYXVsdDtcbiAgZm9udC1zaXplOiA3NSU7XG4gIGZvbnQtd2VpZ2h0OiA1MDA7XG4gIG1hcmdpbi1ib3R0b206IDAuMjVlbTtcbiAgdGV4dC10cmFuc2Zvcm06IHVwcGVyY2FzZTtcbiAgcGFkZGluZy1sZWZ0OiAxMnB4O1xuICBwYWRkaW5nLWxlZnQ6IDEycHg7XG5gO1xuY29uc3QgTWVudUl0ZW0gPSBzdHlsZWQuZGl2IGBcbiAgZGlzcGxheTogYmxvY2s7XG4gIGJhY2tncm91bmQtY29sb3I6ICR7cHJvcHMgPT4gcHJvcHMuc2VsZWN0ZWQgPyBDQUxZUFNPX01FRElVTSA6ICd0cmFuc3BhcmVudCd9O1xuICBjb2xvcjogJHtwcm9wcyA9PiAocHJvcHMuc2VsZWN0ZWQgPyAnI2ZmZicgOiAnaW5oZXJpdCcpfTtcbiAgY3Vyc29yOiBkZWZhdWx0O1xuICBmb250LXNpemU6IGluaGVyaXQ7XG4gIHdpZHRoOiAxMDAlO1xuICBwYWRkaW5nOiA4cHggMTJweDtcbiAgJjpob3ZlciB7XG4gICAgYmFja2dyb3VuZC1jb2xvcjogJHtwcm9wcyA9PiBwcm9wcy5zZWxlY3RlZCA/IENBTFlQU09fTUVESVVNIDogQ0FMWVBTT19MSUdIVH07XG4gIH1cbmA7XG5leHBvcnQgZGVmYXVsdCBmdW5jdGlvbiBBc3luY1NlbGVjdCh7IHBsYWNlaG9sZGVyLCB2YWx1ZSwgbG9hZE9wdGlvbnMsIG9uQ2hhbmdlLCBkZWZhdWx0T3B0aW9ucywgfSkge1xuICAgIGNvbnN0IGlucHV0RWwgPSB1c2VSZWYobnVsbCk7XG4gICAgY29uc3QgaW5wdXRTaGFkb3dFbCA9IHVzZVJlZihudWxsKTtcbiAgICBjb25zdCBbaXNGb2N1c2VkLCBzZXRGb2N1c10gPSB1c2VTdGF0ZShmYWxzZSk7XG4gICAgY29uc3QgW2xvYWRTdGF0ZSwgc2V0TG9hZFN0YXRlXSA9IHVzZVN0YXRlKExvYWRTdGF0ZS5Ob3RMb2FkZWQpO1xuICAgIGNvbnN0IFtsb2NhbFZhbHVlLCBzZXRMb2NhbFZhbHVlXSA9IHVzZVN0YXRlKCcnKTtcbiAgICBjb25zdCBbb3B0aW9ucywgc2V0T3B0aW9uc10gPSB1c2VTdGF0ZShkZWZhdWx0T3B0aW9ucyk7XG4gICAgY29uc3QgaW5wdXRTaXplID0gYCR7aW5wdXRTaGFkb3dFbC5jdXJyZW50ID8gaW5wdXRTaGFkb3dFbC5jdXJyZW50LmNsaWVudFdpZHRoICsgMTAgOiAyfXB4YDtcbiAgICB1c2VFZmZlY3QoKCkgPT4ge1xuICAgICAgICBpZiAobG9hZE9wdGlvbnMgJiYgbG9hZFN0YXRlID09PSBMb2FkU3RhdGUuTm90TG9hZGVkKSB7XG4gICAgICAgICAgICBsb2FkT3B0aW9ucygnJywgKHJlc3VsdCkgPT4ge1xuICAgICAgICAgICAgICAgIHNldE9wdGlvbnMocmVzdWx0KTtcbiAgICAgICAgICAgICAgICBzZXRMb2FkU3RhdGUoTG9hZFN0YXRlLklkbGUpO1xuICAgICAgICAgICAgfSk7XG4gICAgICAgIH1cbiAgICB9LCBbbG9hZE9wdGlvbnMsIGxvYWRTdGF0ZV0pO1xuICAgIGNvbnN0IHJlbmRlckl0ZW1zID0gKGl0ZW1zID0gW10sIHBhcmVudEtleSkgPT4ge1xuICAgICAgICByZXR1cm4gaXRlbXMubWFwKChpdGVtLCBpbmRleCkgPT4ge1xuICAgICAgICAgICAgaWYgKGl0ZW0ub3B0aW9ucykge1xuICAgICAgICAgICAgICAgIHJldHVybiAoX2pzeHMoTWVudUdyb3VwLCB7IGNoaWxkcmVuOiBbX2pzeChNZW51R3JvdXBIZWFkZXIsIHsgaWQ6IGAke2luZGV4fS1oZWFkaW5nYCwgY2hpbGRyZW46IGl0ZW0ubGFiZWwgfSksIF9qc3goXCJkaXZcIiwgeyBjaGlsZHJlbjogcmVuZGVySXRlbXMoaXRlbS5vcHRpb25zLCBpbmRleCkgfSldIH0sIGBhc3luYy1zZWxlY3QtaXRlbS0ke2luZGV4fWApKTtcbiAgICAgICAgICAgIH1cbiAgICAgICAgICAgIGVsc2Uge1xuICAgICAgICAgICAgICAgIGNvbnN0IGtleSA9IGBhc3luYy1zZWxlY3QtaXRlbS0ke3BhcmVudEtleSAhPT0gdW5kZWZpbmVkID8gYCR7cGFyZW50S2V5fS0ke2luZGV4fWAgOiBpbmRleH1gO1xuICAgICAgICAgICAgICAgIHJldHVybiAoX2pzeChNZW51SXRlbSwgeyBpZDoga2V5LCBzZWxlY3RlZDogdmFsdWUgJiYgaXRlbS52YWx1ZSA9PT0gdmFsdWUudmFsdWUsIG9uQ2xpY2s6ICgpID0+IHtcbiAgICAgICAgICAgICAgICAgICAgICAgIG9uQ2hhbmdlKGl0ZW0pO1xuICAgICAgICAgICAgICAgICAgICAgICAgc2V0Rm9jdXMoZmFsc2UpO1xuICAgICAgICAgICAgICAgICAgICB9LCBjaGlsZHJlbjogaXRlbS5sYWJlbCB9LCBrZXkpKTtcbiAgICAgICAgICAgIH1cbiAgICAgICAgfSk7XG4gICAgfTtcbiAgICByZXR1cm4gKF9qc3hzKENvbnRhaW5lciwgeyBjaGlsZHJlbjogW19qc3hzKENvbnRyb2xDb250YWluZXIsIHsgaWQ6IFwibGVhZGluLWFzeW5jLXNlbGVjdG9yXCIsIGZvY3VzZWQ6IGlzRm9jdXNlZCwgb25DbGljazogKCkgPT4ge1xuICAgICAgICAgICAgICAgICAgICBpZiAoaXNGb2N1c2VkKSB7XG4gICAgICAgICAgICAgICAgICAgICAgICBpZiAoaW5wdXRFbC5jdXJyZW50KSB7XG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgaW5wdXRFbC5jdXJyZW50LmJsdXIoKTtcbiAgICAgICAgICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgICAgICAgICAgICAgIHNldEZvY3VzKGZhbHNlKTtcbiAgICAgICAgICAgICAgICAgICAgICAgIHNldExvY2FsVmFsdWUoJycpO1xuICAgICAgICAgICAgICAgICAgICB9XG4gICAgICAgICAgICAgICAgICAgIGVsc2Uge1xuICAgICAgICAgICAgICAgICAgICAgICAgaWYgKGlucHV0RWwuY3VycmVudCkge1xuICAgICAgICAgICAgICAgICAgICAgICAgICAgIGlucHV0RWwuY3VycmVudC5mb2N1cygpO1xuICAgICAgICAgICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgICAgICAgICAgICAgc2V0Rm9jdXModHJ1ZSk7XG4gICAgICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgICAgICB9LCBjaGlsZHJlbjogW19qc3hzKFZhbHVlQ29udGFpbmVyLCB7IGNoaWxkcmVuOiBbbG9jYWxWYWx1ZSA9PT0gJycgJiZcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgKCF2YWx1ZSA/IChfanN4KFBsYWNlaG9sZGVyLCB7IGNoaWxkcmVuOiBwbGFjZWhvbGRlciB9KSkgOiAoX2pzeChTaW5nbGVWYWx1ZSwgeyBjaGlsZHJlbjogdmFsdWUubGFiZWwgfSkpKSwgX2pzeHMoSW5wdXRDb250YWluZXIsIHsgY2hpbGRyZW46IFtfanN4KElucHV0LCB7IHJlZjogaW5wdXRFbCwgb25Gb2N1czogKCkgPT4ge1xuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBzZXRGb2N1cyh0cnVlKTtcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB9LCBvbkNoYW5nZTogZSA9PiB7XG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHNldExvY2FsVmFsdWUoZS50YXJnZXQudmFsdWUpO1xuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBzZXRMb2FkU3RhdGUoTG9hZFN0YXRlLkxvYWRpbmcpO1xuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBsb2FkT3B0aW9ucyAmJlxuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgbG9hZE9wdGlvbnMoZS50YXJnZXQudmFsdWUsIChyZXN1bHQpID0+IHtcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBzZXRPcHRpb25zKHJlc3VsdCk7XG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgc2V0TG9hZFN0YXRlKExvYWRTdGF0ZS5JZGxlKTtcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIH0pO1xuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIH0sIHZhbHVlOiBsb2NhbFZhbHVlLCB3aWR0aDogaW5wdXRTaXplLCBpZDogXCJhc3ljbi1zZWxlY3QtaW5wdXRcIiB9KSwgX2pzeChJbnB1dFNoYWRvdywgeyByZWY6IGlucHV0U2hhZG93RWwsIGNoaWxkcmVuOiBsb2NhbFZhbHVlIH0pXSB9KV0gfSksIF9qc3hzKEluZGljYXRvckNvbnRhaW5lciwgeyBjaGlsZHJlbjogW2xvYWRTdGF0ZSA9PT0gTG9hZFN0YXRlLkxvYWRpbmcgJiYgX2pzeChVSVNwaW5uZXIsIHt9KSwgX2pzeChEcm9wZG93bkluZGljYXRvciwge30pXSB9KV0gfSksIGlzRm9jdXNlZCAmJiAoX2pzeChNZW51Q29udGFpbmVyLCB7IGNoaWxkcmVuOiBfanN4KE1lbnVMaXN0LCB7IGNoaWxkcmVuOiByZW5kZXJJdGVtcyhvcHRpb25zKSB9KSB9KSldIH0pKTtcbn1cbiJdfQ==*/","import { jsx as _jsx, jsxs as _jsxs } from \"react/jsx-runtime\";\nimport { styled } from '@linaria/react';\nimport { MARIGOLD_LIGHT, MARIGOLD_MEDIUM, OBSIDIAN } from './colors';\nconst AlertContainer = styled.div `\n background-color: ${MARIGOLD_LIGHT};\n border-color: ${MARIGOLD_MEDIUM};\n color: ${OBSIDIAN};\n font-size: 14px;\n align-items: center;\n justify-content: space-between;\n display: flex;\n border-style: solid;\n border-top-style: solid;\n border-right-style: solid;\n border-bottom-style: solid;\n border-left-style: solid;\n border-width: 1px;\n min-height: 60px;\n padding: 8px 20px;\n position: relative;\n text-align: left;\n`;\nconst Title = styled.p `\n font-family: 'Lexend Deca';\n font-style: normal;\n font-weight: 700;\n font-size: 16px;\n line-height: 19px;\n color: ${OBSIDIAN};\n margin: 0;\n padding: 0;\n`;\nconst Message = styled.p `\n font-family: 'Lexend Deca';\n font-style: normal;\n font-weight: 400;\n font-size: 14px;\n margin: 0;\n padding: 0;\n`;\nconst MessageContainer = styled.div `\n display: flex;\n flex-direction: column;\n`;\nexport default function UIAlert({ titleText, titleMessage, children, }) {\n return (_jsxs(AlertContainer, { children: [_jsxs(MessageContainer, { children: [_jsx(Title, { children: titleText }), _jsx(Message, { children: titleMessage })] }), children] }));\n}\n",".a1h8m4fo{background-color:#fef8f0;border-color:#fae0b5;color:#33475b;font-size:14px;-webkit-align-items:center;-webkit-box-align:center;-ms-flex-align:center;align-items:center;-webkit-box-pack:justify;-webkit-justify-content:space-between;-ms-flex-pack:justify;justify-content:space-between;display:-webkit-box;display:-webkit-flex;display:-ms-flexbox;display:flex;border-style:solid;border-top-style:solid;border-right-style:solid;border-bottom-style:solid;border-left-style:solid;border-width:1px;min-height:60px;padding:8px 20px;position:relative;text-align:left;}\n.tyndzxk{font-family:'Lexend Deca';font-style:normal;font-weight:700;font-size:16px;line-height:19px;color:#33475b;margin:0;padding:0;}\n.m1m9sbk4{font-family:'Lexend Deca';font-style:normal;font-weight:400;font-size:14px;margin:0;padding:0;}\n.mg5o421{display:-webkit-box;display:-webkit-flex;display:-ms-flexbox;display:flex;-webkit-flex-direction:column;-ms-flex-direction:column;flex-direction:column;}\n/*# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIi91c3Ivc2hhcmUvaHVic3BvdC9idWlsZC93b3Jrc3BhY2UvTGVhZGluV29yZFByZXNzUGx1Z2luL2xlYWRpbi9zY3JpcHRzL3NoYXJlZC9VSUNvbXBvbmVudHMvVUlBbGVydC50c3giXSwibmFtZXMiOlsiLmExaDhtNGZvIiwiLnR5bmR6eGsiLCIubTFtOXNiazQiLCIubWc1bzQyMSJdLCJtYXBwaW5ncyI6IkFBR3VCQTtBQW1CVEM7QUFVRUM7QUFRU0MiLCJmaWxlIjoiL3Vzci9zaGFyZS9odWJzcG90L2J1aWxkL3dvcmtzcGFjZS9MZWFkaW5Xb3JkUHJlc3NQbHVnaW4vbGVhZGluL3NjcmlwdHMvc2hhcmVkL1VJQ29tcG9uZW50cy9VSUFsZXJ0LnRzeCIsInNvdXJjZXNDb250ZW50IjpbImltcG9ydCB7IGpzeCBhcyBfanN4LCBqc3hzIGFzIF9qc3hzIH0gZnJvbSBcInJlYWN0L2pzeC1ydW50aW1lXCI7XG5pbXBvcnQgeyBzdHlsZWQgfSBmcm9tICdAbGluYXJpYS9yZWFjdCc7XG5pbXBvcnQgeyBNQVJJR09MRF9MSUdIVCwgTUFSSUdPTERfTUVESVVNLCBPQlNJRElBTiB9IGZyb20gJy4vY29sb3JzJztcbmNvbnN0IEFsZXJ0Q29udGFpbmVyID0gc3R5bGVkLmRpdiBgXG4gIGJhY2tncm91bmQtY29sb3I6ICR7TUFSSUdPTERfTElHSFR9O1xuICBib3JkZXItY29sb3I6ICR7TUFSSUdPTERfTUVESVVNfTtcbiAgY29sb3I6ICR7T0JTSURJQU59O1xuICBmb250LXNpemU6IDE0cHg7XG4gIGFsaWduLWl0ZW1zOiBjZW50ZXI7XG4gIGp1c3RpZnktY29udGVudDogc3BhY2UtYmV0d2VlbjtcbiAgZGlzcGxheTogZmxleDtcbiAgYm9yZGVyLXN0eWxlOiBzb2xpZDtcbiAgYm9yZGVyLXRvcC1zdHlsZTogc29saWQ7XG4gIGJvcmRlci1yaWdodC1zdHlsZTogc29saWQ7XG4gIGJvcmRlci1ib3R0b20tc3R5bGU6IHNvbGlkO1xuICBib3JkZXItbGVmdC1zdHlsZTogc29saWQ7XG4gIGJvcmRlci13aWR0aDogMXB4O1xuICBtaW4taGVpZ2h0OiA2MHB4O1xuICBwYWRkaW5nOiA4cHggMjBweDtcbiAgcG9zaXRpb246IHJlbGF0aXZlO1xuICB0ZXh0LWFsaWduOiBsZWZ0O1xuYDtcbmNvbnN0IFRpdGxlID0gc3R5bGVkLnAgYFxuICBmb250LWZhbWlseTogJ0xleGVuZCBEZWNhJztcbiAgZm9udC1zdHlsZTogbm9ybWFsO1xuICBmb250LXdlaWdodDogNzAwO1xuICBmb250LXNpemU6IDE2cHg7XG4gIGxpbmUtaGVpZ2h0OiAxOXB4O1xuICBjb2xvcjogJHtPQlNJRElBTn07XG4gIG1hcmdpbjogMDtcbiAgcGFkZGluZzogMDtcbmA7XG5jb25zdCBNZXNzYWdlID0gc3R5bGVkLnAgYFxuICBmb250LWZhbWlseTogJ0xleGVuZCBEZWNhJztcbiAgZm9udC1zdHlsZTogbm9ybWFsO1xuICBmb250LXdlaWdodDogNDAwO1xuICBmb250LXNpemU6IDE0cHg7XG4gIG1hcmdpbjogMDtcbiAgcGFkZGluZzogMDtcbmA7XG5jb25zdCBNZXNzYWdlQ29udGFpbmVyID0gc3R5bGVkLmRpdiBgXG4gIGRpc3BsYXk6IGZsZXg7XG4gIGZsZXgtZGlyZWN0aW9uOiBjb2x1bW47XG5gO1xuZXhwb3J0IGRlZmF1bHQgZnVuY3Rpb24gVUlBbGVydCh7IHRpdGxlVGV4dCwgdGl0bGVNZXNzYWdlLCBjaGlsZHJlbiwgfSkge1xuICAgIHJldHVybiAoX2pzeHMoQWxlcnRDb250YWluZXIsIHsgY2hpbGRyZW46IFtfanN4cyhNZXNzYWdlQ29udGFpbmVyLCB7IGNoaWxkcmVuOiBbX2pzeChUaXRsZSwgeyBjaGlsZHJlbjogdGl0bGVUZXh0IH0pLCBfanN4KE1lc3NhZ2UsIHsgY2hpbGRyZW46IHRpdGxlTWVzc2FnZSB9KV0gfSksIGNoaWxkcmVuXSB9KSk7XG59XG4iXX0=*/"],"names":[".ump7xqy",".ug152ch",".ua13n1c",".h1q5v5ee",".u3qxofx",".u1q7a48k",".sxa9zrc",".s14430wa",".ct87ghk",".avili0h",".c1wxx7eu",".c1rgwbep",".v1mdmbaj",".p1gwkvxy",".s1bwlafs",".i196z9y5",".d1dfo5ow",".if3lze",".i9kxf50",".igjr3uc",".mhb9if7",".mxaof7s",".mw50s5v",".m11rzvjw",".m1jcdsjv",".a1h8m4fo",".tyndzxk",".m1m9sbk4",".mg5o421"],"sourceRoot":""}
\ No newline at end of file
diff --git a/wp/wp-content/plugins/leadin/build/gutenberg.js b/wp/wp-content/plugins/leadin/build/gutenberg.js
new file mode 100644
index 00000000..d4f34eb4
--- /dev/null
+++ b/wp/wp-content/plugins/leadin/build/gutenberg.js
@@ -0,0 +1,13124 @@
+/******/ (() => { // webpackBootstrap
+/******/ var __webpack_modules__ = ({
+
+/***/ "./node_modules/@emotion/is-prop-valid/dist/is-prop-valid.browser.esm.js":
+/*!*******************************************************************************!*\
+ !*** ./node_modules/@emotion/is-prop-valid/dist/is-prop-valid.browser.esm.js ***!
+ \*******************************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (__WEBPACK_DEFAULT_EXPORT__)
+/* harmony export */ });
+/* harmony import */ var _emotion_memoize__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! @emotion/memoize */ "./node_modules/@emotion/is-prop-valid/node_modules/@emotion/memoize/dist/memoize.browser.esm.js");
+
+
+var reactPropsRegex = /^((children|dangerouslySetInnerHTML|key|ref|autoFocus|defaultValue|defaultChecked|innerHTML|suppressContentEditableWarning|suppressHydrationWarning|valueLink|accept|acceptCharset|accessKey|action|allow|allowUserMedia|allowPaymentRequest|allowFullScreen|allowTransparency|alt|async|autoComplete|autoPlay|capture|cellPadding|cellSpacing|challenge|charSet|checked|cite|classID|className|cols|colSpan|content|contentEditable|contextMenu|controls|controlsList|coords|crossOrigin|data|dateTime|decoding|default|defer|dir|disabled|disablePictureInPicture|download|draggable|encType|form|formAction|formEncType|formMethod|formNoValidate|formTarget|frameBorder|headers|height|hidden|high|href|hrefLang|htmlFor|httpEquiv|id|inputMode|integrity|is|keyParams|keyType|kind|label|lang|list|loading|loop|low|marginHeight|marginWidth|max|maxLength|media|mediaGroup|method|min|minLength|multiple|muted|name|nonce|noValidate|open|optimum|pattern|placeholder|playsInline|poster|preload|profile|radioGroup|readOnly|referrerPolicy|rel|required|reversed|role|rows|rowSpan|sandbox|scope|scoped|scrolling|seamless|selected|shape|size|sizes|slot|span|spellCheck|src|srcDoc|srcLang|srcSet|start|step|style|summary|tabIndex|target|title|type|useMap|value|width|wmode|wrap|about|datatype|inlist|prefix|property|resource|typeof|vocab|autoCapitalize|autoCorrect|autoSave|color|inert|itemProp|itemScope|itemType|itemID|itemRef|on|results|security|unselectable|accentHeight|accumulate|additive|alignmentBaseline|allowReorder|alphabetic|amplitude|arabicForm|ascent|attributeName|attributeType|autoReverse|azimuth|baseFrequency|baselineShift|baseProfile|bbox|begin|bias|by|calcMode|capHeight|clip|clipPathUnits|clipPath|clipRule|colorInterpolation|colorInterpolationFilters|colorProfile|colorRendering|contentScriptType|contentStyleType|cursor|cx|cy|d|decelerate|descent|diffuseConstant|direction|display|divisor|dominantBaseline|dur|dx|dy|edgeMode|elevation|enableBackground|end|exponent|externalResourcesRequired|fill|fillOpacity|fillRule|filter|filterRes|filterUnits|floodColor|floodOpacity|focusable|fontFamily|fontSize|fontSizeAdjust|fontStretch|fontStyle|fontVariant|fontWeight|format|from|fr|fx|fy|g1|g2|glyphName|glyphOrientationHorizontal|glyphOrientationVertical|glyphRef|gradientTransform|gradientUnits|hanging|horizAdvX|horizOriginX|ideographic|imageRendering|in|in2|intercept|k|k1|k2|k3|k4|kernelMatrix|kernelUnitLength|kerning|keyPoints|keySplines|keyTimes|lengthAdjust|letterSpacing|lightingColor|limitingConeAngle|local|markerEnd|markerMid|markerStart|markerHeight|markerUnits|markerWidth|mask|maskContentUnits|maskUnits|mathematical|mode|numOctaves|offset|opacity|operator|order|orient|orientation|origin|overflow|overlinePosition|overlineThickness|panose1|paintOrder|pathLength|patternContentUnits|patternTransform|patternUnits|pointerEvents|points|pointsAtX|pointsAtY|pointsAtZ|preserveAlpha|preserveAspectRatio|primitiveUnits|r|radius|refX|refY|renderingIntent|repeatCount|repeatDur|requiredExtensions|requiredFeatures|restart|result|rotate|rx|ry|scale|seed|shapeRendering|slope|spacing|specularConstant|specularExponent|speed|spreadMethod|startOffset|stdDeviation|stemh|stemv|stitchTiles|stopColor|stopOpacity|strikethroughPosition|strikethroughThickness|string|stroke|strokeDasharray|strokeDashoffset|strokeLinecap|strokeLinejoin|strokeMiterlimit|strokeOpacity|strokeWidth|surfaceScale|systemLanguage|tableValues|targetX|targetY|textAnchor|textDecoration|textRendering|textLength|to|transform|u1|u2|underlinePosition|underlineThickness|unicode|unicodeBidi|unicodeRange|unitsPerEm|vAlphabetic|vHanging|vIdeographic|vMathematical|values|vectorEffect|version|vertAdvY|vertOriginX|vertOriginY|viewBox|viewTarget|visibility|widths|wordSpacing|writingMode|x|xHeight|x1|x2|xChannelSelector|xlinkActuate|xlinkArcrole|xlinkHref|xlinkRole|xlinkShow|xlinkTitle|xlinkType|xmlBase|xmlns|xmlnsXlink|xmlLang|xmlSpace|y|y1|y2|yChannelSelector|z|zoomAndPan|for|class|autofocus)|(([Dd][Aa][Tt][Aa]|[Aa][Rr][Ii][Aa]|x)-.*))$/; // https://esbench.com/bench/5bfee68a4cd7e6009ef61d23
+
+var index = (0,_emotion_memoize__WEBPACK_IMPORTED_MODULE_0__["default"])(function (prop) {
+ return reactPropsRegex.test(prop) || prop.charCodeAt(0) === 111
+ /* o */
+ && prop.charCodeAt(1) === 110
+ /* n */
+ && prop.charCodeAt(2) < 91;
+}
+/* Z+1 */
+);
+
+/* harmony default export */ const __WEBPACK_DEFAULT_EXPORT__ = (index);
+
+
+/***/ }),
+
+/***/ "./node_modules/@emotion/is-prop-valid/node_modules/@emotion/memoize/dist/memoize.browser.esm.js":
+/*!*******************************************************************************************************!*\
+ !*** ./node_modules/@emotion/is-prop-valid/node_modules/@emotion/memoize/dist/memoize.browser.esm.js ***!
+ \*******************************************************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (__WEBPACK_DEFAULT_EXPORT__)
+/* harmony export */ });
+function memoize(fn) {
+ var cache = {};
+ return function (arg) {
+ if (cache[arg] === undefined) cache[arg] = fn(arg);
+ return cache[arg];
+ };
+}
+
+/* harmony default export */ const __WEBPACK_DEFAULT_EXPORT__ = (memoize);
+
+
+/***/ }),
+
+/***/ "./node_modules/@emotion/memoize/dist/emotion-memoize.esm.js":
+/*!*******************************************************************!*\
+ !*** ./node_modules/@emotion/memoize/dist/emotion-memoize.esm.js ***!
+ \*******************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (__WEBPACK_DEFAULT_EXPORT__)
+/* harmony export */ });
+function memoize(fn) {
+ var cache = Object.create(null);
+ return function (arg) {
+ if (cache[arg] === undefined) cache[arg] = fn(arg);
+ return cache[arg];
+ };
+}
+
+/* harmony default export */ const __WEBPACK_DEFAULT_EXPORT__ = (memoize);
+
+
+/***/ }),
+
+/***/ "./node_modules/@emotion/unitless/dist/unitless.browser.esm.js":
+/*!*********************************************************************!*\
+ !*** ./node_modules/@emotion/unitless/dist/unitless.browser.esm.js ***!
+ \*********************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (__WEBPACK_DEFAULT_EXPORT__)
+/* harmony export */ });
+var unitlessKeys = {
+ animationIterationCount: 1,
+ borderImageOutset: 1,
+ borderImageSlice: 1,
+ borderImageWidth: 1,
+ boxFlex: 1,
+ boxFlexGroup: 1,
+ boxOrdinalGroup: 1,
+ columnCount: 1,
+ columns: 1,
+ flex: 1,
+ flexGrow: 1,
+ flexPositive: 1,
+ flexShrink: 1,
+ flexNegative: 1,
+ flexOrder: 1,
+ gridRow: 1,
+ gridRowEnd: 1,
+ gridRowSpan: 1,
+ gridRowStart: 1,
+ gridColumn: 1,
+ gridColumnEnd: 1,
+ gridColumnSpan: 1,
+ gridColumnStart: 1,
+ msGridRow: 1,
+ msGridRowSpan: 1,
+ msGridColumn: 1,
+ msGridColumnSpan: 1,
+ fontWeight: 1,
+ lineHeight: 1,
+ opacity: 1,
+ order: 1,
+ orphans: 1,
+ tabSize: 1,
+ widows: 1,
+ zIndex: 1,
+ zoom: 1,
+ WebkitLineClamp: 1,
+ // SVG-related properties
+ fillOpacity: 1,
+ floodOpacity: 1,
+ stopOpacity: 1,
+ strokeDasharray: 1,
+ strokeDashoffset: 1,
+ strokeMiterlimit: 1,
+ strokeOpacity: 1,
+ strokeWidth: 1
+};
+
+/* harmony default export */ const __WEBPACK_DEFAULT_EXPORT__ = (unitlessKeys);
+
+
+/***/ }),
+
+/***/ "./node_modules/@linaria/react/node_modules/@emotion/is-prop-valid/dist/emotion-is-prop-valid.esm.js":
+/*!***********************************************************************************************************!*\
+ !*** ./node_modules/@linaria/react/node_modules/@emotion/is-prop-valid/dist/emotion-is-prop-valid.esm.js ***!
+ \***********************************************************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (__WEBPACK_DEFAULT_EXPORT__)
+/* harmony export */ });
+/* harmony import */ var _emotion_memoize__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! @emotion/memoize */ "./node_modules/@emotion/memoize/dist/emotion-memoize.esm.js");
+
+
+var reactPropsRegex = /^((children|dangerouslySetInnerHTML|key|ref|autoFocus|defaultValue|defaultChecked|innerHTML|suppressContentEditableWarning|suppressHydrationWarning|valueLink|abbr|accept|acceptCharset|accessKey|action|allow|allowUserMedia|allowPaymentRequest|allowFullScreen|allowTransparency|alt|async|autoComplete|autoPlay|capture|cellPadding|cellSpacing|challenge|charSet|checked|cite|classID|className|cols|colSpan|content|contentEditable|contextMenu|controls|controlsList|coords|crossOrigin|data|dateTime|decoding|default|defer|dir|disabled|disablePictureInPicture|download|draggable|encType|enterKeyHint|form|formAction|formEncType|formMethod|formNoValidate|formTarget|frameBorder|headers|height|hidden|high|href|hrefLang|htmlFor|httpEquiv|id|inputMode|integrity|is|keyParams|keyType|kind|label|lang|list|loading|loop|low|marginHeight|marginWidth|max|maxLength|media|mediaGroup|method|min|minLength|multiple|muted|name|nonce|noValidate|open|optimum|pattern|placeholder|playsInline|poster|preload|profile|radioGroup|readOnly|referrerPolicy|rel|required|reversed|role|rows|rowSpan|sandbox|scope|scoped|scrolling|seamless|selected|shape|size|sizes|slot|span|spellCheck|src|srcDoc|srcLang|srcSet|start|step|style|summary|tabIndex|target|title|translate|type|useMap|value|width|wmode|wrap|about|datatype|inlist|prefix|property|resource|typeof|vocab|autoCapitalize|autoCorrect|autoSave|color|incremental|fallback|inert|itemProp|itemScope|itemType|itemID|itemRef|on|option|results|security|unselectable|accentHeight|accumulate|additive|alignmentBaseline|allowReorder|alphabetic|amplitude|arabicForm|ascent|attributeName|attributeType|autoReverse|azimuth|baseFrequency|baselineShift|baseProfile|bbox|begin|bias|by|calcMode|capHeight|clip|clipPathUnits|clipPath|clipRule|colorInterpolation|colorInterpolationFilters|colorProfile|colorRendering|contentScriptType|contentStyleType|cursor|cx|cy|d|decelerate|descent|diffuseConstant|direction|display|divisor|dominantBaseline|dur|dx|dy|edgeMode|elevation|enableBackground|end|exponent|externalResourcesRequired|fill|fillOpacity|fillRule|filter|filterRes|filterUnits|floodColor|floodOpacity|focusable|fontFamily|fontSize|fontSizeAdjust|fontStretch|fontStyle|fontVariant|fontWeight|format|from|fr|fx|fy|g1|g2|glyphName|glyphOrientationHorizontal|glyphOrientationVertical|glyphRef|gradientTransform|gradientUnits|hanging|horizAdvX|horizOriginX|ideographic|imageRendering|in|in2|intercept|k|k1|k2|k3|k4|kernelMatrix|kernelUnitLength|kerning|keyPoints|keySplines|keyTimes|lengthAdjust|letterSpacing|lightingColor|limitingConeAngle|local|markerEnd|markerMid|markerStart|markerHeight|markerUnits|markerWidth|mask|maskContentUnits|maskUnits|mathematical|mode|numOctaves|offset|opacity|operator|order|orient|orientation|origin|overflow|overlinePosition|overlineThickness|panose1|paintOrder|pathLength|patternContentUnits|patternTransform|patternUnits|pointerEvents|points|pointsAtX|pointsAtY|pointsAtZ|preserveAlpha|preserveAspectRatio|primitiveUnits|r|radius|refX|refY|renderingIntent|repeatCount|repeatDur|requiredExtensions|requiredFeatures|restart|result|rotate|rx|ry|scale|seed|shapeRendering|slope|spacing|specularConstant|specularExponent|speed|spreadMethod|startOffset|stdDeviation|stemh|stemv|stitchTiles|stopColor|stopOpacity|strikethroughPosition|strikethroughThickness|string|stroke|strokeDasharray|strokeDashoffset|strokeLinecap|strokeLinejoin|strokeMiterlimit|strokeOpacity|strokeWidth|surfaceScale|systemLanguage|tableValues|targetX|targetY|textAnchor|textDecoration|textRendering|textLength|to|transform|u1|u2|underlinePosition|underlineThickness|unicode|unicodeBidi|unicodeRange|unitsPerEm|vAlphabetic|vHanging|vIdeographic|vMathematical|values|vectorEffect|version|vertAdvY|vertOriginX|vertOriginY|viewBox|viewTarget|visibility|widths|wordSpacing|writingMode|x|xHeight|x1|x2|xChannelSelector|xlinkActuate|xlinkArcrole|xlinkHref|xlinkRole|xlinkShow|xlinkTitle|xlinkType|xmlBase|xmlns|xmlnsXlink|xmlLang|xmlSpace|y|y1|y2|yChannelSelector|z|zoomAndPan|for|class|autofocus)|(([Dd][Aa][Tt][Aa]|[Aa][Rr][Ii][Aa]|x)-.*))$/; // https://esbench.com/bench/5bfee68a4cd7e6009ef61d23
+
+var isPropValid = /* #__PURE__ */(0,_emotion_memoize__WEBPACK_IMPORTED_MODULE_0__["default"])(function (prop) {
+ return reactPropsRegex.test(prop) || prop.charCodeAt(0) === 111
+ /* o */
+ && prop.charCodeAt(1) === 110
+ /* n */
+ && prop.charCodeAt(2) < 91;
+}
+/* Z+1 */
+);
+
+/* harmony default export */ const __WEBPACK_DEFAULT_EXPORT__ = (isPropValid);
+
+
+/***/ }),
+
+/***/ "./scripts/constants/defaultFormOptions.ts":
+/*!*************************************************!*\
+ !*** ./scripts/constants/defaultFormOptions.ts ***!
+ \*************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "DEFAULT_OPTIONS": () => (/* binding */ DEFAULT_OPTIONS),
+/* harmony export */ "isDefaultForm": () => (/* binding */ isDefaultForm)
+/* harmony export */ });
+/* harmony import */ var _wordpress_i18n__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! @wordpress/i18n */ "@wordpress/i18n");
+/* harmony import */ var _wordpress_i18n__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(_wordpress_i18n__WEBPACK_IMPORTED_MODULE_0__);
+
+var REGISTRATION_FORM = 'REGISTRATION_FORM';
+var CONTACT_US_FORM = 'CONTACT_US_FORM';
+var NEWSLETTER_FORM = 'NEWSLETTER_FORM';
+var SUPPORT_FORM = 'SUPPORT_FORM';
+var EVENT_FORM = 'EVENT_FORM';
+var DEFAULT_OPTIONS = {
+ label: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_0__.__)('Templates', 'leadin'),
+ options: [{
+ label: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_0__.__)('Registration Form', 'leadin'),
+ value: REGISTRATION_FORM
+ }, {
+ label: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_0__.__)('Contact us Form', 'leadin'),
+ value: CONTACT_US_FORM
+ }, {
+ label: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_0__.__)('Newsletter sign-up Form', 'leadin'),
+ value: NEWSLETTER_FORM
+ }, {
+ label: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_0__.__)('Support Form', 'leadin'),
+ value: SUPPORT_FORM
+ }, {
+ label: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_0__.__)('Event Registration Form', 'leadin'),
+ value: EVENT_FORM
+ }]
+};
+function isDefaultForm(value) {
+ return value === REGISTRATION_FORM || value === CONTACT_US_FORM || value === NEWSLETTER_FORM || value === SUPPORT_FORM || value === EVENT_FORM;
+}
+
+/***/ }),
+
+/***/ "./scripts/constants/leadinConfig.ts":
+/*!*******************************************!*\
+ !*** ./scripts/constants/leadinConfig.ts ***!
+ \*******************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "accountName": () => (/* binding */ accountName),
+/* harmony export */ "activationTime": () => (/* binding */ activationTime),
+/* harmony export */ "adminUrl": () => (/* binding */ adminUrl),
+/* harmony export */ "connectionStatus": () => (/* binding */ connectionStatus),
+/* harmony export */ "contentEmbed": () => (/* binding */ contentEmbed),
+/* harmony export */ "deviceId": () => (/* binding */ deviceId),
+/* harmony export */ "didDisconnect": () => (/* binding */ didDisconnect),
+/* harmony export */ "env": () => (/* binding */ env),
+/* harmony export */ "formsScript": () => (/* binding */ formsScript),
+/* harmony export */ "formsScriptPayload": () => (/* binding */ formsScriptPayload),
+/* harmony export */ "hublet": () => (/* binding */ hublet),
+/* harmony export */ "hubspotBaseUrl": () => (/* binding */ hubspotBaseUrl),
+/* harmony export */ "hubspotNonce": () => (/* binding */ hubspotNonce),
+/* harmony export */ "iframeUrl": () => (/* binding */ iframeUrl),
+/* harmony export */ "impactLink": () => (/* binding */ impactLink),
+/* harmony export */ "lastAuthorizeTime": () => (/* binding */ lastAuthorizeTime),
+/* harmony export */ "lastDeauthorizeTime": () => (/* binding */ lastDeauthorizeTime),
+/* harmony export */ "lastDisconnectTime": () => (/* binding */ lastDisconnectTime),
+/* harmony export */ "leadinPluginVersion": () => (/* binding */ leadinPluginVersion),
+/* harmony export */ "leadinQueryParams": () => (/* binding */ leadinQueryParams),
+/* harmony export */ "locale": () => (/* binding */ locale),
+/* harmony export */ "loginUrl": () => (/* binding */ loginUrl),
+/* harmony export */ "meetingsScript": () => (/* binding */ meetingsScript),
+/* harmony export */ "phpVersion": () => (/* binding */ phpVersion),
+/* harmony export */ "pluginPath": () => (/* binding */ pluginPath),
+/* harmony export */ "plugins": () => (/* binding */ plugins),
+/* harmony export */ "portalDomain": () => (/* binding */ portalDomain),
+/* harmony export */ "portalEmail": () => (/* binding */ portalEmail),
+/* harmony export */ "portalId": () => (/* binding */ portalId),
+/* harmony export */ "redirectNonce": () => (/* binding */ redirectNonce),
+/* harmony export */ "refreshToken": () => (/* binding */ refreshToken),
+/* harmony export */ "refreshTokenError": () => (/* binding */ refreshTokenError),
+/* harmony export */ "requiresContentEmbedScope": () => (/* binding */ requiresContentEmbedScope),
+/* harmony export */ "restNonce": () => (/* binding */ restNonce),
+/* harmony export */ "restUrl": () => (/* binding */ restUrl),
+/* harmony export */ "reviewSkippedDate": () => (/* binding */ reviewSkippedDate),
+/* harmony export */ "theme": () => (/* binding */ theme),
+/* harmony export */ "trackConsent": () => (/* binding */ trackConsent),
+/* harmony export */ "wpVersion": () => (/* binding */ wpVersion)
+/* harmony export */ });
+var _window$leadinConfig = window.leadinConfig,
+ accountName = _window$leadinConfig.accountName,
+ adminUrl = _window$leadinConfig.adminUrl,
+ activationTime = _window$leadinConfig.activationTime,
+ connectionStatus = _window$leadinConfig.connectionStatus,
+ deviceId = _window$leadinConfig.deviceId,
+ didDisconnect = _window$leadinConfig.didDisconnect,
+ env = _window$leadinConfig.env,
+ formsScript = _window$leadinConfig.formsScript,
+ meetingsScript = _window$leadinConfig.meetingsScript,
+ formsScriptPayload = _window$leadinConfig.formsScriptPayload,
+ hublet = _window$leadinConfig.hublet,
+ hubspotBaseUrl = _window$leadinConfig.hubspotBaseUrl,
+ hubspotNonce = _window$leadinConfig.hubspotNonce,
+ iframeUrl = _window$leadinConfig.iframeUrl,
+ impactLink = _window$leadinConfig.impactLink,
+ lastAuthorizeTime = _window$leadinConfig.lastAuthorizeTime,
+ lastDeauthorizeTime = _window$leadinConfig.lastDeauthorizeTime,
+ lastDisconnectTime = _window$leadinConfig.lastDisconnectTime,
+ leadinPluginVersion = _window$leadinConfig.leadinPluginVersion,
+ leadinQueryParams = _window$leadinConfig.leadinQueryParams,
+ locale = _window$leadinConfig.locale,
+ loginUrl = _window$leadinConfig.loginUrl,
+ phpVersion = _window$leadinConfig.phpVersion,
+ pluginPath = _window$leadinConfig.pluginPath,
+ plugins = _window$leadinConfig.plugins,
+ portalDomain = _window$leadinConfig.portalDomain,
+ portalEmail = _window$leadinConfig.portalEmail,
+ portalId = _window$leadinConfig.portalId,
+ redirectNonce = _window$leadinConfig.redirectNonce,
+ restNonce = _window$leadinConfig.restNonce,
+ restUrl = _window$leadinConfig.restUrl,
+ refreshToken = _window$leadinConfig.refreshToken,
+ reviewSkippedDate = _window$leadinConfig.reviewSkippedDate,
+ theme = _window$leadinConfig.theme,
+ trackConsent = _window$leadinConfig.trackConsent,
+ wpVersion = _window$leadinConfig.wpVersion,
+ contentEmbed = _window$leadinConfig.contentEmbed,
+ requiresContentEmbedScope = _window$leadinConfig.requiresContentEmbedScope,
+ refreshTokenError = _window$leadinConfig.refreshTokenError;
+
+
+/***/ }),
+
+/***/ "./scripts/gutenberg/Common/CalendarIcon.tsx":
+/*!***************************************************!*\
+ !*** ./scripts/gutenberg/Common/CalendarIcon.tsx ***!
+ \***************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ CalendarIcon)
+/* harmony export */ });
+/* harmony import */ var react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react/jsx-runtime */ "./node_modules/react/jsx-runtime.js");
+
+function CalendarIcon() {
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsxs)("svg", {
+ width: "18",
+ height: "18",
+ viewBox: "0 0 18 18",
+ fill: "none",
+ xmlns: "http://www.w3.org/2000/svg",
+ children: [(0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)("g", {
+ clipPath: "url(#clip0_903_1965)",
+ children: (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)("path", {
+ fillRule: "evenodd",
+ clipRule: "evenodd",
+ d: "M13.519 2.48009H15.069H15.0697C16.2619 2.48719 17.2262 3.45597 17.2262 4.65016V12.7434C17.223 12.9953 17.1203 13.2226 16.9549 13.3886L12.6148 17.7287C12.4488 17.8941 12.2214 17.9968 11.9689 18H3.29508C2.09637 18 1.125 17.0286 1.125 15.8299V4.65016C1.125 3.45404 2.09314 2.48396 3.28862 2.48009H4.83867V0.930032C4.83867 0.416577 5.25525 0 5.7687 0C6.28216 0 6.69874 0.416577 6.69874 0.930032V2.48009H11.6589V0.930032C11.6589 0.416577 12.0755 0 12.5889 0C13.1024 0 13.519 0.416577 13.519 0.930032V2.48009ZM2.98506 15.8312C2.99863 15.9882 3.12909 16.1115 3.28862 16.1141H11.5814L11.6589 16.0366V13.634C11.6589 12.9494 12.2143 12.394 12.899 12.394H15.2951L15.3726 12.3165V7.4338H2.98506V15.8312ZM4.83868 8.68029H6.07873H6.07937C6.42684 8.68029 6.71037 8.95478 6.72458 9.30032V14.2863C6.72458 14.6428 6.43524 14.9322 6.07873 14.9322H4.83868C4.48217 14.9322 4.19283 14.6428 4.19283 14.2863V9.32615C4.19283 8.96964 4.48217 8.68029 4.83868 8.68029ZM8.53298 8.68029H9.82469H9.82534C10.1728 8.68029 10.4563 8.95478 10.4705 9.30032V14.2863C10.4705 14.6428 10.1812 14.9322 9.82469 14.9322H8.53298C8.17647 14.9322 7.88712 14.6428 7.88712 14.2863V9.32615C7.88712 8.96964 8.17647 8.68029 8.53298 8.68029ZM13.519 8.68029H12.2789C11.9366 8.68029 11.6589 8.95801 11.6589 9.30032V10.5404C11.6589 10.8827 11.9366 11.1604 12.2789 11.1604H13.519C13.8613 11.1604 14.139 10.8827 14.139 10.5404V9.30032C14.139 8.95801 13.8613 8.68029 13.519 8.68029Z",
+ fill: "#FF7A59"
+ })
+ }), (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)("defs", {
+ children: (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)("clipPath", {
+ id: "clip0_903_1965",
+ children: (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)("rect", {
+ width: "18",
+ height: "18",
+ fill: "white"
+ })
+ })
+ })]
+ });
+}
+
+/***/ }),
+
+/***/ "./scripts/gutenberg/Common/SidebarSprocketIcon.tsx":
+/*!**********************************************************!*\
+ !*** ./scripts/gutenberg/Common/SidebarSprocketIcon.tsx ***!
+ \**********************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ SidebarSprocketIcon)
+/* harmony export */ });
+/* harmony import */ var react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react/jsx-runtime */ "./node_modules/react/jsx-runtime.js");
+
+function SidebarSprocketIcon() {
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)("svg", {
+ width: "20px",
+ height: "20px",
+ version: "1.1",
+ viewBox: "0 0 40 42",
+ xmlns: "http://www.w3.org/2000/svg",
+ xmlnsXlink: "http://www.w3.org/1999/xlink",
+ children: (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)("path", {
+ d: "M28.8989809,30.0402293 C25.817707,30.0402293 23.319363,27.5423949 23.319363,24.461121 C23.319363,21.3798471 25.817707,18.881758 28.8989809,18.881758 C31.98,18.881758 34.4780892,21.3798471 34.4780892,24.461121 C34.4780892,27.5423949 31.98,30.0402293 28.8989809,30.0402293 M30.5692994,13.7199745 L30.5692994,8.75717196 C31.864586,8.14519744 32.7723567,6.8346242 32.7723567,5.31360508 L32.7723567,5.1989554 C32.7723567,3.10010191 31.0546497,1.38264968 28.956051,1.38264968 L28.8414013,1.38264968 C26.7425478,1.38264968 25.0248408,3.10010191 25.0248408,5.1989554 L25.0248408,5.31360508 C25.0248408,6.8346242 25.9328662,8.14519744 27.2281529,8.75717196 L27.2281529,13.7202293 C25.2994904,14.0180637 23.5371974,14.8137325 22.0829299,15.9844331 L8.45643312,5.38417836 C8.54611464,5.0392102 8.6090446,4.6835414 8.60955416,4.310293 C8.61261148,1.93271338 6.68777072,0.00303184713 4.31019108,-2.5477707e-05 C1.93286624,-0.00308280255 0.0029299363,1.92175796 0.000127388535,4.29933756 C-0.0029299363,6.67666244 1.92191083,8.60634396 4.29949044,8.60940128 C5.07426752,8.6104204 5.7912102,8.390293 6.42,8.03284076 L19.8243312,18.4603567 C18.6842038,20.181121 18.0166879,22.2422675 18.0166879,24.461121 C18.0166879,26.7841784 18.7504458,28.9327134 19.9907006,30.7001019 L15.9142675,34.776535 C15.5919745,34.6799745 15.2574522,34.6122038 14.9033121,34.6122038 C12.9499363,34.6122038 11.3659873,36.1961529 11.3659873,38.1497834 C11.3659873,40.103414 12.9499363,41.6871084 14.9033121,41.6871084 C16.8571974,41.6871084 18.4408917,40.103414 18.4408917,38.1497834 C18.4408917,37.7958981 18.3733758,37.461121 18.2765605,37.1390828 L22.3089172,33.1067261 C24.1392357,34.5041784 26.4184713,35.3431592 28.8989809,35.3431592 C34.9089172,35.3431592 39.7810191,30.4710573 39.7810191,24.461121 C39.7810191,19.0203567 35.7840764,14.5255796 30.5692994,13.7199745",
+ id: "Fill-1",
+ fillRule: "evenodd"
+ })
+ });
+}
+
+/***/ }),
+
+/***/ "./scripts/gutenberg/Common/SprocketIcon.tsx":
+/*!***************************************************!*\
+ !*** ./scripts/gutenberg/Common/SprocketIcon.tsx ***!
+ \***************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ SprocketIcon)
+/* harmony export */ });
+/* harmony import */ var react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react/jsx-runtime */ "./node_modules/react/jsx-runtime.js");
+
+function SprocketIcon() {
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsxs)("svg", {
+ width: "40px",
+ height: "42px",
+ viewBox: "0 0 40 42",
+ version: "1.1",
+ xmlns: "http://www.w3.org/2000/svg",
+ xmlnsXlink: "http://www.w3.org/1999/xlink",
+ children: [(0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)("defs", {
+ children: (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)("polygon", {
+ id: "path-1",
+ points: "0.000123751494 0 39.7808917 0 39.7808917 41.6871084 0.000123751494 41.6871084"
+ })
+ }), (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)("g", {
+ id: "Page-1",
+ stroke: "none",
+ strokeWidth: "1",
+ fill: "none",
+ fillRule: "evenodd",
+ children: (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsxs)("g", {
+ id: "HubSpot-Sprocket---Full-Color",
+ children: [(0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)("mask", {
+ id: "mask-2",
+ fill: "white",
+ children: (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)("use", {
+ xlinkHref: "#path-1"
+ })
+ }), (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)("g", {
+ id: "path-1"
+ }), (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)("path", {
+ d: "M28.8989809,30.0402293 C25.817707,30.0402293 23.319363,27.5423949 23.319363,24.461121 C23.319363,21.3798471 25.817707,18.881758 28.8989809,18.881758 C31.98,18.881758 34.4780892,21.3798471 34.4780892,24.461121 C34.4780892,27.5423949 31.98,30.0402293 28.8989809,30.0402293 M30.5692994,13.7199745 L30.5692994,8.75717196 C31.864586,8.14519744 32.7723567,6.8346242 32.7723567,5.31360508 L32.7723567,5.1989554 C32.7723567,3.10010191 31.0546497,1.38264968 28.956051,1.38264968 L28.8414013,1.38264968 C26.7425478,1.38264968 25.0248408,3.10010191 25.0248408,5.1989554 L25.0248408,5.31360508 C25.0248408,6.8346242 25.9328662,8.14519744 27.2281529,8.75717196 L27.2281529,13.7202293 C25.2994904,14.0180637 23.5371974,14.8137325 22.0829299,15.9844331 L8.45643312,5.38417836 C8.54611464,5.0392102 8.6090446,4.6835414 8.60955416,4.310293 C8.61261148,1.93271338 6.68777072,0.00303184713 4.31019108,-2.5477707e-05 C1.93286624,-0.00308280255 0.0029299363,1.92175796 0.000127388535,4.29933756 C-0.0029299363,6.67666244 1.92191083,8.60634396 4.29949044,8.60940128 C5.07426752,8.6104204 5.7912102,8.390293 6.42,8.03284076 L19.8243312,18.4603567 C18.6842038,20.181121 18.0166879,22.2422675 18.0166879,24.461121 C18.0166879,26.7841784 18.7504458,28.9327134 19.9907006,30.7001019 L15.9142675,34.776535 C15.5919745,34.6799745 15.2574522,34.6122038 14.9033121,34.6122038 C12.9499363,34.6122038 11.3659873,36.1961529 11.3659873,38.1497834 C11.3659873,40.103414 12.9499363,41.6871084 14.9033121,41.6871084 C16.8571974,41.6871084 18.4408917,40.103414 18.4408917,38.1497834 C18.4408917,37.7958981 18.3733758,37.461121 18.2765605,37.1390828 L22.3089172,33.1067261 C24.1392357,34.5041784 26.4184713,35.3431592 28.8989809,35.3431592 C34.9089172,35.3431592 39.7810191,30.4710573 39.7810191,24.461121 C39.7810191,19.0203567 35.7840764,14.5255796 30.5692994,13.7199745",
+ id: "Fill-1",
+ fill: "#F3785B",
+ fillRule: "nonzero",
+ mask: "url(#mask-2)"
+ })]
+ })
+ })]
+ });
+}
+
+/***/ }),
+
+/***/ "./scripts/gutenberg/FormBlock/FormBlockSave.tsx":
+/*!*******************************************************!*\
+ !*** ./scripts/gutenberg/FormBlock/FormBlockSave.tsx ***!
+ \*******************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ FormSaveBlock)
+/* harmony export */ });
+/* harmony import */ var react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react/jsx-runtime */ "./node_modules/react/jsx-runtime.js");
+/* harmony import */ var _wordpress_element__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! @wordpress/element */ "@wordpress/element");
+/* harmony import */ var _wordpress_element__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(_wordpress_element__WEBPACK_IMPORTED_MODULE_1__);
+
+
+function FormSaveBlock(_ref) {
+ var attributes = _ref.attributes;
+ var portalId = attributes.portalId,
+ formId = attributes.formId;
+
+ if (portalId && formId) {
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_wordpress_element__WEBPACK_IMPORTED_MODULE_1__.RawHTML, {
+ className: "wp-block-leadin-hubspot-form-block",
+ children: "[hubspot portal=\"".concat(portalId, "\" id=\"").concat(formId, "\" type=\"form\"]")
+ });
+ }
+
+ return null;
+}
+
+/***/ }),
+
+/***/ "./scripts/gutenberg/FormBlock/FormGutenbergPreview.tsx":
+/*!**************************************************************!*\
+ !*** ./scripts/gutenberg/FormBlock/FormGutenbergPreview.tsx ***!
+ \**************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ FormGutenbergPreview)
+/* harmony export */ });
+/* harmony import */ var react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react/jsx-runtime */ "./node_modules/react/jsx-runtime.js");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! react */ "react");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(react__WEBPACK_IMPORTED_MODULE_1__);
+/* harmony import */ var _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ../../constants/leadinConfig */ "./scripts/constants/leadinConfig.ts");
+/* harmony import */ var _UIComponents_UIImage__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ../UIComponents/UIImage */ "./scripts/gutenberg/UIComponents/UIImage.ts");
+
+
+
+
+function FormGutenbergPreview() {
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(react__WEBPACK_IMPORTED_MODULE_1__.Fragment, {
+ children: (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_UIComponents_UIImage__WEBPACK_IMPORTED_MODULE_3__["default"], {
+ alt: "Create a new Hubspot Form",
+ src: "".concat(_constants_leadinConfig__WEBPACK_IMPORTED_MODULE_2__.pluginPath, "/public/assets/images/hubspot-form.png")
+ })
+ });
+}
+
+/***/ }),
+
+/***/ "./scripts/gutenberg/FormBlock/registerFormBlock.tsx":
+/*!***********************************************************!*\
+ !*** ./scripts/gutenberg/FormBlock/registerFormBlock.tsx ***!
+ \***********************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ registerFormBlock)
+/* harmony export */ });
+/* harmony import */ var react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react/jsx-runtime */ "./node_modules/react/jsx-runtime.js");
+/* harmony import */ var _wordpress_blocks__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! @wordpress/blocks */ "@wordpress/blocks");
+/* harmony import */ var _wordpress_blocks__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(_wordpress_blocks__WEBPACK_IMPORTED_MODULE_1__);
+/* harmony import */ var _Common_SprocketIcon__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ../Common/SprocketIcon */ "./scripts/gutenberg/Common/SprocketIcon.tsx");
+/* harmony import */ var _FormBlockSave__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ./FormBlockSave */ "./scripts/gutenberg/FormBlock/FormBlockSave.tsx");
+/* harmony import */ var _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__(/*! ../../constants/leadinConfig */ "./scripts/constants/leadinConfig.ts");
+/* harmony import */ var _FormGutenbergPreview__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__(/*! ./FormGutenbergPreview */ "./scripts/gutenberg/FormBlock/FormGutenbergPreview.tsx");
+/* harmony import */ var _shared_Common_ErrorHandler__WEBPACK_IMPORTED_MODULE_6__ = __webpack_require__(/*! ../../shared/Common/ErrorHandler */ "./scripts/shared/Common/ErrorHandler.tsx");
+/* harmony import */ var _shared_Form_FormEdit__WEBPACK_IMPORTED_MODULE_7__ = __webpack_require__(/*! ../../shared/Form/FormEdit */ "./scripts/shared/Form/FormEdit.tsx");
+/* harmony import */ var _shared_enums_connectionStatus__WEBPACK_IMPORTED_MODULE_8__ = __webpack_require__(/*! ../../shared/enums/connectionStatus */ "./scripts/shared/enums/connectionStatus.ts");
+/* harmony import */ var _wordpress_i18n__WEBPACK_IMPORTED_MODULE_9__ = __webpack_require__(/*! @wordpress/i18n */ "@wordpress/i18n");
+/* harmony import */ var _wordpress_i18n__WEBPACK_IMPORTED_MODULE_9___default = /*#__PURE__*/__webpack_require__.n(_wordpress_i18n__WEBPACK_IMPORTED_MODULE_9__);
+/* harmony import */ var _utils_withMetaData__WEBPACK_IMPORTED_MODULE_10__ = __webpack_require__(/*! ../../utils/withMetaData */ "./scripts/utils/withMetaData.ts");
+function ownKeys(object, enumerableOnly) { var keys = Object.keys(object); if (Object.getOwnPropertySymbols) { var symbols = Object.getOwnPropertySymbols(object); enumerableOnly && (symbols = symbols.filter(function (sym) { return Object.getOwnPropertyDescriptor(object, sym).enumerable; })), keys.push.apply(keys, symbols); } return keys; }
+
+function _objectSpread(target) { for (var i = 1; i < arguments.length; i++) { var source = null != arguments[i] ? arguments[i] : {}; i % 2 ? ownKeys(Object(source), !0).forEach(function (key) { _defineProperty(target, key, source[key]); }) : Object.getOwnPropertyDescriptors ? Object.defineProperties(target, Object.getOwnPropertyDescriptors(source)) : ownKeys(Object(source)).forEach(function (key) { Object.defineProperty(target, key, Object.getOwnPropertyDescriptor(source, key)); }); } return target; }
+
+function _defineProperty(obj, key, value) { if (key in obj) { Object.defineProperty(obj, key, { value: value, enumerable: true, configurable: true, writable: true }); } else { obj[key] = value; } return obj; }
+
+
+
+
+
+
+
+
+
+
+
+
+function registerFormBlock() {
+ var editComponent = function editComponent(props) {
+ if (props.attributes.preview) {
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_FormGutenbergPreview__WEBPACK_IMPORTED_MODULE_5__["default"], {});
+ } else if (_constants_leadinConfig__WEBPACK_IMPORTED_MODULE_4__.connectionStatus === _shared_enums_connectionStatus__WEBPACK_IMPORTED_MODULE_8__["default"].Connected) {
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_shared_Form_FormEdit__WEBPACK_IMPORTED_MODULE_7__["default"], _objectSpread(_objectSpread({}, props), {}, {
+ origin: "gutenberg",
+ preview: true
+ }));
+ } else {
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_shared_Common_ErrorHandler__WEBPACK_IMPORTED_MODULE_6__["default"], {
+ status: 401
+ });
+ }
+ }; // We do not support the full site editor: https://issues.hubspotcentral.com/browse/WP-1033
+
+
+ if (!_wordpress_blocks__WEBPACK_IMPORTED_MODULE_1__ || (0,_utils_withMetaData__WEBPACK_IMPORTED_MODULE_10__.isFullSiteEditor)()) {
+ return null;
+ }
+
+ _wordpress_blocks__WEBPACK_IMPORTED_MODULE_1__.registerBlockType('leadin/hubspot-form-block', {
+ title: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_9__.__)('HubSpot Form', 'leadin'),
+ description: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_9__.__)('Select and embed a HubSpot form', 'leadin'),
+ icon: _Common_SprocketIcon__WEBPACK_IMPORTED_MODULE_2__["default"],
+ category: 'leadin-blocks',
+ attributes: {
+ portalId: {
+ type: 'string',
+ "default": ''
+ },
+ formId: {
+ type: 'string'
+ },
+ formName: {
+ type: 'string'
+ },
+ preview: {
+ type: 'boolean',
+ "default": false
+ }
+ },
+ example: {
+ attributes: {
+ preview: true
+ }
+ },
+ edit: editComponent,
+ save: function save(props) {
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_FormBlockSave__WEBPACK_IMPORTED_MODULE_3__["default"], _objectSpread({}, props));
+ }
+ });
+}
+
+/***/ }),
+
+/***/ "./scripts/gutenberg/MeetingsBlock/MeetingGutenbergPreview.tsx":
+/*!*********************************************************************!*\
+ !*** ./scripts/gutenberg/MeetingsBlock/MeetingGutenbergPreview.tsx ***!
+ \*********************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ MeetingGutenbergPreview)
+/* harmony export */ });
+/* harmony import */ var react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react/jsx-runtime */ "./node_modules/react/jsx-runtime.js");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! react */ "react");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(react__WEBPACK_IMPORTED_MODULE_1__);
+/* harmony import */ var _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ../../constants/leadinConfig */ "./scripts/constants/leadinConfig.ts");
+/* harmony import */ var _UIComponents_UIImage__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ../UIComponents/UIImage */ "./scripts/gutenberg/UIComponents/UIImage.ts");
+
+
+
+
+function MeetingGutenbergPreview() {
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(react__WEBPACK_IMPORTED_MODULE_1__.Fragment, {
+ children: (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_UIComponents_UIImage__WEBPACK_IMPORTED_MODULE_3__["default"], {
+ alt: "Create a new Hubspot Meeting",
+ width: "100%",
+ src: "".concat(_constants_leadinConfig__WEBPACK_IMPORTED_MODULE_2__.pluginPath, "/public/assets/images/hubspot-meetings.png")
+ })
+ });
+}
+
+/***/ }),
+
+/***/ "./scripts/gutenberg/MeetingsBlock/MeetingSaveBlock.tsx":
+/*!**************************************************************!*\
+ !*** ./scripts/gutenberg/MeetingsBlock/MeetingSaveBlock.tsx ***!
+ \**************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ MeetingSaveBlock)
+/* harmony export */ });
+/* harmony import */ var react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react/jsx-runtime */ "./node_modules/react/jsx-runtime.js");
+/* harmony import */ var _wordpress_element__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! @wordpress/element */ "@wordpress/element");
+/* harmony import */ var _wordpress_element__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(_wordpress_element__WEBPACK_IMPORTED_MODULE_1__);
+
+
+function MeetingSaveBlock(_ref) {
+ var attributes = _ref.attributes;
+ var url = attributes.url;
+
+ if (url) {
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_wordpress_element__WEBPACK_IMPORTED_MODULE_1__.RawHTML, {
+ className: "wp-block-leadin-hubspot-meeting-block",
+ children: "[hubspot url=\"".concat(url, "\" type=\"meeting\"]")
+ });
+ }
+
+ return null;
+}
+
+/***/ }),
+
+/***/ "./scripts/gutenberg/MeetingsBlock/registerMeetingBlock.tsx":
+/*!******************************************************************!*\
+ !*** ./scripts/gutenberg/MeetingsBlock/registerMeetingBlock.tsx ***!
+ \******************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ registerMeetingBlock)
+/* harmony export */ });
+/* harmony import */ var react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react/jsx-runtime */ "./node_modules/react/jsx-runtime.js");
+/* harmony import */ var _wordpress_blocks__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! @wordpress/blocks */ "@wordpress/blocks");
+/* harmony import */ var _wordpress_blocks__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(_wordpress_blocks__WEBPACK_IMPORTED_MODULE_1__);
+/* harmony import */ var _Common_CalendarIcon__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ../Common/CalendarIcon */ "./scripts/gutenberg/Common/CalendarIcon.tsx");
+/* harmony import */ var _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ../../constants/leadinConfig */ "./scripts/constants/leadinConfig.ts");
+/* harmony import */ var _MeetingGutenbergPreview__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__(/*! ./MeetingGutenbergPreview */ "./scripts/gutenberg/MeetingsBlock/MeetingGutenbergPreview.tsx");
+/* harmony import */ var _MeetingSaveBlock__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__(/*! ./MeetingSaveBlock */ "./scripts/gutenberg/MeetingsBlock/MeetingSaveBlock.tsx");
+/* harmony import */ var _shared_Meeting_MeetingEdit__WEBPACK_IMPORTED_MODULE_6__ = __webpack_require__(/*! ../../shared/Meeting/MeetingEdit */ "./scripts/shared/Meeting/MeetingEdit.tsx");
+/* harmony import */ var _shared_Common_ErrorHandler__WEBPACK_IMPORTED_MODULE_7__ = __webpack_require__(/*! ../../shared/Common/ErrorHandler */ "./scripts/shared/Common/ErrorHandler.tsx");
+/* harmony import */ var _wordpress_i18n__WEBPACK_IMPORTED_MODULE_8__ = __webpack_require__(/*! @wordpress/i18n */ "@wordpress/i18n");
+/* harmony import */ var _wordpress_i18n__WEBPACK_IMPORTED_MODULE_8___default = /*#__PURE__*/__webpack_require__.n(_wordpress_i18n__WEBPACK_IMPORTED_MODULE_8__);
+/* harmony import */ var _utils_withMetaData__WEBPACK_IMPORTED_MODULE_9__ = __webpack_require__(/*! ../../utils/withMetaData */ "./scripts/utils/withMetaData.ts");
+function ownKeys(object, enumerableOnly) { var keys = Object.keys(object); if (Object.getOwnPropertySymbols) { var symbols = Object.getOwnPropertySymbols(object); enumerableOnly && (symbols = symbols.filter(function (sym) { return Object.getOwnPropertyDescriptor(object, sym).enumerable; })), keys.push.apply(keys, symbols); } return keys; }
+
+function _objectSpread(target) { for (var i = 1; i < arguments.length; i++) { var source = null != arguments[i] ? arguments[i] : {}; i % 2 ? ownKeys(Object(source), !0).forEach(function (key) { _defineProperty(target, key, source[key]); }) : Object.getOwnPropertyDescriptors ? Object.defineProperties(target, Object.getOwnPropertyDescriptors(source)) : ownKeys(Object(source)).forEach(function (key) { Object.defineProperty(target, key, Object.getOwnPropertyDescriptor(source, key)); }); } return target; }
+
+function _defineProperty(obj, key, value) { if (key in obj) { Object.defineProperty(obj, key, { value: value, enumerable: true, configurable: true, writable: true }); } else { obj[key] = value; } return obj; }
+
+
+
+
+
+
+
+
+
+
+
+var ConnectionStatus = {
+ Connected: 'Connected',
+ NotConnected: 'NotConnected'
+};
+function registerMeetingBlock() {
+ var editComponent = function editComponent(props) {
+ if (props.attributes.preview) {
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_MeetingGutenbergPreview__WEBPACK_IMPORTED_MODULE_4__["default"], {});
+ } else if (_constants_leadinConfig__WEBPACK_IMPORTED_MODULE_3__.connectionStatus === ConnectionStatus.Connected) {
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_shared_Meeting_MeetingEdit__WEBPACK_IMPORTED_MODULE_6__["default"], _objectSpread(_objectSpread({}, props), {}, {
+ preview: true,
+ origin: "gutenberg"
+ }));
+ } else {
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_shared_Common_ErrorHandler__WEBPACK_IMPORTED_MODULE_7__["default"], {
+ status: 401
+ });
+ }
+ }; // We do not support the full site editor: https://issues.hubspotcentral.com/browse/WP-1033
+
+
+ if (!_wordpress_blocks__WEBPACK_IMPORTED_MODULE_1__ || (0,_utils_withMetaData__WEBPACK_IMPORTED_MODULE_9__.isFullSiteEditor)()) {
+ return null;
+ }
+
+ _wordpress_blocks__WEBPACK_IMPORTED_MODULE_1__.registerBlockType('leadin/hubspot-meeting-block', {
+ title: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_8__.__)('Hubspot Meetings Scheduler', 'leadin'),
+ description: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_8__.__)('Schedule meetings faster and forget the back-and-forth emails Your calendar stays full, and you stay productive', 'leadin'),
+ icon: _Common_CalendarIcon__WEBPACK_IMPORTED_MODULE_2__["default"],
+ category: 'leadin-blocks',
+ attributes: {
+ url: {
+ type: 'string',
+ "default": ''
+ },
+ preview: {
+ type: 'boolean',
+ "default": false
+ }
+ },
+ example: {
+ attributes: {
+ preview: true
+ }
+ },
+ edit: editComponent,
+ save: function save(props) {
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_MeetingSaveBlock__WEBPACK_IMPORTED_MODULE_5__["default"], _objectSpread({}, props));
+ }
+ });
+}
+
+/***/ }),
+
+/***/ "./scripts/gutenberg/Sidebar/contentType.tsx":
+/*!***************************************************!*\
+ !*** ./scripts/gutenberg/Sidebar/contentType.tsx ***!
+ \***************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "registerHubspotSidebar": () => (/* binding */ registerHubspotSidebar)
+/* harmony export */ });
+/* harmony import */ var react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react/jsx-runtime */ "./node_modules/react/jsx-runtime.js");
+/* harmony import */ var _wordpress_plugins__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! @wordpress/plugins */ "@wordpress/plugins");
+/* harmony import */ var _wordpress_plugins__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(_wordpress_plugins__WEBPACK_IMPORTED_MODULE_1__);
+/* harmony import */ var _wordpress_edit_post__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! @wordpress/edit-post */ "@wordpress/edit-post");
+/* harmony import */ var _wordpress_edit_post__WEBPACK_IMPORTED_MODULE_2___default = /*#__PURE__*/__webpack_require__.n(_wordpress_edit_post__WEBPACK_IMPORTED_MODULE_2__);
+/* harmony import */ var _wordpress_components__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! @wordpress/components */ "@wordpress/components");
+/* harmony import */ var _wordpress_components__WEBPACK_IMPORTED_MODULE_3___default = /*#__PURE__*/__webpack_require__.n(_wordpress_components__WEBPACK_IMPORTED_MODULE_3__);
+/* harmony import */ var _wordpress_data__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__(/*! @wordpress/data */ "@wordpress/data");
+/* harmony import */ var _wordpress_data__WEBPACK_IMPORTED_MODULE_4___default = /*#__PURE__*/__webpack_require__.n(_wordpress_data__WEBPACK_IMPORTED_MODULE_4__);
+/* harmony import */ var _UIComponents_UISidebarSelectControl__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__(/*! ../UIComponents/UISidebarSelectControl */ "./scripts/gutenberg/UIComponents/UISidebarSelectControl.tsx");
+/* harmony import */ var _Common_SidebarSprocketIcon__WEBPACK_IMPORTED_MODULE_6__ = __webpack_require__(/*! ../Common/SidebarSprocketIcon */ "./scripts/gutenberg/Common/SidebarSprocketIcon.tsx");
+/* harmony import */ var styled_components__WEBPACK_IMPORTED_MODULE_11__ = __webpack_require__(/*! styled-components */ "./node_modules/styled-components/dist/styled-components.browser.esm.js");
+/* harmony import */ var _wordpress_i18n__WEBPACK_IMPORTED_MODULE_7__ = __webpack_require__(/*! @wordpress/i18n */ "@wordpress/i18n");
+/* harmony import */ var _wordpress_i18n__WEBPACK_IMPORTED_MODULE_7___default = /*#__PURE__*/__webpack_require__.n(_wordpress_i18n__WEBPACK_IMPORTED_MODULE_7__);
+/* harmony import */ var _iframe_useBackgroundApp__WEBPACK_IMPORTED_MODULE_8__ = __webpack_require__(/*! ../../iframe/useBackgroundApp */ "./scripts/iframe/useBackgroundApp.ts");
+/* harmony import */ var _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_9__ = __webpack_require__(/*! ../../constants/leadinConfig */ "./scripts/constants/leadinConfig.ts");
+/* harmony import */ var _utils_backgroundAppUtils__WEBPACK_IMPORTED_MODULE_10__ = __webpack_require__(/*! ../../utils/backgroundAppUtils */ "./scripts/utils/backgroundAppUtils.ts");
+var _templateObject;
+
+function _taggedTemplateLiteral(strings, raw) { if (!raw) { raw = strings.slice(0); } return Object.freeze(Object.defineProperties(strings, { raw: { value: Object.freeze(raw) } })); }
+
+
+
+
+
+
+
+
+
+
+
+
+
+function registerHubspotSidebar() {
+ var ContentTypeLabelStyle = styled_components__WEBPACK_IMPORTED_MODULE_11__["default"].div(_templateObject || (_templateObject = _taggedTemplateLiteral(["\n white-space: normal;\n text-transform: none;\n "])));
+
+ var ContentTypeLabel = (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(ContentTypeLabelStyle, {
+ children: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_7__.__)('Select the content type HubSpot Analytics uses to track this page', 'leadin')
+ });
+
+ var LeadinPluginSidebar = function LeadinPluginSidebar(_ref) {
+ var postType = _ref.postType;
+ return postType ? (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_wordpress_edit_post__WEBPACK_IMPORTED_MODULE_2__.PluginSidebar, {
+ name: "leadin",
+ title: "HubSpot",
+ icon: (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_wordpress_components__WEBPACK_IMPORTED_MODULE_3__.Icon, {
+ className: "hs-plugin-sidebar-sprocket",
+ icon: (0,_Common_SidebarSprocketIcon__WEBPACK_IMPORTED_MODULE_6__["default"])()
+ }),
+ children: (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_wordpress_components__WEBPACK_IMPORTED_MODULE_3__.PanelBody, {
+ title: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_7__.__)('HubSpot Analytics', 'leadin'),
+ initialOpen: true,
+ children: (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_iframe_useBackgroundApp__WEBPACK_IMPORTED_MODULE_8__.BackgroudAppContext.Provider, {
+ value: _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_9__.refreshToken && (0,_utils_backgroundAppUtils__WEBPACK_IMPORTED_MODULE_10__.getOrCreateBackgroundApp)(_constants_leadinConfig__WEBPACK_IMPORTED_MODULE_9__.refreshToken),
+ children: (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_UIComponents_UISidebarSelectControl__WEBPACK_IMPORTED_MODULE_5__["default"], {
+ metaKey: "content-type",
+ className: "select-content-type",
+ label: ContentTypeLabel,
+ options: [{
+ label: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_7__.__)('Detect Automatically', 'leadin'),
+ value: ''
+ }, {
+ label: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_7__.__)('Blog Post', 'leadin'),
+ value: 'blog-post'
+ }, {
+ label: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_7__.__)('Knowledge Article', 'leadin'),
+ value: 'knowledge-article'
+ }, {
+ label: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_7__.__)('Landing Page', 'leadin'),
+ value: 'landing-page'
+ }, {
+ label: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_7__.__)('Listing Page', 'leadin'),
+ value: 'listing-page'
+ }, {
+ label: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_7__.__)('Standard Page', 'leadin'),
+ value: 'standard-page'
+ }]
+ })
+ })
+ })
+ }) : null;
+ };
+
+ var LeadinPluginSidebarWrapper = (0,_wordpress_data__WEBPACK_IMPORTED_MODULE_4__.withSelect)(function (select) {
+ var data = select('core/editor');
+ return {
+ postType: data && data.getCurrentPostType() && data.getEditedPostAttribute('meta')
+ };
+ })(LeadinPluginSidebar);
+
+ if (_wordpress_plugins__WEBPACK_IMPORTED_MODULE_1__) {
+ _wordpress_plugins__WEBPACK_IMPORTED_MODULE_1__.registerPlugin('leadin', {
+ render: LeadinPluginSidebarWrapper,
+ icon: _Common_SidebarSprocketIcon__WEBPACK_IMPORTED_MODULE_6__["default"]
+ });
+ }
+}
+
+/***/ }),
+
+/***/ "./scripts/gutenberg/UIComponents/UIImage.ts":
+/*!***************************************************!*\
+ !*** ./scripts/gutenberg/UIComponents/UIImage.ts ***!
+ \***************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (__WEBPACK_DEFAULT_EXPORT__)
+/* harmony export */ });
+/* harmony import */ var _linaria_react__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! @linaria/react */ "./node_modules/@linaria/react/dist/index.mjs");
+
+
+var _exp = /*#__PURE__*/function _exp() {
+ return function (props) {
+ return props.height ? props.height : 'auto';
+ };
+};
+
+var _exp2 = /*#__PURE__*/function _exp2() {
+ return function (props) {
+ return props.width ? props.width : 'auto';
+ };
+};
+
+/* harmony default export */ const __WEBPACK_DEFAULT_EXPORT__ = (/*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_0__.styled)('img')({
+ name: "UIImage0",
+ "class": "ump7xqy",
+ propsAsIs: false,
+ vars: {
+ "ump7xqy-0": [_exp()],
+ "ump7xqy-1": [_exp2()]
+ }
+}));
+
+__webpack_require__(/*! ./UIImage.linaria.css!=!../../../node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./UIImage.ts */ "./scripts/gutenberg/UIComponents/UIImage.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/gutenberg/UIComponents/UIImage.ts");
+
+/***/ }),
+
+/***/ "./scripts/gutenberg/UIComponents/UISidebarSelectControl.tsx":
+/*!*******************************************************************!*\
+ !*** ./scripts/gutenberg/UIComponents/UISidebarSelectControl.tsx ***!
+ \*******************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (__WEBPACK_DEFAULT_EXPORT__)
+/* harmony export */ });
+/* harmony import */ var react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react/jsx-runtime */ "./node_modules/react/jsx-runtime.js");
+/* harmony import */ var _wordpress_components__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! @wordpress/components */ "@wordpress/components");
+/* harmony import */ var _wordpress_components__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(_wordpress_components__WEBPACK_IMPORTED_MODULE_1__);
+/* harmony import */ var _utils_withMetaData__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ../../utils/withMetaData */ "./scripts/utils/withMetaData.ts");
+/* harmony import */ var _iframe_useBackgroundApp__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ../../iframe/useBackgroundApp */ "./scripts/iframe/useBackgroundApp.ts");
+/* harmony import */ var _iframe_integratedMessages__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__(/*! ../../iframe/integratedMessages */ "./scripts/iframe/integratedMessages/index.ts");
+function ownKeys(object, enumerableOnly) { var keys = Object.keys(object); if (Object.getOwnPropertySymbols) { var symbols = Object.getOwnPropertySymbols(object); enumerableOnly && (symbols = symbols.filter(function (sym) { return Object.getOwnPropertyDescriptor(object, sym).enumerable; })), keys.push.apply(keys, symbols); } return keys; }
+
+function _objectSpread(target) { for (var i = 1; i < arguments.length; i++) { var source = null != arguments[i] ? arguments[i] : {}; i % 2 ? ownKeys(Object(source), !0).forEach(function (key) { _defineProperty(target, key, source[key]); }) : Object.getOwnPropertyDescriptors ? Object.defineProperties(target, Object.getOwnPropertyDescriptors(source)) : ownKeys(Object(source)).forEach(function (key) { Object.defineProperty(target, key, Object.getOwnPropertyDescriptor(source, key)); }); } return target; }
+
+function _defineProperty(obj, key, value) { if (key in obj) { Object.defineProperty(obj, key, { value: value, enumerable: true, configurable: true, writable: true }); } else { obj[key] = value; } return obj; }
+
+
+
+
+
+
+
+var UISidebarSelectControl = function UISidebarSelectControl(props) {
+ var isBackgroundAppReady = (0,_iframe_useBackgroundApp__WEBPACK_IMPORTED_MODULE_3__.useBackgroundAppContext)();
+ var monitorSidebarMetaChange = (0,_iframe_useBackgroundApp__WEBPACK_IMPORTED_MODULE_3__.usePostBackgroundMessage)();
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_wordpress_components__WEBPACK_IMPORTED_MODULE_1__.SelectControl, _objectSpread({
+ value: props.metaValue,
+ onChange: function onChange(content) {
+ if (props.setMetaValue) {
+ props.setMetaValue(content);
+ }
+
+ isBackgroundAppReady && monitorSidebarMetaChange({
+ key: _iframe_integratedMessages__WEBPACK_IMPORTED_MODULE_4__.ProxyMessages.TrackSidebarMetaChange,
+ payload: {
+ metaKey: props.metaKey
+ }
+ });
+ }
+ }, props));
+};
+
+/* harmony default export */ const __WEBPACK_DEFAULT_EXPORT__ = ((0,_utils_withMetaData__WEBPACK_IMPORTED_MODULE_2__["default"])(UISidebarSelectControl));
+
+/***/ }),
+
+/***/ "./scripts/iframe/integratedMessages/core/CoreMessages.ts":
+/*!****************************************************************!*\
+ !*** ./scripts/iframe/integratedMessages/core/CoreMessages.ts ***!
+ \****************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "CoreMessages": () => (/* binding */ CoreMessages)
+/* harmony export */ });
+var CoreMessages = {
+ HandshakeReceive: 'INTEGRATED_APP_EMBEDDER_HANDSHAKE_RECEIVED',
+ SendRefreshToken: 'INTEGRATED_APP_EMBEDDER_SEND_REFRESH_TOKEN',
+ ReloadParentFrame: 'INTEGRATED_APP_EMBEDDER_RELOAD_PARENT_FRAME',
+ RedirectParentFrame: 'INTEGRATED_APP_EMBEDDER_REDIRECT_PARENT_FRAME',
+ SendLocale: 'INTEGRATED_APP_EMBEDDER_SEND_LOCALE',
+ SendDeviceId: 'INTEGRATED_APP_EMBEDDER_SEND_DEVICE_ID'
+};
+
+/***/ }),
+
+/***/ "./scripts/iframe/integratedMessages/forms/FormsMessages.ts":
+/*!******************************************************************!*\
+ !*** ./scripts/iframe/integratedMessages/forms/FormsMessages.ts ***!
+ \******************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "FormMessages": () => (/* binding */ FormMessages)
+/* harmony export */ });
+var FormMessages = {
+ CreateFormAppNavigation: 'CREATE_FORM_APP_NAVIGATION'
+};
+
+/***/ }),
+
+/***/ "./scripts/iframe/integratedMessages/index.ts":
+/*!****************************************************!*\
+ !*** ./scripts/iframe/integratedMessages/index.ts ***!
+ \****************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "CoreMessages": () => (/* reexport safe */ _core_CoreMessages__WEBPACK_IMPORTED_MODULE_0__.CoreMessages),
+/* harmony export */ "FormMessages": () => (/* reexport safe */ _forms_FormsMessages__WEBPACK_IMPORTED_MODULE_1__.FormMessages),
+/* harmony export */ "LiveChatMessages": () => (/* reexport safe */ _livechat_LiveChatMessages__WEBPACK_IMPORTED_MODULE_2__.LiveChatMessages),
+/* harmony export */ "PluginMessages": () => (/* reexport safe */ _plugin_PluginMessages__WEBPACK_IMPORTED_MODULE_3__.PluginMessages),
+/* harmony export */ "ProxyMessages": () => (/* reexport safe */ _proxy_ProxyMessages__WEBPACK_IMPORTED_MODULE_4__.ProxyMessages)
+/* harmony export */ });
+/* harmony import */ var _core_CoreMessages__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! ./core/CoreMessages */ "./scripts/iframe/integratedMessages/core/CoreMessages.ts");
+/* harmony import */ var _forms_FormsMessages__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! ./forms/FormsMessages */ "./scripts/iframe/integratedMessages/forms/FormsMessages.ts");
+/* harmony import */ var _livechat_LiveChatMessages__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ./livechat/LiveChatMessages */ "./scripts/iframe/integratedMessages/livechat/LiveChatMessages.ts");
+/* harmony import */ var _plugin_PluginMessages__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ./plugin/PluginMessages */ "./scripts/iframe/integratedMessages/plugin/PluginMessages.ts");
+/* harmony import */ var _proxy_ProxyMessages__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__(/*! ./proxy/ProxyMessages */ "./scripts/iframe/integratedMessages/proxy/ProxyMessages.ts");
+
+
+
+
+
+
+/***/ }),
+
+/***/ "./scripts/iframe/integratedMessages/livechat/LiveChatMessages.ts":
+/*!************************************************************************!*\
+ !*** ./scripts/iframe/integratedMessages/livechat/LiveChatMessages.ts ***!
+ \************************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "LiveChatMessages": () => (/* binding */ LiveChatMessages)
+/* harmony export */ });
+var LiveChatMessages = {
+ CreateLiveChatAppNavigation: 'CREATE_LIVE_CHAT_APP_NAVIGATION'
+};
+
+/***/ }),
+
+/***/ "./scripts/iframe/integratedMessages/plugin/PluginMessages.ts":
+/*!********************************************************************!*\
+ !*** ./scripts/iframe/integratedMessages/plugin/PluginMessages.ts ***!
+ \********************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "PluginMessages": () => (/* binding */ PluginMessages)
+/* harmony export */ });
+var PluginMessages = {
+ PluginSettingsNavigation: 'PLUGIN_SETTINGS_NAVIGATION',
+ PluginLeadinConfig: 'PLUGIN_LEADIN_CONFIG',
+ TrackConsent: 'INTEGRATED_APP_EMBEDDER_TRACK_CONSENT',
+ InternalTrackingFetchRequest: 'INTEGRATED_TRACKING_FETCH_REQUEST',
+ InternalTrackingFetchResponse: 'INTEGRATED_TRACKING_FETCH_RESPONSE',
+ InternalTrackingFetchError: 'INTEGRATED_TRACKING_FETCH_ERROR',
+ InternalTrackingChangeRequest: 'INTEGRATED_TRACKING_CHANGE_REQUEST',
+ InternalTrackingChangeError: 'INTEGRATED_TRACKING_CHANGE_ERROR',
+ BusinessUnitFetchRequest: 'BUSINESS_UNIT_FETCH_REQUEST',
+ BusinessUnitFetchResponse: 'BUSINESS_UNIT_FETCH_FETCH_RESPONSE',
+ BusinessUnitFetchError: 'BUSINESS_UNIT_FETCH_FETCH_ERROR',
+ BusinessUnitChangeRequest: 'BUSINESS_UNIT_CHANGE_REQUEST',
+ BusinessUnitChangeError: 'BUSINESS_UNIT_CHANGE_ERROR',
+ SkipReviewRequest: 'SKIP_REVIEW_REQUEST',
+ SkipReviewResponse: 'SKIP_REVIEW_RESPONSE',
+ SkipReviewError: 'SKIP_REVIEW_ERROR',
+ RemoveParentQueryParam: 'REMOVE_PARENT_QUERY_PARAM',
+ ContentEmbedInstallRequest: 'CONTENT_EMBED_INSTALL_REQUEST',
+ ContentEmbedInstallResponse: 'CONTENT_EMBED_INSTALL_RESPONSE',
+ ContentEmbedInstallError: 'CONTENT_EMBED_INSTALL_ERROR',
+ ContentEmbedActivationRequest: 'CONTENT_EMBED_ACTIVATION_REQUEST',
+ ContentEmbedActivationResponse: 'CONTENT_EMBED_ACTIVATION_RESPONSE',
+ ContentEmbedActivationError: 'CONTENT_EMBED_ACTIVATION_ERROR'
+};
+
+/***/ }),
+
+/***/ "./scripts/iframe/integratedMessages/proxy/ProxyMessages.ts":
+/*!******************************************************************!*\
+ !*** ./scripts/iframe/integratedMessages/proxy/ProxyMessages.ts ***!
+ \******************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "ProxyMessages": () => (/* binding */ ProxyMessages)
+/* harmony export */ });
+var ProxyMessages = {
+ FetchForms: 'FETCH_FORMS',
+ FetchForm: 'FETCH_FORM',
+ CreateFormFromTemplate: 'CREATE_FORM_FROM_TEMPLATE',
+ FetchAuth: 'FETCH_AUTH',
+ FetchMeetingsAndUsers: 'FETCH_MEETINGS_AND_USERS',
+ FetchContactsCreateSinceActivation: 'FETCH_CONTACTS_CREATED_SINCE_ACTIVATION',
+ FetchOrCreateMeetingUser: 'FETCH_OR_CREATE_MEETING_USER',
+ ConnectMeetingsCalendar: 'CONNECT_MEETINGS_CALENDAR',
+ TrackFormPreviewRender: 'TRACK_FORM_PREVIEW_RENDER',
+ TrackFormCreatedFromTemplate: 'TRACK_FORM_CREATED_FROM_TEMPLATE',
+ TrackFormCreationFailed: 'TRACK_FORM_CREATION_FAILED',
+ TrackMeetingPreviewRender: 'TRACK_MEETING_PREVIEW_RENDER',
+ TrackSidebarMetaChange: 'TRACK_SIDEBAR_META_CHANGE',
+ TrackReviewBannerRender: 'TRACK_REVIEW_BANNER_RENDER',
+ TrackReviewBannerInteraction: 'TRACK_REVIEW_BANNER_INTERACTION',
+ TrackReviewBannerDismissed: 'TRACK_REVIEW_BANNER_DISMISSED',
+ TrackPluginDeactivation: 'TRACK_PLUGIN_DEACTIVATION'
+};
+
+/***/ }),
+
+/***/ "./scripts/iframe/useBackgroundApp.ts":
+/*!********************************************!*\
+ !*** ./scripts/iframe/useBackgroundApp.ts ***!
+ \********************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "BackgroudAppContext": () => (/* binding */ BackgroudAppContext),
+/* harmony export */ "useBackgroundAppContext": () => (/* binding */ useBackgroundAppContext),
+/* harmony export */ "usePostAsyncBackgroundMessage": () => (/* binding */ usePostAsyncBackgroundMessage),
+/* harmony export */ "usePostBackgroundMessage": () => (/* binding */ usePostBackgroundMessage)
+/* harmony export */ });
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react */ "react");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(react__WEBPACK_IMPORTED_MODULE_0__);
+
+var BackgroudAppContext = /*#__PURE__*/(0,react__WEBPACK_IMPORTED_MODULE_0__.createContext)(null);
+function useBackgroundAppContext() {
+ return (0,react__WEBPACK_IMPORTED_MODULE_0__.useContext)(BackgroudAppContext);
+}
+function usePostBackgroundMessage() {
+ var app = useBackgroundAppContext();
+ return function (message) {
+ app.postMessage(message);
+ };
+}
+function usePostAsyncBackgroundMessage() {
+ var app = useBackgroundAppContext();
+ return function (message) {
+ return app.postAsyncMessage(message);
+ };
+}
+
+/***/ }),
+
+/***/ "./scripts/lib/Raven.ts":
+/*!******************************!*\
+ !*** ./scripts/lib/Raven.ts ***!
+ \******************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "configureRaven": () => (/* binding */ configureRaven),
+/* harmony export */ "default": () => (__WEBPACK_DEFAULT_EXPORT__)
+/* harmony export */ });
+/* harmony import */ var raven_js__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! raven-js */ "./node_modules/raven-js/src/singleton.js");
+/* harmony import */ var raven_js__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(raven_js__WEBPACK_IMPORTED_MODULE_0__);
+/* harmony import */ var _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! ../constants/leadinConfig */ "./scripts/constants/leadinConfig.ts");
+
+
+function configureRaven() {
+ if (_constants_leadinConfig__WEBPACK_IMPORTED_MODULE_1__.hubspotBaseUrl.indexOf('app.hubspot.com') === -1) {
+ return;
+ }
+
+ raven_js__WEBPACK_IMPORTED_MODULE_0___default().config('https://e9b8f382cdd130c0d415cd977d2be56f@exceptions.hubspot.com/1', {
+ instrument: {
+ tryCatch: false
+ },
+ release: _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_1__.leadinPluginVersion
+ }).install();
+ raven_js__WEBPACK_IMPORTED_MODULE_0___default().setTagsContext({
+ v: _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_1__.leadinPluginVersion,
+ php: _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_1__.phpVersion,
+ wordpress: _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_1__.wpVersion
+ });
+ raven_js__WEBPACK_IMPORTED_MODULE_0___default().setExtraContext({
+ hub: _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_1__.portalId,
+ plugins: Object.keys(_constants_leadinConfig__WEBPACK_IMPORTED_MODULE_1__.plugins).map(function (name) {
+ return "".concat(name, "#").concat(_constants_leadinConfig__WEBPACK_IMPORTED_MODULE_1__.plugins[name]);
+ }).join(',')
+ });
+}
+/* harmony default export */ const __WEBPACK_DEFAULT_EXPORT__ = ((raven_js__WEBPACK_IMPORTED_MODULE_0___default()));
+
+/***/ }),
+
+/***/ "./scripts/shared/Common/AsyncSelect.tsx":
+/*!***********************************************!*\
+ !*** ./scripts/shared/Common/AsyncSelect.tsx ***!
+ \***********************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ AsyncSelect)
+/* harmony export */ });
+/* harmony import */ var react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react/jsx-runtime */ "./node_modules/react/jsx-runtime.js");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! react */ "react");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(react__WEBPACK_IMPORTED_MODULE_1__);
+/* harmony import */ var _linaria_react__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__(/*! @linaria/react */ "./node_modules/@linaria/react/dist/index.mjs");
+/* harmony import */ var _UIComponents_colors__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ../UIComponents/colors */ "./scripts/shared/UIComponents/colors.ts");
+/* harmony import */ var _UIComponents_UISpinner__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ../UIComponents/UISpinner */ "./scripts/shared/UIComponents/UISpinner.tsx");
+/* harmony import */ var _enums_loadState__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__(/*! ../enums/loadState */ "./scripts/shared/enums/loadState.ts");
+function _slicedToArray(arr, i) { return _arrayWithHoles(arr) || _iterableToArrayLimit(arr, i) || _unsupportedIterableToArray(arr, i) || _nonIterableRest(); }
+
+function _nonIterableRest() { throw new TypeError("Invalid attempt to destructure non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method."); }
+
+function _unsupportedIterableToArray(o, minLen) { if (!o) return; if (typeof o === "string") return _arrayLikeToArray(o, minLen); var n = Object.prototype.toString.call(o).slice(8, -1); if (n === "Object" && o.constructor) n = o.constructor.name; if (n === "Map" || n === "Set") return Array.from(o); if (n === "Arguments" || /^(?:Ui|I)nt(?:8|16|32)(?:Clamped)?Array$/.test(n)) return _arrayLikeToArray(o, minLen); }
+
+function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len = arr.length; for (var i = 0, arr2 = new Array(len); i < len; i++) { arr2[i] = arr[i]; } return arr2; }
+
+function _iterableToArrayLimit(arr, i) { var _i = arr == null ? null : typeof Symbol !== "undefined" && arr[Symbol.iterator] || arr["@@iterator"]; if (_i == null) return; var _arr = []; var _n = true; var _d = false; var _s, _e; try { for (_i = _i.call(arr); !(_n = (_s = _i.next()).done); _n = true) { _arr.push(_s.value); if (i && _arr.length === i) break; } } catch (err) { _d = true; _e = err; } finally { try { if (!_n && _i["return"] != null) _i["return"](); } finally { if (_d) throw _e; } } return _arr; }
+
+function _arrayWithHoles(arr) { if (Array.isArray(arr)) return arr; }
+
+
+
+
+
+
+
+var Container = /*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_5__.styled)('div')({
+ name: "Container",
+ "class": "c1wxx7eu",
+ propsAsIs: false
+});
+
+var _exp2 = /*#__PURE__*/function _exp2() {
+ return function (props) {
+ return props.focused ? '0' : '1px';
+ };
+};
+
+var _exp3 = /*#__PURE__*/function _exp3() {
+ return function (props) {
+ return props.focused ? "0 0 0 2px ".concat(_UIComponents_colors__WEBPACK_IMPORTED_MODULE_2__.CALYPSO_MEDIUM) : 'none';
+ };
+};
+
+var ControlContainer = /*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_5__.styled)('div')({
+ name: "ControlContainer",
+ "class": "c1rgwbep",
+ propsAsIs: false,
+ vars: {
+ "c1rgwbep-0": [_exp2()],
+ "c1rgwbep-1": [_exp3()]
+ }
+});
+var ValueContainer = /*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_5__.styled)('div')({
+ name: "ValueContainer",
+ "class": "v1mdmbaj",
+ propsAsIs: false
+});
+var Placeholder = /*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_5__.styled)('div')({
+ name: "Placeholder",
+ "class": "p1gwkvxy",
+ propsAsIs: false
+});
+var SingleValue = /*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_5__.styled)('div')({
+ name: "SingleValue",
+ "class": "s1bwlafs",
+ propsAsIs: false
+});
+var IndicatorContainer = /*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_5__.styled)('div')({
+ name: "IndicatorContainer",
+ "class": "i196z9y5",
+ propsAsIs: false
+});
+var DropdownIndicator = /*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_5__.styled)('div')({
+ name: "DropdownIndicator",
+ "class": "d1dfo5ow",
+ propsAsIs: false
+});
+var InputContainer = /*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_5__.styled)('div')({
+ name: "InputContainer",
+ "class": "if3lze",
+ propsAsIs: false
+});
+var Input = /*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_5__.styled)('input')({
+ name: "Input",
+ "class": "i9kxf50",
+ propsAsIs: false
+});
+var InputShadow = /*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_5__.styled)('div')({
+ name: "InputShadow",
+ "class": "igjr3uc",
+ propsAsIs: false
+});
+var MenuContainer = /*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_5__.styled)('div')({
+ name: "MenuContainer",
+ "class": "mhb9if7",
+ propsAsIs: false
+});
+var MenuList = /*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_5__.styled)('div')({
+ name: "MenuList",
+ "class": "mxaof7s",
+ propsAsIs: false
+});
+var MenuGroup = /*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_5__.styled)('div')({
+ name: "MenuGroup",
+ "class": "mw50s5v",
+ propsAsIs: false
+});
+var MenuGroupHeader = /*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_5__.styled)('div')({
+ name: "MenuGroupHeader",
+ "class": "m11rzvjw",
+ propsAsIs: false
+});
+
+var _exp5 = /*#__PURE__*/function _exp5() {
+ return function (props) {
+ return props.selected ? _UIComponents_colors__WEBPACK_IMPORTED_MODULE_2__.CALYPSO_MEDIUM : 'transparent';
+ };
+};
+
+var _exp6 = /*#__PURE__*/function _exp6() {
+ return function (props) {
+ return props.selected ? '#fff' : 'inherit';
+ };
+};
+
+var _exp7 = /*#__PURE__*/function _exp7() {
+ return function (props) {
+ return props.selected ? _UIComponents_colors__WEBPACK_IMPORTED_MODULE_2__.CALYPSO_MEDIUM : _UIComponents_colors__WEBPACK_IMPORTED_MODULE_2__.CALYPSO_LIGHT;
+ };
+};
+
+var MenuItem = /*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_5__.styled)('div')({
+ name: "MenuItem",
+ "class": "m1jcdsjv",
+ propsAsIs: false,
+ vars: {
+ "m1jcdsjv-0": [_exp5()],
+ "m1jcdsjv-1": [_exp6()],
+ "m1jcdsjv-2": [_exp7()]
+ }
+});
+function AsyncSelect(_ref) {
+ var placeholder = _ref.placeholder,
+ value = _ref.value,
+ loadOptions = _ref.loadOptions,
+ onChange = _ref.onChange,
+ defaultOptions = _ref.defaultOptions;
+ var inputEl = (0,react__WEBPACK_IMPORTED_MODULE_1__.useRef)(null);
+ var inputShadowEl = (0,react__WEBPACK_IMPORTED_MODULE_1__.useRef)(null);
+
+ var _useState = (0,react__WEBPACK_IMPORTED_MODULE_1__.useState)(false),
+ _useState2 = _slicedToArray(_useState, 2),
+ isFocused = _useState2[0],
+ setFocus = _useState2[1];
+
+ var _useState3 = (0,react__WEBPACK_IMPORTED_MODULE_1__.useState)(_enums_loadState__WEBPACK_IMPORTED_MODULE_4__["default"].NotLoaded),
+ _useState4 = _slicedToArray(_useState3, 2),
+ loadState = _useState4[0],
+ setLoadState = _useState4[1];
+
+ var _useState5 = (0,react__WEBPACK_IMPORTED_MODULE_1__.useState)(''),
+ _useState6 = _slicedToArray(_useState5, 2),
+ localValue = _useState6[0],
+ setLocalValue = _useState6[1];
+
+ var _useState7 = (0,react__WEBPACK_IMPORTED_MODULE_1__.useState)(defaultOptions),
+ _useState8 = _slicedToArray(_useState7, 2),
+ options = _useState8[0],
+ setOptions = _useState8[1];
+
+ var inputSize = "".concat(inputShadowEl.current ? inputShadowEl.current.clientWidth + 10 : 2, "px");
+ (0,react__WEBPACK_IMPORTED_MODULE_1__.useEffect)(function () {
+ if (loadOptions && loadState === _enums_loadState__WEBPACK_IMPORTED_MODULE_4__["default"].NotLoaded) {
+ loadOptions('', function (result) {
+ setOptions(result);
+ setLoadState(_enums_loadState__WEBPACK_IMPORTED_MODULE_4__["default"].Idle);
+ });
+ }
+ }, [loadOptions, loadState]);
+
+ var renderItems = function renderItems() {
+ var items = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : [];
+ var parentKey = arguments.length > 1 ? arguments[1] : undefined;
+ return items.map(function (item, index) {
+ if (item.options) {
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsxs)(MenuGroup, {
+ children: [(0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(MenuGroupHeader, {
+ id: "".concat(index, "-heading"),
+ children: item.label
+ }), (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)("div", {
+ children: renderItems(item.options, index)
+ })]
+ }, "async-select-item-".concat(index));
+ } else {
+ var key = "async-select-item-".concat(parentKey !== undefined ? "".concat(parentKey, "-").concat(index) : index);
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(MenuItem, {
+ id: key,
+ selected: value && item.value === value.value,
+ onClick: function onClick() {
+ onChange(item);
+ setFocus(false);
+ },
+ children: item.label
+ }, key);
+ }
+ });
+ };
+
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsxs)(Container, {
+ children: [(0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsxs)(ControlContainer, {
+ id: "leadin-async-selector",
+ focused: isFocused,
+ onClick: function onClick() {
+ if (isFocused) {
+ if (inputEl.current) {
+ inputEl.current.blur();
+ }
+
+ setFocus(false);
+ setLocalValue('');
+ } else {
+ if (inputEl.current) {
+ inputEl.current.focus();
+ }
+
+ setFocus(true);
+ }
+ },
+ children: [(0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsxs)(ValueContainer, {
+ children: [localValue === '' && (!value ? (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(Placeholder, {
+ children: placeholder
+ }) : (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(SingleValue, {
+ children: value.label
+ })), (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsxs)(InputContainer, {
+ children: [(0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(Input, {
+ ref: inputEl,
+ onFocus: function onFocus() {
+ setFocus(true);
+ },
+ onChange: function onChange(e) {
+ setLocalValue(e.target.value);
+ setLoadState(_enums_loadState__WEBPACK_IMPORTED_MODULE_4__["default"].Loading);
+ loadOptions && loadOptions(e.target.value, function (result) {
+ setOptions(result);
+ setLoadState(_enums_loadState__WEBPACK_IMPORTED_MODULE_4__["default"].Idle);
+ });
+ },
+ value: localValue,
+ width: inputSize,
+ id: "asycn-select-input"
+ }), (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(InputShadow, {
+ ref: inputShadowEl,
+ children: localValue
+ })]
+ })]
+ }), (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsxs)(IndicatorContainer, {
+ children: [loadState === _enums_loadState__WEBPACK_IMPORTED_MODULE_4__["default"].Loading && (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_UIComponents_UISpinner__WEBPACK_IMPORTED_MODULE_3__["default"], {}), (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(DropdownIndicator, {})]
+ })]
+ }), isFocused && (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(MenuContainer, {
+ children: (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(MenuList, {
+ children: renderItems(options)
+ })
+ })]
+ });
+}
+
+__webpack_require__(/*! ./AsyncSelect.linaria.css!=!../../../node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./AsyncSelect.tsx */ "./scripts/shared/Common/AsyncSelect.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/Common/AsyncSelect.tsx");
+
+/***/ }),
+
+/***/ "./scripts/shared/Common/ErrorHandler.tsx":
+/*!************************************************!*\
+ !*** ./scripts/shared/Common/ErrorHandler.tsx ***!
+ \************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ ErrorHandler)
+/* harmony export */ });
+/* harmony import */ var react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react/jsx-runtime */ "./node_modules/react/jsx-runtime.js");
+/* harmony import */ var _UIComponents_UIButton__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! ../UIComponents/UIButton */ "./scripts/shared/UIComponents/UIButton.ts");
+/* harmony import */ var _UIComponents_UIContainer__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ../UIComponents/UIContainer */ "./scripts/shared/UIComponents/UIContainer.ts");
+/* harmony import */ var _HubspotWrapper__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ./HubspotWrapper */ "./scripts/shared/Common/HubspotWrapper.ts");
+/* harmony import */ var _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__(/*! ../../constants/leadinConfig */ "./scripts/constants/leadinConfig.ts");
+/* harmony import */ var _wordpress_i18n__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__(/*! @wordpress/i18n */ "@wordpress/i18n");
+/* harmony import */ var _wordpress_i18n__WEBPACK_IMPORTED_MODULE_5___default = /*#__PURE__*/__webpack_require__.n(_wordpress_i18n__WEBPACK_IMPORTED_MODULE_5__);
+
+
+
+
+
+
+
+
+function redirectToPlugin() {
+ window.location.href = "".concat(_constants_leadinConfig__WEBPACK_IMPORTED_MODULE_4__.adminUrl, "admin.php?page=leadin&leadin_expired=").concat(_constants_leadinConfig__WEBPACK_IMPORTED_MODULE_4__.redirectNonce);
+}
+
+function ErrorHandler(_ref) {
+ var status = _ref.status,
+ resetErrorState = _ref.resetErrorState,
+ _ref$errorInfo = _ref.errorInfo,
+ errorInfo = _ref$errorInfo === void 0 ? {
+ header: '',
+ message: '',
+ action: ''
+ } : _ref$errorInfo;
+ var isUnauthorized = status === 401 || status === 403;
+ var errorHeader = isUnauthorized ? (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_5__.__)("Your plugin isn't authorized", 'leadin') : errorInfo.header;
+ var errorMessage = isUnauthorized ? (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_5__.__)('Reauthorize your plugin to access your free HubSpot tools', 'leadin') : errorInfo.message;
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_HubspotWrapper__WEBPACK_IMPORTED_MODULE_3__["default"], {
+ pluginPath: _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_4__.pluginPath,
+ children: (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsxs)(_UIComponents_UIContainer__WEBPACK_IMPORTED_MODULE_2__["default"], {
+ textAlign: "center",
+ children: [(0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)("h4", {
+ children: errorHeader
+ }), (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)("p", {
+ children: (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)("b", {
+ children: errorMessage
+ })
+ }), isUnauthorized ? (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_UIComponents_UIButton__WEBPACK_IMPORTED_MODULE_1__["default"], {
+ "data-test-id": "authorize-button",
+ onClick: redirectToPlugin,
+ children: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_5__.__)('Go to plugin', 'leadin')
+ }) : (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_UIComponents_UIButton__WEBPACK_IMPORTED_MODULE_1__["default"], {
+ "data-test-id": "retry-button",
+ onClick: resetErrorState,
+ children: errorInfo.action
+ })]
+ })
+ });
+}
+
+/***/ }),
+
+/***/ "./scripts/shared/Common/HubspotWrapper.ts":
+/*!*************************************************!*\
+ !*** ./scripts/shared/Common/HubspotWrapper.ts ***!
+ \*************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (__WEBPACK_DEFAULT_EXPORT__)
+/* harmony export */ });
+/* harmony import */ var _linaria_react__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! @linaria/react */ "./node_modules/@linaria/react/dist/index.mjs");
+
+
+var _exp = /*#__PURE__*/function _exp() {
+ return function (props) {
+ return "url(".concat(props.pluginPath, "/public/assets/images/hubspot.svg)");
+ };
+};
+
+var _exp2 = /*#__PURE__*/function _exp2() {
+ return function (props) {
+ return props.padding || '90px 20% 25px';
+ };
+};
+
+/* harmony default export */ const __WEBPACK_DEFAULT_EXPORT__ = (/*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_0__.styled)('div')({
+ name: "HubspotWrapper0",
+ "class": "h1q5v5ee",
+ propsAsIs: false,
+ vars: {
+ "h1q5v5ee-0": [_exp()],
+ "h1q5v5ee-1": [_exp2()]
+ }
+}));
+
+__webpack_require__(/*! ./HubspotWrapper.linaria.css!=!../../../node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./HubspotWrapper.ts */ "./scripts/shared/Common/HubspotWrapper.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/Common/HubspotWrapper.ts");
+
+/***/ }),
+
+/***/ "./scripts/shared/Common/LoadingBlock.tsx":
+/*!************************************************!*\
+ !*** ./scripts/shared/Common/LoadingBlock.tsx ***!
+ \************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ LoadingBlock)
+/* harmony export */ });
+/* harmony import */ var react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react/jsx-runtime */ "./node_modules/react/jsx-runtime.js");
+/* harmony import */ var _HubspotWrapper__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! ./HubspotWrapper */ "./scripts/shared/Common/HubspotWrapper.ts");
+/* harmony import */ var _UIComponents_UISpinner__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ../UIComponents/UISpinner */ "./scripts/shared/UIComponents/UISpinner.tsx");
+/* harmony import */ var _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ../../constants/leadinConfig */ "./scripts/constants/leadinConfig.ts");
+
+
+
+
+function LoadingBlock() {
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_HubspotWrapper__WEBPACK_IMPORTED_MODULE_1__["default"], {
+ pluginPath: _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_3__.pluginPath,
+ children: (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_UIComponents_UISpinner__WEBPACK_IMPORTED_MODULE_2__["default"], {
+ size: 50
+ })
+ });
+}
+
+/***/ }),
+
+/***/ "./scripts/shared/Form/FormEdit.tsx":
+/*!******************************************!*\
+ !*** ./scripts/shared/Form/FormEdit.tsx ***!
+ \******************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ FormEditContainer)
+/* harmony export */ });
+/* harmony import */ var react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react/jsx-runtime */ "./node_modules/react/jsx-runtime.js");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! react */ "react");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(react__WEBPACK_IMPORTED_MODULE_1__);
+/* harmony import */ var _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ../../constants/leadinConfig */ "./scripts/constants/leadinConfig.ts");
+/* harmony import */ var _UIComponents_UISpacer__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ../UIComponents/UISpacer */ "./scripts/shared/UIComponents/UISpacer.ts");
+/* harmony import */ var _PreviewForm__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__(/*! ./PreviewForm */ "./scripts/shared/Form/PreviewForm.tsx");
+/* harmony import */ var _FormSelect__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__(/*! ./FormSelect */ "./scripts/shared/Form/FormSelect.tsx");
+/* harmony import */ var _iframe_useBackgroundApp__WEBPACK_IMPORTED_MODULE_6__ = __webpack_require__(/*! ../../iframe/useBackgroundApp */ "./scripts/iframe/useBackgroundApp.ts");
+/* harmony import */ var _iframe_integratedMessages__WEBPACK_IMPORTED_MODULE_7__ = __webpack_require__(/*! ../../iframe/integratedMessages */ "./scripts/iframe/integratedMessages/index.ts");
+/* harmony import */ var _Common_LoadingBlock__WEBPACK_IMPORTED_MODULE_8__ = __webpack_require__(/*! ../Common/LoadingBlock */ "./scripts/shared/Common/LoadingBlock.tsx");
+/* harmony import */ var _utils_backgroundAppUtils__WEBPACK_IMPORTED_MODULE_9__ = __webpack_require__(/*! ../../utils/backgroundAppUtils */ "./scripts/utils/backgroundAppUtils.ts");
+function ownKeys(object, enumerableOnly) { var keys = Object.keys(object); if (Object.getOwnPropertySymbols) { var symbols = Object.getOwnPropertySymbols(object); enumerableOnly && (symbols = symbols.filter(function (sym) { return Object.getOwnPropertyDescriptor(object, sym).enumerable; })), keys.push.apply(keys, symbols); } return keys; }
+
+function _objectSpread(target) { for (var i = 1; i < arguments.length; i++) { var source = null != arguments[i] ? arguments[i] : {}; i % 2 ? ownKeys(Object(source), !0).forEach(function (key) { _defineProperty(target, key, source[key]); }) : Object.getOwnPropertyDescriptors ? Object.defineProperties(target, Object.getOwnPropertyDescriptors(source)) : ownKeys(Object(source)).forEach(function (key) { Object.defineProperty(target, key, Object.getOwnPropertyDescriptor(source, key)); }); } return target; }
+
+function _defineProperty(obj, key, value) { if (key in obj) { Object.defineProperty(obj, key, { value: value, enumerable: true, configurable: true, writable: true }); } else { obj[key] = value; } return obj; }
+
+
+
+
+
+
+
+
+
+
+
+
+function FormEdit(_ref) {
+ var attributes = _ref.attributes,
+ isSelected = _ref.isSelected,
+ setAttributes = _ref.setAttributes,
+ _ref$preview = _ref.preview,
+ preview = _ref$preview === void 0 ? true : _ref$preview,
+ _ref$origin = _ref.origin,
+ origin = _ref$origin === void 0 ? 'gutenberg' : _ref$origin;
+ var formId = attributes.formId,
+ formName = attributes.formName;
+ var formSelected = _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_2__.portalId && formId;
+ var isBackgroundAppReady = (0,_iframe_useBackgroundApp__WEBPACK_IMPORTED_MODULE_6__.useBackgroundAppContext)();
+ var monitorFormPreviewRender = (0,_iframe_useBackgroundApp__WEBPACK_IMPORTED_MODULE_6__.usePostBackgroundMessage)();
+
+ var handleChange = function handleChange(selectedForm) {
+ setAttributes({
+ portalId: _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_2__.portalId,
+ formId: selectedForm.value,
+ formName: selectedForm.label
+ });
+ };
+
+ (0,react__WEBPACK_IMPORTED_MODULE_1__.useEffect)(function () {
+ monitorFormPreviewRender({
+ key: _iframe_integratedMessages__WEBPACK_IMPORTED_MODULE_7__.ProxyMessages.TrackFormPreviewRender,
+ payload: {
+ origin: origin
+ }
+ });
+ }, [origin]);
+ return !isBackgroundAppReady ? (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_Common_LoadingBlock__WEBPACK_IMPORTED_MODULE_8__["default"], {}) : (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsxs)(react__WEBPACK_IMPORTED_MODULE_1__.Fragment, {
+ children: [(isSelected || !formSelected) && (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_FormSelect__WEBPACK_IMPORTED_MODULE_5__["default"], {
+ formId: formId,
+ formName: formName,
+ handleChange: handleChange,
+ origin: origin
+ }), formSelected && (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsxs)(react__WEBPACK_IMPORTED_MODULE_1__.Fragment, {
+ children: [isSelected && (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_UIComponents_UISpacer__WEBPACK_IMPORTED_MODULE_3__["default"], {}), preview && (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_PreviewForm__WEBPACK_IMPORTED_MODULE_4__["default"], {
+ portalId: _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_2__.portalId,
+ formId: formId
+ })]
+ })]
+ });
+}
+
+function FormEditContainer(props) {
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_iframe_useBackgroundApp__WEBPACK_IMPORTED_MODULE_6__.BackgroudAppContext.Provider, {
+ value: _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_2__.refreshToken && (0,_utils_backgroundAppUtils__WEBPACK_IMPORTED_MODULE_9__.getOrCreateBackgroundApp)(_constants_leadinConfig__WEBPACK_IMPORTED_MODULE_2__.refreshToken),
+ children: (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(FormEdit, _objectSpread({}, props))
+ });
+}
+
+/***/ }),
+
+/***/ "./scripts/shared/Form/FormSelect.tsx":
+/*!********************************************!*\
+ !*** ./scripts/shared/Form/FormSelect.tsx ***!
+ \********************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ FormSelect)
+/* harmony export */ });
+/* harmony import */ var react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react/jsx-runtime */ "./node_modules/react/jsx-runtime.js");
+/* harmony import */ var _FormSelector__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! ./FormSelector */ "./scripts/shared/Form/FormSelector.tsx");
+/* harmony import */ var _Common_LoadingBlock__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ../Common/LoadingBlock */ "./scripts/shared/Common/LoadingBlock.tsx");
+/* harmony import */ var _wordpress_i18n__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! @wordpress/i18n */ "@wordpress/i18n");
+/* harmony import */ var _wordpress_i18n__WEBPACK_IMPORTED_MODULE_3___default = /*#__PURE__*/__webpack_require__.n(_wordpress_i18n__WEBPACK_IMPORTED_MODULE_3__);
+/* harmony import */ var _hooks_useForms__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__(/*! ./hooks/useForms */ "./scripts/shared/Form/hooks/useForms.ts");
+/* harmony import */ var _hooks_useCreateFormFromTemplate__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__(/*! ./hooks/useCreateFormFromTemplate */ "./scripts/shared/Form/hooks/useCreateFormFromTemplate.ts");
+/* harmony import */ var _constants_defaultFormOptions__WEBPACK_IMPORTED_MODULE_6__ = __webpack_require__(/*! ../../constants/defaultFormOptions */ "./scripts/constants/defaultFormOptions.ts");
+/* harmony import */ var _Common_ErrorHandler__WEBPACK_IMPORTED_MODULE_7__ = __webpack_require__(/*! ../Common/ErrorHandler */ "./scripts/shared/Common/ErrorHandler.tsx");
+
+
+
+
+
+
+
+
+function FormSelect(_ref) {
+ var formId = _ref.formId,
+ formName = _ref.formName,
+ handleChange = _ref.handleChange,
+ _ref$origin = _ref.origin,
+ origin = _ref$origin === void 0 ? 'gutenberg' : _ref$origin;
+
+ var _useForms = (0,_hooks_useForms__WEBPACK_IMPORTED_MODULE_4__["default"])(),
+ search = _useForms.search,
+ formApiError = _useForms.formApiError,
+ reset = _useForms.reset;
+
+ var _useCreateFormFromTem = (0,_hooks_useCreateFormFromTemplate__WEBPACK_IMPORTED_MODULE_5__["default"])(origin),
+ createFormByTemplate = _useCreateFormFromTem.createFormByTemplate,
+ createReset = _useCreateFormFromTem.reset,
+ isCreating = _useCreateFormFromTem.isCreating,
+ hasError = _useCreateFormFromTem.hasError,
+ createApiError = _useCreateFormFromTem.formApiError;
+
+ var value = formId && formName ? {
+ label: formName,
+ value: formId
+ } : null;
+
+ var handleLocalChange = function handleLocalChange(option) {
+ if ((0,_constants_defaultFormOptions__WEBPACK_IMPORTED_MODULE_6__.isDefaultForm)(option.value)) {
+ createFormByTemplate(option.value).then(function (_ref2) {
+ var guid = _ref2.guid,
+ name = _ref2.name;
+ handleChange({
+ value: guid,
+ label: name
+ });
+ });
+ } else {
+ handleChange(option);
+ }
+ };
+
+ return isCreating ? (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_Common_LoadingBlock__WEBPACK_IMPORTED_MODULE_2__["default"], {}) : formApiError || createApiError ? (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_Common_ErrorHandler__WEBPACK_IMPORTED_MODULE_7__["default"], {
+ status: formApiError ? formApiError.status : createApiError.status,
+ resetErrorState: function resetErrorState() {
+ if (hasError) {
+ createReset();
+ } else {
+ reset();
+ }
+ },
+ errorInfo: {
+ header: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_3__.__)('There was a problem retrieving your forms', 'leadin'),
+ message: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_3__.__)('Please refresh your forms or try again in a few minutes', 'leadin'),
+ action: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_3__.__)('Refresh forms', 'leadin')
+ }
+ }) : (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_FormSelector__WEBPACK_IMPORTED_MODULE_1__["default"], {
+ loadOptions: search,
+ onChange: function onChange(option) {
+ return handleLocalChange(option);
+ },
+ value: value
+ });
+}
+
+/***/ }),
+
+/***/ "./scripts/shared/Form/FormSelector.tsx":
+/*!**********************************************!*\
+ !*** ./scripts/shared/Form/FormSelector.tsx ***!
+ \**********************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ FormSelector)
+/* harmony export */ });
+/* harmony import */ var react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react/jsx-runtime */ "./node_modules/react/jsx-runtime.js");
+/* harmony import */ var _Common_HubspotWrapper__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! ../Common/HubspotWrapper */ "./scripts/shared/Common/HubspotWrapper.ts");
+/* harmony import */ var _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ../../constants/leadinConfig */ "./scripts/constants/leadinConfig.ts");
+/* harmony import */ var _Common_AsyncSelect__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ../Common/AsyncSelect */ "./scripts/shared/Common/AsyncSelect.tsx");
+/* harmony import */ var _wordpress_i18n__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__(/*! @wordpress/i18n */ "@wordpress/i18n");
+/* harmony import */ var _wordpress_i18n__WEBPACK_IMPORTED_MODULE_4___default = /*#__PURE__*/__webpack_require__.n(_wordpress_i18n__WEBPACK_IMPORTED_MODULE_4__);
+
+
+
+
+
+function FormSelector(_ref) {
+ var loadOptions = _ref.loadOptions,
+ onChange = _ref.onChange,
+ value = _ref.value;
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsxs)(_Common_HubspotWrapper__WEBPACK_IMPORTED_MODULE_1__["default"], {
+ pluginPath: _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_2__.pluginPath,
+ children: [(0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)("p", {
+ "data-test-id": "leadin-form-select",
+ children: (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)("b", {
+ children: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_4__.__)('Select an existing form or create a new one from a template', 'leadin')
+ })
+ }), (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_Common_AsyncSelect__WEBPACK_IMPORTED_MODULE_3__["default"], {
+ placeholder: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_4__.__)('Search for a form', 'leadin'),
+ value: value,
+ loadOptions: loadOptions,
+ onChange: onChange
+ })]
+ });
+}
+
+/***/ }),
+
+/***/ "./scripts/shared/Form/PreviewForm.tsx":
+/*!*********************************************!*\
+ !*** ./scripts/shared/Form/PreviewForm.tsx ***!
+ \*********************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ PreviewForm)
+/* harmony export */ });
+/* harmony import */ var react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react/jsx-runtime */ "./node_modules/react/jsx-runtime.js");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! react */ "react");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(react__WEBPACK_IMPORTED_MODULE_1__);
+/* harmony import */ var _UIComponents_UIOverlay__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ../UIComponents/UIOverlay */ "./scripts/shared/UIComponents/UIOverlay.ts");
+/* harmony import */ var _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ../../constants/leadinConfig */ "./scripts/constants/leadinConfig.ts");
+/* harmony import */ var _hooks_useFormsScript__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__(/*! ./hooks/useFormsScript */ "./scripts/shared/Form/hooks/useFormsScript.ts");
+
+
+
+
+
+function PreviewForm(_ref) {
+ var portalId = _ref.portalId,
+ formId = _ref.formId;
+ var inputEl = (0,react__WEBPACK_IMPORTED_MODULE_1__.useRef)(null);
+ var ready = (0,_hooks_useFormsScript__WEBPACK_IMPORTED_MODULE_4__["default"])();
+ (0,react__WEBPACK_IMPORTED_MODULE_1__.useEffect)(function () {
+ if (!ready) {
+ return;
+ }
+
+ if (inputEl.current) {
+ inputEl.current.innerHTML = '';
+ var embedScript = document.createElement('script');
+ embedScript.innerHTML = "hbspt.forms.create({ portalId: '".concat(portalId, "', formId: '").concat(formId, "', region: '").concat(_constants_leadinConfig__WEBPACK_IMPORTED_MODULE_3__.hublet, "', ").concat(_constants_leadinConfig__WEBPACK_IMPORTED_MODULE_3__.formsScriptPayload, " });");
+ inputEl.current.appendChild(embedScript);
+ }
+ }, [formId, portalId, ready, inputEl]);
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_UIComponents_UIOverlay__WEBPACK_IMPORTED_MODULE_2__["default"], {
+ ref: inputEl
+ });
+}
+
+/***/ }),
+
+/***/ "./scripts/shared/Form/hooks/useCreateFormFromTemplate.ts":
+/*!****************************************************************!*\
+ !*** ./scripts/shared/Form/hooks/useCreateFormFromTemplate.ts ***!
+ \****************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ useCreateFormFromTemplate)
+/* harmony export */ });
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react */ "react");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(react__WEBPACK_IMPORTED_MODULE_0__);
+/* harmony import */ var _iframe_useBackgroundApp__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! ../../../iframe/useBackgroundApp */ "./scripts/iframe/useBackgroundApp.ts");
+/* harmony import */ var _enums_loadState__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ../../enums/loadState */ "./scripts/shared/enums/loadState.ts");
+/* harmony import */ var _iframe_integratedMessages__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ../../../iframe/integratedMessages */ "./scripts/iframe/integratedMessages/index.ts");
+function _slicedToArray(arr, i) { return _arrayWithHoles(arr) || _iterableToArrayLimit(arr, i) || _unsupportedIterableToArray(arr, i) || _nonIterableRest(); }
+
+function _nonIterableRest() { throw new TypeError("Invalid attempt to destructure non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method."); }
+
+function _unsupportedIterableToArray(o, minLen) { if (!o) return; if (typeof o === "string") return _arrayLikeToArray(o, minLen); var n = Object.prototype.toString.call(o).slice(8, -1); if (n === "Object" && o.constructor) n = o.constructor.name; if (n === "Map" || n === "Set") return Array.from(o); if (n === "Arguments" || /^(?:Ui|I)nt(?:8|16|32)(?:Clamped)?Array$/.test(n)) return _arrayLikeToArray(o, minLen); }
+
+function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len = arr.length; for (var i = 0, arr2 = new Array(len); i < len; i++) { arr2[i] = arr[i]; } return arr2; }
+
+function _iterableToArrayLimit(arr, i) { var _i = arr == null ? null : typeof Symbol !== "undefined" && arr[Symbol.iterator] || arr["@@iterator"]; if (_i == null) return; var _arr = []; var _n = true; var _d = false; var _s, _e; try { for (_i = _i.call(arr); !(_n = (_s = _i.next()).done); _n = true) { _arr.push(_s.value); if (i && _arr.length === i) break; } } catch (err) { _d = true; _e = err; } finally { try { if (!_n && _i["return"] != null) _i["return"](); } finally { if (_d) throw _e; } } return _arr; }
+
+function _arrayWithHoles(arr) { if (Array.isArray(arr)) return arr; }
+
+
+
+
+
+function useCreateFormFromTemplate() {
+ var origin = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : 'gutenberg';
+ var proxy = (0,_iframe_useBackgroundApp__WEBPACK_IMPORTED_MODULE_1__.usePostAsyncBackgroundMessage)();
+ var track = (0,_iframe_useBackgroundApp__WEBPACK_IMPORTED_MODULE_1__.usePostBackgroundMessage)();
+
+ var _useState = (0,react__WEBPACK_IMPORTED_MODULE_0__.useState)(_enums_loadState__WEBPACK_IMPORTED_MODULE_2__["default"].Idle),
+ _useState2 = _slicedToArray(_useState, 2),
+ loadState = _useState2[0],
+ setLoadState = _useState2[1];
+
+ var _useState3 = (0,react__WEBPACK_IMPORTED_MODULE_0__.useState)(null),
+ _useState4 = _slicedToArray(_useState3, 2),
+ formApiError = _useState4[0],
+ setFormApiError = _useState4[1];
+
+ var createFormByTemplate = function createFormByTemplate(type) {
+ setLoadState(_enums_loadState__WEBPACK_IMPORTED_MODULE_2__["default"].Loading);
+ track({
+ key: _iframe_integratedMessages__WEBPACK_IMPORTED_MODULE_3__.ProxyMessages.TrackFormCreatedFromTemplate,
+ payload: {
+ type: type,
+ origin: origin
+ }
+ });
+ return proxy({
+ key: _iframe_integratedMessages__WEBPACK_IMPORTED_MODULE_3__.ProxyMessages.CreateFormFromTemplate,
+ payload: type
+ }).then(function (form) {
+ setLoadState(_enums_loadState__WEBPACK_IMPORTED_MODULE_2__["default"].Idle);
+ return form;
+ })["catch"](function (err) {
+ setFormApiError(err);
+ track({
+ key: _iframe_integratedMessages__WEBPACK_IMPORTED_MODULE_3__.ProxyMessages.TrackFormCreationFailed,
+ payload: {
+ origin: origin
+ }
+ });
+ setLoadState(_enums_loadState__WEBPACK_IMPORTED_MODULE_2__["default"].Failed);
+ });
+ };
+
+ return {
+ isCreating: loadState === _enums_loadState__WEBPACK_IMPORTED_MODULE_2__["default"].Loading,
+ hasError: loadState === _enums_loadState__WEBPACK_IMPORTED_MODULE_2__["default"].Failed,
+ formApiError: formApiError,
+ createFormByTemplate: createFormByTemplate,
+ reset: function reset() {
+ return setLoadState(_enums_loadState__WEBPACK_IMPORTED_MODULE_2__["default"].Idle);
+ }
+ };
+}
+
+/***/ }),
+
+/***/ "./scripts/shared/Form/hooks/useForms.ts":
+/*!***********************************************!*\
+ !*** ./scripts/shared/Form/hooks/useForms.ts ***!
+ \***********************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ useForms)
+/* harmony export */ });
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react */ "react");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(react__WEBPACK_IMPORTED_MODULE_0__);
+/* harmony import */ var lodash_debounce__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! lodash/debounce */ "./node_modules/lodash/debounce.js");
+/* harmony import */ var lodash_debounce__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(lodash_debounce__WEBPACK_IMPORTED_MODULE_1__);
+/* harmony import */ var _iframe_useBackgroundApp__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ../../../iframe/useBackgroundApp */ "./scripts/iframe/useBackgroundApp.ts");
+/* harmony import */ var _constants_defaultFormOptions__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ../../../constants/defaultFormOptions */ "./scripts/constants/defaultFormOptions.ts");
+/* harmony import */ var _iframe_integratedMessages__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__(/*! ../../../iframe/integratedMessages */ "./scripts/iframe/integratedMessages/index.ts");
+function _toConsumableArray(arr) { return _arrayWithoutHoles(arr) || _iterableToArray(arr) || _unsupportedIterableToArray(arr) || _nonIterableSpread(); }
+
+function _nonIterableSpread() { throw new TypeError("Invalid attempt to spread non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method."); }
+
+function _iterableToArray(iter) { if (typeof Symbol !== "undefined" && iter[Symbol.iterator] != null || iter["@@iterator"] != null) return Array.from(iter); }
+
+function _arrayWithoutHoles(arr) { if (Array.isArray(arr)) return _arrayLikeToArray(arr); }
+
+function _slicedToArray(arr, i) { return _arrayWithHoles(arr) || _iterableToArrayLimit(arr, i) || _unsupportedIterableToArray(arr, i) || _nonIterableRest(); }
+
+function _nonIterableRest() { throw new TypeError("Invalid attempt to destructure non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method."); }
+
+function _unsupportedIterableToArray(o, minLen) { if (!o) return; if (typeof o === "string") return _arrayLikeToArray(o, minLen); var n = Object.prototype.toString.call(o).slice(8, -1); if (n === "Object" && o.constructor) n = o.constructor.name; if (n === "Map" || n === "Set") return Array.from(o); if (n === "Arguments" || /^(?:Ui|I)nt(?:8|16|32)(?:Clamped)?Array$/.test(n)) return _arrayLikeToArray(o, minLen); }
+
+function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len = arr.length; for (var i = 0, arr2 = new Array(len); i < len; i++) { arr2[i] = arr[i]; } return arr2; }
+
+function _iterableToArrayLimit(arr, i) { var _i = arr == null ? null : typeof Symbol !== "undefined" && arr[Symbol.iterator] || arr["@@iterator"]; if (_i == null) return; var _arr = []; var _n = true; var _d = false; var _s, _e; try { for (_i = _i.call(arr); !(_n = (_s = _i.next()).done); _n = true) { _arr.push(_s.value); if (i && _arr.length === i) break; } } catch (err) { _d = true; _e = err; } finally { try { if (!_n && _i["return"] != null) _i["return"](); } finally { if (_d) throw _e; } } return _arr; }
+
+function _arrayWithHoles(arr) { if (Array.isArray(arr)) return arr; }
+
+
+
+
+
+
+function useForms() {
+ var proxy = (0,_iframe_useBackgroundApp__WEBPACK_IMPORTED_MODULE_2__.usePostAsyncBackgroundMessage)();
+
+ var _useState = (0,react__WEBPACK_IMPORTED_MODULE_0__.useState)(null),
+ _useState2 = _slicedToArray(_useState, 2),
+ formApiError = _useState2[0],
+ setFormApiError = _useState2[1];
+
+ var search = lodash_debounce__WEBPACK_IMPORTED_MODULE_1___default()(function (search, callback) {
+ return proxy({
+ key: _iframe_integratedMessages__WEBPACK_IMPORTED_MODULE_4__.ProxyMessages.FetchForms,
+ payload: {
+ search: search
+ }
+ }).then(function (forms) {
+ callback([].concat(_toConsumableArray(forms.map(function (form) {
+ return {
+ label: form.name,
+ value: form.guid
+ };
+ })), [_constants_defaultFormOptions__WEBPACK_IMPORTED_MODULE_3__.DEFAULT_OPTIONS]));
+ })["catch"](function (error) {
+ setFormApiError(error);
+ });
+ }, 300, {
+ trailing: true
+ });
+ return {
+ search: search,
+ formApiError: formApiError,
+ reset: function reset() {
+ return setFormApiError(null);
+ }
+ };
+}
+
+/***/ }),
+
+/***/ "./scripts/shared/Form/hooks/useFormsScript.ts":
+/*!*****************************************************!*\
+ !*** ./scripts/shared/Form/hooks/useFormsScript.ts ***!
+ \*****************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ useFormScript)
+/* harmony export */ });
+/* harmony import */ var jquery__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! jquery */ "jquery");
+/* harmony import */ var jquery__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(jquery__WEBPACK_IMPORTED_MODULE_0__);
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! react */ "react");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(react__WEBPACK_IMPORTED_MODULE_1__);
+/* harmony import */ var _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ../../../constants/leadinConfig */ "./scripts/constants/leadinConfig.ts");
+/* harmony import */ var _lib_Raven__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ../../../lib/Raven */ "./scripts/lib/Raven.ts");
+function _slicedToArray(arr, i) { return _arrayWithHoles(arr) || _iterableToArrayLimit(arr, i) || _unsupportedIterableToArray(arr, i) || _nonIterableRest(); }
+
+function _nonIterableRest() { throw new TypeError("Invalid attempt to destructure non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method."); }
+
+function _unsupportedIterableToArray(o, minLen) { if (!o) return; if (typeof o === "string") return _arrayLikeToArray(o, minLen); var n = Object.prototype.toString.call(o).slice(8, -1); if (n === "Object" && o.constructor) n = o.constructor.name; if (n === "Map" || n === "Set") return Array.from(o); if (n === "Arguments" || /^(?:Ui|I)nt(?:8|16|32)(?:Clamped)?Array$/.test(n)) return _arrayLikeToArray(o, minLen); }
+
+function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len = arr.length; for (var i = 0, arr2 = new Array(len); i < len; i++) { arr2[i] = arr[i]; } return arr2; }
+
+function _iterableToArrayLimit(arr, i) { var _i = arr == null ? null : typeof Symbol !== "undefined" && arr[Symbol.iterator] || arr["@@iterator"]; if (_i == null) return; var _arr = []; var _n = true; var _d = false; var _s, _e; try { for (_i = _i.call(arr); !(_n = (_s = _i.next()).done); _n = true) { _arr.push(_s.value); if (i && _arr.length === i) break; } } catch (err) { _d = true; _e = err; } finally { try { if (!_n && _i["return"] != null) _i["return"](); } finally { if (_d) throw _e; } } return _arr; }
+
+function _arrayWithHoles(arr) { if (Array.isArray(arr)) return arr; }
+
+
+
+
+
+var promise;
+
+function loadFormsScript() {
+ if (!promise) {
+ promise = new Promise(function (resolve, reject) {
+ return jquery__WEBPACK_IMPORTED_MODULE_0___default().getScript(_constants_leadinConfig__WEBPACK_IMPORTED_MODULE_2__.formsScript).done(resolve).fail(reject);
+ });
+ }
+
+ return promise;
+}
+
+function useFormScript() {
+ var _useState = (0,react__WEBPACK_IMPORTED_MODULE_1__.useState)(false),
+ _useState2 = _slicedToArray(_useState, 2),
+ ready = _useState2[0],
+ setReady = _useState2[1];
+
+ (0,react__WEBPACK_IMPORTED_MODULE_1__.useEffect)(function () {
+ loadFormsScript().then(function () {
+ return setReady(true);
+ })["catch"](function (error) {
+ return _lib_Raven__WEBPACK_IMPORTED_MODULE_3__["default"].captureException(error);
+ });
+ }, []);
+ return ready;
+}
+
+/***/ }),
+
+/***/ "./scripts/shared/Meeting/MeetingController.tsx":
+/*!******************************************************!*\
+ !*** ./scripts/shared/Meeting/MeetingController.tsx ***!
+ \******************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ MeetingController)
+/* harmony export */ });
+/* harmony import */ var react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react/jsx-runtime */ "./node_modules/react/jsx-runtime.js");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! react */ "react");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(react__WEBPACK_IMPORTED_MODULE_1__);
+/* harmony import */ var _Common_LoadingBlock__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ../Common/LoadingBlock */ "./scripts/shared/Common/LoadingBlock.tsx");
+/* harmony import */ var _MeetingSelector__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ./MeetingSelector */ "./scripts/shared/Meeting/MeetingSelector.tsx");
+/* harmony import */ var _MeetingWarning__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__(/*! ./MeetingWarning */ "./scripts/shared/Meeting/MeetingWarning.tsx");
+/* harmony import */ var _hooks_useMeetings__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__(/*! ./hooks/useMeetings */ "./scripts/shared/Meeting/hooks/useMeetings.ts");
+/* harmony import */ var _Common_HubspotWrapper__WEBPACK_IMPORTED_MODULE_6__ = __webpack_require__(/*! ../Common/HubspotWrapper */ "./scripts/shared/Common/HubspotWrapper.ts");
+/* harmony import */ var _Common_ErrorHandler__WEBPACK_IMPORTED_MODULE_7__ = __webpack_require__(/*! ../Common/ErrorHandler */ "./scripts/shared/Common/ErrorHandler.tsx");
+/* harmony import */ var _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_8__ = __webpack_require__(/*! ../../constants/leadinConfig */ "./scripts/constants/leadinConfig.ts");
+/* harmony import */ var _wordpress_i18n__WEBPACK_IMPORTED_MODULE_9__ = __webpack_require__(/*! @wordpress/i18n */ "@wordpress/i18n");
+/* harmony import */ var _wordpress_i18n__WEBPACK_IMPORTED_MODULE_9___default = /*#__PURE__*/__webpack_require__.n(_wordpress_i18n__WEBPACK_IMPORTED_MODULE_9__);
+/* harmony import */ var raven_js__WEBPACK_IMPORTED_MODULE_10__ = __webpack_require__(/*! raven-js */ "./node_modules/raven-js/src/singleton.js");
+/* harmony import */ var raven_js__WEBPACK_IMPORTED_MODULE_10___default = /*#__PURE__*/__webpack_require__.n(raven_js__WEBPACK_IMPORTED_MODULE_10__);
+
+
+
+
+
+
+
+
+
+
+
+function MeetingController(_ref) {
+ var handleChange = _ref.handleChange,
+ url = _ref.url;
+
+ var _useMeetings = (0,_hooks_useMeetings__WEBPACK_IMPORTED_MODULE_5__["default"])(),
+ meetings = _useMeetings.mappedMeetings,
+ loading = _useMeetings.loading,
+ error = _useMeetings.error,
+ reload = _useMeetings.reload,
+ connectCalendar = _useMeetings.connectCalendar;
+
+ var selectedMeetingOption = (0,_hooks_useMeetings__WEBPACK_IMPORTED_MODULE_5__.useSelectedMeeting)(url);
+ var selectedMeetingCalendar = (0,_hooks_useMeetings__WEBPACK_IMPORTED_MODULE_5__.useSelectedMeetingCalendar)(url);
+ (0,react__WEBPACK_IMPORTED_MODULE_1__.useEffect)(function () {
+ if (!url && meetings.length > 0) {
+ handleChange(meetings[0].value);
+ }
+ }, [meetings, url, handleChange]);
+
+ var handleLocalChange = function handleLocalChange(option) {
+ handleChange(option.value);
+ };
+
+ var handleConnectCalendar = function handleConnectCalendar() {
+ return connectCalendar().then(function () {
+ reload();
+ })["catch"](function (error) {
+ raven_js__WEBPACK_IMPORTED_MODULE_10___default().captureMessage('Unable to connect calendar', {
+ extra: {
+ error: error
+ }
+ });
+ });
+ };
+
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(react__WEBPACK_IMPORTED_MODULE_1__.Fragment, {
+ children: loading ? (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_Common_LoadingBlock__WEBPACK_IMPORTED_MODULE_2__["default"], {}) : error ? (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_Common_ErrorHandler__WEBPACK_IMPORTED_MODULE_7__["default"], {
+ status: error && error.status || error,
+ resetErrorState: function resetErrorState() {
+ return reload();
+ },
+ errorInfo: {
+ header: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_9__.__)('There was a problem retrieving your meetings', 'leadin'),
+ message: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_9__.__)('Please refresh your meetings or try again in a few minutes', 'leadin'),
+ action: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_9__.__)('Refresh meetings', 'leadin')
+ }
+ }) : (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsxs)(_Common_HubspotWrapper__WEBPACK_IMPORTED_MODULE_6__["default"], {
+ padding: "90px 32px 24px",
+ pluginPath: _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_8__.pluginPath,
+ children: [selectedMeetingCalendar && (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_MeetingWarning__WEBPACK_IMPORTED_MODULE_4__["default"], {
+ status: selectedMeetingCalendar,
+ onConnectCalendar: handleConnectCalendar
+ }), meetings.length > 1 && (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_MeetingSelector__WEBPACK_IMPORTED_MODULE_3__["default"], {
+ onChange: handleLocalChange,
+ options: meetings,
+ value: selectedMeetingOption
+ })]
+ })
+ });
+}
+
+/***/ }),
+
+/***/ "./scripts/shared/Meeting/MeetingEdit.tsx":
+/*!************************************************!*\
+ !*** ./scripts/shared/Meeting/MeetingEdit.tsx ***!
+ \************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ MeetingsEditContainer)
+/* harmony export */ });
+/* harmony import */ var react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react/jsx-runtime */ "./node_modules/react/jsx-runtime.js");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! react */ "react");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(react__WEBPACK_IMPORTED_MODULE_1__);
+/* harmony import */ var _MeetingController__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ./MeetingController */ "./scripts/shared/Meeting/MeetingController.tsx");
+/* harmony import */ var _PreviewMeeting__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ./PreviewMeeting */ "./scripts/shared/Meeting/PreviewMeeting.tsx");
+/* harmony import */ var _iframe_useBackgroundApp__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__(/*! ../../iframe/useBackgroundApp */ "./scripts/iframe/useBackgroundApp.ts");
+/* harmony import */ var _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__(/*! ../../constants/leadinConfig */ "./scripts/constants/leadinConfig.ts");
+/* harmony import */ var _iframe_integratedMessages__WEBPACK_IMPORTED_MODULE_6__ = __webpack_require__(/*! ../../iframe/integratedMessages */ "./scripts/iframe/integratedMessages/index.ts");
+/* harmony import */ var _Common_LoadingBlock__WEBPACK_IMPORTED_MODULE_7__ = __webpack_require__(/*! ../Common/LoadingBlock */ "./scripts/shared/Common/LoadingBlock.tsx");
+/* harmony import */ var _utils_backgroundAppUtils__WEBPACK_IMPORTED_MODULE_8__ = __webpack_require__(/*! ../../utils/backgroundAppUtils */ "./scripts/utils/backgroundAppUtils.ts");
+function ownKeys(object, enumerableOnly) { var keys = Object.keys(object); if (Object.getOwnPropertySymbols) { var symbols = Object.getOwnPropertySymbols(object); enumerableOnly && (symbols = symbols.filter(function (sym) { return Object.getOwnPropertyDescriptor(object, sym).enumerable; })), keys.push.apply(keys, symbols); } return keys; }
+
+function _objectSpread(target) { for (var i = 1; i < arguments.length; i++) { var source = null != arguments[i] ? arguments[i] : {}; i % 2 ? ownKeys(Object(source), !0).forEach(function (key) { _defineProperty(target, key, source[key]); }) : Object.getOwnPropertyDescriptors ? Object.defineProperties(target, Object.getOwnPropertyDescriptors(source)) : ownKeys(Object(source)).forEach(function (key) { Object.defineProperty(target, key, Object.getOwnPropertyDescriptor(source, key)); }); } return target; }
+
+function _defineProperty(obj, key, value) { if (key in obj) { Object.defineProperty(obj, key, { value: value, enumerable: true, configurable: true, writable: true }); } else { obj[key] = value; } return obj; }
+
+
+
+
+
+
+
+
+
+
+
+function MeetingEdit(_ref) {
+ var url = _ref.attributes.url,
+ isSelected = _ref.isSelected,
+ setAttributes = _ref.setAttributes,
+ _ref$preview = _ref.preview,
+ preview = _ref$preview === void 0 ? true : _ref$preview,
+ _ref$origin = _ref.origin,
+ origin = _ref$origin === void 0 ? 'gutenberg' : _ref$origin;
+ var isBackgroundAppReady = (0,_iframe_useBackgroundApp__WEBPACK_IMPORTED_MODULE_4__.useBackgroundAppContext)();
+ var monitorFormPreviewRender = (0,_iframe_useBackgroundApp__WEBPACK_IMPORTED_MODULE_4__.usePostBackgroundMessage)();
+
+ var handleChange = function handleChange(newUrl) {
+ setAttributes({
+ url: newUrl
+ });
+ };
+
+ (0,react__WEBPACK_IMPORTED_MODULE_1__.useEffect)(function () {
+ monitorFormPreviewRender({
+ key: _iframe_integratedMessages__WEBPACK_IMPORTED_MODULE_6__.ProxyMessages.TrackMeetingPreviewRender,
+ payload: {
+ origin: origin
+ }
+ });
+ }, [origin]);
+ return !isBackgroundAppReady ? (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_Common_LoadingBlock__WEBPACK_IMPORTED_MODULE_7__["default"], {}) : (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsxs)(react__WEBPACK_IMPORTED_MODULE_1__.Fragment, {
+ children: [(isSelected || !url) && (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_MeetingController__WEBPACK_IMPORTED_MODULE_2__["default"], {
+ url: url,
+ handleChange: handleChange
+ }), preview && url && (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_PreviewMeeting__WEBPACK_IMPORTED_MODULE_3__["default"], {
+ url: url
+ })]
+ });
+}
+
+function MeetingsEditContainer(props) {
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_iframe_useBackgroundApp__WEBPACK_IMPORTED_MODULE_4__.BackgroudAppContext.Provider, {
+ value: _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_5__.refreshToken && (0,_utils_backgroundAppUtils__WEBPACK_IMPORTED_MODULE_8__.getOrCreateBackgroundApp)(_constants_leadinConfig__WEBPACK_IMPORTED_MODULE_5__.refreshToken),
+ children: (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(MeetingEdit, _objectSpread({}, props))
+ });
+}
+
+/***/ }),
+
+/***/ "./scripts/shared/Meeting/MeetingSelector.tsx":
+/*!****************************************************!*\
+ !*** ./scripts/shared/Meeting/MeetingSelector.tsx ***!
+ \****************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ MeetingSelector)
+/* harmony export */ });
+/* harmony import */ var react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react/jsx-runtime */ "./node_modules/react/jsx-runtime.js");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! react */ "react");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(react__WEBPACK_IMPORTED_MODULE_1__);
+/* harmony import */ var _Common_AsyncSelect__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ../Common/AsyncSelect */ "./scripts/shared/Common/AsyncSelect.tsx");
+/* harmony import */ var _UIComponents_UISpacer__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ../UIComponents/UISpacer */ "./scripts/shared/UIComponents/UISpacer.ts");
+/* harmony import */ var _wordpress_i18n__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__(/*! @wordpress/i18n */ "@wordpress/i18n");
+/* harmony import */ var _wordpress_i18n__WEBPACK_IMPORTED_MODULE_4___default = /*#__PURE__*/__webpack_require__.n(_wordpress_i18n__WEBPACK_IMPORTED_MODULE_4__);
+
+
+
+
+
+function MeetingSelector(_ref) {
+ var options = _ref.options,
+ onChange = _ref.onChange,
+ value = _ref.value;
+ var optionsWrapper = [{
+ label: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_4__.__)('Meeting name', 'leadin'),
+ options: options
+ }];
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsxs)(react__WEBPACK_IMPORTED_MODULE_1__.Fragment, {
+ children: [(0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_UIComponents_UISpacer__WEBPACK_IMPORTED_MODULE_3__["default"], {}), (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)("p", {
+ "data-test-id": "leadin-meeting-select",
+ children: (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)("b", {
+ children: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_4__.__)('Select a meeting scheduling page', 'leadin')
+ })
+ }), (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_Common_AsyncSelect__WEBPACK_IMPORTED_MODULE_2__["default"], {
+ defaultOptions: optionsWrapper,
+ onChange: onChange,
+ placeholder: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_4__.__)('Select a meeting', 'leadin'),
+ value: value
+ })]
+ });
+}
+
+/***/ }),
+
+/***/ "./scripts/shared/Meeting/MeetingWarning.tsx":
+/*!***************************************************!*\
+ !*** ./scripts/shared/Meeting/MeetingWarning.tsx ***!
+ \***************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ MeetingWarning)
+/* harmony export */ });
+/* harmony import */ var react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react/jsx-runtime */ "./node_modules/react/jsx-runtime.js");
+/* harmony import */ var _UIComponents_UIAlert__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! ../UIComponents/UIAlert */ "./scripts/shared/UIComponents/UIAlert.tsx");
+/* harmony import */ var _UIComponents_UIButton__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ../UIComponents/UIButton */ "./scripts/shared/UIComponents/UIButton.ts");
+/* harmony import */ var _constants__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ./constants */ "./scripts/shared/Meeting/constants.ts");
+/* harmony import */ var _wordpress_i18n__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__(/*! @wordpress/i18n */ "@wordpress/i18n");
+/* harmony import */ var _wordpress_i18n__WEBPACK_IMPORTED_MODULE_4___default = /*#__PURE__*/__webpack_require__.n(_wordpress_i18n__WEBPACK_IMPORTED_MODULE_4__);
+
+
+
+
+
+function MeetingWarning(_ref) {
+ var status = _ref.status,
+ onConnectCalendar = _ref.onConnectCalendar;
+ var isMeetingOwner = status === _constants__WEBPACK_IMPORTED_MODULE_3__.CURRENT_USER_CALENDAR_MISSING;
+ var titleText = isMeetingOwner ? (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_4__.__)('Your calendar is not connected', 'leadin') : (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_4__.__)('Calendar is not connected', 'leadin');
+ var titleMessage = isMeetingOwner ? (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_4__.__)('Please connect your calendar to activate your scheduling pages', 'leadin') : (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_4__.__)('Make sure that everybody in this meeting has connected their calendar from the Meetings page in HubSpot', 'leadin');
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_UIComponents_UIAlert__WEBPACK_IMPORTED_MODULE_1__["default"], {
+ titleText: titleText,
+ titleMessage: titleMessage,
+ children: isMeetingOwner && (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_UIComponents_UIButton__WEBPACK_IMPORTED_MODULE_2__["default"], {
+ use: "tertiary",
+ id: "meetings-connect-calendar",
+ onClick: onConnectCalendar,
+ children: (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_4__.__)('Connect calendar', 'leadin')
+ })
+ });
+}
+
+/***/ }),
+
+/***/ "./scripts/shared/Meeting/PreviewMeeting.tsx":
+/*!***************************************************!*\
+ !*** ./scripts/shared/Meeting/PreviewMeeting.tsx ***!
+ \***************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ PreviewForm)
+/* harmony export */ });
+/* harmony import */ var react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react/jsx-runtime */ "./node_modules/react/jsx-runtime.js");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! react */ "react");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(react__WEBPACK_IMPORTED_MODULE_1__);
+/* harmony import */ var _UIComponents_UIOverlay__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ../UIComponents/UIOverlay */ "./scripts/shared/UIComponents/UIOverlay.ts");
+/* harmony import */ var _hooks_useMeetingsScript__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ./hooks/useMeetingsScript */ "./scripts/shared/Meeting/hooks/useMeetingsScript.ts");
+
+
+
+
+function PreviewForm(_ref) {
+ var url = _ref.url;
+ var ready = (0,_hooks_useMeetingsScript__WEBPACK_IMPORTED_MODULE_3__["default"])();
+ var inputEl = (0,react__WEBPACK_IMPORTED_MODULE_1__.useRef)(null);
+ (0,react__WEBPACK_IMPORTED_MODULE_1__.useEffect)(function () {
+ if (!ready) {
+ return;
+ }
+
+ if (inputEl.current) {
+ inputEl.current.innerHTML = '';
+ var container = document.createElement('div');
+ container.dataset.src = "".concat(url, "?embed=true");
+ container.classList.add('meetings-iframe-container');
+ inputEl.current.appendChild(container);
+ var embedScript = document.createElement('script');
+ embedScript.innerHTML = 'hbspt.meetings.create(".meetings-iframe-container");';
+ inputEl.current.appendChild(embedScript);
+ }
+ }, [url, ready, inputEl]);
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(react__WEBPACK_IMPORTED_MODULE_1__.Fragment, {
+ children: url && (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(_UIComponents_UIOverlay__WEBPACK_IMPORTED_MODULE_2__["default"], {
+ ref: inputEl
+ })
+ });
+}
+
+/***/ }),
+
+/***/ "./scripts/shared/Meeting/constants.ts":
+/*!*********************************************!*\
+ !*** ./scripts/shared/Meeting/constants.ts ***!
+ \*********************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "CURRENT_USER_CALENDAR_MISSING": () => (/* binding */ CURRENT_USER_CALENDAR_MISSING),
+/* harmony export */ "OTHER_USER_CALENDAR_MISSING": () => (/* binding */ OTHER_USER_CALENDAR_MISSING)
+/* harmony export */ });
+var OTHER_USER_CALENDAR_MISSING = 'OTHER_USER_CALENDAR_MISSING';
+var CURRENT_USER_CALENDAR_MISSING = 'CURRENT_USER_CALENDAR_MISSING';
+
+/***/ }),
+
+/***/ "./scripts/shared/Meeting/hooks/useCurrentUserFetch.ts":
+/*!*************************************************************!*\
+ !*** ./scripts/shared/Meeting/hooks/useCurrentUserFetch.ts ***!
+ \*************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ useCurrentUserFetch)
+/* harmony export */ });
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react */ "react");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(react__WEBPACK_IMPORTED_MODULE_0__);
+/* harmony import */ var _iframe_useBackgroundApp__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! ../../../iframe/useBackgroundApp */ "./scripts/iframe/useBackgroundApp.ts");
+/* harmony import */ var _enums_loadState__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ../../enums/loadState */ "./scripts/shared/enums/loadState.ts");
+/* harmony import */ var _iframe_integratedMessages__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ../../../iframe/integratedMessages */ "./scripts/iframe/integratedMessages/index.ts");
+function _slicedToArray(arr, i) { return _arrayWithHoles(arr) || _iterableToArrayLimit(arr, i) || _unsupportedIterableToArray(arr, i) || _nonIterableRest(); }
+
+function _nonIterableRest() { throw new TypeError("Invalid attempt to destructure non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method."); }
+
+function _unsupportedIterableToArray(o, minLen) { if (!o) return; if (typeof o === "string") return _arrayLikeToArray(o, minLen); var n = Object.prototype.toString.call(o).slice(8, -1); if (n === "Object" && o.constructor) n = o.constructor.name; if (n === "Map" || n === "Set") return Array.from(o); if (n === "Arguments" || /^(?:Ui|I)nt(?:8|16|32)(?:Clamped)?Array$/.test(n)) return _arrayLikeToArray(o, minLen); }
+
+function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len = arr.length; for (var i = 0, arr2 = new Array(len); i < len; i++) { arr2[i] = arr[i]; } return arr2; }
+
+function _iterableToArrayLimit(arr, i) { var _i = arr == null ? null : typeof Symbol !== "undefined" && arr[Symbol.iterator] || arr["@@iterator"]; if (_i == null) return; var _arr = []; var _n = true; var _d = false; var _s, _e; try { for (_i = _i.call(arr); !(_n = (_s = _i.next()).done); _n = true) { _arr.push(_s.value); if (i && _arr.length === i) break; } } catch (err) { _d = true; _e = err; } finally { try { if (!_n && _i["return"] != null) _i["return"](); } finally { if (_d) throw _e; } } return _arr; }
+
+function _arrayWithHoles(arr) { if (Array.isArray(arr)) return arr; }
+
+
+
+
+
+var user = null;
+function useCurrentUserFetch() {
+ var proxy = (0,_iframe_useBackgroundApp__WEBPACK_IMPORTED_MODULE_1__.usePostAsyncBackgroundMessage)();
+
+ var _useState = (0,react__WEBPACK_IMPORTED_MODULE_0__.useState)(_enums_loadState__WEBPACK_IMPORTED_MODULE_2__["default"].NotLoaded),
+ _useState2 = _slicedToArray(_useState, 2),
+ loadState = _useState2[0],
+ setLoadState = _useState2[1];
+
+ var _useState3 = (0,react__WEBPACK_IMPORTED_MODULE_0__.useState)(null),
+ _useState4 = _slicedToArray(_useState3, 2),
+ error = _useState4[0],
+ setError = _useState4[1];
+
+ var createUser = function createUser() {
+ if (!user) {
+ setLoadState(_enums_loadState__WEBPACK_IMPORTED_MODULE_2__["default"].NotLoaded);
+ }
+ };
+
+ var reload = function reload() {
+ user = null;
+ setLoadState(_enums_loadState__WEBPACK_IMPORTED_MODULE_2__["default"].NotLoaded);
+ setError(null);
+ };
+
+ (0,react__WEBPACK_IMPORTED_MODULE_0__.useEffect)(function () {
+ if (loadState === _enums_loadState__WEBPACK_IMPORTED_MODULE_2__["default"].NotLoaded && !user) {
+ setLoadState(_enums_loadState__WEBPACK_IMPORTED_MODULE_2__["default"].Loading);
+ proxy({
+ key: _iframe_integratedMessages__WEBPACK_IMPORTED_MODULE_3__.ProxyMessages.FetchOrCreateMeetingUser
+ }).then(function (data) {
+ user = data;
+ setLoadState(_enums_loadState__WEBPACK_IMPORTED_MODULE_2__["default"].Idle);
+ })["catch"](function (err) {
+ setError(err);
+ setLoadState(_enums_loadState__WEBPACK_IMPORTED_MODULE_2__["default"].Failed);
+ });
+ }
+ }, [loadState]);
+ return {
+ user: user,
+ loadUserState: loadState,
+ error: error,
+ createUser: createUser,
+ reload: reload
+ };
+}
+
+/***/ }),
+
+/***/ "./scripts/shared/Meeting/hooks/useMeetings.ts":
+/*!*****************************************************!*\
+ !*** ./scripts/shared/Meeting/hooks/useMeetings.ts ***!
+ \*****************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ useMeetings),
+/* harmony export */ "useSelectedMeeting": () => (/* binding */ useSelectedMeeting),
+/* harmony export */ "useSelectedMeetingCalendar": () => (/* binding */ useSelectedMeetingCalendar)
+/* harmony export */ });
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react */ "react");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(react__WEBPACK_IMPORTED_MODULE_0__);
+/* harmony import */ var _wordpress_i18n__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! @wordpress/i18n */ "@wordpress/i18n");
+/* harmony import */ var _wordpress_i18n__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(_wordpress_i18n__WEBPACK_IMPORTED_MODULE_1__);
+/* harmony import */ var _constants__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ../constants */ "./scripts/shared/Meeting/constants.ts");
+/* harmony import */ var _useMeetingsFetch__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ./useMeetingsFetch */ "./scripts/shared/Meeting/hooks/useMeetingsFetch.ts");
+/* harmony import */ var _useCurrentUserFetch__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__(/*! ./useCurrentUserFetch */ "./scripts/shared/Meeting/hooks/useCurrentUserFetch.ts");
+/* harmony import */ var _enums_loadState__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__(/*! ../../enums/loadState */ "./scripts/shared/enums/loadState.ts");
+/* harmony import */ var _iframe_useBackgroundApp__WEBPACK_IMPORTED_MODULE_6__ = __webpack_require__(/*! ../../../iframe/useBackgroundApp */ "./scripts/iframe/useBackgroundApp.ts");
+/* harmony import */ var _iframe_integratedMessages__WEBPACK_IMPORTED_MODULE_7__ = __webpack_require__(/*! ../../../iframe/integratedMessages */ "./scripts/iframe/integratedMessages/index.ts");
+function ownKeys(object, enumerableOnly) { var keys = Object.keys(object); if (Object.getOwnPropertySymbols) { var symbols = Object.getOwnPropertySymbols(object); enumerableOnly && (symbols = symbols.filter(function (sym) { return Object.getOwnPropertyDescriptor(object, sym).enumerable; })), keys.push.apply(keys, symbols); } return keys; }
+
+function _objectSpread(target) { for (var i = 1; i < arguments.length; i++) { var source = null != arguments[i] ? arguments[i] : {}; i % 2 ? ownKeys(Object(source), !0).forEach(function (key) { _defineProperty(target, key, source[key]); }) : Object.getOwnPropertyDescriptors ? Object.defineProperties(target, Object.getOwnPropertyDescriptors(source)) : ownKeys(Object(source)).forEach(function (key) { Object.defineProperty(target, key, Object.getOwnPropertyDescriptor(source, key)); }); } return target; }
+
+function _defineProperty(obj, key, value) { if (key in obj) { Object.defineProperty(obj, key, { value: value, enumerable: true, configurable: true, writable: true }); } else { obj[key] = value; } return obj; }
+
+function _slicedToArray(arr, i) { return _arrayWithHoles(arr) || _iterableToArrayLimit(arr, i) || _unsupportedIterableToArray(arr, i) || _nonIterableRest(); }
+
+function _nonIterableRest() { throw new TypeError("Invalid attempt to destructure non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method."); }
+
+function _unsupportedIterableToArray(o, minLen) { if (!o) return; if (typeof o === "string") return _arrayLikeToArray(o, minLen); var n = Object.prototype.toString.call(o).slice(8, -1); if (n === "Object" && o.constructor) n = o.constructor.name; if (n === "Map" || n === "Set") return Array.from(o); if (n === "Arguments" || /^(?:Ui|I)nt(?:8|16|32)(?:Clamped)?Array$/.test(n)) return _arrayLikeToArray(o, minLen); }
+
+function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len = arr.length; for (var i = 0, arr2 = new Array(len); i < len; i++) { arr2[i] = arr[i]; } return arr2; }
+
+function _iterableToArrayLimit(arr, i) { var _i = arr == null ? null : typeof Symbol !== "undefined" && arr[Symbol.iterator] || arr["@@iterator"]; if (_i == null) return; var _arr = []; var _n = true; var _d = false; var _s, _e; try { for (_i = _i.call(arr); !(_n = (_s = _i.next()).done); _n = true) { _arr.push(_s.value); if (i && _arr.length === i) break; } } catch (err) { _d = true; _e = err; } finally { try { if (!_n && _i["return"] != null) _i["return"](); } finally { if (_d) throw _e; } } return _arr; }
+
+function _arrayWithHoles(arr) { if (Array.isArray(arr)) return arr; }
+
+
+
+
+
+
+
+
+
+
+function getDefaultMeetingName(meeting, currentUser, meetingUsers) {
+ var _meeting$meetingsUser = _slicedToArray(meeting.meetingsUserIds, 1),
+ meetingOwnerId = _meeting$meetingsUser[0];
+
+ var result = (0,_wordpress_i18n__WEBPACK_IMPORTED_MODULE_1__.__)('Default', 'leadin');
+
+ if (currentUser && meetingOwnerId !== currentUser.id && meetingUsers[meetingOwnerId]) {
+ var user = meetingUsers[meetingOwnerId];
+ result += " (".concat(user.userProfile.fullName, ")");
+ }
+
+ return result;
+}
+
+function hasCalendarObject(user) {
+ return user && user.meetingsUserBlob && user.meetingsUserBlob.calendarSettings && user.meetingsUserBlob.calendarSettings.email;
+}
+
+function useMeetings() {
+ var proxy = (0,_iframe_useBackgroundApp__WEBPACK_IMPORTED_MODULE_6__.usePostAsyncBackgroundMessage)();
+
+ var _useMeetingsFetch = (0,_useMeetingsFetch__WEBPACK_IMPORTED_MODULE_3__["default"])(),
+ meetings = _useMeetingsFetch.meetings,
+ meetingUsers = _useMeetingsFetch.meetingUsers,
+ meetingsError = _useMeetingsFetch.error,
+ loadMeetingsState = _useMeetingsFetch.loadMeetingsState,
+ reloadMeetings = _useMeetingsFetch.reload;
+
+ var _useCurrentUserFetch = (0,_useCurrentUserFetch__WEBPACK_IMPORTED_MODULE_4__["default"])(),
+ currentUser = _useCurrentUserFetch.user,
+ userError = _useCurrentUserFetch.error,
+ loadUserState = _useCurrentUserFetch.loadUserState,
+ reloadUser = _useCurrentUserFetch.reload;
+
+ var reload = (0,react__WEBPACK_IMPORTED_MODULE_0__.useCallback)(function () {
+ reloadUser();
+ reloadMeetings();
+ }, [reloadUser, reloadMeetings]);
+
+ var connectCalendar = function connectCalendar() {
+ return proxy({
+ key: _iframe_integratedMessages__WEBPACK_IMPORTED_MODULE_7__.ProxyMessages.ConnectMeetingsCalendar
+ });
+ };
+
+ return {
+ mappedMeetings: meetings.map(function (meet) {
+ return {
+ label: meet.name || getDefaultMeetingName(meet, currentUser, meetingUsers),
+ value: meet.link
+ };
+ }),
+ meetings: meetings,
+ meetingUsers: meetingUsers,
+ currentUser: currentUser,
+ error: meetingsError || userError,
+ loading: loadMeetingsState == _enums_loadState__WEBPACK_IMPORTED_MODULE_5__["default"].Loading || loadUserState === _enums_loadState__WEBPACK_IMPORTED_MODULE_5__["default"].Loading,
+ reload: reload,
+ connectCalendar: connectCalendar
+ };
+}
+function useSelectedMeeting(url) {
+ var _useMeetings = useMeetings(),
+ meetings = _useMeetings.mappedMeetings;
+
+ var option = meetings.find(function (_ref) {
+ var value = _ref.value;
+ return value === url;
+ });
+ return option;
+}
+function useSelectedMeetingCalendar(url) {
+ var _useMeetings2 = useMeetings(),
+ meetings = _useMeetings2.meetings,
+ meetingUsers = _useMeetings2.meetingUsers,
+ currentUser = _useMeetings2.currentUser;
+
+ var meeting = meetings.find(function (meet) {
+ return meet.link === url;
+ });
+ var mappedMeetingUsersId = meetingUsers.reduce(function (p, c) {
+ return _objectSpread(_objectSpread({}, p), {}, _defineProperty({}, c.id, c));
+ }, {});
+
+ if (!meeting) {
+ return null;
+ } else {
+ var meetingsUserIds = meeting.meetingsUserIds;
+
+ if (currentUser && meetingsUserIds.includes(currentUser.id) && !hasCalendarObject(currentUser)) {
+ return _constants__WEBPACK_IMPORTED_MODULE_2__.CURRENT_USER_CALENDAR_MISSING;
+ } else if (meetingsUserIds.map(function (id) {
+ return mappedMeetingUsersId[id];
+ }).some(function (user) {
+ return !hasCalendarObject(user);
+ })) {
+ return _constants__WEBPACK_IMPORTED_MODULE_2__.OTHER_USER_CALENDAR_MISSING;
+ } else {
+ return null;
+ }
+ }
+}
+
+/***/ }),
+
+/***/ "./scripts/shared/Meeting/hooks/useMeetingsFetch.ts":
+/*!**********************************************************!*\
+ !*** ./scripts/shared/Meeting/hooks/useMeetingsFetch.ts ***!
+ \**********************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ useMeetingsFetch)
+/* harmony export */ });
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react */ "react");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(react__WEBPACK_IMPORTED_MODULE_0__);
+/* harmony import */ var _iframe_useBackgroundApp__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! ../../../iframe/useBackgroundApp */ "./scripts/iframe/useBackgroundApp.ts");
+/* harmony import */ var _enums_loadState__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ../../enums/loadState */ "./scripts/shared/enums/loadState.ts");
+/* harmony import */ var _iframe_integratedMessages__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ../../../iframe/integratedMessages */ "./scripts/iframe/integratedMessages/index.ts");
+function _slicedToArray(arr, i) { return _arrayWithHoles(arr) || _iterableToArrayLimit(arr, i) || _unsupportedIterableToArray(arr, i) || _nonIterableRest(); }
+
+function _nonIterableRest() { throw new TypeError("Invalid attempt to destructure non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method."); }
+
+function _unsupportedIterableToArray(o, minLen) { if (!o) return; if (typeof o === "string") return _arrayLikeToArray(o, minLen); var n = Object.prototype.toString.call(o).slice(8, -1); if (n === "Object" && o.constructor) n = o.constructor.name; if (n === "Map" || n === "Set") return Array.from(o); if (n === "Arguments" || /^(?:Ui|I)nt(?:8|16|32)(?:Clamped)?Array$/.test(n)) return _arrayLikeToArray(o, minLen); }
+
+function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len = arr.length; for (var i = 0, arr2 = new Array(len); i < len; i++) { arr2[i] = arr[i]; } return arr2; }
+
+function _iterableToArrayLimit(arr, i) { var _i = arr == null ? null : typeof Symbol !== "undefined" && arr[Symbol.iterator] || arr["@@iterator"]; if (_i == null) return; var _arr = []; var _n = true; var _d = false; var _s, _e; try { for (_i = _i.call(arr); !(_n = (_s = _i.next()).done); _n = true) { _arr.push(_s.value); if (i && _arr.length === i) break; } } catch (err) { _d = true; _e = err; } finally { try { if (!_n && _i["return"] != null) _i["return"](); } finally { if (_d) throw _e; } } return _arr; }
+
+function _arrayWithHoles(arr) { if (Array.isArray(arr)) return arr; }
+
+
+
+
+
+var meetings = [];
+var meetingUsers = [];
+function useMeetingsFetch() {
+ var proxy = (0,_iframe_useBackgroundApp__WEBPACK_IMPORTED_MODULE_1__.usePostAsyncBackgroundMessage)();
+
+ var _useState = (0,react__WEBPACK_IMPORTED_MODULE_0__.useState)(_enums_loadState__WEBPACK_IMPORTED_MODULE_2__["default"].NotLoaded),
+ _useState2 = _slicedToArray(_useState, 2),
+ loadState = _useState2[0],
+ setLoadState = _useState2[1];
+
+ var _useState3 = (0,react__WEBPACK_IMPORTED_MODULE_0__.useState)(null),
+ _useState4 = _slicedToArray(_useState3, 2),
+ error = _useState4[0],
+ setError = _useState4[1];
+
+ var reload = function reload() {
+ meetings = [];
+ setError(null);
+ setLoadState(_enums_loadState__WEBPACK_IMPORTED_MODULE_2__["default"].NotLoaded);
+ };
+
+ (0,react__WEBPACK_IMPORTED_MODULE_0__.useEffect)(function () {
+ if (loadState === _enums_loadState__WEBPACK_IMPORTED_MODULE_2__["default"].NotLoaded && meetings.length === 0) {
+ setLoadState(_enums_loadState__WEBPACK_IMPORTED_MODULE_2__["default"].Loading);
+ proxy({
+ key: _iframe_integratedMessages__WEBPACK_IMPORTED_MODULE_3__.ProxyMessages.FetchMeetingsAndUsers
+ }).then(function (data) {
+ setLoadState(_enums_loadState__WEBPACK_IMPORTED_MODULE_2__["default"].Loaded);
+ meetings = data && data.meetingLinks;
+ meetingUsers = data && data.meetingUsers;
+ })["catch"](function (e) {
+ setError(e);
+ setLoadState(_enums_loadState__WEBPACK_IMPORTED_MODULE_2__["default"].Failed);
+ });
+ }
+ }, [loadState]);
+ return {
+ meetings: meetings,
+ meetingUsers: meetingUsers,
+ loadMeetingsState: loadState,
+ error: error,
+ reload: reload
+ };
+}
+
+/***/ }),
+
+/***/ "./scripts/shared/Meeting/hooks/useMeetingsScript.ts":
+/*!***********************************************************!*\
+ !*** ./scripts/shared/Meeting/hooks/useMeetingsScript.ts ***!
+ \***********************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ useMeetingsScript)
+/* harmony export */ });
+/* harmony import */ var jquery__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! jquery */ "jquery");
+/* harmony import */ var jquery__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(jquery__WEBPACK_IMPORTED_MODULE_0__);
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! react */ "react");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(react__WEBPACK_IMPORTED_MODULE_1__);
+/* harmony import */ var _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ../../../constants/leadinConfig */ "./scripts/constants/leadinConfig.ts");
+/* harmony import */ var _lib_Raven__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ../../../lib/Raven */ "./scripts/lib/Raven.ts");
+function _slicedToArray(arr, i) { return _arrayWithHoles(arr) || _iterableToArrayLimit(arr, i) || _unsupportedIterableToArray(arr, i) || _nonIterableRest(); }
+
+function _nonIterableRest() { throw new TypeError("Invalid attempt to destructure non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method."); }
+
+function _unsupportedIterableToArray(o, minLen) { if (!o) return; if (typeof o === "string") return _arrayLikeToArray(o, minLen); var n = Object.prototype.toString.call(o).slice(8, -1); if (n === "Object" && o.constructor) n = o.constructor.name; if (n === "Map" || n === "Set") return Array.from(o); if (n === "Arguments" || /^(?:Ui|I)nt(?:8|16|32)(?:Clamped)?Array$/.test(n)) return _arrayLikeToArray(o, minLen); }
+
+function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len = arr.length; for (var i = 0, arr2 = new Array(len); i < len; i++) { arr2[i] = arr[i]; } return arr2; }
+
+function _iterableToArrayLimit(arr, i) { var _i = arr == null ? null : typeof Symbol !== "undefined" && arr[Symbol.iterator] || arr["@@iterator"]; if (_i == null) return; var _arr = []; var _n = true; var _d = false; var _s, _e; try { for (_i = _i.call(arr); !(_n = (_s = _i.next()).done); _n = true) { _arr.push(_s.value); if (i && _arr.length === i) break; } } catch (err) { _d = true; _e = err; } finally { try { if (!_n && _i["return"] != null) _i["return"](); } finally { if (_d) throw _e; } } return _arr; }
+
+function _arrayWithHoles(arr) { if (Array.isArray(arr)) return arr; }
+
+
+
+
+
+var promise;
+
+function loadMeetingsScript() {
+ if (!promise) {
+ promise = new Promise(function (resolve, reject) {
+ return jquery__WEBPACK_IMPORTED_MODULE_0___default().getScript(_constants_leadinConfig__WEBPACK_IMPORTED_MODULE_2__.meetingsScript).done(resolve).fail(reject);
+ });
+ }
+
+ return promise;
+}
+
+function useMeetingsScript() {
+ var _useState = (0,react__WEBPACK_IMPORTED_MODULE_1__.useState)(false),
+ _useState2 = _slicedToArray(_useState, 2),
+ ready = _useState2[0],
+ setReady = _useState2[1];
+
+ (0,react__WEBPACK_IMPORTED_MODULE_1__.useEffect)(function () {
+ loadMeetingsScript().then(function () {
+ return setReady(true);
+ })["catch"](function (error) {
+ return _lib_Raven__WEBPACK_IMPORTED_MODULE_3__["default"].captureException(error);
+ });
+ }, []);
+ return ready;
+}
+
+/***/ }),
+
+/***/ "./scripts/shared/UIComponents/UIAlert.tsx":
+/*!*************************************************!*\
+ !*** ./scripts/shared/UIComponents/UIAlert.tsx ***!
+ \*************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ UIAlert)
+/* harmony export */ });
+/* harmony import */ var react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react/jsx-runtime */ "./node_modules/react/jsx-runtime.js");
+/* harmony import */ var _linaria_react__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! @linaria/react */ "./node_modules/@linaria/react/dist/index.mjs");
+
+
+var AlertContainer = /*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_1__.styled)('div')({
+ name: "AlertContainer",
+ "class": "a1h8m4fo",
+ propsAsIs: false
+});
+var Title = /*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_1__.styled)('p')({
+ name: "Title",
+ "class": "tyndzxk",
+ propsAsIs: false
+});
+var Message = /*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_1__.styled)('p')({
+ name: "Message",
+ "class": "m1m9sbk4",
+ propsAsIs: false
+});
+var MessageContainer = /*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_1__.styled)('div')({
+ name: "MessageContainer",
+ "class": "mg5o421",
+ propsAsIs: false
+});
+function UIAlert(_ref) {
+ var titleText = _ref.titleText,
+ titleMessage = _ref.titleMessage,
+ children = _ref.children;
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsxs)(AlertContainer, {
+ children: [(0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsxs)(MessageContainer, {
+ children: [(0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(Title, {
+ children: titleText
+ }), (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(Message, {
+ children: titleMessage
+ })]
+ }), children]
+ });
+}
+
+__webpack_require__(/*! ./UIAlert.linaria.css!=!../../../node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./UIAlert.tsx */ "./scripts/shared/UIComponents/UIAlert.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/UIComponents/UIAlert.tsx");
+
+/***/ }),
+
+/***/ "./scripts/shared/UIComponents/UIButton.ts":
+/*!*************************************************!*\
+ !*** ./scripts/shared/UIComponents/UIButton.ts ***!
+ \*************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (__WEBPACK_DEFAULT_EXPORT__)
+/* harmony export */ });
+/* harmony import */ var _linaria_react__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! @linaria/react */ "./node_modules/@linaria/react/dist/index.mjs");
+/* harmony import */ var _colors__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! ./colors */ "./scripts/shared/UIComponents/colors.ts");
+
+
+
+var _exp2 = /*#__PURE__*/function _exp2() {
+ return function (props) {
+ return props.use === 'tertiary' ? _colors__WEBPACK_IMPORTED_MODULE_0__.HEFFALUMP : _colors__WEBPACK_IMPORTED_MODULE_0__.LORAX;
+ };
+};
+
+/* harmony default export */ const __WEBPACK_DEFAULT_EXPORT__ = (/*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_1__.styled)('button')({
+ name: "UIButton0",
+ "class": "ug152ch",
+ propsAsIs: false,
+ vars: {
+ "ug152ch-0": [_exp2()]
+ }
+}));
+
+__webpack_require__(/*! ./UIButton.linaria.css!=!../../../node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./UIButton.ts */ "./scripts/shared/UIComponents/UIButton.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/UIComponents/UIButton.ts");
+
+/***/ }),
+
+/***/ "./scripts/shared/UIComponents/UIContainer.ts":
+/*!****************************************************!*\
+ !*** ./scripts/shared/UIComponents/UIContainer.ts ***!
+ \****************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (__WEBPACK_DEFAULT_EXPORT__)
+/* harmony export */ });
+/* harmony import */ var _linaria_react__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! @linaria/react */ "./node_modules/@linaria/react/dist/index.mjs");
+
+
+var _exp = /*#__PURE__*/function _exp() {
+ return function (props) {
+ return props.textAlign ? props.textAlign : 'inherit';
+ };
+};
+
+/* harmony default export */ const __WEBPACK_DEFAULT_EXPORT__ = (/*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_0__.styled)('div')({
+ name: "UIContainer0",
+ "class": "ua13n1c",
+ propsAsIs: false,
+ vars: {
+ "ua13n1c-0": [_exp()]
+ }
+}));
+
+__webpack_require__(/*! ./UIContainer.linaria.css!=!../../../node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./UIContainer.ts */ "./scripts/shared/UIComponents/UIContainer.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/UIComponents/UIContainer.ts");
+
+/***/ }),
+
+/***/ "./scripts/shared/UIComponents/UIOverlay.ts":
+/*!**************************************************!*\
+ !*** ./scripts/shared/UIComponents/UIOverlay.ts ***!
+ \**************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (__WEBPACK_DEFAULT_EXPORT__)
+/* harmony export */ });
+/* harmony import */ var _linaria_react__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! @linaria/react */ "./node_modules/@linaria/react/dist/index.mjs");
+
+/* harmony default export */ const __WEBPACK_DEFAULT_EXPORT__ = (/*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_0__.styled)('div')({
+ name: "UIOverlay0",
+ "class": "u1q7a48k",
+ propsAsIs: false
+}));
+
+__webpack_require__(/*! ./UIOverlay.linaria.css!=!../../../node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./UIOverlay.ts */ "./scripts/shared/UIComponents/UIOverlay.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/UIComponents/UIOverlay.ts");
+
+/***/ }),
+
+/***/ "./scripts/shared/UIComponents/UISpacer.ts":
+/*!*************************************************!*\
+ !*** ./scripts/shared/UIComponents/UISpacer.ts ***!
+ \*************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (__WEBPACK_DEFAULT_EXPORT__)
+/* harmony export */ });
+/* harmony import */ var _linaria_react__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! @linaria/react */ "./node_modules/@linaria/react/dist/index.mjs");
+
+/* harmony default export */ const __WEBPACK_DEFAULT_EXPORT__ = (/*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_0__.styled)('div')({
+ name: "UISpacer0",
+ "class": "u3qxofx",
+ propsAsIs: false
+}));
+
+__webpack_require__(/*! ./UISpacer.linaria.css!=!../../../node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./UISpacer.ts */ "./scripts/shared/UIComponents/UISpacer.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/UIComponents/UISpacer.ts");
+
+/***/ }),
+
+/***/ "./scripts/shared/UIComponents/UISpinner.tsx":
+/*!***************************************************!*\
+ !*** ./scripts/shared/UIComponents/UISpinner.tsx ***!
+ \***************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (/* binding */ UISpinner)
+/* harmony export */ });
+/* harmony import */ var react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! react/jsx-runtime */ "./node_modules/react/jsx-runtime.js");
+/* harmony import */ var _linaria_react__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! @linaria/react */ "./node_modules/@linaria/react/dist/index.mjs");
+/* harmony import */ var _colors__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! ./colors */ "./scripts/shared/UIComponents/colors.ts");
+
+
+
+var SpinnerOuter = /*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_2__.styled)('div')({
+ name: "SpinnerOuter",
+ "class": "sxa9zrc",
+ propsAsIs: false
+});
+var SpinnerInner = /*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_2__.styled)('div')({
+ name: "SpinnerInner",
+ "class": "s14430wa",
+ propsAsIs: false
+});
+
+var _exp = /*#__PURE__*/function _exp() {
+ return function (props) {
+ return props.color;
+ };
+};
+
+var Circle = /*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_2__.styled)('circle')({
+ name: "Circle",
+ "class": "ct87ghk",
+ propsAsIs: true,
+ vars: {
+ "ct87ghk-0": [_exp()]
+ }
+});
+
+var _exp2 = /*#__PURE__*/function _exp2() {
+ return function (props) {
+ return props.color;
+ };
+};
+
+var AnimatedCircle = /*#__PURE__*/(0,_linaria_react__WEBPACK_IMPORTED_MODULE_2__.styled)('circle')({
+ name: "AnimatedCircle",
+ "class": "avili0h",
+ propsAsIs: true,
+ vars: {
+ "avili0h-0": [_exp2()]
+ }
+});
+function UISpinner(_ref) {
+ var _ref$size = _ref.size,
+ size = _ref$size === void 0 ? 20 : _ref$size;
+ return (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(SpinnerOuter, {
+ children: (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(SpinnerInner, {
+ children: (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsxs)("svg", {
+ height: size,
+ width: size,
+ viewBox: "0 0 50 50",
+ children: [(0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(Circle, {
+ color: _colors__WEBPACK_IMPORTED_MODULE_1__.CALYPSO_MEDIUM,
+ cx: "25",
+ cy: "25",
+ r: "22.5"
+ }), (0,react_jsx_runtime__WEBPACK_IMPORTED_MODULE_0__.jsx)(AnimatedCircle, {
+ color: _colors__WEBPACK_IMPORTED_MODULE_1__.CALYPSO,
+ cx: "25",
+ cy: "25",
+ r: "22.5"
+ })]
+ })
+ })
+ });
+}
+
+__webpack_require__(/*! ./UISpinner.linaria.css!=!../../../node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./UISpinner.tsx */ "./scripts/shared/UIComponents/UISpinner.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/UIComponents/UISpinner.tsx");
+
+/***/ }),
+
+/***/ "./scripts/shared/UIComponents/colors.ts":
+/*!***********************************************!*\
+ !*** ./scripts/shared/UIComponents/colors.ts ***!
+ \***********************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "CALYPSO": () => (/* binding */ CALYPSO),
+/* harmony export */ "CALYPSO_LIGHT": () => (/* binding */ CALYPSO_LIGHT),
+/* harmony export */ "CALYPSO_MEDIUM": () => (/* binding */ CALYPSO_MEDIUM),
+/* harmony export */ "HEFFALUMP": () => (/* binding */ HEFFALUMP),
+/* harmony export */ "LORAX": () => (/* binding */ LORAX),
+/* harmony export */ "MARIGOLD_LIGHT": () => (/* binding */ MARIGOLD_LIGHT),
+/* harmony export */ "MARIGOLD_MEDIUM": () => (/* binding */ MARIGOLD_MEDIUM),
+/* harmony export */ "OBSIDIAN": () => (/* binding */ OBSIDIAN),
+/* harmony export */ "OLAF": () => (/* binding */ OLAF)
+/* harmony export */ });
+var CALYPSO = '#00a4bd';
+var CALYPSO_MEDIUM = '#7fd1de';
+var CALYPSO_LIGHT = '#e5f5f8';
+var LORAX = '#ff7a59';
+var OLAF = '#ffffff';
+var HEFFALUMP = '#425b76';
+var MARIGOLD_LIGHT = '#fef8f0';
+var MARIGOLD_MEDIUM = '#fae0b5';
+var OBSIDIAN = '#33475b';
+
+/***/ }),
+
+/***/ "./scripts/shared/enums/connectionStatus.ts":
+/*!**************************************************!*\
+ !*** ./scripts/shared/enums/connectionStatus.ts ***!
+ \**************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (__WEBPACK_DEFAULT_EXPORT__)
+/* harmony export */ });
+var ConnectionStatus = {
+ Connected: 'Connected',
+ NotConnected: 'NotConnected'
+};
+/* harmony default export */ const __WEBPACK_DEFAULT_EXPORT__ = (ConnectionStatus);
+
+/***/ }),
+
+/***/ "./scripts/shared/enums/loadState.ts":
+/*!*******************************************!*\
+ !*** ./scripts/shared/enums/loadState.ts ***!
+ \*******************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (__WEBPACK_DEFAULT_EXPORT__)
+/* harmony export */ });
+var LoadState = {
+ NotLoaded: 'NotLoaded',
+ Loading: 'Loading',
+ Loaded: 'Loaded',
+ Idle: 'Idle',
+ Failed: 'Failed'
+};
+/* harmony default export */ const __WEBPACK_DEFAULT_EXPORT__ = (LoadState);
+
+/***/ }),
+
+/***/ "./scripts/utils/appUtils.ts":
+/*!***********************************!*\
+ !*** ./scripts/utils/appUtils.ts ***!
+ \***********************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "initApp": () => (/* binding */ initApp),
+/* harmony export */ "initAppOnReady": () => (/* binding */ initAppOnReady)
+/* harmony export */ });
+/* harmony import */ var jquery__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! jquery */ "jquery");
+/* harmony import */ var jquery__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(jquery__WEBPACK_IMPORTED_MODULE_0__);
+/* harmony import */ var _lib_Raven__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! ../lib/Raven */ "./scripts/lib/Raven.ts");
+
+
+function initApp(initFn) {
+ (0,_lib_Raven__WEBPACK_IMPORTED_MODULE_1__.configureRaven)();
+ _lib_Raven__WEBPACK_IMPORTED_MODULE_1__["default"].context(initFn);
+}
+function initAppOnReady(initFn) {
+ function main() {
+ jquery__WEBPACK_IMPORTED_MODULE_0___default()(initFn);
+ }
+
+ initApp(main);
+}
+
+/***/ }),
+
+/***/ "./scripts/utils/backgroundAppUtils.ts":
+/*!*********************************************!*\
+ !*** ./scripts/utils/backgroundAppUtils.ts ***!
+ \*********************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "getOrCreateBackgroundApp": () => (/* binding */ getOrCreateBackgroundApp),
+/* harmony export */ "initBackgroundApp": () => (/* binding */ initBackgroundApp)
+/* harmony export */ });
+/* harmony import */ var _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! ../constants/leadinConfig */ "./scripts/constants/leadinConfig.ts");
+/* harmony import */ var _appUtils__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! ./appUtils */ "./scripts/utils/appUtils.ts");
+
+
+function initBackgroundApp(initFn) {
+ function main() {
+ if (Array.isArray(initFn)) {
+ initFn.forEach(function (callback) {
+ return callback();
+ });
+ } else {
+ initFn();
+ }
+ }
+
+ (0,_appUtils__WEBPACK_IMPORTED_MODULE_1__.initApp)(main);
+}
+var getOrCreateBackgroundApp = function getOrCreateBackgroundApp(refreshToken) {
+ if (window.LeadinBackgroundApp) {
+ return window.LeadinBackgroundApp;
+ }
+
+ var _window = window,
+ IntegratedAppEmbedder = _window.IntegratedAppEmbedder,
+ IntegratedAppOptions = _window.IntegratedAppOptions;
+ var options = new IntegratedAppOptions().setLocale(_constants_leadinConfig__WEBPACK_IMPORTED_MODULE_0__.locale).setDeviceId(_constants_leadinConfig__WEBPACK_IMPORTED_MODULE_0__.deviceId).setRefreshToken(refreshToken);
+ var embedder = new IntegratedAppEmbedder('integrated-plugin-proxy', _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_0__.portalId, _constants_leadinConfig__WEBPACK_IMPORTED_MODULE_0__.hubspotBaseUrl, function () {}).setOptions(options);
+ embedder.attachTo(document.body, false);
+ embedder.postStartAppMessage(); // lets the app know all all data has been passed to it
+
+ window.LeadinBackgroundApp = embedder;
+ return window.LeadinBackgroundApp;
+};
+
+/***/ }),
+
+/***/ "./scripts/utils/withMetaData.ts":
+/*!***************************************!*\
+ !*** ./scripts/utils/withMetaData.ts ***!
+ \***************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (__WEBPACK_DEFAULT_EXPORT__),
+/* harmony export */ "isFullSiteEditor": () => (/* binding */ isFullSiteEditor)
+/* harmony export */ });
+/* harmony import */ var _wordpress_data__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! @wordpress/data */ "@wordpress/data");
+/* harmony import */ var _wordpress_data__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(_wordpress_data__WEBPACK_IMPORTED_MODULE_0__);
+function _defineProperty(obj, key, value) { if (key in obj) { Object.defineProperty(obj, key, { value: value, enumerable: true, configurable: true, writable: true }); } else { obj[key] = value; } return obj; }
+
+ // from answer here: https://github.com/WordPress/gutenberg/issues/44477#issuecomment-1263026599
+
+var isFullSiteEditor = function isFullSiteEditor() {
+ return _wordpress_data__WEBPACK_IMPORTED_MODULE_0__.select && !!(0,_wordpress_data__WEBPACK_IMPORTED_MODULE_0__.select)('core/edit-site');
+};
+var applyWithSelect = (0,_wordpress_data__WEBPACK_IMPORTED_MODULE_0__.withSelect)(function (select, props) {
+ return {
+ metaValue: select('core/editor').getEditedPostAttribute('meta')[props.metaKey]
+ };
+});
+var applyWithDispatch = (0,_wordpress_data__WEBPACK_IMPORTED_MODULE_0__.withDispatch)(function (dispatch, props) {
+ return {
+ setMetaValue: function setMetaValue(value) {
+ dispatch('core/editor').editPost({
+ meta: _defineProperty({}, props.metaKey, value)
+ });
+ }
+ };
+});
+
+function apply(el) {
+ return applyWithSelect(applyWithDispatch(el));
+}
+
+/* harmony default export */ const __WEBPACK_DEFAULT_EXPORT__ = (apply);
+
+/***/ }),
+
+/***/ "./node_modules/is-what/dist/index.esm.js":
+/*!************************************************!*\
+ !*** ./node_modules/is-what/dist/index.esm.js ***!
+ \************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "getType": () => (/* binding */ getType),
+/* harmony export */ "isAnyObject": () => (/* binding */ isAnyObject),
+/* harmony export */ "isArray": () => (/* binding */ isArray),
+/* harmony export */ "isBlob": () => (/* binding */ isBlob),
+/* harmony export */ "isBoolean": () => (/* binding */ isBoolean),
+/* harmony export */ "isDate": () => (/* binding */ isDate),
+/* harmony export */ "isEmptyArray": () => (/* binding */ isEmptyArray),
+/* harmony export */ "isEmptyObject": () => (/* binding */ isEmptyObject),
+/* harmony export */ "isEmptyString": () => (/* binding */ isEmptyString),
+/* harmony export */ "isError": () => (/* binding */ isError),
+/* harmony export */ "isFile": () => (/* binding */ isFile),
+/* harmony export */ "isFullArray": () => (/* binding */ isFullArray),
+/* harmony export */ "isFullObject": () => (/* binding */ isFullObject),
+/* harmony export */ "isFullString": () => (/* binding */ isFullString),
+/* harmony export */ "isFunction": () => (/* binding */ isFunction),
+/* harmony export */ "isMap": () => (/* binding */ isMap),
+/* harmony export */ "isNaNValue": () => (/* binding */ isNaNValue),
+/* harmony export */ "isNull": () => (/* binding */ isNull),
+/* harmony export */ "isNullOrUndefined": () => (/* binding */ isNullOrUndefined),
+/* harmony export */ "isNumber": () => (/* binding */ isNumber),
+/* harmony export */ "isObject": () => (/* binding */ isObject),
+/* harmony export */ "isObjectLike": () => (/* binding */ isObjectLike),
+/* harmony export */ "isOneOf": () => (/* binding */ isOneOf),
+/* harmony export */ "isPlainObject": () => (/* binding */ isPlainObject),
+/* harmony export */ "isPrimitive": () => (/* binding */ isPrimitive),
+/* harmony export */ "isPromise": () => (/* binding */ isPromise),
+/* harmony export */ "isRegExp": () => (/* binding */ isRegExp),
+/* harmony export */ "isSet": () => (/* binding */ isSet),
+/* harmony export */ "isString": () => (/* binding */ isString),
+/* harmony export */ "isSymbol": () => (/* binding */ isSymbol),
+/* harmony export */ "isType": () => (/* binding */ isType),
+/* harmony export */ "isUndefined": () => (/* binding */ isUndefined),
+/* harmony export */ "isWeakMap": () => (/* binding */ isWeakMap),
+/* harmony export */ "isWeakSet": () => (/* binding */ isWeakSet)
+/* harmony export */ });
+/**
+ * Returns the object type of the given payload
+ *
+ * @param {*} payload
+ * @returns {string}
+ */
+function getType(payload) {
+ return Object.prototype.toString.call(payload).slice(8, -1);
+}
+/**
+ * Returns whether the payload is undefined
+ *
+ * @param {*} payload
+ * @returns {payload is undefined}
+ */
+function isUndefined(payload) {
+ return getType(payload) === 'Undefined';
+}
+/**
+ * Returns whether the payload is null
+ *
+ * @param {*} payload
+ * @returns {payload is null}
+ */
+function isNull(payload) {
+ return getType(payload) === 'Null';
+}
+/**
+ * Returns whether the payload is a plain JavaScript object (excluding special classes or objects with other prototypes)
+ *
+ * @param {*} payload
+ * @returns {payload is PlainObject}
+ */
+function isPlainObject(payload) {
+ if (getType(payload) !== 'Object')
+ return false;
+ return payload.constructor === Object && Object.getPrototypeOf(payload) === Object.prototype;
+}
+/**
+ * Returns whether the payload is a plain JavaScript object (excluding special classes or objects with other prototypes)
+ *
+ * @param {*} payload
+ * @returns {payload is PlainObject}
+ */
+function isObject(payload) {
+ return isPlainObject(payload);
+}
+/**
+ * Returns whether the payload is a an empty object (excluding special classes or objects with other prototypes)
+ *
+ * @param {*} payload
+ * @returns {payload is { [K in any]: never }}
+ */
+function isEmptyObject(payload) {
+ return isPlainObject(payload) && Object.keys(payload).length === 0;
+}
+/**
+ * Returns whether the payload is a an empty object (excluding special classes or objects with other prototypes)
+ *
+ * @param {*} payload
+ * @returns {payload is PlainObject}
+ */
+function isFullObject(payload) {
+ return isPlainObject(payload) && Object.keys(payload).length > 0;
+}
+/**
+ * Returns whether the payload is an any kind of object (including special classes or objects with different prototypes)
+ *
+ * @param {*} payload
+ * @returns {payload is PlainObject}
+ */
+function isAnyObject(payload) {
+ return getType(payload) === 'Object';
+}
+/**
+ * Returns whether the payload is an object like a type passed in < >
+ *
+ * Usage: isObjectLike<{id: any}>(payload) // will make sure it's an object and has an `id` prop.
+ *
+ * @template T this must be passed in < >
+ * @param {*} payload
+ * @returns {payload is T}
+ */
+function isObjectLike(payload) {
+ return isAnyObject(payload);
+}
+/**
+ * Returns whether the payload is a function (regular or async)
+ *
+ * @param {*} payload
+ * @returns {payload is AnyFunction}
+ */
+function isFunction(payload) {
+ return typeof payload === 'function';
+}
+/**
+ * Returns whether the payload is an array
+ *
+ * @param {any} payload
+ * @returns {payload is any[]}
+ */
+function isArray(payload) {
+ return getType(payload) === 'Array';
+}
+/**
+ * Returns whether the payload is a an array with at least 1 item
+ *
+ * @param {*} payload
+ * @returns {payload is any[]}
+ */
+function isFullArray(payload) {
+ return isArray(payload) && payload.length > 0;
+}
+/**
+ * Returns whether the payload is a an empty array
+ *
+ * @param {*} payload
+ * @returns {payload is []}
+ */
+function isEmptyArray(payload) {
+ return isArray(payload) && payload.length === 0;
+}
+/**
+ * Returns whether the payload is a string
+ *
+ * @param {*} payload
+ * @returns {payload is string}
+ */
+function isString(payload) {
+ return getType(payload) === 'String';
+}
+/**
+ * Returns whether the payload is a string, BUT returns false for ''
+ *
+ * @param {*} payload
+ * @returns {payload is string}
+ */
+function isFullString(payload) {
+ return isString(payload) && payload !== '';
+}
+/**
+ * Returns whether the payload is ''
+ *
+ * @param {*} payload
+ * @returns {payload is string}
+ */
+function isEmptyString(payload) {
+ return payload === '';
+}
+/**
+ * Returns whether the payload is a number (but not NaN)
+ *
+ * This will return `false` for `NaN`!!
+ *
+ * @param {*} payload
+ * @returns {payload is number}
+ */
+function isNumber(payload) {
+ return getType(payload) === 'Number' && !isNaN(payload);
+}
+/**
+ * Returns whether the payload is a boolean
+ *
+ * @param {*} payload
+ * @returns {payload is boolean}
+ */
+function isBoolean(payload) {
+ return getType(payload) === 'Boolean';
+}
+/**
+ * Returns whether the payload is a regular expression (RegExp)
+ *
+ * @param {*} payload
+ * @returns {payload is RegExp}
+ */
+function isRegExp(payload) {
+ return getType(payload) === 'RegExp';
+}
+/**
+ * Returns whether the payload is a Map
+ *
+ * @param {*} payload
+ * @returns {payload is Map}
+ */
+function isMap(payload) {
+ return getType(payload) === 'Map';
+}
+/**
+ * Returns whether the payload is a WeakMap
+ *
+ * @param {*} payload
+ * @returns {payload is WeakMap}
+ */
+function isWeakMap(payload) {
+ return getType(payload) === 'WeakMap';
+}
+/**
+ * Returns whether the payload is a Set
+ *
+ * @param {*} payload
+ * @returns {payload is Set}
+ */
+function isSet(payload) {
+ return getType(payload) === 'Set';
+}
+/**
+ * Returns whether the payload is a WeakSet
+ *
+ * @param {*} payload
+ * @returns {payload is WeakSet}
+ */
+function isWeakSet(payload) {
+ return getType(payload) === 'WeakSet';
+}
+/**
+ * Returns whether the payload is a Symbol
+ *
+ * @param {*} payload
+ * @returns {payload is symbol}
+ */
+function isSymbol(payload) {
+ return getType(payload) === 'Symbol';
+}
+/**
+ * Returns whether the payload is a Date, and that the date is valid
+ *
+ * @param {*} payload
+ * @returns {payload is Date}
+ */
+function isDate(payload) {
+ return getType(payload) === 'Date' && !isNaN(payload);
+}
+/**
+ * Returns whether the payload is a Blob
+ *
+ * @param {*} payload
+ * @returns {payload is Blob}
+ */
+function isBlob(payload) {
+ return getType(payload) === 'Blob';
+}
+/**
+ * Returns whether the payload is a File
+ *
+ * @param {*} payload
+ * @returns {payload is File}
+ */
+function isFile(payload) {
+ return getType(payload) === 'File';
+}
+/**
+ * Returns whether the payload is a Promise
+ *
+ * @param {*} payload
+ * @returns {payload is Promise}
+ */
+function isPromise(payload) {
+ return getType(payload) === 'Promise';
+}
+/**
+ * Returns whether the payload is an Error
+ *
+ * @param {*} payload
+ * @returns {payload is Error}
+ */
+function isError(payload) {
+ return getType(payload) === 'Error';
+}
+/**
+ * Returns whether the payload is literally the value `NaN` (it's `NaN` and also a `number`)
+ *
+ * @param {*} payload
+ * @returns {payload is typeof NaN}
+ */
+function isNaNValue(payload) {
+ return getType(payload) === 'Number' && isNaN(payload);
+}
+/**
+ * Returns whether the payload is a primitive type (eg. Boolean | Null | Undefined | Number | String | Symbol)
+ *
+ * @param {*} payload
+ * @returns {(payload is boolean | null | undefined | number | string | symbol)}
+ */
+function isPrimitive(payload) {
+ return (isBoolean(payload) ||
+ isNull(payload) ||
+ isUndefined(payload) ||
+ isNumber(payload) ||
+ isString(payload) ||
+ isSymbol(payload));
+}
+/**
+ * Returns true whether the payload is null or undefined
+ *
+ * @param {*} payload
+ * @returns {(payload is null | undefined)}
+ */
+var isNullOrUndefined = isOneOf(isNull, isUndefined);
+function isOneOf(a, b, c, d, e) {
+ return function (value) {
+ return a(value) || b(value) || (!!c && c(value)) || (!!d && d(value)) || (!!e && e(value));
+ };
+}
+/**
+ * Does a generic check to check that the given payload is of a given type.
+ * In cases like Number, it will return true for NaN as NaN is a Number (thanks javascript!);
+ * It will, however, differentiate between object and null
+ *
+ * @template T
+ * @param {*} payload
+ * @param {T} type
+ * @throws {TypeError} Will throw type error if type is an invalid type
+ * @returns {payload is T}
+ */
+function isType(payload, type) {
+ if (!(type instanceof Function)) {
+ throw new TypeError('Type must be a function');
+ }
+ if (!Object.prototype.hasOwnProperty.call(type, 'prototype')) {
+ throw new TypeError('Type is not a class');
+ }
+ // Classes usually have names (as functions usually have names)
+ var name = type.name;
+ return getType(payload) === name || Boolean(payload && payload.constructor === type);
+}
+
+
+
+
+/***/ }),
+
+/***/ "./node_modules/lodash/_Symbol.js":
+/*!****************************************!*\
+ !*** ./node_modules/lodash/_Symbol.js ***!
+ \****************************************/
+/***/ ((module, __unused_webpack_exports, __webpack_require__) => {
+
+var root = __webpack_require__(/*! ./_root */ "./node_modules/lodash/_root.js");
+
+/** Built-in value references. */
+var Symbol = root.Symbol;
+
+module.exports = Symbol;
+
+
+/***/ }),
+
+/***/ "./node_modules/lodash/_baseGetTag.js":
+/*!********************************************!*\
+ !*** ./node_modules/lodash/_baseGetTag.js ***!
+ \********************************************/
+/***/ ((module, __unused_webpack_exports, __webpack_require__) => {
+
+var Symbol = __webpack_require__(/*! ./_Symbol */ "./node_modules/lodash/_Symbol.js"),
+ getRawTag = __webpack_require__(/*! ./_getRawTag */ "./node_modules/lodash/_getRawTag.js"),
+ objectToString = __webpack_require__(/*! ./_objectToString */ "./node_modules/lodash/_objectToString.js");
+
+/** `Object#toString` result references. */
+var nullTag = '[object Null]',
+ undefinedTag = '[object Undefined]';
+
+/** Built-in value references. */
+var symToStringTag = Symbol ? Symbol.toStringTag : undefined;
+
+/**
+ * The base implementation of `getTag` without fallbacks for buggy environments.
+ *
+ * @private
+ * @param {*} value The value to query.
+ * @returns {string} Returns the `toStringTag`.
+ */
+function baseGetTag(value) {
+ if (value == null) {
+ return value === undefined ? undefinedTag : nullTag;
+ }
+ return (symToStringTag && symToStringTag in Object(value))
+ ? getRawTag(value)
+ : objectToString(value);
+}
+
+module.exports = baseGetTag;
+
+
+/***/ }),
+
+/***/ "./node_modules/lodash/_baseTrim.js":
+/*!******************************************!*\
+ !*** ./node_modules/lodash/_baseTrim.js ***!
+ \******************************************/
+/***/ ((module, __unused_webpack_exports, __webpack_require__) => {
+
+var trimmedEndIndex = __webpack_require__(/*! ./_trimmedEndIndex */ "./node_modules/lodash/_trimmedEndIndex.js");
+
+/** Used to match leading whitespace. */
+var reTrimStart = /^\s+/;
+
+/**
+ * The base implementation of `_.trim`.
+ *
+ * @private
+ * @param {string} string The string to trim.
+ * @returns {string} Returns the trimmed string.
+ */
+function baseTrim(string) {
+ return string
+ ? string.slice(0, trimmedEndIndex(string) + 1).replace(reTrimStart, '')
+ : string;
+}
+
+module.exports = baseTrim;
+
+
+/***/ }),
+
+/***/ "./node_modules/lodash/_freeGlobal.js":
+/*!********************************************!*\
+ !*** ./node_modules/lodash/_freeGlobal.js ***!
+ \********************************************/
+/***/ ((module, __unused_webpack_exports, __webpack_require__) => {
+
+/** Detect free variable `global` from Node.js. */
+var freeGlobal = typeof __webpack_require__.g == 'object' && __webpack_require__.g && __webpack_require__.g.Object === Object && __webpack_require__.g;
+
+module.exports = freeGlobal;
+
+
+/***/ }),
+
+/***/ "./node_modules/lodash/_getRawTag.js":
+/*!*******************************************!*\
+ !*** ./node_modules/lodash/_getRawTag.js ***!
+ \*******************************************/
+/***/ ((module, __unused_webpack_exports, __webpack_require__) => {
+
+var Symbol = __webpack_require__(/*! ./_Symbol */ "./node_modules/lodash/_Symbol.js");
+
+/** Used for built-in method references. */
+var objectProto = Object.prototype;
+
+/** Used to check objects for own properties. */
+var hasOwnProperty = objectProto.hasOwnProperty;
+
+/**
+ * Used to resolve the
+ * [`toStringTag`](http://ecma-international.org/ecma-262/7.0/#sec-object.prototype.tostring)
+ * of values.
+ */
+var nativeObjectToString = objectProto.toString;
+
+/** Built-in value references. */
+var symToStringTag = Symbol ? Symbol.toStringTag : undefined;
+
+/**
+ * A specialized version of `baseGetTag` which ignores `Symbol.toStringTag` values.
+ *
+ * @private
+ * @param {*} value The value to query.
+ * @returns {string} Returns the raw `toStringTag`.
+ */
+function getRawTag(value) {
+ var isOwn = hasOwnProperty.call(value, symToStringTag),
+ tag = value[symToStringTag];
+
+ try {
+ value[symToStringTag] = undefined;
+ var unmasked = true;
+ } catch (e) {}
+
+ var result = nativeObjectToString.call(value);
+ if (unmasked) {
+ if (isOwn) {
+ value[symToStringTag] = tag;
+ } else {
+ delete value[symToStringTag];
+ }
+ }
+ return result;
+}
+
+module.exports = getRawTag;
+
+
+/***/ }),
+
+/***/ "./node_modules/lodash/_objectToString.js":
+/*!************************************************!*\
+ !*** ./node_modules/lodash/_objectToString.js ***!
+ \************************************************/
+/***/ ((module) => {
+
+/** Used for built-in method references. */
+var objectProto = Object.prototype;
+
+/**
+ * Used to resolve the
+ * [`toStringTag`](http://ecma-international.org/ecma-262/7.0/#sec-object.prototype.tostring)
+ * of values.
+ */
+var nativeObjectToString = objectProto.toString;
+
+/**
+ * Converts `value` to a string using `Object.prototype.toString`.
+ *
+ * @private
+ * @param {*} value The value to convert.
+ * @returns {string} Returns the converted string.
+ */
+function objectToString(value) {
+ return nativeObjectToString.call(value);
+}
+
+module.exports = objectToString;
+
+
+/***/ }),
+
+/***/ "./node_modules/lodash/_root.js":
+/*!**************************************!*\
+ !*** ./node_modules/lodash/_root.js ***!
+ \**************************************/
+/***/ ((module, __unused_webpack_exports, __webpack_require__) => {
+
+var freeGlobal = __webpack_require__(/*! ./_freeGlobal */ "./node_modules/lodash/_freeGlobal.js");
+
+/** Detect free variable `self`. */
+var freeSelf = typeof self == 'object' && self && self.Object === Object && self;
+
+/** Used as a reference to the global object. */
+var root = freeGlobal || freeSelf || Function('return this')();
+
+module.exports = root;
+
+
+/***/ }),
+
+/***/ "./node_modules/lodash/_trimmedEndIndex.js":
+/*!*************************************************!*\
+ !*** ./node_modules/lodash/_trimmedEndIndex.js ***!
+ \*************************************************/
+/***/ ((module) => {
+
+/** Used to match a single whitespace character. */
+var reWhitespace = /\s/;
+
+/**
+ * Used by `_.trim` and `_.trimEnd` to get the index of the last non-whitespace
+ * character of `string`.
+ *
+ * @private
+ * @param {string} string The string to inspect.
+ * @returns {number} Returns the index of the last non-whitespace character.
+ */
+function trimmedEndIndex(string) {
+ var index = string.length;
+
+ while (index-- && reWhitespace.test(string.charAt(index))) {}
+ return index;
+}
+
+module.exports = trimmedEndIndex;
+
+
+/***/ }),
+
+/***/ "./node_modules/lodash/debounce.js":
+/*!*****************************************!*\
+ !*** ./node_modules/lodash/debounce.js ***!
+ \*****************************************/
+/***/ ((module, __unused_webpack_exports, __webpack_require__) => {
+
+var isObject = __webpack_require__(/*! ./isObject */ "./node_modules/lodash/isObject.js"),
+ now = __webpack_require__(/*! ./now */ "./node_modules/lodash/now.js"),
+ toNumber = __webpack_require__(/*! ./toNumber */ "./node_modules/lodash/toNumber.js");
+
+/** Error message constants. */
+var FUNC_ERROR_TEXT = 'Expected a function';
+
+/* Built-in method references for those with the same name as other `lodash` methods. */
+var nativeMax = Math.max,
+ nativeMin = Math.min;
+
+/**
+ * Creates a debounced function that delays invoking `func` until after `wait`
+ * milliseconds have elapsed since the last time the debounced function was
+ * invoked. The debounced function comes with a `cancel` method to cancel
+ * delayed `func` invocations and a `flush` method to immediately invoke them.
+ * Provide `options` to indicate whether `func` should be invoked on the
+ * leading and/or trailing edge of the `wait` timeout. The `func` is invoked
+ * with the last arguments provided to the debounced function. Subsequent
+ * calls to the debounced function return the result of the last `func`
+ * invocation.
+ *
+ * **Note:** If `leading` and `trailing` options are `true`, `func` is
+ * invoked on the trailing edge of the timeout only if the debounced function
+ * is invoked more than once during the `wait` timeout.
+ *
+ * If `wait` is `0` and `leading` is `false`, `func` invocation is deferred
+ * until to the next tick, similar to `setTimeout` with a timeout of `0`.
+ *
+ * See [David Corbacho's article](https://css-tricks.com/debouncing-throttling-explained-examples/)
+ * for details over the differences between `_.debounce` and `_.throttle`.
+ *
+ * @static
+ * @memberOf _
+ * @since 0.1.0
+ * @category Function
+ * @param {Function} func The function to debounce.
+ * @param {number} [wait=0] The number of milliseconds to delay.
+ * @param {Object} [options={}] The options object.
+ * @param {boolean} [options.leading=false]
+ * Specify invoking on the leading edge of the timeout.
+ * @param {number} [options.maxWait]
+ * The maximum time `func` is allowed to be delayed before it's invoked.
+ * @param {boolean} [options.trailing=true]
+ * Specify invoking on the trailing edge of the timeout.
+ * @returns {Function} Returns the new debounced function.
+ * @example
+ *
+ * // Avoid costly calculations while the window size is in flux.
+ * jQuery(window).on('resize', _.debounce(calculateLayout, 150));
+ *
+ * // Invoke `sendMail` when clicked, debouncing subsequent calls.
+ * jQuery(element).on('click', _.debounce(sendMail, 300, {
+ * 'leading': true,
+ * 'trailing': false
+ * }));
+ *
+ * // Ensure `batchLog` is invoked once after 1 second of debounced calls.
+ * var debounced = _.debounce(batchLog, 250, { 'maxWait': 1000 });
+ * var source = new EventSource('/stream');
+ * jQuery(source).on('message', debounced);
+ *
+ * // Cancel the trailing debounced invocation.
+ * jQuery(window).on('popstate', debounced.cancel);
+ */
+function debounce(func, wait, options) {
+ var lastArgs,
+ lastThis,
+ maxWait,
+ result,
+ timerId,
+ lastCallTime,
+ lastInvokeTime = 0,
+ leading = false,
+ maxing = false,
+ trailing = true;
+
+ if (typeof func != 'function') {
+ throw new TypeError(FUNC_ERROR_TEXT);
+ }
+ wait = toNumber(wait) || 0;
+ if (isObject(options)) {
+ leading = !!options.leading;
+ maxing = 'maxWait' in options;
+ maxWait = maxing ? nativeMax(toNumber(options.maxWait) || 0, wait) : maxWait;
+ trailing = 'trailing' in options ? !!options.trailing : trailing;
+ }
+
+ function invokeFunc(time) {
+ var args = lastArgs,
+ thisArg = lastThis;
+
+ lastArgs = lastThis = undefined;
+ lastInvokeTime = time;
+ result = func.apply(thisArg, args);
+ return result;
+ }
+
+ function leadingEdge(time) {
+ // Reset any `maxWait` timer.
+ lastInvokeTime = time;
+ // Start the timer for the trailing edge.
+ timerId = setTimeout(timerExpired, wait);
+ // Invoke the leading edge.
+ return leading ? invokeFunc(time) : result;
+ }
+
+ function remainingWait(time) {
+ var timeSinceLastCall = time - lastCallTime,
+ timeSinceLastInvoke = time - lastInvokeTime,
+ timeWaiting = wait - timeSinceLastCall;
+
+ return maxing
+ ? nativeMin(timeWaiting, maxWait - timeSinceLastInvoke)
+ : timeWaiting;
+ }
+
+ function shouldInvoke(time) {
+ var timeSinceLastCall = time - lastCallTime,
+ timeSinceLastInvoke = time - lastInvokeTime;
+
+ // Either this is the first call, activity has stopped and we're at the
+ // trailing edge, the system time has gone backwards and we're treating
+ // it as the trailing edge, or we've hit the `maxWait` limit.
+ return (lastCallTime === undefined || (timeSinceLastCall >= wait) ||
+ (timeSinceLastCall < 0) || (maxing && timeSinceLastInvoke >= maxWait));
+ }
+
+ function timerExpired() {
+ var time = now();
+ if (shouldInvoke(time)) {
+ return trailingEdge(time);
+ }
+ // Restart the timer.
+ timerId = setTimeout(timerExpired, remainingWait(time));
+ }
+
+ function trailingEdge(time) {
+ timerId = undefined;
+
+ // Only invoke if we have `lastArgs` which means `func` has been
+ // debounced at least once.
+ if (trailing && lastArgs) {
+ return invokeFunc(time);
+ }
+ lastArgs = lastThis = undefined;
+ return result;
+ }
+
+ function cancel() {
+ if (timerId !== undefined) {
+ clearTimeout(timerId);
+ }
+ lastInvokeTime = 0;
+ lastArgs = lastCallTime = lastThis = timerId = undefined;
+ }
+
+ function flush() {
+ return timerId === undefined ? result : trailingEdge(now());
+ }
+
+ function debounced() {
+ var time = now(),
+ isInvoking = shouldInvoke(time);
+
+ lastArgs = arguments;
+ lastThis = this;
+ lastCallTime = time;
+
+ if (isInvoking) {
+ if (timerId === undefined) {
+ return leadingEdge(lastCallTime);
+ }
+ if (maxing) {
+ // Handle invocations in a tight loop.
+ clearTimeout(timerId);
+ timerId = setTimeout(timerExpired, wait);
+ return invokeFunc(lastCallTime);
+ }
+ }
+ if (timerId === undefined) {
+ timerId = setTimeout(timerExpired, wait);
+ }
+ return result;
+ }
+ debounced.cancel = cancel;
+ debounced.flush = flush;
+ return debounced;
+}
+
+module.exports = debounce;
+
+
+/***/ }),
+
+/***/ "./node_modules/lodash/isObject.js":
+/*!*****************************************!*\
+ !*** ./node_modules/lodash/isObject.js ***!
+ \*****************************************/
+/***/ ((module) => {
+
+/**
+ * Checks if `value` is the
+ * [language type](http://www.ecma-international.org/ecma-262/7.0/#sec-ecmascript-language-types)
+ * of `Object`. (e.g. arrays, functions, objects, regexes, `new Number(0)`, and `new String('')`)
+ *
+ * @static
+ * @memberOf _
+ * @since 0.1.0
+ * @category Lang
+ * @param {*} value The value to check.
+ * @returns {boolean} Returns `true` if `value` is an object, else `false`.
+ * @example
+ *
+ * _.isObject({});
+ * // => true
+ *
+ * _.isObject([1, 2, 3]);
+ * // => true
+ *
+ * _.isObject(_.noop);
+ * // => true
+ *
+ * _.isObject(null);
+ * // => false
+ */
+function isObject(value) {
+ var type = typeof value;
+ return value != null && (type == 'object' || type == 'function');
+}
+
+module.exports = isObject;
+
+
+/***/ }),
+
+/***/ "./node_modules/lodash/isObjectLike.js":
+/*!*********************************************!*\
+ !*** ./node_modules/lodash/isObjectLike.js ***!
+ \*********************************************/
+/***/ ((module) => {
+
+/**
+ * Checks if `value` is object-like. A value is object-like if it's not `null`
+ * and has a `typeof` result of "object".
+ *
+ * @static
+ * @memberOf _
+ * @since 4.0.0
+ * @category Lang
+ * @param {*} value The value to check.
+ * @returns {boolean} Returns `true` if `value` is object-like, else `false`.
+ * @example
+ *
+ * _.isObjectLike({});
+ * // => true
+ *
+ * _.isObjectLike([1, 2, 3]);
+ * // => true
+ *
+ * _.isObjectLike(_.noop);
+ * // => false
+ *
+ * _.isObjectLike(null);
+ * // => false
+ */
+function isObjectLike(value) {
+ return value != null && typeof value == 'object';
+}
+
+module.exports = isObjectLike;
+
+
+/***/ }),
+
+/***/ "./node_modules/lodash/isSymbol.js":
+/*!*****************************************!*\
+ !*** ./node_modules/lodash/isSymbol.js ***!
+ \*****************************************/
+/***/ ((module, __unused_webpack_exports, __webpack_require__) => {
+
+var baseGetTag = __webpack_require__(/*! ./_baseGetTag */ "./node_modules/lodash/_baseGetTag.js"),
+ isObjectLike = __webpack_require__(/*! ./isObjectLike */ "./node_modules/lodash/isObjectLike.js");
+
+/** `Object#toString` result references. */
+var symbolTag = '[object Symbol]';
+
+/**
+ * Checks if `value` is classified as a `Symbol` primitive or object.
+ *
+ * @static
+ * @memberOf _
+ * @since 4.0.0
+ * @category Lang
+ * @param {*} value The value to check.
+ * @returns {boolean} Returns `true` if `value` is a symbol, else `false`.
+ * @example
+ *
+ * _.isSymbol(Symbol.iterator);
+ * // => true
+ *
+ * _.isSymbol('abc');
+ * // => false
+ */
+function isSymbol(value) {
+ return typeof value == 'symbol' ||
+ (isObjectLike(value) && baseGetTag(value) == symbolTag);
+}
+
+module.exports = isSymbol;
+
+
+/***/ }),
+
+/***/ "./node_modules/lodash/now.js":
+/*!************************************!*\
+ !*** ./node_modules/lodash/now.js ***!
+ \************************************/
+/***/ ((module, __unused_webpack_exports, __webpack_require__) => {
+
+var root = __webpack_require__(/*! ./_root */ "./node_modules/lodash/_root.js");
+
+/**
+ * Gets the timestamp of the number of milliseconds that have elapsed since
+ * the Unix epoch (1 January 1970 00:00:00 UTC).
+ *
+ * @static
+ * @memberOf _
+ * @since 2.4.0
+ * @category Date
+ * @returns {number} Returns the timestamp.
+ * @example
+ *
+ * _.defer(function(stamp) {
+ * console.log(_.now() - stamp);
+ * }, _.now());
+ * // => Logs the number of milliseconds it took for the deferred invocation.
+ */
+var now = function() {
+ return root.Date.now();
+};
+
+module.exports = now;
+
+
+/***/ }),
+
+/***/ "./node_modules/lodash/toNumber.js":
+/*!*****************************************!*\
+ !*** ./node_modules/lodash/toNumber.js ***!
+ \*****************************************/
+/***/ ((module, __unused_webpack_exports, __webpack_require__) => {
+
+var baseTrim = __webpack_require__(/*! ./_baseTrim */ "./node_modules/lodash/_baseTrim.js"),
+ isObject = __webpack_require__(/*! ./isObject */ "./node_modules/lodash/isObject.js"),
+ isSymbol = __webpack_require__(/*! ./isSymbol */ "./node_modules/lodash/isSymbol.js");
+
+/** Used as references for various `Number` constants. */
+var NAN = 0 / 0;
+
+/** Used to detect bad signed hexadecimal string values. */
+var reIsBadHex = /^[-+]0x[0-9a-f]+$/i;
+
+/** Used to detect binary string values. */
+var reIsBinary = /^0b[01]+$/i;
+
+/** Used to detect octal string values. */
+var reIsOctal = /^0o[0-7]+$/i;
+
+/** Built-in method references without a dependency on `root`. */
+var freeParseInt = parseInt;
+
+/**
+ * Converts `value` to a number.
+ *
+ * @static
+ * @memberOf _
+ * @since 4.0.0
+ * @category Lang
+ * @param {*} value The value to process.
+ * @returns {number} Returns the number.
+ * @example
+ *
+ * _.toNumber(3.2);
+ * // => 3.2
+ *
+ * _.toNumber(Number.MIN_VALUE);
+ * // => 5e-324
+ *
+ * _.toNumber(Infinity);
+ * // => Infinity
+ *
+ * _.toNumber('3.2');
+ * // => 3.2
+ */
+function toNumber(value) {
+ if (typeof value == 'number') {
+ return value;
+ }
+ if (isSymbol(value)) {
+ return NAN;
+ }
+ if (isObject(value)) {
+ var other = typeof value.valueOf == 'function' ? value.valueOf() : value;
+ value = isObject(other) ? (other + '') : other;
+ }
+ if (typeof value != 'string') {
+ return value === 0 ? value : +value;
+ }
+ value = baseTrim(value);
+ var isBinary = reIsBinary.test(value);
+ return (isBinary || reIsOctal.test(value))
+ ? freeParseInt(value.slice(2), isBinary ? 2 : 8)
+ : (reIsBadHex.test(value) ? NAN : +value);
+}
+
+module.exports = toNumber;
+
+
+/***/ }),
+
+/***/ "./node_modules/memoize-one/dist/memoize-one.esm.js":
+/*!**********************************************************!*\
+ !*** ./node_modules/memoize-one/dist/memoize-one.esm.js ***!
+ \**********************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "default": () => (__WEBPACK_DEFAULT_EXPORT__)
+/* harmony export */ });
+var safeIsNaN = Number.isNaN ||
+ function ponyfill(value) {
+ return typeof value === 'number' && value !== value;
+ };
+function isEqual(first, second) {
+ if (first === second) {
+ return true;
+ }
+ if (safeIsNaN(first) && safeIsNaN(second)) {
+ return true;
+ }
+ return false;
+}
+function areInputsEqual(newInputs, lastInputs) {
+ if (newInputs.length !== lastInputs.length) {
+ return false;
+ }
+ for (var i = 0; i < newInputs.length; i++) {
+ if (!isEqual(newInputs[i], lastInputs[i])) {
+ return false;
+ }
+ }
+ return true;
+}
+
+function memoizeOne(resultFn, isEqual) {
+ if (isEqual === void 0) { isEqual = areInputsEqual; }
+ var lastThis;
+ var lastArgs = [];
+ var lastResult;
+ var calledOnce = false;
+ function memoized() {
+ var newArgs = [];
+ for (var _i = 0; _i < arguments.length; _i++) {
+ newArgs[_i] = arguments[_i];
+ }
+ if (calledOnce && lastThis === this && isEqual(newArgs, lastArgs)) {
+ return lastResult;
+ }
+ lastResult = resultFn.apply(this, newArgs);
+ calledOnce = true;
+ lastThis = this;
+ lastArgs = newArgs;
+ return lastResult;
+ }
+ return memoized;
+}
+
+/* harmony default export */ const __WEBPACK_DEFAULT_EXPORT__ = (memoizeOne);
+
+
+/***/ }),
+
+/***/ "./node_modules/merge-anything/dist/index.esm.js":
+/*!*******************************************************!*\
+ !*** ./node_modules/merge-anything/dist/index.esm.js ***!
+ \*******************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "concatArrays": () => (/* binding */ concatArrays),
+/* harmony export */ "default": () => (__WEBPACK_DEFAULT_EXPORT__),
+/* harmony export */ "merge": () => (/* binding */ merge)
+/* harmony export */ });
+/* harmony import */ var is_what__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! is-what */ "./node_modules/is-what/dist/index.esm.js");
+
+
+/*! *****************************************************************************
+Copyright (c) Microsoft Corporation. All rights reserved.
+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
+
+THIS CODE IS PROVIDED ON AN *AS IS* BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+KIND, EITHER EXPRESS OR IMPLIED, INCLUDING WITHOUT LIMITATION ANY IMPLIED
+WARRANTIES OR CONDITIONS OF TITLE, FITNESS FOR A PARTICULAR PURPOSE,
+MERCHANTABLITY OR NON-INFRINGEMENT.
+
+See the Apache Version 2.0 License for specific language governing permissions
+and limitations under the License.
+***************************************************************************** */
+
+function __spreadArrays() {
+ for (var s = 0, i = 0, il = arguments.length; i < il; i++) s += arguments[i].length;
+ for (var r = Array(s), k = 0, i = 0; i < il; i++)
+ for (var a = arguments[i], j = 0, jl = a.length; j < jl; j++, k++)
+ r[k] = a[j];
+ return r;
+}
+
+function assignProp(carry, key, newVal, originalObject) {
+ var propType = originalObject.propertyIsEnumerable(key)
+ ? 'enumerable'
+ : 'nonenumerable';
+ if (propType === 'enumerable')
+ carry[key] = newVal;
+ if (propType === 'nonenumerable') {
+ Object.defineProperty(carry, key, {
+ value: newVal,
+ enumerable: false,
+ writable: true,
+ configurable: true
+ });
+ }
+}
+function mergeRecursively(origin, newComer, extensions) {
+ // work directly on newComer if its not an object
+ if (!(0,is_what__WEBPACK_IMPORTED_MODULE_0__.isPlainObject)(newComer)) {
+ // extend merge rules
+ if (extensions && (0,is_what__WEBPACK_IMPORTED_MODULE_0__.isArray)(extensions)) {
+ extensions.forEach(function (extend) {
+ newComer = extend(origin, newComer);
+ });
+ }
+ return newComer;
+ }
+ // define newObject to merge all values upon
+ var newObject = {};
+ if ((0,is_what__WEBPACK_IMPORTED_MODULE_0__.isPlainObject)(origin)) {
+ var props_1 = Object.getOwnPropertyNames(origin);
+ var symbols_1 = Object.getOwnPropertySymbols(origin);
+ newObject = __spreadArrays(props_1, symbols_1).reduce(function (carry, key) {
+ // @ts-ignore
+ var targetVal = origin[key];
+ if ((!(0,is_what__WEBPACK_IMPORTED_MODULE_0__.isSymbol)(key) && !Object.getOwnPropertyNames(newComer).includes(key)) ||
+ ((0,is_what__WEBPACK_IMPORTED_MODULE_0__.isSymbol)(key) && !Object.getOwnPropertySymbols(newComer).includes(key))) {
+ assignProp(carry, key, targetVal, origin);
+ }
+ return carry;
+ }, {});
+ }
+ var props = Object.getOwnPropertyNames(newComer);
+ var symbols = Object.getOwnPropertySymbols(newComer);
+ var result = __spreadArrays(props, symbols).reduce(function (carry, key) {
+ // re-define the origin and newComer as targetVal and newVal
+ var newVal = newComer[key];
+ var targetVal = ((0,is_what__WEBPACK_IMPORTED_MODULE_0__.isPlainObject)(origin))
+ // @ts-ignore
+ ? origin[key]
+ : undefined;
+ // extend merge rules
+ if (extensions && (0,is_what__WEBPACK_IMPORTED_MODULE_0__.isArray)(extensions)) {
+ extensions.forEach(function (extend) {
+ newVal = extend(targetVal, newVal);
+ });
+ }
+ // When newVal is an object do the merge recursively
+ if (targetVal !== undefined && (0,is_what__WEBPACK_IMPORTED_MODULE_0__.isPlainObject)(newVal)) {
+ newVal = mergeRecursively(targetVal, newVal, extensions);
+ }
+ assignProp(carry, key, newVal, newComer);
+ return carry;
+ }, newObject);
+ return result;
+}
+/**
+ * Merge anything recursively.
+ * Objects get merged, special objects (classes etc.) are re-assigned "as is".
+ * Basic types overwrite objects or other basic types.
+ *
+ * @param {(IConfig | any)} origin
+ * @param {...any[]} newComers
+ * @returns the result
+ */
+function merge(origin) {
+ var newComers = [];
+ for (var _i = 1; _i < arguments.length; _i++) {
+ newComers[_i - 1] = arguments[_i];
+ }
+ var extensions = null;
+ var base = origin;
+ if ((0,is_what__WEBPACK_IMPORTED_MODULE_0__.isPlainObject)(origin) && origin.extensions && Object.keys(origin).length === 1) {
+ base = {};
+ extensions = origin.extensions;
+ }
+ return newComers.reduce(function (result, newComer) {
+ return mergeRecursively(result, newComer, extensions);
+ }, base);
+}
+
+function concatArrays(originVal, newVal) {
+ if ((0,is_what__WEBPACK_IMPORTED_MODULE_0__.isArray)(originVal) && (0,is_what__WEBPACK_IMPORTED_MODULE_0__.isArray)(newVal)) {
+ // concat logic
+ return originVal.concat(newVal);
+ }
+ return newVal; // always return newVal as fallback!!
+}
+
+/* harmony default export */ const __WEBPACK_DEFAULT_EXPORT__ = (merge);
+
+
+
+/***/ }),
+
+/***/ "./scripts/gutenberg/UIComponents/UIImage.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/gutenberg/UIComponents/UIImage.ts":
+/*!****************************************************************************************************************************************************************************************!*\
+ !*** ./scripts/gutenberg/UIComponents/UIImage.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/gutenberg/UIComponents/UIImage.ts ***!
+ \****************************************************************************************************************************************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+// extracted by mini-css-extract-plugin
+
+
+/***/ }),
+
+/***/ "./scripts/shared/Common/AsyncSelect.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/Common/AsyncSelect.tsx":
+/*!*******************************************************************************************************************************************************************************!*\
+ !*** ./scripts/shared/Common/AsyncSelect.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/Common/AsyncSelect.tsx ***!
+ \*******************************************************************************************************************************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+// extracted by mini-css-extract-plugin
+
+
+/***/ }),
+
+/***/ "./scripts/shared/Common/HubspotWrapper.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/Common/HubspotWrapper.ts":
+/*!************************************************************************************************************************************************************************************!*\
+ !*** ./scripts/shared/Common/HubspotWrapper.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/Common/HubspotWrapper.ts ***!
+ \************************************************************************************************************************************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+// extracted by mini-css-extract-plugin
+
+
+/***/ }),
+
+/***/ "./scripts/shared/UIComponents/UIAlert.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/UIComponents/UIAlert.tsx":
+/*!***********************************************************************************************************************************************************************************!*\
+ !*** ./scripts/shared/UIComponents/UIAlert.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/UIComponents/UIAlert.tsx ***!
+ \***********************************************************************************************************************************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+// extracted by mini-css-extract-plugin
+
+
+/***/ }),
+
+/***/ "./scripts/shared/UIComponents/UIButton.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/UIComponents/UIButton.ts":
+/*!************************************************************************************************************************************************************************************!*\
+ !*** ./scripts/shared/UIComponents/UIButton.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/UIComponents/UIButton.ts ***!
+ \************************************************************************************************************************************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+// extracted by mini-css-extract-plugin
+
+
+/***/ }),
+
+/***/ "./scripts/shared/UIComponents/UIContainer.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/UIComponents/UIContainer.ts":
+/*!******************************************************************************************************************************************************************************************!*\
+ !*** ./scripts/shared/UIComponents/UIContainer.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/UIComponents/UIContainer.ts ***!
+ \******************************************************************************************************************************************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+// extracted by mini-css-extract-plugin
+
+
+/***/ }),
+
+/***/ "./scripts/shared/UIComponents/UIOverlay.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/UIComponents/UIOverlay.ts":
+/*!**************************************************************************************************************************************************************************************!*\
+ !*** ./scripts/shared/UIComponents/UIOverlay.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/UIComponents/UIOverlay.ts ***!
+ \**************************************************************************************************************************************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+// extracted by mini-css-extract-plugin
+
+
+/***/ }),
+
+/***/ "./scripts/shared/UIComponents/UISpacer.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/UIComponents/UISpacer.ts":
+/*!************************************************************************************************************************************************************************************!*\
+ !*** ./scripts/shared/UIComponents/UISpacer.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/UIComponents/UISpacer.ts ***!
+ \************************************************************************************************************************************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+// extracted by mini-css-extract-plugin
+
+
+/***/ }),
+
+/***/ "./scripts/shared/UIComponents/UISpinner.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/UIComponents/UISpinner.tsx":
+/*!***************************************************************************************************************************************************************************************!*\
+ !*** ./scripts/shared/UIComponents/UISpinner.linaria.css!=!./node_modules/@linaria/webpack5-loader/lib/outputCssLoader.js?cacheProvider=!./scripts/shared/UIComponents/UISpinner.tsx ***!
+ \***************************************************************************************************************************************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+// extracted by mini-css-extract-plugin
+
+
+/***/ }),
+
+/***/ "./node_modules/object-assign/index.js":
+/*!*********************************************!*\
+ !*** ./node_modules/object-assign/index.js ***!
+ \*********************************************/
+/***/ ((module) => {
+
+"use strict";
+/*
+object-assign
+(c) Sindre Sorhus
+@license MIT
+*/
+
+
+/* eslint-disable no-unused-vars */
+var getOwnPropertySymbols = Object.getOwnPropertySymbols;
+var hasOwnProperty = Object.prototype.hasOwnProperty;
+var propIsEnumerable = Object.prototype.propertyIsEnumerable;
+
+function toObject(val) {
+ if (val === null || val === undefined) {
+ throw new TypeError('Object.assign cannot be called with null or undefined');
+ }
+
+ return Object(val);
+}
+
+function shouldUseNative() {
+ try {
+ if (!Object.assign) {
+ return false;
+ }
+
+ // Detect buggy property enumeration order in older V8 versions.
+
+ // https://bugs.chromium.org/p/v8/issues/detail?id=4118
+ var test1 = new String('abc'); // eslint-disable-line no-new-wrappers
+ test1[5] = 'de';
+ if (Object.getOwnPropertyNames(test1)[0] === '5') {
+ return false;
+ }
+
+ // https://bugs.chromium.org/p/v8/issues/detail?id=3056
+ var test2 = {};
+ for (var i = 0; i < 10; i++) {
+ test2['_' + String.fromCharCode(i)] = i;
+ }
+ var order2 = Object.getOwnPropertyNames(test2).map(function (n) {
+ return test2[n];
+ });
+ if (order2.join('') !== '0123456789') {
+ return false;
+ }
+
+ // https://bugs.chromium.org/p/v8/issues/detail?id=3056
+ var test3 = {};
+ 'abcdefghijklmnopqrst'.split('').forEach(function (letter) {
+ test3[letter] = letter;
+ });
+ if (Object.keys(Object.assign({}, test3)).join('') !==
+ 'abcdefghijklmnopqrst') {
+ return false;
+ }
+
+ return true;
+ } catch (err) {
+ // We don't expect any of the above to throw, but better to be safe.
+ return false;
+ }
+}
+
+module.exports = shouldUseNative() ? Object.assign : function (target, source) {
+ var from;
+ var to = toObject(target);
+ var symbols;
+
+ for (var s = 1; s < arguments.length; s++) {
+ from = Object(arguments[s]);
+
+ for (var key in from) {
+ if (hasOwnProperty.call(from, key)) {
+ to[key] = from[key];
+ }
+ }
+
+ if (getOwnPropertySymbols) {
+ symbols = getOwnPropertySymbols(from);
+ for (var i = 0; i < symbols.length; i++) {
+ if (propIsEnumerable.call(from, symbols[i])) {
+ to[symbols[i]] = from[symbols[i]];
+ }
+ }
+ }
+ }
+
+ return to;
+};
+
+
+/***/ }),
+
+/***/ "./node_modules/prop-types/checkPropTypes.js":
+/*!***************************************************!*\
+ !*** ./node_modules/prop-types/checkPropTypes.js ***!
+ \***************************************************/
+/***/ ((module, __unused_webpack_exports, __webpack_require__) => {
+
+"use strict";
+/**
+ * Copyright (c) 2013-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+
+
+var printWarning = function() {};
+
+if (true) {
+ var ReactPropTypesSecret = __webpack_require__(/*! ./lib/ReactPropTypesSecret */ "./node_modules/prop-types/lib/ReactPropTypesSecret.js");
+ var loggedTypeFailures = {};
+ var has = __webpack_require__(/*! ./lib/has */ "./node_modules/prop-types/lib/has.js");
+
+ printWarning = function(text) {
+ var message = 'Warning: ' + text;
+ if (typeof console !== 'undefined') {
+ console.error(message);
+ }
+ try {
+ // --- Welcome to debugging React ---
+ // This error was thrown as a convenience so that you can use this stack
+ // to find the callsite that caused this warning to fire.
+ throw new Error(message);
+ } catch (x) { /**/ }
+ };
+}
+
+/**
+ * Assert that the values match with the type specs.
+ * Error messages are memorized and will only be shown once.
+ *
+ * @param {object} typeSpecs Map of name to a ReactPropType
+ * @param {object} values Runtime values that need to be type-checked
+ * @param {string} location e.g. "prop", "context", "child context"
+ * @param {string} componentName Name of the component for error messages.
+ * @param {?Function} getStack Returns the component stack.
+ * @private
+ */
+function checkPropTypes(typeSpecs, values, location, componentName, getStack) {
+ if (true) {
+ for (var typeSpecName in typeSpecs) {
+ if (has(typeSpecs, typeSpecName)) {
+ var error;
+ // Prop type validation may throw. In case they do, we don't want to
+ // fail the render phase where it didn't fail before. So we log it.
+ // After these have been cleaned up, we'll let them throw.
+ try {
+ // This is intentionally an invariant that gets caught. It's the same
+ // behavior as without this statement except with a better message.
+ if (typeof typeSpecs[typeSpecName] !== 'function') {
+ var err = Error(
+ (componentName || 'React class') + ': ' + location + ' type `' + typeSpecName + '` is invalid; ' +
+ 'it must be a function, usually from the `prop-types` package, but received `' + typeof typeSpecs[typeSpecName] + '`.' +
+ 'This often happens because of typos such as `PropTypes.function` instead of `PropTypes.func`.'
+ );
+ err.name = 'Invariant Violation';
+ throw err;
+ }
+ error = typeSpecs[typeSpecName](values, typeSpecName, componentName, location, null, ReactPropTypesSecret);
+ } catch (ex) {
+ error = ex;
+ }
+ if (error && !(error instanceof Error)) {
+ printWarning(
+ (componentName || 'React class') + ': type specification of ' +
+ location + ' `' + typeSpecName + '` is invalid; the type checker ' +
+ 'function must return `null` or an `Error` but returned a ' + typeof error + '. ' +
+ 'You may have forgotten to pass an argument to the type checker ' +
+ 'creator (arrayOf, instanceOf, objectOf, oneOf, oneOfType, and ' +
+ 'shape all require an argument).'
+ );
+ }
+ if (error instanceof Error && !(error.message in loggedTypeFailures)) {
+ // Only monitor this failure once because there tends to be a lot of the
+ // same error.
+ loggedTypeFailures[error.message] = true;
+
+ var stack = getStack ? getStack() : '';
+
+ printWarning(
+ 'Failed ' + location + ' type: ' + error.message + (stack != null ? stack : '')
+ );
+ }
+ }
+ }
+ }
+}
+
+/**
+ * Resets warning cache when testing.
+ *
+ * @private
+ */
+checkPropTypes.resetWarningCache = function() {
+ if (true) {
+ loggedTypeFailures = {};
+ }
+}
+
+module.exports = checkPropTypes;
+
+
+/***/ }),
+
+/***/ "./node_modules/prop-types/factoryWithTypeCheckers.js":
+/*!************************************************************!*\
+ !*** ./node_modules/prop-types/factoryWithTypeCheckers.js ***!
+ \************************************************************/
+/***/ ((module, __unused_webpack_exports, __webpack_require__) => {
+
+"use strict";
+/**
+ * Copyright (c) 2013-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+
+
+var ReactIs = __webpack_require__(/*! react-is */ "./node_modules/react-is/index.js");
+var assign = __webpack_require__(/*! object-assign */ "./node_modules/object-assign/index.js");
+
+var ReactPropTypesSecret = __webpack_require__(/*! ./lib/ReactPropTypesSecret */ "./node_modules/prop-types/lib/ReactPropTypesSecret.js");
+var has = __webpack_require__(/*! ./lib/has */ "./node_modules/prop-types/lib/has.js");
+var checkPropTypes = __webpack_require__(/*! ./checkPropTypes */ "./node_modules/prop-types/checkPropTypes.js");
+
+var printWarning = function() {};
+
+if (true) {
+ printWarning = function(text) {
+ var message = 'Warning: ' + text;
+ if (typeof console !== 'undefined') {
+ console.error(message);
+ }
+ try {
+ // --- Welcome to debugging React ---
+ // This error was thrown as a convenience so that you can use this stack
+ // to find the callsite that caused this warning to fire.
+ throw new Error(message);
+ } catch (x) {}
+ };
+}
+
+function emptyFunctionThatReturnsNull() {
+ return null;
+}
+
+module.exports = function(isValidElement, throwOnDirectAccess) {
+ /* global Symbol */
+ var ITERATOR_SYMBOL = typeof Symbol === 'function' && Symbol.iterator;
+ var FAUX_ITERATOR_SYMBOL = '@@iterator'; // Before Symbol spec.
+
+ /**
+ * Returns the iterator method function contained on the iterable object.
+ *
+ * Be sure to invoke the function with the iterable as context:
+ *
+ * var iteratorFn = getIteratorFn(myIterable);
+ * if (iteratorFn) {
+ * var iterator = iteratorFn.call(myIterable);
+ * ...
+ * }
+ *
+ * @param {?object} maybeIterable
+ * @return {?function}
+ */
+ function getIteratorFn(maybeIterable) {
+ var iteratorFn = maybeIterable && (ITERATOR_SYMBOL && maybeIterable[ITERATOR_SYMBOL] || maybeIterable[FAUX_ITERATOR_SYMBOL]);
+ if (typeof iteratorFn === 'function') {
+ return iteratorFn;
+ }
+ }
+
+ /**
+ * Collection of methods that allow declaration and validation of props that are
+ * supplied to React components. Example usage:
+ *
+ * var Props = require('ReactPropTypes');
+ * var MyArticle = React.createClass({
+ * propTypes: {
+ * // An optional string prop named "description".
+ * description: Props.string,
+ *
+ * // A required enum prop named "category".
+ * category: Props.oneOf(['News','Photos']).isRequired,
+ *
+ * // A prop named "dialog" that requires an instance of Dialog.
+ * dialog: Props.instanceOf(Dialog).isRequired
+ * },
+ * render: function() { ... }
+ * });
+ *
+ * A more formal specification of how these methods are used:
+ *
+ * type := array|bool|func|object|number|string|oneOf([...])|instanceOf(...)
+ * decl := ReactPropTypes.{type}(.isRequired)?
+ *
+ * Each and every declaration produces a function with the same signature. This
+ * allows the creation of custom validation functions. For example:
+ *
+ * var MyLink = React.createClass({
+ * propTypes: {
+ * // An optional string or URI prop named "href".
+ * href: function(props, propName, componentName) {
+ * var propValue = props[propName];
+ * if (propValue != null && typeof propValue !== 'string' &&
+ * !(propValue instanceof URI)) {
+ * return new Error(
+ * 'Expected a string or an URI for ' + propName + ' in ' +
+ * componentName
+ * );
+ * }
+ * }
+ * },
+ * render: function() {...}
+ * });
+ *
+ * @internal
+ */
+
+ var ANONYMOUS = '<>';
+
+ // Important!
+ // Keep this list in sync with production version in `./factoryWithThrowingShims.js`.
+ var ReactPropTypes = {
+ array: createPrimitiveTypeChecker('array'),
+ bigint: createPrimitiveTypeChecker('bigint'),
+ bool: createPrimitiveTypeChecker('boolean'),
+ func: createPrimitiveTypeChecker('function'),
+ number: createPrimitiveTypeChecker('number'),
+ object: createPrimitiveTypeChecker('object'),
+ string: createPrimitiveTypeChecker('string'),
+ symbol: createPrimitiveTypeChecker('symbol'),
+
+ any: createAnyTypeChecker(),
+ arrayOf: createArrayOfTypeChecker,
+ element: createElementTypeChecker(),
+ elementType: createElementTypeTypeChecker(),
+ instanceOf: createInstanceTypeChecker,
+ node: createNodeChecker(),
+ objectOf: createObjectOfTypeChecker,
+ oneOf: createEnumTypeChecker,
+ oneOfType: createUnionTypeChecker,
+ shape: createShapeTypeChecker,
+ exact: createStrictShapeTypeChecker,
+ };
+
+ /**
+ * inlined Object.is polyfill to avoid requiring consumers ship their own
+ * https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Object/is
+ */
+ /*eslint-disable no-self-compare*/
+ function is(x, y) {
+ // SameValue algorithm
+ if (x === y) {
+ // Steps 1-5, 7-10
+ // Steps 6.b-6.e: +0 != -0
+ return x !== 0 || 1 / x === 1 / y;
+ } else {
+ // Step 6.a: NaN == NaN
+ return x !== x && y !== y;
+ }
+ }
+ /*eslint-enable no-self-compare*/
+
+ /**
+ * We use an Error-like object for backward compatibility as people may call
+ * PropTypes directly and inspect their output. However, we don't use real
+ * Errors anymore. We don't inspect their stack anyway, and creating them
+ * is prohibitively expensive if they are created too often, such as what
+ * happens in oneOfType() for any type before the one that matched.
+ */
+ function PropTypeError(message, data) {
+ this.message = message;
+ this.data = data && typeof data === 'object' ? data: {};
+ this.stack = '';
+ }
+ // Make `instanceof Error` still work for returned errors.
+ PropTypeError.prototype = Error.prototype;
+
+ function createChainableTypeChecker(validate) {
+ if (true) {
+ var manualPropTypeCallCache = {};
+ var manualPropTypeWarningCount = 0;
+ }
+ function checkType(isRequired, props, propName, componentName, location, propFullName, secret) {
+ componentName = componentName || ANONYMOUS;
+ propFullName = propFullName || propName;
+
+ if (secret !== ReactPropTypesSecret) {
+ if (throwOnDirectAccess) {
+ // New behavior only for users of `prop-types` package
+ var err = new Error(
+ 'Calling PropTypes validators directly is not supported by the `prop-types` package. ' +
+ 'Use `PropTypes.checkPropTypes()` to call them. ' +
+ 'Read more at http://fb.me/use-check-prop-types'
+ );
+ err.name = 'Invariant Violation';
+ throw err;
+ } else if ( true && typeof console !== 'undefined') {
+ // Old behavior for people using React.PropTypes
+ var cacheKey = componentName + ':' + propName;
+ if (
+ !manualPropTypeCallCache[cacheKey] &&
+ // Avoid spamming the console because they are often not actionable except for lib authors
+ manualPropTypeWarningCount < 3
+ ) {
+ printWarning(
+ 'You are manually calling a React.PropTypes validation ' +
+ 'function for the `' + propFullName + '` prop on `' + componentName + '`. This is deprecated ' +
+ 'and will throw in the standalone `prop-types` package. ' +
+ 'You may be seeing this warning due to a third-party PropTypes ' +
+ 'library. See https://fb.me/react-warning-dont-call-proptypes ' + 'for details.'
+ );
+ manualPropTypeCallCache[cacheKey] = true;
+ manualPropTypeWarningCount++;
+ }
+ }
+ }
+ if (props[propName] == null) {
+ if (isRequired) {
+ if (props[propName] === null) {
+ return new PropTypeError('The ' + location + ' `' + propFullName + '` is marked as required ' + ('in `' + componentName + '`, but its value is `null`.'));
+ }
+ return new PropTypeError('The ' + location + ' `' + propFullName + '` is marked as required in ' + ('`' + componentName + '`, but its value is `undefined`.'));
+ }
+ return null;
+ } else {
+ return validate(props, propName, componentName, location, propFullName);
+ }
+ }
+
+ var chainedCheckType = checkType.bind(null, false);
+ chainedCheckType.isRequired = checkType.bind(null, true);
+
+ return chainedCheckType;
+ }
+
+ function createPrimitiveTypeChecker(expectedType) {
+ function validate(props, propName, componentName, location, propFullName, secret) {
+ var propValue = props[propName];
+ var propType = getPropType(propValue);
+ if (propType !== expectedType) {
+ // `propValue` being instance of, say, date/regexp, pass the 'object'
+ // check, but we can offer a more precise error message here rather than
+ // 'of type `object`'.
+ var preciseType = getPreciseType(propValue);
+
+ return new PropTypeError(
+ 'Invalid ' + location + ' `' + propFullName + '` of type ' + ('`' + preciseType + '` supplied to `' + componentName + '`, expected ') + ('`' + expectedType + '`.'),
+ {expectedType: expectedType}
+ );
+ }
+ return null;
+ }
+ return createChainableTypeChecker(validate);
+ }
+
+ function createAnyTypeChecker() {
+ return createChainableTypeChecker(emptyFunctionThatReturnsNull);
+ }
+
+ function createArrayOfTypeChecker(typeChecker) {
+ function validate(props, propName, componentName, location, propFullName) {
+ if (typeof typeChecker !== 'function') {
+ return new PropTypeError('Property `' + propFullName + '` of component `' + componentName + '` has invalid PropType notation inside arrayOf.');
+ }
+ var propValue = props[propName];
+ if (!Array.isArray(propValue)) {
+ var propType = getPropType(propValue);
+ return new PropTypeError('Invalid ' + location + ' `' + propFullName + '` of type ' + ('`' + propType + '` supplied to `' + componentName + '`, expected an array.'));
+ }
+ for (var i = 0; i < propValue.length; i++) {
+ var error = typeChecker(propValue, i, componentName, location, propFullName + '[' + i + ']', ReactPropTypesSecret);
+ if (error instanceof Error) {
+ return error;
+ }
+ }
+ return null;
+ }
+ return createChainableTypeChecker(validate);
+ }
+
+ function createElementTypeChecker() {
+ function validate(props, propName, componentName, location, propFullName) {
+ var propValue = props[propName];
+ if (!isValidElement(propValue)) {
+ var propType = getPropType(propValue);
+ return new PropTypeError('Invalid ' + location + ' `' + propFullName + '` of type ' + ('`' + propType + '` supplied to `' + componentName + '`, expected a single ReactElement.'));
+ }
+ return null;
+ }
+ return createChainableTypeChecker(validate);
+ }
+
+ function createElementTypeTypeChecker() {
+ function validate(props, propName, componentName, location, propFullName) {
+ var propValue = props[propName];
+ if (!ReactIs.isValidElementType(propValue)) {
+ var propType = getPropType(propValue);
+ return new PropTypeError('Invalid ' + location + ' `' + propFullName + '` of type ' + ('`' + propType + '` supplied to `' + componentName + '`, expected a single ReactElement type.'));
+ }
+ return null;
+ }
+ return createChainableTypeChecker(validate);
+ }
+
+ function createInstanceTypeChecker(expectedClass) {
+ function validate(props, propName, componentName, location, propFullName) {
+ if (!(props[propName] instanceof expectedClass)) {
+ var expectedClassName = expectedClass.name || ANONYMOUS;
+ var actualClassName = getClassName(props[propName]);
+ return new PropTypeError('Invalid ' + location + ' `' + propFullName + '` of type ' + ('`' + actualClassName + '` supplied to `' + componentName + '`, expected ') + ('instance of `' + expectedClassName + '`.'));
+ }
+ return null;
+ }
+ return createChainableTypeChecker(validate);
+ }
+
+ function createEnumTypeChecker(expectedValues) {
+ if (!Array.isArray(expectedValues)) {
+ if (true) {
+ if (arguments.length > 1) {
+ printWarning(
+ 'Invalid arguments supplied to oneOf, expected an array, got ' + arguments.length + ' arguments. ' +
+ 'A common mistake is to write oneOf(x, y, z) instead of oneOf([x, y, z]).'
+ );
+ } else {
+ printWarning('Invalid argument supplied to oneOf, expected an array.');
+ }
+ }
+ return emptyFunctionThatReturnsNull;
+ }
+
+ function validate(props, propName, componentName, location, propFullName) {
+ var propValue = props[propName];
+ for (var i = 0; i < expectedValues.length; i++) {
+ if (is(propValue, expectedValues[i])) {
+ return null;
+ }
+ }
+
+ var valuesString = JSON.stringify(expectedValues, function replacer(key, value) {
+ var type = getPreciseType(value);
+ if (type === 'symbol') {
+ return String(value);
+ }
+ return value;
+ });
+ return new PropTypeError('Invalid ' + location + ' `' + propFullName + '` of value `' + String(propValue) + '` ' + ('supplied to `' + componentName + '`, expected one of ' + valuesString + '.'));
+ }
+ return createChainableTypeChecker(validate);
+ }
+
+ function createObjectOfTypeChecker(typeChecker) {
+ function validate(props, propName, componentName, location, propFullName) {
+ if (typeof typeChecker !== 'function') {
+ return new PropTypeError('Property `' + propFullName + '` of component `' + componentName + '` has invalid PropType notation inside objectOf.');
+ }
+ var propValue = props[propName];
+ var propType = getPropType(propValue);
+ if (propType !== 'object') {
+ return new PropTypeError('Invalid ' + location + ' `' + propFullName + '` of type ' + ('`' + propType + '` supplied to `' + componentName + '`, expected an object.'));
+ }
+ for (var key in propValue) {
+ if (has(propValue, key)) {
+ var error = typeChecker(propValue, key, componentName, location, propFullName + '.' + key, ReactPropTypesSecret);
+ if (error instanceof Error) {
+ return error;
+ }
+ }
+ }
+ return null;
+ }
+ return createChainableTypeChecker(validate);
+ }
+
+ function createUnionTypeChecker(arrayOfTypeCheckers) {
+ if (!Array.isArray(arrayOfTypeCheckers)) {
+ true ? printWarning('Invalid argument supplied to oneOfType, expected an instance of array.') : 0;
+ return emptyFunctionThatReturnsNull;
+ }
+
+ for (var i = 0; i < arrayOfTypeCheckers.length; i++) {
+ var checker = arrayOfTypeCheckers[i];
+ if (typeof checker !== 'function') {
+ printWarning(
+ 'Invalid argument supplied to oneOfType. Expected an array of check functions, but ' +
+ 'received ' + getPostfixForTypeWarning(checker) + ' at index ' + i + '.'
+ );
+ return emptyFunctionThatReturnsNull;
+ }
+ }
+
+ function validate(props, propName, componentName, location, propFullName) {
+ var expectedTypes = [];
+ for (var i = 0; i < arrayOfTypeCheckers.length; i++) {
+ var checker = arrayOfTypeCheckers[i];
+ var checkerResult = checker(props, propName, componentName, location, propFullName, ReactPropTypesSecret);
+ if (checkerResult == null) {
+ return null;
+ }
+ if (checkerResult.data && has(checkerResult.data, 'expectedType')) {
+ expectedTypes.push(checkerResult.data.expectedType);
+ }
+ }
+ var expectedTypesMessage = (expectedTypes.length > 0) ? ', expected one of type [' + expectedTypes.join(', ') + ']': '';
+ return new PropTypeError('Invalid ' + location + ' `' + propFullName + '` supplied to ' + ('`' + componentName + '`' + expectedTypesMessage + '.'));
+ }
+ return createChainableTypeChecker(validate);
+ }
+
+ function createNodeChecker() {
+ function validate(props, propName, componentName, location, propFullName) {
+ if (!isNode(props[propName])) {
+ return new PropTypeError('Invalid ' + location + ' `' + propFullName + '` supplied to ' + ('`' + componentName + '`, expected a ReactNode.'));
+ }
+ return null;
+ }
+ return createChainableTypeChecker(validate);
+ }
+
+ function invalidValidatorError(componentName, location, propFullName, key, type) {
+ return new PropTypeError(
+ (componentName || 'React class') + ': ' + location + ' type `' + propFullName + '.' + key + '` is invalid; ' +
+ 'it must be a function, usually from the `prop-types` package, but received `' + type + '`.'
+ );
+ }
+
+ function createShapeTypeChecker(shapeTypes) {
+ function validate(props, propName, componentName, location, propFullName) {
+ var propValue = props[propName];
+ var propType = getPropType(propValue);
+ if (propType !== 'object') {
+ return new PropTypeError('Invalid ' + location + ' `' + propFullName + '` of type `' + propType + '` ' + ('supplied to `' + componentName + '`, expected `object`.'));
+ }
+ for (var key in shapeTypes) {
+ var checker = shapeTypes[key];
+ if (typeof checker !== 'function') {
+ return invalidValidatorError(componentName, location, propFullName, key, getPreciseType(checker));
+ }
+ var error = checker(propValue, key, componentName, location, propFullName + '.' + key, ReactPropTypesSecret);
+ if (error) {
+ return error;
+ }
+ }
+ return null;
+ }
+ return createChainableTypeChecker(validate);
+ }
+
+ function createStrictShapeTypeChecker(shapeTypes) {
+ function validate(props, propName, componentName, location, propFullName) {
+ var propValue = props[propName];
+ var propType = getPropType(propValue);
+ if (propType !== 'object') {
+ return new PropTypeError('Invalid ' + location + ' `' + propFullName + '` of type `' + propType + '` ' + ('supplied to `' + componentName + '`, expected `object`.'));
+ }
+ // We need to check all keys in case some are required but missing from props.
+ var allKeys = assign({}, props[propName], shapeTypes);
+ for (var key in allKeys) {
+ var checker = shapeTypes[key];
+ if (has(shapeTypes, key) && typeof checker !== 'function') {
+ return invalidValidatorError(componentName, location, propFullName, key, getPreciseType(checker));
+ }
+ if (!checker) {
+ return new PropTypeError(
+ 'Invalid ' + location + ' `' + propFullName + '` key `' + key + '` supplied to `' + componentName + '`.' +
+ '\nBad object: ' + JSON.stringify(props[propName], null, ' ') +
+ '\nValid keys: ' + JSON.stringify(Object.keys(shapeTypes), null, ' ')
+ );
+ }
+ var error = checker(propValue, key, componentName, location, propFullName + '.' + key, ReactPropTypesSecret);
+ if (error) {
+ return error;
+ }
+ }
+ return null;
+ }
+
+ return createChainableTypeChecker(validate);
+ }
+
+ function isNode(propValue) {
+ switch (typeof propValue) {
+ case 'number':
+ case 'string':
+ case 'undefined':
+ return true;
+ case 'boolean':
+ return !propValue;
+ case 'object':
+ if (Array.isArray(propValue)) {
+ return propValue.every(isNode);
+ }
+ if (propValue === null || isValidElement(propValue)) {
+ return true;
+ }
+
+ var iteratorFn = getIteratorFn(propValue);
+ if (iteratorFn) {
+ var iterator = iteratorFn.call(propValue);
+ var step;
+ if (iteratorFn !== propValue.entries) {
+ while (!(step = iterator.next()).done) {
+ if (!isNode(step.value)) {
+ return false;
+ }
+ }
+ } else {
+ // Iterator will provide entry [k,v] tuples rather than values.
+ while (!(step = iterator.next()).done) {
+ var entry = step.value;
+ if (entry) {
+ if (!isNode(entry[1])) {
+ return false;
+ }
+ }
+ }
+ }
+ } else {
+ return false;
+ }
+
+ return true;
+ default:
+ return false;
+ }
+ }
+
+ function isSymbol(propType, propValue) {
+ // Native Symbol.
+ if (propType === 'symbol') {
+ return true;
+ }
+
+ // falsy value can't be a Symbol
+ if (!propValue) {
+ return false;
+ }
+
+ // 19.4.3.5 Symbol.prototype[@@toStringTag] === 'Symbol'
+ if (propValue['@@toStringTag'] === 'Symbol') {
+ return true;
+ }
+
+ // Fallback for non-spec compliant Symbols which are polyfilled.
+ if (typeof Symbol === 'function' && propValue instanceof Symbol) {
+ return true;
+ }
+
+ return false;
+ }
+
+ // Equivalent of `typeof` but with special handling for array and regexp.
+ function getPropType(propValue) {
+ var propType = typeof propValue;
+ if (Array.isArray(propValue)) {
+ return 'array';
+ }
+ if (propValue instanceof RegExp) {
+ // Old webkits (at least until Android 4.0) return 'function' rather than
+ // 'object' for typeof a RegExp. We'll normalize this here so that /bla/
+ // passes PropTypes.object.
+ return 'object';
+ }
+ if (isSymbol(propType, propValue)) {
+ return 'symbol';
+ }
+ return propType;
+ }
+
+ // This handles more types than `getPropType`. Only used for error messages.
+ // See `createPrimitiveTypeChecker`.
+ function getPreciseType(propValue) {
+ if (typeof propValue === 'undefined' || propValue === null) {
+ return '' + propValue;
+ }
+ var propType = getPropType(propValue);
+ if (propType === 'object') {
+ if (propValue instanceof Date) {
+ return 'date';
+ } else if (propValue instanceof RegExp) {
+ return 'regexp';
+ }
+ }
+ return propType;
+ }
+
+ // Returns a string that is postfixed to a warning about an invalid type.
+ // For example, "undefined" or "of type array"
+ function getPostfixForTypeWarning(value) {
+ var type = getPreciseType(value);
+ switch (type) {
+ case 'array':
+ case 'object':
+ return 'an ' + type;
+ case 'boolean':
+ case 'date':
+ case 'regexp':
+ return 'a ' + type;
+ default:
+ return type;
+ }
+ }
+
+ // Returns class name of the object, if any.
+ function getClassName(propValue) {
+ if (!propValue.constructor || !propValue.constructor.name) {
+ return ANONYMOUS;
+ }
+ return propValue.constructor.name;
+ }
+
+ ReactPropTypes.checkPropTypes = checkPropTypes;
+ ReactPropTypes.resetWarningCache = checkPropTypes.resetWarningCache;
+ ReactPropTypes.PropTypes = ReactPropTypes;
+
+ return ReactPropTypes;
+};
+
+
+/***/ }),
+
+/***/ "./node_modules/prop-types/index.js":
+/*!******************************************!*\
+ !*** ./node_modules/prop-types/index.js ***!
+ \******************************************/
+/***/ ((module, __unused_webpack_exports, __webpack_require__) => {
+
+/**
+ * Copyright (c) 2013-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+if (true) {
+ var ReactIs = __webpack_require__(/*! react-is */ "./node_modules/react-is/index.js");
+
+ // By explicitly using `prop-types` you are opting into new development behavior.
+ // http://fb.me/prop-types-in-prod
+ var throwOnDirectAccess = true;
+ module.exports = __webpack_require__(/*! ./factoryWithTypeCheckers */ "./node_modules/prop-types/factoryWithTypeCheckers.js")(ReactIs.isElement, throwOnDirectAccess);
+} else {}
+
+
+/***/ }),
+
+/***/ "./node_modules/prop-types/lib/ReactPropTypesSecret.js":
+/*!*************************************************************!*\
+ !*** ./node_modules/prop-types/lib/ReactPropTypesSecret.js ***!
+ \*************************************************************/
+/***/ ((module) => {
+
+"use strict";
+/**
+ * Copyright (c) 2013-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+
+
+var ReactPropTypesSecret = 'SECRET_DO_NOT_PASS_THIS_OR_YOU_WILL_BE_FIRED';
+
+module.exports = ReactPropTypesSecret;
+
+
+/***/ }),
+
+/***/ "./node_modules/prop-types/lib/has.js":
+/*!********************************************!*\
+ !*** ./node_modules/prop-types/lib/has.js ***!
+ \********************************************/
+/***/ ((module) => {
+
+module.exports = Function.call.bind(Object.prototype.hasOwnProperty);
+
+
+/***/ }),
+
+/***/ "./node_modules/raven-js/src/configError.js":
+/*!**************************************************!*\
+ !*** ./node_modules/raven-js/src/configError.js ***!
+ \**************************************************/
+/***/ ((module) => {
+
+function RavenConfigError(message) {
+ this.name = 'RavenConfigError';
+ this.message = message;
+}
+RavenConfigError.prototype = new Error();
+RavenConfigError.prototype.constructor = RavenConfigError;
+
+module.exports = RavenConfigError;
+
+
+/***/ }),
+
+/***/ "./node_modules/raven-js/src/console.js":
+/*!**********************************************!*\
+ !*** ./node_modules/raven-js/src/console.js ***!
+ \**********************************************/
+/***/ ((module) => {
+
+var wrapMethod = function(console, level, callback) {
+ var originalConsoleLevel = console[level];
+ var originalConsole = console;
+
+ if (!(level in console)) {
+ return;
+ }
+
+ var sentryLevel = level === 'warn' ? 'warning' : level;
+
+ console[level] = function() {
+ var args = [].slice.call(arguments);
+
+ var msg = '' + args.join(' ');
+ var data = {level: sentryLevel, logger: 'console', extra: {arguments: args}};
+
+ if (level === 'assert') {
+ if (args[0] === false) {
+ // Default browsers message
+ msg = 'Assertion failed: ' + (args.slice(1).join(' ') || 'console.assert');
+ data.extra.arguments = args.slice(1);
+ callback && callback(msg, data);
+ }
+ } else {
+ callback && callback(msg, data);
+ }
+
+ // this fails for some browsers. :(
+ if (originalConsoleLevel) {
+ // IE9 doesn't allow calling apply on console functions directly
+ // See: https://stackoverflow.com/questions/5472938/does-ie9-support-console-log-and-is-it-a-real-function#answer-5473193
+ Function.prototype.apply.call(originalConsoleLevel, originalConsole, args);
+ }
+ };
+};
+
+module.exports = {
+ wrapMethod: wrapMethod
+};
+
+
+/***/ }),
+
+/***/ "./node_modules/raven-js/src/raven.js":
+/*!********************************************!*\
+ !*** ./node_modules/raven-js/src/raven.js ***!
+ \********************************************/
+/***/ ((module, __unused_webpack_exports, __webpack_require__) => {
+
+/*global XDomainRequest:false */
+
+var TraceKit = __webpack_require__(/*! ../vendor/TraceKit/tracekit */ "./node_modules/raven-js/vendor/TraceKit/tracekit.js");
+var stringify = __webpack_require__(/*! ../vendor/json-stringify-safe/stringify */ "./node_modules/raven-js/vendor/json-stringify-safe/stringify.js");
+var RavenConfigError = __webpack_require__(/*! ./configError */ "./node_modules/raven-js/src/configError.js");
+
+var utils = __webpack_require__(/*! ./utils */ "./node_modules/raven-js/src/utils.js");
+var isError = utils.isError;
+var isObject = utils.isObject;
+var isObject = utils.isObject;
+var isErrorEvent = utils.isErrorEvent;
+var isUndefined = utils.isUndefined;
+var isFunction = utils.isFunction;
+var isString = utils.isString;
+var isEmptyObject = utils.isEmptyObject;
+var each = utils.each;
+var objectMerge = utils.objectMerge;
+var truncate = utils.truncate;
+var objectFrozen = utils.objectFrozen;
+var hasKey = utils.hasKey;
+var joinRegExp = utils.joinRegExp;
+var urlencode = utils.urlencode;
+var uuid4 = utils.uuid4;
+var htmlTreeAsString = utils.htmlTreeAsString;
+var isSameException = utils.isSameException;
+var isSameStacktrace = utils.isSameStacktrace;
+var parseUrl = utils.parseUrl;
+var fill = utils.fill;
+
+var wrapConsoleMethod = (__webpack_require__(/*! ./console */ "./node_modules/raven-js/src/console.js").wrapMethod);
+
+var dsnKeys = 'source protocol user pass host port path'.split(' '),
+ dsnPattern = /^(?:(\w+):)?\/\/(?:(\w+)(:\w+)?@)?([\w\.-]+)(?::(\d+))?(\/.*)/;
+
+function now() {
+ return +new Date();
+}
+
+// This is to be defensive in environments where window does not exist (see https://github.com/getsentry/raven-js/pull/785)
+var _window =
+ typeof window !== 'undefined'
+ ? window
+ : typeof __webpack_require__.g !== 'undefined' ? __webpack_require__.g : typeof self !== 'undefined' ? self : {};
+var _document = _window.document;
+var _navigator = _window.navigator;
+
+function keepOriginalCallback(original, callback) {
+ return isFunction(callback)
+ ? function(data) {
+ return callback(data, original);
+ }
+ : callback;
+}
+
+// First, check for JSON support
+// If there is no JSON, we no-op the core features of Raven
+// since JSON is required to encode the payload
+function Raven() {
+ this._hasJSON = !!(typeof JSON === 'object' && JSON.stringify);
+ // Raven can run in contexts where there's no document (react-native)
+ this._hasDocument = !isUndefined(_document);
+ this._hasNavigator = !isUndefined(_navigator);
+ this._lastCapturedException = null;
+ this._lastData = null;
+ this._lastEventId = null;
+ this._globalServer = null;
+ this._globalKey = null;
+ this._globalProject = null;
+ this._globalContext = {};
+ this._globalOptions = {
+ logger: 'javascript',
+ ignoreErrors: [],
+ ignoreUrls: [],
+ whitelistUrls: [],
+ includePaths: [],
+ collectWindowErrors: true,
+ maxMessageLength: 0,
+
+ // By default, truncates URL values to 250 chars
+ maxUrlLength: 250,
+ stackTraceLimit: 50,
+ autoBreadcrumbs: true,
+ instrument: true,
+ sampleRate: 1
+ };
+ this._ignoreOnError = 0;
+ this._isRavenInstalled = false;
+ this._originalErrorStackTraceLimit = Error.stackTraceLimit;
+ // capture references to window.console *and* all its methods first
+ // before the console plugin has a chance to monkey patch
+ this._originalConsole = _window.console || {};
+ this._originalConsoleMethods = {};
+ this._plugins = [];
+ this._startTime = now();
+ this._wrappedBuiltIns = [];
+ this._breadcrumbs = [];
+ this._lastCapturedEvent = null;
+ this._keypressTimeout;
+ this._location = _window.location;
+ this._lastHref = this._location && this._location.href;
+ this._resetBackoff();
+
+ // eslint-disable-next-line guard-for-in
+ for (var method in this._originalConsole) {
+ this._originalConsoleMethods[method] = this._originalConsole[method];
+ }
+}
+
+/*
+ * The core Raven singleton
+ *
+ * @this {Raven}
+ */
+
+Raven.prototype = {
+ // Hardcode version string so that raven source can be loaded directly via
+ // webpack (using a build step causes webpack #1617). Grunt verifies that
+ // this value matches package.json during build.
+ // See: https://github.com/getsentry/raven-js/issues/465
+ VERSION: '3.19.1',
+
+ debug: false,
+
+ TraceKit: TraceKit, // alias to TraceKit
+
+ /*
+ * Configure Raven with a DSN and extra options
+ *
+ * @param {string} dsn The public Sentry DSN
+ * @param {object} options Set of global options [optional]
+ * @return {Raven}
+ */
+ config: function(dsn, options) {
+ var self = this;
+
+ if (self._globalServer) {
+ this._logDebug('error', 'Error: Raven has already been configured');
+ return self;
+ }
+ if (!dsn) return self;
+
+ var globalOptions = self._globalOptions;
+
+ // merge in options
+ if (options) {
+ each(options, function(key, value) {
+ // tags and extra are special and need to be put into context
+ if (key === 'tags' || key === 'extra' || key === 'user') {
+ self._globalContext[key] = value;
+ } else {
+ globalOptions[key] = value;
+ }
+ });
+ }
+
+ self.setDSN(dsn);
+
+ // "Script error." is hard coded into browsers for errors that it can't read.
+ // this is the result of a script being pulled in from an external domain and CORS.
+ globalOptions.ignoreErrors.push(/^Script error\.?$/);
+ globalOptions.ignoreErrors.push(/^Javascript error: Script error\.? on line 0$/);
+
+ // join regexp rules into one big rule
+ globalOptions.ignoreErrors = joinRegExp(globalOptions.ignoreErrors);
+ globalOptions.ignoreUrls = globalOptions.ignoreUrls.length
+ ? joinRegExp(globalOptions.ignoreUrls)
+ : false;
+ globalOptions.whitelistUrls = globalOptions.whitelistUrls.length
+ ? joinRegExp(globalOptions.whitelistUrls)
+ : false;
+ globalOptions.includePaths = joinRegExp(globalOptions.includePaths);
+ globalOptions.maxBreadcrumbs = Math.max(
+ 0,
+ Math.min(globalOptions.maxBreadcrumbs || 100, 100)
+ ); // default and hard limit is 100
+
+ var autoBreadcrumbDefaults = {
+ xhr: true,
+ console: true,
+ dom: true,
+ location: true
+ };
+
+ var autoBreadcrumbs = globalOptions.autoBreadcrumbs;
+ if ({}.toString.call(autoBreadcrumbs) === '[object Object]') {
+ autoBreadcrumbs = objectMerge(autoBreadcrumbDefaults, autoBreadcrumbs);
+ } else if (autoBreadcrumbs !== false) {
+ autoBreadcrumbs = autoBreadcrumbDefaults;
+ }
+ globalOptions.autoBreadcrumbs = autoBreadcrumbs;
+
+ var instrumentDefaults = {
+ tryCatch: true
+ };
+
+ var instrument = globalOptions.instrument;
+ if ({}.toString.call(instrument) === '[object Object]') {
+ instrument = objectMerge(instrumentDefaults, instrument);
+ } else if (instrument !== false) {
+ instrument = instrumentDefaults;
+ }
+ globalOptions.instrument = instrument;
+
+ TraceKit.collectWindowErrors = !!globalOptions.collectWindowErrors;
+
+ // return for chaining
+ return self;
+ },
+
+ /*
+ * Installs a global window.onerror error handler
+ * to capture and report uncaught exceptions.
+ * At this point, install() is required to be called due
+ * to the way TraceKit is set up.
+ *
+ * @return {Raven}
+ */
+ install: function() {
+ var self = this;
+ if (self.isSetup() && !self._isRavenInstalled) {
+ TraceKit.report.subscribe(function() {
+ self._handleOnErrorStackInfo.apply(self, arguments);
+ });
+ if (self._globalOptions.instrument && self._globalOptions.instrument.tryCatch) {
+ self._instrumentTryCatch();
+ }
+
+ if (self._globalOptions.autoBreadcrumbs) self._instrumentBreadcrumbs();
+
+ // Install all of the plugins
+ self._drainPlugins();
+
+ self._isRavenInstalled = true;
+ }
+
+ Error.stackTraceLimit = self._globalOptions.stackTraceLimit;
+ return this;
+ },
+
+ /*
+ * Set the DSN (can be called multiple time unlike config)
+ *
+ * @param {string} dsn The public Sentry DSN
+ */
+ setDSN: function(dsn) {
+ var self = this,
+ uri = self._parseDSN(dsn),
+ lastSlash = uri.path.lastIndexOf('/'),
+ path = uri.path.substr(1, lastSlash);
+
+ self._dsn = dsn;
+ self._globalKey = uri.user;
+ self._globalSecret = uri.pass && uri.pass.substr(1);
+ self._globalProject = uri.path.substr(lastSlash + 1);
+
+ self._globalServer = self._getGlobalServer(uri);
+
+ self._globalEndpoint =
+ self._globalServer + '/' + path + 'api/' + self._globalProject + '/store/';
+
+ // Reset backoff state since we may be pointing at a
+ // new project/server
+ this._resetBackoff();
+ },
+
+ /*
+ * Wrap code within a context so Raven can capture errors
+ * reliably across domains that is executed immediately.
+ *
+ * @param {object} options A specific set of options for this context [optional]
+ * @param {function} func The callback to be immediately executed within the context
+ * @param {array} args An array of arguments to be called with the callback [optional]
+ */
+ context: function(options, func, args) {
+ if (isFunction(options)) {
+ args = func || [];
+ func = options;
+ options = undefined;
+ }
+
+ return this.wrap(options, func).apply(this, args);
+ },
+
+ /*
+ * Wrap code within a context and returns back a new function to be executed
+ *
+ * @param {object} options A specific set of options for this context [optional]
+ * @param {function} func The function to be wrapped in a new context
+ * @param {function} func A function to call before the try/catch wrapper [optional, private]
+ * @return {function} The newly wrapped functions with a context
+ */
+ wrap: function(options, func, _before) {
+ var self = this;
+ // 1 argument has been passed, and it's not a function
+ // so just return it
+ if (isUndefined(func) && !isFunction(options)) {
+ return options;
+ }
+
+ // options is optional
+ if (isFunction(options)) {
+ func = options;
+ options = undefined;
+ }
+
+ // At this point, we've passed along 2 arguments, and the second one
+ // is not a function either, so we'll just return the second argument.
+ if (!isFunction(func)) {
+ return func;
+ }
+
+ // We don't wanna wrap it twice!
+ try {
+ if (func.__raven__) {
+ return func;
+ }
+
+ // If this has already been wrapped in the past, return that
+ if (func.__raven_wrapper__) {
+ return func.__raven_wrapper__;
+ }
+ } catch (e) {
+ // Just accessing custom props in some Selenium environments
+ // can cause a "Permission denied" exception (see raven-js#495).
+ // Bail on wrapping and return the function as-is (defers to window.onerror).
+ return func;
+ }
+
+ function wrapped() {
+ var args = [],
+ i = arguments.length,
+ deep = !options || (options && options.deep !== false);
+
+ if (_before && isFunction(_before)) {
+ _before.apply(this, arguments);
+ }
+
+ // Recursively wrap all of a function's arguments that are
+ // functions themselves.
+ while (i--) args[i] = deep ? self.wrap(options, arguments[i]) : arguments[i];
+
+ try {
+ // Attempt to invoke user-land function
+ // NOTE: If you are a Sentry user, and you are seeing this stack frame, it
+ // means Raven caught an error invoking your application code. This is
+ // expected behavior and NOT indicative of a bug with Raven.js.
+ return func.apply(this, args);
+ } catch (e) {
+ self._ignoreNextOnError();
+ self.captureException(e, options);
+ throw e;
+ }
+ }
+
+ // copy over properties of the old function
+ for (var property in func) {
+ if (hasKey(func, property)) {
+ wrapped[property] = func[property];
+ }
+ }
+ wrapped.prototype = func.prototype;
+
+ func.__raven_wrapper__ = wrapped;
+ // Signal that this function has been wrapped already
+ // for both debugging and to prevent it to being wrapped twice
+ wrapped.__raven__ = true;
+ wrapped.__inner__ = func;
+
+ return wrapped;
+ },
+
+ /*
+ * Uninstalls the global error handler.
+ *
+ * @return {Raven}
+ */
+ uninstall: function() {
+ TraceKit.report.uninstall();
+
+ this._restoreBuiltIns();
+
+ Error.stackTraceLimit = this._originalErrorStackTraceLimit;
+ this._isRavenInstalled = false;
+
+ return this;
+ },
+
+ /*
+ * Manually capture an exception and send it over to Sentry
+ *
+ * @param {error} ex An exception to be logged
+ * @param {object} options A specific set of options for this error [optional]
+ * @return {Raven}
+ */
+ captureException: function(ex, options) {
+ // Cases for sending ex as a message, rather than an exception
+ var isNotError = !isError(ex);
+ var isNotErrorEvent = !isErrorEvent(ex);
+ var isErrorEventWithoutError = isErrorEvent(ex) && !ex.error;
+
+ if ((isNotError && isNotErrorEvent) || isErrorEventWithoutError) {
+ return this.captureMessage(
+ ex,
+ objectMerge(
+ {
+ trimHeadFrames: 1,
+ stacktrace: true // if we fall back to captureMessage, default to attempting a new trace
+ },
+ options
+ )
+ );
+ }
+
+ // Get actual Error from ErrorEvent
+ if (isErrorEvent(ex)) ex = ex.error;
+
+ // Store the raw exception object for potential debugging and introspection
+ this._lastCapturedException = ex;
+
+ // TraceKit.report will re-raise any exception passed to it,
+ // which means you have to wrap it in try/catch. Instead, we
+ // can wrap it here and only re-raise if TraceKit.report
+ // raises an exception different from the one we asked to
+ // report on.
+ try {
+ var stack = TraceKit.computeStackTrace(ex);
+ this._handleStackInfo(stack, options);
+ } catch (ex1) {
+ if (ex !== ex1) {
+ throw ex1;
+ }
+ }
+
+ return this;
+ },
+
+ /*
+ * Manually send a message to Sentry
+ *
+ * @param {string} msg A plain message to be captured in Sentry
+ * @param {object} options A specific set of options for this message [optional]
+ * @return {Raven}
+ */
+ captureMessage: function(msg, options) {
+ // config() automagically converts ignoreErrors from a list to a RegExp so we need to test for an
+ // early call; we'll error on the side of logging anything called before configuration since it's
+ // probably something you should see:
+ if (
+ !!this._globalOptions.ignoreErrors.test &&
+ this._globalOptions.ignoreErrors.test(msg)
+ ) {
+ return;
+ }
+
+ options = options || {};
+
+ var data = objectMerge(
+ {
+ message: msg + '' // Make sure it's actually a string
+ },
+ options
+ );
+
+ var ex;
+ // Generate a "synthetic" stack trace from this point.
+ // NOTE: If you are a Sentry user, and you are seeing this stack frame, it is NOT indicative
+ // of a bug with Raven.js. Sentry generates synthetic traces either by configuration,
+ // or if it catches a thrown object without a "stack" property.
+ try {
+ throw new Error(msg);
+ } catch (ex1) {
+ ex = ex1;
+ }
+
+ // null exception name so `Error` isn't prefixed to msg
+ ex.name = null;
+ var stack = TraceKit.computeStackTrace(ex);
+
+ // stack[0] is `throw new Error(msg)` call itself, we are interested in the frame that was just before that, stack[1]
+ var initialCall = stack.stack[1];
+
+ var fileurl = (initialCall && initialCall.url) || '';
+
+ if (
+ !!this._globalOptions.ignoreUrls.test &&
+ this._globalOptions.ignoreUrls.test(fileurl)
+ ) {
+ return;
+ }
+
+ if (
+ !!this._globalOptions.whitelistUrls.test &&
+ !this._globalOptions.whitelistUrls.test(fileurl)
+ ) {
+ return;
+ }
+
+ if (this._globalOptions.stacktrace || (options && options.stacktrace)) {
+ options = objectMerge(
+ {
+ // fingerprint on msg, not stack trace (legacy behavior, could be
+ // revisited)
+ fingerprint: msg,
+ // since we know this is a synthetic trace, the top N-most frames
+ // MUST be from Raven.js, so mark them as in_app later by setting
+ // trimHeadFrames
+ trimHeadFrames: (options.trimHeadFrames || 0) + 1
+ },
+ options
+ );
+
+ var frames = this._prepareFrames(stack, options);
+ data.stacktrace = {
+ // Sentry expects frames oldest to newest
+ frames: frames.reverse()
+ };
+ }
+
+ // Fire away!
+ this._send(data);
+
+ return this;
+ },
+
+ captureBreadcrumb: function(obj) {
+ var crumb = objectMerge(
+ {
+ timestamp: now() / 1000
+ },
+ obj
+ );
+
+ if (isFunction(this._globalOptions.breadcrumbCallback)) {
+ var result = this._globalOptions.breadcrumbCallback(crumb);
+
+ if (isObject(result) && !isEmptyObject(result)) {
+ crumb = result;
+ } else if (result === false) {
+ return this;
+ }
+ }
+
+ this._breadcrumbs.push(crumb);
+ if (this._breadcrumbs.length > this._globalOptions.maxBreadcrumbs) {
+ this._breadcrumbs.shift();
+ }
+ return this;
+ },
+
+ addPlugin: function(plugin /*arg1, arg2, ... argN*/) {
+ var pluginArgs = [].slice.call(arguments, 1);
+
+ this._plugins.push([plugin, pluginArgs]);
+ if (this._isRavenInstalled) {
+ this._drainPlugins();
+ }
+
+ return this;
+ },
+
+ /*
+ * Set/clear a user to be sent along with the payload.
+ *
+ * @param {object} user An object representing user data [optional]
+ * @return {Raven}
+ */
+ setUserContext: function(user) {
+ // Intentionally do not merge here since that's an unexpected behavior.
+ this._globalContext.user = user;
+
+ return this;
+ },
+
+ /*
+ * Merge extra attributes to be sent along with the payload.
+ *
+ * @param {object} extra An object representing extra data [optional]
+ * @return {Raven}
+ */
+ setExtraContext: function(extra) {
+ this._mergeContext('extra', extra);
+
+ return this;
+ },
+
+ /*
+ * Merge tags to be sent along with the payload.
+ *
+ * @param {object} tags An object representing tags [optional]
+ * @return {Raven}
+ */
+ setTagsContext: function(tags) {
+ this._mergeContext('tags', tags);
+
+ return this;
+ },
+
+ /*
+ * Clear all of the context.
+ *
+ * @return {Raven}
+ */
+ clearContext: function() {
+ this._globalContext = {};
+
+ return this;
+ },
+
+ /*
+ * Get a copy of the current context. This cannot be mutated.
+ *
+ * @return {object} copy of context
+ */
+ getContext: function() {
+ // lol javascript
+ return JSON.parse(stringify(this._globalContext));
+ },
+
+ /*
+ * Set environment of application
+ *
+ * @param {string} environment Typically something like 'production'.
+ * @return {Raven}
+ */
+ setEnvironment: function(environment) {
+ this._globalOptions.environment = environment;
+
+ return this;
+ },
+
+ /*
+ * Set release version of application
+ *
+ * @param {string} release Typically something like a git SHA to identify version
+ * @return {Raven}
+ */
+ setRelease: function(release) {
+ this._globalOptions.release = release;
+
+ return this;
+ },
+
+ /*
+ * Set the dataCallback option
+ *
+ * @param {function} callback The callback to run which allows the
+ * data blob to be mutated before sending
+ * @return {Raven}
+ */
+ setDataCallback: function(callback) {
+ var original = this._globalOptions.dataCallback;
+ this._globalOptions.dataCallback = keepOriginalCallback(original, callback);
+ return this;
+ },
+
+ /*
+ * Set the breadcrumbCallback option
+ *
+ * @param {function} callback The callback to run which allows filtering
+ * or mutating breadcrumbs
+ * @return {Raven}
+ */
+ setBreadcrumbCallback: function(callback) {
+ var original = this._globalOptions.breadcrumbCallback;
+ this._globalOptions.breadcrumbCallback = keepOriginalCallback(original, callback);
+ return this;
+ },
+
+ /*
+ * Set the shouldSendCallback option
+ *
+ * @param {function} callback The callback to run which allows
+ * introspecting the blob before sending
+ * @return {Raven}
+ */
+ setShouldSendCallback: function(callback) {
+ var original = this._globalOptions.shouldSendCallback;
+ this._globalOptions.shouldSendCallback = keepOriginalCallback(original, callback);
+ return this;
+ },
+
+ /**
+ * Override the default HTTP transport mechanism that transmits data
+ * to the Sentry server.
+ *
+ * @param {function} transport Function invoked instead of the default
+ * `makeRequest` handler.
+ *
+ * @return {Raven}
+ */
+ setTransport: function(transport) {
+ this._globalOptions.transport = transport;
+
+ return this;
+ },
+
+ /*
+ * Get the latest raw exception that was captured by Raven.
+ *
+ * @return {error}
+ */
+ lastException: function() {
+ return this._lastCapturedException;
+ },
+
+ /*
+ * Get the last event id
+ *
+ * @return {string}
+ */
+ lastEventId: function() {
+ return this._lastEventId;
+ },
+
+ /*
+ * Determine if Raven is setup and ready to go.
+ *
+ * @return {boolean}
+ */
+ isSetup: function() {
+ if (!this._hasJSON) return false; // needs JSON support
+ if (!this._globalServer) {
+ if (!this.ravenNotConfiguredError) {
+ this.ravenNotConfiguredError = true;
+ this._logDebug('error', 'Error: Raven has not been configured.');
+ }
+ return false;
+ }
+ return true;
+ },
+
+ afterLoad: function() {
+ // TODO: remove window dependence?
+
+ // Attempt to initialize Raven on load
+ var RavenConfig = _window.RavenConfig;
+ if (RavenConfig) {
+ this.config(RavenConfig.dsn, RavenConfig.config).install();
+ }
+ },
+
+ showReportDialog: function(options) {
+ if (
+ !_document // doesn't work without a document (React native)
+ )
+ return;
+
+ options = options || {};
+
+ var lastEventId = options.eventId || this.lastEventId();
+ if (!lastEventId) {
+ throw new RavenConfigError('Missing eventId');
+ }
+
+ var dsn = options.dsn || this._dsn;
+ if (!dsn) {
+ throw new RavenConfigError('Missing DSN');
+ }
+
+ var encode = encodeURIComponent;
+ var qs = '';
+ qs += '?eventId=' + encode(lastEventId);
+ qs += '&dsn=' + encode(dsn);
+
+ var user = options.user || this._globalContext.user;
+ if (user) {
+ if (user.name) qs += '&name=' + encode(user.name);
+ if (user.email) qs += '&email=' + encode(user.email);
+ }
+
+ var globalServer = this._getGlobalServer(this._parseDSN(dsn));
+
+ var script = _document.createElement('script');
+ script.async = true;
+ script.src = globalServer + '/api/embed/error-page/' + qs;
+ (_document.head || _document.body).appendChild(script);
+ },
+
+ /**** Private functions ****/
+ _ignoreNextOnError: function() {
+ var self = this;
+ this._ignoreOnError += 1;
+ setTimeout(function() {
+ // onerror should trigger before setTimeout
+ self._ignoreOnError -= 1;
+ });
+ },
+
+ _triggerEvent: function(eventType, options) {
+ // NOTE: `event` is a native browser thing, so let's avoid conflicting wiht it
+ var evt, key;
+
+ if (!this._hasDocument) return;
+
+ options = options || {};
+
+ eventType = 'raven' + eventType.substr(0, 1).toUpperCase() + eventType.substr(1);
+
+ if (_document.createEvent) {
+ evt = _document.createEvent('HTMLEvents');
+ evt.initEvent(eventType, true, true);
+ } else {
+ evt = _document.createEventObject();
+ evt.eventType = eventType;
+ }
+
+ for (key in options)
+ if (hasKey(options, key)) {
+ evt[key] = options[key];
+ }
+
+ if (_document.createEvent) {
+ // IE9 if standards
+ _document.dispatchEvent(evt);
+ } else {
+ // IE8 regardless of Quirks or Standards
+ // IE9 if quirks
+ try {
+ _document.fireEvent('on' + evt.eventType.toLowerCase(), evt);
+ } catch (e) {
+ // Do nothing
+ }
+ }
+ },
+
+ /**
+ * Wraps addEventListener to capture UI breadcrumbs
+ * @param evtName the event name (e.g. "click")
+ * @returns {Function}
+ * @private
+ */
+ _breadcrumbEventHandler: function(evtName) {
+ var self = this;
+ return function(evt) {
+ // reset keypress timeout; e.g. triggering a 'click' after
+ // a 'keypress' will reset the keypress debounce so that a new
+ // set of keypresses can be recorded
+ self._keypressTimeout = null;
+
+ // It's possible this handler might trigger multiple times for the same
+ // event (e.g. event propagation through node ancestors). Ignore if we've
+ // already captured the event.
+ if (self._lastCapturedEvent === evt) return;
+
+ self._lastCapturedEvent = evt;
+
+ // try/catch both:
+ // - accessing evt.target (see getsentry/raven-js#838, #768)
+ // - `htmlTreeAsString` because it's complex, and just accessing the DOM incorrectly
+ // can throw an exception in some circumstances.
+ var target;
+ try {
+ target = htmlTreeAsString(evt.target);
+ } catch (e) {
+ target = '';
+ }
+
+ self.captureBreadcrumb({
+ category: 'ui.' + evtName, // e.g. ui.click, ui.input
+ message: target
+ });
+ };
+ },
+
+ /**
+ * Wraps addEventListener to capture keypress UI events
+ * @returns {Function}
+ * @private
+ */
+ _keypressEventHandler: function() {
+ var self = this,
+ debounceDuration = 1000; // milliseconds
+
+ // TODO: if somehow user switches keypress target before
+ // debounce timeout is triggered, we will only capture
+ // a single breadcrumb from the FIRST target (acceptable?)
+ return function(evt) {
+ var target;
+ try {
+ target = evt.target;
+ } catch (e) {
+ // just accessing event properties can throw an exception in some rare circumstances
+ // see: https://github.com/getsentry/raven-js/issues/838
+ return;
+ }
+ var tagName = target && target.tagName;
+
+ // only consider keypress events on actual input elements
+ // this will disregard keypresses targeting body (e.g. tabbing
+ // through elements, hotkeys, etc)
+ if (
+ !tagName ||
+ (tagName !== 'INPUT' && tagName !== 'TEXTAREA' && !target.isContentEditable)
+ )
+ return;
+
+ // record first keypress in a series, but ignore subsequent
+ // keypresses until debounce clears
+ var timeout = self._keypressTimeout;
+ if (!timeout) {
+ self._breadcrumbEventHandler('input')(evt);
+ }
+ clearTimeout(timeout);
+ self._keypressTimeout = setTimeout(function() {
+ self._keypressTimeout = null;
+ }, debounceDuration);
+ };
+ },
+
+ /**
+ * Captures a breadcrumb of type "navigation", normalizing input URLs
+ * @param to the originating URL
+ * @param from the target URL
+ * @private
+ */
+ _captureUrlChange: function(from, to) {
+ var parsedLoc = parseUrl(this._location.href);
+ var parsedTo = parseUrl(to);
+ var parsedFrom = parseUrl(from);
+
+ // because onpopstate only tells you the "new" (to) value of location.href, and
+ // not the previous (from) value, we need to track the value of the current URL
+ // state ourselves
+ this._lastHref = to;
+
+ // Use only the path component of the URL if the URL matches the current
+ // document (almost all the time when using pushState)
+ if (parsedLoc.protocol === parsedTo.protocol && parsedLoc.host === parsedTo.host)
+ to = parsedTo.relative;
+ if (parsedLoc.protocol === parsedFrom.protocol && parsedLoc.host === parsedFrom.host)
+ from = parsedFrom.relative;
+
+ this.captureBreadcrumb({
+ category: 'navigation',
+ data: {
+ to: to,
+ from: from
+ }
+ });
+ },
+
+ /**
+ * Wrap timer functions and event targets to catch errors and provide
+ * better metadata.
+ */
+ _instrumentTryCatch: function() {
+ var self = this;
+
+ var wrappedBuiltIns = self._wrappedBuiltIns;
+
+ function wrapTimeFn(orig) {
+ return function(fn, t) {
+ // preserve arity
+ // Make a copy of the arguments to prevent deoptimization
+ // https://github.com/petkaantonov/bluebird/wiki/Optimization-killers#32-leaking-arguments
+ var args = new Array(arguments.length);
+ for (var i = 0; i < args.length; ++i) {
+ args[i] = arguments[i];
+ }
+ var originalCallback = args[0];
+ if (isFunction(originalCallback)) {
+ args[0] = self.wrap(originalCallback);
+ }
+
+ // IE < 9 doesn't support .call/.apply on setInterval/setTimeout, but it
+ // also supports only two arguments and doesn't care what this is, so we
+ // can just call the original function directly.
+ if (orig.apply) {
+ return orig.apply(this, args);
+ } else {
+ return orig(args[0], args[1]);
+ }
+ };
+ }
+
+ var autoBreadcrumbs = this._globalOptions.autoBreadcrumbs;
+
+ function wrapEventTarget(global) {
+ var proto = _window[global] && _window[global].prototype;
+ if (proto && proto.hasOwnProperty && proto.hasOwnProperty('addEventListener')) {
+ fill(
+ proto,
+ 'addEventListener',
+ function(orig) {
+ return function(evtName, fn, capture, secure) {
+ // preserve arity
+ try {
+ if (fn && fn.handleEvent) {
+ fn.handleEvent = self.wrap(fn.handleEvent);
+ }
+ } catch (err) {
+ // can sometimes get 'Permission denied to access property "handle Event'
+ }
+
+ // More breadcrumb DOM capture ... done here and not in `_instrumentBreadcrumbs`
+ // so that we don't have more than one wrapper function
+ var before, clickHandler, keypressHandler;
+
+ if (
+ autoBreadcrumbs &&
+ autoBreadcrumbs.dom &&
+ (global === 'EventTarget' || global === 'Node')
+ ) {
+ // NOTE: generating multiple handlers per addEventListener invocation, should
+ // revisit and verify we can just use one (almost certainly)
+ clickHandler = self._breadcrumbEventHandler('click');
+ keypressHandler = self._keypressEventHandler();
+ before = function(evt) {
+ // need to intercept every DOM event in `before` argument, in case that
+ // same wrapped method is re-used for different events (e.g. mousemove THEN click)
+ // see #724
+ if (!evt) return;
+
+ var eventType;
+ try {
+ eventType = evt.type;
+ } catch (e) {
+ // just accessing event properties can throw an exception in some rare circumstances
+ // see: https://github.com/getsentry/raven-js/issues/838
+ return;
+ }
+ if (eventType === 'click') return clickHandler(evt);
+ else if (eventType === 'keypress') return keypressHandler(evt);
+ };
+ }
+ return orig.call(
+ this,
+ evtName,
+ self.wrap(fn, undefined, before),
+ capture,
+ secure
+ );
+ };
+ },
+ wrappedBuiltIns
+ );
+ fill(
+ proto,
+ 'removeEventListener',
+ function(orig) {
+ return function(evt, fn, capture, secure) {
+ try {
+ fn = fn && (fn.__raven_wrapper__ ? fn.__raven_wrapper__ : fn);
+ } catch (e) {
+ // ignore, accessing __raven_wrapper__ will throw in some Selenium environments
+ }
+ return orig.call(this, evt, fn, capture, secure);
+ };
+ },
+ wrappedBuiltIns
+ );
+ }
+ }
+
+ fill(_window, 'setTimeout', wrapTimeFn, wrappedBuiltIns);
+ fill(_window, 'setInterval', wrapTimeFn, wrappedBuiltIns);
+ if (_window.requestAnimationFrame) {
+ fill(
+ _window,
+ 'requestAnimationFrame',
+ function(orig) {
+ return function(cb) {
+ return orig(self.wrap(cb));
+ };
+ },
+ wrappedBuiltIns
+ );
+ }
+
+ // event targets borrowed from bugsnag-js:
+ // https://github.com/bugsnag/bugsnag-js/blob/master/src/bugsnag.js#L666
+ var eventTargets = [
+ 'EventTarget',
+ 'Window',
+ 'Node',
+ 'ApplicationCache',
+ 'AudioTrackList',
+ 'ChannelMergerNode',
+ 'CryptoOperation',
+ 'EventSource',
+ 'FileReader',
+ 'HTMLUnknownElement',
+ 'IDBDatabase',
+ 'IDBRequest',
+ 'IDBTransaction',
+ 'KeyOperation',
+ 'MediaController',
+ 'MessagePort',
+ 'ModalWindow',
+ 'Notification',
+ 'SVGElementInstance',
+ 'Screen',
+ 'TextTrack',
+ 'TextTrackCue',
+ 'TextTrackList',
+ 'WebSocket',
+ 'WebSocketWorker',
+ 'Worker',
+ 'XMLHttpRequest',
+ 'XMLHttpRequestEventTarget',
+ 'XMLHttpRequestUpload'
+ ];
+ for (var i = 0; i < eventTargets.length; i++) {
+ wrapEventTarget(eventTargets[i]);
+ }
+ },
+
+ /**
+ * Instrument browser built-ins w/ breadcrumb capturing
+ * - XMLHttpRequests
+ * - DOM interactions (click/typing)
+ * - window.location changes
+ * - console
+ *
+ * Can be disabled or individually configured via the `autoBreadcrumbs` config option
+ */
+ _instrumentBreadcrumbs: function() {
+ var self = this;
+ var autoBreadcrumbs = this._globalOptions.autoBreadcrumbs;
+
+ var wrappedBuiltIns = self._wrappedBuiltIns;
+
+ function wrapProp(prop, xhr) {
+ if (prop in xhr && isFunction(xhr[prop])) {
+ fill(xhr, prop, function(orig) {
+ return self.wrap(orig);
+ }); // intentionally don't track filled methods on XHR instances
+ }
+ }
+
+ if (autoBreadcrumbs.xhr && 'XMLHttpRequest' in _window) {
+ var xhrproto = XMLHttpRequest.prototype;
+ fill(
+ xhrproto,
+ 'open',
+ function(origOpen) {
+ return function(method, url) {
+ // preserve arity
+
+ // if Sentry key appears in URL, don't capture
+ if (isString(url) && url.indexOf(self._globalKey) === -1) {
+ this.__raven_xhr = {
+ method: method,
+ url: url,
+ status_code: null
+ };
+ }
+
+ return origOpen.apply(this, arguments);
+ };
+ },
+ wrappedBuiltIns
+ );
+
+ fill(
+ xhrproto,
+ 'send',
+ function(origSend) {
+ return function(data) {
+ // preserve arity
+ var xhr = this;
+
+ function onreadystatechangeHandler() {
+ if (xhr.__raven_xhr && xhr.readyState === 4) {
+ try {
+ // touching statusCode in some platforms throws
+ // an exception
+ xhr.__raven_xhr.status_code = xhr.status;
+ } catch (e) {
+ /* do nothing */
+ }
+
+ self.captureBreadcrumb({
+ type: 'http',
+ category: 'xhr',
+ data: xhr.__raven_xhr
+ });
+ }
+ }
+
+ var props = ['onload', 'onerror', 'onprogress'];
+ for (var j = 0; j < props.length; j++) {
+ wrapProp(props[j], xhr);
+ }
+
+ if ('onreadystatechange' in xhr && isFunction(xhr.onreadystatechange)) {
+ fill(
+ xhr,
+ 'onreadystatechange',
+ function(orig) {
+ return self.wrap(orig, undefined, onreadystatechangeHandler);
+ } /* intentionally don't track this instrumentation */
+ );
+ } else {
+ // if onreadystatechange wasn't actually set by the page on this xhr, we
+ // are free to set our own and capture the breadcrumb
+ xhr.onreadystatechange = onreadystatechangeHandler;
+ }
+
+ return origSend.apply(this, arguments);
+ };
+ },
+ wrappedBuiltIns
+ );
+ }
+
+ if (autoBreadcrumbs.xhr && 'fetch' in _window) {
+ fill(
+ _window,
+ 'fetch',
+ function(origFetch) {
+ return function(fn, t) {
+ // preserve arity
+ // Make a copy of the arguments to prevent deoptimization
+ // https://github.com/petkaantonov/bluebird/wiki/Optimization-killers#32-leaking-arguments
+ var args = new Array(arguments.length);
+ for (var i = 0; i < args.length; ++i) {
+ args[i] = arguments[i];
+ }
+
+ var fetchInput = args[0];
+ var method = 'GET';
+ var url;
+
+ if (typeof fetchInput === 'string') {
+ url = fetchInput;
+ } else if ('Request' in _window && fetchInput instanceof _window.Request) {
+ url = fetchInput.url;
+ if (fetchInput.method) {
+ method = fetchInput.method;
+ }
+ } else {
+ url = '' + fetchInput;
+ }
+
+ if (args[1] && args[1].method) {
+ method = args[1].method;
+ }
+
+ var fetchData = {
+ method: method,
+ url: url,
+ status_code: null
+ };
+
+ self.captureBreadcrumb({
+ type: 'http',
+ category: 'fetch',
+ data: fetchData
+ });
+
+ return origFetch.apply(this, args).then(function(response) {
+ fetchData.status_code = response.status;
+
+ return response;
+ });
+ };
+ },
+ wrappedBuiltIns
+ );
+ }
+
+ // Capture breadcrumbs from any click that is unhandled / bubbled up all the way
+ // to the document. Do this before we instrument addEventListener.
+ if (autoBreadcrumbs.dom && this._hasDocument) {
+ if (_document.addEventListener) {
+ _document.addEventListener('click', self._breadcrumbEventHandler('click'), false);
+ _document.addEventListener('keypress', self._keypressEventHandler(), false);
+ } else {
+ // IE8 Compatibility
+ _document.attachEvent('onclick', self._breadcrumbEventHandler('click'));
+ _document.attachEvent('onkeypress', self._keypressEventHandler());
+ }
+ }
+
+ // record navigation (URL) changes
+ // NOTE: in Chrome App environment, touching history.pushState, *even inside
+ // a try/catch block*, will cause Chrome to output an error to console.error
+ // borrowed from: https://github.com/angular/angular.js/pull/13945/files
+ var chrome = _window.chrome;
+ var isChromePackagedApp = chrome && chrome.app && chrome.app.runtime;
+ var hasPushAndReplaceState =
+ !isChromePackagedApp &&
+ _window.history &&
+ history.pushState &&
+ history.replaceState;
+ if (autoBreadcrumbs.location && hasPushAndReplaceState) {
+ // TODO: remove onpopstate handler on uninstall()
+ var oldOnPopState = _window.onpopstate;
+ _window.onpopstate = function() {
+ var currentHref = self._location.href;
+ self._captureUrlChange(self._lastHref, currentHref);
+
+ if (oldOnPopState) {
+ return oldOnPopState.apply(this, arguments);
+ }
+ };
+
+ var historyReplacementFunction = function(origHistFunction) {
+ // note history.pushState.length is 0; intentionally not declaring
+ // params to preserve 0 arity
+ return function(/* state, title, url */) {
+ var url = arguments.length > 2 ? arguments[2] : undefined;
+
+ // url argument is optional
+ if (url) {
+ // coerce to string (this is what pushState does)
+ self._captureUrlChange(self._lastHref, url + '');
+ }
+
+ return origHistFunction.apply(this, arguments);
+ };
+ };
+
+ fill(history, 'pushState', historyReplacementFunction, wrappedBuiltIns);
+ fill(history, 'replaceState', historyReplacementFunction, wrappedBuiltIns);
+ }
+
+ if (autoBreadcrumbs.console && 'console' in _window && console.log) {
+ // console
+ var consoleMethodCallback = function(msg, data) {
+ self.captureBreadcrumb({
+ message: msg,
+ level: data.level,
+ category: 'console'
+ });
+ };
+
+ each(['debug', 'info', 'warn', 'error', 'log'], function(_, level) {
+ wrapConsoleMethod(console, level, consoleMethodCallback);
+ });
+ }
+ },
+
+ _restoreBuiltIns: function() {
+ // restore any wrapped builtins
+ var builtin;
+ while (this._wrappedBuiltIns.length) {
+ builtin = this._wrappedBuiltIns.shift();
+
+ var obj = builtin[0],
+ name = builtin[1],
+ orig = builtin[2];
+
+ obj[name] = orig;
+ }
+ },
+
+ _drainPlugins: function() {
+ var self = this;
+
+ // FIX ME TODO
+ each(this._plugins, function(_, plugin) {
+ var installer = plugin[0];
+ var args = plugin[1];
+ installer.apply(self, [self].concat(args));
+ });
+ },
+
+ _parseDSN: function(str) {
+ var m = dsnPattern.exec(str),
+ dsn = {},
+ i = 7;
+
+ try {
+ while (i--) dsn[dsnKeys[i]] = m[i] || '';
+ } catch (e) {
+ throw new RavenConfigError('Invalid DSN: ' + str);
+ }
+
+ if (dsn.pass && !this._globalOptions.allowSecretKey) {
+ throw new RavenConfigError(
+ 'Do not specify your secret key in the DSN. See: http://bit.ly/raven-secret-key'
+ );
+ }
+
+ return dsn;
+ },
+
+ _getGlobalServer: function(uri) {
+ // assemble the endpoint from the uri pieces
+ var globalServer = '//' + uri.host + (uri.port ? ':' + uri.port : '');
+
+ if (uri.protocol) {
+ globalServer = uri.protocol + ':' + globalServer;
+ }
+ return globalServer;
+ },
+
+ _handleOnErrorStackInfo: function() {
+ // if we are intentionally ignoring errors via onerror, bail out
+ if (!this._ignoreOnError) {
+ this._handleStackInfo.apply(this, arguments);
+ }
+ },
+
+ _handleStackInfo: function(stackInfo, options) {
+ var frames = this._prepareFrames(stackInfo, options);
+
+ this._triggerEvent('handle', {
+ stackInfo: stackInfo,
+ options: options
+ });
+
+ this._processException(
+ stackInfo.name,
+ stackInfo.message,
+ stackInfo.url,
+ stackInfo.lineno,
+ frames,
+ options
+ );
+ },
+
+ _prepareFrames: function(stackInfo, options) {
+ var self = this;
+ var frames = [];
+ if (stackInfo.stack && stackInfo.stack.length) {
+ each(stackInfo.stack, function(i, stack) {
+ var frame = self._normalizeFrame(stack, stackInfo.url);
+ if (frame) {
+ frames.push(frame);
+ }
+ });
+
+ // e.g. frames captured via captureMessage throw
+ if (options && options.trimHeadFrames) {
+ for (var j = 0; j < options.trimHeadFrames && j < frames.length; j++) {
+ frames[j].in_app = false;
+ }
+ }
+ }
+ frames = frames.slice(0, this._globalOptions.stackTraceLimit);
+ return frames;
+ },
+
+ _normalizeFrame: function(frame, stackInfoUrl) {
+ // normalize the frames data
+ var normalized = {
+ filename: frame.url,
+ lineno: frame.line,
+ colno: frame.column,
+ function: frame.func || '?'
+ };
+
+ // Case when we don't have any information about the error
+ // E.g. throwing a string or raw object, instead of an `Error` in Firefox
+ // Generating synthetic error doesn't add any value here
+ //
+ // We should probably somehow let a user know that they should fix their code
+ if (!frame.url) {
+ normalized.filename = stackInfoUrl; // fallback to whole stacks url from onerror handler
+ }
+
+ normalized.in_app = !// determine if an exception came from outside of our app
+ // first we check the global includePaths list.
+ (
+ (!!this._globalOptions.includePaths.test &&
+ !this._globalOptions.includePaths.test(normalized.filename)) ||
+ // Now we check for fun, if the function name is Raven or TraceKit
+ /(Raven|TraceKit)\./.test(normalized['function']) ||
+ // finally, we do a last ditch effort and check for raven.min.js
+ /raven\.(min\.)?js$/.test(normalized.filename)
+ );
+
+ return normalized;
+ },
+
+ _processException: function(type, message, fileurl, lineno, frames, options) {
+ var prefixedMessage = (type ? type + ': ' : '') + (message || '');
+ if (
+ !!this._globalOptions.ignoreErrors.test &&
+ (this._globalOptions.ignoreErrors.test(message) ||
+ this._globalOptions.ignoreErrors.test(prefixedMessage))
+ ) {
+ return;
+ }
+
+ var stacktrace;
+
+ if (frames && frames.length) {
+ fileurl = frames[0].filename || fileurl;
+ // Sentry expects frames oldest to newest
+ // and JS sends them as newest to oldest
+ frames.reverse();
+ stacktrace = {frames: frames};
+ } else if (fileurl) {
+ stacktrace = {
+ frames: [
+ {
+ filename: fileurl,
+ lineno: lineno,
+ in_app: true
+ }
+ ]
+ };
+ }
+
+ if (
+ !!this._globalOptions.ignoreUrls.test &&
+ this._globalOptions.ignoreUrls.test(fileurl)
+ ) {
+ return;
+ }
+
+ if (
+ !!this._globalOptions.whitelistUrls.test &&
+ !this._globalOptions.whitelistUrls.test(fileurl)
+ ) {
+ return;
+ }
+
+ var data = objectMerge(
+ {
+ // sentry.interfaces.Exception
+ exception: {
+ values: [
+ {
+ type: type,
+ value: message,
+ stacktrace: stacktrace
+ }
+ ]
+ },
+ culprit: fileurl
+ },
+ options
+ );
+
+ // Fire away!
+ this._send(data);
+ },
+
+ _trimPacket: function(data) {
+ // For now, we only want to truncate the two different messages
+ // but this could/should be expanded to just trim everything
+ var max = this._globalOptions.maxMessageLength;
+ if (data.message) {
+ data.message = truncate(data.message, max);
+ }
+ if (data.exception) {
+ var exception = data.exception.values[0];
+ exception.value = truncate(exception.value, max);
+ }
+
+ var request = data.request;
+ if (request) {
+ if (request.url) {
+ request.url = truncate(request.url, this._globalOptions.maxUrlLength);
+ }
+ if (request.Referer) {
+ request.Referer = truncate(request.Referer, this._globalOptions.maxUrlLength);
+ }
+ }
+
+ if (data.breadcrumbs && data.breadcrumbs.values)
+ this._trimBreadcrumbs(data.breadcrumbs);
+
+ return data;
+ },
+
+ /**
+ * Truncate breadcrumb values (right now just URLs)
+ */
+ _trimBreadcrumbs: function(breadcrumbs) {
+ // known breadcrumb properties with urls
+ // TODO: also consider arbitrary prop values that start with (https?)?://
+ var urlProps = ['to', 'from', 'url'],
+ urlProp,
+ crumb,
+ data;
+
+ for (var i = 0; i < breadcrumbs.values.length; ++i) {
+ crumb = breadcrumbs.values[i];
+ if (
+ !crumb.hasOwnProperty('data') ||
+ !isObject(crumb.data) ||
+ objectFrozen(crumb.data)
+ )
+ continue;
+
+ data = objectMerge({}, crumb.data);
+ for (var j = 0; j < urlProps.length; ++j) {
+ urlProp = urlProps[j];
+ if (data.hasOwnProperty(urlProp) && data[urlProp]) {
+ data[urlProp] = truncate(data[urlProp], this._globalOptions.maxUrlLength);
+ }
+ }
+ breadcrumbs.values[i].data = data;
+ }
+ },
+
+ _getHttpData: function() {
+ if (!this._hasNavigator && !this._hasDocument) return;
+ var httpData = {};
+
+ if (this._hasNavigator && _navigator.userAgent) {
+ httpData.headers = {
+ 'User-Agent': navigator.userAgent
+ };
+ }
+
+ if (this._hasDocument) {
+ if (_document.location && _document.location.href) {
+ httpData.url = _document.location.href;
+ }
+ if (_document.referrer) {
+ if (!httpData.headers) httpData.headers = {};
+ httpData.headers.Referer = _document.referrer;
+ }
+ }
+
+ return httpData;
+ },
+
+ _resetBackoff: function() {
+ this._backoffDuration = 0;
+ this._backoffStart = null;
+ },
+
+ _shouldBackoff: function() {
+ return this._backoffDuration && now() - this._backoffStart < this._backoffDuration;
+ },
+
+ /**
+ * Returns true if the in-process data payload matches the signature
+ * of the previously-sent data
+ *
+ * NOTE: This has to be done at this level because TraceKit can generate
+ * data from window.onerror WITHOUT an exception object (IE8, IE9,
+ * other old browsers). This can take the form of an "exception"
+ * data object with a single frame (derived from the onerror args).
+ */
+ _isRepeatData: function(current) {
+ var last = this._lastData;
+
+ if (
+ !last ||
+ current.message !== last.message || // defined for captureMessage
+ current.culprit !== last.culprit // defined for captureException/onerror
+ )
+ return false;
+
+ // Stacktrace interface (i.e. from captureMessage)
+ if (current.stacktrace || last.stacktrace) {
+ return isSameStacktrace(current.stacktrace, last.stacktrace);
+ } else if (current.exception || last.exception) {
+ // Exception interface (i.e. from captureException/onerror)
+ return isSameException(current.exception, last.exception);
+ }
+
+ return true;
+ },
+
+ _setBackoffState: function(request) {
+ // If we are already in a backoff state, don't change anything
+ if (this._shouldBackoff()) {
+ return;
+ }
+
+ var status = request.status;
+
+ // 400 - project_id doesn't exist or some other fatal
+ // 401 - invalid/revoked dsn
+ // 429 - too many requests
+ if (!(status === 400 || status === 401 || status === 429)) return;
+
+ var retry;
+ try {
+ // If Retry-After is not in Access-Control-Expose-Headers, most
+ // browsers will throw an exception trying to access it
+ retry = request.getResponseHeader('Retry-After');
+ retry = parseInt(retry, 10) * 1000; // Retry-After is returned in seconds
+ } catch (e) {
+ /* eslint no-empty:0 */
+ }
+
+ this._backoffDuration = retry
+ ? // If Sentry server returned a Retry-After value, use it
+ retry
+ : // Otherwise, double the last backoff duration (starts at 1 sec)
+ this._backoffDuration * 2 || 1000;
+
+ this._backoffStart = now();
+ },
+
+ _send: function(data) {
+ var globalOptions = this._globalOptions;
+
+ var baseData = {
+ project: this._globalProject,
+ logger: globalOptions.logger,
+ platform: 'javascript'
+ },
+ httpData = this._getHttpData();
+
+ if (httpData) {
+ baseData.request = httpData;
+ }
+
+ // HACK: delete `trimHeadFrames` to prevent from appearing in outbound payload
+ if (data.trimHeadFrames) delete data.trimHeadFrames;
+
+ data = objectMerge(baseData, data);
+
+ // Merge in the tags and extra separately since objectMerge doesn't handle a deep merge
+ data.tags = objectMerge(objectMerge({}, this._globalContext.tags), data.tags);
+ data.extra = objectMerge(objectMerge({}, this._globalContext.extra), data.extra);
+
+ // Send along our own collected metadata with extra
+ data.extra['session:duration'] = now() - this._startTime;
+
+ if (this._breadcrumbs && this._breadcrumbs.length > 0) {
+ // intentionally make shallow copy so that additions
+ // to breadcrumbs aren't accidentally sent in this request
+ data.breadcrumbs = {
+ values: [].slice.call(this._breadcrumbs, 0)
+ };
+ }
+
+ // If there are no tags/extra, strip the key from the payload alltogther.
+ if (isEmptyObject(data.tags)) delete data.tags;
+
+ if (this._globalContext.user) {
+ // sentry.interfaces.User
+ data.user = this._globalContext.user;
+ }
+
+ // Include the environment if it's defined in globalOptions
+ if (globalOptions.environment) data.environment = globalOptions.environment;
+
+ // Include the release if it's defined in globalOptions
+ if (globalOptions.release) data.release = globalOptions.release;
+
+ // Include server_name if it's defined in globalOptions
+ if (globalOptions.serverName) data.server_name = globalOptions.serverName;
+
+ if (isFunction(globalOptions.dataCallback)) {
+ data = globalOptions.dataCallback(data) || data;
+ }
+
+ // Why??????????
+ if (!data || isEmptyObject(data)) {
+ return;
+ }
+
+ // Check if the request should be filtered or not
+ if (
+ isFunction(globalOptions.shouldSendCallback) &&
+ !globalOptions.shouldSendCallback(data)
+ ) {
+ return;
+ }
+
+ // Backoff state: Sentry server previously responded w/ an error (e.g. 429 - too many requests),
+ // so drop requests until "cool-off" period has elapsed.
+ if (this._shouldBackoff()) {
+ this._logDebug('warn', 'Raven dropped error due to backoff: ', data);
+ return;
+ }
+
+ if (typeof globalOptions.sampleRate === 'number') {
+ if (Math.random() < globalOptions.sampleRate) {
+ this._sendProcessedPayload(data);
+ }
+ } else {
+ this._sendProcessedPayload(data);
+ }
+ },
+
+ _getUuid: function() {
+ return uuid4();
+ },
+
+ _sendProcessedPayload: function(data, callback) {
+ var self = this;
+ var globalOptions = this._globalOptions;
+
+ if (!this.isSetup()) return;
+
+ // Try and clean up the packet before sending by truncating long values
+ data = this._trimPacket(data);
+
+ // ideally duplicate error testing should occur *before* dataCallback/shouldSendCallback,
+ // but this would require copying an un-truncated copy of the data packet, which can be
+ // arbitrarily deep (extra_data) -- could be worthwhile? will revisit
+ if (!this._globalOptions.allowDuplicates && this._isRepeatData(data)) {
+ this._logDebug('warn', 'Raven dropped repeat event: ', data);
+ return;
+ }
+
+ // Send along an event_id if not explicitly passed.
+ // This event_id can be used to reference the error within Sentry itself.
+ // Set lastEventId after we know the error should actually be sent
+ this._lastEventId = data.event_id || (data.event_id = this._getUuid());
+
+ // Store outbound payload after trim
+ this._lastData = data;
+
+ this._logDebug('debug', 'Raven about to send:', data);
+
+ var auth = {
+ sentry_version: '7',
+ sentry_client: 'raven-js/' + this.VERSION,
+ sentry_key: this._globalKey
+ };
+
+ if (this._globalSecret) {
+ auth.sentry_secret = this._globalSecret;
+ }
+
+ var exception = data.exception && data.exception.values[0];
+ this.captureBreadcrumb({
+ category: 'sentry',
+ message: exception
+ ? (exception.type ? exception.type + ': ' : '') + exception.value
+ : data.message,
+ event_id: data.event_id,
+ level: data.level || 'error' // presume error unless specified
+ });
+
+ var url = this._globalEndpoint;
+ (globalOptions.transport || this._makeRequest).call(this, {
+ url: url,
+ auth: auth,
+ data: data,
+ options: globalOptions,
+ onSuccess: function success() {
+ self._resetBackoff();
+
+ self._triggerEvent('success', {
+ data: data,
+ src: url
+ });
+ callback && callback();
+ },
+ onError: function failure(error) {
+ self._logDebug('error', 'Raven transport failed to send: ', error);
+
+ if (error.request) {
+ self._setBackoffState(error.request);
+ }
+
+ self._triggerEvent('failure', {
+ data: data,
+ src: url
+ });
+ error = error || new Error('Raven send failed (no additional details provided)');
+ callback && callback(error);
+ }
+ });
+ },
+
+ _makeRequest: function(opts) {
+ var request = _window.XMLHttpRequest && new _window.XMLHttpRequest();
+ if (!request) return;
+
+ // if browser doesn't support CORS (e.g. IE7), we are out of luck
+ var hasCORS = 'withCredentials' in request || typeof XDomainRequest !== 'undefined';
+
+ if (!hasCORS) return;
+
+ var url = opts.url;
+
+ if ('withCredentials' in request) {
+ request.onreadystatechange = function() {
+ if (request.readyState !== 4) {
+ return;
+ } else if (request.status === 200) {
+ opts.onSuccess && opts.onSuccess();
+ } else if (opts.onError) {
+ var err = new Error('Sentry error code: ' + request.status);
+ err.request = request;
+ opts.onError(err);
+ }
+ };
+ } else {
+ request = new XDomainRequest();
+ // xdomainrequest cannot go http -> https (or vice versa),
+ // so always use protocol relative
+ url = url.replace(/^https?:/, '');
+
+ // onreadystatechange not supported by XDomainRequest
+ if (opts.onSuccess) {
+ request.onload = opts.onSuccess;
+ }
+ if (opts.onError) {
+ request.onerror = function() {
+ var err = new Error('Sentry error code: XDomainRequest');
+ err.request = request;
+ opts.onError(err);
+ };
+ }
+ }
+
+ // NOTE: auth is intentionally sent as part of query string (NOT as custom
+ // HTTP header) so as to avoid preflight CORS requests
+ request.open('POST', url + '?' + urlencode(opts.auth));
+ request.send(stringify(opts.data));
+ },
+
+ _logDebug: function(level) {
+ if (this._originalConsoleMethods[level] && this.debug) {
+ // In IE<10 console methods do not have their own 'apply' method
+ Function.prototype.apply.call(
+ this._originalConsoleMethods[level],
+ this._originalConsole,
+ [].slice.call(arguments, 1)
+ );
+ }
+ },
+
+ _mergeContext: function(key, context) {
+ if (isUndefined(context)) {
+ delete this._globalContext[key];
+ } else {
+ this._globalContext[key] = objectMerge(this._globalContext[key] || {}, context);
+ }
+ }
+};
+
+// Deprecations
+Raven.prototype.setUser = Raven.prototype.setUserContext;
+Raven.prototype.setReleaseContext = Raven.prototype.setRelease;
+
+module.exports = Raven;
+
+
+/***/ }),
+
+/***/ "./node_modules/raven-js/src/singleton.js":
+/*!************************************************!*\
+ !*** ./node_modules/raven-js/src/singleton.js ***!
+ \************************************************/
+/***/ ((module, __unused_webpack_exports, __webpack_require__) => {
+
+/**
+ * Enforces a single instance of the Raven client, and the
+ * main entry point for Raven. If you are a consumer of the
+ * Raven library, you SHOULD load this file (vs raven.js).
+ **/
+
+var RavenConstructor = __webpack_require__(/*! ./raven */ "./node_modules/raven-js/src/raven.js");
+
+// This is to be defensive in environments where window does not exist (see https://github.com/getsentry/raven-js/pull/785)
+var _window =
+ typeof window !== 'undefined'
+ ? window
+ : typeof __webpack_require__.g !== 'undefined' ? __webpack_require__.g : typeof self !== 'undefined' ? self : {};
+var _Raven = _window.Raven;
+
+var Raven = new RavenConstructor();
+
+/*
+ * Allow multiple versions of Raven to be installed.
+ * Strip Raven from the global context and returns the instance.
+ *
+ * @return {Raven}
+ */
+Raven.noConflict = function() {
+ _window.Raven = _Raven;
+ return Raven;
+};
+
+Raven.afterLoad();
+
+module.exports = Raven;
+
+
+/***/ }),
+
+/***/ "./node_modules/raven-js/src/utils.js":
+/*!********************************************!*\
+ !*** ./node_modules/raven-js/src/utils.js ***!
+ \********************************************/
+/***/ ((module, __unused_webpack_exports, __webpack_require__) => {
+
+var _window =
+ typeof window !== 'undefined'
+ ? window
+ : typeof __webpack_require__.g !== 'undefined' ? __webpack_require__.g : typeof self !== 'undefined' ? self : {};
+
+function isObject(what) {
+ return typeof what === 'object' && what !== null;
+}
+
+// Yanked from https://git.io/vS8DV re-used under CC0
+// with some tiny modifications
+function isError(value) {
+ switch ({}.toString.call(value)) {
+ case '[object Error]':
+ return true;
+ case '[object Exception]':
+ return true;
+ case '[object DOMException]':
+ return true;
+ default:
+ return value instanceof Error;
+ }
+}
+
+function isErrorEvent(value) {
+ return supportsErrorEvent() && {}.toString.call(value) === '[object ErrorEvent]';
+}
+
+function isUndefined(what) {
+ return what === void 0;
+}
+
+function isFunction(what) {
+ return typeof what === 'function';
+}
+
+function isString(what) {
+ return Object.prototype.toString.call(what) === '[object String]';
+}
+
+function isEmptyObject(what) {
+ for (var _ in what) return false; // eslint-disable-line guard-for-in, no-unused-vars
+ return true;
+}
+
+function supportsErrorEvent() {
+ try {
+ new ErrorEvent(''); // eslint-disable-line no-new
+ return true;
+ } catch (e) {
+ return false;
+ }
+}
+
+function wrappedCallback(callback) {
+ function dataCallback(data, original) {
+ var normalizedData = callback(data) || data;
+ if (original) {
+ return original(normalizedData) || normalizedData;
+ }
+ return normalizedData;
+ }
+
+ return dataCallback;
+}
+
+function each(obj, callback) {
+ var i, j;
+
+ if (isUndefined(obj.length)) {
+ for (i in obj) {
+ if (hasKey(obj, i)) {
+ callback.call(null, i, obj[i]);
+ }
+ }
+ } else {
+ j = obj.length;
+ if (j) {
+ for (i = 0; i < j; i++) {
+ callback.call(null, i, obj[i]);
+ }
+ }
+ }
+}
+
+function objectMerge(obj1, obj2) {
+ if (!obj2) {
+ return obj1;
+ }
+ each(obj2, function(key, value) {
+ obj1[key] = value;
+ });
+ return obj1;
+}
+
+/**
+ * This function is only used for react-native.
+ * react-native freezes object that have already been sent over the
+ * js bridge. We need this function in order to check if the object is frozen.
+ * So it's ok that objectFrozen returns false if Object.isFrozen is not
+ * supported because it's not relevant for other "platforms". See related issue:
+ * https://github.com/getsentry/react-native-sentry/issues/57
+ */
+function objectFrozen(obj) {
+ if (!Object.isFrozen) {
+ return false;
+ }
+ return Object.isFrozen(obj);
+}
+
+function truncate(str, max) {
+ return !max || str.length <= max ? str : str.substr(0, max) + '\u2026';
+}
+
+/**
+ * hasKey, a better form of hasOwnProperty
+ * Example: hasKey(MainHostObject, property) === true/false
+ *
+ * @param {Object} host object to check property
+ * @param {string} key to check
+ */
+function hasKey(object, key) {
+ return Object.prototype.hasOwnProperty.call(object, key);
+}
+
+function joinRegExp(patterns) {
+ // Combine an array of regular expressions and strings into one large regexp
+ // Be mad.
+ var sources = [],
+ i = 0,
+ len = patterns.length,
+ pattern;
+
+ for (; i < len; i++) {
+ pattern = patterns[i];
+ if (isString(pattern)) {
+ // If it's a string, we need to escape it
+ // Taken from: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Guide/Regular_Expressions
+ sources.push(pattern.replace(/([.*+?^=!:${}()|\[\]\/\\])/g, '\\$1'));
+ } else if (pattern && pattern.source) {
+ // If it's a regexp already, we want to extract the source
+ sources.push(pattern.source);
+ }
+ // Intentionally skip other cases
+ }
+ return new RegExp(sources.join('|'), 'i');
+}
+
+function urlencode(o) {
+ var pairs = [];
+ each(o, function(key, value) {
+ pairs.push(encodeURIComponent(key) + '=' + encodeURIComponent(value));
+ });
+ return pairs.join('&');
+}
+
+// borrowed from https://tools.ietf.org/html/rfc3986#appendix-B
+// intentionally using regex and not href parsing trick because React Native and other
+// environments where DOM might not be available
+function parseUrl(url) {
+ var match = url.match(/^(([^:\/?#]+):)?(\/\/([^\/?#]*))?([^?#]*)(\?([^#]*))?(#(.*))?$/);
+ if (!match) return {};
+
+ // coerce to undefined values to empty string so we don't get 'undefined'
+ var query = match[6] || '';
+ var fragment = match[8] || '';
+ return {
+ protocol: match[2],
+ host: match[4],
+ path: match[5],
+ relative: match[5] + query + fragment // everything minus origin
+ };
+}
+function uuid4() {
+ var crypto = _window.crypto || _window.msCrypto;
+
+ if (!isUndefined(crypto) && crypto.getRandomValues) {
+ // Use window.crypto API if available
+ // eslint-disable-next-line no-undef
+ var arr = new Uint16Array(8);
+ crypto.getRandomValues(arr);
+
+ // set 4 in byte 7
+ arr[3] = (arr[3] & 0xfff) | 0x4000;
+ // set 2 most significant bits of byte 9 to '10'
+ arr[4] = (arr[4] & 0x3fff) | 0x8000;
+
+ var pad = function(num) {
+ var v = num.toString(16);
+ while (v.length < 4) {
+ v = '0' + v;
+ }
+ return v;
+ };
+
+ return (
+ pad(arr[0]) +
+ pad(arr[1]) +
+ pad(arr[2]) +
+ pad(arr[3]) +
+ pad(arr[4]) +
+ pad(arr[5]) +
+ pad(arr[6]) +
+ pad(arr[7])
+ );
+ } else {
+ // http://stackoverflow.com/questions/105034/how-to-create-a-guid-uuid-in-javascript/2117523#2117523
+ return 'xxxxxxxxxxxx4xxxyxxxxxxxxxxxxxxx'.replace(/[xy]/g, function(c) {
+ var r = (Math.random() * 16) | 0,
+ v = c === 'x' ? r : (r & 0x3) | 0x8;
+ return v.toString(16);
+ });
+ }
+}
+
+/**
+ * Given a child DOM element, returns a query-selector statement describing that
+ * and its ancestors
+ * e.g. [HTMLElement] => body > div > input#foo.btn[name=baz]
+ * @param elem
+ * @returns {string}
+ */
+function htmlTreeAsString(elem) {
+ /* eslint no-extra-parens:0*/
+ var MAX_TRAVERSE_HEIGHT = 5,
+ MAX_OUTPUT_LEN = 80,
+ out = [],
+ height = 0,
+ len = 0,
+ separator = ' > ',
+ sepLength = separator.length,
+ nextStr;
+
+ while (elem && height++ < MAX_TRAVERSE_HEIGHT) {
+ nextStr = htmlElementAsString(elem);
+ // bail out if
+ // - nextStr is the 'html' element
+ // - the length of the string that would be created exceeds MAX_OUTPUT_LEN
+ // (ignore this limit if we are on the first iteration)
+ if (
+ nextStr === 'html' ||
+ (height > 1 && len + out.length * sepLength + nextStr.length >= MAX_OUTPUT_LEN)
+ ) {
+ break;
+ }
+
+ out.push(nextStr);
+
+ len += nextStr.length;
+ elem = elem.parentNode;
+ }
+
+ return out.reverse().join(separator);
+}
+
+/**
+ * Returns a simple, query-selector representation of a DOM element
+ * e.g. [HTMLElement] => input#foo.btn[name=baz]
+ * @param HTMLElement
+ * @returns {string}
+ */
+function htmlElementAsString(elem) {
+ var out = [],
+ className,
+ classes,
+ key,
+ attr,
+ i;
+
+ if (!elem || !elem.tagName) {
+ return '';
+ }
+
+ out.push(elem.tagName.toLowerCase());
+ if (elem.id) {
+ out.push('#' + elem.id);
+ }
+
+ className = elem.className;
+ if (className && isString(className)) {
+ classes = className.split(/\s+/);
+ for (i = 0; i < classes.length; i++) {
+ out.push('.' + classes[i]);
+ }
+ }
+ var attrWhitelist = ['type', 'name', 'title', 'alt'];
+ for (i = 0; i < attrWhitelist.length; i++) {
+ key = attrWhitelist[i];
+ attr = elem.getAttribute(key);
+ if (attr) {
+ out.push('[' + key + '="' + attr + '"]');
+ }
+ }
+ return out.join('');
+}
+
+/**
+ * Returns true if either a OR b is truthy, but not both
+ */
+function isOnlyOneTruthy(a, b) {
+ return !!(!!a ^ !!b);
+}
+
+/**
+ * Returns true if the two input exception interfaces have the same content
+ */
+function isSameException(ex1, ex2) {
+ if (isOnlyOneTruthy(ex1, ex2)) return false;
+
+ ex1 = ex1.values[0];
+ ex2 = ex2.values[0];
+
+ if (ex1.type !== ex2.type || ex1.value !== ex2.value) return false;
+
+ return isSameStacktrace(ex1.stacktrace, ex2.stacktrace);
+}
+
+/**
+ * Returns true if the two input stack trace interfaces have the same content
+ */
+function isSameStacktrace(stack1, stack2) {
+ if (isOnlyOneTruthy(stack1, stack2)) return false;
+
+ var frames1 = stack1.frames;
+ var frames2 = stack2.frames;
+
+ // Exit early if frame count differs
+ if (frames1.length !== frames2.length) return false;
+
+ // Iterate through every frame; bail out if anything differs
+ var a, b;
+ for (var i = 0; i < frames1.length; i++) {
+ a = frames1[i];
+ b = frames2[i];
+ if (
+ a.filename !== b.filename ||
+ a.lineno !== b.lineno ||
+ a.colno !== b.colno ||
+ a['function'] !== b['function']
+ )
+ return false;
+ }
+ return true;
+}
+
+/**
+ * Polyfill a method
+ * @param obj object e.g. `document`
+ * @param name method name present on object e.g. `addEventListener`
+ * @param replacement replacement function
+ * @param track {optional} record instrumentation to an array
+ */
+function fill(obj, name, replacement, track) {
+ var orig = obj[name];
+ obj[name] = replacement(orig);
+ if (track) {
+ track.push([obj, name, orig]);
+ }
+}
+
+module.exports = {
+ isObject: isObject,
+ isError: isError,
+ isErrorEvent: isErrorEvent,
+ isUndefined: isUndefined,
+ isFunction: isFunction,
+ isString: isString,
+ isEmptyObject: isEmptyObject,
+ supportsErrorEvent: supportsErrorEvent,
+ wrappedCallback: wrappedCallback,
+ each: each,
+ objectMerge: objectMerge,
+ truncate: truncate,
+ objectFrozen: objectFrozen,
+ hasKey: hasKey,
+ joinRegExp: joinRegExp,
+ urlencode: urlencode,
+ uuid4: uuid4,
+ htmlTreeAsString: htmlTreeAsString,
+ htmlElementAsString: htmlElementAsString,
+ isSameException: isSameException,
+ isSameStacktrace: isSameStacktrace,
+ parseUrl: parseUrl,
+ fill: fill
+};
+
+
+/***/ }),
+
+/***/ "./node_modules/raven-js/vendor/TraceKit/tracekit.js":
+/*!***********************************************************!*\
+ !*** ./node_modules/raven-js/vendor/TraceKit/tracekit.js ***!
+ \***********************************************************/
+/***/ ((module, __unused_webpack_exports, __webpack_require__) => {
+
+var utils = __webpack_require__(/*! ../../src/utils */ "./node_modules/raven-js/src/utils.js");
+
+/*
+ TraceKit - Cross brower stack traces
+
+ This was originally forked from github.com/occ/TraceKit, but has since been
+ largely re-written and is now maintained as part of raven-js. Tests for
+ this are in test/vendor.
+
+ MIT license
+*/
+
+var TraceKit = {
+ collectWindowErrors: true,
+ debug: false
+};
+
+// This is to be defensive in environments where window does not exist (see https://github.com/getsentry/raven-js/pull/785)
+var _window =
+ typeof window !== 'undefined'
+ ? window
+ : typeof __webpack_require__.g !== 'undefined' ? __webpack_require__.g : typeof self !== 'undefined' ? self : {};
+
+// global reference to slice
+var _slice = [].slice;
+var UNKNOWN_FUNCTION = '?';
+
+// https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Error#Error_types
+var ERROR_TYPES_RE = /^(?:[Uu]ncaught (?:exception: )?)?(?:((?:Eval|Internal|Range|Reference|Syntax|Type|URI|)Error): )?(.*)$/;
+
+function getLocationHref() {
+ if (typeof document === 'undefined' || document.location == null) return '';
+
+ return document.location.href;
+}
+
+/**
+ * TraceKit.report: cross-browser processing of unhandled exceptions
+ *
+ * Syntax:
+ * TraceKit.report.subscribe(function(stackInfo) { ... })
+ * TraceKit.report.unsubscribe(function(stackInfo) { ... })
+ * TraceKit.report(exception)
+ * try { ...code... } catch(ex) { TraceKit.report(ex); }
+ *
+ * Supports:
+ * - Firefox: full stack trace with line numbers, plus column number
+ * on top frame; column number is not guaranteed
+ * - Opera: full stack trace with line and column numbers
+ * - Chrome: full stack trace with line and column numbers
+ * - Safari: line and column number for the top frame only; some frames
+ * may be missing, and column number is not guaranteed
+ * - IE: line and column number for the top frame only; some frames
+ * may be missing, and column number is not guaranteed
+ *
+ * In theory, TraceKit should work on all of the following versions:
+ * - IE5.5+ (only 8.0 tested)
+ * - Firefox 0.9+ (only 3.5+ tested)
+ * - Opera 7+ (only 10.50 tested; versions 9 and earlier may require
+ * Exceptions Have Stacktrace to be enabled in opera:config)
+ * - Safari 3+ (only 4+ tested)
+ * - Chrome 1+ (only 5+ tested)
+ * - Konqueror 3.5+ (untested)
+ *
+ * Requires TraceKit.computeStackTrace.
+ *
+ * Tries to catch all unhandled exceptions and report them to the
+ * subscribed handlers. Please note that TraceKit.report will rethrow the
+ * exception. This is REQUIRED in order to get a useful stack trace in IE.
+ * If the exception does not reach the top of the browser, you will only
+ * get a stack trace from the point where TraceKit.report was called.
+ *
+ * Handlers receive a stackInfo object as described in the
+ * TraceKit.computeStackTrace docs.
+ */
+TraceKit.report = (function reportModuleWrapper() {
+ var handlers = [],
+ lastArgs = null,
+ lastException = null,
+ lastExceptionStack = null;
+
+ /**
+ * Add a crash handler.
+ * @param {Function} handler
+ */
+ function subscribe(handler) {
+ installGlobalHandler();
+ handlers.push(handler);
+ }
+
+ /**
+ * Remove a crash handler.
+ * @param {Function} handler
+ */
+ function unsubscribe(handler) {
+ for (var i = handlers.length - 1; i >= 0; --i) {
+ if (handlers[i] === handler) {
+ handlers.splice(i, 1);
+ }
+ }
+ }
+
+ /**
+ * Remove all crash handlers.
+ */
+ function unsubscribeAll() {
+ uninstallGlobalHandler();
+ handlers = [];
+ }
+
+ /**
+ * Dispatch stack information to all handlers.
+ * @param {Object.} stack
+ */
+ function notifyHandlers(stack, isWindowError) {
+ var exception = null;
+ if (isWindowError && !TraceKit.collectWindowErrors) {
+ return;
+ }
+ for (var i in handlers) {
+ if (handlers.hasOwnProperty(i)) {
+ try {
+ handlers[i].apply(null, [stack].concat(_slice.call(arguments, 2)));
+ } catch (inner) {
+ exception = inner;
+ }
+ }
+ }
+
+ if (exception) {
+ throw exception;
+ }
+ }
+
+ var _oldOnerrorHandler, _onErrorHandlerInstalled;
+
+ /**
+ * Ensures all global unhandled exceptions are recorded.
+ * Supported by Gecko and IE.
+ * @param {string} message Error message.
+ * @param {string} url URL of script that generated the exception.
+ * @param {(number|string)} lineNo The line number at which the error
+ * occurred.
+ * @param {?(number|string)} colNo The column number at which the error
+ * occurred.
+ * @param {?Error} ex The actual Error object.
+ */
+ function traceKitWindowOnError(message, url, lineNo, colNo, ex) {
+ var stack = null;
+
+ if (lastExceptionStack) {
+ TraceKit.computeStackTrace.augmentStackTraceWithInitialElement(
+ lastExceptionStack,
+ url,
+ lineNo,
+ message
+ );
+ processLastException();
+ } else if (ex && utils.isError(ex)) {
+ // non-string `ex` arg; attempt to extract stack trace
+
+ // New chrome and blink send along a real error object
+ // Let's just report that like a normal error.
+ // See: https://mikewest.org/2013/08/debugging-runtime-errors-with-window-onerror
+ stack = TraceKit.computeStackTrace(ex);
+ notifyHandlers(stack, true);
+ } else {
+ var location = {
+ url: url,
+ line: lineNo,
+ column: colNo
+ };
+
+ var name = undefined;
+ var msg = message; // must be new var or will modify original `arguments`
+ var groups;
+ if ({}.toString.call(message) === '[object String]') {
+ var groups = message.match(ERROR_TYPES_RE);
+ if (groups) {
+ name = groups[1];
+ msg = groups[2];
+ }
+ }
+
+ location.func = UNKNOWN_FUNCTION;
+
+ stack = {
+ name: name,
+ message: msg,
+ url: getLocationHref(),
+ stack: [location]
+ };
+ notifyHandlers(stack, true);
+ }
+
+ if (_oldOnerrorHandler) {
+ return _oldOnerrorHandler.apply(this, arguments);
+ }
+
+ return false;
+ }
+
+ function installGlobalHandler() {
+ if (_onErrorHandlerInstalled) {
+ return;
+ }
+ _oldOnerrorHandler = _window.onerror;
+ _window.onerror = traceKitWindowOnError;
+ _onErrorHandlerInstalled = true;
+ }
+
+ function uninstallGlobalHandler() {
+ if (!_onErrorHandlerInstalled) {
+ return;
+ }
+ _window.onerror = _oldOnerrorHandler;
+ _onErrorHandlerInstalled = false;
+ _oldOnerrorHandler = undefined;
+ }
+
+ function processLastException() {
+ var _lastExceptionStack = lastExceptionStack,
+ _lastArgs = lastArgs;
+ lastArgs = null;
+ lastExceptionStack = null;
+ lastException = null;
+ notifyHandlers.apply(null, [_lastExceptionStack, false].concat(_lastArgs));
+ }
+
+ /**
+ * Reports an unhandled Error to TraceKit.
+ * @param {Error} ex
+ * @param {?boolean} rethrow If false, do not re-throw the exception.
+ * Only used for window.onerror to not cause an infinite loop of
+ * rethrowing.
+ */
+ function report(ex, rethrow) {
+ var args = _slice.call(arguments, 1);
+ if (lastExceptionStack) {
+ if (lastException === ex) {
+ return; // already caught by an inner catch block, ignore
+ } else {
+ processLastException();
+ }
+ }
+
+ var stack = TraceKit.computeStackTrace(ex);
+ lastExceptionStack = stack;
+ lastException = ex;
+ lastArgs = args;
+
+ // If the stack trace is incomplete, wait for 2 seconds for
+ // slow slow IE to see if onerror occurs or not before reporting
+ // this exception; otherwise, we will end up with an incomplete
+ // stack trace
+ setTimeout(function() {
+ if (lastException === ex) {
+ processLastException();
+ }
+ }, stack.incomplete ? 2000 : 0);
+
+ if (rethrow !== false) {
+ throw ex; // re-throw to propagate to the top level (and cause window.onerror)
+ }
+ }
+
+ report.subscribe = subscribe;
+ report.unsubscribe = unsubscribe;
+ report.uninstall = unsubscribeAll;
+ return report;
+})();
+
+/**
+ * TraceKit.computeStackTrace: cross-browser stack traces in JavaScript
+ *
+ * Syntax:
+ * s = TraceKit.computeStackTrace(exception) // consider using TraceKit.report instead (see below)
+ * Returns:
+ * s.name - exception name
+ * s.message - exception message
+ * s.stack[i].url - JavaScript or HTML file URL
+ * s.stack[i].func - function name, or empty for anonymous functions (if guessing did not work)
+ * s.stack[i].args - arguments passed to the function, if known
+ * s.stack[i].line - line number, if known
+ * s.stack[i].column - column number, if known
+ *
+ * Supports:
+ * - Firefox: full stack trace with line numbers and unreliable column
+ * number on top frame
+ * - Opera 10: full stack trace with line and column numbers
+ * - Opera 9-: full stack trace with line numbers
+ * - Chrome: full stack trace with line and column numbers
+ * - Safari: line and column number for the topmost stacktrace element
+ * only
+ * - IE: no line numbers whatsoever
+ *
+ * Tries to guess names of anonymous functions by looking for assignments
+ * in the source code. In IE and Safari, we have to guess source file names
+ * by searching for function bodies inside all page scripts. This will not
+ * work for scripts that are loaded cross-domain.
+ * Here be dragons: some function names may be guessed incorrectly, and
+ * duplicate functions may be mismatched.
+ *
+ * TraceKit.computeStackTrace should only be used for tracing purposes.
+ * Logging of unhandled exceptions should be done with TraceKit.report,
+ * which builds on top of TraceKit.computeStackTrace and provides better
+ * IE support by utilizing the window.onerror event to retrieve information
+ * about the top of the stack.
+ *
+ * Note: In IE and Safari, no stack trace is recorded on the Error object,
+ * so computeStackTrace instead walks its *own* chain of callers.
+ * This means that:
+ * * in Safari, some methods may be missing from the stack trace;
+ * * in IE, the topmost function in the stack trace will always be the
+ * caller of computeStackTrace.
+ *
+ * This is okay for tracing (because you are likely to be calling
+ * computeStackTrace from the function you want to be the topmost element
+ * of the stack trace anyway), but not okay for logging unhandled
+ * exceptions (because your catch block will likely be far away from the
+ * inner function that actually caused the exception).
+ *
+ */
+TraceKit.computeStackTrace = (function computeStackTraceWrapper() {
+ // Contents of Exception in various browsers.
+ //
+ // SAFARI:
+ // ex.message = Can't find variable: qq
+ // ex.line = 59
+ // ex.sourceId = 580238192
+ // ex.sourceURL = http://...
+ // ex.expressionBeginOffset = 96
+ // ex.expressionCaretOffset = 98
+ // ex.expressionEndOffset = 98
+ // ex.name = ReferenceError
+ //
+ // FIREFOX:
+ // ex.message = qq is not defined
+ // ex.fileName = http://...
+ // ex.lineNumber = 59
+ // ex.columnNumber = 69
+ // ex.stack = ...stack trace... (see the example below)
+ // ex.name = ReferenceError
+ //
+ // CHROME:
+ // ex.message = qq is not defined
+ // ex.name = ReferenceError
+ // ex.type = not_defined
+ // ex.arguments = ['aa']
+ // ex.stack = ...stack trace...
+ //
+ // INTERNET EXPLORER:
+ // ex.message = ...
+ // ex.name = ReferenceError
+ //
+ // OPERA:
+ // ex.message = ...message... (see the example below)
+ // ex.name = ReferenceError
+ // ex.opera#sourceloc = 11 (pretty much useless, duplicates the info in ex.message)
+ // ex.stacktrace = n/a; see 'opera:config#UserPrefs|Exceptions Have Stacktrace'
+
+ /**
+ * Computes stack trace information from the stack property.
+ * Chrome and Gecko use this property.
+ * @param {Error} ex
+ * @return {?Object.} Stack trace information.
+ */
+ function computeStackTraceFromStackProp(ex) {
+ if (typeof ex.stack === 'undefined' || !ex.stack) return;
+
+ var chrome = /^\s*at (.*?) ?\(((?:file|https?|blob|chrome-extension|native|eval|webpack||[a-z]:|\/).*?)(?::(\d+))?(?::(\d+))?\)?\s*$/i,
+ gecko = /^\s*(.*?)(?:\((.*?)\))?(?:^|@)((?:file|https?|blob|chrome|webpack|resource|\[native).*?|[^@]*bundle)(?::(\d+))?(?::(\d+))?\s*$/i,
+ winjs = /^\s*at (?:((?:\[object object\])?.+) )?\(?((?:file|ms-appx|https?|webpack|blob):.*?):(\d+)(?::(\d+))?\)?\s*$/i,
+ // Used to additionally parse URL/line/column from eval frames
+ geckoEval = /(\S+) line (\d+)(?: > eval line \d+)* > eval/i,
+ chromeEval = /\((\S*)(?::(\d+))(?::(\d+))\)/,
+ lines = ex.stack.split('\n'),
+ stack = [],
+ submatch,
+ parts,
+ element,
+ reference = /^(.*) is undefined$/.exec(ex.message);
+
+ for (var i = 0, j = lines.length; i < j; ++i) {
+ if ((parts = chrome.exec(lines[i]))) {
+ var isNative = parts[2] && parts[2].indexOf('native') === 0; // start of line
+ var isEval = parts[2] && parts[2].indexOf('eval') === 0; // start of line
+ if (isEval && (submatch = chromeEval.exec(parts[2]))) {
+ // throw out eval line/column and use top-most line/column number
+ parts[2] = submatch[1]; // url
+ parts[3] = submatch[2]; // line
+ parts[4] = submatch[3]; // column
+ }
+ element = {
+ url: !isNative ? parts[2] : null,
+ func: parts[1] || UNKNOWN_FUNCTION,
+ args: isNative ? [parts[2]] : [],
+ line: parts[3] ? +parts[3] : null,
+ column: parts[4] ? +parts[4] : null
+ };
+ } else if ((parts = winjs.exec(lines[i]))) {
+ element = {
+ url: parts[2],
+ func: parts[1] || UNKNOWN_FUNCTION,
+ args: [],
+ line: +parts[3],
+ column: parts[4] ? +parts[4] : null
+ };
+ } else if ((parts = gecko.exec(lines[i]))) {
+ var isEval = parts[3] && parts[3].indexOf(' > eval') > -1;
+ if (isEval && (submatch = geckoEval.exec(parts[3]))) {
+ // throw out eval line/column and use top-most line number
+ parts[3] = submatch[1];
+ parts[4] = submatch[2];
+ parts[5] = null; // no column when eval
+ } else if (i === 0 && !parts[5] && typeof ex.columnNumber !== 'undefined') {
+ // FireFox uses this awesome columnNumber property for its top frame
+ // Also note, Firefox's column number is 0-based and everything else expects 1-based,
+ // so adding 1
+ // NOTE: this hack doesn't work if top-most frame is eval
+ stack[0].column = ex.columnNumber + 1;
+ }
+ element = {
+ url: parts[3],
+ func: parts[1] || UNKNOWN_FUNCTION,
+ args: parts[2] ? parts[2].split(',') : [],
+ line: parts[4] ? +parts[4] : null,
+ column: parts[5] ? +parts[5] : null
+ };
+ } else {
+ continue;
+ }
+
+ if (!element.func && element.line) {
+ element.func = UNKNOWN_FUNCTION;
+ }
+
+ stack.push(element);
+ }
+
+ if (!stack.length) {
+ return null;
+ }
+
+ return {
+ name: ex.name,
+ message: ex.message,
+ url: getLocationHref(),
+ stack: stack
+ };
+ }
+
+ /**
+ * Adds information about the first frame to incomplete stack traces.
+ * Safari and IE require this to get complete data on the first frame.
+ * @param {Object.} stackInfo Stack trace information from
+ * one of the compute* methods.
+ * @param {string} url The URL of the script that caused an error.
+ * @param {(number|string)} lineNo The line number of the script that
+ * caused an error.
+ * @param {string=} message The error generated by the browser, which
+ * hopefully contains the name of the object that caused the error.
+ * @return {boolean} Whether or not the stack information was
+ * augmented.
+ */
+ function augmentStackTraceWithInitialElement(stackInfo, url, lineNo, message) {
+ var initial = {
+ url: url,
+ line: lineNo
+ };
+
+ if (initial.url && initial.line) {
+ stackInfo.incomplete = false;
+
+ if (!initial.func) {
+ initial.func = UNKNOWN_FUNCTION;
+ }
+
+ if (stackInfo.stack.length > 0) {
+ if (stackInfo.stack[0].url === initial.url) {
+ if (stackInfo.stack[0].line === initial.line) {
+ return false; // already in stack trace
+ } else if (
+ !stackInfo.stack[0].line &&
+ stackInfo.stack[0].func === initial.func
+ ) {
+ stackInfo.stack[0].line = initial.line;
+ return false;
+ }
+ }
+ }
+
+ stackInfo.stack.unshift(initial);
+ stackInfo.partial = true;
+ return true;
+ } else {
+ stackInfo.incomplete = true;
+ }
+
+ return false;
+ }
+
+ /**
+ * Computes stack trace information by walking the arguments.caller
+ * chain at the time the exception occurred. This will cause earlier
+ * frames to be missed but is the only way to get any stack trace in
+ * Safari and IE. The top frame is restored by
+ * {@link augmentStackTraceWithInitialElement}.
+ * @param {Error} ex
+ * @return {?Object.} Stack trace information.
+ */
+ function computeStackTraceByWalkingCallerChain(ex, depth) {
+ var functionName = /function\s+([_$a-zA-Z\xA0-\uFFFF][_$a-zA-Z0-9\xA0-\uFFFF]*)?\s*\(/i,
+ stack = [],
+ funcs = {},
+ recursion = false,
+ parts,
+ item,
+ source;
+
+ for (
+ var curr = computeStackTraceByWalkingCallerChain.caller;
+ curr && !recursion;
+ curr = curr.caller
+ ) {
+ if (curr === computeStackTrace || curr === TraceKit.report) {
+ // console.log('skipping internal function');
+ continue;
+ }
+
+ item = {
+ url: null,
+ func: UNKNOWN_FUNCTION,
+ line: null,
+ column: null
+ };
+
+ if (curr.name) {
+ item.func = curr.name;
+ } else if ((parts = functionName.exec(curr.toString()))) {
+ item.func = parts[1];
+ }
+
+ if (typeof item.func === 'undefined') {
+ try {
+ item.func = parts.input.substring(0, parts.input.indexOf('{'));
+ } catch (e) {}
+ }
+
+ if (funcs['' + curr]) {
+ recursion = true;
+ } else {
+ funcs['' + curr] = true;
+ }
+
+ stack.push(item);
+ }
+
+ if (depth) {
+ // console.log('depth is ' + depth);
+ // console.log('stack is ' + stack.length);
+ stack.splice(0, depth);
+ }
+
+ var result = {
+ name: ex.name,
+ message: ex.message,
+ url: getLocationHref(),
+ stack: stack
+ };
+ augmentStackTraceWithInitialElement(
+ result,
+ ex.sourceURL || ex.fileName,
+ ex.line || ex.lineNumber,
+ ex.message || ex.description
+ );
+ return result;
+ }
+
+ /**
+ * Computes a stack trace for an exception.
+ * @param {Error} ex
+ * @param {(string|number)=} depth
+ */
+ function computeStackTrace(ex, depth) {
+ var stack = null;
+ depth = depth == null ? 0 : +depth;
+
+ try {
+ stack = computeStackTraceFromStackProp(ex);
+ if (stack) {
+ return stack;
+ }
+ } catch (e) {
+ if (TraceKit.debug) {
+ throw e;
+ }
+ }
+
+ try {
+ stack = computeStackTraceByWalkingCallerChain(ex, depth + 1);
+ if (stack) {
+ return stack;
+ }
+ } catch (e) {
+ if (TraceKit.debug) {
+ throw e;
+ }
+ }
+ return {
+ name: ex.name,
+ message: ex.message,
+ url: getLocationHref()
+ };
+ }
+
+ computeStackTrace.augmentStackTraceWithInitialElement = augmentStackTraceWithInitialElement;
+ computeStackTrace.computeStackTraceFromStackProp = computeStackTraceFromStackProp;
+
+ return computeStackTrace;
+})();
+
+module.exports = TraceKit;
+
+
+/***/ }),
+
+/***/ "./node_modules/raven-js/vendor/json-stringify-safe/stringify.js":
+/*!***********************************************************************!*\
+ !*** ./node_modules/raven-js/vendor/json-stringify-safe/stringify.js ***!
+ \***********************************************************************/
+/***/ ((module, exports) => {
+
+/*
+ json-stringify-safe
+ Like JSON.stringify, but doesn't throw on circular references.
+
+ Originally forked from https://github.com/isaacs/json-stringify-safe
+ version 5.0.1 on 3/8/2017 and modified to handle Errors serialization
+ and IE8 compatibility. Tests for this are in test/vendor.
+
+ ISC license: https://github.com/isaacs/json-stringify-safe/blob/master/LICENSE
+*/
+
+exports = module.exports = stringify;
+exports.getSerialize = serializer;
+
+function indexOf(haystack, needle) {
+ for (var i = 0; i < haystack.length; ++i) {
+ if (haystack[i] === needle) return i;
+ }
+ return -1;
+}
+
+function stringify(obj, replacer, spaces, cycleReplacer) {
+ return JSON.stringify(obj, serializer(replacer, cycleReplacer), spaces);
+}
+
+// https://github.com/ftlabs/js-abbreviate/blob/fa709e5f139e7770a71827b1893f22418097fbda/index.js#L95-L106
+function stringifyError(value) {
+ var err = {
+ // These properties are implemented as magical getters and don't show up in for in
+ stack: value.stack,
+ message: value.message,
+ name: value.name
+ };
+
+ for (var i in value) {
+ if (Object.prototype.hasOwnProperty.call(value, i)) {
+ err[i] = value[i];
+ }
+ }
+
+ return err;
+}
+
+function serializer(replacer, cycleReplacer) {
+ var stack = [];
+ var keys = [];
+
+ if (cycleReplacer == null) {
+ cycleReplacer = function(key, value) {
+ if (stack[0] === value) {
+ return '[Circular ~]';
+ }
+ return '[Circular ~.' + keys.slice(0, indexOf(stack, value)).join('.') + ']';
+ };
+ }
+
+ return function(key, value) {
+ if (stack.length > 0) {
+ var thisPos = indexOf(stack, this);
+ ~thisPos ? stack.splice(thisPos + 1) : stack.push(this);
+ ~thisPos ? keys.splice(thisPos, Infinity, key) : keys.push(key);
+
+ if (~indexOf(stack, value)) {
+ value = cycleReplacer.call(this, key, value);
+ }
+ } else {
+ stack.push(value);
+ }
+
+ return replacer == null
+ ? value instanceof Error ? stringifyError(value) : value
+ : replacer.call(this, key, value);
+ };
+}
+
+
+/***/ }),
+
+/***/ "./node_modules/react-is/cjs/react-is.development.js":
+/*!***********************************************************!*\
+ !*** ./node_modules/react-is/cjs/react-is.development.js ***!
+ \***********************************************************/
+/***/ ((__unused_webpack_module, exports) => {
+
+"use strict";
+/** @license React v16.13.1
+ * react-is.development.js
+ *
+ * Copyright (c) Facebook, Inc. and its affiliates.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+
+
+
+
+if (true) {
+ (function() {
+'use strict';
+
+// The Symbol used to tag the ReactElement-like types. If there is no native Symbol
+// nor polyfill, then a plain number is used for performance.
+var hasSymbol = typeof Symbol === 'function' && Symbol.for;
+var REACT_ELEMENT_TYPE = hasSymbol ? Symbol.for('react.element') : 0xeac7;
+var REACT_PORTAL_TYPE = hasSymbol ? Symbol.for('react.portal') : 0xeaca;
+var REACT_FRAGMENT_TYPE = hasSymbol ? Symbol.for('react.fragment') : 0xeacb;
+var REACT_STRICT_MODE_TYPE = hasSymbol ? Symbol.for('react.strict_mode') : 0xeacc;
+var REACT_PROFILER_TYPE = hasSymbol ? Symbol.for('react.profiler') : 0xead2;
+var REACT_PROVIDER_TYPE = hasSymbol ? Symbol.for('react.provider') : 0xeacd;
+var REACT_CONTEXT_TYPE = hasSymbol ? Symbol.for('react.context') : 0xeace; // TODO: We don't use AsyncMode or ConcurrentMode anymore. They were temporary
+// (unstable) APIs that have been removed. Can we remove the symbols?
+
+var REACT_ASYNC_MODE_TYPE = hasSymbol ? Symbol.for('react.async_mode') : 0xeacf;
+var REACT_CONCURRENT_MODE_TYPE = hasSymbol ? Symbol.for('react.concurrent_mode') : 0xeacf;
+var REACT_FORWARD_REF_TYPE = hasSymbol ? Symbol.for('react.forward_ref') : 0xead0;
+var REACT_SUSPENSE_TYPE = hasSymbol ? Symbol.for('react.suspense') : 0xead1;
+var REACT_SUSPENSE_LIST_TYPE = hasSymbol ? Symbol.for('react.suspense_list') : 0xead8;
+var REACT_MEMO_TYPE = hasSymbol ? Symbol.for('react.memo') : 0xead3;
+var REACT_LAZY_TYPE = hasSymbol ? Symbol.for('react.lazy') : 0xead4;
+var REACT_BLOCK_TYPE = hasSymbol ? Symbol.for('react.block') : 0xead9;
+var REACT_FUNDAMENTAL_TYPE = hasSymbol ? Symbol.for('react.fundamental') : 0xead5;
+var REACT_RESPONDER_TYPE = hasSymbol ? Symbol.for('react.responder') : 0xead6;
+var REACT_SCOPE_TYPE = hasSymbol ? Symbol.for('react.scope') : 0xead7;
+
+function isValidElementType(type) {
+ return typeof type === 'string' || typeof type === 'function' || // Note: its typeof might be other than 'symbol' or 'number' if it's a polyfill.
+ type === REACT_FRAGMENT_TYPE || type === REACT_CONCURRENT_MODE_TYPE || type === REACT_PROFILER_TYPE || type === REACT_STRICT_MODE_TYPE || type === REACT_SUSPENSE_TYPE || type === REACT_SUSPENSE_LIST_TYPE || typeof type === 'object' && type !== null && (type.$$typeof === REACT_LAZY_TYPE || type.$$typeof === REACT_MEMO_TYPE || type.$$typeof === REACT_PROVIDER_TYPE || type.$$typeof === REACT_CONTEXT_TYPE || type.$$typeof === REACT_FORWARD_REF_TYPE || type.$$typeof === REACT_FUNDAMENTAL_TYPE || type.$$typeof === REACT_RESPONDER_TYPE || type.$$typeof === REACT_SCOPE_TYPE || type.$$typeof === REACT_BLOCK_TYPE);
+}
+
+function typeOf(object) {
+ if (typeof object === 'object' && object !== null) {
+ var $$typeof = object.$$typeof;
+
+ switch ($$typeof) {
+ case REACT_ELEMENT_TYPE:
+ var type = object.type;
+
+ switch (type) {
+ case REACT_ASYNC_MODE_TYPE:
+ case REACT_CONCURRENT_MODE_TYPE:
+ case REACT_FRAGMENT_TYPE:
+ case REACT_PROFILER_TYPE:
+ case REACT_STRICT_MODE_TYPE:
+ case REACT_SUSPENSE_TYPE:
+ return type;
+
+ default:
+ var $$typeofType = type && type.$$typeof;
+
+ switch ($$typeofType) {
+ case REACT_CONTEXT_TYPE:
+ case REACT_FORWARD_REF_TYPE:
+ case REACT_LAZY_TYPE:
+ case REACT_MEMO_TYPE:
+ case REACT_PROVIDER_TYPE:
+ return $$typeofType;
+
+ default:
+ return $$typeof;
+ }
+
+ }
+
+ case REACT_PORTAL_TYPE:
+ return $$typeof;
+ }
+ }
+
+ return undefined;
+} // AsyncMode is deprecated along with isAsyncMode
+
+var AsyncMode = REACT_ASYNC_MODE_TYPE;
+var ConcurrentMode = REACT_CONCURRENT_MODE_TYPE;
+var ContextConsumer = REACT_CONTEXT_TYPE;
+var ContextProvider = REACT_PROVIDER_TYPE;
+var Element = REACT_ELEMENT_TYPE;
+var ForwardRef = REACT_FORWARD_REF_TYPE;
+var Fragment = REACT_FRAGMENT_TYPE;
+var Lazy = REACT_LAZY_TYPE;
+var Memo = REACT_MEMO_TYPE;
+var Portal = REACT_PORTAL_TYPE;
+var Profiler = REACT_PROFILER_TYPE;
+var StrictMode = REACT_STRICT_MODE_TYPE;
+var Suspense = REACT_SUSPENSE_TYPE;
+var hasWarnedAboutDeprecatedIsAsyncMode = false; // AsyncMode should be deprecated
+
+function isAsyncMode(object) {
+ {
+ if (!hasWarnedAboutDeprecatedIsAsyncMode) {
+ hasWarnedAboutDeprecatedIsAsyncMode = true; // Using console['warn'] to evade Babel and ESLint
+
+ console['warn']('The ReactIs.isAsyncMode() alias has been deprecated, ' + 'and will be removed in React 17+. Update your code to use ' + 'ReactIs.isConcurrentMode() instead. It has the exact same API.');
+ }
+ }
+
+ return isConcurrentMode(object) || typeOf(object) === REACT_ASYNC_MODE_TYPE;
+}
+function isConcurrentMode(object) {
+ return typeOf(object) === REACT_CONCURRENT_MODE_TYPE;
+}
+function isContextConsumer(object) {
+ return typeOf(object) === REACT_CONTEXT_TYPE;
+}
+function isContextProvider(object) {
+ return typeOf(object) === REACT_PROVIDER_TYPE;
+}
+function isElement(object) {
+ return typeof object === 'object' && object !== null && object.$$typeof === REACT_ELEMENT_TYPE;
+}
+function isForwardRef(object) {
+ return typeOf(object) === REACT_FORWARD_REF_TYPE;
+}
+function isFragment(object) {
+ return typeOf(object) === REACT_FRAGMENT_TYPE;
+}
+function isLazy(object) {
+ return typeOf(object) === REACT_LAZY_TYPE;
+}
+function isMemo(object) {
+ return typeOf(object) === REACT_MEMO_TYPE;
+}
+function isPortal(object) {
+ return typeOf(object) === REACT_PORTAL_TYPE;
+}
+function isProfiler(object) {
+ return typeOf(object) === REACT_PROFILER_TYPE;
+}
+function isStrictMode(object) {
+ return typeOf(object) === REACT_STRICT_MODE_TYPE;
+}
+function isSuspense(object) {
+ return typeOf(object) === REACT_SUSPENSE_TYPE;
+}
+
+exports.AsyncMode = AsyncMode;
+exports.ConcurrentMode = ConcurrentMode;
+exports.ContextConsumer = ContextConsumer;
+exports.ContextProvider = ContextProvider;
+exports.Element = Element;
+exports.ForwardRef = ForwardRef;
+exports.Fragment = Fragment;
+exports.Lazy = Lazy;
+exports.Memo = Memo;
+exports.Portal = Portal;
+exports.Profiler = Profiler;
+exports.StrictMode = StrictMode;
+exports.Suspense = Suspense;
+exports.isAsyncMode = isAsyncMode;
+exports.isConcurrentMode = isConcurrentMode;
+exports.isContextConsumer = isContextConsumer;
+exports.isContextProvider = isContextProvider;
+exports.isElement = isElement;
+exports.isForwardRef = isForwardRef;
+exports.isFragment = isFragment;
+exports.isLazy = isLazy;
+exports.isMemo = isMemo;
+exports.isPortal = isPortal;
+exports.isProfiler = isProfiler;
+exports.isStrictMode = isStrictMode;
+exports.isSuspense = isSuspense;
+exports.isValidElementType = isValidElementType;
+exports.typeOf = typeOf;
+ })();
+}
+
+
+/***/ }),
+
+/***/ "./node_modules/react-is/index.js":
+/*!****************************************!*\
+ !*** ./node_modules/react-is/index.js ***!
+ \****************************************/
+/***/ ((module, __unused_webpack_exports, __webpack_require__) => {
+
+"use strict";
+
+
+if (false) {} else {
+ module.exports = __webpack_require__(/*! ./cjs/react-is.development.js */ "./node_modules/react-is/cjs/react-is.development.js");
+}
+
+
+/***/ }),
+
+/***/ "./node_modules/react/cjs/react-jsx-runtime.development.js":
+/*!*****************************************************************!*\
+ !*** ./node_modules/react/cjs/react-jsx-runtime.development.js ***!
+ \*****************************************************************/
+/***/ ((__unused_webpack_module, exports, __webpack_require__) => {
+
+"use strict";
+/** @license React v17.0.2
+ * react-jsx-runtime.development.js
+ *
+ * Copyright (c) Facebook, Inc. and its affiliates.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+
+
+if (true) {
+ (function() {
+'use strict';
+
+var React = __webpack_require__(/*! react */ "react");
+var _assign = __webpack_require__(/*! object-assign */ "./node_modules/object-assign/index.js");
+
+// ATTENTION
+// When adding new symbols to this file,
+// Please consider also adding to 'react-devtools-shared/src/backend/ReactSymbols'
+// The Symbol used to tag the ReactElement-like types. If there is no native Symbol
+// nor polyfill, then a plain number is used for performance.
+var REACT_ELEMENT_TYPE = 0xeac7;
+var REACT_PORTAL_TYPE = 0xeaca;
+exports.Fragment = 0xeacb;
+var REACT_STRICT_MODE_TYPE = 0xeacc;
+var REACT_PROFILER_TYPE = 0xead2;
+var REACT_PROVIDER_TYPE = 0xeacd;
+var REACT_CONTEXT_TYPE = 0xeace;
+var REACT_FORWARD_REF_TYPE = 0xead0;
+var REACT_SUSPENSE_TYPE = 0xead1;
+var REACT_SUSPENSE_LIST_TYPE = 0xead8;
+var REACT_MEMO_TYPE = 0xead3;
+var REACT_LAZY_TYPE = 0xead4;
+var REACT_BLOCK_TYPE = 0xead9;
+var REACT_SERVER_BLOCK_TYPE = 0xeada;
+var REACT_FUNDAMENTAL_TYPE = 0xead5;
+var REACT_SCOPE_TYPE = 0xead7;
+var REACT_OPAQUE_ID_TYPE = 0xeae0;
+var REACT_DEBUG_TRACING_MODE_TYPE = 0xeae1;
+var REACT_OFFSCREEN_TYPE = 0xeae2;
+var REACT_LEGACY_HIDDEN_TYPE = 0xeae3;
+
+if (typeof Symbol === 'function' && Symbol.for) {
+ var symbolFor = Symbol.for;
+ REACT_ELEMENT_TYPE = symbolFor('react.element');
+ REACT_PORTAL_TYPE = symbolFor('react.portal');
+ exports.Fragment = symbolFor('react.fragment');
+ REACT_STRICT_MODE_TYPE = symbolFor('react.strict_mode');
+ REACT_PROFILER_TYPE = symbolFor('react.profiler');
+ REACT_PROVIDER_TYPE = symbolFor('react.provider');
+ REACT_CONTEXT_TYPE = symbolFor('react.context');
+ REACT_FORWARD_REF_TYPE = symbolFor('react.forward_ref');
+ REACT_SUSPENSE_TYPE = symbolFor('react.suspense');
+ REACT_SUSPENSE_LIST_TYPE = symbolFor('react.suspense_list');
+ REACT_MEMO_TYPE = symbolFor('react.memo');
+ REACT_LAZY_TYPE = symbolFor('react.lazy');
+ REACT_BLOCK_TYPE = symbolFor('react.block');
+ REACT_SERVER_BLOCK_TYPE = symbolFor('react.server.block');
+ REACT_FUNDAMENTAL_TYPE = symbolFor('react.fundamental');
+ REACT_SCOPE_TYPE = symbolFor('react.scope');
+ REACT_OPAQUE_ID_TYPE = symbolFor('react.opaque.id');
+ REACT_DEBUG_TRACING_MODE_TYPE = symbolFor('react.debug_trace_mode');
+ REACT_OFFSCREEN_TYPE = symbolFor('react.offscreen');
+ REACT_LEGACY_HIDDEN_TYPE = symbolFor('react.legacy_hidden');
+}
+
+var MAYBE_ITERATOR_SYMBOL = typeof Symbol === 'function' && Symbol.iterator;
+var FAUX_ITERATOR_SYMBOL = '@@iterator';
+function getIteratorFn(maybeIterable) {
+ if (maybeIterable === null || typeof maybeIterable !== 'object') {
+ return null;
+ }
+
+ var maybeIterator = MAYBE_ITERATOR_SYMBOL && maybeIterable[MAYBE_ITERATOR_SYMBOL] || maybeIterable[FAUX_ITERATOR_SYMBOL];
+
+ if (typeof maybeIterator === 'function') {
+ return maybeIterator;
+ }
+
+ return null;
+}
+
+var ReactSharedInternals = React.__SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED;
+
+function error(format) {
+ {
+ for (var _len2 = arguments.length, args = new Array(_len2 > 1 ? _len2 - 1 : 0), _key2 = 1; _key2 < _len2; _key2++) {
+ args[_key2 - 1] = arguments[_key2];
+ }
+
+ printWarning('error', format, args);
+ }
+}
+
+function printWarning(level, format, args) {
+ // When changing this logic, you might want to also
+ // update consoleWithStackDev.www.js as well.
+ {
+ var ReactDebugCurrentFrame = ReactSharedInternals.ReactDebugCurrentFrame;
+ var stack = ReactDebugCurrentFrame.getStackAddendum();
+
+ if (stack !== '') {
+ format += '%s';
+ args = args.concat([stack]);
+ }
+
+ var argsWithFormat = args.map(function (item) {
+ return '' + item;
+ }); // Careful: RN currently depends on this prefix
+
+ argsWithFormat.unshift('Warning: ' + format); // We intentionally don't use spread (or .apply) directly because it
+ // breaks IE9: https://github.com/facebook/react/issues/13610
+ // eslint-disable-next-line react-internal/no-production-logging
+
+ Function.prototype.apply.call(console[level], console, argsWithFormat);
+ }
+}
+
+// Filter certain DOM attributes (e.g. src, href) if their values are empty strings.
+
+var enableScopeAPI = false; // Experimental Create Event Handle API.
+
+function isValidElementType(type) {
+ if (typeof type === 'string' || typeof type === 'function') {
+ return true;
+ } // Note: typeof might be other than 'symbol' or 'number' (e.g. if it's a polyfill).
+
+
+ if (type === exports.Fragment || type === REACT_PROFILER_TYPE || type === REACT_DEBUG_TRACING_MODE_TYPE || type === REACT_STRICT_MODE_TYPE || type === REACT_SUSPENSE_TYPE || type === REACT_SUSPENSE_LIST_TYPE || type === REACT_LEGACY_HIDDEN_TYPE || enableScopeAPI ) {
+ return true;
+ }
+
+ if (typeof type === 'object' && type !== null) {
+ if (type.$$typeof === REACT_LAZY_TYPE || type.$$typeof === REACT_MEMO_TYPE || type.$$typeof === REACT_PROVIDER_TYPE || type.$$typeof === REACT_CONTEXT_TYPE || type.$$typeof === REACT_FORWARD_REF_TYPE || type.$$typeof === REACT_FUNDAMENTAL_TYPE || type.$$typeof === REACT_BLOCK_TYPE || type[0] === REACT_SERVER_BLOCK_TYPE) {
+ return true;
+ }
+ }
+
+ return false;
+}
+
+function getWrappedName(outerType, innerType, wrapperName) {
+ var functionName = innerType.displayName || innerType.name || '';
+ return outerType.displayName || (functionName !== '' ? wrapperName + "(" + functionName + ")" : wrapperName);
+}
+
+function getContextName(type) {
+ return type.displayName || 'Context';
+}
+
+function getComponentName(type) {
+ if (type == null) {
+ // Host root, text node or just invalid type.
+ return null;
+ }
+
+ {
+ if (typeof type.tag === 'number') {
+ error('Received an unexpected object in getComponentName(). ' + 'This is likely a bug in React. Please file an issue.');
+ }
+ }
+
+ if (typeof type === 'function') {
+ return type.displayName || type.name || null;
+ }
+
+ if (typeof type === 'string') {
+ return type;
+ }
+
+ switch (type) {
+ case exports.Fragment:
+ return 'Fragment';
+
+ case REACT_PORTAL_TYPE:
+ return 'Portal';
+
+ case REACT_PROFILER_TYPE:
+ return 'Profiler';
+
+ case REACT_STRICT_MODE_TYPE:
+ return 'StrictMode';
+
+ case REACT_SUSPENSE_TYPE:
+ return 'Suspense';
+
+ case REACT_SUSPENSE_LIST_TYPE:
+ return 'SuspenseList';
+ }
+
+ if (typeof type === 'object') {
+ switch (type.$$typeof) {
+ case REACT_CONTEXT_TYPE:
+ var context = type;
+ return getContextName(context) + '.Consumer';
+
+ case REACT_PROVIDER_TYPE:
+ var provider = type;
+ return getContextName(provider._context) + '.Provider';
+
+ case REACT_FORWARD_REF_TYPE:
+ return getWrappedName(type, type.render, 'ForwardRef');
+
+ case REACT_MEMO_TYPE:
+ return getComponentName(type.type);
+
+ case REACT_BLOCK_TYPE:
+ return getComponentName(type._render);
+
+ case REACT_LAZY_TYPE:
+ {
+ var lazyComponent = type;
+ var payload = lazyComponent._payload;
+ var init = lazyComponent._init;
+
+ try {
+ return getComponentName(init(payload));
+ } catch (x) {
+ return null;
+ }
+ }
+ }
+ }
+
+ return null;
+}
+
+// Helpers to patch console.logs to avoid logging during side-effect free
+// replaying on render function. This currently only patches the object
+// lazily which won't cover if the log function was extracted eagerly.
+// We could also eagerly patch the method.
+var disabledDepth = 0;
+var prevLog;
+var prevInfo;
+var prevWarn;
+var prevError;
+var prevGroup;
+var prevGroupCollapsed;
+var prevGroupEnd;
+
+function disabledLog() {}
+
+disabledLog.__reactDisabledLog = true;
+function disableLogs() {
+ {
+ if (disabledDepth === 0) {
+ /* eslint-disable react-internal/no-production-logging */
+ prevLog = console.log;
+ prevInfo = console.info;
+ prevWarn = console.warn;
+ prevError = console.error;
+ prevGroup = console.group;
+ prevGroupCollapsed = console.groupCollapsed;
+ prevGroupEnd = console.groupEnd; // https://github.com/facebook/react/issues/19099
+
+ var props = {
+ configurable: true,
+ enumerable: true,
+ value: disabledLog,
+ writable: true
+ }; // $FlowFixMe Flow thinks console is immutable.
+
+ Object.defineProperties(console, {
+ info: props,
+ log: props,
+ warn: props,
+ error: props,
+ group: props,
+ groupCollapsed: props,
+ groupEnd: props
+ });
+ /* eslint-enable react-internal/no-production-logging */
+ }
+
+ disabledDepth++;
+ }
+}
+function reenableLogs() {
+ {
+ disabledDepth--;
+
+ if (disabledDepth === 0) {
+ /* eslint-disable react-internal/no-production-logging */
+ var props = {
+ configurable: true,
+ enumerable: true,
+ writable: true
+ }; // $FlowFixMe Flow thinks console is immutable.
+
+ Object.defineProperties(console, {
+ log: _assign({}, props, {
+ value: prevLog
+ }),
+ info: _assign({}, props, {
+ value: prevInfo
+ }),
+ warn: _assign({}, props, {
+ value: prevWarn
+ }),
+ error: _assign({}, props, {
+ value: prevError
+ }),
+ group: _assign({}, props, {
+ value: prevGroup
+ }),
+ groupCollapsed: _assign({}, props, {
+ value: prevGroupCollapsed
+ }),
+ groupEnd: _assign({}, props, {
+ value: prevGroupEnd
+ })
+ });
+ /* eslint-enable react-internal/no-production-logging */
+ }
+
+ if (disabledDepth < 0) {
+ error('disabledDepth fell below zero. ' + 'This is a bug in React. Please file an issue.');
+ }
+ }
+}
+
+var ReactCurrentDispatcher = ReactSharedInternals.ReactCurrentDispatcher;
+var prefix;
+function describeBuiltInComponentFrame(name, source, ownerFn) {
+ {
+ if (prefix === undefined) {
+ // Extract the VM specific prefix used by each line.
+ try {
+ throw Error();
+ } catch (x) {
+ var match = x.stack.trim().match(/\n( *(at )?)/);
+ prefix = match && match[1] || '';
+ }
+ } // We use the prefix to ensure our stacks line up with native stack frames.
+
+
+ return '\n' + prefix + name;
+ }
+}
+var reentry = false;
+var componentFrameCache;
+
+{
+ var PossiblyWeakMap = typeof WeakMap === 'function' ? WeakMap : Map;
+ componentFrameCache = new PossiblyWeakMap();
+}
+
+function describeNativeComponentFrame(fn, construct) {
+ // If something asked for a stack inside a fake render, it should get ignored.
+ if (!fn || reentry) {
+ return '';
+ }
+
+ {
+ var frame = componentFrameCache.get(fn);
+
+ if (frame !== undefined) {
+ return frame;
+ }
+ }
+
+ var control;
+ reentry = true;
+ var previousPrepareStackTrace = Error.prepareStackTrace; // $FlowFixMe It does accept undefined.
+
+ Error.prepareStackTrace = undefined;
+ var previousDispatcher;
+
+ {
+ previousDispatcher = ReactCurrentDispatcher.current; // Set the dispatcher in DEV because this might be call in the render function
+ // for warnings.
+
+ ReactCurrentDispatcher.current = null;
+ disableLogs();
+ }
+
+ try {
+ // This should throw.
+ if (construct) {
+ // Something should be setting the props in the constructor.
+ var Fake = function () {
+ throw Error();
+ }; // $FlowFixMe
+
+
+ Object.defineProperty(Fake.prototype, 'props', {
+ set: function () {
+ // We use a throwing setter instead of frozen or non-writable props
+ // because that won't throw in a non-strict mode function.
+ throw Error();
+ }
+ });
+
+ if (typeof Reflect === 'object' && Reflect.construct) {
+ // We construct a different control for this case to include any extra
+ // frames added by the construct call.
+ try {
+ Reflect.construct(Fake, []);
+ } catch (x) {
+ control = x;
+ }
+
+ Reflect.construct(fn, [], Fake);
+ } else {
+ try {
+ Fake.call();
+ } catch (x) {
+ control = x;
+ }
+
+ fn.call(Fake.prototype);
+ }
+ } else {
+ try {
+ throw Error();
+ } catch (x) {
+ control = x;
+ }
+
+ fn();
+ }
+ } catch (sample) {
+ // This is inlined manually because closure doesn't do it for us.
+ if (sample && control && typeof sample.stack === 'string') {
+ // This extracts the first frame from the sample that isn't also in the control.
+ // Skipping one frame that we assume is the frame that calls the two.
+ var sampleLines = sample.stack.split('\n');
+ var controlLines = control.stack.split('\n');
+ var s = sampleLines.length - 1;
+ var c = controlLines.length - 1;
+
+ while (s >= 1 && c >= 0 && sampleLines[s] !== controlLines[c]) {
+ // We expect at least one stack frame to be shared.
+ // Typically this will be the root most one. However, stack frames may be
+ // cut off due to maximum stack limits. In this case, one maybe cut off
+ // earlier than the other. We assume that the sample is longer or the same
+ // and there for cut off earlier. So we should find the root most frame in
+ // the sample somewhere in the control.
+ c--;
+ }
+
+ for (; s >= 1 && c >= 0; s--, c--) {
+ // Next we find the first one that isn't the same which should be the
+ // frame that called our sample function and the control.
+ if (sampleLines[s] !== controlLines[c]) {
+ // In V8, the first line is describing the message but other VMs don't.
+ // If we're about to return the first line, and the control is also on the same
+ // line, that's a pretty good indicator that our sample threw at same line as
+ // the control. I.e. before we entered the sample frame. So we ignore this result.
+ // This can happen if you passed a class to function component, or non-function.
+ if (s !== 1 || c !== 1) {
+ do {
+ s--;
+ c--; // We may still have similar intermediate frames from the construct call.
+ // The next one that isn't the same should be our match though.
+
+ if (c < 0 || sampleLines[s] !== controlLines[c]) {
+ // V8 adds a "new" prefix for native classes. Let's remove it to make it prettier.
+ var _frame = '\n' + sampleLines[s].replace(' at new ', ' at ');
+
+ {
+ if (typeof fn === 'function') {
+ componentFrameCache.set(fn, _frame);
+ }
+ } // Return the line we found.
+
+
+ return _frame;
+ }
+ } while (s >= 1 && c >= 0);
+ }
+
+ break;
+ }
+ }
+ }
+ } finally {
+ reentry = false;
+
+ {
+ ReactCurrentDispatcher.current = previousDispatcher;
+ reenableLogs();
+ }
+
+ Error.prepareStackTrace = previousPrepareStackTrace;
+ } // Fallback to just using the name if we couldn't make it throw.
+
+
+ var name = fn ? fn.displayName || fn.name : '';
+ var syntheticFrame = name ? describeBuiltInComponentFrame(name) : '';
+
+ {
+ if (typeof fn === 'function') {
+ componentFrameCache.set(fn, syntheticFrame);
+ }
+ }
+
+ return syntheticFrame;
+}
+function describeFunctionComponentFrame(fn, source, ownerFn) {
+ {
+ return describeNativeComponentFrame(fn, false);
+ }
+}
+
+function shouldConstruct(Component) {
+ var prototype = Component.prototype;
+ return !!(prototype && prototype.isReactComponent);
+}
+
+function describeUnknownElementTypeFrameInDEV(type, source, ownerFn) {
+
+ if (type == null) {
+ return '';
+ }
+
+ if (typeof type === 'function') {
+ {
+ return describeNativeComponentFrame(type, shouldConstruct(type));
+ }
+ }
+
+ if (typeof type === 'string') {
+ return describeBuiltInComponentFrame(type);
+ }
+
+ switch (type) {
+ case REACT_SUSPENSE_TYPE:
+ return describeBuiltInComponentFrame('Suspense');
+
+ case REACT_SUSPENSE_LIST_TYPE:
+ return describeBuiltInComponentFrame('SuspenseList');
+ }
+
+ if (typeof type === 'object') {
+ switch (type.$$typeof) {
+ case REACT_FORWARD_REF_TYPE:
+ return describeFunctionComponentFrame(type.render);
+
+ case REACT_MEMO_TYPE:
+ // Memo may contain any component type so we recursively resolve it.
+ return describeUnknownElementTypeFrameInDEV(type.type, source, ownerFn);
+
+ case REACT_BLOCK_TYPE:
+ return describeFunctionComponentFrame(type._render);
+
+ case REACT_LAZY_TYPE:
+ {
+ var lazyComponent = type;
+ var payload = lazyComponent._payload;
+ var init = lazyComponent._init;
+
+ try {
+ // Lazy may contain any component type so we recursively resolve it.
+ return describeUnknownElementTypeFrameInDEV(init(payload), source, ownerFn);
+ } catch (x) {}
+ }
+ }
+ }
+
+ return '';
+}
+
+var loggedTypeFailures = {};
+var ReactDebugCurrentFrame = ReactSharedInternals.ReactDebugCurrentFrame;
+
+function setCurrentlyValidatingElement(element) {
+ {
+ if (element) {
+ var owner = element._owner;
+ var stack = describeUnknownElementTypeFrameInDEV(element.type, element._source, owner ? owner.type : null);
+ ReactDebugCurrentFrame.setExtraStackFrame(stack);
+ } else {
+ ReactDebugCurrentFrame.setExtraStackFrame(null);
+ }
+ }
+}
+
+function checkPropTypes(typeSpecs, values, location, componentName, element) {
+ {
+ // $FlowFixMe This is okay but Flow doesn't know it.
+ var has = Function.call.bind(Object.prototype.hasOwnProperty);
+
+ for (var typeSpecName in typeSpecs) {
+ if (has(typeSpecs, typeSpecName)) {
+ var error$1 = void 0; // Prop type validation may throw. In case they do, we don't want to
+ // fail the render phase where it didn't fail before. So we log it.
+ // After these have been cleaned up, we'll let them throw.
+
+ try {
+ // This is intentionally an invariant that gets caught. It's the same
+ // behavior as without this statement except with a better message.
+ if (typeof typeSpecs[typeSpecName] !== 'function') {
+ var err = Error((componentName || 'React class') + ': ' + location + ' type `' + typeSpecName + '` is invalid; ' + 'it must be a function, usually from the `prop-types` package, but received `' + typeof typeSpecs[typeSpecName] + '`.' + 'This often happens because of typos such as `PropTypes.function` instead of `PropTypes.func`.');
+ err.name = 'Invariant Violation';
+ throw err;
+ }
+
+ error$1 = typeSpecs[typeSpecName](values, typeSpecName, componentName, location, null, 'SECRET_DO_NOT_PASS_THIS_OR_YOU_WILL_BE_FIRED');
+ } catch (ex) {
+ error$1 = ex;
+ }
+
+ if (error$1 && !(error$1 instanceof Error)) {
+ setCurrentlyValidatingElement(element);
+
+ error('%s: type specification of %s' + ' `%s` is invalid; the type checker ' + 'function must return `null` or an `Error` but returned a %s. ' + 'You may have forgotten to pass an argument to the type checker ' + 'creator (arrayOf, instanceOf, objectOf, oneOf, oneOfType, and ' + 'shape all require an argument).', componentName || 'React class', location, typeSpecName, typeof error$1);
+
+ setCurrentlyValidatingElement(null);
+ }
+
+ if (error$1 instanceof Error && !(error$1.message in loggedTypeFailures)) {
+ // Only monitor this failure once because there tends to be a lot of the
+ // same error.
+ loggedTypeFailures[error$1.message] = true;
+ setCurrentlyValidatingElement(element);
+
+ error('Failed %s type: %s', location, error$1.message);
+
+ setCurrentlyValidatingElement(null);
+ }
+ }
+ }
+ }
+}
+
+var ReactCurrentOwner = ReactSharedInternals.ReactCurrentOwner;
+var hasOwnProperty = Object.prototype.hasOwnProperty;
+var RESERVED_PROPS = {
+ key: true,
+ ref: true,
+ __self: true,
+ __source: true
+};
+var specialPropKeyWarningShown;
+var specialPropRefWarningShown;
+var didWarnAboutStringRefs;
+
+{
+ didWarnAboutStringRefs = {};
+}
+
+function hasValidRef(config) {
+ {
+ if (hasOwnProperty.call(config, 'ref')) {
+ var getter = Object.getOwnPropertyDescriptor(config, 'ref').get;
+
+ if (getter && getter.isReactWarning) {
+ return false;
+ }
+ }
+ }
+
+ return config.ref !== undefined;
+}
+
+function hasValidKey(config) {
+ {
+ if (hasOwnProperty.call(config, 'key')) {
+ var getter = Object.getOwnPropertyDescriptor(config, 'key').get;
+
+ if (getter && getter.isReactWarning) {
+ return false;
+ }
+ }
+ }
+
+ return config.key !== undefined;
+}
+
+function warnIfStringRefCannotBeAutoConverted(config, self) {
+ {
+ if (typeof config.ref === 'string' && ReactCurrentOwner.current && self && ReactCurrentOwner.current.stateNode !== self) {
+ var componentName = getComponentName(ReactCurrentOwner.current.type);
+
+ if (!didWarnAboutStringRefs[componentName]) {
+ error('Component "%s" contains the string ref "%s". ' + 'Support for string refs will be removed in a future major release. ' + 'This case cannot be automatically converted to an arrow function. ' + 'We ask you to manually fix this case by using useRef() or createRef() instead. ' + 'Learn more about using refs safely here: ' + 'https://reactjs.org/link/strict-mode-string-ref', getComponentName(ReactCurrentOwner.current.type), config.ref);
+
+ didWarnAboutStringRefs[componentName] = true;
+ }
+ }
+ }
+}
+
+function defineKeyPropWarningGetter(props, displayName) {
+ {
+ var warnAboutAccessingKey = function () {
+ if (!specialPropKeyWarningShown) {
+ specialPropKeyWarningShown = true;
+
+ error('%s: `key` is not a prop. Trying to access it will result ' + 'in `undefined` being returned. If you need to access the same ' + 'value within the child component, you should pass it as a different ' + 'prop. (https://reactjs.org/link/special-props)', displayName);
+ }
+ };
+
+ warnAboutAccessingKey.isReactWarning = true;
+ Object.defineProperty(props, 'key', {
+ get: warnAboutAccessingKey,
+ configurable: true
+ });
+ }
+}
+
+function defineRefPropWarningGetter(props, displayName) {
+ {
+ var warnAboutAccessingRef = function () {
+ if (!specialPropRefWarningShown) {
+ specialPropRefWarningShown = true;
+
+ error('%s: `ref` is not a prop. Trying to access it will result ' + 'in `undefined` being returned. If you need to access the same ' + 'value within the child component, you should pass it as a different ' + 'prop. (https://reactjs.org/link/special-props)', displayName);
+ }
+ };
+
+ warnAboutAccessingRef.isReactWarning = true;
+ Object.defineProperty(props, 'ref', {
+ get: warnAboutAccessingRef,
+ configurable: true
+ });
+ }
+}
+/**
+ * Factory method to create a new React element. This no longer adheres to
+ * the class pattern, so do not use new to call it. Also, instanceof check
+ * will not work. Instead test $$typeof field against Symbol.for('react.element') to check
+ * if something is a React Element.
+ *
+ * @param {*} type
+ * @param {*} props
+ * @param {*} key
+ * @param {string|object} ref
+ * @param {*} owner
+ * @param {*} self A *temporary* helper to detect places where `this` is
+ * different from the `owner` when React.createElement is called, so that we
+ * can warn. We want to get rid of owner and replace string `ref`s with arrow
+ * functions, and as long as `this` and owner are the same, there will be no
+ * change in behavior.
+ * @param {*} source An annotation object (added by a transpiler or otherwise)
+ * indicating filename, line number, and/or other information.
+ * @internal
+ */
+
+
+var ReactElement = function (type, key, ref, self, source, owner, props) {
+ var element = {
+ // This tag allows us to uniquely identify this as a React Element
+ $$typeof: REACT_ELEMENT_TYPE,
+ // Built-in properties that belong on the element
+ type: type,
+ key: key,
+ ref: ref,
+ props: props,
+ // Record the component responsible for creating this element.
+ _owner: owner
+ };
+
+ {
+ // The validation flag is currently mutative. We put it on
+ // an external backing store so that we can freeze the whole object.
+ // This can be replaced with a WeakMap once they are implemented in
+ // commonly used development environments.
+ element._store = {}; // To make comparing ReactElements easier for testing purposes, we make
+ // the validation flag non-enumerable (where possible, which should
+ // include every environment we run tests in), so the test framework
+ // ignores it.
+
+ Object.defineProperty(element._store, 'validated', {
+ configurable: false,
+ enumerable: false,
+ writable: true,
+ value: false
+ }); // self and source are DEV only properties.
+
+ Object.defineProperty(element, '_self', {
+ configurable: false,
+ enumerable: false,
+ writable: false,
+ value: self
+ }); // Two elements created in two different places should be considered
+ // equal for testing purposes and therefore we hide it from enumeration.
+
+ Object.defineProperty(element, '_source', {
+ configurable: false,
+ enumerable: false,
+ writable: false,
+ value: source
+ });
+
+ if (Object.freeze) {
+ Object.freeze(element.props);
+ Object.freeze(element);
+ }
+ }
+
+ return element;
+};
+/**
+ * https://github.com/reactjs/rfcs/pull/107
+ * @param {*} type
+ * @param {object} props
+ * @param {string} key
+ */
+
+function jsxDEV(type, config, maybeKey, source, self) {
+ {
+ var propName; // Reserved names are extracted
+
+ var props = {};
+ var key = null;
+ var ref = null; // Currently, key can be spread in as a prop. This causes a potential
+ // issue if key is also explicitly declared (ie.
+ // or
). We want to deprecate key spread,
+ // but as an intermediary step, we will use jsxDEV for everything except
+ //
, because we aren't currently able to tell if
+ // key is explicitly declared to be undefined or not.
+
+ if (maybeKey !== undefined) {
+ key = '' + maybeKey;
+ }
+
+ if (hasValidKey(config)) {
+ key = '' + config.key;
+ }
+
+ if (hasValidRef(config)) {
+ ref = config.ref;
+ warnIfStringRefCannotBeAutoConverted(config, self);
+ } // Remaining properties are added to a new props object
+
+
+ for (propName in config) {
+ if (hasOwnProperty.call(config, propName) && !RESERVED_PROPS.hasOwnProperty(propName)) {
+ props[propName] = config[propName];
+ }
+ } // Resolve default props
+
+
+ if (type && type.defaultProps) {
+ var defaultProps = type.defaultProps;
+
+ for (propName in defaultProps) {
+ if (props[propName] === undefined) {
+ props[propName] = defaultProps[propName];
+ }
+ }
+ }
+
+ if (key || ref) {
+ var displayName = typeof type === 'function' ? type.displayName || type.name || 'Unknown' : type;
+
+ if (key) {
+ defineKeyPropWarningGetter(props, displayName);
+ }
+
+ if (ref) {
+ defineRefPropWarningGetter(props, displayName);
+ }
+ }
+
+ return ReactElement(type, key, ref, self, source, ReactCurrentOwner.current, props);
+ }
+}
+
+var ReactCurrentOwner$1 = ReactSharedInternals.ReactCurrentOwner;
+var ReactDebugCurrentFrame$1 = ReactSharedInternals.ReactDebugCurrentFrame;
+
+function setCurrentlyValidatingElement$1(element) {
+ {
+ if (element) {
+ var owner = element._owner;
+ var stack = describeUnknownElementTypeFrameInDEV(element.type, element._source, owner ? owner.type : null);
+ ReactDebugCurrentFrame$1.setExtraStackFrame(stack);
+ } else {
+ ReactDebugCurrentFrame$1.setExtraStackFrame(null);
+ }
+ }
+}
+
+var propTypesMisspellWarningShown;
+
+{
+ propTypesMisspellWarningShown = false;
+}
+/**
+ * Verifies the object is a ReactElement.
+ * See https://reactjs.org/docs/react-api.html#isvalidelement
+ * @param {?object} object
+ * @return {boolean} True if `object` is a ReactElement.
+ * @final
+ */
+
+function isValidElement(object) {
+ {
+ return typeof object === 'object' && object !== null && object.$$typeof === REACT_ELEMENT_TYPE;
+ }
+}
+
+function getDeclarationErrorAddendum() {
+ {
+ if (ReactCurrentOwner$1.current) {
+ var name = getComponentName(ReactCurrentOwner$1.current.type);
+
+ if (name) {
+ return '\n\nCheck the render method of `' + name + '`.';
+ }
+ }
+
+ return '';
+ }
+}
+
+function getSourceInfoErrorAddendum(source) {
+ {
+ if (source !== undefined) {
+ var fileName = source.fileName.replace(/^.*[\\\/]/, '');
+ var lineNumber = source.lineNumber;
+ return '\n\nCheck your code at ' + fileName + ':' + lineNumber + '.';
+ }
+
+ return '';
+ }
+}
+/**
+ * Warn if there's no key explicitly set on dynamic arrays of children or
+ * object keys are not valid. This allows us to keep track of children between
+ * updates.
+ */
+
+
+var ownerHasKeyUseWarning = {};
+
+function getCurrentComponentErrorInfo(parentType) {
+ {
+ var info = getDeclarationErrorAddendum();
+
+ if (!info) {
+ var parentName = typeof parentType === 'string' ? parentType : parentType.displayName || parentType.name;
+
+ if (parentName) {
+ info = "\n\nCheck the top-level render call using <" + parentName + ">.";
+ }
+ }
+
+ return info;
+ }
+}
+/**
+ * Warn if the element doesn't have an explicit key assigned to it.
+ * This element is in an array. The array could grow and shrink or be
+ * reordered. All children that haven't already been validated are required to
+ * have a "key" property assigned to it. Error statuses are cached so a warning
+ * will only be shown once.
+ *
+ * @internal
+ * @param {ReactElement} element Element that requires a key.
+ * @param {*} parentType element's parent's type.
+ */
+
+
+function validateExplicitKey(element, parentType) {
+ {
+ if (!element._store || element._store.validated || element.key != null) {
+ return;
+ }
+
+ element._store.validated = true;
+ var currentComponentErrorInfo = getCurrentComponentErrorInfo(parentType);
+
+ if (ownerHasKeyUseWarning[currentComponentErrorInfo]) {
+ return;
+ }
+
+ ownerHasKeyUseWarning[currentComponentErrorInfo] = true; // Usually the current owner is the offender, but if it accepts children as a
+ // property, it may be the creator of the child that's responsible for
+ // assigning it a key.
+
+ var childOwner = '';
+
+ if (element && element._owner && element._owner !== ReactCurrentOwner$1.current) {
+ // Give the component that originally created this child.
+ childOwner = " It was passed a child from " + getComponentName(element._owner.type) + ".";
+ }
+
+ setCurrentlyValidatingElement$1(element);
+
+ error('Each child in a list should have a unique "key" prop.' + '%s%s See https://reactjs.org/link/warning-keys for more information.', currentComponentErrorInfo, childOwner);
+
+ setCurrentlyValidatingElement$1(null);
+ }
+}
+/**
+ * Ensure that every element either is passed in a static location, in an
+ * array with an explicit keys property defined, or in an object literal
+ * with valid key property.
+ *
+ * @internal
+ * @param {ReactNode} node Statically passed child of any type.
+ * @param {*} parentType node's parent's type.
+ */
+
+
+function validateChildKeys(node, parentType) {
+ {
+ if (typeof node !== 'object') {
+ return;
+ }
+
+ if (Array.isArray(node)) {
+ for (var i = 0; i < node.length; i++) {
+ var child = node[i];
+
+ if (isValidElement(child)) {
+ validateExplicitKey(child, parentType);
+ }
+ }
+ } else if (isValidElement(node)) {
+ // This element was passed in a valid location.
+ if (node._store) {
+ node._store.validated = true;
+ }
+ } else if (node) {
+ var iteratorFn = getIteratorFn(node);
+
+ if (typeof iteratorFn === 'function') {
+ // Entry iterators used to provide implicit keys,
+ // but now we print a separate warning for them later.
+ if (iteratorFn !== node.entries) {
+ var iterator = iteratorFn.call(node);
+ var step;
+
+ while (!(step = iterator.next()).done) {
+ if (isValidElement(step.value)) {
+ validateExplicitKey(step.value, parentType);
+ }
+ }
+ }
+ }
+ }
+ }
+}
+/**
+ * Given an element, validate that its props follow the propTypes definition,
+ * provided by the type.
+ *
+ * @param {ReactElement} element
+ */
+
+
+function validatePropTypes(element) {
+ {
+ var type = element.type;
+
+ if (type === null || type === undefined || typeof type === 'string') {
+ return;
+ }
+
+ var propTypes;
+
+ if (typeof type === 'function') {
+ propTypes = type.propTypes;
+ } else if (typeof type === 'object' && (type.$$typeof === REACT_FORWARD_REF_TYPE || // Note: Memo only checks outer props here.
+ // Inner props are checked in the reconciler.
+ type.$$typeof === REACT_MEMO_TYPE)) {
+ propTypes = type.propTypes;
+ } else {
+ return;
+ }
+
+ if (propTypes) {
+ // Intentionally inside to avoid triggering lazy initializers:
+ var name = getComponentName(type);
+ checkPropTypes(propTypes, element.props, 'prop', name, element);
+ } else if (type.PropTypes !== undefined && !propTypesMisspellWarningShown) {
+ propTypesMisspellWarningShown = true; // Intentionally inside to avoid triggering lazy initializers:
+
+ var _name = getComponentName(type);
+
+ error('Component %s declared `PropTypes` instead of `propTypes`. Did you misspell the property assignment?', _name || 'Unknown');
+ }
+
+ if (typeof type.getDefaultProps === 'function' && !type.getDefaultProps.isReactClassApproved) {
+ error('getDefaultProps is only used on classic React.createClass ' + 'definitions. Use a static property named `defaultProps` instead.');
+ }
+ }
+}
+/**
+ * Given a fragment, validate that it can only be provided with fragment props
+ * @param {ReactElement} fragment
+ */
+
+
+function validateFragmentProps(fragment) {
+ {
+ var keys = Object.keys(fragment.props);
+
+ for (var i = 0; i < keys.length; i++) {
+ var key = keys[i];
+
+ if (key !== 'children' && key !== 'key') {
+ setCurrentlyValidatingElement$1(fragment);
+
+ error('Invalid prop `%s` supplied to `React.Fragment`. ' + 'React.Fragment can only have `key` and `children` props.', key);
+
+ setCurrentlyValidatingElement$1(null);
+ break;
+ }
+ }
+
+ if (fragment.ref !== null) {
+ setCurrentlyValidatingElement$1(fragment);
+
+ error('Invalid attribute `ref` supplied to `React.Fragment`.');
+
+ setCurrentlyValidatingElement$1(null);
+ }
+ }
+}
+
+function jsxWithValidation(type, props, key, isStaticChildren, source, self) {
+ {
+ var validType = isValidElementType(type); // We warn in this case but don't throw. We expect the element creation to
+ // succeed and there will likely be errors in render.
+
+ if (!validType) {
+ var info = '';
+
+ if (type === undefined || typeof type === 'object' && type !== null && Object.keys(type).length === 0) {
+ info += ' You likely forgot to export your component from the file ' + "it's defined in, or you might have mixed up default and named imports.";
+ }
+
+ var sourceInfo = getSourceInfoErrorAddendum(source);
+
+ if (sourceInfo) {
+ info += sourceInfo;
+ } else {
+ info += getDeclarationErrorAddendum();
+ }
+
+ var typeString;
+
+ if (type === null) {
+ typeString = 'null';
+ } else if (Array.isArray(type)) {
+ typeString = 'array';
+ } else if (type !== undefined && type.$$typeof === REACT_ELEMENT_TYPE) {
+ typeString = "<" + (getComponentName(type.type) || 'Unknown') + " />";
+ info = ' Did you accidentally export a JSX literal instead of a component?';
+ } else {
+ typeString = typeof type;
+ }
+
+ error('React.jsx: type is invalid -- expected a string (for ' + 'built-in components) or a class/function (for composite ' + 'components) but got: %s.%s', typeString, info);
+ }
+
+ var element = jsxDEV(type, props, key, source, self); // The result can be nullish if a mock or a custom function is used.
+ // TODO: Drop this when these are no longer allowed as the type argument.
+
+ if (element == null) {
+ return element;
+ } // Skip key warning if the type isn't valid since our key validation logic
+ // doesn't expect a non-string/function type and can throw confusing errors.
+ // We don't want exception behavior to differ between dev and prod.
+ // (Rendering will throw with a helpful message and as soon as the type is
+ // fixed, the key warnings will appear.)
+
+
+ if (validType) {
+ var children = props.children;
+
+ if (children !== undefined) {
+ if (isStaticChildren) {
+ if (Array.isArray(children)) {
+ for (var i = 0; i < children.length; i++) {
+ validateChildKeys(children[i], type);
+ }
+
+ if (Object.freeze) {
+ Object.freeze(children);
+ }
+ } else {
+ error('React.jsx: Static children should always be an array. ' + 'You are likely explicitly calling React.jsxs or React.jsxDEV. ' + 'Use the Babel transform instead.');
+ }
+ } else {
+ validateChildKeys(children, type);
+ }
+ }
+ }
+
+ if (type === exports.Fragment) {
+ validateFragmentProps(element);
+ } else {
+ validatePropTypes(element);
+ }
+
+ return element;
+ }
+} // These two functions exist to still get child warnings in dev
+// even with the prod transform. This means that jsxDEV is purely
+// opt-in behavior for better messages but that we won't stop
+// giving you warnings if you use production apis.
+
+function jsxWithValidationStatic(type, props, key) {
+ {
+ return jsxWithValidation(type, props, key, true);
+ }
+}
+function jsxWithValidationDynamic(type, props, key) {
+ {
+ return jsxWithValidation(type, props, key, false);
+ }
+}
+
+var jsx = jsxWithValidationDynamic ; // we may want to special case jsxs internally to take advantage of static children.
+// for now we can ship identical prod functions
+
+var jsxs = jsxWithValidationStatic ;
+
+exports.jsx = jsx;
+exports.jsxs = jsxs;
+ })();
+}
+
+
+/***/ }),
+
+/***/ "./node_modules/react/jsx-runtime.js":
+/*!*******************************************!*\
+ !*** ./node_modules/react/jsx-runtime.js ***!
+ \*******************************************/
+/***/ ((module, __unused_webpack_exports, __webpack_require__) => {
+
+"use strict";
+
+
+if (false) {} else {
+ module.exports = __webpack_require__(/*! ./cjs/react-jsx-runtime.development.js */ "./node_modules/react/cjs/react-jsx-runtime.development.js");
+}
+
+
+/***/ }),
+
+/***/ "./node_modules/styled-components/dist/styled-components.browser.esm.js":
+/*!******************************************************************************!*\
+ !*** ./node_modules/styled-components/dist/styled-components.browser.esm.js ***!
+ \******************************************************************************/
+/***/ ((__unused_webpack_module, __webpack_exports__, __webpack_require__) => {
+
+"use strict";
+__webpack_require__.r(__webpack_exports__);
+/* harmony export */ __webpack_require__.d(__webpack_exports__, {
+/* harmony export */ "ServerStyleSheet": () => (/* binding */ ServerStyleSheet),
+/* harmony export */ "StyleSheetConsumer": () => (/* binding */ StyleSheetConsumer),
+/* harmony export */ "StyleSheetContext": () => (/* binding */ StyleSheetContext),
+/* harmony export */ "StyleSheetManager": () => (/* binding */ StyleSheetManager),
+/* harmony export */ "ThemeConsumer": () => (/* binding */ ThemeConsumer),
+/* harmony export */ "ThemeContext": () => (/* binding */ ThemeContext),
+/* harmony export */ "ThemeProvider": () => (/* binding */ ThemeProvider),
+/* harmony export */ "__DO_NOT_USE_OR_YOU_WILL_BE_HAUNTED_BY_SPOOKY_GHOSTS": () => (/* binding */ __DO_NOT_USE_OR_YOU_WILL_BE_HAUNTED_BY_SPOOKY_GHOSTS),
+/* harmony export */ "createGlobalStyle": () => (/* binding */ createGlobalStyle),
+/* harmony export */ "css": () => (/* binding */ css),
+/* harmony export */ "default": () => (__WEBPACK_DEFAULT_EXPORT__),
+/* harmony export */ "isStyledComponent": () => (/* binding */ isStyledComponent),
+/* harmony export */ "keyframes": () => (/* binding */ keyframes),
+/* harmony export */ "withTheme": () => (/* binding */ withTheme)
+/* harmony export */ });
+/* harmony import */ var stylis_stylis_min__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! stylis/stylis.min */ "./node_modules/stylis/stylis.min.js");
+/* harmony import */ var stylis_stylis_min__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(stylis_stylis_min__WEBPACK_IMPORTED_MODULE_0__);
+/* harmony import */ var stylis_rule_sheet__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! stylis-rule-sheet */ "./node_modules/stylis-rule-sheet/index.js");
+/* harmony import */ var stylis_rule_sheet__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(stylis_rule_sheet__WEBPACK_IMPORTED_MODULE_1__);
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! react */ "react");
+/* harmony import */ var react__WEBPACK_IMPORTED_MODULE_2___default = /*#__PURE__*/__webpack_require__.n(react__WEBPACK_IMPORTED_MODULE_2__);
+/* harmony import */ var _emotion_unitless__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! @emotion/unitless */ "./node_modules/@emotion/unitless/dist/unitless.browser.esm.js");
+/* harmony import */ var react_is__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__(/*! react-is */ "./node_modules/react-is/index.js");
+/* harmony import */ var memoize_one__WEBPACK_IMPORTED_MODULE_7__ = __webpack_require__(/*! memoize-one */ "./node_modules/memoize-one/dist/memoize-one.esm.js");
+/* harmony import */ var prop_types__WEBPACK_IMPORTED_MODULE_8__ = __webpack_require__(/*! prop-types */ "./node_modules/prop-types/index.js");
+/* harmony import */ var prop_types__WEBPACK_IMPORTED_MODULE_8___default = /*#__PURE__*/__webpack_require__.n(prop_types__WEBPACK_IMPORTED_MODULE_8__);
+/* harmony import */ var _emotion_is_prop_valid__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__(/*! @emotion/is-prop-valid */ "./node_modules/@emotion/is-prop-valid/dist/is-prop-valid.browser.esm.js");
+/* harmony import */ var merge_anything__WEBPACK_IMPORTED_MODULE_6__ = __webpack_require__(/*! merge-anything */ "./node_modules/merge-anything/dist/index.esm.js");
+
+
+
+
+
+
+
+
+
+
+//
+
+var interleave = (function (strings, interpolations) {
+ var result = [strings[0]];
+
+ for (var i = 0, len = interpolations.length; i < len; i += 1) {
+ result.push(interpolations[i], strings[i + 1]);
+ }
+
+ return result;
+});
+
+var _typeof = typeof Symbol === "function" && typeof Symbol.iterator === "symbol" ? function (obj) {
+ return typeof obj;
+} : function (obj) {
+ return obj && typeof Symbol === "function" && obj.constructor === Symbol && obj !== Symbol.prototype ? "symbol" : typeof obj;
+};
+
+var classCallCheck = function (instance, Constructor) {
+ if (!(instance instanceof Constructor)) {
+ throw new TypeError("Cannot call a class as a function");
+ }
+};
+
+var createClass = function () {
+ function defineProperties(target, props) {
+ for (var i = 0; i < props.length; i++) {
+ var descriptor = props[i];
+ descriptor.enumerable = descriptor.enumerable || false;
+ descriptor.configurable = true;
+ if ("value" in descriptor) descriptor.writable = true;
+ Object.defineProperty(target, descriptor.key, descriptor);
+ }
+ }
+
+ return function (Constructor, protoProps, staticProps) {
+ if (protoProps) defineProperties(Constructor.prototype, protoProps);
+ if (staticProps) defineProperties(Constructor, staticProps);
+ return Constructor;
+ };
+}();
+
+var _extends = Object.assign || function (target) {
+ for (var i = 1; i < arguments.length; i++) {
+ var source = arguments[i];
+
+ for (var key in source) {
+ if (Object.prototype.hasOwnProperty.call(source, key)) {
+ target[key] = source[key];
+ }
+ }
+ }
+
+ return target;
+};
+
+var inherits = function (subClass, superClass) {
+ if (typeof superClass !== "function" && superClass !== null) {
+ throw new TypeError("Super expression must either be null or a function, not " + typeof superClass);
+ }
+
+ subClass.prototype = Object.create(superClass && superClass.prototype, {
+ constructor: {
+ value: subClass,
+ enumerable: false,
+ writable: true,
+ configurable: true
+ }
+ });
+ if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass;
+};
+
+var objectWithoutProperties = function (obj, keys) {
+ var target = {};
+
+ for (var i in obj) {
+ if (keys.indexOf(i) >= 0) continue;
+ if (!Object.prototype.hasOwnProperty.call(obj, i)) continue;
+ target[i] = obj[i];
+ }
+
+ return target;
+};
+
+var possibleConstructorReturn = function (self, call) {
+ if (!self) {
+ throw new ReferenceError("this hasn't been initialised - super() hasn't been called");
+ }
+
+ return call && (typeof call === "object" || typeof call === "function") ? call : self;
+};
+
+//
+var isPlainObject = (function (x) {
+ return (typeof x === 'undefined' ? 'undefined' : _typeof(x)) === 'object' && x.constructor === Object;
+});
+
+//
+var EMPTY_ARRAY = Object.freeze([]);
+var EMPTY_OBJECT = Object.freeze({});
+
+//
+function isFunction(test) {
+ return typeof test === 'function';
+}
+
+//
+
+function getComponentName(target) {
+ return ( true ? typeof target === 'string' && target : 0) || target.displayName || target.name || 'Component';
+}
+
+//
+function isStatelessFunction(test) {
+ return typeof test === 'function' && !(test.prototype && test.prototype.isReactComponent);
+}
+
+//
+function isStyledComponent(target) {
+ return target && typeof target.styledComponentId === 'string';
+}
+
+//
+
+var SC_ATTR = typeof process !== 'undefined' && (process.env.REACT_APP_SC_ATTR || process.env.SC_ATTR) || 'data-styled';
+
+var SC_VERSION_ATTR = 'data-styled-version';
+
+var SC_STREAM_ATTR = 'data-styled-streamed';
+
+var IS_BROWSER = typeof window !== 'undefined' && 'HTMLElement' in window;
+
+var DISABLE_SPEEDY = typeof SC_DISABLE_SPEEDY === 'boolean' && SC_DISABLE_SPEEDY || typeof process !== 'undefined' && (process.env.REACT_APP_SC_DISABLE_SPEEDY || process.env.SC_DISABLE_SPEEDY) || "development" !== 'production';
+
+// Shared empty execution context when generating static styles
+var STATIC_EXECUTION_CONTEXT = {};
+
+//
+
+
+/**
+ * Parse errors.md and turn it into a simple hash of code: message
+ */
+var ERRORS = true ? {
+ "1": "Cannot create styled-component for component: %s.\n\n",
+ "2": "Can't collect styles once you've consumed a `ServerStyleSheet`'s styles! `ServerStyleSheet` is a one off instance for each server-side render cycle.\n\n- Are you trying to reuse it across renders?\n- Are you accidentally calling collectStyles twice?\n\n",
+ "3": "Streaming SSR is only supported in a Node.js environment; Please do not try to call this method in the browser.\n\n",
+ "4": "The `StyleSheetManager` expects a valid target or sheet prop!\n\n- Does this error occur on the client and is your target falsy?\n- Does this error occur on the server and is the sheet falsy?\n\n",
+ "5": "The clone method cannot be used on the client!\n\n- Are you running in a client-like environment on the server?\n- Are you trying to run SSR on the client?\n\n",
+ "6": "Trying to insert a new style tag, but the given Node is unmounted!\n\n- Are you using a custom target that isn't mounted?\n- Does your document not have a valid head element?\n- Have you accidentally removed a style tag manually?\n\n",
+ "7": "ThemeProvider: Please return an object from your \"theme\" prop function, e.g.\n\n```js\ntheme={() => ({})}\n```\n\n",
+ "8": "ThemeProvider: Please make your \"theme\" prop an object.\n\n",
+ "9": "Missing document ``\n\n",
+ "10": "Cannot find a StyleSheet instance. Usually this happens if there are multiple copies of styled-components loaded at once. Check out this issue for how to troubleshoot and fix the common cases where this situation can happen: https://github.com/styled-components/styled-components/issues/1941#issuecomment-417862021\n\n",
+ "11": "_This error was replaced with a dev-time warning, it will be deleted for v4 final._ [createGlobalStyle] received children which will not be rendered. Please use the component without passing children elements.\n\n",
+ "12": "It seems you are interpolating a keyframe declaration (%s) into an untagged string. This was supported in styled-components v3, but is not longer supported in v4 as keyframes are now injected on-demand. Please wrap your string in the css\\`\\` helper which ensures the styles are injected correctly. See https://www.styled-components.com/docs/api#css\n\n",
+ "13": "%s is not a styled component and cannot be referred to via component selector. See https://www.styled-components.com/docs/advanced#referring-to-other-components for more details.\n"
+} : 0;
+
+/**
+ * super basic version of sprintf
+ */
+function format() {
+ var a = arguments.length <= 0 ? undefined : arguments[0];
+ var b = [];
+
+ for (var c = 1, len = arguments.length; c < len; c += 1) {
+ b.push(arguments.length <= c ? undefined : arguments[c]);
+ }
+
+ b.forEach(function (d) {
+ a = a.replace(/%[a-z]/, d);
+ });
+
+ return a;
+}
+
+/**
+ * Create an error file out of errors.md for development and a simple web link to the full errors
+ * in production mode.
+ */
+
+var StyledComponentsError = function (_Error) {
+ inherits(StyledComponentsError, _Error);
+
+ function StyledComponentsError(code) {
+ classCallCheck(this, StyledComponentsError);
+
+ for (var _len = arguments.length, interpolations = Array(_len > 1 ? _len - 1 : 0), _key = 1; _key < _len; _key++) {
+ interpolations[_key - 1] = arguments[_key];
+ }
+
+ if (false) { var _this; } else {
+ var _this = possibleConstructorReturn(this, _Error.call(this, format.apply(undefined, [ERRORS[code]].concat(interpolations)).trim()));
+ }
+ return possibleConstructorReturn(_this);
+ }
+
+ return StyledComponentsError;
+}(Error);
+
+//
+var SC_COMPONENT_ID = /^[^\S\n]*?\/\* sc-component-id:\s*(\S+)\s+\*\//gm;
+
+var extractComps = (function (maybeCSS) {
+ var css = '' + (maybeCSS || ''); // Definitely a string, and a clone
+ var existingComponents = [];
+ css.replace(SC_COMPONENT_ID, function (match, componentId, matchIndex) {
+ existingComponents.push({ componentId: componentId, matchIndex: matchIndex });
+ return match;
+ });
+ return existingComponents.map(function (_ref, i) {
+ var componentId = _ref.componentId,
+ matchIndex = _ref.matchIndex;
+
+ var nextComp = existingComponents[i + 1];
+ var cssFromDOM = nextComp ? css.slice(matchIndex, nextComp.matchIndex) : css.slice(matchIndex);
+ return { componentId: componentId, cssFromDOM: cssFromDOM };
+ });
+});
+
+//
+
+var COMMENT_REGEX = /^\s*\/\/.*$/gm;
+
+// NOTE: This stylis instance is only used to split rules from SSR'd style tags
+var stylisSplitter = new (stylis_stylis_min__WEBPACK_IMPORTED_MODULE_0___default())({
+ global: false,
+ cascade: true,
+ keyframe: false,
+ prefix: false,
+ compress: false,
+ semicolon: true
+});
+
+var stylis = new (stylis_stylis_min__WEBPACK_IMPORTED_MODULE_0___default())({
+ global: false,
+ cascade: true,
+ keyframe: false,
+ prefix: true,
+ compress: false,
+ semicolon: false // NOTE: This means "autocomplete missing semicolons"
+});
+
+// Wrap `insertRulePlugin to build a list of rules,
+// and then make our own plugin to return the rules. This
+// makes it easier to hook into the existing SSR architecture
+
+var parsingRules = [];
+
+// eslint-disable-next-line consistent-return
+var returnRulesPlugin = function returnRulesPlugin(context) {
+ if (context === -2) {
+ var parsedRules = parsingRules;
+ parsingRules = [];
+ return parsedRules;
+ }
+};
+
+var parseRulesPlugin = stylis_rule_sheet__WEBPACK_IMPORTED_MODULE_1___default()(function (rule) {
+ parsingRules.push(rule);
+});
+
+var _componentId = void 0;
+var _selector = void 0;
+var _selectorRegexp = void 0;
+
+var selfReferenceReplacer = function selfReferenceReplacer(match, offset, string) {
+ if (
+ // the first self-ref is always untouched
+ offset > 0 &&
+ // there should be at least two self-refs to do a replacement (.b > .b)
+ string.slice(0, offset).indexOf(_selector) !== -1 &&
+ // no consecutive self refs (.b.b); that is a precedence boost and treated differently
+ string.slice(offset - _selector.length, offset) !== _selector) {
+ return '.' + _componentId;
+ }
+
+ return match;
+};
+
+/**
+ * When writing a style like
+ *
+ * & + & {
+ * color: red;
+ * }
+ *
+ * The second ampersand should be a reference to the static component class. stylis
+ * has no knowledge of static class so we have to intelligently replace the base selector.
+ */
+var selfReferenceReplacementPlugin = function selfReferenceReplacementPlugin(context, _, selectors) {
+ if (context === 2 && selectors.length && selectors[0].lastIndexOf(_selector) > 0) {
+ // eslint-disable-next-line no-param-reassign
+ selectors[0] = selectors[0].replace(_selectorRegexp, selfReferenceReplacer);
+ }
+};
+
+stylis.use([selfReferenceReplacementPlugin, parseRulesPlugin, returnRulesPlugin]);
+stylisSplitter.use([parseRulesPlugin, returnRulesPlugin]);
+
+var splitByRules = function splitByRules(css) {
+ return stylisSplitter('', css);
+};
+
+function stringifyRules(rules, selector, prefix) {
+ var componentId = arguments.length > 3 && arguments[3] !== undefined ? arguments[3] : '&';
+
+ var flatCSS = rules.join('').replace(COMMENT_REGEX, ''); // replace JS comments
+
+ var cssStr = selector && prefix ? prefix + ' ' + selector + ' { ' + flatCSS + ' }' : flatCSS;
+
+ // stylis has no concept of state to be passed to plugins
+ // but since JS is single=threaded, we can rely on that to ensure
+ // these properties stay in sync with the current stylis run
+ _componentId = componentId;
+ _selector = selector;
+ _selectorRegexp = new RegExp('\\' + _selector + '\\b', 'g');
+
+ return stylis(prefix || !selector ? '' : selector, cssStr);
+}
+
+//
+/* eslint-disable camelcase, no-undef */
+
+var getNonce = (function () {
+ return true ? __webpack_require__.nc : 0;
+});
+
+//
+/* These are helpers for the StyleTags to keep track of the injected
+ * rule names for each (component) ID that they're keeping track of.
+ * They're crucial for detecting whether a name has already been
+ * injected.
+ * (This excludes rehydrated names) */
+
+/* adds a new ID:name pairing to a names dictionary */
+var addNameForId = function addNameForId(names, id, name) {
+ if (name) {
+ // eslint-disable-next-line no-param-reassign
+ var namesForId = names[id] || (names[id] = Object.create(null));
+ namesForId[name] = true;
+ }
+};
+
+/* resets an ID entirely by overwriting it in the dictionary */
+var resetIdNames = function resetIdNames(names, id) {
+ // eslint-disable-next-line no-param-reassign
+ names[id] = Object.create(null);
+};
+
+/* factory for a names dictionary checking the existance of an ID:name pairing */
+var hasNameForId = function hasNameForId(names) {
+ return function (id, name) {
+ return names[id] !== undefined && names[id][name];
+ };
+};
+
+/* stringifies names for the html/element output */
+var stringifyNames = function stringifyNames(names) {
+ var str = '';
+ // eslint-disable-next-line guard-for-in
+ for (var id in names) {
+ str += Object.keys(names[id]).join(' ') + ' ';
+ }
+ return str.trim();
+};
+
+/* clones the nested names dictionary */
+var cloneNames = function cloneNames(names) {
+ var clone = Object.create(null);
+ // eslint-disable-next-line guard-for-in
+ for (var id in names) {
+ clone[id] = _extends({}, names[id]);
+ }
+ return clone;
+};
+
+//
+
+/* These are helpers that deal with the insertRule (aka speedy) API
+ * They are used in the StyleTags and specifically the speedy tag
+ */
+
+/* retrieve a sheet for a given style tag */
+var sheetForTag = function sheetForTag(tag) {
+ // $FlowFixMe
+ if (tag.sheet) return tag.sheet;
+
+ /* Firefox quirk requires us to step through all stylesheets to find one owned by the given tag */
+ var size = tag.ownerDocument.styleSheets.length;
+ for (var i = 0; i < size; i += 1) {
+ var sheet = tag.ownerDocument.styleSheets[i];
+ // $FlowFixMe
+ if (sheet.ownerNode === tag) return sheet;
+ }
+
+ /* we should always be able to find a tag */
+ throw new StyledComponentsError(10);
+};
+
+/* insert a rule safely and return whether it was actually injected */
+var safeInsertRule = function safeInsertRule(sheet, cssRule, index) {
+ /* abort early if cssRule string is falsy */
+ if (!cssRule) return false;
+
+ var maxIndex = sheet.cssRules.length;
+
+ try {
+ /* use insertRule and cap passed index with maxIndex (no of cssRules) */
+ sheet.insertRule(cssRule, index <= maxIndex ? index : maxIndex);
+ } catch (err) {
+ /* any error indicates an invalid rule */
+ return false;
+ }
+
+ return true;
+};
+
+/* deletes `size` rules starting from `removalIndex` */
+var deleteRules = function deleteRules(sheet, removalIndex, size) {
+ var lowerBound = removalIndex - size;
+ for (var i = removalIndex; i > lowerBound; i -= 1) {
+ sheet.deleteRule(i);
+ }
+};
+
+//
+
+/* this marker separates component styles and is important for rehydration */
+var makeTextMarker = function makeTextMarker(id) {
+ return '\n/* sc-component-id: ' + id + ' */\n';
+};
+
+/* add up all numbers in array up until and including the index */
+var addUpUntilIndex = function addUpUntilIndex(sizes, index) {
+ var totalUpToIndex = 0;
+ for (var i = 0; i <= index; i += 1) {
+ totalUpToIndex += sizes[i];
+ }
+
+ return totalUpToIndex;
+};
+
+/* create a new style tag after lastEl */
+var makeStyleTag = function makeStyleTag(target, tagEl, insertBefore) {
+ var targetDocument = document;
+ if (target) targetDocument = target.ownerDocument;else if (tagEl) targetDocument = tagEl.ownerDocument;
+
+ var el = targetDocument.createElement('style');
+ el.setAttribute(SC_ATTR, '');
+ el.setAttribute(SC_VERSION_ATTR, "4.4.1");
+
+ var nonce = getNonce();
+ if (nonce) {
+ el.setAttribute('nonce', nonce);
+ }
+
+ /* Work around insertRule quirk in EdgeHTML */
+ el.appendChild(targetDocument.createTextNode(''));
+
+ if (target && !tagEl) {
+ /* Append to target when no previous element was passed */
+ target.appendChild(el);
+ } else {
+ if (!tagEl || !target || !tagEl.parentNode) {
+ throw new StyledComponentsError(6);
+ }
+
+ /* Insert new style tag after the previous one */
+ tagEl.parentNode.insertBefore(el, insertBefore ? tagEl : tagEl.nextSibling);
+ }
+
+ return el;
+};
+
+/* takes a css factory function and outputs an html styled tag factory */
+var wrapAsHtmlTag = function wrapAsHtmlTag(css, names) {
+ return function (additionalAttrs) {
+ var nonce = getNonce();
+ var attrs = [nonce && 'nonce="' + nonce + '"', SC_ATTR + '="' + stringifyNames(names) + '"', SC_VERSION_ATTR + '="' + "4.4.1" + '"', additionalAttrs];
+
+ var htmlAttr = attrs.filter(Boolean).join(' ');
+ return '';
+ };
+};
+
+/* takes a css factory function and outputs an element factory */
+var wrapAsElement = function wrapAsElement(css, names) {
+ return function () {
+ var _props;
+
+ var props = (_props = {}, _props[SC_ATTR] = stringifyNames(names), _props[SC_VERSION_ATTR] = "4.4.1", _props);
+
+ var nonce = getNonce();
+ if (nonce) {
+ // $FlowFixMe
+ props.nonce = nonce;
+ }
+
+ // eslint-disable-next-line react/no-danger
+ return react__WEBPACK_IMPORTED_MODULE_2___default().createElement('style', _extends({}, props, { dangerouslySetInnerHTML: { __html: css() } }));
+ };
+};
+
+var getIdsFromMarkersFactory = function getIdsFromMarkersFactory(markers) {
+ return function () {
+ return Object.keys(markers);
+ };
+};
+
+/* speedy tags utilise insertRule */
+var makeSpeedyTag = function makeSpeedyTag(el, getImportRuleTag) {
+ var names = Object.create(null);
+ var markers = Object.create(null);
+ var sizes = [];
+
+ var extractImport = getImportRuleTag !== undefined;
+ /* indicates whether getImportRuleTag was called */
+ var usedImportRuleTag = false;
+
+ var insertMarker = function insertMarker(id) {
+ var prev = markers[id];
+ if (prev !== undefined) {
+ return prev;
+ }
+
+ markers[id] = sizes.length;
+ sizes.push(0);
+ resetIdNames(names, id);
+
+ return markers[id];
+ };
+
+ var insertRules = function insertRules(id, cssRules, name) {
+ var marker = insertMarker(id);
+ var sheet = sheetForTag(el);
+ var insertIndex = addUpUntilIndex(sizes, marker);
+
+ var injectedRules = 0;
+ var importRules = [];
+ var cssRulesSize = cssRules.length;
+
+ for (var i = 0; i < cssRulesSize; i += 1) {
+ var cssRule = cssRules[i];
+ var mayHaveImport = extractImport; /* @import rules are reordered to appear first */
+ if (mayHaveImport && cssRule.indexOf('@import') !== -1) {
+ importRules.push(cssRule);
+ } else if (safeInsertRule(sheet, cssRule, insertIndex + injectedRules)) {
+ mayHaveImport = false;
+ injectedRules += 1;
+ }
+ }
+
+ if (extractImport && importRules.length > 0) {
+ usedImportRuleTag = true;
+ // $FlowFixMe
+ getImportRuleTag().insertRules(id + '-import', importRules);
+ }
+
+ sizes[marker] += injectedRules; /* add up no of injected rules */
+ addNameForId(names, id, name);
+ };
+
+ var removeRules = function removeRules(id) {
+ var marker = markers[id];
+ if (marker === undefined) return;
+ // $FlowFixMe
+ if (el.isConnected === false) return;
+
+ var size = sizes[marker];
+ var sheet = sheetForTag(el);
+ var removalIndex = addUpUntilIndex(sizes, marker) - 1;
+ deleteRules(sheet, removalIndex, size);
+ sizes[marker] = 0;
+ resetIdNames(names, id);
+
+ if (extractImport && usedImportRuleTag) {
+ // $FlowFixMe
+ getImportRuleTag().removeRules(id + '-import');
+ }
+ };
+
+ var css = function css() {
+ var _sheetForTag = sheetForTag(el),
+ cssRules = _sheetForTag.cssRules;
+
+ var str = '';
+
+ // eslint-disable-next-line guard-for-in
+ for (var id in markers) {
+ str += makeTextMarker(id);
+ var marker = markers[id];
+ var end = addUpUntilIndex(sizes, marker);
+ var size = sizes[marker];
+ for (var i = end - size; i < end; i += 1) {
+ var rule = cssRules[i];
+ if (rule !== undefined) {
+ str += rule.cssText;
+ }
+ }
+ }
+
+ return str;
+ };
+
+ return {
+ clone: function clone() {
+ throw new StyledComponentsError(5);
+ },
+
+ css: css,
+ getIds: getIdsFromMarkersFactory(markers),
+ hasNameForId: hasNameForId(names),
+ insertMarker: insertMarker,
+ insertRules: insertRules,
+ removeRules: removeRules,
+ sealed: false,
+ styleTag: el,
+ toElement: wrapAsElement(css, names),
+ toHTML: wrapAsHtmlTag(css, names)
+ };
+};
+
+var makeTextNode = function makeTextNode(targetDocument, id) {
+ return targetDocument.createTextNode(makeTextMarker(id));
+};
+
+var makeBrowserTag = function makeBrowserTag(el, getImportRuleTag) {
+ var names = Object.create(null);
+ var markers = Object.create(null);
+
+ var extractImport = getImportRuleTag !== undefined;
+
+ /* indicates whether getImportRuleTag was called */
+ var usedImportRuleTag = false;
+
+ var insertMarker = function insertMarker(id) {
+ var prev = markers[id];
+ if (prev !== undefined) {
+ return prev;
+ }
+
+ markers[id] = makeTextNode(el.ownerDocument, id);
+ el.appendChild(markers[id]);
+ names[id] = Object.create(null);
+
+ return markers[id];
+ };
+
+ var insertRules = function insertRules(id, cssRules, name) {
+ var marker = insertMarker(id);
+ var importRules = [];
+ var cssRulesSize = cssRules.length;
+
+ for (var i = 0; i < cssRulesSize; i += 1) {
+ var rule = cssRules[i];
+ var mayHaveImport = extractImport;
+ if (mayHaveImport && rule.indexOf('@import') !== -1) {
+ importRules.push(rule);
+ } else {
+ mayHaveImport = false;
+ var separator = i === cssRulesSize - 1 ? '' : ' ';
+ marker.appendData('' + rule + separator);
+ }
+ }
+
+ addNameForId(names, id, name);
+
+ if (extractImport && importRules.length > 0) {
+ usedImportRuleTag = true;
+ // $FlowFixMe
+ getImportRuleTag().insertRules(id + '-import', importRules);
+ }
+ };
+
+ var removeRules = function removeRules(id) {
+ var marker = markers[id];
+ if (marker === undefined) return;
+
+ /* create new empty text node and replace the current one */
+ var newMarker = makeTextNode(el.ownerDocument, id);
+ el.replaceChild(newMarker, marker);
+ markers[id] = newMarker;
+ resetIdNames(names, id);
+
+ if (extractImport && usedImportRuleTag) {
+ // $FlowFixMe
+ getImportRuleTag().removeRules(id + '-import');
+ }
+ };
+
+ var css = function css() {
+ var str = '';
+
+ // eslint-disable-next-line guard-for-in
+ for (var id in markers) {
+ str += markers[id].data;
+ }
+
+ return str;
+ };
+
+ return {
+ clone: function clone() {
+ throw new StyledComponentsError(5);
+ },
+
+ css: css,
+ getIds: getIdsFromMarkersFactory(markers),
+ hasNameForId: hasNameForId(names),
+ insertMarker: insertMarker,
+ insertRules: insertRules,
+ removeRules: removeRules,
+ sealed: false,
+ styleTag: el,
+ toElement: wrapAsElement(css, names),
+ toHTML: wrapAsHtmlTag(css, names)
+ };
+};
+
+var makeServerTag = function makeServerTag(namesArg, markersArg) {
+ var names = namesArg === undefined ? Object.create(null) : namesArg;
+ var markers = markersArg === undefined ? Object.create(null) : markersArg;
+
+ var insertMarker = function insertMarker(id) {
+ var prev = markers[id];
+ if (prev !== undefined) {
+ return prev;
+ }
+
+ return markers[id] = [''];
+ };
+
+ var insertRules = function insertRules(id, cssRules, name) {
+ var marker = insertMarker(id);
+ marker[0] += cssRules.join(' ');
+ addNameForId(names, id, name);
+ };
+
+ var removeRules = function removeRules(id) {
+ var marker = markers[id];
+ if (marker === undefined) return;
+ marker[0] = '';
+ resetIdNames(names, id);
+ };
+
+ var css = function css() {
+ var str = '';
+ // eslint-disable-next-line guard-for-in
+ for (var id in markers) {
+ var cssForId = markers[id][0];
+ if (cssForId) {
+ str += makeTextMarker(id) + cssForId;
+ }
+ }
+ return str;
+ };
+
+ var clone = function clone() {
+ var namesClone = cloneNames(names);
+ var markersClone = Object.create(null);
+
+ // eslint-disable-next-line guard-for-in
+ for (var id in markers) {
+ markersClone[id] = [markers[id][0]];
+ }
+
+ return makeServerTag(namesClone, markersClone);
+ };
+
+ var tag = {
+ clone: clone,
+ css: css,
+ getIds: getIdsFromMarkersFactory(markers),
+ hasNameForId: hasNameForId(names),
+ insertMarker: insertMarker,
+ insertRules: insertRules,
+ removeRules: removeRules,
+ sealed: false,
+ styleTag: null,
+ toElement: wrapAsElement(css, names),
+ toHTML: wrapAsHtmlTag(css, names)
+ };
+
+ return tag;
+};
+
+var makeTag = function makeTag(target, tagEl, forceServer, insertBefore, getImportRuleTag) {
+ if (IS_BROWSER && !forceServer) {
+ var el = makeStyleTag(target, tagEl, insertBefore);
+
+ if (DISABLE_SPEEDY) {
+ return makeBrowserTag(el, getImportRuleTag);
+ } else {
+ return makeSpeedyTag(el, getImportRuleTag);
+ }
+ }
+
+ return makeServerTag();
+};
+
+var rehydrate = function rehydrate(tag, els, extracted) {
+ /* add all extracted components to the new tag */
+ for (var i = 0, len = extracted.length; i < len; i += 1) {
+ var _extracted$i = extracted[i],
+ componentId = _extracted$i.componentId,
+ cssFromDOM = _extracted$i.cssFromDOM;
+
+ var cssRules = splitByRules(cssFromDOM);
+ tag.insertRules(componentId, cssRules);
+ }
+
+ /* remove old HTMLStyleElements, since they have been rehydrated */
+ for (var _i = 0, _len = els.length; _i < _len; _i += 1) {
+ var el = els[_i];
+ if (el.parentNode) {
+ el.parentNode.removeChild(el);
+ }
+ }
+};
+
+//
+
+var SPLIT_REGEX = /\s+/;
+
+/* determine the maximum number of components before tags are sharded */
+var MAX_SIZE = void 0;
+if (IS_BROWSER) {
+ /* in speedy mode we can keep a lot more rules in a sheet before a slowdown can be expected */
+ MAX_SIZE = DISABLE_SPEEDY ? 40 : 1000;
+} else {
+ /* for servers we do not need to shard at all */
+ MAX_SIZE = -1;
+}
+
+var sheetRunningId = 0;
+var master = void 0;
+
+var StyleSheet = function () {
+
+ /* a map from ids to tags */
+
+ /* deferred rules for a given id */
+
+ /* this is used for not reinjecting rules via hasNameForId() */
+
+ /* when rules for an id are removed using remove() we have to ignore rehydratedNames for it */
+
+ /* a list of tags belonging to this StyleSheet */
+
+ /* a tag for import rules */
+
+ /* current capacity until a new tag must be created */
+
+ /* children (aka clones) of this StyleSheet inheriting all and future injections */
+
+ function StyleSheet() {
+ var _this = this;
+
+ var target = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : IS_BROWSER ? document.head : null;
+ var forceServer = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : false;
+ classCallCheck(this, StyleSheet);
+
+ this.getImportRuleTag = function () {
+ var importRuleTag = _this.importRuleTag;
+
+ if (importRuleTag !== undefined) {
+ return importRuleTag;
+ }
+
+ var firstTag = _this.tags[0];
+ var insertBefore = true;
+
+ return _this.importRuleTag = makeTag(_this.target, firstTag ? firstTag.styleTag : null, _this.forceServer, insertBefore);
+ };
+
+ sheetRunningId += 1;
+ this.id = sheetRunningId;
+ this.forceServer = forceServer;
+ this.target = forceServer ? null : target;
+ this.tagMap = {};
+ this.deferred = {};
+ this.rehydratedNames = {};
+ this.ignoreRehydratedNames = {};
+ this.tags = [];
+ this.capacity = 1;
+ this.clones = [];
+ }
+
+ /* rehydrate all SSR'd style tags */
+
+
+ StyleSheet.prototype.rehydrate = function rehydrate$$1() {
+ if (!IS_BROWSER || this.forceServer) return this;
+
+ var els = [];
+ var extracted = [];
+ var isStreamed = false;
+
+ /* retrieve all of our SSR style elements from the DOM */
+ var nodes = document.querySelectorAll('style[' + SC_ATTR + '][' + SC_VERSION_ATTR + '="' + "4.4.1" + '"]');
+
+ var nodesSize = nodes.length;
+
+ /* abort rehydration if no previous style tags were found */
+ if (!nodesSize) return this;
+
+ for (var i = 0; i < nodesSize; i += 1) {
+ var el = nodes[i];
+
+ /* check if style tag is a streamed tag */
+ if (!isStreamed) isStreamed = !!el.getAttribute(SC_STREAM_ATTR);
+
+ /* retrieve all component names */
+ var elNames = (el.getAttribute(SC_ATTR) || '').trim().split(SPLIT_REGEX);
+ var elNamesSize = elNames.length;
+ for (var j = 0, name; j < elNamesSize; j += 1) {
+ name = elNames[j];
+ /* add rehydrated name to sheet to avoid re-adding styles */
+ this.rehydratedNames[name] = true;
+ }
+
+ /* extract all components and their CSS */
+ extracted.push.apply(extracted, extractComps(el.textContent));
+
+ /* store original HTMLStyleElement */
+ els.push(el);
+ }
+
+ /* abort rehydration if nothing was extracted */
+ var extractedSize = extracted.length;
+ if (!extractedSize) return this;
+
+ /* create a tag to be used for rehydration */
+ var tag = this.makeTag(null);
+
+ rehydrate(tag, els, extracted);
+
+ /* reset capacity and adjust MAX_SIZE by the initial size of the rehydration */
+ this.capacity = Math.max(1, MAX_SIZE - extractedSize);
+ this.tags.push(tag);
+
+ /* retrieve all component ids */
+ for (var _j = 0; _j < extractedSize; _j += 1) {
+ this.tagMap[extracted[_j].componentId] = tag;
+ }
+
+ return this;
+ };
+
+ /* retrieve a "master" instance of StyleSheet which is typically used when no other is available
+ * The master StyleSheet is targeted by createGlobalStyle, keyframes, and components outside of any
+ * StyleSheetManager's context */
+
+
+ /* reset the internal "master" instance */
+ StyleSheet.reset = function reset() {
+ var forceServer = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : false;
+
+ master = new StyleSheet(undefined, forceServer).rehydrate();
+ };
+
+ /* adds "children" to the StyleSheet that inherit all of the parents' rules
+ * while their own rules do not affect the parent */
+
+
+ StyleSheet.prototype.clone = function clone() {
+ var sheet = new StyleSheet(this.target, this.forceServer);
+
+ /* add to clone array */
+ this.clones.push(sheet);
+
+ /* clone all tags */
+ sheet.tags = this.tags.map(function (tag) {
+ var ids = tag.getIds();
+ var newTag = tag.clone();
+
+ /* reconstruct tagMap */
+ for (var i = 0; i < ids.length; i += 1) {
+ sheet.tagMap[ids[i]] = newTag;
+ }
+
+ return newTag;
+ });
+
+ /* clone other maps */
+ sheet.rehydratedNames = _extends({}, this.rehydratedNames);
+ sheet.deferred = _extends({}, this.deferred);
+
+ return sheet;
+ };
+
+ /* force StyleSheet to create a new tag on the next injection */
+
+
+ StyleSheet.prototype.sealAllTags = function sealAllTags() {
+ this.capacity = 1;
+
+ this.tags.forEach(function (tag) {
+ // eslint-disable-next-line no-param-reassign
+ tag.sealed = true;
+ });
+ };
+
+ StyleSheet.prototype.makeTag = function makeTag$$1(tag) {
+ var lastEl = tag ? tag.styleTag : null;
+ var insertBefore = false;
+
+ return makeTag(this.target, lastEl, this.forceServer, insertBefore, this.getImportRuleTag);
+ };
+
+ /* get a tag for a given componentId, assign the componentId to one, or shard */
+ StyleSheet.prototype.getTagForId = function getTagForId(id) {
+ /* simply return a tag, when the componentId was already assigned one */
+ var prev = this.tagMap[id];
+ if (prev !== undefined && !prev.sealed) {
+ return prev;
+ }
+
+ var tag = this.tags[this.tags.length - 1];
+
+ /* shard (create a new tag) if the tag is exhausted (See MAX_SIZE) */
+ this.capacity -= 1;
+
+ if (this.capacity === 0) {
+ this.capacity = MAX_SIZE;
+ tag = this.makeTag(tag);
+ this.tags.push(tag);
+ }
+
+ return this.tagMap[id] = tag;
+ };
+
+ /* mainly for createGlobalStyle to check for its id */
+
+
+ StyleSheet.prototype.hasId = function hasId(id) {
+ return this.tagMap[id] !== undefined;
+ };
+
+ /* caching layer checking id+name to already have a corresponding tag and injected rules */
+
+
+ StyleSheet.prototype.hasNameForId = function hasNameForId(id, name) {
+ /* exception for rehydrated names which are checked separately */
+ if (this.ignoreRehydratedNames[id] === undefined && this.rehydratedNames[name]) {
+ return true;
+ }
+
+ var tag = this.tagMap[id];
+ return tag !== undefined && tag.hasNameForId(id, name);
+ };
+
+ /* registers a componentId and registers it on its tag */
+
+
+ StyleSheet.prototype.deferredInject = function deferredInject(id, cssRules) {
+ /* don't inject when the id is already registered */
+ if (this.tagMap[id] !== undefined) return;
+
+ var clones = this.clones;
+
+ for (var i = 0; i < clones.length; i += 1) {
+ clones[i].deferredInject(id, cssRules);
+ }
+
+ this.getTagForId(id).insertMarker(id);
+ this.deferred[id] = cssRules;
+ };
+
+ /* injects rules for a given id with a name that will need to be cached */
+
+
+ StyleSheet.prototype.inject = function inject(id, cssRules, name) {
+ var clones = this.clones;
+
+
+ for (var i = 0; i < clones.length; i += 1) {
+ clones[i].inject(id, cssRules, name);
+ }
+
+ var tag = this.getTagForId(id);
+
+ /* add deferred rules for component */
+ if (this.deferred[id] !== undefined) {
+ // Combine passed cssRules with previously deferred CSS rules
+ // NOTE: We cannot mutate the deferred array itself as all clones
+ // do the same (see clones[i].inject)
+ var rules = this.deferred[id].concat(cssRules);
+ tag.insertRules(id, rules, name);
+
+ this.deferred[id] = undefined;
+ } else {
+ tag.insertRules(id, cssRules, name);
+ }
+ };
+
+ /* removes all rules for a given id, which doesn't remove its marker but resets it */
+
+
+ StyleSheet.prototype.remove = function remove(id) {
+ var tag = this.tagMap[id];
+ if (tag === undefined) return;
+
+ var clones = this.clones;
+
+ for (var i = 0; i < clones.length; i += 1) {
+ clones[i].remove(id);
+ }
+
+ /* remove all rules from the tag */
+ tag.removeRules(id);
+
+ /* ignore possible rehydrated names */
+ this.ignoreRehydratedNames[id] = true;
+
+ /* delete possible deferred rules */
+ this.deferred[id] = undefined;
+ };
+
+ StyleSheet.prototype.toHTML = function toHTML() {
+ return this.tags.map(function (tag) {
+ return tag.toHTML();
+ }).join('');
+ };
+
+ StyleSheet.prototype.toReactElements = function toReactElements() {
+ var id = this.id;
+
+
+ return this.tags.map(function (tag, i) {
+ var key = 'sc-' + id + '-' + i;
+ return (0,react__WEBPACK_IMPORTED_MODULE_2__.cloneElement)(tag.toElement(), { key: key });
+ });
+ };
+
+ createClass(StyleSheet, null, [{
+ key: 'master',
+ get: function get$$1() {
+ return master || (master = new StyleSheet().rehydrate());
+ }
+
+ /* NOTE: This is just for backwards-compatibility with jest-styled-components */
+
+ }, {
+ key: 'instance',
+ get: function get$$1() {
+ return StyleSheet.master;
+ }
+ }]);
+ return StyleSheet;
+}();
+
+//
+
+var Keyframes = function () {
+ function Keyframes(name, rules) {
+ var _this = this;
+
+ classCallCheck(this, Keyframes);
+
+ this.inject = function (styleSheet) {
+ if (!styleSheet.hasNameForId(_this.id, _this.name)) {
+ styleSheet.inject(_this.id, _this.rules, _this.name);
+ }
+ };
+
+ this.toString = function () {
+ throw new StyledComponentsError(12, String(_this.name));
+ };
+
+ this.name = name;
+ this.rules = rules;
+
+ this.id = 'sc-keyframes-' + name;
+ }
+
+ Keyframes.prototype.getName = function getName() {
+ return this.name;
+ };
+
+ return Keyframes;
+}();
+
+//
+
+/**
+ * inlined version of
+ * https://github.com/facebook/fbjs/blob/master/packages/fbjs/src/core/hyphenateStyleName.js
+ */
+
+var uppercasePattern = /([A-Z])/g;
+var msPattern = /^ms-/;
+
+/**
+ * Hyphenates a camelcased CSS property name, for example:
+ *
+ * > hyphenateStyleName('backgroundColor')
+ * < "background-color"
+ * > hyphenateStyleName('MozTransition')
+ * < "-moz-transition"
+ * > hyphenateStyleName('msTransition')
+ * < "-ms-transition"
+ *
+ * As Modernizr suggests (http://modernizr.com/docs/#prefixed), an `ms` prefix
+ * is converted to `-ms-`.
+ *
+ * @param {string} string
+ * @return {string}
+ */
+function hyphenateStyleName(string) {
+ return string.replace(uppercasePattern, '-$1').toLowerCase().replace(msPattern, '-ms-');
+}
+
+//
+
+// Taken from https://github.com/facebook/react/blob/b87aabdfe1b7461e7331abb3601d9e6bb27544bc/packages/react-dom/src/shared/dangerousStyleValue.js
+function addUnitIfNeeded(name, value) {
+ // https://github.com/amilajack/eslint-plugin-flowtype-errors/issues/133
+ // $FlowFixMe
+ if (value == null || typeof value === 'boolean' || value === '') {
+ return '';
+ }
+
+ if (typeof value === 'number' && value !== 0 && !(name in _emotion_unitless__WEBPACK_IMPORTED_MODULE_3__["default"])) {
+ return value + 'px'; // Presumes implicit 'px' suffix for unitless numbers
+ }
+
+ return String(value).trim();
+}
+
+//
+
+/**
+ * It's falsish not falsy because 0 is allowed.
+ */
+var isFalsish = function isFalsish(chunk) {
+ return chunk === undefined || chunk === null || chunk === false || chunk === '';
+};
+
+var objToCssArray = function objToCssArray(obj, prevKey) {
+ var rules = [];
+ var keys = Object.keys(obj);
+
+ keys.forEach(function (key) {
+ if (!isFalsish(obj[key])) {
+ if (isPlainObject(obj[key])) {
+ rules.push.apply(rules, objToCssArray(obj[key], key));
+
+ return rules;
+ } else if (isFunction(obj[key])) {
+ rules.push(hyphenateStyleName(key) + ':', obj[key], ';');
+
+ return rules;
+ }
+ rules.push(hyphenateStyleName(key) + ': ' + addUnitIfNeeded(key, obj[key]) + ';');
+ }
+ return rules;
+ });
+
+ return prevKey ? [prevKey + ' {'].concat(rules, ['}']) : rules;
+};
+
+function flatten(chunk, executionContext, styleSheet) {
+ if (Array.isArray(chunk)) {
+ var ruleSet = [];
+
+ for (var i = 0, len = chunk.length, result; i < len; i += 1) {
+ result = flatten(chunk[i], executionContext, styleSheet);
+
+ if (result === null) continue;else if (Array.isArray(result)) ruleSet.push.apply(ruleSet, result);else ruleSet.push(result);
+ }
+
+ return ruleSet;
+ }
+
+ if (isFalsish(chunk)) {
+ return null;
+ }
+
+ /* Handle other components */
+ if (isStyledComponent(chunk)) {
+ return '.' + chunk.styledComponentId;
+ }
+
+ /* Either execute or defer the function */
+ if (isFunction(chunk)) {
+ if (isStatelessFunction(chunk) && executionContext) {
+ var _result = chunk(executionContext);
+
+ if ( true && (0,react_is__WEBPACK_IMPORTED_MODULE_4__.isElement)(_result)) {
+ // eslint-disable-next-line no-console
+ console.warn(getComponentName(chunk) + ' is not a styled component and cannot be referred to via component selector. See https://www.styled-components.com/docs/advanced#referring-to-other-components for more details.');
+ }
+
+ return flatten(_result, executionContext, styleSheet);
+ } else return chunk;
+ }
+
+ if (chunk instanceof Keyframes) {
+ if (styleSheet) {
+ chunk.inject(styleSheet);
+ return chunk.getName();
+ } else return chunk;
+ }
+
+ /* Handle objects */
+ return isPlainObject(chunk) ? objToCssArray(chunk) : chunk.toString();
+}
+
+//
+
+function css(styles) {
+ for (var _len = arguments.length, interpolations = Array(_len > 1 ? _len - 1 : 0), _key = 1; _key < _len; _key++) {
+ interpolations[_key - 1] = arguments[_key];
+ }
+
+ if (isFunction(styles) || isPlainObject(styles)) {
+ // $FlowFixMe
+ return flatten(interleave(EMPTY_ARRAY, [styles].concat(interpolations)));
+ }
+
+ // $FlowFixMe
+ return flatten(interleave(styles, interpolations));
+}
+
+//
+
+function constructWithOptions(componentConstructor, tag) {
+ var options = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : EMPTY_OBJECT;
+
+ if (!(0,react_is__WEBPACK_IMPORTED_MODULE_4__.isValidElementType)(tag)) {
+ throw new StyledComponentsError(1, String(tag));
+ }
+
+ /* This is callable directly as a template function */
+ // $FlowFixMe: Not typed to avoid destructuring arguments
+ var templateFunction = function templateFunction() {
+ return componentConstructor(tag, options, css.apply(undefined, arguments));
+ };
+
+ /* If config methods are called, wrap up a new template function and merge options */
+ templateFunction.withConfig = function (config) {
+ return constructWithOptions(componentConstructor, tag, _extends({}, options, config));
+ };
+
+ /* Modify/inject new props at runtime */
+ templateFunction.attrs = function (attrs) {
+ return constructWithOptions(componentConstructor, tag, _extends({}, options, {
+ attrs: Array.prototype.concat(options.attrs, attrs).filter(Boolean)
+ }));
+ };
+
+ return templateFunction;
+}
+
+//
+// Source: https://github.com/garycourt/murmurhash-js/blob/master/murmurhash2_gc.js
+function murmurhash(c) {
+ for (var e = c.length | 0, a = e | 0, d = 0, b; e >= 4;) {
+ b = c.charCodeAt(d) & 255 | (c.charCodeAt(++d) & 255) << 8 | (c.charCodeAt(++d) & 255) << 16 | (c.charCodeAt(++d) & 255) << 24, b = 1540483477 * (b & 65535) + ((1540483477 * (b >>> 16) & 65535) << 16), b ^= b >>> 24, b = 1540483477 * (b & 65535) + ((1540483477 * (b >>> 16) & 65535) << 16), a = 1540483477 * (a & 65535) + ((1540483477 * (a >>> 16) & 65535) << 16) ^ b, e -= 4, ++d;
+ }
+ switch (e) {
+ case 3:
+ a ^= (c.charCodeAt(d + 2) & 255) << 16;
+ case 2:
+ a ^= (c.charCodeAt(d + 1) & 255) << 8;
+ case 1:
+ a ^= c.charCodeAt(d) & 255, a = 1540483477 * (a & 65535) + ((1540483477 * (a >>> 16) & 65535) << 16);
+ }
+ a ^= a >>> 13;
+ a = 1540483477 * (a & 65535) + ((1540483477 * (a >>> 16) & 65535) << 16);
+ return (a ^ a >>> 15) >>> 0;
+}
+
+//
+/* eslint-disable no-bitwise */
+
+/* This is the "capacity" of our alphabet i.e. 2x26 for all letters plus their capitalised
+ * counterparts */
+var charsLength = 52;
+
+/* start at 75 for 'a' until 'z' (25) and then start at 65 for capitalised letters */
+var getAlphabeticChar = function getAlphabeticChar(code) {
+ return String.fromCharCode(code + (code > 25 ? 39 : 97));
+};
+
+/* input a number, usually a hash and convert it to base-52 */
+function generateAlphabeticName(code) {
+ var name = '';
+ var x = void 0;
+
+ /* get a char and divide by alphabet-length */
+ for (x = code; x > charsLength; x = Math.floor(x / charsLength)) {
+ name = getAlphabeticChar(x % charsLength) + name;
+ }
+
+ return getAlphabeticChar(x % charsLength) + name;
+}
+
+//
+
+function hasFunctionObjectKey(obj) {
+ // eslint-disable-next-line guard-for-in, no-restricted-syntax
+ for (var key in obj) {
+ if (isFunction(obj[key])) {
+ return true;
+ }
+ }
+
+ return false;
+}
+
+function isStaticRules(rules, attrs) {
+ for (var i = 0; i < rules.length; i += 1) {
+ var rule = rules[i];
+
+ // recursive case
+ if (Array.isArray(rule) && !isStaticRules(rule, attrs)) {
+ return false;
+ } else if (isFunction(rule) && !isStyledComponent(rule)) {
+ // functions are allowed to be static if they're just being
+ // used to get the classname of a nested styled component
+ return false;
+ }
+ }
+
+ if (attrs.some(function (x) {
+ return isFunction(x) || hasFunctionObjectKey(x);
+ })) return false;
+
+ return true;
+}
+
+//
+
+/* combines hashStr (murmurhash) and nameGenerator for convenience */
+var hasher = function hasher(str) {
+ return generateAlphabeticName(murmurhash(str));
+};
+
+/*
+ ComponentStyle is all the CSS-specific stuff, not
+ the React-specific stuff.
+ */
+
+var ComponentStyle = function () {
+ function ComponentStyle(rules, attrs, componentId) {
+ classCallCheck(this, ComponentStyle);
+
+ this.rules = rules;
+ this.isStatic = false && 0;
+ this.componentId = componentId;
+
+ if (!StyleSheet.master.hasId(componentId)) {
+ StyleSheet.master.deferredInject(componentId, []);
+ }
+ }
+
+ /*
+ * Flattens a rule set into valid CSS
+ * Hashes it, wraps the whole chunk in a .hash1234 {}
+ * Returns the hash to be injected on render()
+ * */
+
+
+ ComponentStyle.prototype.generateAndInjectStyles = function generateAndInjectStyles(executionContext, styleSheet) {
+ var isStatic = this.isStatic,
+ componentId = this.componentId,
+ lastClassName = this.lastClassName;
+
+ if (IS_BROWSER && isStatic && typeof lastClassName === 'string' && styleSheet.hasNameForId(componentId, lastClassName)) {
+ return lastClassName;
+ }
+
+ var flatCSS = flatten(this.rules, executionContext, styleSheet);
+ var name = hasher(this.componentId + flatCSS.join(''));
+ if (!styleSheet.hasNameForId(componentId, name)) {
+ styleSheet.inject(this.componentId, stringifyRules(flatCSS, '.' + name, undefined, componentId), name);
+ }
+
+ this.lastClassName = name;
+ return name;
+ };
+
+ ComponentStyle.generateName = function generateName(str) {
+ return hasher(str);
+ };
+
+ return ComponentStyle;
+}();
+
+//
+
+var LIMIT = 200;
+
+var createWarnTooManyClasses = (function (displayName) {
+ var generatedClasses = {};
+ var warningSeen = false;
+
+ return function (className) {
+ if (!warningSeen) {
+ generatedClasses[className] = true;
+ if (Object.keys(generatedClasses).length >= LIMIT) {
+ // Unable to find latestRule in test environment.
+ /* eslint-disable no-console, prefer-template */
+ console.warn('Over ' + LIMIT + ' classes were generated for component ' + displayName + '. \n' + 'Consider using the attrs method, together with a style object for frequently changed styles.\n' + 'Example:\n' + ' const Component = styled.div.attrs(props => ({\n' + ' style: {\n' + ' background: props.background,\n' + ' },\n' + ' }))`width: 100%;`\n\n' + ' ');
+ warningSeen = true;
+ generatedClasses = {};
+ }
+ }
+ };
+});
+
+//
+
+var determineTheme = (function (props, fallbackTheme) {
+ var defaultProps = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : EMPTY_OBJECT;
+
+ // Props should take precedence over ThemeProvider, which should take precedence over
+ // defaultProps, but React automatically puts defaultProps on props.
+
+ /* eslint-disable react/prop-types, flowtype-errors/show-errors */
+ var isDefaultTheme = defaultProps ? props.theme === defaultProps.theme : false;
+ var theme = props.theme && !isDefaultTheme ? props.theme : fallbackTheme || defaultProps.theme;
+ /* eslint-enable */
+
+ return theme;
+});
+
+//
+var escapeRegex = /[[\].#*$><+~=|^:(),"'`-]+/g;
+var dashesAtEnds = /(^-|-$)/g;
+
+/**
+ * TODO: Explore using CSS.escape when it becomes more available
+ * in evergreen browsers.
+ */
+function escape(str) {
+ return str
+ // Replace all possible CSS selectors
+ .replace(escapeRegex, '-')
+
+ // Remove extraneous hyphens at the start and end
+ .replace(dashesAtEnds, '');
+}
+
+//
+
+function isTag(target) {
+ return typeof target === 'string' && ( true ? target.charAt(0) === target.charAt(0).toLowerCase() : 0);
+}
+
+//
+
+function generateDisplayName(target) {
+ // $FlowFixMe
+ return isTag(target) ? 'styled.' + target : 'Styled(' + getComponentName(target) + ')';
+}
+
+var _TYPE_STATICS;
+
+var REACT_STATICS = {
+ childContextTypes: true,
+ contextTypes: true,
+ defaultProps: true,
+ displayName: true,
+ getDerivedStateFromProps: true,
+ propTypes: true,
+ type: true
+};
+
+var KNOWN_STATICS = {
+ name: true,
+ length: true,
+ prototype: true,
+ caller: true,
+ callee: true,
+ arguments: true,
+ arity: true
+};
+
+var TYPE_STATICS = (_TYPE_STATICS = {}, _TYPE_STATICS[react_is__WEBPACK_IMPORTED_MODULE_4__.ForwardRef] = {
+ $$typeof: true,
+ render: true
+}, _TYPE_STATICS);
+
+var defineProperty$1 = Object.defineProperty,
+ getOwnPropertyNames = Object.getOwnPropertyNames,
+ _Object$getOwnPropert = Object.getOwnPropertySymbols,
+ getOwnPropertySymbols = _Object$getOwnPropert === undefined ? function () {
+ return [];
+} : _Object$getOwnPropert,
+ getOwnPropertyDescriptor = Object.getOwnPropertyDescriptor,
+ getPrototypeOf = Object.getPrototypeOf,
+ objectPrototype = Object.prototype;
+var arrayPrototype = Array.prototype;
+
+
+function hoistNonReactStatics(targetComponent, sourceComponent, blacklist) {
+ if (typeof sourceComponent !== 'string') {
+ // don't hoist over string (html) components
+
+ var inheritedComponent = getPrototypeOf(sourceComponent);
+
+ if (inheritedComponent && inheritedComponent !== objectPrototype) {
+ hoistNonReactStatics(targetComponent, inheritedComponent, blacklist);
+ }
+
+ var keys = arrayPrototype.concat(getOwnPropertyNames(sourceComponent),
+ // $FlowFixMe
+ getOwnPropertySymbols(sourceComponent));
+
+ var targetStatics = TYPE_STATICS[targetComponent.$$typeof] || REACT_STATICS;
+
+ var sourceStatics = TYPE_STATICS[sourceComponent.$$typeof] || REACT_STATICS;
+
+ var i = keys.length;
+ var descriptor = void 0;
+ var key = void 0;
+
+ // eslint-disable-next-line no-plusplus
+ while (i--) {
+ key = keys[i];
+
+ if (
+ // $FlowFixMe
+ !KNOWN_STATICS[key] && !(blacklist && blacklist[key]) && !(sourceStatics && sourceStatics[key]) &&
+ // $FlowFixMe
+ !(targetStatics && targetStatics[key])) {
+ descriptor = getOwnPropertyDescriptor(sourceComponent, key);
+
+ if (descriptor) {
+ try {
+ // Avoid failures from read-only properties
+ defineProperty$1(targetComponent, key, descriptor);
+ } catch (e) {
+ /* fail silently */
+ }
+ }
+ }
+ }
+
+ return targetComponent;
+ }
+
+ return targetComponent;
+}
+
+//
+function isDerivedReactComponent(fn) {
+ return !!(fn && fn.prototype && fn.prototype.isReactComponent);
+}
+
+//
+// Helper to call a given function, only once
+var once = (function (cb) {
+ var called = false;
+
+ return function () {
+ if (!called) {
+ called = true;
+ cb.apply(undefined, arguments);
+ }
+ };
+});
+
+//
+
+var ThemeContext = (0,react__WEBPACK_IMPORTED_MODULE_2__.createContext)();
+
+var ThemeConsumer = ThemeContext.Consumer;
+
+/**
+ * Provide a theme to an entire react component tree via context
+ */
+
+var ThemeProvider = function (_Component) {
+ inherits(ThemeProvider, _Component);
+
+ function ThemeProvider(props) {
+ classCallCheck(this, ThemeProvider);
+
+ var _this = possibleConstructorReturn(this, _Component.call(this, props));
+
+ _this.getContext = (0,memoize_one__WEBPACK_IMPORTED_MODULE_7__["default"])(_this.getContext.bind(_this));
+ _this.renderInner = _this.renderInner.bind(_this);
+ return _this;
+ }
+
+ ThemeProvider.prototype.render = function render() {
+ if (!this.props.children) return null;
+
+ return react__WEBPACK_IMPORTED_MODULE_2___default().createElement(
+ ThemeContext.Consumer,
+ null,
+ this.renderInner
+ );
+ };
+
+ ThemeProvider.prototype.renderInner = function renderInner(outerTheme) {
+ var context = this.getContext(this.props.theme, outerTheme);
+
+ return react__WEBPACK_IMPORTED_MODULE_2___default().createElement(
+ ThemeContext.Provider,
+ { value: context },
+ this.props.children
+ );
+ };
+
+ /**
+ * Get the theme from the props, supporting both (outerTheme) => {}
+ * as well as object notation
+ */
+
+
+ ThemeProvider.prototype.getTheme = function getTheme(theme, outerTheme) {
+ if (isFunction(theme)) {
+ var mergedTheme = theme(outerTheme);
+
+ if ( true && (mergedTheme === null || Array.isArray(mergedTheme) || (typeof mergedTheme === 'undefined' ? 'undefined' : _typeof(mergedTheme)) !== 'object')) {
+ throw new StyledComponentsError(7);
+ }
+
+ return mergedTheme;
+ }
+
+ if (theme === null || Array.isArray(theme) || (typeof theme === 'undefined' ? 'undefined' : _typeof(theme)) !== 'object') {
+ throw new StyledComponentsError(8);
+ }
+
+ return _extends({}, outerTheme, theme);
+ };
+
+ ThemeProvider.prototype.getContext = function getContext(theme, outerTheme) {
+ return this.getTheme(theme, outerTheme);
+ };
+
+ return ThemeProvider;
+}(react__WEBPACK_IMPORTED_MODULE_2__.Component);
+
+//
+
+var CLOSING_TAG_R = /^\s*<\/[a-z]/i;
+
+var ServerStyleSheet = function () {
+ function ServerStyleSheet() {
+ classCallCheck(this, ServerStyleSheet);
+
+ /* The master sheet might be reset, so keep a reference here */
+ this.masterSheet = StyleSheet.master;
+ this.instance = this.masterSheet.clone();
+ this.sealed = false;
+ }
+
+ /**
+ * Mark the ServerStyleSheet as being fully emitted and manually GC it from the
+ * StyleSheet singleton.
+ */
+
+
+ ServerStyleSheet.prototype.seal = function seal() {
+ if (!this.sealed) {
+ /* Remove sealed StyleSheets from the master sheet */
+ var index = this.masterSheet.clones.indexOf(this.instance);
+ this.masterSheet.clones.splice(index, 1);
+ this.sealed = true;
+ }
+ };
+
+ ServerStyleSheet.prototype.collectStyles = function collectStyles(children) {
+ if (this.sealed) {
+ throw new StyledComponentsError(2);
+ }
+
+ return react__WEBPACK_IMPORTED_MODULE_2___default().createElement(
+ StyleSheetManager,
+ { sheet: this.instance },
+ children
+ );
+ };
+
+ ServerStyleSheet.prototype.getStyleTags = function getStyleTags() {
+ this.seal();
+ return this.instance.toHTML();
+ };
+
+ ServerStyleSheet.prototype.getStyleElement = function getStyleElement() {
+ this.seal();
+ return this.instance.toReactElements();
+ };
+
+ ServerStyleSheet.prototype.interleaveWithNodeStream = function interleaveWithNodeStream(readableStream) {
+ var _this = this;
+
+ {
+ throw new StyledComponentsError(3);
+ }
+
+ /* the tag index keeps track of which tags have already been emitted */
+ var instance = this.instance;
+
+ var instanceTagIndex = 0;
+
+ var streamAttr = SC_STREAM_ATTR + '="true"';
+
+ var transformer = new stream.Transform({
+ transform: function appendStyleChunks(chunk, /* encoding */_, callback) {
+ var tags = instance.tags;
+
+ var html = '';
+
+ /* retrieve html for each new style tag */
+ for (; instanceTagIndex < tags.length; instanceTagIndex += 1) {
+ var tag = tags[instanceTagIndex];
+ html += tag.toHTML(streamAttr);
+ }
+
+ /* force our StyleSheets to emit entirely new tags */
+ instance.sealAllTags();
+
+ var renderedHtml = chunk.toString();
+
+ /* prepend style html to chunk, unless the start of the chunk is a closing tag in which case append right after that */
+ if (CLOSING_TAG_R.test(renderedHtml)) {
+ var endOfClosingTag = renderedHtml.indexOf('>');
+
+ this.push(renderedHtml.slice(0, endOfClosingTag + 1) + html + renderedHtml.slice(endOfClosingTag + 1));
+ } else this.push(html + renderedHtml);
+
+ callback();
+ }
+ });
+
+ readableStream.on('end', function () {
+ return _this.seal();
+ });
+
+ readableStream.on('error', function (err) {
+ _this.seal();
+
+ // forward the error to the transform stream
+ transformer.emit('error', err);
+ });
+
+ return readableStream.pipe(transformer);
+ };
+
+ return ServerStyleSheet;
+}();
+
+//
+
+var StyleSheetContext = (0,react__WEBPACK_IMPORTED_MODULE_2__.createContext)();
+var StyleSheetConsumer = StyleSheetContext.Consumer;
+
+var StyleSheetManager = function (_Component) {
+ inherits(StyleSheetManager, _Component);
+
+ function StyleSheetManager(props) {
+ classCallCheck(this, StyleSheetManager);
+
+ var _this = possibleConstructorReturn(this, _Component.call(this, props));
+
+ _this.getContext = (0,memoize_one__WEBPACK_IMPORTED_MODULE_7__["default"])(_this.getContext);
+ return _this;
+ }
+
+ StyleSheetManager.prototype.getContext = function getContext(sheet, target) {
+ if (sheet) {
+ return sheet;
+ } else if (target) {
+ return new StyleSheet(target);
+ } else {
+ throw new StyledComponentsError(4);
+ }
+ };
+
+ StyleSheetManager.prototype.render = function render() {
+ var _props = this.props,
+ children = _props.children,
+ sheet = _props.sheet,
+ target = _props.target;
+
+
+ return react__WEBPACK_IMPORTED_MODULE_2___default().createElement(
+ StyleSheetContext.Provider,
+ { value: this.getContext(sheet, target) },
+ true ? react__WEBPACK_IMPORTED_MODULE_2___default().Children.only(children) : 0
+ );
+ };
+
+ return StyleSheetManager;
+}(react__WEBPACK_IMPORTED_MODULE_2__.Component);
+ true ? StyleSheetManager.propTypes = {
+ sheet: prop_types__WEBPACK_IMPORTED_MODULE_8___default().oneOfType([prop_types__WEBPACK_IMPORTED_MODULE_8___default().instanceOf(StyleSheet), prop_types__WEBPACK_IMPORTED_MODULE_8___default().instanceOf(ServerStyleSheet)]),
+
+ target: prop_types__WEBPACK_IMPORTED_MODULE_8___default().shape({
+ appendChild: (prop_types__WEBPACK_IMPORTED_MODULE_8___default().func.isRequired)
+ })
+} : 0;
+
+//
+
+var identifiers = {};
+
+/* We depend on components having unique IDs */
+function generateId(_ComponentStyle, _displayName, parentComponentId) {
+ var displayName = typeof _displayName !== 'string' ? 'sc' : escape(_displayName);
+
+ /**
+ * This ensures uniqueness if two components happen to share
+ * the same displayName.
+ */
+ var nr = (identifiers[displayName] || 0) + 1;
+ identifiers[displayName] = nr;
+
+ var componentId = displayName + '-' + _ComponentStyle.generateName(displayName + nr);
+
+ return parentComponentId ? parentComponentId + '-' + componentId : componentId;
+}
+
+// $FlowFixMe
+
+var StyledComponent = function (_Component) {
+ inherits(StyledComponent, _Component);
+
+ function StyledComponent() {
+ classCallCheck(this, StyledComponent);
+
+ var _this = possibleConstructorReturn(this, _Component.call(this));
+
+ _this.attrs = {};
+
+ _this.renderOuter = _this.renderOuter.bind(_this);
+ _this.renderInner = _this.renderInner.bind(_this);
+
+ if (true) {
+ _this.warnInnerRef = once(function (displayName) {
+ return (
+ // eslint-disable-next-line no-console
+ console.warn('The "innerRef" API has been removed in styled-components v4 in favor of React 16 ref forwarding, use "ref" instead like a typical component. "innerRef" was detected on component "' + displayName + '".')
+ );
+ });
+
+ _this.warnAttrsFnObjectKeyDeprecated = once(function (key, displayName) {
+ return (
+ // eslint-disable-next-line no-console
+ console.warn('Functions as object-form attrs({}) keys are now deprecated and will be removed in a future version of styled-components. Switch to the new attrs(props => ({})) syntax instead for easier and more powerful composition. The attrs key in question is "' + key + '" on component "' + displayName + '".', '\n ' + new Error().stack)
+ );
+ });
+
+ _this.warnNonStyledComponentAttrsObjectKey = once(function (key, displayName) {
+ return (
+ // eslint-disable-next-line no-console
+ console.warn('It looks like you\'ve used a non styled-component as the value for the "' + key + '" prop in an object-form attrs constructor of "' + displayName + '".\n' + 'You should use the new function-form attrs constructor which avoids this issue: attrs(props => ({ yourStuff }))\n' + "To continue using the deprecated object syntax, you'll need to wrap your component prop in a function to make it available inside the styled component (you'll still get the deprecation warning though.)\n" + ('For example, { ' + key + ': () => InnerComponent } instead of { ' + key + ': InnerComponent }'))
+ );
+ });
+ }
+ return _this;
+ }
+
+ StyledComponent.prototype.render = function render() {
+ return react__WEBPACK_IMPORTED_MODULE_2___default().createElement(
+ StyleSheetConsumer,
+ null,
+ this.renderOuter
+ );
+ };
+
+ StyledComponent.prototype.renderOuter = function renderOuter() {
+ var styleSheet = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : StyleSheet.master;
+
+ this.styleSheet = styleSheet;
+
+ // No need to subscribe a static component to theme changes, it won't change anything
+ if (this.props.forwardedComponent.componentStyle.isStatic) return this.renderInner();
+
+ return react__WEBPACK_IMPORTED_MODULE_2___default().createElement(
+ ThemeConsumer,
+ null,
+ this.renderInner
+ );
+ };
+
+ StyledComponent.prototype.renderInner = function renderInner(theme) {
+ var _props$forwardedCompo = this.props.forwardedComponent,
+ componentStyle = _props$forwardedCompo.componentStyle,
+ defaultProps = _props$forwardedCompo.defaultProps,
+ displayName = _props$forwardedCompo.displayName,
+ foldedComponentIds = _props$forwardedCompo.foldedComponentIds,
+ styledComponentId = _props$forwardedCompo.styledComponentId,
+ target = _props$forwardedCompo.target;
+
+
+ var generatedClassName = void 0;
+ if (componentStyle.isStatic) {
+ generatedClassName = this.generateAndInjectStyles(EMPTY_OBJECT, this.props);
+ } else {
+ generatedClassName = this.generateAndInjectStyles(determineTheme(this.props, theme, defaultProps) || EMPTY_OBJECT, this.props);
+ }
+
+ var elementToBeCreated = this.props.as || this.attrs.as || target;
+ var isTargetTag = isTag(elementToBeCreated);
+
+ var propsForElement = {};
+ var computedProps = _extends({}, this.props, this.attrs);
+
+ var key = void 0;
+ // eslint-disable-next-line guard-for-in
+ for (key in computedProps) {
+ if ( true && key === 'innerRef' && isTargetTag) {
+ this.warnInnerRef(displayName);
+ }
+
+ if (key === 'forwardedComponent' || key === 'as') {
+ continue;
+ } else if (key === 'forwardedRef') propsForElement.ref = computedProps[key];else if (key === 'forwardedAs') propsForElement.as = computedProps[key];else if (!isTargetTag || (0,_emotion_is_prop_valid__WEBPACK_IMPORTED_MODULE_5__["default"])(key)) {
+ // Don't pass through non HTML tags through to HTML elements
+ propsForElement[key] = computedProps[key];
+ }
+ }
+
+ if (this.props.style && this.attrs.style) {
+ propsForElement.style = _extends({}, this.attrs.style, this.props.style);
+ }
+
+ propsForElement.className = Array.prototype.concat(foldedComponentIds, styledComponentId, generatedClassName !== styledComponentId ? generatedClassName : null, this.props.className, this.attrs.className).filter(Boolean).join(' ');
+
+ return (0,react__WEBPACK_IMPORTED_MODULE_2__.createElement)(elementToBeCreated, propsForElement);
+ };
+
+ StyledComponent.prototype.buildExecutionContext = function buildExecutionContext(theme, props, attrs) {
+ var _this2 = this;
+
+ var context = _extends({}, props, { theme: theme });
+
+ if (!attrs.length) return context;
+
+ this.attrs = {};
+
+ attrs.forEach(function (attrDef) {
+ var resolvedAttrDef = attrDef;
+ var attrDefWasFn = false;
+ var attr = void 0;
+ var key = void 0;
+
+ if (isFunction(resolvedAttrDef)) {
+ // $FlowFixMe
+ resolvedAttrDef = resolvedAttrDef(context);
+ attrDefWasFn = true;
+ }
+
+ /* eslint-disable guard-for-in */
+ // $FlowFixMe
+ for (key in resolvedAttrDef) {
+ attr = resolvedAttrDef[key];
+
+ if (!attrDefWasFn) {
+ if (isFunction(attr) && !isDerivedReactComponent(attr) && !isStyledComponent(attr)) {
+ if (true) {
+ _this2.warnAttrsFnObjectKeyDeprecated(key, props.forwardedComponent.displayName);
+ }
+
+ attr = attr(context);
+
+ if ( true && react__WEBPACK_IMPORTED_MODULE_2___default().isValidElement(attr)) {
+ _this2.warnNonStyledComponentAttrsObjectKey(key, props.forwardedComponent.displayName);
+ }
+ }
+ }
+
+ _this2.attrs[key] = attr;
+ context[key] = attr;
+ }
+ /* eslint-enable */
+ });
+
+ return context;
+ };
+
+ StyledComponent.prototype.generateAndInjectStyles = function generateAndInjectStyles(theme, props) {
+ var _props$forwardedCompo2 = props.forwardedComponent,
+ attrs = _props$forwardedCompo2.attrs,
+ componentStyle = _props$forwardedCompo2.componentStyle,
+ warnTooManyClasses = _props$forwardedCompo2.warnTooManyClasses;
+
+ // statically styled-components don't need to build an execution context object,
+ // and shouldn't be increasing the number of class names
+
+ if (componentStyle.isStatic && !attrs.length) {
+ return componentStyle.generateAndInjectStyles(EMPTY_OBJECT, this.styleSheet);
+ }
+
+ var className = componentStyle.generateAndInjectStyles(this.buildExecutionContext(theme, props, attrs), this.styleSheet);
+
+ if ( true && warnTooManyClasses) warnTooManyClasses(className);
+
+ return className;
+ };
+
+ return StyledComponent;
+}(react__WEBPACK_IMPORTED_MODULE_2__.Component);
+
+function createStyledComponent(target, options, rules) {
+ var isTargetStyledComp = isStyledComponent(target);
+ var isClass = !isTag(target);
+
+ var _options$displayName = options.displayName,
+ displayName = _options$displayName === undefined ? generateDisplayName(target) : _options$displayName,
+ _options$componentId = options.componentId,
+ componentId = _options$componentId === undefined ? generateId(ComponentStyle, options.displayName, options.parentComponentId) : _options$componentId,
+ _options$ParentCompon = options.ParentComponent,
+ ParentComponent = _options$ParentCompon === undefined ? StyledComponent : _options$ParentCompon,
+ _options$attrs = options.attrs,
+ attrs = _options$attrs === undefined ? EMPTY_ARRAY : _options$attrs;
+
+
+ var styledComponentId = options.displayName && options.componentId ? escape(options.displayName) + '-' + options.componentId : options.componentId || componentId;
+
+ // fold the underlying StyledComponent attrs up (implicit extend)
+ var finalAttrs =
+ // $FlowFixMe
+ isTargetStyledComp && target.attrs ? Array.prototype.concat(target.attrs, attrs).filter(Boolean) : attrs;
+
+ var componentStyle = new ComponentStyle(isTargetStyledComp ? // fold the underlying StyledComponent rules up (implicit extend)
+ // $FlowFixMe
+ target.componentStyle.rules.concat(rules) : rules, finalAttrs, styledComponentId);
+
+ /**
+ * forwardRef creates a new interim component, which we'll take advantage of
+ * instead of extending ParentComponent to create _another_ interim class
+ */
+ var WrappedStyledComponent = void 0;
+ var forwardRef = function forwardRef(props, ref) {
+ return react__WEBPACK_IMPORTED_MODULE_2___default().createElement(ParentComponent, _extends({}, props, { forwardedComponent: WrappedStyledComponent, forwardedRef: ref }));
+ };
+ forwardRef.displayName = displayName;
+ WrappedStyledComponent = react__WEBPACK_IMPORTED_MODULE_2___default().forwardRef(forwardRef);
+ WrappedStyledComponent.displayName = displayName;
+
+ // $FlowFixMe
+ WrappedStyledComponent.attrs = finalAttrs;
+ // $FlowFixMe
+ WrappedStyledComponent.componentStyle = componentStyle;
+
+ // $FlowFixMe
+ WrappedStyledComponent.foldedComponentIds = isTargetStyledComp ? // $FlowFixMe
+ Array.prototype.concat(target.foldedComponentIds, target.styledComponentId) : EMPTY_ARRAY;
+
+ // $FlowFixMe
+ WrappedStyledComponent.styledComponentId = styledComponentId;
+
+ // fold the underlying StyledComponent target up since we folded the styles
+ // $FlowFixMe
+ WrappedStyledComponent.target = isTargetStyledComp ? target.target : target;
+
+ // $FlowFixMe
+ WrappedStyledComponent.withComponent = function withComponent(tag) {
+ var previousComponentId = options.componentId,
+ optionsToCopy = objectWithoutProperties(options, ['componentId']);
+
+
+ var newComponentId = previousComponentId && previousComponentId + '-' + (isTag(tag) ? tag : escape(getComponentName(tag)));
+
+ var newOptions = _extends({}, optionsToCopy, {
+ attrs: finalAttrs,
+ componentId: newComponentId,
+ ParentComponent: ParentComponent
+ });
+
+ return createStyledComponent(tag, newOptions, rules);
+ };
+
+ // $FlowFixMe
+ Object.defineProperty(WrappedStyledComponent, 'defaultProps', {
+ get: function get$$1() {
+ return this._foldedDefaultProps;
+ },
+ set: function set$$1(obj) {
+ // $FlowFixMe
+ this._foldedDefaultProps = isTargetStyledComp ? (0,merge_anything__WEBPACK_IMPORTED_MODULE_6__["default"])(target.defaultProps, obj) : obj;
+ }
+ });
+
+ if (true) {
+ // $FlowFixMe
+ WrappedStyledComponent.warnTooManyClasses = createWarnTooManyClasses(displayName);
+ }
+
+ // $FlowFixMe
+ WrappedStyledComponent.toString = function () {
+ return '.' + WrappedStyledComponent.styledComponentId;
+ };
+
+ if (isClass) {
+ hoistNonReactStatics(WrappedStyledComponent, target, {
+ // all SC-specific things should not be hoisted
+ attrs: true,
+ componentStyle: true,
+ displayName: true,
+ foldedComponentIds: true,
+ styledComponentId: true,
+ target: true,
+ withComponent: true
+ });
+ }
+
+ return WrappedStyledComponent;
+}
+
+//
+// Thanks to ReactDOMFactories for this handy list!
+
+var domElements = ['a', 'abbr', 'address', 'area', 'article', 'aside', 'audio', 'b', 'base', 'bdi', 'bdo', 'big', 'blockquote', 'body', 'br', 'button', 'canvas', 'caption', 'cite', 'code', 'col', 'colgroup', 'data', 'datalist', 'dd', 'del', 'details', 'dfn', 'dialog', 'div', 'dl', 'dt', 'em', 'embed', 'fieldset', 'figcaption', 'figure', 'footer', 'form', 'h1', 'h2', 'h3', 'h4', 'h5', 'h6', 'head', 'header', 'hgroup', 'hr', 'html', 'i', 'iframe', 'img', 'input', 'ins', 'kbd', 'keygen', 'label', 'legend', 'li', 'link', 'main', 'map', 'mark', 'marquee', 'menu', 'menuitem', 'meta', 'meter', 'nav', 'noscript', 'object', 'ol', 'optgroup', 'option', 'output', 'p', 'param', 'picture', 'pre', 'progress', 'q', 'rp', 'rt', 'ruby', 's', 'samp', 'script', 'section', 'select', 'small', 'source', 'span', 'strong', 'style', 'sub', 'summary', 'sup', 'table', 'tbody', 'td', 'textarea', 'tfoot', 'th', 'thead', 'time', 'title', 'tr', 'track', 'u', 'ul', 'var', 'video', 'wbr',
+
+// SVG
+'circle', 'clipPath', 'defs', 'ellipse', 'foreignObject', 'g', 'image', 'line', 'linearGradient', 'marker', 'mask', 'path', 'pattern', 'polygon', 'polyline', 'radialGradient', 'rect', 'stop', 'svg', 'text', 'tspan'];
+
+//
+
+var styled = function styled(tag) {
+ return constructWithOptions(createStyledComponent, tag);
+};
+
+// Shorthands for all valid HTML Elements
+domElements.forEach(function (domElement) {
+ styled[domElement] = styled(domElement);
+});
+
+//
+
+var GlobalStyle = function () {
+ function GlobalStyle(rules, componentId) {
+ classCallCheck(this, GlobalStyle);
+
+ this.rules = rules;
+ this.componentId = componentId;
+ this.isStatic = isStaticRules(rules, EMPTY_ARRAY);
+
+ if (!StyleSheet.master.hasId(componentId)) {
+ StyleSheet.master.deferredInject(componentId, []);
+ }
+ }
+
+ GlobalStyle.prototype.createStyles = function createStyles(executionContext, styleSheet) {
+ var flatCSS = flatten(this.rules, executionContext, styleSheet);
+ var css = stringifyRules(flatCSS, '');
+
+ styleSheet.inject(this.componentId, css);
+ };
+
+ GlobalStyle.prototype.removeStyles = function removeStyles(styleSheet) {
+ var componentId = this.componentId;
+
+ if (styleSheet.hasId(componentId)) {
+ styleSheet.remove(componentId);
+ }
+ };
+
+ // TODO: overwrite in-place instead of remove+create?
+
+
+ GlobalStyle.prototype.renderStyles = function renderStyles(executionContext, styleSheet) {
+ this.removeStyles(styleSheet);
+ this.createStyles(executionContext, styleSheet);
+ };
+
+ return GlobalStyle;
+}();
+
+//
+
+// place our cache into shared context so it'll persist between HMRs
+if (IS_BROWSER) {
+ window.scCGSHMRCache = {};
+}
+
+function createGlobalStyle(strings) {
+ for (var _len = arguments.length, interpolations = Array(_len > 1 ? _len - 1 : 0), _key = 1; _key < _len; _key++) {
+ interpolations[_key - 1] = arguments[_key];
+ }
+
+ var rules = css.apply(undefined, [strings].concat(interpolations));
+ var id = 'sc-global-' + murmurhash(JSON.stringify(rules));
+ var style = new GlobalStyle(rules, id);
+
+ var GlobalStyleComponent = function (_React$Component) {
+ inherits(GlobalStyleComponent, _React$Component);
+
+ function GlobalStyleComponent(props) {
+ classCallCheck(this, GlobalStyleComponent);
+
+ var _this = possibleConstructorReturn(this, _React$Component.call(this, props));
+
+ var _this$constructor = _this.constructor,
+ globalStyle = _this$constructor.globalStyle,
+ styledComponentId = _this$constructor.styledComponentId;
+
+
+ if (IS_BROWSER) {
+ window.scCGSHMRCache[styledComponentId] = (window.scCGSHMRCache[styledComponentId] || 0) + 1;
+ }
+
+ /**
+ * This fixes HMR compatibility. Don't ask me why, but this combination of
+ * caching the closure variables via statics and then persisting the statics in
+ * state works across HMR where no other combination did. ÂŻ\_(ă„)_/ÂŻ
+ */
+ _this.state = {
+ globalStyle: globalStyle,
+ styledComponentId: styledComponentId
+ };
+ return _this;
+ }
+
+ GlobalStyleComponent.prototype.componentWillUnmount = function componentWillUnmount() {
+ if (window.scCGSHMRCache[this.state.styledComponentId]) {
+ window.scCGSHMRCache[this.state.styledComponentId] -= 1;
+ }
+ /**
+ * Depending on the order "render" is called this can cause the styles to be lost
+ * until the next render pass of the remaining instance, which may
+ * not be immediate.
+ */
+ if (window.scCGSHMRCache[this.state.styledComponentId] === 0) {
+ this.state.globalStyle.removeStyles(this.styleSheet);
+ }
+ };
+
+ GlobalStyleComponent.prototype.render = function render() {
+ var _this2 = this;
+
+ if ( true && react__WEBPACK_IMPORTED_MODULE_2___default().Children.count(this.props.children)) {
+ // eslint-disable-next-line no-console
+ console.warn('The global style component ' + this.state.styledComponentId + ' was given child JSX. createGlobalStyle does not render children.');
+ }
+
+ return react__WEBPACK_IMPORTED_MODULE_2___default().createElement(
+ StyleSheetConsumer,
+ null,
+ function (styleSheet) {
+ _this2.styleSheet = styleSheet || StyleSheet.master;
+
+ var globalStyle = _this2.state.globalStyle;
+
+
+ if (globalStyle.isStatic) {
+ globalStyle.renderStyles(STATIC_EXECUTION_CONTEXT, _this2.styleSheet);
+
+ return null;
+ } else {
+ return react__WEBPACK_IMPORTED_MODULE_2___default().createElement(
+ ThemeConsumer,
+ null,
+ function (theme) {
+ // $FlowFixMe
+ var defaultProps = _this2.constructor.defaultProps;
+
+
+ var context = _extends({}, _this2.props);
+
+ if (typeof theme !== 'undefined') {
+ context.theme = determineTheme(_this2.props, theme, defaultProps);
+ }
+
+ globalStyle.renderStyles(context, _this2.styleSheet);
+
+ return null;
+ }
+ );
+ }
+ }
+ );
+ };
+
+ return GlobalStyleComponent;
+ }((react__WEBPACK_IMPORTED_MODULE_2___default().Component));
+
+ GlobalStyleComponent.globalStyle = style;
+ GlobalStyleComponent.styledComponentId = id;
+
+
+ return GlobalStyleComponent;
+}
+
+//
+
+var replaceWhitespace = function replaceWhitespace(str) {
+ return str.replace(/\s|\\n/g, '');
+};
+
+function keyframes(strings) {
+ /* Warning if you've used keyframes on React Native */
+ if ( true && typeof navigator !== 'undefined' && navigator.product === 'ReactNative') {
+ // eslint-disable-next-line no-console
+ console.warn('`keyframes` cannot be used on ReactNative, only on the web. To do animation in ReactNative please use Animated.');
+ }
+
+ for (var _len = arguments.length, interpolations = Array(_len > 1 ? _len - 1 : 0), _key = 1; _key < _len; _key++) {
+ interpolations[_key - 1] = arguments[_key];
+ }
+
+ var rules = css.apply(undefined, [strings].concat(interpolations));
+
+ var name = generateAlphabeticName(murmurhash(replaceWhitespace(JSON.stringify(rules))));
+
+ return new Keyframes(name, stringifyRules(rules, name, '@keyframes'));
+}
+
+//
+
+var withTheme = (function (Component$$1) {
+ var WithTheme = react__WEBPACK_IMPORTED_MODULE_2___default().forwardRef(function (props, ref) {
+ return react__WEBPACK_IMPORTED_MODULE_2___default().createElement(
+ ThemeConsumer,
+ null,
+ function (theme) {
+ // $FlowFixMe
+ var defaultProps = Component$$1.defaultProps;
+
+ var themeProp = determineTheme(props, theme, defaultProps);
+
+ if ( true && themeProp === undefined) {
+ // eslint-disable-next-line no-console
+ console.warn('[withTheme] You are not using a ThemeProvider nor passing a theme prop or a theme in defaultProps in component class "' + getComponentName(Component$$1) + '"');
+ }
+
+ return react__WEBPACK_IMPORTED_MODULE_2___default().createElement(Component$$1, _extends({}, props, { theme: themeProp, ref: ref }));
+ }
+ );
+ });
+
+ hoistNonReactStatics(WithTheme, Component$$1);
+
+ WithTheme.displayName = 'WithTheme(' + getComponentName(Component$$1) + ')';
+
+ return WithTheme;
+});
+
+//
+
+/* eslint-disable */
+var __DO_NOT_USE_OR_YOU_WILL_BE_HAUNTED_BY_SPOOKY_GHOSTS = {
+ StyleSheet: StyleSheet
+};
+
+//
+
+/* Warning if you've imported this file on React Native */
+if ( true && typeof navigator !== 'undefined' && navigator.product === 'ReactNative') {
+ // eslint-disable-next-line no-console
+ console.warn("It looks like you've imported 'styled-components' on React Native.\n" + "Perhaps you're looking to import 'styled-components/native'?\n" + 'Read more about this at https://www.styled-components.com/docs/basics#react-native');
+}
+
+/* Warning if there are several instances of styled-components */
+if ( true && typeof window !== 'undefined' && typeof navigator !== 'undefined' && typeof navigator.userAgent === 'string' && navigator.userAgent.indexOf('Node.js') === -1 && navigator.userAgent.indexOf('jsdom') === -1) {
+ window['__styled-components-init__'] = window['__styled-components-init__'] || 0;
+
+ if (window['__styled-components-init__'] === 1) {
+ // eslint-disable-next-line no-console
+ console.warn("It looks like there are several instances of 'styled-components' initialized in this application. " + 'This may cause dynamic styles not rendering properly, errors happening during rehydration process ' + 'and makes your application bigger without a good reason.\n\n' + 'See https://s-c.sh/2BAXzed for more info.');
+ }
+
+ window['__styled-components-init__'] += 1;
+}
+
+//
+
+/* harmony default export */ const __WEBPACK_DEFAULT_EXPORT__ = (styled);
+
+//# sourceMappingURL=styled-components.browser.esm.js.map
+
+
+/***/ }),
+
+/***/ "./node_modules/stylis-rule-sheet/index.js":
+/*!*************************************************!*\
+ !*** ./node_modules/stylis-rule-sheet/index.js ***!
+ \*************************************************/
+/***/ ((module) => {
+
+(function (factory) {
+ true ? (module['exports'] = factory()) :
+ 0
+}(function () {
+
+ 'use strict'
+
+ return function (insertRule) {
+ var delimiter = '/*|*/'
+ var needle = delimiter+'}'
+
+ function toSheet (block) {
+ if (block)
+ try {
+ insertRule(block + '}')
+ } catch (e) {}
+ }
+
+ return function ruleSheet (context, content, selectors, parents, line, column, length, ns, depth, at) {
+ switch (context) {
+ // property
+ case 1:
+ // @import
+ if (depth === 0 && content.charCodeAt(0) === 64)
+ return insertRule(content+';'), ''
+ break
+ // selector
+ case 2:
+ if (ns === 0)
+ return content + delimiter
+ break
+ // at-rule
+ case 3:
+ switch (ns) {
+ // @font-face, @page
+ case 102:
+ case 112:
+ return insertRule(selectors[0]+content), ''
+ default:
+ return content + (at === 0 ? delimiter : '')
+ }
+ case -2:
+ content.split(needle).forEach(toSheet)
+ }
+ }
+ }
+}))
+
+
+/***/ }),
+
+/***/ "./node_modules/stylis/stylis.min.js":
+/*!*******************************************!*\
+ !*** ./node_modules/stylis/stylis.min.js ***!
+ \*******************************************/
+/***/ ((module) => {
+
+!function(e){ true?module.exports=e(null):0}(function e(a){"use strict";var r=/^\0+/g,c=/[\0\r\f]/g,s=/: */g,t=/zoo|gra/,i=/([,: ])(transform)/g,f=/,+\s*(?![^(]*[)])/g,n=/ +\s*(?![^(]*[)])/g,l=/ *[\0] */g,o=/,\r+?/g,h=/([\t\r\n ])*\f?&/g,u=/:global\(((?:[^\(\)\[\]]*|\[.*\]|\([^\(\)]*\))*)\)/g,d=/\W+/g,b=/@(k\w+)\s*(\S*)\s*/,p=/::(place)/g,k=/:(read-only)/g,g=/\s+(?=[{\];=:>])/g,A=/([[}=:>])\s+/g,C=/(\{[^{]+?);(?=\})/g,w=/\s{2,}/g,v=/([^\(])(:+) */g,m=/[svh]\w+-[tblr]{2}/,x=/\(\s*(.*)\s*\)/g,$=/([\s\S]*?);/g,y=/-self|flex-/g,O=/[^]*?(:[rp][el]a[\w-]+)[^]*/,j=/stretch|:\s*\w+\-(?:conte|avail)/,z=/([^-])(image-set\()/,N="-webkit-",S="-moz-",F="-ms-",W=59,q=125,B=123,D=40,E=41,G=91,H=93,I=10,J=13,K=9,L=64,M=32,P=38,Q=45,R=95,T=42,U=44,V=58,X=39,Y=34,Z=47,_=62,ee=43,ae=126,re=0,ce=12,se=11,te=107,ie=109,fe=115,ne=112,le=111,oe=105,he=99,ue=100,de=112,be=1,pe=1,ke=0,ge=1,Ae=1,Ce=1,we=0,ve=0,me=0,xe=[],$e=[],ye=0,Oe=null,je=-2,ze=-1,Ne=0,Se=1,Fe=2,We=3,qe=0,Be=1,De="",Ee="",Ge="";function He(e,a,s,t,i){for(var f,n,o=0,h=0,u=0,d=0,g=0,A=0,C=0,w=0,m=0,$=0,y=0,O=0,j=0,z=0,R=0,we=0,$e=0,Oe=0,je=0,ze=s.length,Je=ze-1,Re="",Te="",Ue="",Ve="",Xe="",Ye="";R0)Te=Te.replace(c,"");if(Te.trim().length>0){switch(C){case M:case K:case W:case J:case I:break;default:Te+=s.charAt(R)}C=W}}if(1===$e)switch(C){case B:case q:case W:case Y:case X:case D:case E:case U:$e=0;case K:case J:case I:case M:break;default:for($e=0,je=R,g=C,R--,C=W;je0)++R,C=g;case B:je=ze}}switch(C){case B:for(g=(Te=Te.trim()).charCodeAt(0),y=1,je=++R;R0)Te=Te.replace(c,"");switch(A=Te.charCodeAt(1)){case ue:case ie:case fe:case Q:f=a;break;default:f=xe}if(je=(Ue=He(a,f,Ue,A,i+1)).length,me>0&&0===je)je=Te.length;if(ye>0)if(f=Ie(xe,Te,Oe),n=Pe(We,Ue,f,a,pe,be,je,A,i,t),Te=f.join(""),void 0!==n)if(0===(je=(Ue=n.trim()).length))A=0,Ue="";if(je>0)switch(A){case fe:Te=Te.replace(x,Me);case ue:case ie:case Q:Ue=Te+"{"+Ue+"}";break;case te:if(Ue=(Te=Te.replace(b,"$1 $2"+(Be>0?De:"")))+"{"+Ue+"}",1===Ae||2===Ae&&Le("@"+Ue,3))Ue="@"+N+Ue+"@"+Ue;else Ue="@"+Ue;break;default:if(Ue=Te+Ue,t===de)Ve+=Ue,Ue=""}else Ue="";break;default:Ue=He(a,Ie(a,Te,Oe),Ue,t,i+1)}Xe+=Ue,O=0,$e=0,z=0,we=0,Oe=0,j=0,Te="",Ue="",C=s.charCodeAt(++R);break;case q:case W:if((je=(Te=(we>0?Te.replace(c,""):Te).trim()).length)>1){if(0===z)if((g=Te.charCodeAt(0))===Q||g>96&&g<123)je=(Te=Te.replace(" ",":")).length;if(ye>0)if(void 0!==(n=Pe(Se,Te,a,e,pe,be,Ve.length,t,i,t)))if(0===(je=(Te=n.trim()).length))Te="\0\0";switch(g=Te.charCodeAt(0),A=Te.charCodeAt(1),g){case re:break;case L:if(A===oe||A===he){Ye+=Te+s.charAt(R);break}default:if(Te.charCodeAt(je-1)===V)break;Ve+=Ke(Te,g,A,Te.charCodeAt(2))}}O=0,$e=0,z=0,we=0,Oe=0,Te="",C=s.charCodeAt(++R)}}switch(C){case J:case I:if(h+d+u+o+ve===0)switch($){case E:case X:case Y:case L:case ae:case _:case T:case ee:case Z:case Q:case V:case U:case W:case B:case q:break;default:if(z>0)$e=1}if(h===Z)h=0;else if(ge+O===0&&t!==te&&Te.length>0)we=1,Te+="\0";if(ye*qe>0)Pe(Ne,Te,a,e,pe,be,Ve.length,t,i,t);be=1,pe++;break;case W:case q:if(h+d+u+o===0){be++;break}default:switch(be++,Re=s.charAt(R),C){case K:case M:if(d+o+h===0)switch(w){case U:case V:case K:case M:Re="";break;default:if(C!==M)Re=" "}break;case re:Re="\\0";break;case ce:Re="\\f";break;case se:Re="\\v";break;case P:if(d+h+o===0&&ge>0)Oe=1,we=1,Re="\f"+Re;break;case 108:if(d+h+o+ke===0&&z>0)switch(R-z){case 2:if(w===ne&&s.charCodeAt(R-3)===V)ke=w;case 8:if(m===le)ke=m}break;case V:if(d+h+o===0)z=R;break;case U:if(h+u+d+o===0)we=1,Re+="\r";break;case Y:case X:if(0===h)d=d===C?0:0===d?C:d;break;case G:if(d+h+u===0)o++;break;case H:if(d+h+u===0)o--;break;case E:if(d+h+o===0)u--;break;case D:if(d+h+o===0){if(0===O)switch(2*w+3*m){case 533:break;default:y=0,O=1}u++}break;case L:if(h+u+d+o+z+j===0)j=1;break;case T:case Z:if(d+o+u>0)break;switch(h){case 0:switch(2*C+3*s.charCodeAt(R+1)){case 235:h=Z;break;case 220:je=R,h=T}break;case T:if(C===Z&&w===T&&je+2!==R){if(33===s.charCodeAt(je+2))Ve+=s.substring(je,R+1);Re="",h=0}}}if(0===h){if(ge+d+o+j===0&&t!==te&&C!==W)switch(C){case U:case ae:case _:case ee:case E:case D:if(0===O){switch(w){case K:case M:case I:case J:Re+="\0";break;default:Re="\0"+Re+(C===U?"":"\0")}we=1}else switch(C){case D:if(z+7===R&&108===w)z=0;O=++y;break;case E:if(0==(O=--y))we=1,Re+="\0"}break;case K:case M:switch(w){case re:case B:case q:case W:case U:case ce:case K:case M:case I:case J:break;default:if(0===O)we=1,Re+="\0"}}if(Te+=Re,C!==M&&C!==K)$=C}}m=w,w=C,R++}if(je=Ve.length,me>0)if(0===je&&0===Xe.length&&0===a[0].length==false)if(t!==ie||1===a.length&&(ge>0?Ee:Ge)===a[0])je=a.join(",").length+2;if(je>0){if(f=0===ge&&t!==te?function(e){for(var a,r,s=0,t=e.length,i=Array(t);s1)continue;if(u=n.charCodeAt(n.length-1),d=r.charCodeAt(0),a="",0!==o)switch(u){case T:case ae:case _:case ee:case M:case D:break;default:a=" "}switch(d){case P:r=a+Ee;case ae:case _:case ee:case M:case E:case D:break;case G:r=a+r+Ee;break;case V:switch(2*r.charCodeAt(1)+3*r.charCodeAt(2)){case 530:if(Ce>0){r=a+r.substring(8,h-1);break}default:if(o<1||f[o-1].length<1)r=a+Ee+r}break;case U:a="";default:if(h>1&&r.indexOf(":")>0)r=a+r.replace(v,"$1"+Ee+"$2");else r=a+r+Ee}n+=r}i[s]=n.replace(c,"").trim()}return i}(a):a,ye>0)if(void 0!==(n=Pe(Fe,Ve,f,e,pe,be,je,t,i,t))&&0===(Ve=n).length)return Ye+Ve+Xe;if(Ve=f.join(",")+"{"+Ve+"}",Ae*ke!=0){if(2===Ae&&!Le(Ve,2))ke=0;switch(ke){case le:Ve=Ve.replace(k,":"+S+"$1")+Ve;break;case ne:Ve=Ve.replace(p,"::"+N+"input-$1")+Ve.replace(p,"::"+S+"$1")+Ve.replace(p,":"+F+"input-$1")+Ve}ke=0}}return Ye+Ve+Xe}function Ie(e,a,r){var c=a.trim().split(o),s=c,t=c.length,i=e.length;switch(i){case 0:case 1:for(var f=0,n=0===i?"":e[0]+" ";f0&&ge>0)return s.replace(u,"$1").replace(h,"$1"+Ge);break;default:return e.trim()+s.replace(h,"$1"+e.trim())}default:if(r*ge>0&&s.indexOf("\f")>0)return s.replace(h,(e.charCodeAt(0)===V?"":"$1")+e.trim())}return e+s}function Ke(e,a,r,c){var l,o=0,h=e+";",u=2*a+3*r+4*c;if(944===u)return function(e){var a=e.length,r=e.indexOf(":",9)+1,c=e.substring(0,r).trim(),s=e.substring(r,a-1).trim();switch(e.charCodeAt(9)*Be){case 0:break;case Q:if(110!==e.charCodeAt(10))break;default:for(var t=s.split((s="",f)),i=0,r=0,a=t.length;iL&&h<90||h>96&&h<123||h===R||h===Q&&l.charCodeAt(1)!==Q))switch(isNaN(parseFloat(l))+(-1!==l.indexOf("("))){case 1:switch(l){case"infinite":case"alternate":case"backwards":case"running":case"normal":case"forwards":case"both":case"none":case"linear":case"ease":case"ease-in":case"ease-out":case"ease-in-out":case"paused":case"reverse":case"alternate-reverse":case"inherit":case"initial":case"unset":case"step-start":case"step-end":break;default:l+=De}}o[r++]=l}s+=(0===i?"":",")+o.join(" ")}}if(s=c+s+";",1===Ae||2===Ae&&Le(s,1))return N+s+s;return s}(h);else if(0===Ae||2===Ae&&!Le(h,1))return h;switch(u){case 1015:return 97===h.charCodeAt(10)?N+h+h:h;case 951:return 116===h.charCodeAt(3)?N+h+h:h;case 963:return 110===h.charCodeAt(5)?N+h+h:h;case 1009:if(100!==h.charCodeAt(4))break;case 969:case 942:return N+h+h;case 978:return N+h+S+h+h;case 1019:case 983:return N+h+S+h+F+h+h;case 883:if(h.charCodeAt(8)===Q)return N+h+h;if(h.indexOf("image-set(",11)>0)return h.replace(z,"$1"+N+"$2")+h;return h;case 932:if(h.charCodeAt(4)===Q)switch(h.charCodeAt(5)){case 103:return N+"box-"+h.replace("-grow","")+N+h+F+h.replace("grow","positive")+h;case 115:return N+h+F+h.replace("shrink","negative")+h;case 98:return N+h+F+h.replace("basis","preferred-size")+h}return N+h+F+h+h;case 964:return N+h+F+"flex-"+h+h;case 1023:if(99!==h.charCodeAt(8))break;return l=h.substring(h.indexOf(":",15)).replace("flex-","").replace("space-between","justify"),N+"box-pack"+l+N+h+F+"flex-pack"+l+h;case 1005:return t.test(h)?h.replace(s,":"+N)+h.replace(s,":"+S)+h:h;case 1e3:switch(o=(l=h.substring(13).trim()).indexOf("-")+1,l.charCodeAt(0)+l.charCodeAt(o)){case 226:l=h.replace(m,"tb");break;case 232:l=h.replace(m,"tb-rl");break;case 220:l=h.replace(m,"lr");break;default:return h}return N+h+F+l+h;case 1017:if(-1===h.indexOf("sticky",9))return h;case 975:switch(o=(h=e).length-10,u=(l=(33===h.charCodeAt(o)?h.substring(0,o):h).substring(e.indexOf(":",7)+1).trim()).charCodeAt(0)+(0|l.charCodeAt(7))){case 203:if(l.charCodeAt(8)<111)break;case 115:h=h.replace(l,N+l)+";"+h;break;case 207:case 102:h=h.replace(l,N+(u>102?"inline-":"")+"box")+";"+h.replace(l,N+l)+";"+h.replace(l,F+l+"box")+";"+h}return h+";";case 938:if(h.charCodeAt(5)===Q)switch(h.charCodeAt(6)){case 105:return l=h.replace("-items",""),N+h+N+"box-"+l+F+"flex-"+l+h;case 115:return N+h+F+"flex-item-"+h.replace(y,"")+h;default:return N+h+F+"flex-line-pack"+h.replace("align-content","").replace(y,"")+h}break;case 973:case 989:if(h.charCodeAt(3)!==Q||122===h.charCodeAt(4))break;case 931:case 953:if(true===j.test(e))if(115===(l=e.substring(e.indexOf(":")+1)).charCodeAt(0))return Ke(e.replace("stretch","fill-available"),a,r,c).replace(":fill-available",":stretch");else return h.replace(l,N+l)+h.replace(l,S+l.replace("fill-",""))+h;break;case 962:if(h=N+h+(102===h.charCodeAt(5)?F+h:"")+h,r+c===211&&105===h.charCodeAt(13)&&h.indexOf("transform",10)>0)return h.substring(0,h.indexOf(";",27)+1).replace(i,"$1"+N+"$2")+h}return h}function Le(e,a){var r=e.indexOf(1===a?":":"{"),c=e.substring(0,3!==a?r:10),s=e.substring(r+1,e.length-1);return Oe(2!==a?c:c.replace(O,"$1"),s,a)}function Me(e,a){var r=Ke(a,a.charCodeAt(0),a.charCodeAt(1),a.charCodeAt(2));return r!==a+";"?r.replace($," or ($1)").substring(4):"("+a+")"}function Pe(e,a,r,c,s,t,i,f,n,l){for(var o,h=0,u=a;h