403Webshell
Server IP : 85.158.181.41  /  Your IP : 216.73.217.12
Web Server : Apache
System : Linux cloud9-vm129 6.1.178+1-ph #ph SMP PREEMPT_DYNAMIC Wed Jul 29 09:00:54 UTC 2026 x86_64
User : moncbefd ( 1024)
PHP Version : 7.3.33
Disable Function : NONE
MySQL : OFF  |  cURL : ON  |  WGET : ON  |  Perl : ON  |  Python : ON  |  Sudo : OFF  |  Pkexec : OFF
Directory :  /home/moncbefd/www.moneta.at/templates/Honeygrid/assets/javascript/engine/widgets/

Upload File :
current_dir [ Writeable ] document_root [ Writeable ]

 

Command :


[ Back ]     

Current File : /home/moncbefd/www.moneta.at/templates/Honeygrid/assets/javascript/engine/widgets/product_hover.js
'use strict';

/* --------------------------------------------------------------
 product_hover.js 2016-06-03
 Gambio GmbH
 http://www.gambio.de
 Copyright (c) 2016 Gambio GmbH
 Released under the GNU General Public License (Version 2)
 [http://www.gnu.org/licenses/gpl-2.0.html]
 --------------------------------------------------------------
 */

/**
 * Widget that is used for the hover functionality
 * of the product tiles. It includes the functionality
 * for the image gallery inside the tile
 */
