diff options
| author | James Barnett <noreply@jamesbarnett.xyz> | 2018-02-20 21:44:28 +0000 |
|---|---|---|
| committer | James Barnett <noreply@jamesbarnett.xyz> | 2018-02-20 21:44:28 +0000 |
| commit | b81c0f834f7f2285c40cfd57eb2943140025edad (patch) | |
| tree | 2c45b5d844e2a8413f3189090e5f6373226f4fca | |
| parent | 52f6783f63d2e2f52e06d14a97b5e00eab8ac1c0 (diff) | |
| download | sql-plus-plus-b81c0f834f7f2285c40cfd57eb2943140025edad.tar.xz sql-plus-plus-b81c0f834f7f2285c40cfd57eb2943140025edad.zip | |
Dynamically create query executors - WIP
| -rw-r--r-- | editor-instance.js | 29 | ||||
| -rw-r--r-- | instance-manager.js | 47 | ||||
| -rw-r--r-- | main.js | 64 | ||||
| -rw-r--r-- | new-connection.html | 89 | ||||
| -rw-r--r-- | new-connection.js | 46 | ||||
| -rw-r--r-- | query-executor.js | 41 |
6 files changed, 199 insertions, 117 deletions
diff --git a/editor-instance.js b/editor-instance.js index cb26db7..008705f 100644 --- a/editor-instance.js +++ b/editor-instance.js @@ -11,7 +11,8 @@ require("codemirror/addon/hint/sql-hint.js"); const Split = require("split.js"); const editorInstanceId = require('uuid/v1')(); -console.log("instanceId=" + editorInstanceId); + +let queryExecutorId; const editorContext = cm(document.getElementById("editor"), { value: "select *\nfrom information_schema.tables\n/\nselect now()\n/\nselect *\nfrom foo", @@ -27,7 +28,20 @@ editorContext.on("cursorActivity", (instance) => { $("#cursor-coords").text("Ln " + (parseInt(coords.line) + 1) + ", Col " + (parseInt(coords.ch) + 1)); }); -ipcRenderer.send("queryExecutor.queryTableMetadata", _generateIpcPayload()); +const statementDelimiter = "/"; + +let dataTable; +let execStartTime; +let execTimerInterval; +let execElapsedTime; +let queryMark; + +ipcRenderer.on("editorInstance.registerQueryExecutor", (event, payload) => { + queryExecutorId = payload; + console.log(queryExecutorId); + ipcRenderer.send("queryExecutor.queryTableMetadata", _generateIpcPayload()); +}) + ipcRenderer.on("queryExecutor.queryTableMetadataComplete", (event, response) => { console.log(response); cm.commands.autocomplete = function (cmInstance) { @@ -37,14 +51,6 @@ ipcRenderer.on("queryExecutor.queryTableMetadataComplete", (event, response) => } }); -const statementDelimiter = "/"; - -let dataTable; -let execStartTime; -let execTimerInterval; -let execElapsedTime; -let queryMark; - function runQuery() { _setExecutionStatusIndicator("RUNNING"); @@ -132,7 +138,8 @@ function _clearQueryMarks() { function _generateIpcPayload() { return { - editorInstanceId: editorInstanceId + editorInstanceId: editorInstanceId, + queryExecutorId: queryExecutorId } } diff --git a/instance-manager.js b/instance-manager.js index 115f359..6a4d019 100644 --- a/instance-manager.js +++ b/instance-manager.js @@ -4,37 +4,32 @@ const { ipcRenderer } = require('electron'); const TabGroup = require("electron-tabs"); const $ = window.jQuery = require("jquery"); -let tabGroup = new TabGroup(); -let tab = tabGroup.addTab({ - title: "Electron", - src: 'file://' + __dirname + '/editor-instance.html', - visible: true, - active: true, - webviewAttributes: {"nodeintegration":true}, - // ready: tab => { - // let webview = tab.webview; - // if (!!webview) { - // webview.addEventListener('dom-ready', () => { - // webview.openDevTools(); - // }) - // } - // } -}); - -let tab2 = tabGroup.addTab({ - title: "Electron", - src: 'file://' + __dirname + '/editor-instance.html', - visible: true, - active: true, - webviewAttributes: { "nodeintegration": true }, -}); +const tabGroup = new TabGroup(); function createNewConnection() { ipcRenderer.send("instanceManager.openNewConnectionDialog"); } -ipcRenderer.on("instanceManager.newConnectionCallback", (event, response) => { - console.log(response); +function registerNewInstance(assignedQueryExecutorId) { + tabGroup.addTab({ + title: "Electron", + src: "file://" + __dirname + "/editor-instance.html", + visible: true, + active: true, + webviewAttributes: {"nodeintegration":true}, + ready: tab => { + let webview = tab.webview; + if (!!webview) { + webview.addEventListener("dom-ready", () => { + webview.send("editorInstance.registerQueryExecutor", assignedQueryExecutorId); + }) + } + } + }); +} + +ipcRenderer.on("instanceManager.registerNewInstance", (event, assignedQueryExecutorId) => { + registerNewInstance(assignedQueryExecutorId); }); @@ -4,8 +4,8 @@ const path = require("path"); const url = require("url"); let uiWindow; -let queryExecutorProcess; let newConnectionDialog; +let queryExecutors = []; function createMainWindow() { uiWindow = new BrowserWindow({ @@ -24,26 +24,8 @@ function createMainWindow() { }); } -function createQueryExecutorProcess() { - queryExecutorProcess = new BrowserWindow({ - show: false - }); - - queryExecutorProcess.loadURL(url.format({ - pathname: path.join(__dirname, "./query-executor-wrapper.html"), - protocol: "file:", - slashes: true - })); - - queryExecutorProcess.on("closed", () => { - queryExecutorProcess = null; - }); - -} - app.on("ready", () => { createMainWindow(); - createQueryExecutorProcess(); }); app.on("window-all-closed", () => { @@ -78,6 +60,36 @@ ipcMain.on("instanceManager.openNewConnectionDialog", (event, payload) => { createNewConnectionDialog(); }); +function createQueryExecutor(payload) { + let executor = new BrowserWindow({ + show: false, + }); + + executor.connectionConfig = payload; + + executor.loadURL(url.format({ + pathname: path.join(__dirname, "./query-executor-wrapper.html"), + protocol: "file:", + slashes: true + })); + + queryExecutors.push(executor); + + return executor; +} + +ipcMain.on("newConnection.createConnection", (event, payload) => { + createQueryExecutor(payload); +}); + + +ipcMain.on("queryExecutor.initialiseConnectionCallback", (event, payload) => { + // TODO - handle connection initialisation errors + + uiWindow.webContents.send("instanceManager.registerNewInstance", payload); + newConnectionDialog.close(); +}); + const { webContents } = require('electron'); @@ -88,11 +100,21 @@ ipcMain.on("queryExecutor.runQueryComplete", (event, payload) => { w.send("queryExecutor.runQueryComplete", payload); }) }); -ipcMain.on("queryExecutor.runQuery", (event, payload) => queryExecutorProcess.webContents.send("queryExecutor.runQuery", payload)); + +ipcMain.on("queryExecutor.runQuery", (event, payload) => { + queryExecutors.forEach((executor) => { + executor.webContents.send("queryExecutor.runQuery", payload); + }); +}); ipcMain.on("queryExecutor.queryTableMetadataComplete", (event, payload) => { webContents.getAllWebContents().forEach((w) => { w.send("queryExecutor.queryTableMetadataComplete", payload); }) }); -ipcMain.on("queryExecutor.queryTableMetadata", (event, payload) => queryExecutorProcess.webContents.send("queryExecutor.queryTableMetadata", payload));
\ No newline at end of file +; +ipcMain.on("queryExecutor.queryTableMetadata", (event, payload) => { + queryExecutors.forEach((executor) => { + executor.webContents.send("queryExecutor.queryTableMetadata", payload); + }); +});
\ No newline at end of file diff --git a/new-connection.html b/new-connection.html index dace021..18d4ad9 100644 --- a/new-connection.html +++ b/new-connection.html @@ -9,54 +9,57 @@ <body> <h4 class="title is-4" >Add new connection</h4> - - <div class="field"> - <label class="label is-small" for="vendor">Vendor</label> - <div class="control"> - <div class="select is-small"> - <select id="vendor"> - <option>Postgres</option> - <option>MySQL/MariaDB</option> - <option>Oracle</option> - </select> - </div> - </div> - </div> - <div class="field"> - <label class="label is-small" for="hostname">Hostname</label> - <div class="control"> - <input id="hostname" class="input is-small" type="text"/> - </div> - </div> - <div class="field"> - <label class="label is-small" for="port">Port</label> - <div class="control"> - <input id="port" class="input is-small" type="text" placeholder="5432"/> + <form> + <div class="field"> + <label class="label is-small" for="vendor">Vendor</label> + <div class="control"> + <div class="select is-small"> + <select name="vendor"> + <option value="postgres">Postgres</option> + <option value="mysql">MySQL/MariaDB</option> + <option value="oracle">Oracle</option> + </select> + </div> + </div> </div> - </div> - <div class="field"> - <label class="label is-small" for="username">Username</label> - <div class="control"> - <input id="username" class="input is-small" type="text"/> + <div class="field"> + <label class="label is-small" for="hostname">Hostname</label> + <div class="control"> + <input name="hostname" class="input is-small" type="text"/> + </div> </div> - </div> - <div class="field"> - <label class="label is-small" for="password">Password</label> - <div class="control"> - <input id="password" class="input is-small" type="text"/> + <div class="field"> + <label class="label is-small" for="port">Port</label> + <div class="control"> + <input name="port" class="input is-small" type="text" placeholder="5432"/> + </div> </div> - </div> - <div class="field is-grouped"> - <div class="control"> - <button id="create-connection" class="button is-link is-small">Add</button> + <div class="field"> + <label class="label is-small" for="username">Username</label> + <div class="control"> + <input name="username" class="input is-small" type="text"/> + </div> </div> - <div class="control"> - <button id="test-connection" class="button is-small">Test connection</button> + <div class="field"> + <label class="label is-small" for="password">Password</label> + <div class="control"> + <input name="password" class="input is-small" type="text"/> + </div> </div> - <div class="control"> - <button id="cancel" class="button is-text is-small">Cancel</button> + <div class="field is-grouped"> + <div class="control"> + <input id="create-connection" type="button" class="button is-link is-small" value="Add"></input> + </div> + <div class="control"> + <input id="test-connection" type="button" class="button is-small" value="Test connection"></input> + </div> + <div class="control"> + <input id="cancel" type="button" class="button is-text is-small" value="Cancel"></input> + </div> </div> - </div> + </form> </body> - + <script> + require("./new-connection.js"); + </script> </html>
\ No newline at end of file diff --git a/new-connection.js b/new-connection.js new file mode 100644 index 0000000..2493c25 --- /dev/null +++ b/new-connection.js @@ -0,0 +1,46 @@ +"use strict"; + +const { remote, ipcRenderer } = require("electron"); +const $ = window.jQuery = require("jquery"); + +function cancel() { + let confirm = remote.dialog.showMessageBox(remote.getCurrentWindow(), { + type: "question", + buttons: ["Yes", "No"], + title: "Confirm", + message: "Remove this connection?" + }); + + if (confirm === 0) { + remote.getCurrentWindow().close(); + } +} + +function parseForm() { + let formData = {}; + + $("form").serializeArray().forEach((input) => { + formData[input.name] = input.value; + }); + + return formData; +} + +function createConnection() { + let connectionProps = parseForm(); + ipcRenderer.send("newConnection.createConnection", connectionProps); +} + +$(document).ready(() => { + $("#create-connection").click(() => { + createConnection(); + }); + + $("#test-connection").click(() => { + //TODO + }); + + $("#cancel").click(() => { + cancel(); + }); +});
\ No newline at end of file diff --git a/query-executor.js b/query-executor.js index 871da9e..0c5b440 100644 --- a/query-executor.js +++ b/query-executor.js @@ -1,30 +1,39 @@ "use strict"; -const { ipcRenderer } = require("electron"); +const { remote, ipcRenderer } = require("electron"); const { Pool } = require("pg"); +const executorId = require("uuid/v1")(); + +const connectionConfig = remote.getCurrentWindow().connectionConfig; + const connectionPool = new Pool({ - user: "postgres", - host: "localhost", + user: connectionConfig.username, + host: connectionConfig.host, database: "postgres", - password: "", - port: 5432 + password: connectionConfig.password, + port: connectionConfig.port }); -ipcRenderer.on("queryExecutor.runQuery", (event, payload) => { - - connectionPool.query(payload.query, (err, res) => { +// Initialisation completed +ipcRenderer.send("queryExecutor.initialiseConnectionCallback", executorId); - console.log(err, res) +ipcRenderer.on("queryExecutor.runQuery", (event, payload) => { - ipcRenderer.send("queryExecutor.runQueryComplete", { - "error": err, - "result": res, - "editorInstanceId": payload.editorInstanceId + if(payload.queryExecutorId === executorId) { + connectionPool.query(payload.query, (err, res) => { + + console.log(err, res) + + ipcRenderer.send("queryExecutor.runQueryComplete", { + "error": err, + "result": res, + "editorInstanceId": payload.editorInstanceId + }); + }); - - }); - + } + }); ipcRenderer.on("queryExecutor.queryTableMetadata", (event, payload) => { |