<!DOCTYPE html>
{% load staticfiles %}
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Deploy task trace</title>
    <script type="text/javascript" src="//yastatic.net/react/15.0.1/react.js"></script>
    <script type="text/javascript" src="//yastatic.net/react/15.0.1/react-dom.js"></script>
    <script src="https://yandex.st/jquery/2.0.3/jquery.min.js"></script>

</head>
<style>
    td {
        vertical-align: top;
    }
</style>
<script type="text/javascript">

    let current_task_info = {};
    let current_children_info = {};
    let current_task_id = '';
    let current_watcher_hash = '';
    let is_watching_task = false;

    function get_task_updates() {
        return {
            answer_id: 'task_trace_answer',
            hr_legend: 'task info',
            watcher_hash: current_watcher_hash,
            get_url: get_trace_url,
            on_load: update_task_info,
            should_stop: function() { return (this.watcher_hash !== current_watcher_hash)
                || (current_task_info.hasOwnProperty('is_finished') && current_task_info['is_finished']); }
        };
    }

    function gen_child_updates(id) {
        return {
            answer_id: 'task_trace_answer',
            hr_legend: 'subtask info',
            url: '{% url "deploy_trace" %}?task_id=' + encodeURIComponent(id),
            watcher_hash: current_watcher_hash,
            on_load: function(res) { update_subtask_info(res, id); },
            should_stop: function() { return (this.watcher_hash !== current_watcher_hash)
                || (current_task_id === '')
                || (current_children_info.hasOwnProperty(id) && current_children_info[id]['is_finished']); }
        };
    }

    const status_colors = {
        0: 'grey',
        1: 'blue',
        2: 'red',
        3: 'orange',
        4: 'green'
    };

    function get_trace_url() {
        return '{% url "deploy_trace" %}?task_id=' + encodeURIComponent(current_task_id);
    }

    class TInfoBlock extends React.Component {
        render() {
            let task_info = {};
            if (this.props.is_root_task) {
                task_info = current_task_info;
                if (!task_info.hasOwnProperty('is_finished')) {
                    return React.createElement('div', null, 'not loaded yet: ' + this.props.task_id);
                }
            } else {
                task_info = current_children_info[this.props.task_id];
                if (!current_children_info.hasOwnProperty(this.props.task_id)
                    || !task_info.hasOwnProperty('is_finished')) {
                    return React.createElement('div', null, 'not loaded yet: ' + this.props.task_id);
                }
            }
            let els = [];
            try {
            let head_text = 'is_finished=' + task_info['is_finished'] +
                '; result=' + task_info['result_code'];
            let task_head_el = React.createElement('div', {key: 'ti-head'}, head_text);
            els.push(task_head_el);
            let stat_text = 'success_cnt=' + task_info['script']['success'] +
                '; failed_cnt=' + task_info['script']['failed'] +
                ';running=' + task_info['script']['running'] +
                ';total=' + task_info['script']['size'];
            let task_stat_el = React.createElement('div', {key: 'ti-stat'}, stat_text);
            els.push(task_stat_el);
            let verts = task_info['script']['graph']['vertices'];
            let action_els = [];
            for (let i=0; i<verts.length; ++i) {
                let text = verts[i]['task']['action']['result']['status'];
                let child_task_id = verts[i]['task']['action']['id_task'];
                let status_num = verts[i]['status'];
                let should_draw_child = (!!child_task_id) ? /*!verts[i]['task']['is_remote'] &&*/ child_task_id.startsWith('type=') : false;
               // console.log(!verts[i]['task']['is_remote']);
                if (should_draw_child) {
                    text += ' ' + child_task_id;
                } else {
                    if (status_num !== 0) {
                        try {
                            if (verts[i]['task']['action']['result'].hasOwnProperty('hr_info'))
                                text += ': ' + verts[i]['task']['action']['result']['hr_info'] + ' ';
                        } catch(err) {}
                        let ts = '';
                        try {
                            let tfin = verts[i]['task']['action']['result']['time_finish'];
                            if (parseInt(tfin) === tfin) {
                                ts = tfin - verts[i]['task']['action']['result']['time_start'];
                            } else {
                                ts = (new Date().getTime()) - verts[i]['task']['action']['result']['time_start'];
                            }
                        } catch(err) { ts = '-'; }
                        text += ' (' + ts + 'ms)';
                    }
                }
                let color = status_colors.hasOwnProperty(status_num) ? status_colors[status_num] : 'pink';
                let task_info_el = text;
                if (should_draw_child) {
                    if (!current_children_info.hasOwnProperty(child_task_id)) {
                        current_children_info[child_task_id] = {};
                        let upds = gen_child_updates(child_task_id);
                        do_data_load(upds);
                    }
                    let link_el = React.createElement('a', {
                        key: 'chlink-' + child_task_id,
                        target: '_blank',
                        href: '{% url "deploy_trace" %}?task_id=' + encodeURIComponent(child_task_id)
                    }, 'open');
                    task_info_el = [
                        React.createElement('div', {key: 'ch-name-' + child_task_id},
                            [React.createElement('span', {key: 'ch-namespan-' + child_task_id}, text),
                            link_el])
                    ];
                    try {
                        task_info_el.push(React.createElement(TInfoBlock,
                            {
                                is_root_task: false,
                                key: 'chinfo-'+child_task_id,
                                task_id: child_task_id
                            }, null));
                    } catch(err) {
                        task_info_el.push(React.createElement('div', null, 'subtask error'));
                    }
                }

                let task_gr_el = React.createElement('td',
                    {key: 'ti-script-td-' + i},
                    task_info_el);
                action_els.push(React.createElement('tr',
                    {key: 'ti-script-' + i, style: {color: color}},
                    [
                        React.createElement('td', {key: 'ti-name-' + i}, verts[i]['name']),
                        task_gr_el
                    ]));
            }
            let gr_table_el = React.createElement('table', {key: 'ti-tb'},
                React.createElement('tbody', {}, action_els));
            els.push(gr_table_el);
            } catch(err) {
                console.log(err);
                els.push(React.createElement('div', {key: 'err'}, 'ERROR on parse'));
            }
            return React.createElement('div', null, els);
        }
    }

    function redraw_task() {
        let el = React.createElement(TInfoBlock, {is_root_task: true}, null);
        ReactDOM.render(el, document.getElementById('deploy_task_info'));
    }

    function update_task_info(res) {
        current_task_info = res['ans'];
        redraw_task();
    }

    function update_subtask_info(res, id) {
        current_children_info[id] = res['ans'];
        if (current_task_info['is_finished']) {
            redraw_task();
        }
    }

    function stop_task_watch() {
        current_task_id = '';
    }

    function start_task_watch(task_id) {
        current_task_id = task_id;
        let date = new Date();
        current_watcher_hash = date.getMilliseconds();
        let same_id = (task_id === current_task_id);
        if (is_watching_task && same_id) {
            document.getElementById('deploy_task_info').innerHTML = '';
            is_watching_task = false;
            current_task_info = {};
        } else {
            is_watching_task = true;
            do_data_load(get_task_updates());
        }
    }

    $(document).ready(function() {
        window.addEventListener('taskattach', function(evt){ start_task_watch(evt.detail.task_id);});
    });
</script>
<body>
<div id="deploy_task_info"></div>
<div id="task_trace_answer"></div>
</body>
</html>