gambio.widgets.module('product_hover', [gambio.source + '/libs/events'], function (data) {

    'use strict';

    // ########## VARIABLE INITIALIZATION ##########

    var $this = $(this),
        $window = $(window),
        $body = $('body'),
        $container = null,
        timer = null,
        componentId = null,
        clickTimer = 0,
        defaults = {
        delay: 50, // Delay in ms after which a hovered element gets closed after mouseleave
        flyoverClass: 'flyover', // Class that gets added to every flyover
        scope: '', // Sets the scope selector for the mouseover events
        container: '#wrapper', // Container selector which is the boundary for the cloned element
        productUrlSelector: '.product-url' // a tag selector of product's url
    },
        options = $.extend(true, {}, defaults, data),
        module = {};

    // ########## HELPER FUNCTIONS ##########

    /**
     * Helper function to remove the opened flyovers that
     * were appended to the body by this component
     * @private
     */
    var _removeFlyover = function _removeFlyover(all) {
        var $flyover = $body.children('.' + options.flyoverClass);
        $flyover = all ? $flyover : $flyover.filter('.product-hover-' + componentId);

        $flyover.remove();
    };

    /**
     * Helper function that replaces the preloader
     * images with the real thumbnail images on
     * layer creation. This is needed to save
     * bandwidth
     * @param       {object}    $clone      jQuery selection of the layer
     * @private
     */
    var _loadImages = function _loadImages($clone) {
        $clone.find('.thumbnails img').each(function () {

            var $self = $(this),
                $img = $('<img />'),
                dataset = $self.data(),
                src = dataset.thumbSrc || dataset.src,
                $parentListItem = null;

            $img.on('load', function () {
                $parentListItem = $self.closest('li');
                $parentListItem.addClass('loaded').css({
                    'background': '#FFFFFF url("' + src + '") no-repeat center',
                    'background-size': 'contain'
                }).find('img, .align-helper').remove();
            }).attr('src', src);
        });
    };

    // ########## EVENT HANDLER ##########

    /**
     * Handler for the click event on the thumbnail
     * images. After a click on such an image the
     * main image of the hover element gets replaced
     * with the bigger version of the thumbnail image
     * @param       {object}        e       jQuery event object
     * @private
     */
    var _mouseEnterThumbHandler = function _mouseEnterThumbHandler(e) {
        e.preventDefault();

        var $img = $(this),
            $container = $img.closest('.' + options.flyoverClass),
            dataSrc = $img.css('background-image');

        // Change path to big images and remove quotes
        dataSrc = dataSrc.replace('/thumbnail_images/', '/info_images/').replace('/gallery_images/', '/thumbnail_images/').replace(/["']/gm, '');

        // Remove "url()"
        var matches = dataSrc.match(/url\((.+)\)/);
        if (matches && matches[1]) {
            dataSrc = matches[1];
        }

        if (dataSrc) {
            $container.find('.product-hover-main-image > img').attr('src', dataSrc);
        }
    };

    /**
     * Event handler for the mouse leave event of the
     * hovered element. It sets a timer to remove the
     * hover element after a certain time
     * @param       {object}    e       jQuery event object
     * @private
     */
    var _mouseLeaveHandler = function _mouseLeaveHandler(e) {
        e.stopPropagation();
        timer = timer ? clearTimeout(timer) : null;
        timer = window.setTimeout(_removeFlyover, options.delay);
    };

    /**
     * Event handler for the mouse enter event on both
     * elements (initial & hovered element).
     * It clones the initial element and adds the clone
     * to the body. It additionally adds functionality
     * for the image gallery inside the hovered element
     * @param       {object}        e       jQuery event object
     * @private
     */
    var _mouseEnterHandler = function _mouseEnterHandler(e) {
        e.stopPropagation();

        var $self = $(this),
            $clone = null,
            $target = $body,
            uid = $self.data().uid || parseInt(Math.random() * 10000, 10),
            $flyover = $target.children('.' + options.flyoverClass + '.product-hover-' + componentId + '[data-product_hover-uid="' + uid + '"]'),
            offset = $self.offset();

        timer = timer ? clearTimeout(timer) : null;

        // Check if flyover needs to be created
        if (!$self.hasClass(options.flyoverClass) && !$flyover.length) {
            // Remove old opened flyovers
            _removeFlyover(true);
            $this.trigger(jse.libs.theme.events.OPEN_FLYOUT(), $this);

            // Add a UID for identification to th hovered object
            $self.attr('data-product_hover-uid', uid).data('uid', uid);

            // Generate the markup
            $clone = $self.clone(true);

            // Replace the preloader images with the thumbnail images
            _loadImages($clone);

            // Set the positioning of the layer
            $clone.addClass(options.flyoverClass + ' product-hover-' + componentId).css({
                'position': 'absolute',
                'left': offset.left,
                'top': offset.top,
                'width': $self[0].getBoundingClientRect().width,
                'height': $self[0].getBoundingClientRect().height
            });

            // Add event listener to the hover elements
            $clone.on('mouseenter', _mouseEnterHandler).on('mouseleave', _mouseLeaveHandler).on('mouseenter', '.thumbnails', _mouseEnterThumbHandler).on('click', _clickHandler);

            // Add the element to the body element
            $body.append($clone);

            if ($container.offset().left > $clone.offset().left) {
                $clone.addClass('gallery-right');
            }
        }
    };

    /**
     * Handler for the window resize event. It
     * recalculates the position of the overlays
     * @private
     */
    var _resizeHandler = function _resizeHandler() {

        var $flyover = $body.children('.' + options.flyoverClass + '.product-hover-' + componentId);

        $flyover.each(function () {
            var $self = $(this),
                uid = $self.data().uid,
                $source = $this.find('[data-product_hover-uid="' + uid + '"]'),
                offset = $source.offset();

            $self.css({
                left: offset.left,
                top: offset.top,
                width: 2 * $source.outerWidth()
            });
        });
    };

    /**
     * Event handler that closes the flyovers
     * if another flyover opens on the page
     * @param       {object}        e           jQuery event object
     * @param       {object}        d           jQuery selection of the event emitter
     * @private
     */
    var _closeLayers = function _closeLayers(e, d) {
        if ($this !== d) {
            _removeFlyover();
        }
    };

    /**
     * Event handler that makes the flyover and product image clickable linking to the product details page
     *
     * @param       {object}        e           jQuery event object
     * @private
     */
    var _clickHandler = function _clickHandler(e) {
        var $container = $(this);

        if ($(this).hasClass('product-container') === false) {
            $container = $(this).closest('.product-container');
        }

        var $link = $container.find(options.productUrlSelector).first();

        function callback() {
            if ($link.length) {
                var url = $link.attr('href');

                if (url !== undefined) {
                    e.stopPropagation();
                    e.preventDefault();

                    // prevent double _clickHandler actions
                    if (new Date().getTime() - clickTimer < 100) {
                        return;
                    } else {
                        clickTimer = new Date().getTime();
                    }

                    switch (e.which) {
                        // left click
                        case 1:
                            if (e.ctrlKey) {
                                window.open(url, '_blank');
                                return;
                            }
                            break;

                        // middle click
                        case 2:
                            window.open(url, '_blank');
                            return;
                            break;

                        // right click
                        case 3:
                            return;
                    }

                    location.href = url;
                }
            }
        }

        jse.libs.hooks.execute(jse.libs.hooks.keys.shop.product.listing.hover, { container: $container }, 500).then(callback).catch(callback);
    };

    // ########## INITIALIZATION ##########

    /**
     * Init function of the widget
     * @constructor
     */
    module.init = function (done) {

        componentId = parseInt(Math.random() * 10000, 10);
        $container = $(options.container);

        $this.on('touchstart', function () {
            // Workaround for tablet navigation problem
            $this.off('mouseenter mouseleave');
        }).on('touchend', function () {
            $this.off('mouseenter', options.scope + ' .product-container', _mouseEnterHandler).off('mouseleave', options.scope + ' .product-container', _mouseLeaveHandler);
        }).on('mouseenter', options.scope + ' .product-container', _mouseEnterHandler).on('mouseleave', options.scope + ' .product-container', _mouseLeaveHandler);

        $this.find('.product-container .product-image').on('click mouseup', _clickHandler);

        $body.on(jse.libs.theme.events.OPEN_FLYOUT(), _closeLayers);

        $window.on('resize', _resizeHandler);

        done();
    };

    // Return data to widget engine
    return module;
});
//# sourceMappingURL=data:application/json;charset=utf8;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIndpZGdldHMvcHJvZHVjdF9ob3Zlci5qcyJdLCJuYW1lcyI6WyJnYW1iaW8iLCJ3aWRnZXRzIiwibW9kdWxlIiwic291cmNlIiwiZGF0YSIsIiR0aGlzIiwiJCIsIiR3aW5kb3ciLCJ3aW5kb3ciLCIkYm9keSIsIiRjb250YWluZXIiLCJ0aW1lciIsImNvbXBvbmVudElkIiwiY2xpY2tUaW1lciIsImRlZmF1bHRzIiwiZGVsYXkiLCJmbHlvdmVyQ2xhc3MiLCJzY29wZSIsImNvbnRhaW5lciIsInByb2R1Y3RVcmxTZWxlY3RvciIsIm9wdGlvbnMiLCJleHRlbmQiLCJfcmVtb3ZlRmx5b3ZlciIsImFsbCIsIiRmbHlvdmVyIiwiY2hpbGRyZW4iLCJmaWx0ZXIiLCJyZW1vdmUiLCJfbG9hZEltYWdlcyIsIiRjbG9uZSIsImZpbmQiLCJlYWNoIiwiJHNlbGYiLCIkaW1nIiwiZGF0YXNldCIsInNyYyIsInRodW1iU3JjIiwiJHBhcmVudExpc3RJdGVtIiwib24iLCJjbG9zZXN0IiwiYWRkQ2xhc3MiLCJjc3MiLCJhdHRyIiwiX21vdXNlRW50ZXJUaHVtYkhhbmRsZXIiLCJlIiwicHJldmVudERlZmF1bHQiLCJkYXRhU3JjIiwicmVwbGFjZSIsIm1hdGNoZXMiLCJtYXRjaCIsIl9tb3VzZUxlYXZlSGFuZGxlciIsInN0b3BQcm9wYWdhdGlvbiIsImNsZWFyVGltZW91dCIsInNldFRpbWVvdXQiLCJfbW91c2VFbnRlckhhbmRsZXIiLCIkdGFyZ2V0IiwidWlkIiwicGFyc2VJbnQiLCJNYXRoIiwicmFuZG9tIiwib2Zmc2V0IiwiaGFzQ2xhc3MiLCJsZW5ndGgiLCJ0cmlnZ2VyIiwianNlIiwibGlicyIsInRoZW1lIiwiZXZlbnRzIiwiT1BFTl9GTFlPVVQiLCJjbG9uZSIsImxlZnQiLCJ0b3AiLCJnZXRCb3VuZGluZ0NsaWVudFJlY3QiLCJ3aWR0aCIsImhlaWdodCIsIl9jbGlja0hhbmRsZXIiLCJhcHBlbmQiLCJfcmVzaXplSGFuZGxlciIsIiRzb3VyY2UiLCJvdXRlcldpZHRoIiwiX2Nsb3NlTGF5ZXJzIiwiZCIsIiRsaW5rIiwiZmlyc3QiLCJjYWxsYmFjayIsInVybCIsInVuZGVmaW5lZCIsIkRhdGUiLCJnZXRUaW1lIiwid2hpY2giLCJjdHJsS2V5Iiwib3BlbiIsImxvY2F0aW9uIiwiaHJlZiIsImhvb2tzIiwiZXhlY3V0ZSIsImtleXMiLCJzaG9wIiwicHJvZHVjdCIsImxpc3RpbmciLCJob3ZlciIsInRoZW4iLCJjYXRjaCIsImluaXQiLCJkb25lIiwib2ZmIl0sIm1hcHBpbmdzIjoiOztBQUFBOzs7Ozs7Ozs7O0FBVUE7Ozs7O0FBS0FBLE9BQU9DLE9BQVAsQ0FBZUMsTUFBZixDQUNJLGVBREosRUFHSSxDQUNJRixPQUFPRyxNQUFQLEdBQWdCLGNBRHBCLENBSEosRUFPSSxVQUFVQyxJQUFWLEVBQWdCOztBQUVaOztBQUVSOztBQUVRLFFBQUlDLFFBQVFDLEVBQUUsSUFBRixDQUFaO0FBQUEsUUFDSUMsVUFBVUQsRUFBRUUsTUFBRixDQURkO0FBQUEsUUFFSUMsUUFBUUgsRUFBRSxNQUFGLENBRlo7QUFBQSxRQUdJSSxhQUFhLElBSGpCO0FBQUEsUUFJSUMsUUFBUSxJQUpaO0FBQUEsUUFLSUMsY0FBYyxJQUxsQjtBQUFBLFFBTUlDLGFBQWEsQ0FOakI7QUFBQSxRQU9JQyxXQUFXO0FBQ1BDLGVBQU8sRUFEQSxFQUNVO0FBQ2pCQyxzQkFBYyxTQUZQLEVBRW1CO0FBQzFCQyxlQUFPLEVBSEEsRUFHYTtBQUNwQkMsbUJBQVcsVUFKSixFQUlnQjtBQUN2QkMsNEJBQW9CLGNBTGIsQ0FLNEI7QUFMNUIsS0FQZjtBQUFBLFFBY0lDLFVBQVVkLEVBQUVlLE1BQUYsQ0FBUyxJQUFULEVBQWUsRUFBZixFQUFtQlAsUUFBbkIsRUFBNkJWLElBQTdCLENBZGQ7QUFBQSxRQWVJRixTQUFTLEVBZmI7O0FBaUJSOztBQUVROzs7OztBQUtBLFFBQUlvQixpQkFBaUIsU0FBakJBLGNBQWlCLENBQVVDLEdBQVYsRUFBZTtBQUNoQyxZQUFJQyxXQUFXZixNQUFNZ0IsUUFB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QUdBMkI7QUFDSCxLQTNCRDs7QUE2QkE7QUFDQSxXQUFPdEcsTUFBUDtBQUNILENBelVMIiwiZmlsZSI6IndpZGdldHMvcHJvZHVjdF9ob3Zlci5qcyIsInNvdXJjZXNDb250ZW50IjpbIi8qIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tXG4gcHJvZHVjdF9ob3Zlci5qcyAyMDE2LTA2LTAzXG4gR2FtYmlvIEdtYkhcbiBodHRwOi8vd3d3LmdhbWJpby5kZVxuIENvcHlyaWdodCAoYykgMjAxNiBHYW1iaW8gR21iSFxuIFJlbGVhc2VkIHVuZGVyIHRoZSBHTlUgR2VuZXJhbCBQdWJsaWMgTGljZW5zZSAoVmVyc2lvbiAyKVxuIFtodHRwOi8vd3d3LmdudS5vcmcvbGljZW5zZXMvZ3BsLTIuMC5odG1sXVxuIC0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tXG4gKi9cblxuLyoqXG4gKiBXaWRnZXQgdGhhdCBpcyB1c2VkIGZvciB0aGUgaG92ZXIgZnVuY3Rpb25hbGl0eVxuICogb2YgdGhlIHByb2R1Y3QgdGlsZXMuIEl0IGluY2x1ZGVzIHRoZSBmdW5jdGlvbmFsaXR5XG4gKiBmb3IgdGhlIGltYWdlIGdhbGxlcnkgaW5zaWRlIHRoZSB0aWxlXG4gKi9cbmdhbWJpby53aWRnZXRzLm1vZHVsZShcbiAgICAncHJvZHVjdF9ob3ZlcicsXG5cbiAgICBbXG4gICAgICAgIGdhbWJpby5zb3VyY2UgKyAnL2xpYnMvZXZlbnRzJ1xuICAgIF0sXG5cbiAgICBmdW5jdGlvbiAoZGF0YSkge1xuXG4gICAgICAgICd1c2Ugc3RyaWN0JztcblxuLy8gIyMjIyMjIyMjIyBWQVJJQUJMRSBJTklUSUFMSVpBVElPTiAjIyMjIyMjIyMjXG5cbiAgICAgICAgdmFyICR0aGlzID0gJCh0aGlzKSxcbiAgICAgICAgICAgICR3aW5kb3cgPSAkKHdpbmRvdyksXG4gICAgICAgICAgICAkYm9keSA9ICQoJ2JvZHknKSxcbiAgICAgICAgICAgICRjb250YWluZXIgPSBudWxsLFxuICAgICAgICAgICAgdGltZXIgPSBudWxsLFxuICAgICAgICAgICAgY29tcG9uZW50SWQgPSBudWxsLFxuICAgICAgICAgICAgY2xpY2tUaW1lciA9IDAsXG4gICAgICAgICAgICBkZWZhdWx0cyA9IHtcbiAgICAgICAgICAgICAgICBkZWxheTogNTAsICAgICAgIC8vIERlbGF5IGluIG1zIGFmdGVyIHdoaWNoIGEgaG92ZXJlZCBlbGVtZW50IGdldHMgY2xvc2VkIGFmdGVyIG1vdXNlbGVhdmVcbiAgICAgICAgICAgICAgICBmbHlvdmVyQ2xhc3M6ICdmbHlvdmVyJywgIC8vIENsYXNzIHRoYXQgZ2V0cyBhZGRlZCB0byBldmVyeSBmbHlvdmVyXG4gICAgICAgICAgICAgICAgc2NvcGU6ICcnLCAgICAgICAgICAvLyBTZXRzIHRoZSBzY29wZSBzZWxlY3RvciBmb3IgdGhlIG1vdXNlb3ZlciBldmVudHNcbiAgICAgICAgICAgICAgICBjb250YWluZXI6ICcjd3JhcHBlcicsIC8vIENvbnRhaW5lciBzZWxlY3RvciB3aGljaCBpcyB0aGUgYm91bmRhcnkgZm9yIHRoZSBjbG9uZWQgZWxlbWVudFxuICAgICAgICAgICAgICAgIHByb2R1Y3RVcmxTZWxlY3RvcjogJy5wcm9kdWN0LXVybCcgLy8gYSB0YWcgc2VsZWN0b3Igb2YgcHJvZHVjdCdzIHVybFxuICAgICAgICAgICAgfSxcbiAgICAgICAgICAgIG9wdGlvbnMgPSAkLmV4dGVuZCh0cnVlLCB7fSwgZGVmYXVsdHMsIGRhdGEpLFxuICAgICAgICAgICAgbW9kdWxlID0ge307XG5cbi8vICMjIyMjIyMjIyMgSEVMUEVSIEZVTkNUSU9OUyAjIyMjIyMjIyMjXG5cbiAgICAgICAgLyoqXG4gICAgICAgICAqIEhlbHBlciBmdW5jdGlvbiB0byByZW1vdmUgdGhlIG9wZW5lZCBmbHlvdmVycyB0aGF0XG4gICAgICAgICAqIHdlcmUgYXBwZW5kZWQgdG8gdGhlIGJvZHkgYnkgdGhpcyBjb21wb25lbnRcbiAgICAgICAgICogQHByaXZhdGVcbiAgICAgICAgICovXG4gICAgICAgIHZhciBfcmVtb3ZlRmx5b3ZlciA9IGZ1bmN0aW9uIChhbGwpIHtcbiAgICAgICAgICAgIHZhciAkZmx5b3ZlciA9ICRib2R5LmNoaWxkcmVuKCcuJyArIG9wdGlvbnMuZmx5b3ZlckNsYXNzKTtcbiAgICAgICAgICAgICRmbHlvdmVyID0gYWxsID8gJGZseW92ZXIgOiAkZmx5b3Zlci5maWx0ZXIoJy5wcm9kdWN0LWhvdmVyLScgKyBjb21wb25lbnRJZCk7XG5cbiAgICAgICAgICAgICRmbHlvdmVyLnJlbW92ZSgpO1xuICAgICAgICB9O1xuXG4gICAgICAgIC8qKlxuICAgICAgICAgKiBIZWxwZXIgZnVuY3Rpb24gdGhhdCByZXBsYWNlcyB0aGUgcHJlbG9hZGVyXG4gICAgICAgICAqIGltYWdlcyB3aXRoIHRoZSByZWFsIHRodW1ibmFpbCBpbWFnZXMgb25cbiAgICAgICAgICogbGF5ZXIgY3JlYXRpb24uIFRoaXMgaXMgbmVlZGVkIHRvIHNhdmVcbiAgICAgICAgICogYmFuZHdpZHRoXG4gICAgICAgICAqIEBwYXJhbSAgICAgICB7b2JqZWN0fSAgICAkY2xvbmUgICAgICBqUXVlcnkgc2VsZWN0aW9uIG9mIHRoZSBsYXllclxuICAgICAgICAgKiBAcHJpdmF0ZVxuICAgICAgICAgKi9cbiAgICAgICAgdmFyIF9sb2FkSW1hZ2VzID0gZnVuY3Rpb24gKCRjbG9uZSkge1xuICAgICAgICAgICAgJGNsb25lXG4gICAgICAgICAgICAgICAgLmZpbmQoJy50aHVtYm5haWxzIGltZycpXG4gICAgICAgICAgICAgICAgLmVhY2goZnVuY3Rpb24gKCkge1xuXG4gICAgICAgICAgICAgICAgICAgIHZhciAkc2VsZiA9ICQodGhpcyksXG4gICAgICAgICAgICAgICAgICAgICAgICAkaW1nID0gJCgnPGltZyAvPicpLFxuICAgICAgICAgICAgICAgICAgICAgICAgZGF0YXNldCA9ICRzZWxmLmRhdGEoKSxcbiAgICAgICAgICAgICAgICAgICAgICAgIHNyYyA9IGRhdGFzZXQudGh1bWJTcmMgfHwgZGF0YXNldC5zcmMsXG4gICAgICAgICAgICAgICAgICAgICAgICAkcGFyZW50TGlzdEl0ZW0gPSBudWxsO1xuXG4gICAgICAgICAgICAgICAgICAgICRpbWcub24oJ2xvYWQnLCBmdW5jdGlvbiAoKSB7XG4gICAgICAgICAgICAgICAgICAgICAgICAkcGFyZW50TGlzdEl0ZW0gPSAkc2VsZi5jbG9zZXN0KCdsaScpO1xuICAgICAgICAgICAgICAgICAgICAgICAgJHBhcmVudExpc3RJdGVtXG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgLmFkZENsYXNzKCdsb2FkZWQnKVxuICAgICAgICAgICAgICAgICAgICAgICAgICAgIC5jc3Moe1xuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAnYmFja2dyb3VuZCc6ICcjRkZGRkZGIHVybChcIicgKyBzcmMgKyAnXCIpIG5vLXJlcGVhdCBjZW50ZXInLFxuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAnYmFja2dyb3VuZC1zaXplJzogJ2NvbnRhaW4nXG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgfSlcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAuZmluZCgnaW1nLCAuYWxpZ24taGVscGVyJylcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAucmVtb3ZlKCk7XG4gICAgICAgICAgICAgICAgICAgIH0pLmF0dHIoJ3NyYycsIHNyYyk7XG5cbiAgICAgICAgICAgICAgICB9KTtcbiAgICAgICAgfTtcblxuXG4vLyAjIyMjIyMjIyMjIEVWRU5UIEhBTkRMRVIgIyMjIyMjIyMjI1xuXG4gICAgICAgIC8qKlxuICAgICAgICAgKiBIYW5kbGVyIGZvciB0aGUgY2xpY2sgZXZlbnQgb24gdGhlIHRodW1ibmFpbFxuICAgICAgICAgKiBpbWFnZXMuIEFmdGVyIGEgY2xpY2sgb24gc3VjaCBhbiBpbWFnZSB0aGVcbiAgICAgICAgICogbWFpbiBpbWFnZSBvZiB0aGUgaG92ZXIgZWxlbWVudCBnZXRzIHJlcGxhY2VkXG4gICAgICAgICAqIHdpdGggdGhlIGJpZ2dlciB2ZXJzaW9uIG9mIHRoZSB0aHVtYm5haWwgaW1hZ2VcbiAgICAgICAgICogQHBhcmFtICAgICAgIHtvYmplY3R9ICAgICAgICBlICAgICAgIGpRdWVyeSBldmVudCBvYmplY3RcbiAgICAgICAgICogQHByaXZhdGVcbiAgICAgICAgICovXG4gICAgICAgIHZhciBfbW91c2VFbnRlclRodW1iSGFuZGxlciA9IGZ1bmN0aW9uIChlKSB7XG4gICAgICAgICAgICBlLnByZXZlbnREZWZhdWx0KCk7XG5cbiAgICAgICAgICAgIHZhciAkaW1nID0gJCh0aGlzKSxcbiAgICAgICAgICAgICAgICAkY29udGFpbmVyID0gJGltZy5jbG9zZXN0KCcuJyArIG9wdGlvbnMuZmx5b3ZlckNsYXNzKSxcbiAgICAgICAgICAgICAgICBkYXRhU3JjID0gJGltZy5jc3MoJ2JhY2tncm91bmQtaW1hZ2UnKTtcblxuICAgICAgICAgICAgLy8gQ2hhbmdlIHBhdGggdG8gYmlnIGltYWdlcyBhbmQgcmVtb3ZlIHF1b3Rlc1xuICAgICAgICAgICAgZGF0YVNyYyA9IGRhdGFTcmNcbiAgICAgICAgICAgICAgICAucmVwbGFjZSgnL3RodW1ibmFpbF9pbWFnZXMvJywgJy9pbmZvX2ltYWdlcy8nKVxuICAgICAgICAgICAgICAgIC5yZXBsYWNlKCcvZ2FsbGVyeV9pbWFnZXMvJywgJy90aHVtYm5haWxfaW1hZ2VzLycpXG4gICAgICAgICAgICAgICAgLnJlcGxhY2UoL1tcIiddL2dtLCAnJyk7XG5cbiAgICAgICAgICAgIC8vIFJlbW92ZSBcInVybCgpXCJcbiAgICAgICAgICAgIHZhciBtYXRjaGVzID0gZGF0YVNyYy5tYXRjaCgvdXJsXFwoKC4rKVxcKS8pO1xuICAgICAgICAgICAgaWYgKG1hdGNoZXMgJiYgbWF0Y2hlc1sxXSkge1xuICAgICAgICAgICAgICAgIGRhdGFTcmMgPSBtYXRjaGVzWzFdO1xuICAgICAgICAgICAgfVxuXG4gICAgICAgICAgICBpZiAoZGF0YVNyYykge1xuICAgICAgICAgICAgICAgICRjb250YWluZXJcbiAgICAgICAgICAgICAgICAgICAgLmZpbmQoJy5wcm9kdWN0LWhvdmVyLW1haW4taW1hZ2UgPiBpbWcnKVxuICAgICAgICAgICAgICAgICAgICAuYXR0cignc3JjJywgZGF0YVNyYyk7XG4gICAgICAgICAgICB9XG4gICAgICAgIH07XG5cbiAgICAgICAgLyoqXG4gICAgICAgICAqIEV2ZW50IGhhbmRsZXIgZm9yIHRoZSBtb3VzZSBsZWF2ZSBldmVudCBvZiB0aGVcbiAgICAgICAgICogaG92ZXJlZCBlbGVtZW50LiBJdCBzZXRzIGEgdGltZXIgdG8gcmVtb3ZlIHRoZVxuICAgICAgICAgKiBob3ZlciBlbGVtZW50IGFmdGVyIGEgY2VydGFpbiB0aW1lXG4gICAgICAgICAqIEBwYXJhbSAgICAgICB7b2JqZWN0fSAgICBlICAgICAgIGpRdWVyeSBldmVudCBvYmplY3RcbiAgICAgICAgICogQHByaXZhdGVcbiAgICAgICAgICovXG4gICAgICAgIHZhciBfbW91c2VMZWF2ZUhhbmRsZXIgPSBmdW5jdGlvbiAoZSkge1xuICAgICAgICAgICAgZS5zdG9wUHJvcGFnYXRpb24oKTtcbiAgICAgICAgICAgIHRpbWVyID0gdGltZXIgPyBjbGVhclRpbWVvdXQodGltZXIpIDogbnVsbDtcbiAgICAgICAgICAgIHRpbWVyID0gd2luZG93LnNldFRpbWVvdXQoX3JlbW92ZUZseW92ZXIsIG9wdGlvbnMuZGVsYXkpO1xuICAgICAgICB9O1xuXG4gICAgICAgIC8qKlxuICAgICAgICAgKiBFdmVudCBoYW5kbGVyIGZvciB0aGUgbW91c2UgZW50ZXIgZXZlbnQgb24gYm90aFxuICAgICAgICAgKiBlbGVtZW50cyAoaW5pdGlhbCAmIGhvdmVyZWQgZWxlbWVudCkuXG4gICAgICAgICAqIEl0IGNsb25lcyB0aGUgaW5pdGlhbCBlbGVtZW50IGFuZCBhZGRzIHRoZSBjbG9uZVxuICAgICAgICAgKiB0byB0aGUgYm9keS4gSXQgYWRkaXRpb25hbGx5IGFkZHMgZnVuY3Rpb25hbGl0eVxuICAgICAgICAgKiBmb3IgdGhlIGltYWdlIGdhbGxlcnkgaW5zaWRlIHRoZSBob3ZlcmVkIGVsZW1lbnRcbiAgICAgICAgICogQHBhcmFtICAgICAgIHtvYmplY3R9ICAgICAgICBlICAgICAgIGpRdWVyeSBldmVudCBvYmplY3RcbiAgICAgICAgICogQHByaXZhdGVcbiAgICAgICAgICovXG4gICAgICAgIHZhciBfbW91c2VFbnRlckhhbmRsZXIgPSBmdW5jdGlvbiAoZSkge1xuICAgICAgICAgICAgZS5zdG9wUHJvcGFnYXRpb24oKTtcblxuICAgICAgICAgICAgdmFyICRzZWxmID0gJCh0aGlzKSxcbiAgICAgICAgICAgICAgICAkY2xvbmUgPSBudWxsLFxuICAgICAgICAgICAgICAgICR0YXJnZXQgPSAkYm9keSxcbiAgICAgICAgICAgICAgICB1aWQgPSAkc2VsZi5kYXRhKCkudWlkIHx8IHBhcnNlSW50KE1hdGgucmFuZG9tKCkgKiAxMDAwMCwgMTApLFxuICAgICAgICAgICAgICAgICRmbHlvdmVyID0gJHRhcmdldC5jaGlsZHJlbignLicgKyBvcHRpb25zLmZseW92ZXJDbGFzcyArICcucHJvZHVjdC1ob3Zlci0nICsgY29tcG9uZW50SWRcbiAgICAgICAgICAgICAgICAgICAgKyAnW2RhdGEtcHJvZHVjdF9ob3Zlci11aWQ9XCInICsgdWlkICsgJ1wiXScpLFxuICAgICAgICAgICAgICAgIG9mZnNldCA9ICRzZWxmLm9mZnNldCgpO1xuXG4gICAgICAgICAgICB0aW1lciA9IHRpbWVyID8gY2xlYXJUaW1lb3V0KHRpbWVyKSA6IG51bGw7XG5cbiAgICAgICAgICAgIC8vIENoZWNrIGlmIGZseW92ZXIgbmVlZHMgdG8gYmUgY3JlYXRlZFxuICAgICAgICAgICAgaWYgKCEkc2VsZi5oYXNDbGFzcyhvcHRpb25zLmZseW92ZXJDbGFzcykgJiYgISRmbHlvdmVyLmxlbmd0aCkge1xuICAgICAgICAgICAgICAgIC8vIFJlbW92ZSBvbGQgb3BlbmVkIGZseW92ZXJzXG4gICAgICAgICAgICAgICAgX3JlbW92ZUZseW92ZXIodHJ1ZSk7XG4gICAgICAgICAgICAgICAgJHRoaXMudHJpZ2dlcihqc2UubGlicy50aGVtZS5ldmVudHMuT1BFTl9GTFlPVVQoKSwgJHRoaXMpO1xuXG4gICAgICAgICAgICAgICAgLy8gQWRkIGEgVUlEIGZvciBpZGVudGlmaWNhdGlvbiB0byB0aCBob3ZlcmVkIG9iamVjdFxuICAgICAgICAgICAgICAgICRzZWxmXG4gICAgICAgICAgICAgICAgICAgIC5hdHRyKCdkYXRhLXByb2R1Y3RfaG92ZXItdWlkJywgdWlkKVxuICAgICAgICAgICAgICAgICAgICAuZGF0YSgndWlkJywgdWlkKTtcblxuICAgICAgICAgICAgICAgIC8vIEdlbmVyYXRlIHRoZSBtYXJrdXBcbiAgICAgICAgICAgICAgICAkY2xvbmUgPSAkc2VsZi5jbG9uZSh0cnVlKTtcblxuICAgICAgICAgICAgICAgIC8vIFJlcGxhY2UgdGhlIHByZWxvYWRlciBpbWFnZXMgd2l0aCB0aGUgdGh1bWJuYWlsIGltYWdlc1xuICAgICAgICAgICAgICAgIF9sb2FkSW1hZ2VzKCRjbG9uZSk7XG5cbiAgICAgICAgICAgICAgICAvLyBTZXQgdGhlIHBvc2l0aW9uaW5nIG9mIHRoZSBsYXllclxuICAgICAgICAgICAgICAgICRjbG9uZVxuICAgICAgICAgICAgICAgICAgICAuYWRkQ2xhc3Mob3B0aW9ucy5mbHlvdmVyQ2xhc3MgKyAnIHByb2R1Y3QtaG92ZXItJyArIGNvbXBvbmVudElkKVxuICAgICAgICAgICAgICAgICAgICAuY3NzKHtcbiAgICAgICAgICAgICAgICAgICAgICAgICdwb3NpdGlvbic6ICdhYnNvbHV0ZScsXG4gICAgICAgICAgICAgICAgICAgICAgICAnbGVmdCc6IG9mZnNldC5sZWZ0LFxuICAgICAgICAgICAgICAgICAgICAgICAgJ3RvcCc6IG9mZnNldC50b3AsXG4gICAgICAgICAgICAgICAgICAgICAgICAnd2lkdGgnOiAkc2VsZlswXS5nZXRCb3VuZGluZ0NsaWVudFJlY3QoKS53aWR0aCxcbiAgICAgICAgICAgICAgICAgICAgICAgICdoZWlnaHQnOiAkc2VsZlswXS5nZXRCb3VuZGluZ0NsaWVudFJlY3QoKS5oZWlnaHRcbiAgICAgICAgICAgICAgICAgICAgfSk7XG5cbiAgICAgICAgICAgICAgICAvLyBBZGQgZXZlbnQgbGlzdGVuZXIgdG8gdGhlIGhvdmVyIGVsZW1lbnRzXG4gICAgICAgICAgICAgICAgJGNsb25lXG4gICAgICAgICAgICAgICAgICAgIC5vbignbW91c2VlbnRlcicsIF9tb3VzZUVudGVySGFuZGxlcilcbiAgICAgICAgICAgICAgICAgICAgLm9uKCdtb3VzZWxlYXZlJywgX21vdXNlTGVhdmVIYW5kbGVyKVxuICAgICAgICAgICAgICAgICAgICAub24oJ21vdXNlZW50ZXInLCAnLnRodW1ibmFpbHMnLCBfbW91c2VFbnRlclRodW1iSGFuZGxlcilcbiAgICAgICAgICAgICAgICAgICAgLm9uKCdjbGljaycsIF9jbGlja0hhbmRsZXIpO1xuXG4gICAgICAgICAgICAgICAgLy8gQWRkIHRoZSBlbGVtZW50IHRvIHRoZSBib2R5IGVsZW1lbnRcbiAgICAgICAgICAgICAgICAkYm9keS5hcHBlbmQoJGNsb25lKTtcblxuICAgICAgICAgICAgICAgIGlmICgkY29udGFpbmVyLm9mZnNldCgpLmxlZnQgPiAkY2xvbmUub2Zmc2V0KCkubGVmdCkge1xuICAgICAgICAgICAgICAgICAgICAkY2xvbmUuYWRkQ2xhc3MoJ2dhbGxlcnktcmlnaHQnKTtcbiAgICAgICAgICAgICAgICB9XG4gICAgICAgICAgICB9XG4gICAgICAgIH07XG5cbiAgICAgICAgLyoqXG4gICAgICAgICAqIEhhbmRsZXIgZm9yIHRoZSB3aW5kb3cgcmVzaXplIGV2ZW50LiBJdFxuICAgICAgICAgKiByZWNhbGN1bGF0ZXMgdGhlIHBvc2l0aW9uIG9mIHRoZSBvdmVybGF5c1xuICAgICAgICAgKiBAcHJpdmF0ZVxuICAgICAgICAgKi9cbiAgICAgICAgdmFyIF9yZXNpemVIYW5kbGVyID0gZnVuY3Rpb24gKCkge1xuXG4gICAgICAgICAgICB2YXIgJGZseW92ZXIgPSAkYm9keS5jaGlsZHJlbignLicgKyBvcHRpb25zLmZseW92ZXJDbGFzcyArICcucHJvZHVjdC1ob3Zlci0nICsgY29tcG9uZW50SWQpO1xuXG4gICAgICAgICAgICAkZmx5b3Zlci5lYWNoKGZ1bmN0aW9uICgpIHtcbiAgICAgICAgICAgICAgICB2YXIgJHNlbGYgPSAkKHRoaXMpLFxuICAgICAgICAgICAgICAgICAgICB1aWQgPSAkc2VsZi5kYXRhKCkudWlkLFxuICAgICAgICAgICAgICAgICAgICAkc291cmNlID0gJHRoaXMuZmluZCgnW2RhdGEtcHJvZHVjdF9ob3Zlci11aWQ9XCInICsgdWlkICsgJ1wiXScpLFxuICAgICAgICAgICAgICAgICAgICBvZmZzZXQgPSAkc291cmNlLm9mZnNldCgpO1xuXG4gICAgICAgICAgICAgICAgJHNlbGYuY3NzKHtcbiAgICAgICAgICAgICAgICAgICAgbGVmdDogb2Zmc2V0LmxlZnQsXG4gICAgICAgICAgICAgICAgICAgIHRvcDogb2Zmc2V0LnRvcCxcbiAgICAgICAgICAgICAgICAgICAgd2lkdGg6IDIgKiAkc291cmNlLm91dGVyV2lkdGgoKVxuICAgICAgICAgICAgICAgIH0pO1xuICAgICAgICAgICAgfSk7XG5cbiAgICAgICAgfTtcblxuICAgICAgICAvKipcbiAgICAgICAgICogRXZlbnQgaGFuZGxlciB0aGF0IGNsb3NlcyB0aGUgZmx5b3ZlcnNcbiAgICAgICAgICogaWYgYW5vdGhlciBmbHlvdmVyIG9wZW5zIG9uIHRoZSBwYWdlXG4gICAgICAgICAqIEBwYXJhbSAgICAgICB7b2JqZWN0fSAgICAgICAgZSAgICAgICAgICAgalF1ZXJ5IGV2ZW50IG9iamVjdFxuICAgICAgICAgKiBAcGFyYW0gICAgICAge29iamVjdH0gICAgICAgIGQgICAgICAgICAgIGpRdWVyeSBzZWxlY3Rpb24gb2YgdGhlIGV2ZW50IGVtaXR0ZXJcbiAgICAgICAgICogQHByaXZhdGVcbiAgICAgICAgICovXG4gICAgICAgIHZhciBfY2xvc2VMYXllcnMgPSBmdW5jdGlvbiAoZSwgZCkge1xuICAgICAgICAgICAgaWYgKCR0aGlzICE9PSBkKSB7XG4gICAgICAgICAgICAgICAgX3JlbW92ZUZseW92ZXIoKTtcbiAgICAgICAgICAgIH1cbiAgICAgICAgfTtcblxuXG4gICAgICAgIC8qKlxuICAgICAgICAgKiBFdmVudCBoYW5kbGVyIHRoYXQgbWFrZXMgdGhlIGZseW92ZXIgYW5kIHByb2R1Y3QgaW1hZ2UgY2xpY2thYmxlIGxpbmtpbmcgdG8gdGhlIHByb2R1Y3QgZGV0YWlscyBwYWdlXG4gICAgICAgICAqXG4gICAgICAgICAqIEBwYXJhbSAgICAgICB7b2JqZWN0fSAgICAgICAgZSAgICAgICAgICAgalF1ZXJ5IGV2ZW50IG9iamVjdFxuICAgICAgICAgKiBAcHJpdmF0ZVxuICAgICAgICAgKi9cbiAgICAgICAgdmFyIF9jbGlja0hhbmRsZXIgPSBmdW5jdGlvbiAoZSkge1xuICAgICAgICAgICAgdmFyICRjb250YWluZXIgPSAkKHRoaXMpO1xuXG4gICAgICAgICAgICBpZiAoJCh0aGlzKS5oYXNDbGFzcygncHJvZHVjdC1jb250YWluZXInKSA9PT0gZmFsc2UpIHtcbiAgICAgICAgICAgICAgICAkY29udGFpbmVyID0gJCh0aGlzKS5jbG9zZXN0KCcucHJvZHVjdC1jb250YWluZXInKTtcbiAgICAgICAgICAgIH1cblxuICAgICAgICAgICAgdmFyICRsaW5rID0gJGNvbnRhaW5lci5maW5kKG9wdGlvbnMucHJvZHVjdFVybFNlbGVjdG9yKS5maXJzdCgpO1xuXG4gICAgICAgICAgICBmdW5jdGlvbiBjYWxsYmFjaygpIHtcbiAgICAgICAgICAgICAgICBpZiAoJGxpbmsubGVuZ3RoKSB7XG4gICAgICAgICAgICAgICAgICAgIHZhciB1cmwgPSAkbGluay5hdHRyKCdocmVmJyk7XG5cbiAgICAgICAgICAgICAgICAgICAgaWYgKHVybCAhPT0gdW5kZWZpbmVkKSB7XG4gICAgICAgICAgICAgICAgICAgICAgICBlLnN0b3BQcm9wYWdhdGlvbigpO1xuICAgICAgICAgICAgICAgICAgICAgICAgZS5wcmV2ZW50RGVmYXVsdCgpO1xuXG4gICAgICAgICAgICAgICAgICAgICAgICAvLyBwcmV2ZW50IGRvdWJsZSBfY2xpY2tIYW5kbGVyIGFjdGlvbnNcbiAgICAgICAgICAgICAgICAgICAgICAgIGlmIChuZXcgRGF0ZSgpLmdldFRpbWUoKSAtIGNsaWNrVGltZXIgPCAxMDApIHtcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICByZXR1cm47XG4gICAgICAgICAgICAgICAgICAgICAgICB9IGVsc2Uge1xuICAgICAgICAgICAgICAgICAgICAgICAgICAgIGNsaWNrVGltZXIgPSBuZXcgRGF0ZSgpLmdldFRpbWUoKTtcbiAgICAgICAgICAgICAgICAgICAgICAgIH1cblxuICAgICAgICAgICAgICAgICAgICAgICAgc3dpdGNoIChlLndoaWNoKSB7XG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgLy8gbGVmdCBjbGlja1xuICAgICAgICAgICAgICAgICAgICAgICAgICAgIGNhc2UgMTpcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgaWYgKGUuY3RybEtleSkge1xuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgd2luZG93Lm9wZW4odXJsLCAnX2JsYW5rJyk7XG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICByZXR1cm47XG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgYnJlYWs7XG5cbiAgICAgICAgICAgICAgICAgICAgICAgICAgICAvLyBtaWRkbGUgY2xpY2tcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICBjYXNlIDI6XG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHdpbmRvdy5vcGVuKHVybCwgJ19ibGFuaycpO1xuICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICByZXR1cm47XG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGJyZWFrO1xuXG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgLy8gcmlnaHQgY2xpY2tcbiAgICAgICAgICAgICAgICAgICAgICAgICAgICBjYXNlIDM6XG4gICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHJldHVybjtcbiAgICAgICAgICAgICAgICAgICAgICAgIH1cblxuICAgICAgICAgICAgICAgICAgICAgICAgbG9jYXRpb24uaHJlZiA9IHVybDtcbiAgICAgICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgIH1cblxuICAgICAgICAgICAganNlLmxpYnMuaG9va3MuZXhlY3V0ZShqc2UubGlicy5ob29rcy5rZXlzLnNob3AucHJvZHVjdC5saXN0aW5nLmhvdmVyLCB7Y29udGFpbmVyOiAkY29udGFpbmVyfSwgNTAwKVxuICAgICAgICAgICAgICAgIC50aGVuKGNhbGxiYWNrKVxuICAgICAgICAgICAgICAgIC5jYXRjaChjYWxsYmFjayk7XG4gICAgICAgIH07XG5cbi8vICMjIyMjIyMjIyMgSU5JVElBTElaQVRJT04gIyMjIyMjIyMjI1xuXG4gICAgICAgIC8qKlxuICAgICAgICAgKiBJbml0IGZ1bmN0aW9uIG9mIHRoZSB3aWRnZXRcbiAgICAgICAgICogQGNvbnN0cnVjdG9yXG4gICAgICAgICAqL1xuICAgICAgICBtb2R1bGUuaW5pdCA9IGZ1bmN0aW9uIChkb25lKSB7XG5cbiAgICAgICAgICAgIGNvbXBvbmVudElkID0gcGFyc2VJbnQoTWF0aC5yYW5kb20oKSAqIDEwMDAwLCAxMCk7XG4gICAgICAgICAgICAkY29udGFpbmVyID0gJChvcHRpb25zLmNvbnRhaW5lcik7XG5cbiAgICAgICAgICAgICR0aGlzXG4gICAgICAgICAgICAgICAgLm9uKCd0b3VjaHN0YXJ0JywgZnVuY3Rpb24gKCkge1xuICAgICAgICAgICAgICAgICAgICAvLyBXb3JrYXJvdW5kIGZvciB0YWJsZXQgbmF2aWdhdGlvbiBwcm9ibGVtXG4gICAgICAgICAgICAgICAgICAgICR0aGlzLm9mZignbW91c2VlbnRlciBtb3VzZWxlYXZlJyk7XG4gICAgICAgICAgICAgICAgfSlcbiAgICAgICAgICAgICAgICAub24oJ3RvdWNoZW5kJywgZnVuY3Rpb24gKCkge1xuICAgICAgICAgICAgICAgICAgICAkdGhpc1xuICAgICAgICAgICAgICAgICAgICAgICAgLm9mZignbW91c2VlbnRlcicsIG9wdGlvbnMuc2NvcGUgKyAnIC5wcm9kdWN0LWNvbnRhaW5lcicsIF9tb3VzZUVudGVySGFuZGxlcilcbiAgICAgICAgICAgICAgICAgICAgICAgIC5vZmYoJ21vdXNlbGVhdmUnLCBvcHRpb25zLnNjb3BlICsgJyAucHJvZHVjdC1jb250YWluZXInLCBfbW91c2VMZWF2ZUhhbmRsZXIpO1xuICAgICAgICAgICAgICAgIH0pXG4gICAgICAgICAgICAgICAgLm9uKCdtb3VzZWVudGVyJywgb3B0aW9ucy5zY29wZSArICcgLnByb2R1Y3QtY29udGFpbmVyJywgX21vdXNlRW50ZXJIYW5kbGVyKVxuICAgICAgICAgICAgICAgIC5vbignbW91c2VsZWF2ZScsIG9wdGlvbnMuc2NvcGUgKyAnIC5wcm9kdWN0LWNvbnRhaW5lcicsIF9tb3VzZUxlYXZlSGFuZGxlcik7XG5cbiAgICAgICAgICAgICR0aGlzLmZpbmQoJy5wcm9kdWN0LWNvbnRhaW5lciAucHJvZHVjdC1pbWFnZScpLm9uKCdjbGljayBtb3VzZXVwJywgX2NsaWNrSGFuZGxlcik7XG5cbiAgICAgICAgICAgICRib2R5XG4gICAgICAgICAgICAgICAgLm9uKGpzZS5saWJzLnRoZW1lLmV2ZW50cy5PUEVOX0ZMWU9VVCgpLCBfY2xvc2VMYXllcnMpO1xuXG4gICAgICAgICAgICAkd2luZG93XG4gICAgICAgICAgICAgICAgLm9uKCdyZXNpemUnLCBfcmVzaXplSGFuZGxlcik7XG5cbiAgICAgICAgICAgIGRvbmUoKTtcbiAgICAgICAgfTtcblxuICAgICAgICAvLyBSZXR1cm4gZGF0YSB0byB3aWRnZXQgZW5naW5lXG4gICAgICAgIHJldHVybiBtb2R1bGU7XG4gICAgfSk7XG4iXX0=

Youez - 2016 - github.com/yon3zu
LinuXploit