<link rel="stylesheet" href="jquery-ui.css">
<script src="jquery.js"></script>
<script src="jquery-ui.js"></script>
<style type="text/css">
    body{
    }
    .cut_head {
        background: url(arrow-square.gif) no-repeat right -51px;
    cursor: pointer;
        padding-bottom: 5px;
        padding-right: 35px;
        margin-bottom: 0;
        margin-top: 0;
        text-decoration: underline;
    }
    .cut_head:hover  {
        background-color: rgba(128, 128, 128, .2);
    }
    .cut_head.active {
        background-position: right 5px;
        background-color: rgba(128, 128, 128, .2);
    border-left: solid 1px #949494;
    }
    .cut_head.active:hover  {
        background-color: rgba(128, 128, 128, .4);
    }
    .cut_body {
        background-color: rgba(128, 128, 128, .2);
        padding-left: 20px;
        padding-top: 5px;
        padding-bottom: 5px;
        padding-right: 5px;
    border-left: solid 1px #949494;
        margin-top: 5px;
        font-size: smaller;
    }
    .attention {
        color:red;
        font-weight: bold;
    }
    .monospace {
        background-color: rgba(255, 255, 128, .2);
        white-space: pre;
    }
    .error_ERROR {
        color: red;
        font-weight: bold;
        font-size: larger;
    }
    .error_WARNING {
        color: orange;
        font-weight: bold;
        font-size: larger;
    }
    .error_INFO {
        font-weight: bold;
        font-size: larger;
    }
    .status {
        font-weight: bold;
        font-size: large;
    }
    .question_id {
        color: red;
        font-size: x-small;
    }
