// ==UserScript== // @name Sync:Extension-For-app.huawei.com-Actual // @namespace https://github.com/le91 // @version 1.14--12.08.2024 // @description Перехватываем XMLHttpRequest и обновляем глобальные переменные для кнопки "Синхронизация" // @author LukasEndigo // @match https://app.huawei.com/iscp/esupplier/portal* // @icon https://www.google.com/s2/favicons?sz=64&domain=app.huawei.com // @run-at document-end // ==/UserScript== 'use strict'; // Глобальные переменные let Global_poHeaderId, Global_instanceId, Global_poReleaseId; // Перехват XMLHttpRequest (function() { console.log('*************** ЛОГ function'); // Сохранение оригинальных методов XMLHttpRequest const originalOpen = XMLHttpRequest.prototype.open; const originalSend = XMLHttpRequest.prototype.send; console.log('*************** ЛОГ originalOpen и originalSend'); // Переопределение метода open XMLHttpRequest.prototype.open = function(method, url, async, user, password) { this._url = url; // Сохраняем URL запроса return originalOpen.apply(this, arguments); }; console.log('*************** ЛОГ originalOpen и originalSend'); // Переопределение метода send XMLHttpRequest.prototype.send = function(body) { console.log('*************** ЛОГ XMLHttpRequest.prototype.send = function(body)'); // Проверка URL с использованием includes для поиска части пути if (this._url && this._url.includes('/iscp/esupplier/po/services/poList/findPoLineList/20/1')) { console.log('*************** ЛОГ','XMLHttpRequest.prototype.send = function(body)'); try { console.log('*************** ЛОГ','JSON.parse(body)'); const requestPayload = JSON.parse(body); // Пытаемся распарсить Request Payload // Обновление глобальных переменных из requestPayload if (requestPayload.poHeaderId) Global_poHeaderId = requestPayload.poHeaderId; if (requestPayload.instanceId) Global_instanceId = requestPayload.instanceId; if (requestPayload.poReleaseId) Global_poReleaseId = requestPayload.poReleaseId; console.log('*************** ЛОГ','if Global_poHeaderId'); console.log('Перехваченный запрос на URL:', this._url); console.log('Request Payload:', requestPayload); // Здесь requestPayload - это содержимое запроса console.log('Request Payload, Global_poHeaderId:', Global_poHeaderId); // Здесь requestPayload - это содержимое запроса console.log('Request Payload, Global_instanceId:', Global_instanceId); // Здесь requestPayload - это содержимое запроса console.log('Request Payload, Global_poReleaseId:', Global_poReleaseId); // Здесь requestPayload - это содержимое запроса } catch (e) { console.error('Ошибка при парсинге Request Payload:', e); console.log('*************** ЛОГ','Request Payload:'); } } if (1 == 1) { console.log('*************** ЛОГ','1 == 1 '); try { console.log('*************** ЛОГ',' TRY 1 '); const requestPayload = JSON.parse(body); // Пытаемся распарсить Request Payload // Обновление глобальных переменных из requestPayload if (requestPayload.poHeaderId) Global_poHeaderId = requestPayload.poHeaderId; if (requestPayload.instanceId) Global_instanceId = requestPayload.instanceId; if (requestPayload.poReleaseId) Global_poReleaseId = requestPayload.poReleaseId; console.log('*************** ЛОГ','Global_poHeaderId 2222 '); console.log('Перехваченный запрос на URL:', this._url); console.log('Request Payload:', requestPayload); // Здесь requestPayload - это содержимое запроса console.log('Request Payload, Global_poHeaderId:', Global_poHeaderId); // Здесь requestPayload - это содержимое запроса console.log('Request Payload, Global_instanceId:', Global_instanceId); // Здесь requestPayload - это содержимое запроса console.log('Request Payload, Global_poReleaseId:', Global_poReleaseId); // Здесь requestPayload - это содержимое запроса } catch (e) { console.error('Ошибка при парсинге Request Payload:', e); } } console.log('*************** ЛОГ','END END END'); return originalSend.apply(this, arguments); }; })(); console.log('*************** ЛОГ','FREEE 82'); // Наблюдатель для отслеживания изменений в DOM const observer = new MutationObserver(mutations => { mutations.forEach(mutation => { if (mutation.addedNodes) { mutation.addedNodes.forEach(node => { if (node.nodeType === 1) { // элемент checkAndAddSyncButton(node); } }); } }); }); // Запуск наблюдателя observer.observe(document.body, { childList: true, subtree: true }); // Проверка и добавление кнопки "Синхронизация" function checkAndAddSyncButton(node) { const targetClass = "webix_view webix_hwFlextableV2_toolbar webix_layout_line"; if (node.classList && node.classList.contains(targetClass)) { addSyncButton(node); } node.querySelectorAll(`.${targetClass.split(" ").join(".")}`).forEach(addSyncButton); } function addSyncButton(container) { console.log('ЗАПУСК Перехвачено 84 paramsNew:'); const exportTemplateButton = Array.from(container.querySelectorAll('button.webixtype_default')) .find(button => button.textContent.trim() === 'Export Acceptance Template'); if (exportTemplateButton) { // Создаем кнопку, если она еще не добавлена if (!container.querySelector('.le-skynet-sync-button')) { const syncButton = document.createElement('div'); syncButton.className = 'webix_view webix_control webix_el_button hwButtonV2 webix_hwFlextableV2_customBtn le-skynet-sync-button'; syncButton.style.cssText = 'display: inline-block; vertical-align: top; border-width: 0px; margin-top: 0px; margin-left: -1px; width: 188px; height: 34px;'; syncButton.innerHTML = '
'; syncButton.querySelector('button').addEventListener('click', () => executeSyncRequest(syncButton)); exportTemplateButton.parentElement.parentElement.insertAdjacentElement('afterend', syncButton); console.log('Добавлена кнопка "Синхронизация", Global_poHeaderId:', Global_poHeaderId); } } } // Function to execute sync request on button click function executeSyncRequest(buttonContainer) { const button = buttonContainer.querySelector('button'); button.disabled = true; button.textContent = 'В процессе синхронизации'; button.style.cssText = 'border: 1px solid #ffffff; background-color: rgb(170 230 255); cursor: wait;'; console.log('ЗАПУСК Перехвачено 112 paramsNew:'); fetch("https://app.huawei.com/iscp/esupplier/po/services/poList/findPoLineList/20/1", { headers: { "Accept": "*/*", "Accept-Language": "ru,en;q=0.9", "Content-Type": "application/json" }, referrer: "https://app.huawei.com/iscp/esupplier/portal/", referrerPolicy: "strict-origin-when-cross-origin", body: JSON.stringify({ instanceId: Global_instanceId, poHeaderId: Global_poHeaderId, poReleaseId: Global_poReleaseId, poSubType: "E", calculateOrderAmount: true }), method: "POST", mode: "cors", credentials: "include" }) .then(response => response.json()) .then(data => { // console.log('Синхронизация данные:', JSON.stringify(data, null, 2)); // Форматирование JSON для удобного просмотра console.log('ЗАПУСК Перехвачено 135 paramsNew:'); return fetch("https://huawei-po-5m2hn5f7q75izgid.lse.kz/api/app_huawei_po", { headers: { "Content-Type": "application/json" }, method: "POST", body: JSON.stringify(data) }) .then(response => response.json()) .then(result => { console.log('Отправка запросом poHeaderId как:', Global_poHeaderId, '| ответ:', JSON.stringify(result)); // console.log('Ответ от API:', JSON.stringify(result, null, 2)); if (result.detail !== "OK Status") { throw new Error('Ошибка от API'); } }); }) .catch(error => { button.style.backgroundColor = 'rgb(255 200 200)'; console.error('Error:', error); button.textContent = 'ОШИБКА'; button.disabled = true; }) .finally(() => { button.disabled = false; if (button.textContent !== 'ОШИБКА') { button.textContent = 'Успешно'; button.style.backgroundColor = 'rgb(200 245 200)'; button.style.cursor = ''; button.style.border = '1px solid #d9d9d9'; button.disabled = false; } }); console.log('ЗАПУСК Перехвачено 168 paramsNew:'); } console.log('=======================================Успешно внедрен==============================================');