Hero Wars CSV Export

A script for intercepting data for the Hero Wars game and converting it to csv.

Aby zainstalować ten skrypt, wymagana jest instalacje jednego z następujących rozszerzeń: Tampermonkey, Greasemonkey lub Violentmonkey.

Aby zainstalować ten skrypt, wymagana jest instalacje jednego z następujących rozszerzeń: Tampermonkey, Violentmonkey.

Aby zainstalować ten skrypt, wymagana jest instalacje jednego z następujących rozszerzeń: Tampermonkey, Violentmonkey.

Aby zainstalować ten skrypt, wymagana będzie instalacja rozszerzenia Tampermonkey lub Userscripts.

You will need to install an extension such as Tampermonkey to install this script.

Aby zainstalować ten skrypt, musisz zainstalować rozszerzenie menedżera skryptów użytkownika.

(Mam już menedżera skryptów użytkownika, pozwól mi to zainstalować!)

You will need to install an extension such as Stylus to install this style.

You will need to install an extension such as Stylus to install this style.

You will need to install an extension such as Stylus to install this style.

Będziesz musiał zainstalować rozszerzenie menedżera stylów użytkownika, aby zainstalować ten styl.

Będziesz musiał zainstalować rozszerzenie menedżera stylów użytkownika, aby zainstalować ten styl.

Musisz zainstalować rozszerzenie menedżera stylów użytkownika, aby zainstalować ten styl.

(Mam już menedżera stylów użytkownika, pozwól mi to zainstalować!)

// ==UserScript==
// @name           Hero Wars CSV Export
// @namespace      http://tampermonkey.net/
// @version        0.0.12
// @description    A script for intercepting data for the Hero Wars game and converting it to csv.
// @description:zh 一个脚本,用于截取英雄战争游戏的数据并将其转换为csv。
// @description:ja Hero Warsゲームのデータを傍受してcsvに変換するためのスクリプト。
// @description:ru Скрипт для перехвата данных для игры Hero Wars и преобразования их в csv.
// @description:es Un script para interceptar datos para el juego Hero Wars y convertirlos a csv.
// @description:pt Um script para interceptar dados para o jogo Hero Wars e convertê-los em csv.
// @author         EnterBrain42
// @match          https://www.hero-wars.com/*
// @require        https://openuserjs.org/src/libs/sizzle/GM_config.js
// @icon           https://www.google.com/s2/favicons?sz=64&domain=www.hero-wars.com
// @grant          GM.setValue
// @grant          GM.getValue
// @grant          GM_registerMenuCommand
// @grant          GM_setClipboard
// @license        MIT
// ==/UserScript==

