From 25c3a1bdffb516f76ba758f98d406af2e5d12fbc Mon Sep 17 00:00:00 2001 From: Julian <julian@edyoucated.org> Date: Sun, 10 Mar 2024 11:45:44 +0100 Subject: [PATCH] first running version of dash inside of jupyterlab via proxy --- .gitignore | 2 ++ Dockerfile | 22 ++++++++++--------- README.md | 2 +- app/app.py | 44 ++++++++++++++++++++++++++++++++++++++ app/callbacks.py | 23 ++++++++++++++++++++ app/layout.py | 14 ++++++++++++ environment.yml | 7 ++++++ jupyter_notebook_config.py | 13 +++++++++++ requirements.txt | 12 +++++++++++ 9 files changed, 128 insertions(+), 11 deletions(-) create mode 100644 .gitignore create mode 100644 app/app.py create mode 100644 app/callbacks.py create mode 100644 app/layout.py create mode 100644 environment.yml create mode 100644 jupyter_notebook_config.py create mode 100644 requirements.txt diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..f75c4cd --- /dev/null +++ b/.gitignore @@ -0,0 +1,2 @@ +*env/ +.env diff --git a/Dockerfile b/Dockerfile index 8786a75..e5fa561 100644 --- a/Dockerfile +++ b/Dockerfile @@ -1,15 +1,17 @@ FROM jupyter/datascience-notebook:hub-3.1.1 -# Install from APT repository USER root -RUN apt-get update -y -RUN apt-get install -y git -# Install basics -USER jovyan -RUN pip3 install --upgrade pip +COPY requirements.txt environment.yml /tmp/ +RUN conda env update -q -f /tmp/environment.yml && \ + /opt/conda/bin/pip install -r /tmp/requirements.txt && \ + conda clean -y --all && \ + conda env export -n "root" && \ + jupyter lab build + +COPY jupyter_notebook_config.py ${HOME}/.jupyter/ + +# copy dash app +COPY app ${HOME}/app/ +RUN chown -R jovyan ${HOME}/app/ -# RUN pip3 install --upgrade pip -RUN pip install jupyter-server-proxy==4.0.0 -RUN pip install jupyterlab-git==0.42.0 -RUN pip install jupyterlab-gitlab==3.0.0 diff --git a/README.md b/README.md index 38011d6..0afc659 100644 --- a/README.md +++ b/README.md @@ -1,2 +1,2 @@ -# bücker +# A Jupyterlab for LLM diff --git a/app/app.py b/app/app.py new file mode 100644 index 0000000..4975d67 --- /dev/null +++ b/app/app.py @@ -0,0 +1,44 @@ +import sys +sys.path.append("/home/jovyan") + +import argparse +import logging + +from dash import Dash + +from layout import layout +from callbacks import register_callbacks + +logging.basicConfig(level=logging.INFO) + + +# get the correct port from proxy +parser = argparse.ArgumentParser() +parser.add_argument("--port", type=int) +args = parser.parse_args() +port: int = args.port + +if not port: + raise ValueError(f"Port of proxy server for Dash not found in {args}.") +else: + logging.debug(f"Dash app running on port {port}.") + +# define Dash app +app = Dash( + name=__name__, + requests_pathname_prefix="/dash/" +) + +# define layout +app.layout = layout + +# register all callback functions +register_callbacks(app=app) + +# Run Dash app in the notebook +app.run( + jupyter_mode="jupyterlab", + port=port, + host="localhost", + debug=True +) diff --git a/app/callbacks.py b/app/callbacks.py new file mode 100644 index 0000000..9d22226 --- /dev/null +++ b/app/callbacks.py @@ -0,0 +1,23 @@ +from dash import ( + html, + Dash +) +from dash.dependencies import ( + Input, + Output, + State +) + + +def register_callbacks(app: Dash): + @app.callback( + Output("output-container", "children"), + [Input("send-button", "n_clicks")], + [State("input-text", "value")] + ) + def generate_response(n_clicks, input_text): + if n_clicks > 0: + response = "You said: " + input_text + return html.Div(response) + else: + return "" diff --git a/app/layout.py b/app/layout.py new file mode 100644 index 0000000..fbc93fa --- /dev/null +++ b/app/layout.py @@ -0,0 +1,14 @@ +from dash import ( + html, + dcc +) + +layout = html.Div( + className="container", + children=[ + html.H1("GPT Chat", className="mt-5 mb-4"), + dcc.Textarea(id="input-text", placeholder="Enter your message:", className="form-control mb-3"), + html.Button("Send", id="send-button", n_clicks=0, className="btn btn-primary mb-3"), + html.Div(id="output-container") + ] +) diff --git a/environment.yml b/environment.yml new file mode 100644 index 0000000..eef32e1 --- /dev/null +++ b/environment.yml @@ -0,0 +1,7 @@ +name: "base" +channels: + - defaults +# dependencies: +# - add packages here +# - one per line +prefix: "/opt/conda" diff --git a/jupyter_notebook_config.py b/jupyter_notebook_config.py new file mode 100644 index 0000000..22208d3 --- /dev/null +++ b/jupyter_notebook_config.py @@ -0,0 +1,13 @@ +# Configuration file for jupyter-notebook. +c.ServerProxy.servers = { + 'dash': { + 'command': [ + 'python', + 'app/app.py', + '--port', + '{port}' + ], + 'absolute_url': False, + 'new_browser_tab': False + } +} diff --git a/requirements.txt b/requirements.txt new file mode 100644 index 0000000..cf2d387 --- /dev/null +++ b/requirements.txt @@ -0,0 +1,12 @@ +jupyter-server-proxy==4.0.0 +jupyterlab-git==0.42.0 +jupyter_server>=2.0 + +dash +dash-bootstrap-components +plotly + +openai +rapidfuzz + +python-dotenv -- GitLab