From 953bd631ace67b7dc1a1dc9510e7fa3c8bb2cfa7 Mon Sep 17 00:00:00 2001 From: Umar Farooq Ghumman Date: Thu, 9 May 2024 10:53:39 -0500 Subject: [PATCH 1/3] added basic UI for entering other detailed connection info --- project/ui/conn.ipynb | 308 +++++++++++++++++------------------------- 1 file changed, 125 insertions(+), 183 deletions(-) diff --git a/project/ui/conn.ipynb b/project/ui/conn.ipynb index 4b76a1bb..62e71b23 100644 --- a/project/ui/conn.ipynb +++ b/project/ui/conn.ipynb @@ -2,7 +2,46 @@ "cells": [ { "cell_type": "code", - "execution_count": 1, + "execution_count": null, + "id": "646eaee7-3870-4fee-af2a-3e2df937d88c", + "metadata": {}, + "outputs": [], + "source": [ + "import ipywidgets as widgets\n", + "from IPython.display import display, HTML\n", + "\n", + "# Define the URLs for the links\n", + "url1 = \"/lab/\"\n", + "url2 = \"/voila/render/ui/qprof_main.ipynb\"\n", + "\n", + "# Define the button labels\n", + "button_label1 = \"Go to Home Page\"\n", + "button_label2 = \"Go to Query Profiler\"\n", + "\n", + "# Define HTML links for buttons\n", + "button_html1 = f\"\"\n", + "button_html2 = f\"{button_label2}\"\n", + "\n", + "\n", + "# Create HTML widgets\n", + "html_button1 = widgets.HTML(value=button_html1)\n", + "html_button2 = widgets.HTML(value=button_html2)\n", + "\n", + "# Display buttons\n", + "display(widgets.HBox([html_button1, html_button2]))\n" + ] + }, + { + "cell_type": "markdown", + "id": "6537d006-71a5-45ae-b6d9-032a4b2879e9", + "metadata": {}, + "source": [ + "_________" + ] + }, + { + "cell_type": "code", + "execution_count": null, "id": "739353e9-44cd-4dbb-8891-f1dea998067f", "metadata": {}, "outputs": [], @@ -16,7 +55,7 @@ }, { "cell_type": "code", - "execution_count": 2, + "execution_count": null, "id": "8ed8016c-dacf-437d-af27-7005b66f6739", "metadata": {}, "outputs": [], @@ -28,6 +67,24 @@ "password = widgets.Password(description = \"Password\", placeholder = \"Enter Password (default is Empty)\")\n", "database = widgets.Text(description = \"Database\", placeholder = \"Enter Database (default is 'demo')\")\n", "name = widgets.Text(description = \"Name\", placeholder = \"Enter Name (default is 'VerticaDSN')\")\n", + "ssl = widgets.Text(description = \"SSL/TLS\", placeholder = \"TLS/SSL. (default is false)\", layout=widgets.Layout(width='350px'))\n", + "ssl.style.description_width = '130px'\n", + "connection_timeout = widgets.Text(description = \"Connection Timeout\", placeholder = \"Time in seconds (default is 5)\", layout=widgets.Layout(width='350px'))\n", + "connection_timeout.style.description_width = '130px'\n", + "autocommit = widgets.Checkbox(value = False, description = 'Autocommit', disabled = False, indent = False,layout=widgets.Layout(width = '350px',align_items='flex-end'))\n", + "\n", + "#Oauth\n", + "oauth_access_token = widgets.Password(description = \"OAuth Access Token\", placeholder = \"Enter Access Token\", layout=widgets.Layout(width='500px'))\n", + "oauth_access_token.style.description_width = '150px'\n", + "oauth_refresh_token = widgets.Password(description = \"OAuth Refresh Token\", placeholder = \"Enter Refresh Token\", layout=widgets.Layout(width='500px'))\n", + "oauth_refresh_token.style.description_width = '150px'\n", + "\n", + "#Kerberos\n", + "kerberos_host_name = widgets.Text(description = \"Kerberos host name\", placeholder = \"Enter Host\", layout=widgets.Layout(width='500px'))\n", + "kerberos_host_name.style.description_width = '150px'\n", + "kerberos_service_name = widgets.Text(description = \"Kerberos service name\", placeholder = \"Enter Name\", layout=widgets.Layout(width='500px'))\n", + "kerberos_service_name.style.description_width = '150px'\n", + "\n", "backup_server_node = [\"localhost\"]" ] }, @@ -41,25 +98,10 @@ }, { "cell_type": "code", - "execution_count": 3, + "execution_count": null, "id": "1cdf1aa6-6310-4764-823c-c0aff71e396a", "metadata": {}, - "outputs": [ - { - "data": { - "application/vnd.jupyter.widget-view+json": { - "model_id": "09fd8c1943344c58ade9173242e7e43f", - "version_major": 2, - "version_minor": 0 - }, - "text/plain": [ - "VBox(children=(Text(value='', description='Host', placeholder=\"Enter Host (default is 'verticadb')\"), Text(val…" - ] - }, - "metadata": {}, - "output_type": "display_data" - } - ], + "outputs": [], "source": [ "import ipywidgets as widgets\n", "\n", @@ -75,39 +117,35 @@ }, { "cell_type": "code", - "execution_count": 4, + "execution_count": null, + "id": "640cf2ec-5c0f-4c45-89e0-a5d025e2d26c", + "metadata": {}, + "outputs": [], + "source": [ + "more_options = widgets.VBox([\n", + " ssl,\n", + " connection_timeout,\n", + "])\n", + "\n", + "\n", + "tab = widgets.Tab()\n", + "child_1 = widgets.VBox([oauth_access_token,oauth_refresh_token])\n", + "child_2 = widgets.VBox([kerberos_host_name,kerberos_service_name])\n", + "tab.children = [child_1, child_2]\n", + "tab.titles = [\"OAuth\", \"Kerberos\"]\n", + "\n", + "advanced_options = widgets.VBox([more_options, tab, autocommit,])\n", + "\n", + "accordion = widgets.Accordion(children=[advanced_options], titles=('Advanced Options',))\n", + "accordion" + ] + }, + { + "cell_type": "code", + "execution_count": null, "id": "a70eb307-19eb-4ecd-866f-54864d981032", "metadata": {}, - "outputs": [ - { - "data": { - "application/vnd.jupyter.widget-view+json": { - "model_id": "ec3f62d585ee463da4c13e30b491b62d", - "version_major": 2, - "version_minor": 0 - }, - "text/plain": [ - "Button(description='Create a Connection', style=ButtonStyle())" - ] - }, - "metadata": {}, - "output_type": "display_data" - }, - { - "data": { - "application/vnd.jupyter.widget-view+json": { - "model_id": "62eeee9a4c154b7fa341937bb05bb531", - "version_major": 2, - "version_minor": 0 - }, - "text/plain": [ - "Output(layout=Layout(border_bottom='1px solid black', border_left='1px solid black', border_right='1px solid b…" - ] - }, - "metadata": {}, - "output_type": "display_data" - } - ], + "outputs": [], "source": [ "\n", "button = widgets.Button(description=\"Create a Connection\")\n", @@ -146,53 +184,10 @@ }, { "cell_type": "code", - "execution_count": 9, + "execution_count": null, "id": "074edcaf-2212-4dbf-9d3e-0b430ef514ac", "metadata": {}, - "outputs": [ - { - "data": { - "application/vnd.jupyter.widget-view+json": { - "model_id": "0a1d68d3a20e4c09a2bde924745e8504", - "version_major": 2, - "version_minor": 0 - }, - "text/plain": [ - "Dropdown(description='Available Coneections:', layout=Layout(width='300px'), options=('Yuanzhe', 'VerticaDSN')…" - ] - }, - "metadata": {}, - "output_type": "display_data" - }, - { - "data": { - "application/vnd.jupyter.widget-view+json": { - "model_id": "9821d701390645ae98d18fdd9bd8784c", - "version_major": 2, - "version_minor": 0 - }, - "text/plain": [ - "Button(description='Create a Connection', style=ButtonStyle())" - ] - }, - "metadata": {}, - "output_type": "display_data" - }, - { - "data": { - "application/vnd.jupyter.widget-view+json": { - "model_id": "5eaf0e2b73004f838a77404fa4be150f", - "version_major": 2, - "version_minor": 0 - }, - "text/plain": [ - "Output(layout=Layout(border_bottom='1px solid black', border_left='1px solid black', border_right='1px solid b…" - ] - }, - "metadata": {}, - "output_type": "display_data" - } - ], + "outputs": [], "source": [ "from verticapy.connection import change_auto_connection\n", "\n", @@ -215,76 +210,9 @@ "button_select.on_click(on_button_clicked_select)" ] }, - { - "cell_type": "markdown", - "id": "b3ef9cd5-0769-4586-98f1-0f460a22ff1c", - "metadata": {}, - "source": [ - "____" - ] - }, - { - "cell_type": "code", - "execution_count": 6, - "id": "14e6b51c-72d8-4611-b991-47f9aeaa1473", - "metadata": { - "collapsed": true, - "jupyter": { - "outputs_hidden": true - } - }, - "outputs": [ - { - "data": { - "application/vnd.jupyter.widget-view+json": { - "model_id": "1d01048d0ffd4a88a33456ba7a857415", - "version_major": 2, - "version_minor": 0 - }, - "text/plain": [ - "HBox(children=(HTML(value=\"\"\n", - "button_html2 = f\"{button_label2}\"\n", - "\n", - "\n", - "# Create HTML widgets\n", - "html_button1 = widgets.HTML(value=button_html1)\n", - "html_button2 = widgets.HTML(value=button_html2)\n", - "\n", - "# Display buttons\n", - "display(widgets.HBox([html_button1, html_button2]))\n" - ] - }, - { - "cell_type": "markdown", - "id": "32f3c37b-1446-4114-99a0-8dc62998ac5d", - "metadata": {}, - "source": [ - "____" - ] - }, { "cell_type": "code", - "execution_count": 29, + "execution_count": null, "id": "dd19b4c5-f99f-4467-b885-3cc34a58a7ae", "metadata": {}, "outputs": [], @@ -306,38 +234,52 @@ }, { "cell_type": "code", - "execution_count": 27, + "execution_count": null, "id": "db3e615b-7ed6-4b14-a508-432a0e6735a5", "metadata": {}, - "outputs": [ - { - "data": { - "application/vnd.jupyter.widget-view+json": { - "model_id": "2100538297184c6494d87fa467acb6f5", - "version_major": 2, - "version_minor": 0 - }, - "text/plain": [ - "Accordion(children=(VBox(children=(Button(description='Click to display', style=ButtonStyle()), Output(outputs…" - ] - }, - "execution_count": 27, - "metadata": {}, - "output_type": "execute_result" - } - ], + "outputs": [], "source": [ "accordion = widgets.Accordion(children=[version_details], titles=('Version Details',))\n", "accordion" ] }, + { + "cell_type": "markdown", + "id": "b295fdd4-b6c3-4749-a639-d9a589e1d46b", + "metadata": {}, + "source": [ + "_________" + ] + }, { "cell_type": "code", "execution_count": null, "id": "c7e6ed2f-af31-48a8-80fc-f5a9402647b4", "metadata": {}, "outputs": [], - "source": [] + "source": [ + "import subprocess\n", + "output_install = widgets.Output()\n", + "\n", + "def install_verticapy(_):\n", + " with output_install:\n", + " subprocess.run([\"pip\", \"install\", \"git+https://github.com/vertica/VerticaPy.git@master\"])\n", + " print(\"Successfully installed latest verticapy from the master branch.\")\n", + " print(\"Note: You must refresh to get the latest version.\")\n", + "\n", + "install_button = widgets.Button(description=\"Install latest verticapy\")\n", + "install_button.on_click(install_verticapy)\n", + "\n", + "display(install_button, output_install)" + ] + }, + { + "cell_type": "markdown", + "id": "a935e70f-9cad-4149-9f66-a8c6b95e9405", + "metadata": {}, + "source": [ + "_________" + ] } ], "metadata": { @@ -356,7 +298,7 @@ "name": "python", "nbconvert_exporter": "python", "pygments_lexer": "ipython3", - "version": "3.10.12" + "version": "3.10.13" } }, "nbformat": 4, From bb110eef48387c1be1be06e5de96856f3f6a9035 Mon Sep 17 00:00:00 2001 From: Umar Farooq Ghumman Date: Thu, 9 May 2024 11:50:14 -0500 Subject: [PATCH 2/3] added a better flow for TLS --- project/ui/conn.ipynb | 101 ++++++++++++++++++++++++++++++++++-------- 1 file changed, 82 insertions(+), 19 deletions(-) diff --git a/project/ui/conn.ipynb b/project/ui/conn.ipynb index 62e71b23..d1d0edcf 100644 --- a/project/ui/conn.ipynb +++ b/project/ui/conn.ipynb @@ -49,6 +49,7 @@ "from ipywidgets import interact, interactive, fixed, interact_manual\n", "import ipywidgets as widgets\n", "from IPython.display import display,clear_output, HTML\n", + "from ipyfilechooser import FileChooser\n", "\n", "import verticapy as vp" ] @@ -61,14 +62,13 @@ "outputs": [], "source": [ "# style = {'description_width': '150px', 'width' : '400px'}\n", - "host = widgets.Text(description = \"Host\",placeholder = \"Enter Host (default is 'verticadb')\")\n", - "port = widgets.Text(description = \"Port\", placeholder = \"Enter Port (default is 5433)\")\n", - "user = widgets.Text(description = \"User name\", placeholder = \"Enter User Name (default is 'dbadmin')\")\n", - "password = widgets.Password(description = \"Password\", placeholder = \"Enter Password (default is Empty)\")\n", - "database = widgets.Text(description = \"Database\", placeholder = \"Enter Database (default is 'demo')\")\n", - "name = widgets.Text(description = \"Name\", placeholder = \"Enter Name (default is 'VerticaDSN')\")\n", - "ssl = widgets.Text(description = \"SSL/TLS\", placeholder = \"TLS/SSL. (default is false)\", layout=widgets.Layout(width='350px'))\n", - "ssl.style.description_width = '130px'\n", + "host = widgets.Text(description = \"Host\",placeholder = \"Enter Host (default is 'verticadb')\", layout=widgets.Layout(width='350px'))\n", + "port = widgets.Text(description = \"Port\", placeholder = \"Enter Port (default is 5433)\", layout=widgets.Layout(width='350px'))\n", + "user = widgets.Text(description = \"User name\", placeholder = \"Enter User Name (default is 'dbadmin')\", layout=widgets.Layout(width='350px'))\n", + "password = widgets.Password(description = \"Password\", placeholder = \"Enter Password (default is Empty)\", layout=widgets.Layout(width='350px'))\n", + "database = widgets.Text(description = \"Database\", placeholder = \"Enter Database (default is 'demo')\", layout=widgets.Layout(width='350px'))\n", + "name = widgets.Text(description = \"Name\", placeholder = \"Enter Name (default is 'VerticaDSN')\", layout=widgets.Layout(width='350px'))\n", + "\n", "connection_timeout = widgets.Text(description = \"Connection Timeout\", placeholder = \"Time in seconds (default is 5)\", layout=widgets.Layout(width='350px'))\n", "connection_timeout.style.description_width = '130px'\n", "autocommit = widgets.Checkbox(value = False, description = 'Autocommit', disabled = False, indent = False,layout=widgets.Layout(width = '350px',align_items='flex-end'))\n", @@ -96,6 +96,14 @@ "## Please enter connection details" ] }, + { + "cell_type": "code", + "execution_count": null, + "id": "b98d2f06-e7e8-4edd-94e7-8e82ed18e367", + "metadata": {}, + "outputs": [], + "source": [] + }, { "cell_type": "code", "execution_count": null, @@ -112,29 +120,83 @@ " password,\n", " database,\n", " name,\n", + " connection_timeout\n", "]))" ] }, { "cell_type": "code", "execution_count": null, - "id": "640cf2ec-5c0f-4c45-89e0-a5d025e2d26c", + "id": "d87806cd-929a-48e6-9b33-1e93f1df556c", "metadata": {}, "outputs": [], "source": [ - "more_options = widgets.VBox([\n", - " ssl,\n", - " connection_timeout,\n", - "])\n", + "tls_params = widgets.RadioButtons(\n", + " options=['Require', 'Verify-CA', 'Verify-Full'],\n", + " value='Require', # Defaults to 'Require'\n", + " description='Select:',\n", + " disabled=False\n", + ")\n", "\n", + "# Create uploader widget\n", + "uploader = FileChooser('')\n", + "output_tls = widgets.Output()\n", + "# Function to display appropriate widget based on radio button selection\n", + "def display_widget_tls(selection):\n", + " output_tls.clear_output()\n", + " with output_tls:\n", + " if selection == 'Verify-CA' or selection == 'Verify-Full':\n", + " display(uploader)\n", + "\n", + "# Call function when radio button value changes\n", + "tls_params.observe(lambda change: display_widget_tls(change['new']), names='value')\n", + "\n" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "id": "840c448c-cc61-412d-b68e-8700c136a1c7", + "metadata": {}, + "outputs": [], + "source": [ + "# Create dropdown widget\n", + "dropdown = widgets.Dropdown(\n", + " options=['', 'OAuth', 'TLS', 'Kerberos'],\n", + " description='Advanced Connection',\n", + " disabled=False\n", + ")\n", + "output_advanced_connection = widgets.Output()\n", + "\n", + "oauth_params = widgets.VBox([oauth_access_token,oauth_refresh_token])\n", + "kerberos_params = widgets.VBox([kerberos_host_name,kerberos_service_name])\n", + "\n", + "\n", + "# Function to display appropriate widget based on dropdown selection\n", + "def display_widget_advanced_connection(selection):\n", + " output_advanced_connection.clear_output()\n", + " with output_advanced_connection:\n", + " if selection == 'OAuth':\n", + " display(oauth_params)\n", + " elif selection == 'Kerberos':\n", + " display(kerberos_params)\n", + " elif selection == 'TLS':\n", + " display(tls_params,output_tls)\n", + "\n", + "# Call function when dropdown value changes\n", + "dropdown.observe(lambda change: display_widget_advanced_connection(change['new']), names='value')" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "id": "640cf2ec-5c0f-4c45-89e0-a5d025e2d26c", + "metadata": {}, + "outputs": [], + "source": [ "\n", - "tab = widgets.Tab()\n", - "child_1 = widgets.VBox([oauth_access_token,oauth_refresh_token])\n", - "child_2 = widgets.VBox([kerberos_host_name,kerberos_service_name])\n", - "tab.children = [child_1, child_2]\n", - "tab.titles = [\"OAuth\", \"Kerberos\"]\n", "\n", - "advanced_options = widgets.VBox([more_options, tab, autocommit,])\n", + "advanced_options = widgets.VBox([dropdown,output_advanced_connection, autocommit])\n", "\n", "accordion = widgets.Accordion(children=[advanced_options], titles=('Advanced Options',))\n", "accordion" @@ -163,6 +225,7 @@ " 'user': user.value if user.value else \"dbadmin\",\n", " 'password': password.value if password.value else \"\",\n", " 'database': database.value if database.value else \"demo\",\n", + " 'ssl': ssl.value if ssl.value else False,\n", " }\n", " vp.new_connection(\n", " conn_info,\n", From 3ac6bfa02da0bd18c62c13529cbdbadcefba4b21 Mon Sep 17 00:00:00 2001 From: Umar Farooq Ghumman Date: Thu, 9 May 2024 14:00:36 -0500 Subject: [PATCH 3/3] updated TLS code --- project/ui/conn.ipynb | 31 ++++++++++++++++++++----------- 1 file changed, 20 insertions(+), 11 deletions(-) diff --git a/project/ui/conn.ipynb b/project/ui/conn.ipynb index d1d0edcf..09c6598e 100644 --- a/project/ui/conn.ipynb +++ b/project/ui/conn.ipynb @@ -50,6 +50,7 @@ "import ipywidgets as widgets\n", "from IPython.display import display,clear_output, HTML\n", "from ipyfilechooser import FileChooser\n", + "import ssl\n", "\n", "import verticapy as vp" ] @@ -96,14 +97,6 @@ "## Please enter connection details" ] }, - { - "cell_type": "code", - "execution_count": null, - "id": "b98d2f06-e7e8-4edd-94e7-8e82ed18e367", - "metadata": {}, - "outputs": [], - "source": [] - }, { "cell_type": "code", "execution_count": null, @@ -137,16 +130,21 @@ " description='Select:',\n", " disabled=False\n", ")\n", - "\n", + "ssl_context = None\n", "# Create uploader widget\n", "uploader = FileChooser('')\n", "output_tls = widgets.Output()\n", "# Function to display appropriate widget based on radio button selection\n", "def display_widget_tls(selection):\n", " output_tls.clear_output()\n", + " global ssl_context\n", " with output_tls:\n", " if selection == 'Verify-CA' or selection == 'Verify-Full':\n", " display(uploader)\n", + " if selection == \"Verify-CA\":\n", + " ssl_context.check_hostname = False\n", + " elif selection == \"Verify-Full\":\n", + " ssl_context.check_hostname = True\n", "\n", "# Call function when radio button value changes\n", "tls_params.observe(lambda change: display_widget_tls(change['new']), names='value')\n", @@ -174,14 +172,20 @@ "\n", "# Function to display appropriate widget based on dropdown selection\n", "def display_widget_advanced_connection(selection):\n", + " global ssl_context\n", " output_advanced_connection.clear_output()\n", + "\n", " with output_advanced_connection:\n", " if selection == 'OAuth':\n", " display(oauth_params)\n", " elif selection == 'Kerberos':\n", " display(kerberos_params)\n", " elif selection == 'TLS':\n", + " ssl_context = ssl.SSLContext(ssl.PROTOCOL_TLS_CLIENT)\n", + " ssl_context.check_hostname = False\n", + " ssl_context.verify_mode = ssl.CERT_NONE\n", " display(tls_params,output_tls)\n", + " ssl_context\n", "\n", "# Call function when dropdown value changes\n", "dropdown.observe(lambda change: display_widget_advanced_connection(change['new']), names='value')" @@ -218,6 +222,9 @@ "\n", "def on_button_clicked(b):\n", " output.clear_output(wait=True) # Clear the output\n", + " global ssl_context\n", + " if dropdown.value ==\"TLS\" and (tls_params==\"Verify-Full\" or tls_params==\"Verify-CA\"):\n", + " ssl_context.load_verify_locations(cafile=uploader.value) # CA certificate used to verify server certificate\n", " with output:\n", " conn_info = {\n", " 'host': host.value if host.value else \"verticadb\", \n", @@ -225,7 +232,7 @@ " 'user': user.value if user.value else \"dbadmin\",\n", " 'password': password.value if password.value else \"\",\n", " 'database': database.value if database.value else \"demo\",\n", - " 'ssl': ssl.value if ssl.value else False,\n", + " 'ssl': ssl_context if dropdown.value ==\"TLS\" else False,\n", " }\n", " vp.new_connection(\n", " conn_info,\n", @@ -240,7 +247,9 @@ { "cell_type": "markdown", "id": "4caf85a1-a3f9-4dd2-af9f-f2a43d239ed1", - "metadata": {}, + "metadata": { + "jp-MarkdownHeadingCollapsed": true + }, "source": [ "## Or Select From List" ]