(function() {
    'use strict';

    (function(open) {
        function jsonResponseHandler(jsonResponse) {
            //console.log(typeof jsonResponse);
            //var jsonResponse = JSON.parse(jsonResponseText);
            if (Array.isArray(jsonResponse.results)){
                jsonResponse.results.forEach(function(item, i, arr) {
                    //console.log( item );
                    if ("result" in item && typeof item.result === 'object' && item.result !== null){
                        if ("response" in item.result && typeof item.result.response === 'object' && item.result.response !== null){
                            //console.log( item.result.response );
                            //guild teams
                            if ("teams" in item.result.response && typeof item.result.response.teams === 'object' && item.result.response.teams !== null){
                                console.log("Guild Teams");
                                var clanTeams = JSON.stringify(item.result.response.teams);
                                clanTeams = clanTeams.replace(/^\{/g,'[');
                                clanTeams = clanTeams.replace(/\}$/g,']');
                                clanTeams = clanTeams.replace(/,"userId":\d+/g,'');
                                clanTeams = clanTeams.replace(/"(\d+)":\{"clanDefence_titans"(.*?)\},"clanDefence_heroes"/g,'{"userId":$1,"clanDefence_titans"$2,"totems":[],"clanDefence_heroes"');
                                clanTeams = clanTeams.replace(/\},"clanDefence_heroes"/g,',"totems":[],"clanDefence_heroes"');
                                clanTeams = clanTeams.replace(/("element":"(light)","elementSpiritLevel":\d+,"elementSpiritStar":[^0])(,.*?\}\},"totems":\[)/g,'$1$3"$2",');
                                clanTeams = clanTeams.replace(/("element":"(dark)","elementSpiritLevel":\d+,"elementSpiritStar":[^0])(,.*?\}\},"totems":\[)/g,'$1$3"$2",');
                                clanTeams = clanTeams.replace(/("element":"(earth)","elementSpiritLevel":\d+,"elementSpiritStar":[^0])(,.*?\}\},"totems":\[)/g,'$1$3"$2",');
                                clanTeams = clanTeams.replace(/("element":"(fire)","elementSpiritLevel":\d+,"elementSpiritStar":[^0])(,.*?\}\},"totems":\[)/g,'$1$3"$2",');
                                clanTeams = clanTeams.replace(/("element":"(water)","elementSpiritLevel":\d+,"elementSpiritStar":[^0])(,.*?\}\},"totems":\[)/g,'$1$3"$2",');
                                clanTeams = clanTeams.replace(/,\],"clanDefence_heroes"/g,'],"clanDefence_heroes"');
                                clanTeams = clanTeams.replace(/"\d+":\{"id":\d+,"level":\d+,"star":\d+,"element":"\w+","elementSpiritLevel":\d+,"elementSpiritStar":\d+,"power":(\d+)\}/g,'$1');
                                clanTeams = clanTeams.replace(/\{"units":\{(.*?)\}/g,'[$1]');
                                clanTeams = clanTeams.replace(/"banner":null\}/g,'"pet":0,"banner":[0,0,0]');
                                clanTeams = clanTeams.replace(/"banner":\{"id":\d+,"slots":[\[\{](.*?)[\]\}]\}\}/g,function (match, p1, offset, string) {
                                    var resultString = p1.replace(/"\d+":/g,'');
                                    if (resultString == '') { resultString = "0"; }
                                    var resultStringArr = resultString.split(',');
                                    while (resultStringArr.length < 3) { // выводит 0, затем 1, затем 2
                                        resultStringArr.push(0);
                                    }
                                    resultString = resultStringArr.join();
                                    return '"pet":0,"banner":['+resultString+']';
                                });
                                clanTeams = clanTeams.replace(/"\d+":\{"id":\d+,"level":\d+,"color":\d+,"star":\d+,"power":(\d+)[\]\}]/g,'$1');
                                clanTeams = clanTeams.replace(/,"\d+":\{"id":\d+,"level":\d+,"color":\d+,"star":\d+,"type":"pet","power":(\d+)\}\},"pet":0/g,'],"pet":$1');
                                clanTeams = clanTeams.replace(/\},"pet":0/g,'],"pet":0');
                                GM.setValue("clanTeams", clanTeams);
                                //console.log(clanTeams);
                            }
                            //My Heroes
                            if (item.ident == 'heroGetAll'){
                                console.log("My Heroes");
                                var heroGetAll = JSON.stringify(item.result.response);
                                heroGetAll = heroGetAll.replace(/^\{/g,'[');
                                heroGetAll = heroGetAll.replace(/\}$/g,']');
                                heroGetAll = heroGetAll.replace(/"\d+":\{"id"/g,'{"id"');
                                heroGetAll = heroGetAll.replace(/"slots":[\{\[].*?[\}\]],/g,'');
                                heroGetAll = heroGetAll.replace(/"skills":\{(.*?)\}/g,function (match, p1, offset, string) {
                                    var resultString = p1.replace(/"\d+":(\d+)/g,'$1');
                                    return '"skills":"'+resultString+'"';
                                });
                                heroGetAll = heroGetAll.replace(/"skins":\{(.*?)\}/g,function (match, p1, offset, string) {
                                    var resultString = p1.replace(/"(\d+)":(\d+)/g,'$1-$2');
                                    return '"skins":"'+resultString+'"';
                                });
                                heroGetAll = heroGetAll.replace(/"skins":\[\]/g,'"skins":""');
                                heroGetAll = heroGetAll.replace(/\{"level":(\d+),"star":(\d+)\}/g,'"$2-$1"');
                                heroGetAll = heroGetAll.replace(/"ascensions":\{"\d+":(.*?)\}/g,'"ascensions":$1');
                                heroGetAll = heroGetAll.replace(/"titanCoinsSpent":.*?,/g,'');
                                heroGetAll = heroGetAll.replace(/"currentSkin":\d+,/g,'');
                                heroGetAll = heroGetAll.replace(/"scale":\d+,/g,'');
                                heroGetAll = heroGetAll.replace(/"petId":\d+,/g,'');
                                GM.setValue("heroGetAll", heroGetAll);
                                //console.log(heroGetAll);
                            }
                            //clanGetInfo
                            if (item.ident == 'clanGetInfo'){
                                console.log("Guild Members clanGetInfo");
                                var guild_members = {};
                                for (const [key, value] of Object.entries(item.result.response.clan.members)) {
                                    guild_members[key] = {'id':value.id,'name':value.name,'level':value.level,'lastLoginTime':value.lastLoginTime};
                                }
                                //console.log(JSON.stringify(guild_members));
                                GM.setValue("guild_members", JSON.stringify(guild_members));
                                var clanMembers = JSON.stringify(item.result.response.clan.members);
                                clanMembers = clanMembers.replace(/^\{/g,'[');
                                clanMembers = clanMembers.replace(/\}$/g,']');
                                clanMembers = clanMembers.replace(/"\d+":\{"id"/g,'{"id"');
                                GM.setValue("clanMembers", clanMembers);
                                //console.log(clanMembers);
                            }
                            //guild war enemySlots
                            if ("enemySlots" in item.result.response && typeof item.result.response.enemySlots === 'object' && item.result.response.enemySlots !== null){
                                console.log("Guild War Enemy Slots");
                                var enemySlots = JSON.stringify(item.result.response.enemySlots);
                                enemySlots = enemySlots.replace(/^\{/g,'[');
                                enemySlots = enemySlots.replace(/\}$/g,']');
                                enemySlots = enemySlots.replace(/"(\d+)":\{"team":\[\],"attackerId":.*?\}/g,'{"idSlot":"$1","typeSlot":"null","team":[0,0,0,0,0,0],"id":"null","name":"null"}');
                                enemySlots = enemySlots.replace(/\{*?"\d+":\{"state":.*?"power":(\d+),"type":"(.*?)".*?\}+/g,'{"power":$1,"type":"$2"}');
                                enemySlots = enemySlots.replace(/"(\d+)":\{"team":\[\{"power":(\d+),"type":"(.*?)"\}(.*?\]),"attackerId":.*?"id":"(\d+)","name":"(.*?)".*?pointsFarmed":(\d+),.*?\}/g,'{"idSlot":"$1","typeSlot":"$3","team":[{"power":$2,"type":"$3"}$4,"id":"$5","name":"$6","pointsFarmed":"$7"}');
                                enemySlots = enemySlots.replace(/\{"power":(.*?),"type":".*?"\}/g,'$1');
                                GM.setValue("enemySlots", enemySlots);
                                //console.log(enemySlots);
                            }
                            //guild war ourSlots
                            if ("ourSlots" in item.result.response && typeof item.result.response.ourSlots === 'object' && item.result.response.ourSlots !== null){
                                console.log("Guild War Enemy Slots");
                                var ourSlots = JSON.stringify(item.result.response.ourSlots);
                                ourSlots = ourSlots.replace(/^\{/g,'[');
                                ourSlots = ourSlots.replace(/\}$/g,']');
                                ourSlots = ourSlots.replace(/"(\d+)":\{"team":\[\],"attackerId":.*?\}/g,'{"idSlot":"$1","typeSlot":"null","team":[0,0,0,0,0,0],"id":"null","name":"null"}');
                                ourSlots = ourSlots.replace(/\{*?"\d+":\{"state":.*?"power":(\d+),"type":"(.*?)".*?\}+/g,'{"power":$1,"type":"$2"}');
                                ourSlots = ourSlots.replace(/"(\d+)":\{"team":\[\{"power":(\d+),"type":"(.*?)"\}(.*?\]),"attackerId":.*?"id":"(\d+)","name":"(.*?)".*?pointsFarmed":(\d+),.*?\}/g,'{"idSlot":"$1","typeSlot":"$3","team":[{"power":$2,"type":"$3"}$4,"id":"$5","name":"$6","pointsFarmed":"$7"}');
                                ourSlots = ourSlots.replace(/\{"power":(.*?),"type":".*?"\}/g,'$1');
                                GM.setValue("ourSlots", ourSlots);
                                //console.log(ourSlots);
                            }
                            //guild members
                            //if ("clan" in item.result.response && typeof item.result.response.clan === 'object' && item.result.response.clan !== null && "members" in item.result.response.clan){
                            //    console.log("Guild Members");
                            //    var clanMembers = JSON.stringify(item.result.response.clan.members);
                            //    clanMembers = clanMembers.replace(/^\{/g,'[');
                            //    clanMembers = clanMembers.replace(/\}$/g,']');
                            //    clanMembers = clanMembers.replace(/"\d+":\{"id"/g,'{"id"');
                            //    GM.setValue("clanMembers", clanMembers);
                            //    //console.log(clanMembers);
                            //}
                            //guild stat
                            if ("stat" in item.result.response && Array.isArray(item.result.response.stat)){
                                console.log("Guild Stats");
                                var clanStats = JSON.stringify(item.result.response.stat);
                                GM.setValue("clanStats", clanStats);
                                //console.log(clanStats);
                            }
                            //console.log(item.result);
                        }
                    }
                });
                //console.log(this.responseText);
            }
        }
        XMLHttpRequest.prototype.open = function() {
            this.addEventListener("readystatechange", function() {
                if (this.readyState == 4 && (this.responseType == 'json' || this.responseType == '') && this.status == 200 && this.responseURL == "https://heroes-wb.nextersglobal.com/api/") {
                    let jsonResponse = this.response;
                    if (typeof jsonResponse === 'string'){
                        jsonResponse = JSON.parse(jsonResponse);
                    }
                    setTimeout(jsonResponseHandler, 1, jsonResponse);
                }
            }, false);
            open.apply(this, arguments);
        };
    })(XMLHttpRequest.prototype.open);
    function jsonToCSV(data){
        const replacer = (key, value) => value === null ? '' : value; // specify how you want to handle null values here
        const header = Object.keys(data[0]);
        function replacerArrayCSV(match, p1, offset, string) {
            var resultArrayCSV = p1.replace(/"/g,'');
            //console.log(resultArrayCSV);
            return '"'+resultArrayCSV+'"';
        }
        var csv = [
            header.join(','), // header row first
            ...data.map(row => header.map(fieldName => JSON.stringify(row[fieldName], replacer)).join(','))
        ].join('\r\n');

        csv = csv.replace(/\[(.*?)\]/g,replacerArrayCSV);
        csv = csv.replace(/\{(.*?)\}/g,replacerArrayCSV);
        return csv;
    };
    GM_registerMenuCommand('Copy Last Guild-Power-GW-CSV', async () => {
        let count_after = await GM.getValue('clanTeams');
        GM_setClipboard(jsonToCSV(JSON.parse(count_after)));
    });
    GM_registerMenuCommand('Copy Last Guild-Stats-CSV', async () => {
        let guild_members = JSON.parse(await GM.getValue('guild_members'));
        let clanStats = JSON.parse(await GM.getValue('clanStats'));
        let newGuildMembers = [];
        for (const [key, value] of Object.entries(clanStats)) {
            newGuildMembers.push ({
                'id':guild_members[value.id].id,
                'name':guild_members[value.id].name,
                'level':guild_members[value.id].level,
                'lastLoginTime':guild_members[value.id].lastLoginTime,
                'activity':value.activity,
                'dungeonActivity':value.dungeonActivity,
                'adventureStat':value.adventureStat,
                'clanWarStat':value.clanWarStat,
                'clanGifts':value.clanGifts,
                'prestigeStat':value.prestigeStat
            });
        }
        //console.log(JSON.stringify(newGuildMembers));
        //console.log(clanMembers);
        GM_setClipboard(jsonToCSV(newGuildMembers));
    });
    //GM_registerMenuCommand('Copy Last clanStatsGifts', async () => {
    //    let count_after = await GM.getValue('clanStats');
    //    GM_setClipboard(jsonToCSV(JSON.parse(count_after)));
    //});
    GM_registerMenuCommand('Copy Last GW-Enemy-CSV', async () => {
        let count_after = await GM.getValue('enemySlots');
        GM_setClipboard(jsonToCSV(JSON.parse(count_after)));
    });
    GM_registerMenuCommand('Copy Last GW-Guild-CSV', async () => {
        let count_after = await GM.getValue('ourSlots');
        GM_setClipboard(jsonToCSV(JSON.parse(count_after)));
    });
    GM_registerMenuCommand('Copy Last All-You-Heroes-CSV', async () => {
        let count_after = await GM.getValue('heroGetAll');
        GM_setClipboard(jsonToCSV(JSON.parse(count_after)));
    });
})();