412 lines
		
	
	
		
			22 KiB
		
	
	
	
		
			HTML
		
	
	
			
		
		
	
	
			412 lines
		
	
	
		
			22 KiB
		
	
	
	
		
			HTML
		
	
	
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01//EN" "http://www.w3.org/TR/html4/strict.dtd">
 | 
						|
<!--
 | 
						|
Copyright (c) 2012, 2019, Oracle and/or its affiliates. All rights reserved.
 | 
						|
 | 
						|
This program is free software; you can redistribute it and/or modify
 | 
						|
it under the terms of the GNU General Public License as published by
 | 
						|
the Free Software Foundation; version 2 of the License.
 | 
						|
 | 
						|
This program is distributed in the hope that it will be useful,
 | 
						|
but WITHOUT ANY WARRANTY; without even the implied warranty of
 | 
						|
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 | 
						|
GNU General Public License for more details.
 | 
						|
 | 
						|
You should have received a copy of the GNU General Public License
 | 
						|
along with this program; if not, write to the Free Software
 | 
						|
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301 USA
 | 
						|
-->
 | 
						|
<html dir="ltr" lang="en">
 | 
						|
    <head>
 | 
						|
        <meta http-equiv="Content-Type" content="text/html;charset=iso-8859-1"/>
 | 
						|
        <title>MySQL Cluster</title>
 | 
						|
        <link rel="icon" type="image/x-icon" href="/img/favicon.ico"/>
 | 
						|
        <link rel="stylesheet" type="text/css" 
 | 
						|
                href="dojo/dijit/themes/claro/claro.css"/>
 | 
						|
        <link rel="stylesheet" type="text/css" href="css/welcome.css"/>
 | 
						|
        <style type="text/css">
 | 
						|
            @import "dojo/dojox/form/resources/CheckedMultiSelect.css";
 | 
						|
        </style>
 | 
						|
        <script type="text/javascript" src="dojo/dojo/dojo.js" djConfig="parseOnLoad: true, locale: 'en'"></script>
 | 
						|
        <script type="text/javascript">
 | 
						|
            // Path to top level mcc module
 | 
						|
            dojo.registerModulePath("mcc", "../../js/mcc");
 | 
						|
            dojo.require("dijit.form.Button");
 | 
						|
            dojo.require("dojo.dom");
 | 
						|
            dojo.require("dojo.dom-construct");
 | 
						|
            dojo.require("dojo.domReady!");
 | 
						|
            dojo.require("dojox.widget.Standby");
 | 
						|
 | 
						|
            // MCC modules immediately required
 | 
						|
            if (!!window.MSInputMethodContext && !!document.documentMode) {
 | 
						|
                dojo.require("mcc.userconfigIE");
 | 
						|
            } else {
 | 
						|
                dojo.require("mcc.userconfig");
 | 
						|
            }
 | 
						|
            function parseURLParams(url) {
 | 
						|
                var queryStart = url.indexOf("?") + 1,
 | 
						|
                    queryEnd   = url.indexOf("#") + 1 || url.length + 1,
 | 
						|
                    query = url.slice(queryStart, queryEnd - 1),
 | 
						|
                    pairs = query.replace(/\+/g, " ").split("&"),
 | 
						|
                    parms = {}, i, n, v, nv;
 | 
						|
 | 
						|
                if (query === url || query === "") return;
 | 
						|
                //Actually there are no K/V pairs in this concrete example.
 | 
						|
                //The output is in form of [config1.mcc, config2.mcc,...].
 | 
						|
                return pairs;
 | 
						|
            }
 | 
						|
            var url = window.location.href;
 | 
						|
            var cfgList = parseURLParams(url);
 | 
						|
            console.debug('[DBG]cfgList: ' + cfgList);
 | 
						|
            let picked = 'New configuration';
 | 
						|
            var standby = new dojox.widget.Standby({target: "configure-box"});
 | 
						|
 | 
						|
 | 
						|
            function doStuff() {
 | 
						|
                standby.show();
 | 
						|
                
 | 
						|
                function do_post(msg) {
 | 
						|
                    // Convert to json string
 | 
						|
                    var jsonMsg = JSON.stringify(msg); //dojo.toJson(msg);
 | 
						|
                    //var dbgMsg = JSON.stringify(msg); //dojo.toJson(msg);
 | 
						|
                    // Return deferred from xhrPost
 | 
						|
                    return dojo.xhrPost({
 | 
						|
                        url: "/cmd",
 | 
						|
                        headers: { "Content-Type": "application/json" },
 | 
						|
                        postData: jsonMsg,
 | 
						|
                        handleAs: "json"
 | 
						|
                    });
 | 
						|
                }
 | 
						|
                // Generic error handler closure
 | 
						|
                function errorHandler(req, onError) {
 | 
						|
                    if (onError) {
 | 
						|
                        return onError;
 | 
						|
                    } else {
 | 
						|
                        return function (error) {
 | 
						|
                            console.error("An error occurred while executing '" + req.cmd + 
 | 
						|
                                    " (" + req.seq + ")': " + error);
 | 
						|
                        };
 | 
						|
                    }
 | 
						|
                }
 | 
						|
                
 | 
						|
                // Generic reply handler closure
 | 
						|
                function replyHandler(onReply, onError) {
 | 
						|
                    return function (reply) {
 | 
						|
                        if (reply && reply.stat && reply.stat.errMsg != "OK") {
 | 
						|
                            if (onError) {
 | 
						|
                                onError(reply.stat.errMsg, reply);
 | 
						|
                            } else {
 | 
						|
                                alert(reply.stat.errMsg);
 | 
						|
                            }
 | 
						|
                        } else {
 | 
						|
                            try{
 | 
						|
                                onReply(reply);
 | 
						|
                            } catch (E) {
 | 
						|
                                alert("Error in formatting reply.");
 | 
						|
                            }
 | 
						|
                        }
 | 
						|
                    };
 | 
						|
                }
 | 
						|
                
 | 
						|
                function cffileExistsReq(mesg, onReply, onError) {
 | 
						|
                    console.debug("[DBG]Composing cffileExistsReq message for host localhost.");
 | 
						|
                    var ms = mesg;       
 | 
						|
                    // Call do_post, provide callbacks
 | 
						|
                    do_post(ms).then(replyHandler(onReply, onError), 
 | 
						|
                        errorHandler(ms.head, onError));
 | 
						|
                }
 | 
						|
                function createCfgFileReq(mesg, onReply, onError) {
 | 
						|
                    console.debug("[DBG]Composing createCfgFileReq message for host localhost.");
 | 
						|
                    var ms = mesg;       
 | 
						|
                    // Call do_post, provide callbacks
 | 
						|
                    do_post(ms).then(replyHandler(onReply, onError), 
 | 
						|
                        errorHandler(ms.head, onError));
 | 
						|
                }
 | 
						|
                function readCfgFileReq(mesg, onReply, onError) {
 | 
						|
                    console.debug("[DBG]Composing readCfgFileReq message for host localhost.");
 | 
						|
                    var ms = mesg;       
 | 
						|
                    // Call do_post, provide callbacks
 | 
						|
                    do_post(ms).then(replyHandler(onReply, onError), 
 | 
						|
                            errorHandler(ms.head, onError));
 | 
						|
                }
 | 
						|
                
 | 
						|
                var cf = picked;
 | 
						|
                if (cf) {
 | 
						|
                    if (cf == 'New configuration') {
 | 
						|
                        cf = "NewConfig";
 | 
						|
                        cf = prompt("Please provide the name for new configuration file: ");
 | 
						|
                        if (cf == null || cf == "") {
 | 
						|
                            //Cancelled or empty.
 | 
						|
                            console.warn("window.location.reload() - CF name NULL or EMPTY");
 | 
						|
                            standby.hide();
 | 
						|
                            window.location.reload();
 | 
						|
                            return;
 | 
						|
                        }
 | 
						|
                    }
 | 
						|
                    // We are no longer sending cfgname.MCC from back end!
 | 
						|
                    if ( /\.(mcc)$/i.test(cf) === false ) {
 | 
						|
                        cf += '.mcc'; 
 | 
						|
                    }
 | 
						|
                    mcc.userconfig.setConfigFile(cf);
 | 
						|
                    
 | 
						|
                    var defCfg = mcc.userconfig.getDefaultCfg();
 | 
						|
                    var fileExists = false;
 | 
						|
                    var res = new dojo.Deferred();
 | 
						|
                    var msg = {
 | 
						|
                        head: {cmd: "cffileExistsReq", seq: 0},
 | 
						|
                        body: {
 | 
						|
                            ssh: {keyBased: false, user: "", pwd: ""},
 | 
						|
                            hostName: 'localhost',
 | 
						|
                            path: "~",
 | 
						|
                            fname: cf 
 | 
						|
                        }
 | 
						|
                    };
 | 
						|
                    cffileExistsReq(
 | 
						|
                        msg,
 | 
						|
                        function (reply) {
 | 
						|
                            //File with that name already exists. Will load that later on.
 | 
						|
                            console.debug("[DBG]reply.body.hostRes.exists is: " + reply.body.hostRes.exists);
 | 
						|
                            fileExists = reply.body.hostRes.exists == 1;
 | 
						|
                            res.resolve(true);
 | 
						|
                            return res;
 | 
						|
                        },
 | 
						|
                        function (errMsg, reply) {
 | 
						|
                            console.error("Error happened while checking for existence of " + cf + ' file!'+
 | 
						|
                                    "Error message is: " + errMsg);
 | 
						|
                            alert("Error happened while checking for existence of " + cf + ' file!'+
 | 
						|
                                    "Error message is: " + errMsg);
 | 
						|
                            res.resolve(false);
 | 
						|
                            return res;
 | 
						|
                        }
 | 
						|
                    );
 | 
						|
                    res.then(function(success){
 | 
						|
                        console.debug("[DBG]cffileExistsReq success: ", success);
 | 
						|
                        return true;
 | 
						|
                    }, function(error){
 | 
						|
                        console.error("cffileExistsReq error: ", error);
 | 
						|
                        return false;
 | 
						|
                    }).then(function(info){
 | 
						|
                        console.debug("[DBG]cffileExistsReq has finished with success status: " + info);
 | 
						|
                        if (info) {
 | 
						|
                            //var cfNoExt = cf.substr(0, cf.lastIndexOf('.')) || cf;
 | 
						|
                            console.debug("[DBG]FileExists is NOT " + (!fileExists));
 | 
						|
                            if (!fileExists) {
 | 
						|
                                var res2 = new dojo.Deferred();
 | 
						|
                                console.debug("[DBG]Config doesn't exit. Creating file, writing defaults.");
 | 
						|
                                //Fill new config with predefined defaults:
 | 
						|
                                msg = {
 | 
						|
                                    head: {cmd: "createCfgFileReq", seq: 1},
 | 
						|
                                    body: {
 | 
						|
                                        ssh: {keyBased: false, user: "", pwd: ""},
 | 
						|
                                        hostName: 'localhost',
 | 
						|
                                        path: "~",
 | 
						|
                                        fname: cf,
 | 
						|
                                        contentString: defCfg,
 | 
						|
                                        phr: ""
 | 
						|
                                    }
 | 
						|
                                };
 | 
						|
                                createCfgFileReq(
 | 
						|
                                        msg,
 | 
						|
                                    function (resFNC) {
 | 
						|
                                        console.debug("[DBG]Configuration didn't exits. Created."); 
 | 
						|
                                        res2.resolve(true);
 | 
						|
                                        return res2;
 | 
						|
                                    },  
 | 
						|
                                    function (errMsgFNC) {
 | 
						|
                                        console.error("Unable to create config file " + cf+ " in HOME directory: " + errMsgFNC);
 | 
						|
                                        //This is bad, bail out and just work from tree.
 | 
						|
                                        cf = "";
 | 
						|
                                        res2.resolve(false);
 | 
						|
                                        return res2;
 | 
						|
                                    }
 | 
						|
                                );
 | 
						|
                                res2.then(function(success1){
 | 
						|
                                    console.debug("[DBG]createCfgFileReq success: ", success1);
 | 
						|
                                    return true;
 | 
						|
                                }, function(error1){
 | 
						|
                                    console.error("createCfgFileReq error: ", error1);
 | 
						|
                                    return false;
 | 
						|
                                }).then(function(info1){
 | 
						|
                                    console.debug("[DBG]createCfgFileReq has finished with success status: ", info1);
 | 
						|
                                    if (info1) {
 | 
						|
                                        console.debug("[DBG]Setting global conf file.");
 | 
						|
                                        mcc.userconfig.setConfigFile(cf);
 | 
						|
                                        mcc.userconfig.setConfigFileContents(defCfg);
 | 
						|
                                        window.name = JSON.stringify({
 | 
						|
                                            "CFC": mcc.userconfig.getConfigFileContents(),
 | 
						|
                                            "CF": cf,
 | 
						|
                                            "CFPP": ""});
 | 
						|
                                        standby.hide();
 | 
						|
                                        window.open('content.html', '_self');
 | 
						|
                                    }
 | 
						|
                                });
 | 
						|
                            } else {
 | 
						|
                                console.debug("[DBG]Reading from existing config file.");
 | 
						|
                                console.debug("[DBG]Setting global conf file.");
 | 
						|
                                mcc.userconfig.setConfigFile(cf);
 | 
						|
                                msg = {
 | 
						|
                                    head: {cmd: "readCfgFileReq", seq: 1},
 | 
						|
                                    body: {
 | 
						|
                                        ssh: {keyBased: false, user: "", pwd: ""},
 | 
						|
                                        hostName: 'localhost',
 | 
						|
                                        path: "~",
 | 
						|
                                        fname: cf,
 | 
						|
                                        phr: ""
 | 
						|
                                    }
 | 
						|
                                };
 | 
						|
                                readCfgFileReq(
 | 
						|
                                    msg,
 | 
						|
                                    function (reply) {
 | 
						|
                                        console.debug("[DBG]readCfgFileReq has finished with success.");
 | 
						|
                                        // Just in case someone thinks it's funny to create empty mcc file...
 | 
						|
                                        if (reply.body.hostRes.contentString.length > 10) {
 | 
						|
                                            // "Someone" thought _on_ would be nice value for Boolean.
 | 
						|
                                            // Now have to convert to _true_.
 | 
						|
                                            mcc.userconfig.setConfigFileContents(
 | 
						|
                                                reply.body.hostRes.contentString.replace(/"on"/g, 'true'));
 | 
						|
                                        } else {
 | 
						|
                                            mcc.userconfig.setConfigFileContents(defCfg);
 | 
						|
                                        }
 | 
						|
                                        window.name = JSON.stringify({ 
 | 
						|
                                            "CFC": mcc.userconfig.getConfigFileContents(),
 | 
						|
                                            "CF": cf,
 | 
						|
                                            "CFPP": ""});
 | 
						|
                                        standby.hide();
 | 
						|
                                        window.open('content.html', '_self');
 | 
						|
                                    },
 | 
						|
                                    function (errMsgFNC) {
 | 
						|
                                        console.error("window.location.reload() - errMsgFNC");
 | 
						|
                                        standby.hide();
 | 
						|
                                        alert("Unable to read config file " + cf +
 | 
						|
                                            " in HOME directory: " + errMsgFNC); 
 | 
						|
                                        //This is bad, bail out and just work from tree.
 | 
						|
                                        cf = "";
 | 
						|
                                        window.location.reload();
 | 
						|
                                        return;
 | 
						|
                                    }
 | 
						|
                                );
 | 
						|
                            }
 | 
						|
                        }
 | 
						|
                    });
 | 
						|
                } else {
 | 
						|
                    console.debug("[DBG]window.location.reload() - LAST");
 | 
						|
                    standby.hide();
 | 
						|
                    window.location.reload();
 | 
						|
                    return;
 | 
						|
                }
 | 
						|
            } //doStuff()
 | 
						|
 | 
						|
            dojo.ready(function() {
 | 
						|
                // Check browser type
 | 
						|
                var supportedUa = navigator.userAgent.match(/firefox|safari|chrome|msie/gi);
 | 
						|
 | 
						|
                console.debug("[DBG]Browser application name is " + navigator.appName);
 | 
						|
                console.debug("[DBG]Browser application version is " + navigator.appVersion);
 | 
						|
                console.debug("[DBG]User agent string is: " + navigator.userAgent);
 | 
						|
                console.debug("[DBG]User agent " + supportedUa + " is supported"); 
 | 
						|
                
 | 
						|
                if (!supportedUa) {
 | 
						|
                    alert("You seem to be using a " + navigator.appName + 
 | 
						|
                        " browser, which is currently not supported by the " +
 | 
						|
                        "MySQL Cluster configuration tool. You may choose to " +
 | 
						|
                        "continue anyway, but beware that the tool may not " +
 | 
						|
                        "work as intended.");
 | 
						|
                }
 | 
						|
 | 
						|
                document.body.appendChild(standby.domNode);
 | 
						|
                standby.startup();
 | 
						|
                
 | 
						|
                // No need to send path along as it is always HOME.
 | 
						|
                function populateMultiSelect(optionData){
 | 
						|
                    require([
 | 
						|
                        "dojox/form/CheckedMultiSelect",
 | 
						|
                        "dojo/dom", "dojo/_base/window", "dojo/domReady!"
 | 
						|
                    ], function(CheckedMultiSelect, dom, win){
 | 
						|
                        var sel = dojo.byId('sid1');
 | 
						|
                        var ss1 = new CheckedMultiSelect({
 | 
						|
                            name: 'sid1',
 | 
						|
                            options: optionData,
 | 
						|
                            onChange: function(val){
 | 
						|
                                    picked = val;
 | 
						|
                                    console.debug("[DBG]PICKED: " + picked);
 | 
						|
                                },
 | 
						|
                            multiple: false,
 | 
						|
                            class: "narrow wrap",
 | 
						|
                            style: "white-space: normal; height: 85%;"
 | 
						|
                        }, sel);
 | 
						|
                        ss1.startup();
 | 
						|
                        document.getElementById("sid1").focus();
 | 
						|
                        ss1.on("keydown", function(e) {
 | 
						|
                            console.debug("[DBG]CMS.keydown");
 | 
						|
                            switch(e.keyCode) {
 | 
						|
                                case dojo.keys.ENTER:
 | 
						|
                                    dojo.stopEvent(e);
 | 
						|
                                    console.debug("[DBG]CMS.keydown ENTER");
 | 
						|
                                    break;
 | 
						|
                                case dojo.keys.TAB:
 | 
						|
                                    dojo.stopEvent(e);
 | 
						|
                                    console.debug("[DBG]CMS.keydown TAB");
 | 
						|
                                    break;
 | 
						|
                                default:
 | 
						|
                            }
 | 
						|
                        });
 | 
						|
                    });
 | 
						|
                }
 | 
						|
 | 
						|
                var opts = new Array();
 | 
						|
                opts.push(
 | 
						|
                            {value: "New configuration",
 | 
						|
                            label: "New configuration",
 | 
						|
                            selected: true}
 | 
						|
                );
 | 
						|
                
 | 
						|
                if (cfgList) {
 | 
						|
                    console.debug("[DBG]Found " + cfgList.length + " configurations.");
 | 
						|
                    console.info('List of configurations found: %s', cfgList);
 | 
						|
                    for (var i = 0; i < cfgList.length; i++) {
 | 
						|
                        opts.push({value:cfgList[i], label:cfgList[i]});
 | 
						|
                    }
 | 
						|
                } else {
 | 
						|
                    console.warn("No existing configurations found.");
 | 
						|
                }
 | 
						|
                populateMultiSelect(opts);
 | 
						|
            });
 | 
						|
        </script>
 | 
						|
    </head>
 | 
						|
    <body class="claro">
 | 
						|
        <!-- Welcome title image -->
 | 
						|
        <div id="title"><img alt="Oracle logo" src="img/welcome-title.png"></div>
 | 
						|
        <!-- Big MySQL Logo image in the background -->
 | 
						|
        <div id="mysql-logo"><img alt="MySQL logo" src="img/welcome-mysql-logo.png"></div>
 | 
						|
            <!-- Configuration box: Start from scratch or continue -->
 | 
						|
            <div id="configure-box-wrapper" style="display: flex; flex-wrap: nowrap;top: 300px">
 | 
						|
                <div id="intro-box" style="width: -webkit-fill-available; display: flow-root; margin-right: 2%; height: 400px; font-size: large;color: wheat;">
 | 
						|
                    <h2> MCC quick reference:</h2>
 | 
						|
                    <p> ➤ Create <b>New configuration</b> or resume work on existing one by picking it from the list.</p>
 | 
						|
                    <p> ➤ RUN configuration will load it from disk to MCC and allow you to continue working on/with it.</p>
 | 
						|
                    <p> ➤ SECURITY: The configuration files are located in your HOME/.mcc directory and stored in plain text. Configuration files do not store sensitive information, like passwords, but do store user names and External/Internal IP addresses of hosts.</p>
 | 
						|
                    <p> ➤ SECURITY: Please use properly signed certificate to encrypt communication between front and back end.</p>
 | 
						|
                    <p> ➤ Make sure to allow pop-up windows in the browser where MCC runs as we communicate important things using that mechanism.</p>
 | 
						|
                </div>
 | 
						|
                <div id="configure-box" style="margin: 5px auto; height: 400px; float: right;position: relative">
 | 
						|
                    <div id = "configListContainer" style="width: 95%; height: 85%;margin: 10 auto;float: left;text-align: left;border: 0;">
 | 
						|
                        <select id="sid1"  class="narrow wrap"></select>
 | 
						|
                    </div>
 | 
						|
                    <div id = "configBtnContainer" style="width: 95%; margin: 10 auto; position: absolute; bottom: 0;">
 | 
						|
                        <button 
 | 
						|
                            type="button"
 | 
						|
                            id="createNewCluster"
 | 
						|
                            style="width: 100%;height: 80%;margin: 5 auto;float: left;text-align: center;border: 2px solid;background-color: #011D33;font-size: large;"
 | 
						|
                            >RUN configuration
 | 
						|
                        </button>
 | 
						|
                        <script type="text/javascript">
 | 
						|
                            function clickRunB() {
 | 
						|
                                doStuff();
 | 
						|
                            }
 | 
						|
                            document.getElementById("createNewCluster").addEventListener("click", clickRunB);
 | 
						|
                        </script>
 | 
						|
                    </div>
 | 
						|
                </div><!--CONFIGUREBOX-->
 | 
						|
            </div> <!--CONFIGUREBOX WRAPPER-->
 | 
						|
    </body>
 | 
						|
</html>
 |