PageSourceSearch

https://drivemotors.by/local/components/codex/user.consent.request…/.default/script.js?174305693028774

js drivemotors.by collected 2026-10-07 00:02:57 UTC 28,774 bytes, 646 lines download raw bytes

1(function () {
2
3    'use strict';
4
5    BX.namespace('BX.CodeX');
6
7    /**
8     * Constructor.
9     * @param params
10     * @constructor
11     */
12    BX.CodeX.Cookies = function (params) {
13        this.storageKey = 'bxCookies-v34';
14        this.storage = window.localStorage;
15        this.currentStorage = this.storage;
16        this.isFirstVisit = this.getStorage(true) === null;
17        this.openCurentPopup=false;
18        this.enable = params.enable === true;
19        this.onlyInformation = params.onlyInformation === true;
20        this.siteId = parseInt(params.siteId);
21        this.availableCodes = params.availableCodes || [];
22        this.idButtonOpt = params.idButtonOpt || 'bx-landing-cookies-opt';
23        this.idButtonOptLink = params.idButtonOptLink || 'bx-landing-cookies-opt-link';
24        this.idButtonAccept = params.idButtonAccept || 'bx-landing-cookies-accept';
25        this.idAgreementPopup = params.idAgreementPopup || 'bx-landing-cookies-popup';
26        this.idCookiesNotice = params.idCookiesNotice || 'bx-landing-cookies-popup-notice';
27        this.idAgreementSmallPopup = params.idAgreementSmallPopup || 'bx-landing-cookies-popup-warning';
28        this.classNameMainAgreement = params.classNameMainAgreement || 'bx-landing-cookies-main-agreement';
29        this.classNameAnalyticAgreements = params.classNameAnalyticAgreements || 'bx-landing-cookies-system-agreements';
30        this.classNameTechnicalAgreements = params.classNameTechnicalAgreements || 'bx-landing-cookies-technical-agreements';
31        this.classNameOtherAgreements = params.classNameOtherAgreements || 'bx-landing-cookies-other-agreements';
32        this.classNameButtonSave = params.classNameButtonSave || 'bx-landing-cookies-button-save';
33        this.classNameButtonCancel = params.classNameButtonCancel || 'bx-landing-cookies-button-cancel';
34        this.classNameButtonCancelSmall = params.classNameButtonCancelSmall || 'bx-landing-cookies-button-cancel-second';
35        this.classNameButtonClose = params.classNameButtonClose || 'bx-landing-cookies-button-close';
36        this.classNameCookiesSwitcher = params.classNameCookiesSwitcher || 'bx-landing-cookies-switcher';
37        this.messages = params.messages || {};
38        this.agreementAjaxPath = params.agreementAjaxPath || '/';
39
40        this.overlay = BX.create('div', {
41            attrs: {className: 'bx-landing-cookies-popup-overlay'}
42        });
43
44        this.cookiesNotice = BX(this.idCookiesNotice);
45
46        this.acceptedAgreements = {};
47        this.agreementsChckRefs = {};
48        this.popupModified = false;
49        this.popupInited = false;
50        this.dataLoaded = false;
51        this.idMainAgreementContainer = null;
52        this.idAnalyticAgreementsContainer = null;
53        this.idTechnicalAgreementsContainer = null;
54        this.idOtherAgreementsContainer = null;
55        this.idButtonSave = null;
56        this.idButtonCancel = null;
57        this.idButtonClose = null;
58        this.idButtonSwitcher = null;
59
60        if (!this.enable) {
61            this.enableAllCookies();
62        } else {
63            if (BX(this.idButtonOpt) && BX(this.idAgreementPopup)) {
64                BX.bind(BX(this.idButtonOpt), 'click', BX.delegate(this.openPopup, this));
65            }
66            if (BX(this.idButtonOptLink) && BX(this.idAgreementPopup)) {
67                BX.bind(BX(this.idButtonOptLink), 'click', BX.delegate(this.openPopup, this));
68            }
69            if (BX(this.idButtonAccept)) {
70                BX.bind(BX(this.idButtonAccept), 'click', BX.delegate(this.enableAllCookies, this));
71            }
72            if (this.cookiesNotice) {
73                BX.bind(this.cookiesNotice, 'mouseenter', BX.delegate(this.showCookiesNoticeText, this));
74                BX.bind(this.cookiesNotice, 'mouseleave', BX.delegate(this.hideCookiesNoticeText, this));
75                BX.bind(this.cookiesNotice, 'click', BX.delegate(this.openPopup, this));
76            }
77            if (this.getCookie('cookies_declined')) {
78                this.showCookiesNotice();
79            } else {
80                this.actualizeFromStorage();
81            }
82        }
83        this.checkLastVisitCookie();
84    };
85
86    BX.CodeX.Cookies.prototype = {
87
88        getAvailableHooks: function () {
89            let codes = [];
90            this.availableCodes.map(function (code) {
91                if (!BX.util.in_array(code, codes)) {
92                    codes.push(code);
93                }
94            });
95            return codes;
96        }, enableAllCookies: function () {
97            window.dataLayer = window.dataLayer || [];
98            window.dataLayer.push({'event': 'cookie_consent_granted'});
99            let hooks = this.getAvailableHooks();
100            this.setStorage(hooks);
101            this.hideSmallPopup();
102            this.showCookiesNotice();
103            location.reload();
104        }, disableAllCookies: function () {
105            window.dataLayer = window.dataLayer || [];
106            //this.storage.removeItem(this.storageKey);
107            this.storage.clear();
108            // Получаем все cookies
109            const SYSTEM_COOKIES = ['PHPSESSID'];
110            document.cookie.split(";").forEach(cookie => {
111                const name = cookie.split("=")[0].trim();
112                if (!SYSTEM_COOKIES.includes(name)) {
113                    document.cookie = `${name}=; expires=Thu, 01 Jan 1970 00:00:00 GMT; path=/; domain=${window.location.hostname}`;
114                }
115            });
116            // Отправка события в DataLayer
117            window.dataLayer.push({'event': 'cookie_consent_revoked'});
118            document.cookie = 'cookies_declined=true; path=/; max-age=31536000';
119            location.reload();
120        }, actualizeFromStorage: function () {
121            let storage = this.getStorage(true);
122            if (storage !== null) {
123                this.showCookiesNotice();
124            } else {
125                this.showSmallPopup();
126                this.initializeSmallPopup();
127            }
128
129            // Применяем только те cookies, которые были сохранены в localStorage
130            this.fireEvent(storage || []);
131        },
132
133        initializeSmallPopup: function () {
134            if (this.idAgreementSmallPopup) {
135                this.idButtonCancelSecond = BX(this.idAgreementSmallPopup).querySelector('.' + this.classNameButtonCancelSmall);
136            }
137
138            if (this.idButtonCancelSecond) {
139                BX.bind(BX(this.idButtonCancelSecond), 'click', BX.delegate(this.cancelPopup, this));
140            }
141
142        }, initializePopup: function () {
143            if (this.popupInited) {
144                return;
145            }
146            this.popupInited = true;
147            if (this.classNameMainAgreement) {
148                if (BX(this.idAgreementPopup)) {
149                    this.idMainAgreementContainer = BX(this.idAgreementPopup).querySelector('.' + this.classNameMainAgreement);
150                    this.idAnalyticAgreementsContainer = BX(this.idAgreementPopup).querySelector('.' + this.classNameAnalyticAgreements);
151                    this.idTechnicalAgreementsContainer = BX(this.idAgreementPopup).querySelector('.' + this.classNameTechnicalAgreements);
152                    this.idOtherAgreementsContainer = BX(this.idAgreementPopup).querySelector('.' + this.classNameOtherAgreements);
153                    this.idButtonClose = BX(this.idAgreementPopup).querySelector('.' + this.classNameButtonClose);
154                    this.idButtonSave = BX(this.idAgreementPopup).querySelector('.' + this.classNameButtonSave);
155                    this.idButtonCancel = BX(this.idAgreementPopup).querySelector('.' + this.classNameButtonCancel);
156                    this.idButtonSwitcher = [].slice.call(BX(this.idAgreementPopup).querySelectorAll('.' + this.classNameCookiesSwitcher));
157                }
158                if (this.idButtonClose) {
159                    BX.bind(BX(this.idButtonClose), 'click', BX.delegate(this.onClickCloseIcon, this));
160                }
161                if (this.idButtonSave) {
162                    BX.bind(BX(this.idButtonSave), 'click', BX.delegate(this.savePopup, this));
163                }
164                if (this.idButtonCancel) {
165                    BX.bind(BX(this.idButtonCancel), 'click', BX.delegate(this.cancelPopup, this));
166                }
167                if (this.idButtonSwitcher) {
168                    this.idButtonSwitcher.map(function (node) {
169                        BX.bind(BX(node), 'click', this.switchAgreements.bind(this, BX.data(BX(node), 'type')));
170                    }.bind(this));
171                }
172            }
173        }, loadAgreements: function () {
174
175            if (!this.idMainAgreementContainer || this.dataLoaded) {
176                this.initCheckboxes();
177                return;
178            }
179
180            this.idMainAgreementContainer.innerHTML = '...';
181
182            BX.ajax({
183                url: this.agreementAjaxPath + '?action=landing.api.cookies.getAgreements',
184                method: 'POST',
185                dataType: 'json',
186                data: {
187                    siteId: this.siteId
188                },
189                onsuccess: function (result) {
190                    if (!result.data) {
191                        return;
192                    }
193                    this.dataLoaded = true;
194                    if (result.data['main']) {
195                        this.idMainAgreementContainer.innerHTML = result.data['main']['AGREEMENT_TEXT'];
196                    }
197                    let agreementsLoaded = false;
198                    if (result.data['analytic'] && this.idAnalyticAgreementsContainer) {
199                        agreementsLoaded = true;
200                        this.buildAgreements(this.idAnalyticAgreementsContainer, result.data['analytic']);
201                    } else if (this.idAnalyticAgreementsContainer) {
202                        BX.hide(this.idAnalyticAgreementsContainer.parentNode);
203                    }
204                    if (result.data['technical'] && this.idTechnicalAgreementsContainer) {
205                        agreementsLoaded = true;
206                        this.buildAgreements(this.idTechnicalAgreementsContainer, result.data['technical']);
207                    } else if (this.idTechnicalAgreementsContainer) {
208                        BX.hide(this.idTechnicalAgreementsContainer.parentNode);
209                    }
210                    if (result.data['other'] && this.idOtherAgreementsContainer) {
211                        agreementsLoaded = true;
212                        this.buildAgreements(this.idOtherAgreementsContainer, result.data['other']);
213                    } else if (this.idOtherAgreementsContainer) {
214                        BX.hide(this.idOtherAgreementsContainer.parentNode);
215                    }
216                    if (agreementsLoaded) {
217                        this.initCheckboxes();
218                    }
219                }.bind(this)
220            });
221        }, openPopup: function () {
222            this.initializePopup();
223            if (BX(this.idAgreementPopup)) {
224                BX.show(BX(this.idAgreementPopup));
225                this.showOverlay();
226                this.hideSmallPopup();
227                this.loadAgreements();
228            }
229        }, closePopup: function () {
230            this.openCurentPopup=false;
231            this.setPopupModified(false);
232            if (BX(this.idAgreementPopup)) {
233                this.hideOverlay();
234                BX.hide(BX(this.idAgreementPopup));
235            }
236            this.hideSmallPopup();
237            this.showCookiesNotice();
238        }, savePopup: function () {
239            const allSwitchersOff = this.checkSwitchersState(null, false);
240            if (allSwitchersOff) {
241                this.enableAllCookies();
242                this.closePopup();
243                return;
244            }
245            if (this.popupModified) {
246                let agreementCodes = this.getAcceptedAgreements();
247                this.setStorage(agreementCodes);
248            } else {
249                this.enableAllCookies();
250            }
251            this.closePopup();
252        }, cancelPopup: function () {
253            if (this.popupModified) {
254                let agreementCodes = this.currentStorage;
255                this.setStorage(agreementCodes);
256            } else {
257                this.disableAllCookies();
258            }
259            this.showSmallPopup();
260            this.closePopup();
261        },
262
263        /**
264         * Declines agreements and closes popup.
265         */
266        onClickCloseIcon: function () {
267            this.closePopup();
268        },
269
270        /**
271         * Sets flag popup modified and rename buttons.
272         * @param {bool} flag Flag.
273         */
274        setPopupModified: function (flag) {
275            this.popupModified = flag;
276
277            if (this.idButtonSave) {
278                if (this.popupModified) {
279                    this.idButtonSave.textContent = this.messages.acceptModified;
280                } else {
281                    this.idButtonSave.textContent = this.messages.acceptAll
282                }
283            }
284            if (this.idButtonCancel) {
285                this.idButtonCancel.textContent = this.popupModified ? this.messages.declineModified : this.messages.declineAll;
286            }
287        },
288
289        /**
290         * Returns data from local storage.
291         * @package {bool} asIs If true returns original value.
292         * @return {object}
293         */
294        getStorage: function (asIs) {
295            let store = this.storage.getItem(this.storageKey);
296            if (store) {
297                store = JSON.parse(store);
298            }
299            if (asIs === true) {
300                return store;
301            }
302            return store || [];
303        },
304
305        setStorage: function (store) {
306            const allowedCookies = ["ga", "gtm", "ym", "fbp", "vkp", "yt", "kumvp"];
307            const filteredStore = store.filter(code => allowedCookies.includes(code));
308
309            // Сохраняем только разрешенные cookies
310            this.storage.setItem(this.storageKey, JSON.stringify(filteredStore));
311
312            // Отправляем событие только с разрешенными cookies
313            this.fireEvent(filteredStore);
314
315            // Отправляем данные на сервер
316            BX.ajax({
317                url: this.agreementAjaxPath + '?action=landing.api.cookies.acceptAgreements',
318                method: 'POST',
319                dataType: 'json',
320                data: {
321                    siteId: this.siteId, accepted: filteredStore
322                }
323            });
324        }, fireEvent: function (params) {
325            const allowedCookies = ["ga", "gtm", "ym", "fbp", "vkp", "yt", "kumvp"];
326            const filteredParams = params.filter(code => allowedCookies.includes(code));
327
328            // Отправляем событие в GTM
329            window.dataLayer = window.dataLayer || [];
330            window.dataLayer.push({
331                event: 'BX.Landing.Cookies:onAccept', allowedCookies: filteredParams
332            });
333
334            // Если разрешен GTM, загружаем его
335            if (filteredParams.includes('gtm')) {
336                loadGTM();
337            }
338
339            // Отправляем событие в Bitrix (если нужно)
340            BX.onCustomEvent('BX.Landing.Cookies:onAccept', [filteredParams]);
341        },
342
343        switchAgreements: function (type) {
344            if (!this.idButtonSwitcher) {
345                return;
346            }
347
348            // Определяем новое состояние для переключателей указанного типа
349            let setToState = !this.checkSwitchersState(type, true); // Инвертируем текущее состояние
350
351            // Применяем новое состояние ко всем переключателям указанного типа
352            for (let key in this.agreementsChckRefs) {
353                let switcher = BX.UI.Switcher.getById(key);
354                if (switcher) {
355                    let switcherType = switcher.getNode().getAttribute('data-type');
356                    if (switcherType === type) {
357                        switcher.check(setToState);
358                        this.acceptAgreement(key, setToState);
359                    }
360                }
361            }
362
363            // Обновляем текст переключателей
364            this.actualizeAgreementsSwitcher();
365
366            // Устанавливаем флаг, что настройки были изменены
367            this.setPopupModified(true);
368
369            // Сохраняем изменения в localStorage
370            let agreementCodes = this.getAcceptedAgreements();
371            this.setStorage(agreementCodes);
372        },
373
374        /**
375         * Actualize agreements switcher title.
376         */
377        actualizeAgreementsSwitcher: function () {
378
379            if (this.idButtonSwitcher) {
380                let typesChecked = {};
381                for (let key in this.agreementsChckRefs) {
382                    //console.log(key);
383                    let switcher = BX.UI.Switcher.getById(key);
384
385                    if (switcher) {
386                        let type = switcher.getNode().getAttribute('data-type');
387                        if (switcher.isChecked()) {
388                            typesChecked[type] = true;
389                        }
390                    }
391                }
392                this.idButtonSwitcher.map(function (node) {
393                    let type = BX.data(BX(node), 'type');
394                    if (typesChecked[type] === true) {
395                        BX(node).textContent = this.messages.switcherOff;
396                        BX(node).setAttribute('data-state', false);
397                    } else {
398                        BX(node).textContent = this.messages.switcherOn;
399                        BX(node).setAttribute('data-state', true);
400                    }
401                }.bind(this));
402            }
403        },
404
405        /**
406         * Accepts one agreement.
407         * @param {string} code Agreement code.
408         * @param {bool} flag Checked flag.
409         */
410        acceptAgreement: function (code, flag) {
411
412            this.acceptedAgreements['ym'] = flag;
413            this.acceptedAgreements['kumvp'] = flag;
414            this.acceptedAgreements['ga'] = flag;
415            this.acceptedAgreements['gtm'] = flag;
416            this.acceptedAgreements['fbp'] = flag;
417            this.acceptedAgreements['vkp'] = flag;
418            this.acceptedAgreements['yt'] = flag;
419            // Обновляем визуальное состояние переключателей через setTimeout
420            setTimeout(() => {
421                BX.UI.Switcher.getById('ym').check(flag); // Устанавливаем состояние переключателя ym
422                BX.UI.Switcher.getById('kumvp').check(flag); // Устанавливаем состояние переключателя kumvp
423                BX.UI.Switcher.getById('ga').check(flag); // Устанавливаем состояние переключателя ga
424                BX.UI.Switcher.getById('gtm').check(flag); // Устанавливаем состояние переключателя gtm
425                BX.UI.Switcher.getById('fbp').check(flag); // Устанавливаем состояние переключателя fbp
426                BX.UI.Switcher.getById('vkp').check(flag); // Устанавливаем состояние переключателя vkp
427                BX.UI.Switcher.getById('yt').check(flag); // Устанавливаем состояние переключателя yt
428            }, 0);
429
430        },
431
432        /**
433         * Returns all accepted agreements.
434         * @return {[]}
435         */
436        getAcceptedAgreements: function () {
437            let codes = [];
438            for (let code in this.acceptedAgreements) {
439                if (this.acceptedAgreements[code] === true) {
440                    codes.push(code);
441                }
442            }
443
444            return codes;
445        }, initCheckboxes: function () {
446            let codesFromStorage = this.getStorage();
447            this.currentStorage = this.getStorage();
448
449            for (let key in this.agreementsChckRefs) {
450                let switcher = BX.UI.Switcher.getById(key);
451                if (switcher) {
452                    let checked = BX.util.in_array(key, codesFromStorage);
453                    switcher.check(checked);
454                    this.acceptAgreement(key, checked);
455                }
456            }
457
458            this.actualizeAgreementsSwitcher();
459        },
460
461        /**
462         * Builds agreements div.
463         * @param {HTMLElement} node Root element.
464         * @param {object} agreements Agreements data.
465         */
466        buildAgreements: function (node, agreements) {
467            let agreementsNodes = [];
468
469            for (let key in agreements) {
470                this.agreementsChckRefs[key] = BX.create('span', {
471                    attrs: {
472                        className: 'ui-switcher ui-switcher-size-sm',
473                        'data-type': agreements[key]['TYPE'],
474                        'data-switcher': '{"id":"' + key + '"}'
475                    }, events: {
476                        click: function (key) {
477                            this.acceptAgreement(key, !BX.UI.Switcher.getById(key).isChecked());
478                            this.setPopupModified(true);
479                            setTimeout(function () {
480                                this.actualizeAgreementsSwitcher();
481                            }.bind(this), 0);
482                        }.bind(this, key)
483                    }
484                });
485                agreementsNodes.push(BX.create('div', {
486                    attrs: {
487                        className: 'bx-landing-cookies-analytics-block' + ((agreements[key]['TYPE'] !== 'analytic') ? ' bx-landing-cookies-analytics-block-disabled' : '')
488                    }, children: [BX.create('div', {
489                        attrs: {className: 'bx-landing-cookies-analytics-header'}, children: [BX.create('div', {
490                            attrs: {className: 'bx-landing-cookies-analytics-title'}, html: agreements[key]['TITLE']
491                        }), this.agreementsChckRefs[key],]
492                    }), BX.create('div', {
493                        attrs: {className: 'bx-landing-cookies-analytics-content'}, html: agreements[key]['CONTENT']
494                    })]
495                }));
496            }
497
498            node.appendChild(BX.create('div', {
499                children: agreementsNodes
500            }));
501            BX.UI.Switcher.initByClassName();
502        },
503
504        //Popup parts below
505
506        showCookiesNotice: function () {
507            if (BX(this.idAgreementSmallPopup) && !this.onlyInformation) {
508                this.cookiesNotice.style.display = 'flex';
509            }
510        },
511
512        showCookiesNoticeText: function () {
513            this.cookiesNotice.classList.add('bx-landing-cookies-popup-notice-full');
514            let textWidth = this.cookiesNotice.querySelector('.bx-landing-cookies-popup-notice-text').offsetWidth;
515            this.cookiesNotice.style.width = this.cookiesNotice.offsetWidth + textWidth + 'px';
516        },
517
518        hideCookiesNoticeText: function () {
519            this.cookiesNotice.style.width = '27px';
520            this.cookiesNotice.classList.remove('bx-landing-cookies-popup-notice-full');
521        },
522
523        showOverlay: function () {
524            document.body.append(this.overlay);
525        },
526
527        hideOverlay: function () {
528            this.overlay.remove();
529        },
530
531        showSmallPopup: function () {
532            if (BX(this.idAgreementSmallPopup)) {
533                BX(this.idAgreementSmallPopup).style.display = 'block';
534            }
535        },
536
537        hideSmallPopup: function () {
538            if (BX(this.idAgreementSmallPopup)) {
539                BX(this.idAgreementSmallPopup).style.display = 'none';
540            }
541        },
542        getCookie: function(name) {
543            const value = `; ${document.cookie}`;
544            const parts = value.split(`; ${name}=`);
545            if (parts.length === 2) return parts.pop().split(';').shift();
546        },
547        checkSwitchersState: function (type, expectedState) {
548            let allInState = true;
549            for (const code in this.agreementsChckRefs) {
550                const switcher = BX.UI.Switcher.getById(code);
551                if (switcher) {
552                    const currentType = switcher.getNode().getAttribute('data-type');
553                    if (type && currentType !== type) continue;
554                    if (switcher.isChecked() !== expectedState) {
555                        allInState = false;
556                        break;
557                    }
558                }
559            }
560            return allInState;
561        },
562        checkLastVisitCookie: function() {
563            if (!this.getCookie('BITRIX_SM_LAST_VISIT') && this.enable) {
564                this.showCookieWarning();
565            }
566        },
567
568        showCookieWarning: function() {
569            const createWarningBlock = () => {
570                const warningBlock = BX.create('div', {
571                    attrs: {className: 'bx-cookie-warning-alert'},
572                    html: `
573                <div class="bx-cookie-warning-content">
574                    <svg class="bx-cookie-warning-icon" width="24" height="24" viewBox="0 0 24 24" fill="none">
575                        <path d="M12 2C6.48 2 2 6.48 2 12s4.48 10 10 10 10-4.48 10-10S17.52 2 12 2zm1 15h-2v-2h2v2zm0-4h-2V7h2v6z" 
576                              fill="currentColor"/>
577                    </svg>
578                    <div class="bx-cookie-warning-text">
579                        <h4>Функционал ограничен</h4>
580                        <p>Для полной работы сайта необходимо разрешить использование cookies</p>
581                    </div>
582                </div>
583            `
584                });
585
586                const detailsButton = BX.create('button', {
587                    attrs: {
588                        className: 'bx-cookie-warning-btn'
589                    },
590                    html: `
591                <span>Подробнее</span>
592                <svg width="16" height="16" viewBox="0 0 24 24" fill="none">
593                    <path d="M10 7l5 5-5 5" stroke="currentColor" stroke-width="2" 
594                          stroke-linecap="round" stroke-linejoin="round"/>
595                </svg>
596            `,
597                    events: {
598                        click: BX.delegate(this.openPopup, this),
599                        mouseenter: () => detailsButton.classList.add('hover'),
600                        mouseleave: () => detailsButton.classList.remove('hover')
601                    }
602                });
603
604                warningBlock.appendChild(detailsButton);
605                return warningBlock;
606            };
607
608            // Обрабатываем modal-body с формами
609            const modalBodies = document.querySelectorAll('.modal-body');
610            modalBodies.forEach(modalBody => {
611                const hasForm = modalBody.querySelector('form');
612                    const existingAlert = modalBody.querySelector('.bx-cookie-warning-alert');
613                    if (!existingAlert) {
614                        const warningBlock = createWarningBlock();
615                        modalBody.insertBefore(warningBlock, modalBody.firstChild);
616                    }
617            });
618
619            const contactForms  = document.querySelectorAll('.contact-form');
620            contactForms.forEach(contactForms => {
621                const hasForm = contactForms.querySelector('form');
622                if (hasForm) {
623                    const existingAlert = contactForms.querySelector('.bx-cookie-warning-alert');
624                    if (!existingAlert) {
625                        const warningBlock = createWarningBlock();
626                        contactForms.insertBefore(warningBlock, contactForms.firstChild);
627                    }
628                }
629            });
630        },
631    };
632
633})();
634
635function loadGTM() {
vendor: 451 bytes, lines 635-645
635
636    (function (w, d, s, l, i) {
637        w[l] = w[l] || [];
638        w[l].push({
639            'gtm.start': new Date().getTime(), event: 'gtm.js'
640        });
641        var f = d.getElementsByTagName(s)[0], j = d.createElement(s), dl = l != 'dataLayer' ? '&l=' + l : '';
642        j.async = true;
643        j.src = 'https://www.googletagmanager.com/gtm.js?id=' + i + dl;
644        f.parentNode.insertBefore(j, f);
645    })(window, document, 'script', 'dataLayer', '
645GTM-K46KFRH
vendor: 4 bytes, line 645
645');
vendor: 2 bytes, line 646
646}

Line numbers count LF bytes from the start of the resource, as the search results do. Vendor segments are library code the classifier recognised; they are stored but not indexed. Bytes are shown as Latin1 characters, one per byte.