</style>
<script type="text/javascript">
    var pages;
    
    function smartSplit(s, separator) {
        return s === "" ? new Array() : s.split(separator);
    }
    
    function getQuestionHtmlText(question, cl, formId, onChange) {
        var params = "value" in question ? " value='" + question.value + "'" : "";
        if (cl !== "")
            params += "class='" + cl + "'";
        var result = "<input size='50' placeholder='' type='text' name='" + question.common.id + "' form='" + formId + "' onInput=\"" + onChange + "\"" + params + "'></input>";
        return result;
    }

    function getQuestionHtmlStrings(question, formId, onChange) {
        var result = "<textarea placeholder='' cols='50' rows='10' type='number' name='" + question.common.id + "' form='" + formId + "' onInput=\"" + onChange + "\">";
        if ("value" in question)
            result += question.value;
        result += "</textarea>";
        return result;
    }

    function getQuestionHtmlNumber(question, formId, onChange, step) {
        var params = "value" in question ? " value='" + question.value + "'" : "";
        params += "max_value" in question ? " max='" + question.max_value + "'" : "";
        params += "min_value" in question ? " min='" + question.min_value + "'" : "";
        params += " step='" + step + "'";
        var result = "<input placeholder='' size='50' type='number' name='" + question.common.id + "' form='" + formId + "' onInput=\"" + onChange + "\"" + params + "></input>";
        return result;
    }

    function removeEmptyTableRows(tableName, rowIsEmpty) {
        var table = document.getElementById(tableName);
        var lastIndex = table.rows.length - 2;
        for (; lastIndex > 0; --lastIndex)
            if (rowIsEmpty(table.rows[lastIndex]))
                table.deleteRow(lastIndex);
    }
    function addTableRowsIfNeed(tableName, rowIsEmpty, getRowHtml) {
        var table = document.getElementById(tableName);
        var index = table.rows.length - 1;
        if (index <= 0 || !rowIsEmpty(table.rows[index])) {
            var row = table.insertRow(-1);
            var inner = getRowHtml();
            row.id = inner[0];
            for (var i = 1; i < inner.length; ++i)
                row.appendChild(inner[i]);
        }
    }

    function onChangeTableRow(tableName, rowIsEmpty, getRowHtml) {
        removeEmptyTableRows(tableName, rowIsEmpty);
        addTableRowsIfNeed(tableName, rowIsEmpty, getRowHtml);
        hideElements();
    }
    
    var valId = 0;

    function bin2hex(s) {
        var i, f = s.length, a = [];
        for (i = 0; i < f; i++) {
            c = s.charCodeAt(i).toString(16);
            while (c.length < 4)
                c = '0' + c;
            a[i] = c;
        }
        return a.join('');
    }

    function hex2bin(hex) {
        var result = "";
        var bytes = [];
        for (var i = 0; i < hex.length - 3; i += 4) {
            if (bytes.length === 1024) {
                result += String.fromCharCode.apply(String, bytes);
                bytes = [];
            }
            bytes.push(parseInt(hex.substr(i, 4), 16));
        }
        if (bytes.length > 0) {
            result += String.fromCharCode.apply(String, bytes);
        }
        return result;
    }

    function encodeObject(q) {
        return bin2hex(JSON.stringify(q));
    }

    function decodeObject(q) {
        var j = hex2bin(q);
        return JSON.parse(j);
    }
    
    function getRowHtml(q, value, tableName) {
        var question = decodeObject(q);
        var id = valId++;
        var result = new Array();
        result.push(id);
        var form = document.createElement("FORM");
        form.id = question.common.id + "_" + id;
        for (var i = 0; i < question.list_item_parts.length; ++i) {
            var item = question.list_item_parts[i];
            if (item.common.id in value) {
                item = JSON.parse(JSON.stringify(item));
                item.value = value[item.common.id];
            }
            var rIsEmpty = "function(row){return rowIsEmpty('" + q + "', row);}";
            var getRHtml = "function(){return getRowHtml('" + q + "', new Object(),'" + tableName + "');}";
            var onChange = "onChangeTableRow('" + tableName + "'," + rIsEmpty + "," + getRHtml + ")";
            var td = document.createElement("TD");
            td.innerHTML = getQuestionHtml(item, true, form.id, onChange);
            result.push(td);
        }
        result.push(form);
        return result;
    }

    function elementsToHtml(elements) {
        var result = "<tr id='" + elements[0] + "'>";
        for (var i = 1; i < elements.length; ++i) {
            var div = document.createElement("div");
            div.appendChild(elements[i].cloneNode(true));
            result += div.innerHTML;
        }
        result += "</tr>";
        return result;
    }
    
    function rowIsEmptyByValue(question, value) {
        if (value !== null) {
            var data = new Object();
            data[question.common.id] = value;
            for (var i = 0; i < question.list_item_parts.length; ++i) {
                var item = question.list_item_parts[i];
                if ("condition" in item.common && eval(item.common.condition) && value[item.common.id] != "")
                    return false;
            }
        }
        return true;
    }    

    function rowIsEmpty(q, row) {
        var question = decodeObject(q);
        var value = getListRowValue(question, row.id);
        return rowIsEmptyByValue(question, value);
    }
    function getQuestionHtmlList(question, formId, onChange) {
        if (!("list_item_parts" in question))
            return "";
        var tableName = "table_" + question.common.id + "_" + formId;
        var result = "<table  border='1' cellpandding='3' cellspacing='0' id='" + tableName + "'>";
        result += "<tr style='background-color:#DDDDDD' align='center'>";
        for (var i = 0; i < question.list_item_parts.length; ++i)
            result += "<td>" + question.list_item_parts[i].common.title + "</td>";
        result += "</tr>";
        
        if ("value" in question) {
            var values;
            if (typeof(question.value) === 'string')
                values = JSON.parse(question.value);
            else
                values = question.value;
            for (var i = 0; i < values.length; ++i)
                result += elementsToHtml(getRowHtml(encodeObject(question), values[i], tableName));
        }

        result += elementsToHtml(getRowHtml(encodeObject(question), new Object(), tableName));
        
        result += "</table>";
        return result;
    }

    function getQuestionHtmlCheckBox(question, formId, onChange) {
        var params = "";
        if ("value" in question) {
            if (JSON.parse(question.value))
                params = " checked='1'";
        }
        var result = "<input placeholder='' type='checkbox' name='" + question.common.id + "' form='" + formId + "' onClick=\"" + onChange + "\"" + params + "'></input>";
        return result;
    }

    function getQuestionHtmlEnum(question, formId, onChange) {
        var result = "";
        if ("answer_options" in question) {
            for (var ao = 0; ao < question.answer_options.length; ++ao) {
                var option = question.answer_options[ao];
                var checked = "value" in question && question.value === option.id ? " checked='1'" : "";
                if (ao > 0)
                    result += "<br>";
                result += "<input type='radio' width='100%' name='" + question.common.id + "' form='" + formId + "' onClick=\"" + onChange + "\" value='" + option.id + "'" + checked + ">";
                if ("description" in option)
                    result += "<span class='cut_head'>";
                result += option.title + " <span class='question_id'>(" + option.id + ")</span>";
                if ("description" in option)
                    result += "</span><div class='cut_body'>" + option.description + "</div>";
                result += "</input>";
            }
        }
        return result;
    }

    function getQuestionHtmlSelect(question, formId, onChange) {
        var result = "<select name='" + question.common.id + "' form='" + formId +"' onChange=\"" + onChange + "\">";
        if ("answer_options" in question) {
            for (var ao = 0; ao < question.answer_options.length; ++ao) {
                var option = question.answer_options[ao];
                var checked = "value" in question && question.value === option.id ? " selected='1'" : "";
                result += "<option width='100%' onClick='hideElements()' value='" + option.id + "'" + checked + ">";
                if ("description" in option)
                    result += "<span class='cut_head'>";
                result += option.title;
                if ("description" in option)
                    result += "</span><div class='cut_body'>" + option.description + "</div>";
                result += "</option>";
            }
        }
        result += "</select>";
        return result;
    }

    function getQuestionHtmlCheckList(question, formId, onChange) {
        var result = "";
        if ("answer_options" in question) {
            var value = new Array();
            if ("value" in question)
                value = JSON.parse(question.value);
            for (var ao = 0; ao < question.answer_options.length; ++ao) {
                var option = question.answer_options[ao];
                var checked =  (value.indexOf(option.id) > -1) ? " checked='1'" : "";
                if (ao > 0)
                    result += "<br>";
                result += "<input type='checkbox' name='" + question.common.id + "' form='" + formId + "' onClick=\"" + onChange + "\" value='" + option.id + "'" + checked + ">";
                if ("description" in option)
                    result += "<span class='cut_head'>";
                result += option.title + " <span class='question_id'>(" + option.id + ")</span>";
                if ("description" in option)
                    result += "</span><div class='cut_body'>" + option.description + "</div>";
                result += "</input>";
            }
        }
        return result;
    }
    
    function getQuestionHtml(question, flat, formId, onChange) {
        switch(question.type) {
            case "TEXT":
                return getQuestionHtmlText(question, "", formId, onChange);
            case "STRINGS":
                return getQuestionHtmlStrings(question, formId, onChange);
            case "LIST":
                return getQuestionHtmlList(question, formId, onChange);
            case "DATE":
                return getQuestionHtmlText(question, "datepicker", formId, onChange);
            case "INTEGER":
                return getQuestionHtmlNumber(question, formId, onChange, 1);
            case "FLOAT":
                return getQuestionHtmlNumber(question, formId, onChange, 0.00001);
            case "ENUM":
                if (flat)
                    return getQuestionHtmlSelect(question, formId, onChange);
                else
                    return getQuestionHtmlEnum(question, formId, onChange);
            case "CHECK_LIST":
                return getQuestionHtmlCheckList(question, formId, onChange);
            case "CHECK_BOX":
                return getQuestionHtmlCheckBox(question, formId, onChange);
        }
    }
    
    function getPageHtml(page) {
        var result = "";
        if ("description" in page.common)
            result += "<p><strong>" + page.common.description + "</strong></p>";
        result += "<table width='100%' cellspacing='4'><col width='50%'><col width='50%'>";
        if ("questions" in page) {
            for (var q = 0; q < page.questions.length; ++q) {
                var question = page.questions[q];
                result += "<tr id='line_" + question.common.id + "'>";
                result += "<td><p";
                if ("description" in question.common)
                    result += " class='cut_head'";
                result += ">" + question.common.title + " <span class='question_id'>(" + question.common.id + ")</span></p>";
                if ("description" in question.common)
                    result += "<div class='cut_body'>" + question.common.description + "</div>";
                result += "</td><td>";
                result += getQuestionHtml(question, false, "data", "hideElements()");
                result += "</td></tr>";
            }
        }
        result += "</table>";
        return result;
    }

    function getListRowValue(question, index) {
        var form = document.forms[question.common.id + "_" + index];
        if (form === null)
            return null;
        var val = new Object();
        for (var i = 0; i < question.list_item_parts.length; ++i) {
            var item = question.list_item_parts[i];
            val[item.common.id] = getElementValue(form, item);
        }
        return val;
    }
    
    function getElementValue(form, question) {
        var id = question.common.id;
        switch(question.type) {
            case "TEXT":
            case "INTEGER":
            case "FLOAT":
            case "DATE":
            case "STRINGS":
                if (id in form.elements)
                    return form.elements[id].value;
                return "";
            case "CHECK_BOX":
                if (id in form.elements)
                    return form.elements[id].checked;
                return false;
            case "ENUM":
                if (id in form.elements)
                    for (var v = 0; v < form.elements[id].length; ++v)
                        if (form.elements[id][v].checked || form.elements[id][v].selected)
                            return form.elements[id][v].value;
                return "";
            case "CHECK_LIST":
                var result = new Array();
                if (id in form.elements)
                    for (var v = 0; v < form.elements[id].length; ++v)
                        if (form.elements[id][v].checked)
                            result.push(form.elements[id][v].value);
                return result;
            case "LIST":
                var table = document.getElementById("table_" + question.common.id + "_" + form.id);
                var result = new Array();
                for (var i = 1; i < table.rows.length; ++i) {
                    var value = getListRowValue(question, table.rows[i].id);
                    if (!rowIsEmptyByValue(question, value))
                        result.push(value);
                }
                return result;
        }
    }
    
    function getData() {
        var result = new Object();
        var form = document.forms.data;
        for (var p = 0; p < pages.length; ++p) {
            var page = pages[p];
            if ("questions" in page) {
                for (var q = 0; q < page.questions.length; ++q) {
                    var question = page.questions[q];
                    var id = question.common.id;
                    result[id] = getElementValue(form, question);
                }
            }
        }
        return result;
    }
    
    function hideElements() {
        var data = getData();
        for (var p = 0; p < pages.length; ++p) {
            var page = pages[p];
            if ("condition" in page.common) {
                document.getElementById("page_header_" + page.common.id).style.display = eval(page.common.condition) ? '' : 'none';
            }
            if ("questions" in page) {
                for (var q = 0; q < page.questions.length; ++q) {
                    var question = page.questions[q];
                    if ("condition" in question.common) {
                        document.getElementById("line_" + question.common.id).style.display = eval(question.common.condition) ? '' : 'none';
                    }
                    if ("answer_options" in question) {
                        for (var ao = 0; ao < question.answer_options.length; ++ao) {
                            var option = question.answer_options[ao];
                            if ("condition" in option) {
                                document.getElementById("option_" + question.common.id + "_" + option.id).style.display = eval(question.common.condition) ? '' : 'none';
                            }
                        }
                    }
                }
            }
        }
    }
    
    window.onload = function() {
        disable_links = false;
        $("#btn_send").hide();
        koolajax.callback(get_request_from_dm("api/service_wizard?project=<?php echo $service_cgi ?>"), onGetQuestions);
    };
    
    function onClickCutHead() {
        $(this).next(".cut_body").slideToggle(10);
        $(this).toggleClass("active");
    }
    
    function onGetQuestions(s) {
        var pages_tabs = document.getElementById("pages_tabs");
        if (!s.success) {
            pages_tabs.innerHTML = s.reply;
            return;
        }
        pages = JSON.parse(s.reply).pages;
        var pages_content = "";
        var pages_list = "<ul>";
        for (var p = 0; p < pages.length; ++p) {
            var page = pages[p];
            pages_content += "<div id='page_" + page.common.id + "'>";
            pages_content += getPageHtml(pages[p]);
            pages_content += "</div>";
            pages_list += "<li id='page_header_" + page.common.id + "'><a href='#page_" + page.common.id + "'><span>" + page.common.title + "</span></a></li>";
        }
        pages_list += "</ul>";
        pages_tabs.innerHTML = pages_list + pages_content;
        hideElements();
        $(".cut_body").hide();
        $(".cut_head").click(onClickCutHead);
        $("#pages_tabs").tabs({active: 0});
        $(".datepicker").datepicker();
        $("#btn_send").show();
    }
    
    function sendData(checkOnly) {
        var btnSend = document.getElementById("btn_send");
        btnSend.disabled = true;
        btnSend.value = "...";
        var btnCheck = document.getElementById("btn_check");
        btnCheck.disabled = true;
        btnCheck.value = "...";
        document.getElementById("status").innerHTML = "<span style='color: blue'>Sending...</span>";
        document.getElementById("errors").innerHTML = "";
        document.getElementById("files").innerHTML = "";
        document.getElementById("documents").innerHTML = "";
        document.getElementById("requests").innerHTML = "";
        var data = getData();
        document.getElementById("debug").innerHTML = "<pre>" + JSON.stringify(data, "", 2) + "</pre>";
        koolajax.callback(post_request_to_dm("api/service_wizard?check_only=" + checkOnly + "&project=<?php echo $service_cgi ?>", JSON.stringify(data), 0), onDataSend);
    }
    
    function displayErrors(reply) {
        if (!("errors" in reply))
            return;
        var html = "<h2>Ошибки</h2>";
        for (var i = 0; i < reply.errors.length;++i) {
            var err = reply.errors[i];
            var msgParts = smartSplit(err.message, "%s");
            html +="<p class='error_" + err.level + "'>"; 
            for (var p = 0; p < msgParts.length; ++p) {
                html += msgParts[p];
                if ("links" in err && p < err.links.length) {
                    html += "<a href='/" + err.links[p].page_id +  "/" + err.links[p].question_id +"'>" + err.links[p].text + "</a>";
                }
            }
            html +="</p>"; 
        }
        document.getElementById("errors").innerHTML = html;
    }

    function displayFiles(reply) {
        if (!("files" in reply))
            return;
        var html = "<h2>Файлы</h2>";
        for (var i = 0; i < reply.files.length;++i) {
            var file = reply.files[i];
            html +="<p class='cut_head'>" + file.name + "</p>"; 
            html +="<div class='cut_body' class=monospace><textarea readonly='1' cols='200' rows='20' id='file_" + file.name + "'></textarea></div>"; 
        }
        document.getElementById("files").innerHTML = html;
        for (var i = 0; i < reply.files.length;++i) {
            var file = reply.files[i];
            document.getElementById("file_" + file.name).value = file.content;
        }
    }

    function displayDocuments(reply) {
        if (!("documents" in reply))
            return;
        var html = "<h2>Образцы документов</h2>";
        for (var i = 0; i < reply.documents.length;++i) {
            var doc = reply.documents[i];
            html +="<p class='cut_head'>" + doc.format + "</p>"; 
            html +="<div class='cut_body' class=monospace><code>" + doc.example + "</code></p>"; 
        }
        document.getElementById("documents").innerHTML = html;
    }

    function displayRequests(reply) {
        if (!("project" in reply) || !("request_examples" in reply.project))
            return;
        var html = "<h2>Образец запроса</h2>";
        for (var r = 0; r < reply.project.request_examples.length; ++r) {
            var request = reply.project.request_examples[r];
            var url = "http://saas-searchproxy-testing.yandex.net:17000/?";
            var descr = "<table>";
            for (var i = 0; i < request.params.length;++i) {
                var param = request.params[i];
                if (param.optional)
                    url += "[";
                if (i > 0)
                    url += "&amp";
                url += param.name + "=";
                if ("description" in param) {
                    descr += "<tr><td>" + param.name+"</td>";
                    descr += "<td>" + param.description + "</td></tr>";
                }
                url += "&lt";
                if ("values" in param && param.values.length > 0)
                    for (var v = 0; v < param.values.length; ++v) {
                        var value = param.values[v];
                        if (v > 0)
                            url += "|";
                        url += value.data;
                        if ("description" in value) {
                            descr += "<tr><td style='padding-left:35px'>" + value.data+"</td>";
                            descr += "<td>" + value.description + "</td></tr>";
                        }
                    }
                url += "&gt";
                if (param.optional)
                    url += "]";
            }
            descr += "</table>";
            html += "<p class='monospace'>" + url + "</p>" + descr;
        }
        document.getElementById("documents").innerHTML = html;
    }
    
    function onDataSend(s) {
        var btnSend = document.getElementById("btn_send");
        btnSend.disabled = false;
        btnSend.value = "Отослать";
        var btnCheck = document.getElementById("btn_check");
        btnCheck.disabled = false;
        btnCheck.value = "Проверить";
        var reply = JSON.parse(s.reply);
        displayErrors(reply);
        displayFiles(reply);
        displayDocuments(reply);
        displayRequests(reply);
        if (reply.ok && s.success)
            document.getElementById("status").innerHTML = "<span style='color: green'>OK</span>";
        else
            document.getElementById("status").innerHTML = "<span style='color: red'>FAIL</span>";
        $(".cut_body").hide();
    $(".cut_head").click(onClickCutHead);
    }
</script>

<?php
    $service_wizard = "<form id='data'></form>";
    $service_wizard .= "<div id='pages_tabs'></div>";
    $service_wizard .= "<input id='btn_send' type='button' value='Отослать' onclick='sendData(0)'></input>";
    $service_wizard .= "<input id='btn_check' type='button' value='Проверить' onclick='sendData(1)'></input>";
    $service_wizard .= "<div id='status' class='status'></div>";
    $service_wizard .= "<div id='responce'>";
    $service_wizard .= "<div id='errors'></div>";
    $service_wizard .= "<div id='files'></div>";
    $service_wizard .= "<div id='documents'></div>";
    $service_wizard .= "<div id='requests'></div>";
    $service_wizard .= "<h1>Отладка</h1><div id='debug'></div>";
    $service_wizard .= "</div>";
?>