From 8a845bf156dbd7f29141d4d304aebf25c823a7fa Mon Sep 17 00:00:00 2001
From: atla8167 <athanasio.lakes@dsv.su.se>
Date: Fri, 29 Nov 2024 14:59:34 +0200
Subject: [PATCH] Fixed Glacier Experiments not Viewed in Counterfactuals
 template. Enhanced home template

---
 base/handlers/__init__.py                     |    4 +
 .../__pycache__/__init__.cpython-310.pyc      |  Bin 0 -> 367 bytes
 .../ajaxChartsHandler.cpython-310.pyc         |  Bin 0 -> 3680 bytes
 ...ajaxCounterfactualsHandler.cpython-310.pyc |  Bin 0 -> 10364 bytes
 .../ajaxHomeHandler.cpython-310.pyc           |  Bin 0 -> 5673 bytes
 .../ajaxTrainHandler.cpython-310.pyc          |  Bin 0 -> 7285 bytes
 base/handlers/ajaxChartsHandler.py            |  219 +++
 base/handlers/ajaxCounterfactualsHandler.py   |  768 +++++++++
 base/handlers/ajaxHomeHandler.py              |  437 +++++
 base/handlers/ajaxTrainHandler.py             |  464 +++++
 base/static/css/sb-admin-2.css                |  478 +++++-
 base/static/img/digital_features.png          |  Bin 0 -> 12071 bytes
 base/static/img/su_logo.png                   |  Bin 0 -> 40692 bytes
 base/static/img/undraw_posting_photo.svg      |    1 -
 base/static/img/undraw_profile.svg            |   38 -
 base/static/img/undraw_profile_1.svg          |   38 -
 base/static/img/undraw_profile_2.svg          |   44 -
 base/static/img/undraw_profile_3.svg          |   47 -
 base/static/img/undraw_rocket.svg             |   39 -
 base/static/js/click_reset.js                 |   29 -
 base/static/js/counterfactuals.js             |    1 +
 base/static/js/home.js                        |  613 +++++++
 base/static/js/import.js                      |   21 -
 base/static/js/main.js                        |   38 +-
 base/static/js/methods.js                     |  108 +-
 base/static/js/radio_dataset.js               |   98 --
 base/static/js/radio_model.js                 |   82 +-
 base/static/js/radio_timeseries_dataset.js    |  130 +-
 base/static/js/radio_uploaded_dataset.js      |  118 --
 base/static/js/train.js                       |  307 +++-
 base/templates/base/charts.html               |   27 +-
 base/templates/base/counterfactuals.html      |   91 +-
 base/templates/base/home.html                 |  512 ++++--
 base/templates/base/train.html                |  153 +-
 base/views.py                                 | 1515 +----------------
 35 files changed, 4169 insertions(+), 2251 deletions(-)
 create mode 100644 base/handlers/__init__.py
 create mode 100644 base/handlers/__pycache__/__init__.cpython-310.pyc
 create mode 100644 base/handlers/__pycache__/ajaxChartsHandler.cpython-310.pyc
 create mode 100644 base/handlers/__pycache__/ajaxCounterfactualsHandler.cpython-310.pyc
 create mode 100644 base/handlers/__pycache__/ajaxHomeHandler.cpython-310.pyc
 create mode 100644 base/handlers/__pycache__/ajaxTrainHandler.cpython-310.pyc
 create mode 100644 base/handlers/ajaxChartsHandler.py
 create mode 100644 base/handlers/ajaxCounterfactualsHandler.py
 create mode 100644 base/handlers/ajaxHomeHandler.py
 create mode 100644 base/handlers/ajaxTrainHandler.py
 create mode 100644 base/static/img/digital_features.png
 create mode 100644 base/static/img/su_logo.png
 delete mode 100755 base/static/img/undraw_posting_photo.svg
 delete mode 100755 base/static/img/undraw_profile.svg
 delete mode 100755 base/static/img/undraw_profile_1.svg
 delete mode 100755 base/static/img/undraw_profile_2.svg
 delete mode 100755 base/static/img/undraw_profile_3.svg
 delete mode 100755 base/static/img/undraw_rocket.svg
 delete mode 100755 base/static/js/click_reset.js
 create mode 100755 base/static/js/home.js
 delete mode 100755 base/static/js/import.js
 delete mode 100755 base/static/js/radio_dataset.js
 delete mode 100644 base/static/js/radio_uploaded_dataset.js

diff --git a/base/handlers/__init__.py b/base/handlers/__init__.py
new file mode 100644
index 000000000..fdae05bc9
--- /dev/null
+++ b/base/handlers/__init__.py
@@ -0,0 +1,4 @@
+from .ajaxHomeHandler import handler as home_handler
+from .ajaxCounterfactualsHandler import handler as counterfactuals_handler
+from .ajaxChartsHandler import handler as charts_handler
+from .ajaxTrainHandler import handler as train_handler
diff --git a/base/handlers/__pycache__/__init__.cpython-310.pyc b/base/handlers/__pycache__/__init__.cpython-310.pyc
new file mode 100644
index 0000000000000000000000000000000000000000..830ecc83b6554a47997e4a71383138e808712db6
GIT binary patch
literal 367
zcmY+9u};J=42F{)(1KbxCM4dV3y}~bLP#*&#BxksB42B0A!$*PisNw@d8MvQY|KnJ
zy<7#BV*kJOIdQryJ75&=;`Z^I>Zdn<BO-H6$6ipXSj837yomTl&q(hCy-Rv8=$Ldu
zI$E-P_Qh#5=R;gWTPZYm`F?Q(Pq1Ee8W)?M@$U?2O&uAq;?y%YUEex14^X-ulnwZB
zQvUBxL&xJ#4aQCEVL93fnS12kK+|q-%ba&x;Dec%wi(mUx$rv)1<z;&uAM>MYx#;R
lu>y-C>}rLSP1`sr&tBe!<WhH4ukgx$+$NM#mhzO(`7f5(YMKB5

literal 0
HcmV?d00001

diff --git a/base/handlers/__pycache__/ajaxChartsHandler.cpython-310.pyc b/base/handlers/__pycache__/ajaxChartsHandler.cpython-310.pyc
new file mode 100644
index 0000000000000000000000000000000000000000..08c8a3de6c6e7ca07e5ccb7c7c54f5f8070cc7a5
GIT binary patch
literal 3680
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

literal 0
HcmV?d00001

diff --git a/base/handlers/__pycache__/ajaxCounterfactualsHandler.cpython-310.pyc b/base/handlers/__pycache__/ajaxCounterfactualsHandler.cpython-310.pyc
new file mode 100644
index 0000000000000000000000000000000000000000..b8666251ebd9e08c44d2b35dd5728488f74c8f42
GIT binary patch
literal 10364
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
bNI9Llb3(&z?@=_V$Ouf1!fnvr_tgInC~@C8

literal 0
HcmV?d00001

diff --git a/base/handlers/__pycache__/ajaxHomeHandler.cpython-310.pyc b/base/handlers/__pycache__/ajaxHomeHandler.cpython-310.pyc
new file mode 100644
index 0000000000000000000000000000000000000000..d0d39195b61073b7003dc142b23404eaa47ebf03
GIT binary patch
literal 5673
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
G%>M#l`UQ3X

literal 0
HcmV?d00001

diff --git a/base/handlers/__pycache__/ajaxTrainHandler.cpython-310.pyc b/base/handlers/__pycache__/ajaxTrainHandler.cpython-310.pyc
new file mode 100644
index 0000000000000000000000000000000000000000..3f957594366efcb8bfd39684d3a924890d80e0c9
GIT binary patch
literal 7285
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

literal 0
HcmV?d00001

diff --git a/base/handlers/ajaxChartsHandler.py b/base/handlers/ajaxChartsHandler.py
new file mode 100644
index 000000000..df690c95c
--- /dev/null
+++ b/base/handlers/ajaxChartsHandler.py
@@ -0,0 +1,219 @@
+import base.pipeline as pipeline
+import os
+import pandas as pd
+import joblib
+from dict_and_html import *
+from .. import methods
+from ..methods import PIPELINE_PATH
+import base.pipeline as pipeline
+import json
+from django.shortcuts import HttpResponse
+
+def handler(action, request):
+    status = 200
+    if action == "pre_trained":
+        # load pre trained models
+        pre_trained_model_name = request.POST.get("pre_trained")
+        request.session["model_name"] = pre_trained_model_name
+        # dataframe name
+        df_name = request.session.get("df_name")
+
+        if df_name == "upload":
+            df_name = request.session.get("df_name_upload_base_name")
+
+        model_name_path = os.path.join(
+        PIPELINE_PATH + f"{df_name}" + "/trained_models/" + pre_trained_model_name
+        )
+
+        model_name_dir_path = os.path.join(PIPELINE_PATH + f"{df_name}")
+
+        # get the type of the file
+        datasets_types_PipelineJSON_path = os.path.join(
+        PIPELINE_PATH + "/dataset_types_pipeline.json"
+        )
+        datasets_types_pipeline = pipeline.PipelineJSON(
+        datasets_types_PipelineJSON_path
+        )
+        dataset_type = datasets_types_pipeline.read_from_json([df_name])
+
+        if type(dataset_type) is list:
+            dataset_type = dataset_type[0]
+
+        if "url" in request.POST:
+            url = request.POST.get("url")
+            
+            if url == "counterfactuals":
+                # only TSNE
+                tsne = joblib.load(model_name_path + "/tsne.sav")
+
+                # Assuming you already have your fig object created, you can update it like this:
+                # Improved and modern t-SNE visualization
+                tsne.update_layout(
+                    # Modern Legend Design
+                    legend=dict(
+                        x=0.9,
+                        y=0.95,
+                        xanchor="right",
+                        yanchor="top",
+                        bgcolor="rgba(255,255,255,0.8)",  # Light semi-transparent white background
+                        bordercolor="rgba(0,0,0,0.1)",  # Light border for contrast
+                        borderwidth=1,
+                        font=dict(size=12, color="#444"),  # Subtle grey for legend text
+                    ),
+                    # Tight Margins to Focus on the Plot
+                    margin=dict(
+                        l=10, r=10, t=30, b=10
+                    ),  # Very slim margins for a modern look
+                    # Axis Design: Minimalist and Clean
+                    xaxis=dict(
+                        title_text="",  # No axis labels for a clean design
+                        tickfont=dict(
+                            size=10, color="#aaa"
+                        ),  # Light grey for tick labels
+                        showline=True,
+                        linecolor="rgba(0,0,0,0.2)",  # Subtle line color for axis lines
+                        zeroline=False,  # No zero line for a sleek look
+                        showgrid=False,  # Hide grid lines for a minimal appearance
+                        ticks="outside",  # Small ticks outside the axis
+                        ticklen=3,  # Short tick marks for subtlety
+                    ),
+                    yaxis=dict(
+                        title_text="",  # No axis labels
+                        tickfont=dict(size=10, color="#aaa"),
+                        showline=True,
+                        linecolor="rgba(0,0,0,0.2)",
+                        zeroline=False,
+                        showgrid=False,
+                        ticks="outside",
+                        ticklen=3,
+                    ),
+                    # Sleek Background
+                    plot_bgcolor="#fafafa",  # Very light grey background for a smooth finish
+                    paper_bgcolor="#ffffff",  # Pure white paper background
+                    # Modern Title with Elegant Style
+                    title=dict(
+                        text="t-SNE Visualization of Data",
+                        font=dict(
+                            size=16, color="#222", family="Helvetica, Arial, sans-serif"
+                        ),  # Classy font style
+                        x=0.5,
+                        xanchor="center",
+                        yanchor="top",
+                        pad=dict(t=15),  # Padding to separate the title from the plot
+                    ),
+                )
+
+                # Add hover effects for a smooth user experience
+                tsne.update_traces(
+                    hoverinfo="text+name",
+                    hoverlabel=dict(bgcolor="white", font_size=12, font_family="Arial"),
+                )
+
+                context = {
+                    "tsne": tsne.to_html(),
+                }
+            else:
+                # load plots
+                pca = joblib.load(model_name_path + "/pca.sav")
+                classification_report = joblib.load(
+                    model_name_path + "/classification_report.sav"
+                )
+                # tsne = joblib.load(model_name_path + "/tsne.sav")
+
+                # pipeline path
+                json_path = os.path.join(PIPELINE_PATH, f"{df_name}" + "/pipeline.json")
+                jsonFile = pipeline.PipelineJSON(json_path)
+
+                # load pipeline data
+                # jsonFile = open(json_path, "r")
+                # pipeline_data = json.load(jsonFile)  # data becomes a dictionary
+                # classifier_data = pipeline_data["classifier"][pre_trained_model_name]
+
+                classifier_data = jsonFile.read_from_json(
+                    ["classifier", pre_trained_model_name]
+                )
+                classifier_data_flattened = methods.flatten_dict(classifier_data)
+                classifier_data_df = pd.DataFrame([classifier_data_flattened])
+
+                if dataset_type == "tabular":
+                    feature_importance = joblib.load(
+                        model_name_path + "/feature_importance.sav"
+                    )
+                    context = {
+                        "dataset_type": dataset_type,
+                        "pca": pca.to_html(),
+                        "class_report": classification_report.to_html(),
+                        "feature_importance": feature_importance.to_html(),
+                        "classifier_data": classifier_data_df.to_html(),
+                    }
+                elif dataset_type == "timeseries":
+                    tsne = joblib.load(model_name_path + "/tsne.sav")
+                    context = {
+                        "dataset_type": dataset_type,
+                        "pca": pca.to_html(),
+                        "class_report": classification_report.to_html(),
+                        "tsne": tsne.to_html(),
+                        "classifier_data": classifier_data_df.to_html(),
+                    }          
+    elif action == "delete_pre_trained":
+        
+        df_name = request.session["df_name"]
+        model_name = request.POST.get("model_name")
+        model_name_path = os.path.join(
+            PIPELINE_PATH + f"{df_name}" + "/trained_models/" + model_name
+        )
+        
+        print(model_name_path)
+        
+        excel_file_name_preprocessed_path = os.path.join(
+            PIPELINE_PATH,
+            f"{df_name}" + "/" + df_name + "_preprocessed" + ".csv",
+        )
+        try:
+            # Check if the file exists
+            if os.path.exists(excel_file_name_preprocessed_path):
+                # Delete the file
+                os.remove(excel_file_name_preprocessed_path)
+                # print(f"File '{excel_file_name_preprocessed_path}' has been deleted successfully.")
+            else:
+                print(f"File '{excel_file_name_preprocessed_path}' does not exist.")
+        except Exception as e:
+            print(f"An error occurred while deleting the file: {e}")
+            
+        json_path = os.path.join(PIPELINE_PATH + f"{df_name}" + "/pipeline.json")
+        jsonFile = pipeline.PipelineJSON(json_path)
+        jsonFile.delete_key(["classifier", model_name])
+        
+        methods.remove_dir_and_empty_parent(model_name_path)
+        # load paths
+        # absolute excel_file_preprocessed_path
+
+        if not jsonFile.key_exists("classifier"):
+            # pre trained models do not exist
+            # check if dataset directory exists
+            df_dir = os.path.join(PIPELINE_PATH + f"{df_name}")
+            if not os.path.exists(df_dir):
+                df_name = None
+
+            context = {
+                "df_name": df_name,
+                "available_pretrained_models_info": [],
+            }
+        else:
+            # if it exists
+            # check the section of "classifiers"
+            # folder path
+            available_pretrained_models = jsonFile.read_from_json(
+                ["classifier"]
+            ).keys()
+
+            available_pretrained_models_info = (
+                methods.create_tuple_of_models_text_value(
+                    available_pretrained_models
+                )
+            )
+            context = {
+                "df_name": df_name,
+                "available_pretrained_models_info": available_pretrained_models_info,
+            }
+    return HttpResponse(json.dumps(context), status=status)
\ No newline at end of file
diff --git a/base/handlers/ajaxCounterfactualsHandler.py b/base/handlers/ajaxCounterfactualsHandler.py
new file mode 100644
index 000000000..8ce97890d
--- /dev/null
+++ b/base/handlers/ajaxCounterfactualsHandler.py
@@ -0,0 +1,768 @@
+import base.pipeline as pipeline
+import pickle, os
+import pandas as pd
+import json
+from sklearn.preprocessing import LabelEncoder
+import joblib
+from dict_and_html import *
+from .. import methods
+from ..methods import PIPELINE_PATH
+import math
+import numpy as np
+from .. glacier.src.glacier_compute_counterfactuals import gc_compute_counterfactuals
+import base.pipeline as pipeline
+import concurrent.futures
+import json
+from django.shortcuts import HttpResponse
+
+def handler(action, request):
+    status = 200
+    if action == "reset_graph":
+        model_name = request.session.get("model_name")
+        # dataframe name
+        excel_file_name = request.session.get("df_name")
+        # save the plots for future use
+        # folder path: pipelines/<dataset name>/trained_models/<model_name>/
+        model_name_path = os.path.join(
+            PIPELINE_PATH + f"{excel_file_name}" + "/trained_models/" + model_name
+        )
+
+        model_name_dir_path = os.path.join(PIPELINE_PATH + f"{df_name}")
+
+        tsne = joblib.load(model_name_dir_path + "/tsne.sav")
+        context = {"fig": tsne.to_html()}
+    elif action == "pre_trained":
+        # load pre trained models
+        pre_trained_model_name = request.POST.get("pre_trained")
+        request.session["model_name"] = pre_trained_model_name
+        # dataframe name
+        df_name = request.session.get("df_name")
+
+        if df_name == "upload":
+            df_name = request.session.get("df_name_upload_base_name")
+
+        model_name_path = os.path.join(
+        PIPELINE_PATH + f"{df_name}" + "/trained_models/" + pre_trained_model_name
+        )
+
+        model_name_dir_path = os.path.join(PIPELINE_PATH + f"{df_name}")
+
+        # get the type of the file
+        datasets_types_PipelineJSON_path = os.path.join(
+        PIPELINE_PATH + "/dataset_types_pipeline.json"
+        )
+        datasets_types_pipeline = pipeline.PipelineJSON(
+        datasets_types_PipelineJSON_path
+        )
+        dataset_type = datasets_types_pipeline.read_from_json([df_name])
+
+        if type(dataset_type) is list:
+            dataset_type = dataset_type[0]
+
+        if "url" in request.POST:
+            url = request.POST.get("url")
+            
+            if url == "counterfactuals":
+                # only TSNE
+                tsne = joblib.load(model_name_path + "/tsne.sav")
+
+                # Assuming you already have your fig object created, you can update it like this:
+                # Improved and modern t-SNE visualization
+                tsne.update_layout(
+                    # Modern Legend Design
+                    legend=dict(
+                        x=0.9,
+                        y=0.95,
+                        xanchor="right",
+                        yanchor="top",
+                        bgcolor="rgba(255,255,255,0.8)",  # Light semi-transparent white background
+                        bordercolor="rgba(0,0,0,0.1)",  # Light border for contrast
+                        borderwidth=1,
+                        font=dict(size=12, color="#444"),  # Subtle grey for legend text
+                    ),
+                    # Tight Margins to Focus on the Plot
+                    margin=dict(
+                        l=10, r=10, t=30, b=10
+                    ),  # Very slim margins for a modern look
+                    # Axis Design: Minimalist and Clean
+                    xaxis=dict(
+                        title_text="",  # No axis labels for a clean design
+                        tickfont=dict(
+                            size=10, color="#aaa"
+                        ),  # Light grey for tick labels
+                        showline=True,
+                        linecolor="rgba(0,0,0,0.2)",  # Subtle line color for axis lines
+                        zeroline=False,  # No zero line for a sleek look
+                        showgrid=False,  # Hide grid lines for a minimal appearance
+                        ticks="outside",  # Small ticks outside the axis
+                        ticklen=3,  # Short tick marks for subtlety
+                    ),
+                    yaxis=dict(
+                        title_text="",  # No axis labels
+                        tickfont=dict(size=10, color="#aaa"),
+                        showline=True,
+                        linecolor="rgba(0,0,0,0.2)",
+                        zeroline=False,
+                        showgrid=False,
+                        ticks="outside",
+                        ticklen=3,
+                    ),
+                    # Sleek Background
+                    plot_bgcolor="#fafafa",  # Very light grey background for a smooth finish
+                    paper_bgcolor="#ffffff",  # Pure white paper background
+                    # Modern Title with Elegant Style
+                    title=dict(
+                        text="t-SNE Visualization of Data",
+                        font=dict(
+                            size=16, color="#222", family="Helvetica, Arial, sans-serif"
+                        ),  # Classy font style
+                        x=0.5,
+                        xanchor="center",
+                        yanchor="top",
+                        pad=dict(t=15),  # Padding to separate the title from the plot
+                    ),
+                )
+
+                # Add hover effects for a smooth user experience
+                tsne.update_traces(
+                    hoverinfo="text+name",
+                    hoverlabel=dict(bgcolor="white", font_size=12, font_family="Arial"),
+                )
+
+                context = {
+                    "tsne": tsne.to_html(),
+                }
+            else:
+                # load plots
+                pca = joblib.load(model_name_path + "/pca.sav")
+                classification_report = joblib.load(
+                    model_name_path + "/classification_report.sav"
+                )
+                # tsne = joblib.load(model_name_path + "/tsne.sav")
+
+                # pipeline path
+                json_path = os.path.join(PIPELINE_PATH, f"{df_name}" + "/pipeline.json")
+                jsonFile = pipeline.PipelineJSON(json_path)
+
+                # load pipeline data
+                # jsonFile = open(json_path, "r")
+                # pipeline_data = json.load(jsonFile)  # data becomes a dictionary
+                # classifier_data = pipeline_data["classifier"][pre_trained_model_name]
+
+                classifier_data = jsonFile.read_from_json(
+                    ["classifier", pre_trained_model_name]
+                )
+                classifier_data_flattened = methods.flatten_dict(classifier_data)
+                classifier_data_df = pd.DataFrame([classifier_data_flattened])
+
+                if dataset_type == "tabular":
+                    feature_importance = joblib.load(
+                        model_name_path + "/feature_importance.sav"
+                    )
+                    context = {
+                        "dataset_type": dataset_type,
+                        "pca": pca.to_html(),
+                        "class_report": classification_report.to_html(),
+                        "feature_importance": feature_importance.to_html(),
+                        "classifier_data": classifier_data_df.to_html(),
+                    }
+                elif dataset_type == "timeseries":
+                    tsne = joblib.load(model_name_path + "/tsne.sav")
+                    context = {
+                        "dataset_type": dataset_type,
+                        "pca": pca.to_html(),
+                        "class_report": classification_report.to_html(),
+                        "tsne": tsne.to_html(),
+                        "classifier_data": classifier_data_df.to_html(),
+                    }
+    elif action == "click_graph":
+        # get df used name
+        df_name = request.session.get("df_name")
+        if df_name == "upload": 
+            df_name = request.session.get("df_name_upload_base_name")
+        # get model_name
+        model_name = request.POST.get("model_name")
+
+        # preprocessed_path
+        excel_file_name_preprocessed_path = os.path.join(
+            PIPELINE_PATH + f"{df_name}" + "/" + df_name + "_preprocessed" + ".csv"
+        )
+
+        excel_file_name_path = os.path.join(
+            PIPELINE_PATH + f"{df_name}" + "/" + df_name + ".csv"
+        )
+
+        model_name_path = os.path.join(
+            PIPELINE_PATH + f"{df_name}" + "/trained_models/" + model_name
+        )
+
+        # pipeline path
+        json_path = os.path.join(PIPELINE_PATH, f"{df_name}" + "/pipeline.json")
+
+        # load pipeline data
+        # jsonFile = open(json_path, "r")
+        # pipeline_data = PipelineJSON.load(jsonFile)  # data becomes a dictionary
+        # class_label = pipeline_data["classifier"][model_name]["class_label"]
+        jsonFile = pipeline.PipelineJSON(json_path)
+        class_label = jsonFile.read_from_json(
+            ["classifier", model_name, "class_label"]
+        )
+
+        df = pd.read_csv(excel_file_name_path)
+
+        # Load your saved feature importance from a .sav file
+        feature_importance_df = pd.read_csv(
+            model_name_path + "/feature_importance_df.csv"
+        )
+        # sorted_df = feature_importance_df.sort_values(by="importance", ascending=False)
+
+        # x and y coordinates of the clicked point in tsne
+        x_coord = request.POST["x"]
+        y_coord = request.POST["y"]
+
+        # tsne_projections
+        tsne_projections_path = os.path.join(
+            PIPELINE_PATH
+            + f"{df_name}/"
+            + f"trained_models/{model_name}"
+            + "/tsne_projections.json",
+        )
+
+        # tsne projections of all points (saved during generation of tsne)
+        projections = pd.read_json(tsne_projections_path)
+        projections = projections.values.tolist()
+
+        # projections array is a list of pairs with the (x, y)
+        # [ [], [], [] ... ]
+        # coordinates for a point in tsne. These are actual absolute
+        # coordinates and not SVG.
+        # find the pair of the projection with x and y coordinates matching that of
+        # clicked point coordinates
+        for clicked_id, item in enumerate(projections):
+            if math.isclose(item[0], float(x_coord)) and math.isclose(
+                item[1], float(y_coord)
+            ):
+                break
+
+        # save clicked point projections
+        request.session["clicked_point"] = item
+        # get clicked point row
+        row = df.iloc[[int(clicked_id)]]
+        request.session["cfrow_id"] = clicked_id
+        request.session["cfrow_og"] = row.to_html()
+        context = {
+            "row": row.to_html(index=False),
+            "feature_importance_dict": feature_importance_df.to_dict(orient="records"),
+        }
+    elif action == "cf":
+        # dataframe name
+        df_name = request.session.get("df_name")
+        if df_name == "upload":
+            df_name = request.session.get("df_name_upload_base_name")
+
+        # preprocessed_path
+        excel_file_name_preprocessed_path = os.path.join(
+            PIPELINE_PATH + f"{df_name}" + "/" + df_name + "_preprocessed" + ".csv"
+        )
+
+        excel_file_name_path = os.path.join(
+            PIPELINE_PATH + f"{df_name}" + "/" + df_name + ".csv"
+        )
+        # which model is being used during that session
+        model_name = request.POST.get("model_name")
+        # path of used model
+        model_name_path = os.path.join(
+            PIPELINE_PATH + f"{df_name}/" + "trained_models/" + f"{model_name}/"
+        )
+        model_name_dir_path = os.path.join(PIPELINE_PATH + f"{df_name}")
+
+        # read preprocessed data
+        if os.path.exists(excel_file_name_preprocessed_path):
+            df = pd.read_csv(excel_file_name_preprocessed_path)
+        else:
+            df = pd.read_csv(excel_file_name_path)
+
+        datasets_types_PipelineJSON_path = os.path.join(
+            PIPELINE_PATH + "/dataset_types_pipeline.json"
+        )
+        datasets_types_pipeline = pipeline.PipelineJSON(
+            datasets_types_PipelineJSON_path
+        )
+        dataset_type = datasets_types_pipeline.read_from_json([df_name])
+
+        if type(dataset_type) is list:
+            dataset_type = dataset_type[0]
+
+        df_id = request.session.get("cfrow_id")
+        if dataset_type == "tabular":
+
+            # get row
+            features_to_vary = json.loads(request.POST.get("features_to_vary"))
+
+            row = df.iloc[[int(df_id)]]
+
+            # not preprocessed
+            notpre_df = pd.read_csv(excel_file_name_path)
+            notpre_row = notpre_df.iloc[[int(df_id)]]
+
+            # if feature_to_vary has a categorical column then I cannot just
+            # pass that to dice since the trained model does not contain the
+            # categorical column but the one-hot-encoded sub-columns
+            features_to_vary = methods.update_column_list_with_one_hot_columns(
+                notpre_df, df, features_to_vary
+            )
+
+            # pipeline path
+            json_path = os.path.join(PIPELINE_PATH, f"{df_name}" + "/pipeline.json")
+
+            # load pipeline data
+            jsonFile = pipeline.PipelineJSON(json_path)
+            class_label = jsonFile.read_from_json(
+                ["classifier", model_name, "class_label"]
+            )  # data becomes a dictionary
+
+            # number of counterfactuals
+            # (TBD) input field value as parameter
+            # in ajax
+            num_counterfactuals = 5
+            le = LabelEncoder()
+            notpre_df[class_label] = le.fit_transform(notpre_df[class_label])
+
+            continuous_features = methods.get_continuous_features(df)
+            non_continuous_features = methods.get_non_continuous_features(df)
+
+            # load used classifier
+            clf = joblib.load(model_name_path + model_name + ".sav")
+
+            try:
+                # Set up the executor to run the function in a separate thread
+                with concurrent.futures.ThreadPoolExecutor() as executor:
+                    # Submit the function to the executor
+                    future = executor.submit(
+                        methods.counterfactuals,
+                        row,
+                        clf,
+                        df,
+                        class_label,
+                        continuous_features,
+                        num_counterfactuals,
+                        features_to_vary,
+                    )
+                    # Wait for the result with a timeout of 10 seconds
+                    counterfactuals = future.result(timeout=10)
+                    print("Counterfactuals computed successfully!")
+            except concurrent.futures.TimeoutError:
+                message = (
+                    "It seems like it took more than expected. Refresh and try again..."
+                )
+                context = {"message": message}
+
+            if counterfactuals:
+                cf_df = counterfactuals[0].final_cfs_df
+                counterfactuals[0].final_cfs_df.to_csv(
+                    model_name_path + "counterfactuals.csv", index=False
+                )
+
+                # get coordinates of the clicked point (saved during 'click' event)
+                clicked_point = request.session.get("clicked_point")
+                clicked_point_df = pd.DataFrame(
+                    {
+                        "0": clicked_point[0],
+                        "1": clicked_point[1],
+                        f"{class_label}": row[class_label].astype(str),
+                    }
+                )
+
+                # tSNE
+                cf_df = pd.read_csv(model_name_path + "counterfactuals.csv")
+                model_name_dir_path = os.path.join(PIPELINE_PATH + f"{df_name}")
+                tsne_path_to_augment = model_name_path + "tsne.sav"
+
+                tsne = methods.generateAugmentedTSNE(
+                    df,
+                    cf_df,
+                    num_counterfactuals,
+                    clicked_point_df,
+                    tsne_path_to_augment,
+                    class_label,
+                )
+
+                tsne.update_layout(
+                    # Modern Legend Design
+                    legend=dict(
+                        x=0.85,
+                        y=0.95,
+                        xanchor="right",
+                        yanchor="top",
+                        bgcolor="rgba(0,0,0,0.05)",  # Transparent black background for a sleek look
+                        bordercolor="rgba(0,0,0,0.1)",  # Soft border for separation
+                        borderwidth=1,
+                        font=dict(
+                            size=12, color="#333"
+                        ),  # Modern grey font color for text
+                    ),
+                    # Tight Margins for a Focused Plot Area
+                    margin=dict(
+                        l=20, r=20, t=40, b=40
+                    ),  # Reduced margins for a cleaner look
+                    # Axis Titles and Labels: Minimalist Design
+                    xaxis=dict(
+                        title_font=dict(
+                            size=14, color="#555"
+                        ),  # Medium grey color for axis title
+                        tickfont=dict(
+                            size=11, color="#777"
+                        ),  # Light grey color for tick labels
+                        showline=True,
+                        linecolor="rgba(0,0,0,0.15)",  # Subtle line color for axis lines
+                        zeroline=False,  # Hide the zero line for a cleaner design
+                        showgrid=False,  # No grid lines for a modern look
+                    ),
+                    yaxis=dict(
+                        title_font=dict(size=14, color="#555"),
+                        tickfont=dict(size=11, color="#777"),
+                        showline=True,
+                        linecolor="rgba(0,0,0,0.15)",
+                        zeroline=False,
+                        showgrid=False,
+                    ),
+                    # Sleek Background Design
+                    plot_bgcolor="white",  # Crisp white background for a modern touch
+                    paper_bgcolor="white",  # Ensure the entire background is uniform
+                    # Title: Modern Font and Centered
+                    title=dict(
+                        text="t-SNE Visualization of Data",
+                        font=dict(
+                            size=18, color="#333", family="Arial, sans-serif"
+                        ),  # Modern font style
+                        x=0.5,
+                        xanchor="center",
+                        yanchor="top",
+                        pad=dict(t=10),  # Padding to give the title breathing space
+                    ),
+                )
+
+                pickle.dump(tsne, open(model_name_path + "tsne_cfs.sav", "wb"))
+
+                context = {
+                    "dataset_type": dataset_type,
+                    "model_name": model_name,
+                    "tsne": tsne.to_html(),
+                    "num_counterfactuals": num_counterfactuals,
+                    "default_counterfactual": "1",
+                    "clicked_point": notpre_row.to_html(),
+                    "counterfactual": cf_df.iloc[[1]].to_html(),
+                }
+
+            else:
+                context = {
+                    "dataset_type": dataset_type,
+                    "model_name": model_name,
+                    "message": "Please try again with different features.",
+                }
+        elif dataset_type == "timeseries":
+            model_name = request.POST["model_name"]
+            model_name_path = os.path.join(
+                PIPELINE_PATH + f"{df_name}/" + "trained_models/" + f"{model_name}/"
+            )
+            path = model_name_path
+            if model_name == "glacier":
+                constraint = request.POST["constraint"]
+                path = os.path.join(
+                    PIPELINE_PATH
+                    + f"{df_name}/"
+                    + "trained_models/"
+                    + f"{model_name}/"
+                    + f"{constraint}/"
+                )
+
+            X_test_path = os.path.join(model_name_path + "X_test.csv")
+            y_test_path = os.path.join(model_name_path + "y_test.npy")
+            y_pred_path = os.path.join(path + "y_pred.npy")
+            X_cf_path = os.path.join(path + "X_cf.npy")
+            cf_pred_path = os.path.join(path + "cf_pred.npy")
+
+            X_test = pd.read_csv(X_test_path)
+            y_test = np.load(y_test_path)
+            y_pred = np.load(y_pred_path)
+            X_cf = np.load(X_cf_path)
+            cf_pred = np.load(cf_pred_path)
+
+            if model_name != "glacier":
+                scaler = joblib.load(model_name_path + "/min_max_scaler.sav")
+                X_test = pd.DataFrame(scaler.inverse_transform(X_test))
+                X_cf = scaler.inverse_transform(X_cf)
+
+            fig = methods.ecg_plot_counterfactuals(
+                int(df_id), X_test, y_test, y_pred, X_cf, cf_pred
+            )
+
+            context = {
+                "df_name": df_name,
+                "fig": fig.to_html(),
+                "dataset_type": dataset_type,
+            }
+    elif action == "compute_cf":
+        model_name = request.POST.get("model_name")
+        if model_name == "glacier":
+            constraint_type = request.POST.get("constraint")
+            w_value = request.POST.get("w_value")
+            df_name = request.session.get("df_name")
+
+            model_name_path = os.path.join(
+                PIPELINE_PATH + f"{df_name}/" + "trained_models/" + f"{model_name}/"
+            )
+            model_name_path_constraint = model_name_path + f"{constraint_type}/"
+            if not os.path.exists(model_name_path_constraint):
+                os.makedirs(model_name_path_constraint)
+
+            # https://github.com/wildboar-foundation/wildboar/blob/master/docs/guide/explain/counterfactuals.rst#id27
+            classifier = joblib.load(model_name_path + "/classifier.sav")
+
+            # pipeline path
+            json_path = os.path.join(PIPELINE_PATH, f"{df_name}" + "/pipeline.json")
+            # load pipeline data
+            jsonFile = pipeline.PipelineJSON(json_path)
+            autoencoder = jsonFile.read_from_json(
+                ["classifier", model_name, "autoencoder"]
+            )
+
+            experiment_dict = {"constraint": constraint_type, "w_value": w_value}
+
+            # if "experiments" in pipeline_data["classifier"][model_name]:
+            #     # if there exists key with value "experiments"
+            #     keys = pipeline_data["classifier"][model_name]["experiments"].keys()
+            #     last_key_int = int(list(keys)[-1])
+            #     last_key_int_incr_str = str(last_key_int + 1)
+            # else:
+            #     last_key_int_incr_str = "0"
+            #     experiment_key_dict = {"experiments": {last_key_int_incr_str: {}}}
+            #     pipeline_data["classifier"][model_name].update(experiment_key_dict)
+
+            # outter_dict = {last_key_int_incr_str: experiment_dict}
+            # pipeline_data["classifier"][model_name]["experiments"].update(outter_dict)
+
+            if jsonFile.key_exists("experiments"):
+                keys = jsonFile.read_from_json(
+                    ["classifier", model_name, "experiments"]
+                ).keys()
+                last_key_int = int(list(keys)[-1])
+                last_key_int_incr_str = str(last_key_int + 1)
+            else:
+                last_key_int_incr_str = "0"
+                experiment_key_dict = {"experiments": {last_key_int_incr_str: {}}}
+                jsonFile.update_json(
+                    ["classifier", model_name], experiment_key_dict
+                )
+
+            outter_dict = {last_key_int_incr_str: experiment_dict}
+            jsonFile.update_json(
+                ["classifier", model_name, "experiments"], outter_dict
+            )
+
+            if autoencoder == "Yes":
+                autoencoder = joblib.load(model_name_path + "/autoencoder.sav")
+            else:
+                autoencoder = None
+
+            gc_compute_counterfactuals(
+                model_name_path,
+                model_name_path_constraint,
+                constraint_type,
+                [0.0001],
+                float(w_value),
+                0.5,
+                classifier,
+                autoencoder,
+            )
+            path = model_name_path_constraint
+            context = {"experiment_dict": experiment_dict}
+    elif action == "counterfactual_select":
+
+        # if <select> element is used, and a specific counterfactual
+        # is inquired to be demonstrated:
+        df_name = request.session.get("df_name")
+        df_name = request.session.get("df_name")
+        if df_name == "upload":
+            df_name = request.session.get("df_name_upload_base_name")
+
+        model_name = request.session.get("model_name")
+        model_name_path = os.path.join(
+            PIPELINE_PATH + f"{df_name}" + "/trained_models/" + model_name
+        )
+
+        excel_file_name_path = os.path.join(
+            PIPELINE_PATH + f"{df_name}" + "/" + df_name + ".csv"
+        )
+
+        # pipeline path
+        json_path = os.path.join(PIPELINE_PATH, f"{df_name}" + "/pipeline.json")
+        # load pipeline data
+        jsonFile = pipeline.PipelineJSON(json_path)
+
+        class_label = jsonFile.read_from_json(
+            ["classifier", model_name, "class_label"]
+        )
+
+        # decode counterfactual to original values
+        preprocessing_list = jsonFile.read_from_json(
+            ["classifier", model_name, "preprocessing"]
+        )
+
+        df = pd.read_csv(excel_file_name_path)
+        cf_df = pd.read_csv(model_name_path + "/counterfactuals.csv")
+        cf_id = request.POST["cf_id"]
+        row = cf_df.iloc[[int(cf_id)]]
+
+        if "id" in df.columns:
+            df = df.drop("id", axis=1)
+
+        dec_row = methods.decode_cf(
+            df, row, class_label, model_name_path, preprocessing_list
+        )
+
+        fig = joblib.load(model_name_path + "/tsne_cfs.sav")
+
+        # tsne stores data for each class in different data[]
+        # index.
+        # data[0] is class A
+        # data[1] is class B
+        # ...
+        # data[n-2] is counterfactuals
+        # data[n-1] is clicked point
+
+        fig_data_array_length = len(fig.data)
+        for i in range(fig_data_array_length - 2):
+            fig.data[i].update(
+                opacity=0.3,
+            )
+
+        # last one, data[n-1], contains clicked point
+        l = fig.data[fig_data_array_length - 1]
+        clicked_id = -1
+        for clicked_id, item in enumerate(list(zip(l.x, l.y))):
+            if math.isclose(
+                item[0], request.session.get("clicked_point")[0]
+            ) and math.isclose(item[1], request.session.get("clicked_point")[1]):
+                break
+
+        # data[n-2] contains counterfactuals
+        fig.data[fig_data_array_length - 2].update(
+            selectedpoints=[int(cf_id)],
+            unselected=dict(
+                marker=dict(
+                    opacity=0.3,
+                )
+            ),
+        )
+
+        fig.data[fig_data_array_length - 1].update(
+            selectedpoints=[clicked_id],
+            unselected=dict(
+                marker=dict(
+                    opacity=0.3,
+                )
+            ),
+        )
+
+        if "id" in df.columns:
+            df = df.drop("id", axis=1)
+
+        # order the columns
+        dec_row = dec_row[df.columns]
+        clicked_point_row_id = request.session.get("cfrow_id")
+
+        # return only the differences
+        dec_row = dec_row.reset_index(drop=True)
+        df2 = df.iloc[[int(clicked_point_row_id)]].reset_index(drop=True)
+        difference = dec_row.loc[
+            :,
+            [
+                methods.compare_values(dec_row[col].iloc[0], df2[col].iloc[0])
+                for col in dec_row.columns
+            ],
+        ]
+
+        merged_df = pd.concat([df2[difference.columns], difference], ignore_index=True)
+
+        context = {
+            "row": merged_df.to_html(index=False),
+            "fig": fig.to_html(),
+        }
+    elif action == "class_label_selection":
+
+        df_name = request.session.get("df_name")
+
+        if df_name == "upload":
+            df_name = request.session["df_name_upload_base_name"]
+
+        datasets_types_PipelineJSON_path = os.path.join(
+            PIPELINE_PATH + "/dataset_types_pipeline.json"
+        )
+
+        dataset_type_json = pipeline.PipelineJSON(datasets_types_PipelineJSON_path)
+
+        dataset_type = dataset_type_json.read_from_json([df_name])
+        
+        if isinstance(dataset_type, list):
+            dataset_type = dataset_type[0]
+            
+        # preprocessed_path
+        excel_file_name_preprocessed_path = os.path.join(
+            PIPELINE_PATH + f"{df_name}" + "/" + df_name + "_preprocessed" + ".csv"
+        )
+
+        excel_file_name_path = os.path.join(
+            PIPELINE_PATH + f"{df_name}" + "/" + df_name + ".csv"
+        )
+
+        # which model is being used during that session
+        model_name = request.POST.get("model_name")
+
+        model_name_path = os.path.join(
+            PIPELINE_PATH + f"{df_name}" + "/trained_models/" + model_name
+        )
+        
+        X_test_path = os.path.join(
+            PIPELINE_PATH
+            + f"{df_name}"
+            + "/trained_models"
+            + f"/{model_name}"
+            + "/X_test.csv"
+        )
+        y_test_path = os.path.join(
+            PIPELINE_PATH
+            + f"{df_name}"
+            + "/trained_models"
+            + f"/{model_name}"
+            + "/y_test.npy"
+        )
+
+        X_test = pd.read_csv(X_test_path)
+        y_test = np.load(y_test_path)
+
+        if model_name != "glacier":
+            scaler = joblib.load(model_name_path + "/min_max_scaler.sav")
+            X_test = pd.DataFrame(scaler.inverse_transform(X_test))
+                
+        if dataset_type == "timeseries":
+            class_label = request.POST.get("class_label")
+            cfrow_id = request.POST.get("cfrow_id")
+
+            class_label = (
+                int(class_label)
+                if class_label.isdigit()
+                else (
+                    float(class_label)
+                    if class_label.replace(".", "", 1).isdigit()
+                    else class_label
+                )
+            )
+
+            fig, index = methods.get_ecg_entry(
+                X_test, y_test, int(cfrow_id), class_label
+            )
+            request.session["cfrow_id"] = index
+            request.session["class_label"] = class_label
+            context = {"fig": fig.to_html(), "dataset_type": dataset_type}
+    return HttpResponse(json.dumps(context), status=status)
\ No newline at end of file
diff --git a/base/handlers/ajaxHomeHandler.py b/base/handlers/ajaxHomeHandler.py
new file mode 100644
index 000000000..adcab037a
--- /dev/null
+++ b/base/handlers/ajaxHomeHandler.py
@@ -0,0 +1,437 @@
+import base.pipeline as pipeline
+import os
+from dict_and_html import *
+from .. import methods
+from ..methods import PIPELINE_PATH
+from django.core.files.storage import FileSystemStorage
+import random
+import base.pipeline as pipeline
+import shutil
+import json
+from django.shortcuts import HttpResponse
+
+def handler(action, request):
+    status = 200
+    if action == "upload_dataset":
+
+        uploaded_file = request.FILES["excel_file"]  # Get the file from request.FILES
+        dataset_type = request.POST.get("dataset_type")
+
+        # action to add dataset when from radio button click
+        # add name of used dataframe in session for future use
+        request.session["df_name"] = "upload"
+        name = uploaded_file.name
+
+        # Split the name and extension
+        base_name, extension = os.path.splitext(name)
+        request.session["df_name_upload_base_name"] = base_name
+        request.session["df_name_upload_extension"] = extension
+
+        df_name = base_name
+
+        df_name_path = os.path.join(
+            PIPELINE_PATH + f"{base_name}",
+        )
+
+        if not os.path.exists(df_name_path):
+            os.makedirs(df_name_path)
+
+        fs = FileSystemStorage()  # FileSystemStorage to save the file
+
+        # Save the file with the new filename
+        fs = FileSystemStorage(location=df_name_path)
+        filename = fs.save(uploaded_file.name, uploaded_file)  # Save file
+
+        request.session["excel_file_name"] = df_name_path
+
+        excel_file_name_path = os.path.join(PIPELINE_PATH + f"{base_name}" + "/" + name)
+
+        df = methods.get_dataframe(excel_file_name_path)
+
+        ## update the datasets_types json file
+        datasets_types_PipelineJSON_path = os.path.join(
+            PIPELINE_PATH + "dataset_types_pipeline.json"
+        )
+        jsonFile = pipeline.PipelineJSON(datasets_types_PipelineJSON_path)
+
+        # with open(datasets_types_PipelineJSON_path, "r") as jsonFile:
+        #     datasets_types_PipelineJSON = pipeline.load(
+        #         jsonFile
+        #     )  # data becomes a dictionary
+
+        jsonFile.append_to_json({df_name: [dataset_type, "uploaded"]})
+        dataset_type = jsonFile.read_from_json([df_name])[0]
+        uploaded_files = jsonFile.get_keys_with_value("uploaded")
+
+        # datasets_types_PipelineJSON[df_name] = dataset_type
+        # with open(datasets_types_PipelineJSON_path, "w") as file:
+        #     pipeline.dump(
+        #         datasets_types_PipelineJSON, file, indent=4
+        #     )  # Write with pretty print (indent=4)
+
+        if df.columns.str.contains(" ").any():
+            df.columns = df.columns.str.replace(" ", "_")
+            # if columns contain space
+            os.remove(excel_file_name_path)
+            df.to_csv(excel_file_name_path, index=None)
+            df = methods.get_dataframe(excel_file_name_path)
+
+        if "id" in df.columns:
+            df.drop(["id"], axis=1, inplace=True)
+            df.to_csv(excel_file_name_path, index=False)
+
+        # if dataset_type == "tabular":
+        #     # tabular datasets
+        #     features = df.columns
+        #     feature1 = df.columns[3]
+        #     feature2 = df.columns[2]
+
+        #     labels = list(df.select_dtypes(include=["object", "category"]).columns)
+        #     # Find binary columns (columns with only two unique values, including numerics)
+        #     binary_columns = [col for col in df.columns if df[col].nunique() == 2]
+
+        #     # Combine categorical and binary columns into one list
+        #     labels = list(set(labels + binary_columns))
+
+        #     label = random.choice(labels)
+        #     fig = methods.stats(
+        #         excel_file_name_path,
+        #         dataset_type,
+        #         None,
+        #         None,
+        #         feature1,
+        #         feature2,
+        #         label,
+        #         df_name,
+        #     )
+
+        #     # tabular dataset
+        #     request.session["data_to_display"] = df[:10].to_html()
+        #     request.session["features"] = list(features)
+        #     request.session["feature1"] = feature1
+        #     request.session["feature2"] = feature2
+        #     request.session["labels"] = list(labels)
+        #     request.session["curlabel"] = label
+        #     request.session["fig"] = fig
+
+        #     context = {
+        #         "dataset_type": dataset_type,
+        #         "data_to_display": df[:10].to_html(),
+        #         "fig": fig,
+        #         "features": list(features),  # error if not a list
+        #         "feature1": feature1,
+        #         "feature2": feature2,
+        #         "labels": list(labels),
+        #         "curlabel": label,
+        #         "df_name": request.session["df_name"],
+        #     }
+        # elif dataset_type == "timeseries":
+        #     fig, fig1 = methods.stats(excel_file_name_path, dataset_type)
+        #     request.session["fig"] = fig
+        #     request.session["fig1"] = fig1
+        #     context = {
+        #         "dataset_type": dataset_type,
+        #         "df_name": df_name,
+        #         "fig": fig,
+        #         "fig1": fig1,
+        #     }
+
+        context = {"dataset_type": dataset_type, "df_name": df_name}
+        context.update({"uploaded_files": uploaded_files})
+        
+        if dataset_type == "timeseries":
+            target_labels = list(df.iloc[:, -1].unique())
+            context.update({"target_labels": target_labels})
+            
+        request.session["context"] = context
+    elif action == "delete_uploaded_file":
+        dataset_name = request.POST.get("dataset_name")
+        dataset_path = os.path.join(PIPELINE_PATH + f"/{dataset_name}")
+
+        # pipeline path
+        datasets_types_pipeline_path = os.path.join(
+            PIPELINE_PATH + "/dataset_types_pipeline.json"
+        )
+        # load pipeline data
+        datasets_types_pipeline = pipeline.PipelineJSON(datasets_types_pipeline_path)
+        datasets_types_pipeline.delete_key([dataset_name])
+
+        request.FILES["excel_file"] = None
+        request.session["df_name"] = None
+
+        # check if there exist uploaded files
+        uploaded_files = datasets_types_pipeline.get_keys_with_value(
+            "uploaded"
+        )
+        if uploaded_files == []:
+            uploaded_files = None
+        try:
+            shutil.rmtree(dataset_path)
+        except Exception as error:
+            print(error)
+
+        context = {"uploaded_files": uploaded_files}
+    elif action == "dataset" or action == "uploaded_datasets":
+
+        # action to add dataset when from radio button click
+        name = request.POST.get("df_name")
+        request.session["df_name"] = name
+
+        # if name == "upload":
+        #     name = request.session.get("df_name_upload_base_name")
+
+        if action == "dataset" and name == "upload":
+            request.session["upload"] = 1
+            context = {"upload": 1}
+        else:
+
+            if name == "timeseries":
+                name = request.session.get("df_name")
+
+            excel_file_name_path = os.path.join(
+                PIPELINE_PATH + f"{name}" + "/" + name + ".csv",
+            )
+
+            datasets_types_PipelineJSON_path = os.path.join(
+                PIPELINE_PATH + "/dataset_types_pipeline.json"
+            )
+            datasets_types_PipelineJSON = pipeline.PipelineJSON(
+                datasets_types_PipelineJSON_path
+            )
+            dataset_type = datasets_types_PipelineJSON.read_from_json([name])
+            uploaded_files = datasets_types_PipelineJSON.get_keys_with_value(
+                "uploaded"
+            )
+
+            if request.POST.get("df_name") == "upload" or action == "uploaded_datasets":
+                if type(dataset_type) is list:
+                    dataset_type = dataset_type[0]
+
+            if request.POST.get("df_name") != "upload" or action == "uploaded_datasets":
+                if os.path.exists(excel_file_name_path):
+                    df = methods.get_dataframe(excel_file_name_path)
+                    df.columns = df.columns.str.replace(" ", "_")
+                    request.session["excel_file_name"] = excel_file_name_path
+
+                    json_path = os.path.join(
+                        PIPELINE_PATH + f"{name}" + "/pipeline.json"
+                    )
+                    if not os.path.exists(json_path):
+                        PipelineJSON = pipeline.PipelineJSON(json_path)
+                        PipelineJSON.append_to_json({"name": name})
+
+                    if "tabular" == dataset_type:
+
+                        if "id" in df.columns:
+                            df.drop(["id"], axis=1, inplace=True)
+                            df.to_csv(excel_file_name_path, index=False)
+
+                        # tabular datasets
+                        features = df.columns
+                        feature1 = df.columns[3]
+                        feature2 = df.columns[2]
+                        label = ""
+
+                        labels = list(
+                            df.select_dtypes(include=["object", "category"]).columns
+                        )
+                        # Find binary columns (columns with only two unique values, including numerics)
+                        binary_columns = [
+                            col for col in df.columns if df[col].nunique() == 2
+                        ]
+
+                        # Combine categorical and binary columns into one list
+                        labels = list(set(labels + binary_columns))
+                        label = random.choice(labels)
+                        fig = methods.stats(
+                            excel_file_name_path,
+                            dataset_type,
+                            feature1=feature1,
+                            feature2=feature2,
+                            label=label,
+                        )
+
+                        # tabular dataset
+                        request.session["data_to_display"] = df[:10].to_html()
+                        request.session["features"] = list(features)
+                        request.session["feature1"] = feature1
+                        request.session["feature2"] = feature2
+                        request.session["labels"] = list(labels)
+                        request.session["curlabel"] = label
+                        request.session["fig"] = fig
+
+                        context = {
+                            "dataset_type": dataset_type,
+                            "data_to_display": df[:10].to_html(),
+                            "fig": fig,
+                            "features": list(features),  # error if not a list
+                            "feature1": feature1,
+                            "feature2": feature2,
+                            "labels": list(labels),
+                            "curlabel": label,
+                            "uploaded_files": list(uploaded_files),
+                        }
+                    elif dataset_type == "timeseries":
+
+                        json_path = os.path.join(
+                            PIPELINE_PATH, f"{name}" + "/pipeline.json"
+                        )
+                        jsonFile = pipeline.PipelineJSON(json_path)
+
+                        pos = jsonFile.read_from_json(["pos"])
+                        neg = jsonFile.read_from_json(["neg"])
+
+                        fig, fig1 = methods.stats(
+                            excel_file_name_path,
+                            dataset_type,
+                            int(pos),
+                            int(neg),
+                            None,
+                            None,
+                            None,
+                            name=name,
+                        )
+                        # timeseries
+                        request.session["fig"] = fig
+                        request.session["fig1"] = fig1
+                        context = {
+                            "fig": fig,
+                            "fig1": fig1,
+                            "dataset_type": dataset_type,
+                        }
+                else:
+                    context = {"uploaded_files": list(uploaded_files)}
+            else:
+                context = {}
+                
+            if (
+                action == "uploaded_datasets"
+                and "upload" in request.session
+                and request.session["upload"] == 1
+            ):
+                request.session["upload"] = 1
+                context.update({"upload": 1, "df_name": name})
+                print(name)
+            else:
+                request.session["upload"] = 0
+    elif action == "dataset_charts":
+        df_name = request.POST.get("df_name")
+        request.session["df_name"] = df_name
+        context = {}
+    elif action == "select_class_labels_for_uploaded_timeseries":
+        name = request.session["df_name"]
+        
+        if name == "upload":
+            name = request.session["df_name_upload_base_name"]
+    
+        pos = request.POST.get("positive_label")
+        neg = request.POST.get("negative_label")
+        
+        json_path = os.path.join(PIPELINE_PATH, f"{name}" + "/pipeline.json")
+        jsonFile = pipeline.PipelineJSON(json_path)
+        
+        jsonFile.append_to_json({"name": name})
+        jsonFile.append_to_json({"pos": pos})
+        jsonFile.append_to_json({"neg": neg})
+        
+        context = {}
+    elif action == "timeseries-dataset": 
+
+        # action to add dataset when from radio button click
+        name = request.POST.get("timeseries_dataset")
+
+        # add name of used dataframe in session for future use
+        request.session["df_name"] = name
+        excel_file_name_path = os.path.join(
+            PIPELINE_PATH + f"{name}" + "/" + name + ".csv",
+        )
+        datasets_types_PipelineJSON_path = os.path.join(
+            PIPELINE_PATH + "/dataset_types_pipeline.json"
+        )
+        datasets_types_PipelineJSON = pipeline.PipelineJSON(
+            datasets_types_PipelineJSON_path
+        )
+        if os.path.exists(excel_file_name_path):
+
+            dataset_type = datasets_types_PipelineJSON.read_from_json([name])
+
+            df = methods.get_dataframe(excel_file_name_path)
+            df.columns = df.columns.str.replace(" ", "_")
+            request.session["excel_file_name"] = excel_file_name_path
+
+            # find the available pre trained datasets
+            # check the pipeline file
+            json_path = os.path.join(PIPELINE_PATH, f"{name}" + "/pipeline.json")
+            jsonFile = pipeline.PipelineJSON(json_path)
+
+            preprocessing_info = {"name": name}
+            dataset_camel = methods.convert_to_camel_case(name)
+            if "Ecg" in dataset_camel:
+                dataset_camel = dataset_camel.replace("Ecg", "ECG")
+            experiment = methods.fetch_line_by_dataset(
+                PIPELINE_PATH + "/glacier_experiments.txt",
+                dataset_camel,
+            )
+            if experiment is not None:
+                stripped_arguments = methods.extract_arguments_from_line(experiment)
+                
+            indices_to_keys = {
+                1: "pos",
+                2: "neg",
+            }
+
+            # Create a dictionary by fetching items from the list at the specified indices
+            inner_dict = {
+                key: stripped_arguments[index] for index, key in indices_to_keys.items()
+            }
+            preprocessing_info.update(inner_dict)
+            jsonFile.append_to_json(preprocessing_info)
+
+            pos = inner_dict["pos"]
+            neg = inner_dict["neg"]
+            fig, fig1 = methods.stats(
+                excel_file_name_path, dataset_type, int(pos), int(neg), name=name
+            )
+            # timeseries
+            request.session["fig"] = fig
+            request.session["fig1"] = fig1
+            context = {"fig": fig, "fig1": fig1, "dataset_type": dataset_type}
+        else:
+            context = {}
+    elif action == "stat":
+
+        name = request.session.get("df_name")
+        datasets_types_PipelineJSON_path = os.path.join(
+            PIPELINE_PATH + "/dataset_types_pipeline.json"
+        )
+        jsonFile = pipeline.PipelineJSON(datasets_types_PipelineJSON_path)
+        dataset_type = jsonFile.read_from_json([name])
+
+        if type(dataset_type) is list:
+            dataset_type = dataset_type[0]
+
+        file_path = os.path.join(
+            PIPELINE_PATH + f"{name}" + "/" + name + ".csv",
+        )
+        if dataset_type == "tabular":
+            feature1 = request.POST.get("feature1")
+            feature2 = request.POST.get("feature2")
+            label = request.POST.get("label")
+        else:
+            feature1 = request.POST.get("feature1")
+            feature2 = []
+            label = []
+
+        fig = methods.stats(
+            file_path,
+            dataset_type,
+            None,
+            None,
+            feature1=feature1,
+            feature2=feature2,
+            label=label,
+        )
+        context = {
+            "fig": fig,
+        }
+    return HttpResponse(json.dumps(context), status=status)
\ No newline at end of file
diff --git a/base/handlers/ajaxTrainHandler.py b/base/handlers/ajaxTrainHandler.py
new file mode 100644
index 000000000..38dc1d782
--- /dev/null
+++ b/base/handlers/ajaxTrainHandler.py
@@ -0,0 +1,464 @@
+import base.pipeline as pipeline
+import pickle, os
+import pandas as pd
+import json
+from sklearn.preprocessing import LabelEncoder
+from dict_and_html import *
+from .. import methods
+from ..methods import PIPELINE_PATH
+import numpy as np
+from collections import defaultdict
+import base.pipeline as pipeline
+import json
+from django.shortcuts import HttpResponse
+
+def handler(action, request):
+    status = 200
+    if action == "train":
+        # train a new model
+        # parameters sent via ajax
+        model_name = request.POST.get("model_name")
+        df_name = request.session.get("df_name")
+
+        # dataframe name
+        if df_name == "upload":
+            df_name = request.session.get("df_name_upload_base_name")
+
+        request.session["model_name"] = model_name
+        test_set_ratio = ""
+        if "test_set_ratio" in request.POST:
+            test_set_ratio = request.POST.get("test_set_ratio")
+
+        datasets_types_PipelineJSON_path = os.path.join(
+            PIPELINE_PATH + "/dataset_types_pipeline.json"
+        )
+        jsonFile = pipeline.PipelineJSON(datasets_types_PipelineJSON_path)
+        dataset_type = jsonFile.read_from_json([df_name])
+
+        if type(dataset_type) is list:
+            dataset_type = dataset_type[0]
+
+        if "array_preprocessing" in request.POST:
+            array_preprocessing = request.POST.get("array_preprocessing")
+
+        if dataset_type == "tabular":
+            class_label = request.POST.get("class_label")
+            preprocessing_info = {
+                "preprocessing": array_preprocessing,
+                "test_set_ratio": test_set_ratio,
+                "explainability": {"technique": "dice"},
+                "class_label": class_label,
+            }
+        elif dataset_type == "timeseries":
+            if model_name != "glacier":
+                preprocessing_info = {
+                    "preprocessing": array_preprocessing,
+                    "test_set_ratio": test_set_ratio,
+                    "explainability": {"technique": model_name},
+                }
+            else:
+                # Path to the Bash script
+                autoencoder = request.POST.get("autoencoder")
+                preprocessing_info = {
+                    "autoencoder": autoencoder,
+                    "explainability": {"technique": model_name},
+                }
+
+        # absolute excel_file_name_path
+        excel_file_name_path = os.path.join(
+            PIPELINE_PATH + f"{df_name}" + "/" + df_name + ".csv"
+        )
+
+        # load paths
+        # absolute excel_file_preprocessed_path
+        excel_file_name_preprocessed_path = os.path.join(
+            PIPELINE_PATH,
+            f"{df_name}" + "/" + df_name + "_preprocessed" + ".csv",
+        )
+
+        json_path = os.path.join(PIPELINE_PATH + f"{df_name}" + "/pipeline.json")
+        jsonFile = pipeline.PipelineJSON(json_path)
+        # save the plots for future use
+        # folder path: pipelines/<dataset name>/trained_models/<model_name>/
+
+        model_name_path = os.path.join(
+            PIPELINE_PATH + f"{df_name}" + "/trained_models/" + model_name
+        )
+
+        model_name_dir_path = os.path.join(PIPELINE_PATH + f"{df_name}")
+
+        if os.path.exists(excel_file_name_preprocessed_path) == True:
+            # if preprocessed_file exists
+            # delete it and do preprocessing again
+            # maybe should optimize it for cases
+            # where the preprocessing is the same with
+            # the one applited on the existing file
+            os.remove(excel_file_name_preprocessed_path)
+
+        # generate filename
+        idx = excel_file_name_path.index(".")
+        excel_file_name_preprocessed = (
+            df_name[:idx] + "_preprocessed" + excel_file_name_path[idx:]
+        )
+
+        # save file for preprocessing
+        preprocess_df = pd.read_csv(excel_file_name_path)
+        request.session["excel_file_name_preprocessed"] = excel_file_name_preprocessed
+
+        # make the dir
+        if not os.path.exists(model_name_path):
+            os.makedirs(model_name_path)
+
+        try:
+            if dataset_type == "tabular":
+                le = LabelEncoder()
+                preprocess_df[class_label] = le.fit_transform(
+                    preprocess_df[class_label]
+                )
+
+                if "array_preprocessing" in request.POST:
+                    preprocess_df = methods.preprocess(
+                        preprocess_df,
+                        array_preprocessing,
+                        excel_file_name_path,
+                        dataset_type,
+                        model_name_path,
+                        class_label,
+                    )
+            elif dataset_type == "timeseries":
+
+                pos = jsonFile.read_from_json(["pos"])
+                neg = jsonFile.read_from_json(["neg"])
+                pos_label, neg_label = 1, 0
+
+                if pos != pos_label:
+                    preprocess_df.iloc[:, -1] = preprocess_df.iloc[:, -1].apply(
+                        lambda x: pos_label if x == int(pos) else x
+                    )
+                if neg != neg_label:
+                    preprocess_df.iloc[:, -1] = preprocess_df.iloc[:, -1].apply(
+                        lambda x: neg_label if x == int(neg) else x
+                    )
+                if "array_preprocessing" in request.POST:
+                    preprocess_df = methods.preprocess(
+                        preprocess_df,
+                        array_preprocessing,
+                        excel_file_name_path,
+                        dataset_type,
+                        model_name_path,
+                    )
+
+            pca = methods.generatePCA(preprocess_df)
+
+            # TSNE
+            if dataset_type == "tabular":
+                tsne, projections = methods.generateTSNE(
+                    preprocess_df, dataset_type, class_label
+                )
+            else:
+                tsne, projections = methods.generateTSNE(preprocess_df, dataset_type)
+
+            if dataset_type == "tabular":
+                # training
+                feature_importance, classification_report, importance_dict = (
+                    methods.training(
+                        preprocess_df,
+                        model_name,
+                        float(test_set_ratio),
+                        class_label,
+                        dataset_type,
+                        df_name,
+                        model_name_path,
+                    )
+                )
+
+                # feature importance on the original categorical columns (if they exist)
+                df = pd.read_csv(excel_file_name_path)
+                df = df.drop(class_label, axis=1)
+
+                # Initialize a dictionary to hold aggregated feature importances
+                categorical_columns = methods.get_categorical_features(df)
+
+                if categorical_columns != []:
+                    aggregated_importance = {}
+                    encoded_columns = methods.update_column_list_with_one_hot_columns(
+                        df, preprocess_df, df.columns
+                    )
+
+                    feature_mapping = defaultdict(list)
+                    for col in encoded_columns:
+                        for original_col in categorical_columns:
+                            if col.startswith(original_col + "_"):
+                                feature_mapping[original_col].append(col)
+                                break
+                        else:
+                            feature_mapping[col].append(
+                                col
+                            )  # If no match, map to itself
+
+                    # Aggregate the feature importances
+                    for original_feature, encoded_columns in feature_mapping.items():
+                        if encoded_columns:  # Check if encoded_columns is not empty
+                            if original_feature not in encoded_columns:
+                                aggregated_importance[original_feature] = np.sum(
+                                    [
+                                        importance_dict.get(col, 0)
+                                        for col in encoded_columns
+                                    ]
+                                )
+                            else:
+                                aggregated_importance[original_feature] = (
+                                    importance_dict.get(original_feature, 0)
+                                )
+
+                    importance_df = pd.DataFrame(
+                        {
+                            "feature": list(aggregated_importance.keys()),
+                            "importance": list(aggregated_importance.values()),
+                        }
+                    )
+
+                    importance_df.to_csv(
+                        model_name_path + "/feature_importance_df.csv", index=None
+                    )
+                else:
+                    # if no categorical columns
+                    # Combine feature names with their respective importance values
+                    feature_importance_df = pd.DataFrame(
+                        {
+                            "feature": importance_dict.keys(),
+                            "importance": importance_dict.values(),
+                        }
+                    )
+
+                    feature_importance_df.to_csv(
+                        model_name_path + "/feature_importance_df.csv", index=None
+                    )
+
+                # save some files
+                pickle.dump(
+                    classification_report,
+                    open(model_name_path + "/classification_report.sav", "wb"),
+                )
+                pickle.dump(
+                    feature_importance,
+                    open(model_name_path + "/feature_importance.sav", "wb"),
+                )
+                pickle.dump(le, open(model_name_path + "/label_encoder.sav", "wb"))
+
+                context = {
+                    "dataset_type": dataset_type,
+                    "pca": pca.to_html(),
+                    "class_report": classification_report.to_html(),
+                    "feature_importance": feature_importance.to_html(),
+                }
+            elif dataset_type == "timeseries":
+
+                path = model_name_path
+                dataset_camel = methods.convert_to_camel_case(df_name)
+                if "Ecg" in dataset_camel:
+                    dataset_camel = dataset_camel.replace("Ecg", "ECG")
+
+                experiment = methods.fetch_line_by_dataset(
+                    PIPELINE_PATH + "/glacier_experiments.txt",
+                    dataset_camel,
+                )
+
+                if experiment is not None:
+                    stripped_arguments = methods.extract_arguments_from_line(experiment)
+
+                if model_name == "glacier":
+                    classification_report = methods.training(
+                        preprocess_df,
+                        model_name,
+                        float(test_set_ratio) if test_set_ratio != "" else 0,
+                        "",
+                        dataset_type,
+                        df_name,
+                        path,
+                        autoencoder,
+                        stripped_arguments,
+                    )
+                else:
+                    classification_report = methods.training(
+                        preprocess_df,
+                        model_name,
+                        float(test_set_ratio) if test_set_ratio != "" else 0,
+                        "",
+                        dataset_type,
+                        df_name,
+                        path,
+                    )
+
+                pickle.dump(
+                    classification_report,
+                    open(path + "/classification_report.sav", "wb"),
+                )
+                
+                context = {
+                    "dataset_type": dataset_type,
+                    "pca": pca.to_html(),
+                    "tsne": tsne.to_html(),
+                    "class_report": classification_report.to_html(),
+                }
+
+            # save the plots
+            pickle.dump(tsne, open(model_name_path + "/tsne.sav", "wb"))
+            pickle.dump(pca, open(model_name_path + "/pca.sav", "wb"))
+
+            # save projections file for future use
+            with open(model_name_path + "/tsne_projections.json", "w") as f:
+                json.dump(projections.tolist(), f, indent=2)
+
+            if jsonFile.key_exists("classifier"):
+                temp_json = {model_name: preprocessing_info}
+                jsonFile.update_json(["classifier"], temp_json)
+            else:
+                temp_jason = {
+                    "preprocessed_name": df_name + "_preprocessed.csv",
+                    "classifier": {model_name: preprocessing_info},
+                }
+                jsonFile.append_to_json(temp_jason)
+                        
+            classifier_data = jsonFile.read_from_json(["classifier", model_name])
+            classifier_data_html = dict_and_html(classifier_data)
+            context.update({"classifier_data": classifier_data_html})
+            preprocess_df.to_csv(excel_file_name_preprocessed_path, index=False)
+            status = 200
+
+        except FileNotFoundError as e:
+            methods.remove_dir_and_empty_parent(model_name_path)
+            context = methods.format_error_context(
+                e, "File error. Please check if all required files are available."
+            )
+            status = 400
+
+        except PermissionError as e:
+            methods.remove_dir_and_empty_parent(model_name_path)
+            context = methods.format_error_context(
+                e, "Permission error. Ensure appropriate file permissions."
+            )
+            status = 400
+
+        except KeyError as e: 
+            methods.remove_dir_and_empty_parent(model_name_path)
+            context = methods.format_error_context(
+                e, f"Key error. Missing expected key {str(e)}. Verify dataset and configuration settings."
+            )
+            status = 400
+
+        except ValueError as e:
+            methods.remove_dir_and_empty_parent(model_name_path)
+            context = methods.format_error_context(
+                e, "Data error. Please verify the data format and preprocessing steps."
+            )
+            status = 400
+
+        except TypeError as e:
+            methods.remove_dir_and_empty_parent(model_name_path)
+            context = methods.format_error_context(
+                e, "Type error. Check for data type compatibility in operations."
+            )
+            status = 400
+
+        except Exception as e:
+            methods.remove_dir_and_empty_parent(model_name_path)
+            context = methods.format_error_context(
+                e, "An unexpected error occurred. Please review the code and data."
+            )
+            status = 400
+    elif action == "delete_pre_trained":
+        
+        df_name = request.session["df_name"]
+        model_name = request.POST.get("model_name")
+        model_name_path = os.path.join(
+            PIPELINE_PATH + f"{df_name}" + "/trained_models/" + model_name
+        )
+        
+        print(model_name_path)
+        
+        excel_file_name_preprocessed_path = os.path.join(
+            PIPELINE_PATH,
+            f"{df_name}" + "/" + df_name + "_preprocessed" + ".csv",
+        )
+        try:
+            # Check if the file exists
+            if os.path.exists(excel_file_name_preprocessed_path):
+                # Delete the file
+                os.remove(excel_file_name_preprocessed_path)
+                # print(f"File '{excel_file_name_preprocessed_path}' has been deleted successfully.")
+            else:
+                print(f"File '{excel_file_name_preprocessed_path}' does not exist.")
+        except Exception as e:
+            print(f"An error occurred while deleting the file: {e}")
+            
+        json_path = os.path.join(PIPELINE_PATH + f"{df_name}" + "/pipeline.json")
+        jsonFile = pipeline.PipelineJSON(json_path)
+        jsonFile.delete_key(["classifier", model_name])
+        
+        methods.remove_dir_and_empty_parent(model_name_path)
+        # load paths
+        # absolute excel_file_preprocessed_path
+
+        if not jsonFile.key_exists("classifier"):
+            # pre trained models do not exist
+            # check if dataset directory exists
+            df_dir = os.path.join(PIPELINE_PATH + f"{df_name}")
+            if not os.path.exists(df_dir):
+                df_name = None
+
+            context = {
+                "df_name": df_name,
+                "available_pretrained_models_info": [],
+            }
+        else:
+            # if it exists
+            # check the section of "classifiers"
+            # folder path
+            available_pretrained_models = jsonFile.read_from_json(
+                ["classifier"]
+            ).keys()
+
+            available_pretrained_models_info = (
+                methods.create_tuple_of_models_text_value(
+                    available_pretrained_models
+                )
+            )
+            context = {
+                "df_name": df_name,
+                "available_pretrained_models_info": available_pretrained_models_info,
+            }
+    elif action == "discard_model":
+        name = request.session["df_name"]
+        model_name = request.session["model_name"]
+        model_name_path = os.path.join(
+            PIPELINE_PATH + f"{name}" + "/trained_models/" + model_name
+        )
+        # should delete model folder
+        # should delete classifier from json
+        # should delete preprocessed path too
+        methods.remove_dir_and_empty_parent(model_name_path)
+        # load paths
+        # absolute excel_file_preprocessed_path
+        excel_file_name_preprocessed_path = os.path.join(
+            PIPELINE_PATH,
+            f"{name}" + "/" + name + "_preprocessed" + ".csv",
+        )
+        try:
+            # Check if the file exists
+            if os.path.exists(excel_file_name_preprocessed_path):
+                # Delete the file
+                os.remove(excel_file_name_preprocessed_path)
+                # print(f"File '{excel_file_name_preprocessed_path}' has been deleted successfully.")
+            else:
+                print(f"File '{excel_file_name_preprocessed_path}' does not exist.")
+        except Exception as e:
+            print(f"An error occurred while deleting the file: {e}")
+            
+        json_path = os.path.join(PIPELINE_PATH + f"{name}" + "/pipeline.json")
+        jsonFile = pipeline.PipelineJSON(json_path)
+        jsonFile.delete_key(["classifier",model_name])
+        
+        context = {}
+        
+    return HttpResponse(json.dumps(context), status=status)
\ No newline at end of file
diff --git a/base/static/css/sb-admin-2.css b/base/static/css/sb-admin-2.css
index 440295341..119f169b8 100755
--- a/base/static/css/sb-admin-2.css
+++ b/base/static/css/sb-admin-2.css
@@ -4884,30 +4884,6 @@ input[type="button"].btn-block {
   max-height: 100%;
 }
 
-.loader {
-  width: 48px;
-  height: 48px;
-  border: 5px solid #fff;
-  border-bottom-color: #ff3d00;
-  border-radius: 50%;
-  display: inline-block;
-  box-sizing: border-box;
-  animation: rotation 1s linear infinite;
-}
-
-.loader_small {
-  width: 22px;
-  height: 22px;
-  border: 3px solid #fff;
-  margin-left: 5px;
-  border-bottom-color: #ff3d00;
-  border-radius: 50%;
-  display: inline-block;
-  box-sizing: border-box;
-  animation: rotation 1s linear infinite;
-  position: fixed;
-}
-
 @keyframes rotation {
   0% {
     transform: rotate(0deg);
@@ -12097,22 +12073,6 @@ button.btn-primary:hover {
   margin-top: 30px;
 }
 
-/* Loader styling */
-.loader {
-  border: 4px solid #f3f3f3;
-  border-top: 4px solid #007bff;
-  border-radius: 50%;
-  width: 25px;
-  height: 25px;
-  animation: spin 1s linear infinite;
-}
-
-/* Keyframes for loader spin */
-@keyframes spin {
-  0% { transform: rotate(0deg); }
-  100% { transform: rotate(360deg); }
-}
-
 /* Preprocessing checkboxes styling */
 .form-check-inline .form-check-label {
   margin-left: 5px;
@@ -12529,7 +12489,7 @@ h6 {
   animation: fadeIn 0.8s ease forwards;
 }
 
-/* Loader Style */
+/* Existing Loader Spinner */
 .loader {
   display: inline-block;
   width: 1.5rem;
@@ -12541,10 +12501,45 @@ h6 {
   margin-left: 8px;
 }
 
+/* Keyframes for spinner animation */
 @keyframes spin {
-  to { transform: rotate(360deg); }
+  to {
+    transform: rotate(360deg);
+  }
 }
 
+/* Loader Overlay */
+.loader-overlay {
+  position: absolute;
+  top: 0;
+  left: 0;
+  width: 100%;
+  height: 100%;
+  background: rgba(255, 255, 255, 0.8); /* Semi-transparent white background */
+  display: flex;
+  justify-content: center;
+  align-items: center;
+  z-index: 10; /* Ensure it overlays the content */
+}
+
+/* Spinner Loader */
+.spinner-border {
+  width: 3rem;
+  height: 3rem;
+  border: 4px solid rgba(0, 0, 0, 0.1);
+  border-top-color: #007bff; /* Customize color */
+  border-radius: 50%;
+  animation: spin 0.6s linear infinite;
+}
+
+/* Keyframes for spinner animation */
+@keyframes spin {
+  to {
+      transform: rotate(360deg);
+  }
+}
+
+
 /* Enhanced style for the modal trigger button */
 .info-button {
   background: none;
@@ -12586,4 +12581,401 @@ table th, .sticky-top-table table td {
 /* Hover effect for rows */
 .sticky-top-table table tbody tr:hover {
   background-color: #eaf1f8; /* Soft highlight on hover */
-}
\ No newline at end of file
+}
+
+/* Modal Styling */
+#deleteFileModal .modal-content {
+  border-radius: 4px;
+  padding: 0;
+  box-shadow: 0 2px 8px rgba(0, 0, 0, 0.1);
+}
+#deleteFileModal .modal-header {
+  padding: 0.5rem 1rem;
+  border-bottom: none;
+}
+#deleteFileModal .modal-title {
+  font-size: 1rem;
+  color: #d9534f;
+}
+#deleteFileModal .modal-body {
+  font-size: 0.9rem;
+  color: #444;
+}
+
+/* Custom Buttons */
+.custom-btn-secondary,
+.custom-btn-danger {
+  font-size: 0.85rem;
+  padding: 0.4rem 1rem;
+  border-radius: 2px;
+  cursor: pointer;
+  transition: background-color 0.2s;
+}
+
+.custom-btn-secondary {
+  color: #555;
+  background-color: #f8f9fa;
+  border: 1px solid #ddd;
+}
+
+.custom-btn-secondary:hover {
+  background-color: #e2e6ea;
+}
+
+.custom-btn-danger {
+  color: #fff;
+  background-color: #d9534f;
+  border: 1px solid transparent;
+}
+
+.custom-btn-danger:hover {
+  background-color: #c9302c;
+}
+
+/* Delete icon next to file names */
+.delete-file-icon {
+  font-size: 1.2rem;
+  color: #bbb;
+  cursor: pointer;
+  transition: color 0.2s;
+}
+.delete-file-icon:hover {
+  color: #d9534f;
+}
+
+.custom-alert {
+  display: flex;
+  align-items: center;
+  padding: 5px 10px;
+  border-radius: 8px;
+  background-color: #eafaf1;
+  color: #28a745;
+  font-size: 14px;
+  max-width: 250px;
+  opacity: 0;
+  transform: translateY(-10px);
+  transition: opacity 0.4s ease, transform 0.4s ease;
+}
+
+.custom-alert.show {
+  opacity: 1;
+  transform: translateY(0);
+}
+
+.loader i {
+  font-size: 1.2em;
+  color: #007bff;
+}
+
+.card-header h6 {
+  font-size: 1rem;
+  font-weight: 600;
+  margin-right: auto;
+}
+
+.card-footer {
+  font-size: 0.85rem;
+  color: #6c757d;
+}
+
+/* Add to your CSS file */
+.blur-effect {
+  transition: filter 0.3s ease, opacity 0.3s ease;
+}
+
+/* Ensure the modal respects the maximum height */
+#modelAnalysisModal .modal-content {
+  max-height: 80vh; /* Adjust the maximum height as needed */
+  overflow-y: auto; /* Add vertical scrolling when content exceeds height */
+}
+
+/* Style for the modal body */
+#modelAnalysisModal .modal-body {
+  padding: 20px; /* Add some padding for better readability */
+}
+
+/* Optional: Keep the tabs navigation fixed at the top inside the modal */
+#modelAnalysisModal .nav-tabs {
+  position: sticky;
+  top: 0;
+  z-index: 1020;
+  background-color: #f8f9fa; /* Match with modal header background */
+  border-bottom: 1px solid #dee2e6;
+}
+
+/* Optional: Add smooth scrolling */
+#modelAnalysisModal .modal-content::-webkit-scrollbar {
+  width: 8px;
+}
+
+#modelAnalysisModal .modal-content::-webkit-scrollbar-thumb {
+  background-color: #6c757d; /* Darker thumb for scrollbar */
+  border-radius: 4px;
+}
+
+#modelAnalysisModal .modal-content::-webkit-scrollbar-track {
+  background-color: #f8f9fa; /* Light track for scrollbar */
+}
+
+/* Make the modal footer fixed to the bottom of the modal */
+#modelAnalysisModal .modal-footer {
+    position: sticky; /* Keep it at the bottom of the modal body */
+    bottom: 0;
+    z-index: 1050; /* Ensure it appears above the modal body content */
+    background-color: #fff; /* Match the modal's background color */
+    border-top: 1px solid #dee2e6; /* Optional: Add a top border */
+    box-shadow: 0 -1px 5px rgba(0, 0, 0, 0.1); /* Optional: Add subtle shadow */
+}
+
+/* Adjust the modal body to account for the footer's height */
+#modelAnalysisModal .modal-body {
+    max-height: calc(80vh - 60px); /* Subtract the approximate footer height */
+    overflow-y: auto; /* Enable scrolling if content exceeds height */
+}
+
+        /* Minimal animations and transitions */
+        .fade-in {
+          opacity: 0;
+          transform: translateY(20px);
+          transition: all 0.5s ease-in-out;
+      }
+
+      .fade-in.visible {
+          opacity: 1;
+          transform: translateY(0);
+      }
+
+      /* Button hover effect */
+      .btn-outline-primary {
+          border: 2px solid #007bff;
+          color: #007bff;
+          background: none;
+          transition: all 0.3s ease-in-out;
+      }
+
+      .btn-outline-primary:hover {
+          background: #007bff;
+          color: #fff;
+          transform: scale(1.05);
+      }
+
+      /* Card hover effect */
+      .feature-card {
+          transition: transform 0.3s ease-in-out, box-shadow 0.3s ease-in-out;
+      }
+
+      .feature-card:hover {
+          transform: translateY(-5px);
+          box-shadow: 0 8px 16px rgba(0, 0, 0, 0.1);
+      }
+
+      /* Typography tweaks */
+      h1, h2, h3 {
+          font-weight: 600;
+      }
+
+      p {
+          font-size: 1rem;
+          line-height: 1.6;
+      }
+
+      .separator {
+          height: 2px;
+          background-color: #ddd;
+          width: 100px;
+          margin: 20px auto;
+      }
+
+      .fade-in {
+        animation: fadeIn 1s ease-in-out;
+    }
+    
+    .btn-primary {
+        transition: background-color 0.3s ease, transform 0.2s ease;
+    }
+    
+    .btn-primary:hover {
+        background-color: #0056b3;
+        transform: scale(1.05);
+    }
+    
+    @keyframes fadeIn {
+        from {
+            opacity: 0;
+            transform: translateY(20px);
+        }
+        to {
+            opacity: 1;
+            transform: translateY(0);
+        }
+    }
+    
+    .carousel-control-prev-icon, .carousel-control-next-icon {
+        width: 3rem;
+        height: 3rem;
+    }
+    
+    .carousel-indicators li {
+        width: 1rem;
+        height: 1rem;
+        margin: 0 0.5rem;
+    }
+    
+    #backToTop {
+        position: fixed;
+        bottom: 20px;
+        right: 20px;
+        display: none;
+        z-index: 1000;
+        box-shadow: 0 2px 5px rgba(0, 0, 0, 0.2);
+    }
+    
+    #backToTop:hover {
+        background-color: #007bff;
+        color: white;
+    }
+    
+    body.dark-mode {
+        background-color: #121212;
+        color: #ffffff;
+    }
+    
+    .dark-mode .bg-light {
+        background-color: #2a2a2a;
+    }
+    
+    .dark-mode .text-dark {
+        color: #ffffff;
+    }
+    
+    .dark-mode .btn-primary {
+        background-color: #0056b3;
+        border-color: #0056b3;
+    }
+/* Background Enhancements */
+#home_intro {
+  overflow: hidden;
+  position: relative;
+  background: linear-gradient(145deg, #f3f4f6, #ffffff);
+}
+
+#home_intro .background-shape {
+  position: absolute;
+  width: 180px; /* Reduced size */
+  height: 180px; /* Reduced size */
+  background: rgba(0, 123, 255, 0.2);
+  border-radius: 50%;
+  filter: blur(60px);
+  z-index: 0;
+  animation: float 5s ease-in-out infinite;
+}
+
+#home_intro .background-shape.shape-1 {
+  top: -40px;
+  left: -40px;
+}
+
+#home_intro .background-shape.shape-2 {
+  bottom: -40px;
+  right: -40px;
+  animation-delay: 2s;
+}
+
+/* Keyframe Animation for Background Shapes */
+@keyframes float {
+  0%, 100% {
+      transform: translateY(0);
+  }
+  50% {
+      transform: translateY(15px);
+  }
+}
+
+/* Logo Styling */
+#home_intro .logos .logo {
+  max-height: 60px; /* Smaller logo size */
+  filter: drop-shadow(0 3px 5px rgba(0, 0, 0, 0.1));
+  transition: transform 0.3s ease, filter 0.3s ease;
+}
+
+#home_intro .logos .logo:hover {
+  transform: scale(1.1);
+  filter: drop-shadow(0 5px 7px rgba(0, 0, 0, 0.2));
+}
+
+/* Animation for Fading in */
+.fade-in {
+  animation: fadeIn 1s ease-in-out;
+}
+
+@keyframes fadeIn {
+  from {
+      opacity: 0;
+      transform: translateY(20px);
+  }
+  to {
+      opacity: 1;
+      transform: translateY(0);
+  }
+}
+
+/* Responsive Styling */
+@media (max-width: 768px) {
+  #home_intro .logos {
+      flex-wrap: wrap;
+  }
+
+  #home_intro .logos .logo {
+      margin-bottom: 8px; /* Reduced spacing */
+  }
+}
+
+/* Overall Styling */
+.collapse {
+  padding: 20px;
+  line-height: 1.6;
+  font-size: 16px;
+}
+
+.collapse h4 {
+  font-weight: 600;
+  text-align: center;
+  margin-bottom: 20px;
+}
+
+.collapse ul {
+  padding: 0;
+  margin: 20px 0;
+  list-style: none;
+}
+
+.collapse ul li {
+  display: inline-block;
+  margin: 0 15px;
+  font-size: 16px;
+  font-weight: 500;
+  color: #495057;
+}
+
+.collapse ul li i {
+  font-size: 20px;
+  vertical-align: middle;
+}
+
+.collapse p {
+  text-align: justify;
+  margin: 10px 0;
+}
+
+.collapse a.btn {
+  font-size: 14px;
+  padding: 10px 20px;
+  border: 1px solid #007bff;
+  color: #007bff;
+  transition: background-color 0.3s ease, color 0.3s ease;
+}
+
+.collapse a.btn:hover {
+  background-color: #007bff;
+  color: white;
+}
diff --git a/base/static/img/digital_features.png b/base/static/img/digital_features.png
new file mode 100644
index 0000000000000000000000000000000000000000..a7cdcbb847a444a52dbfa19a5393458e51cce2b3
GIT binary patch
literal 12071
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

literal 0
HcmV?d00001

diff --git a/base/static/img/su_logo.png b/base/static/img/su_logo.png
new file mode 100644
index 0000000000000000000000000000000000000000..c433f410a1d25340e90b542a997b743219238ff9
GIT binary patch
literal 40692
zcmZttW3VVqtOg1%+g^LEy=>dIZQHhO+qP}nwr$(E`#tA7^;O-vshV{1q%-Nx{7KJb
z00026O`P2A^j*wN0RGW`qqVsSy|uaiKOJz|+Sp0|Kl~rzn;BU-{I3WAU}tXV^nddI
zjc|76PS*dU0RH15=2o_b|7k*e0Kfo1|4D%N0RLJ3kxcaeN^(B`he)^moAr-!SpE+I
z==rBgo15GG&%*x4iuzA6{@+{uw^Ta%|2+Qx;6Ka%8wC8%PuT5$H@9kT=V15Gqu$)k
z(DvVmY-nrcU}I?I_AewX0GQuD2u9z9UeF%^`=1DaV(w^X{GR{-0HpShb^p8m?a|Hr
zKLilsA7j&Zb`$(hb9S)du(mTc{U0X4VQ6k>$KmMi=wxi|$nkHExs|!TgFA=5m7UrD
zWb^+Q1?E53|F0+r{}%-q0^+|oIOcZN|MwVx002P%L%<;bfItF(L4yBT$;=&$|2Ief
z*7q-()xT^5{!bR+42>KO|7GBRv}|Z=BYh_%04OjF;$zPdREFOyKtw%I6u$mGZfLRd
z$0jSf%TQi&k}f3bJmwu{0MHJQx2$tuo(LDWL~nu-T&c6nsiQs;;r)-L84!T?$w<X&
z(Lc@Io&7taQazirqO|lQvQ3Do?(RcrwCWw#&bGBP6%lY&tKX8;1aA6-{b?I2j?<PD
zKHt;8(2yrblTj}v<SbE+yvNoM?yntC3|%1!7Hyi)$DubUWrRJ5_|^h|53A*k7+pE<
z?^*nG5mRXs>hrC3sP`k%0o505J;RM^>w<W7T3SMnJLLn1nsSB(@U1x@6EC29N@;<R
zTBsIuULw|{Z|U>^Mz1Dul52O|PH!?xkR#turpwkS#+v1^oWgkW3&yiUG8$gH-avP#
zfwYlF*6CP>*IxvJtDLVjOVx3(t;C{`>uZdHz>XG)Je}@JeqmCHngT8T@qI(Fc>W7>
zSpG4c+~WKfQ-@h%{ypIkxTDSf0Iy{_bD^PnSc<$&a6ojFFZyizHz-!M8aMrZq;=0-
ze8<EXhuD)jvwpo?Ck%kJx&5n7wYcXVHj>ugpX$7q>(>ik0>9)19AT4xr3P+exN!|<
zx#(VPy8Ni_)Z&uwznWh*Kop>>wx@B>e#nbuucd97vp*ZOy-r#`a;@x#qzt~9sY4?Z
zdxst(yR1+&nk|~V6VB3uD>bYd@))-aNOaID?LxeIMV^m^UKn`kM#ht|A8X+Rq<_hQ
z;#}ETR*4yU?@A{uu|FFFk}ptrXHChQ2H-Bsy>5nsn)e8~-?3n2cl9-y9{V^%vH!R|
zq%)d0^w0bSxJiE2dMyyB;~3k~B{eCuV(!oh()+8MtI-F)aGrNayXU3XGBeMYU+>Xz
z^t;j?5GKs*ijwu+pS>ilDo%eL&RQ~Vy>qxQ@|yl_D*Iq;%i;-WVu{#M_|h3urj3ZE
zj@YnuGZ%7z98iU&Z$rBo-1oBR`5o)D^#}}7KTqvajjZzHNTab3N{Z$ET855ZkFUt?
zFx#~B+&f2>pehuY>pYOn?K7h+2$^1iXe&petu;lUgAo)lLBK|?B8suTYlmH*_+2o!
z!cvN4VUkTk+18i4Z)<PXo7hxqj`I;HHCp<(`qdteoTsY#%%`kW%oqT&$bQ%e0sbka
zq0y>4S;0OzOfB`e;W=F)@j%+0%7A97Lm)BB*S8J#_3)i?0nt!g<g=#h&WPyP8$4%1
z8(p4(6~F8k&q(@9kO`7E>KN@wx6!&JRlmv+$`Dj$2GVHbVX6cWQ8nTxe2bBkL7E8j
zF>fzN><r6B+E%Ic4t&@hVC&j^qEzi_L)VQGVY1NzET-JxAUF3_=}XokVK~=DF%~G4
zSbk__AE+(am0jM-=M_}xX=7->9pjcmZ&D2Msl$XVidUsd<=n^v8Qw;{>jw}HG{DmS
z9Cvb#u8#qIrlx9Z&!#T#Qpl5_>bF9)XLs0epD8cUwsyxAgq4&ahX4#@mCBnS6ui{`
zqgf>n=eRgU94;G-K>=IJEZkqpXrprKKE#TQyP*Tw03;peSl9z`|F@5ue9BzSpOZ-3
zYi=iCoosF`RgZdu=7IBQ0kM#n!<jpUJNu<q`$l~~d|NPSPR2e$M^&bATe6=3{ruXb
zoX!uH$;|wN4T|YwXz)#=;CtKKzUaQZ<5rgWYqJ%u*iVm*|N6M98d6!;P6ExQfU00n
zV59V@2HHIQ2JvLWd~X!qa@I$S{AJcb>2o2stn5)xdj>N!-a!UP`ZD8kYq&T-N)t^!
zQqiv;r~hw<cIrJ48wUsEk%BH8^eG@`$AS$55@Edy!Uudq=o(&s^IPjTDG9d^!|D%;
zKZnvCxH7mylt82zZ=ke5Ua`u~z~+ALPQ9Ft;QVSPg?H40*~7!Z9qO?}T-idx)j=ZN
z{f-nD{f<6=T0Ns6R>9<*y%q8}(YQZaU7IgzUp&J(X_+op`*OcM9as^q)Xu#u|BS9&
zKHal*x?%?AnN*?RuA?6Zz=hU*O_rIv1TU*>p&Ryi3ATEqylJP;&BH2i#p-HftTQ8o
ztM+1Q+5<Mtjyr48Ujfni6CDZySZzdmo)hVg;&y#WMTm+x*0+N%{(dB{%e}Xdl|FBe
zQup@>qMcN8+S<5#RPAh`&`L7`#4iF%LDp!7W6@OBu6`_0t3-YuWIoLXYB0+ECJ>kF
zsdZA_py?Hw$E=sUZ)?m7IP~ACpe@Aw_Z^2E`D1*T<5(~zGB;9zH9Eml+-lTy(Wnaw
zq>G!0kWym+A2J6TEK^8!RdFJRk!E&CYQ<?(YU)UI^TnVKo>XmOXp@Z6iXZ*-C!od>
z-VwGB1g0l&tuz{W6X2pF-gu&_E5`s_IGJRj5n$#AXqsLAc}&c5^<6#$UQ7mSl_%SE
zh-{+U9Yz;imT+DPN#I&%L>+wFfC76tWg*iwD&i~x82|=3?@)@l(;f=yh{e0K80n!@
z{KQ5m?=(ov6{ke7-^g#sFo#g2BmAv4JgUT<loP0DkXAdNgu;<^F<78HA4P$^v8UEb
z=Yv*VR7*mkZa8~C>5UfZtdbFqdI$=O;^z6<QVK#ve}*%7yHYG~T?rN6#+P%9F=se@
zn_{rxS760I!+SU2f-e(=Gqx&<N$+#8;U5#QZP_@yRpfRP0EUONYIrxFr60Sao-9<F
zQ{t7PPWD02m>S)q83I)@b^z%;0`~o(h>_F-__Eh@z@uw8tj!zq7U5EB3)DD377(;V
z#Eo~C?(Vn4Sd-CRFog=**hlft^@9}Gk-OrnbMw39E`{?L-_#xeYRZ8R01WKB4S;&Y
zZfV9AFe+*)4`PY$2#)+IT`jfB=|E*vz~+CaRQn5T&h%b%u;@Q{)X~ocmn%U<GgS{=
z+nLHy1T(~LVkt<_hAH;Gu{6XF@1%~oA>+qtFm}9f-8Uf8h+D4NFKxtsb#!E97>TsJ
z!DVtSjW+2%YzJOwyRyK9(dD^ieo10GLjX^Q=hgQmkx9u&klMHlyBvoPv{wfm;9M6z
zVaM7O>b5p*pJR{qAS|0HvMaMOl7nkcOIpq&%++6*ZRrT;IP(O$H?hV9TloWEihJMN
znI;NL>7-;SjaS*VU;Al&$s-!hq1=ig0e6KVjM}PZoQ3_OD{cexvj`LJ#h^2XUd%O$
z2~AGlncrBuv8FFVx?%9=o2ohk5CgciU2#F^5C^CcDx8xaJT}gHCZc6K>-L>t0Gw|6
z>z}uiUl}fCjqxgQjZZNrlzcie!G}}|yHv<OSL%SwLAWFn?)w*X4-e5H)g_Qj3^)_D
zDr-Z$ms8}K@+OYIA2=KF|MoQ1-5Xa?s?OCC;#HkIYfhMO_^OvEkY<q#Fld0YW?g$K
z`UCC?RyJ|Z=44XL@6+SQh|=@NWk2!t8{A%jJc3@$(_nJAWkor*5df^$dzmO>0YQ2x
zv;<OKK`AA-bN(<;z*<|yqA7n;*HxO_p`!Ha(e;N8b@SWS5;8hV>Nz?{Z|azI1;pHE
zE3p{@uMTjIO+`88Tn_Rk09+D?S(>v^zmvVLiJz0>FE3s<{Qh2C_lg%a;bg_D!eb4v
zl2O+e0yL<v1JdzHmVI}pC|{}=PugsgaaNu+3_hl4O-Se1-+yvM$LeQvh`f`<vBU<s
zIn2P0XH=;J71U8{bXUVfLWPdEvdk%Vu^e>7sKSQDO;MrQA>t07xERa$56!D>2bA%>
zR#Mi_X#k1*VMEYSwlrQIxP9+%rwBC<)Zf!?#k*j{>Z(L7i<0~@1n{+;t}C1628>1r
z4>Nbr@L=AZPGVkh#(bd>(aF1^qmRDzy}p%_)FWp#`*)CG?|r4{idr78Dta}`rwR>K
z#p8+<;8fQgw6uLuNhk?UT^WL>jP|(fCQM)>nKhS{Y=;g#acqYKEZ<K{-FK#W)-G<x
z7ZxS}<g}>ln*a=_GU8WSdL$Vb_l_9DE9b&e2{~CBQ&~1=Rvijgl?9G3?8bmHs#UZO
z#hioTwOII?u#7JP-h~L-F=?vb{E|58$O(@K6e6r^!50Pzx=79A^$+j@P~Vc7KgWE1
zTwve`wkmBeVmqq@e_(h(jwXXWL!01d_KKf7ED1S-p&_!rBpiACTRy~IBOA!Nc(Ek~
zOZ%|=(35`e_RxY|?Ee>7m@6*7)=GQwkDF%?=p(cEV;A=XRU;FY6vU7TM7)MTlq1|G
zq(*%2Bwp`JonM^b?z|z$&z@-Iv79fMSP9=@2z`|kn>-#ThMGCf2_s*oX9xDuK{z+s
z>D(Ov<ZBTSt)|1xXO21;s5*8Dejuz3_~_f?R6gGmcubEjAA9B1N03iItDQk5BZ}BX
z=BskIMbG+kY3$rXmewOwt#X1!aduCtk5?l`80Z}ar|b?C_r<ZFivn(hgwbSu(v$PN
z`Q+1;!N3@MzkK>}p#F_|NRMIyzY<BV7-arVY`#hOqmh+*N-W=6ugH_G=-sM{bw<+M
zL1inH`6~gN9hs@S+=RM4v+W!{@El!I5kPrt(A?3{?;vNS@s+2sM3^K-=iT@OW0#4$
zWYn-@Y@m)NsMrp?>WaV?=Q<I|+VaRaWz5QKq^uYJZ_G`zsU8)%<>?sn@**ncR_sEZ
z6`ctKSYvt2TpZ;=c|8|Sz)4fd6jvgW&Yl5;z~u^^g1;>l1%@ntO8}?ySZvq^LZdg{
zaXkip-rn+SwULCfrKfQOF0D|b2ZO<u81h#DxIzV-;yZZlc0ef6keOf*cuGQZjfMC+
z80uGuYokkUCey>Crc1V2iFV~eQPg^f9mLRQ7nnyl{Z7q{^Jepm#RvS2#&5VPdoLAf
z$JgM?ntRynU`m5Ue2Jz}Kt7_fGFxT;o>d?Ztp2_IyiV~_u((7xi^WeUtS)9hIR3r7
zS=+gkSt6I}3w4COkh2Gs+3xB)Nc%jZ<j?@K{85w~LkwG(trD#RfabNr?kz5sCBm18
z7{DT9A%B<7mD0@Zho*y1rwB(~e#s<X4Ji{_?d$qpnsY}tXo6011Ys~KqEZo;PD0FJ
zSyiViL64b#3t!djwu@N;L>vam9g^27no6e7>;+-Q2o<8<*1A2vk;7@(bKPId(aC@-
zRb*DQnA!J8P*_j`*}?Dj_$O0dFJ4M}Jz@)~)?X)0%V1R<*)JCUm6^?XuMZBNfn;1>
zU%Rwr<C|@)7curpW9^_$@L8z1f>YMF<kWEgUr0LJK{U(M4b$^*r+09PBlw6NT-Aa|
zk?0*!kP(E#p?8g%38>`-BxdpAJL2jZ)HE0Mo(d`=<p8?6>2bvMmQ3HX?GlR_yRhN7
zQ2fT^|B7y~-U)6`-94TQ9sa+`w_fb=w@1oyi+`ek3_ygzNper_-@*s@O<#@;&}w!v
z!{nqL)&+h1cfHG1B$gukiZty0otxZ57eM=upIx5<cjfF*(SA{<KrCxB_*=YAFZV9c
zhiy}6v{Nb$?(1;Zi+*&95-s;9R?7f)FiNK*l3ufoEUA?PE1I<4-wx?IU4mrVQWCXG
zNhZ3(J)to0En$&&9AP~Z$ELNL<&a23%{cmhaOy`VGTTW!m)s9W`4Tc_b$`O;n}ms@
zTyP<Ve1XtW!^loUP7AI<54^(mx{Q=*Uf=ep#;(i6N=*mrWJ_3+F84+1j<BTtEt04t
zSQ#fL*4hb;w#skYpojv&TaMBzLIVBxQ;lqo0b^I5VR>);25g+Ck;_}Zrc%xy^m<;e
z@efo~4%*cU6!<-JO05Z++`&<%7ZF=zY6leTAuk^jWFA^oZ6t7#+GnoAT?Y$AdC5jx
zWz26kq#O()R0#Z>rqsw0D|QHgb#<&NwIJf2mrrD}GcgT}^ZiBni`~)+Q6v(`=7L_9
zerg{xN|%s_dU~}TCz%hSanLB0dJUH;`WAb#bD?*Us_zf{GB>lRj|iUFP<%nZ-L3ud
z(f@ATo%su$Xh6UjGt)Mx?$ow?(B))b4-wA`Qe(HhvQ<_>3tHCSsG(#DieWPP%G(<k
z77VYm4K~!WG6hRHpMs0w_Ch+P|12vpL25be|MGIyNsjdp+U6RjbtxeLUl@8f2z@aG
zDBVDdIV^|mWNe6sM}pA%ZU-n`GL-&ZW>Q-cKWF4*{eqfEj>MS&uZ)p=_&$;H#rODK
zH46yCp$}uCND8MoXm0Y_&wwCx%uJT~>j*T`P-MX;;^d5#;t#i~+^)yAIa1pVR{=Q)
zQQH$Oo~eD^yk0Hz2Nq7#3FW7qKTxnPS;(j&$30mE`r@x_(;wwYU=GjeMKcc#HdM_Z
zD_#M*m-dsL%BdD7nvCeG7#yb+zgCsAERlZ1QBJTS3DGvY!Gu5o?ptojj%4H3m0F-f
zgMrA`ruRQ8$gwQ-u9Z@SVYxBn>s2iSSi>|47>_clg^NZ)cj70t&ggvWntEM8yic-3
z#S96Qh}bRS@S*Q|9Lel!Kew!NtbyH>6=DFjaJ>DFd<O_FE9FmXpsl>&tHNn~b80H$
z-n2d}fro;fFdtnQ&j$oXZj=FGSib8Xc0PWwSi2zs%9&tPTNAred-jQ>A&chuNXjzq
zN2CQAMRhNd{V{(uVDe-R*>4MG5YxEZ*(3LnQXcCzm{t%|KDTBiYOIylr6BA$H;xMJ
z-d=sQR3`fDs*TdXPCk8q=uh9PygYo`L%^oV<2YNVChYadZrDLdTrkMJ5OE)F?Mu>c
zo_f3S%O}bN>eM6qKK407S(;Y%<gP}K?dO7ydFQp5Ea9Erk^fWy(-r)3GrhlTE_+}V
z9~phu0lT2~yl_1Ce#`8Uh*)%F&dmu64e;RsXrU&N!?jciq$dzI|Do9=D1p<3@*i5J
z;_4d<#y=iSGt)Rj)^U|wgk-Zf;IQe!ExSQ6SvT=g8v+_9>5$}vbCL%Q&2g4(ONR09
z<R}voz@#q3E2p}GnJI@J@C@WTybM!a4Z>}>Qmgas8R2@5x2k+pzZW%Gqi|6w(d(S+
zY^pVs9?0UJ@X!z;7YNKhtTh2<WD=Eu5SFTH_c$DO#z)Nj%cBt_V!#IjssZc)!F3WX
z^{1^?zu8*n?CQ6Fx<`4R1b+%PUd>6R2Ze+p4;V@V8_66#CJVA~CF?|HT-QL9fUzI0
zw6)_^cdV|za8Srpy;zjq-0XHJg%-)1e$o9R(J)x>unIk$NhAn!-dC|q9u}d?TY9fI
zfhivLnYWo-?^Z-iM#;0YqHDcoKpV85H2MyCoH~jtMc5z8bK+1Fz>39yng(-;$3Fk}
zYgB1Bj}U|2=wp+pJ}V$fD}2;xXZlMQbWf8&2iL2m`~H4ekdVrGnGAr+Yue+9fC5)L
zzJg0Ee$<I1mg3L6Mt@T8hHqq5GG&Z{Nn5B594@vvHvd~xQ}yU=D#L*2y2gS3kc#=#
zVkDT0?s+d#-n~d~YDh-SbmRHwVp^lgB1Q~~0Wu499Q7>|^ktSFVR10V&*t<io>#|M
zh1y;eI??k?Iq;P<H)yY=2VMwew#X}`o3!G{S8Dnw%I&P@L|S1Tc@9>03Xiv{fD+8D
z4~8-+vNjoS@aImzso$#Dpcp*Fa<vo<r*Mq}`)5DX`G|M{M5eA`j~4~!$CiuL`dtH;
z!l_`r4!`DG7P9$i;V2j;e{z>{36Ub@J0ThO<8L5;(W`{9o|WQ0dwZ606YoKtLUdN^
z66&is8&}Z<E;ekNXFF}*8w!IUkW=S&B4*yOR004bD+=;cO-BitBjwZ&RQ`fJZ`6o-
zsbW@rnGu4ePf06ZEF;Wn+@EKEe)0;C8de%ZnN?%~!qk2SohKP4)+|LY{wQt)w`~<K
zJplr{q5)w*Zq`KfR7ZNPn`M2I!pPuti*5||p}%ZSu0yv>qc68`ebFNTMud&b#z%{R
z_AiT0hvXJe0E}W?`d{0iC)lE6VBJd4e75e@gxX6l0Cb8Clq!TL+NC_q%N`+bKbxBa
z<Ud{CQ7f_I%7MJpJ_eNHPfG#3DtTC&c?;>{inFlfF!sT=iE$*!h~#pW9AS5dw&(DU
zsSaJG5E$@ej|ZSynZ}NZho}Uv{KBLKFHUgaXHmHB*nDY>bXr$aQ2i}ECtLmZVHsTV
z5k+B7asBptz61Cw*EgS^1+M}qsbjnPMB+~corG48oL$6MR{Vf(46a59K#pM{H}Zea
zz+w=J;R>^ERwIt3cW@qxI&>>APUb{-nsVf;m$NE05xuE8l_DZx(m%NKuYVGRLU3-S
zPelMtRbB_JJpX(a8)X9vWa|HlZSb!;3XQ?sC-7k3NaE<ECh6`;+IE8Xj8@_ZN4<G{
zhZ7g4n+HO25CWauq_t;8#z`(Kv}(E^dYx@(E>!YCKYW==IAN{(-#S^gjc=nnORa4i
zCsFW99bzst@s=GfEOurvqKHU;MT3pNf?M6fH@I*+HuY=8NcM;qXq$N5U4e%FJuG%3
z=@Ck0YI0RqNV9DUoWGN0T>qvy`C-&Z<0Do2qa4{bb87W%3ZCpZS*!Ky#QO_@cI^_~
z4}*TekVYQ(npxQ799!GRhG^T2zsjuWWow42$9^+_#F$E?-hf<diR?PJE0T;1{SIxA
z$k7#+AT`AciyY1oM!hSPm}t`9iRGg1x$i1$02(O_fs8)`c7o6f4@l5W;)*%HF55Bx
z;`;eB&r1}}SRQl^RCBx5hgprqaT5N8x<K+|bpR60VA9AfS0LGw4$&5?#b~zeR4R#X
zh{&K3IyF1fU%N;XGfxAQZB}MI(W@10{OTI8pT<5M+{SoHFm9|O9=uHc$q&XMwwep4
zIpriB!N32Vne+B_jJKD##fTQO@X=R84HqRI$9UeP<2pnSmGy+<pi+p8%7Tx6BNY9T
zJp*D;X_|%j$I#hliXf3Gw;>>*l<Wm_)`Ek92L@lHb^&7cK%W<o9F714g7C7-R^x;c
z>PgPT8DVHQ#Lx<qZ`~+`pl5ru7W6@HEMoDPMCEL`#5OdhNX8wF&}`iT5=zgq*_{9$
zlG@ygF1mLL@IZodRZuyqJA6xvlfY|n6xRVvCnN@Jec1Gtu6ubJ;PV20IQyaVZWQVp
zOTI-CS|CCK)eTuSQFTZJ+4oT5AUFh6BPv4Fx0=1dm6ceA77I;%1ME5Piqxhc=~e26
znpZJ?MnRAh%Wq;fDo&00@AGe4CGd9wLv%Z_nihUnPCYpfog<y3YEHw!+dY6CyTMYx
z=yD|>LLGmqsmdLg+rG{EOt*g8S@DIx?E#h+3-bs7>d+z!&gM`}g~P<cx?XPS^!sJt
zBC%c^qX-Hck!SqCQL%D-yc*Tm!(JokUY?IvylL>)Ct8uVL|KA)ee{_hl}6UdU6q4C
zhQVHw(vuJC>AJt;gR!XMRxrI!z@@=ccz%%}M)<yM14Pv$^B60pr!b8pY^&%WSK2;t
zz>4+8ojRFxLn*wwd~nW0Z<&VbpiuyrcHRr?{bs>{3~z9De@J})o*qG4fmkuwP$}TP
zl)b+Mju4v@e9g}krhtr4mXUO{N84!++bFa<v6ANgAjj~K<tQPjky+T~ozGx@UhoH7
z^hnWR;L+_SnP96|#QSYX06C|H4wb=){YaK~Wk;_npe|QM2$bw_ohr-)@y^Tvw$Omm
zv8;#-Fve3P(OYMR090Hs@_@n#7pm1?&JP%J=KzM3p1KL@*59$5DfP?OXA~(%<>?3Z
zmrGkFTu_TlOGL?PYQJ}D$aBv44$TA|2zHyn^J)PG9oq4-QiwRfRVxFRyM}r5Dzx{;
ztJYni0qSbG)KaGBEy4bdvDDjT(^(MT%e9_(9_dXE$unzvEiIN$D5;~J4HftT%^+s0
zknt{EsM0uvC_zvhOsHp{&R3#YM?`+e&+Tsetm-2bqQUq0R&c1ycAo!a!%@#T`gN)4
zy=fXP%!}?z_w8}Yj^dN_o%G)B%B}2JulBB(Eswp6&5)F;xdo>{=x2GSd9ru&Ne2Nz
z6ZTH<y91)T_U>gPT=xf3wz!N<b(_fqDR;${zZQ*oHLK7)DaxF=E}ML{R(Wf=BKZ@t
zg%v5J#{aRc&T`JHPDDEzY?wd5SW!z*PC~6W)HwUtvLYDAnSVCZkg}^3o5sFNBQ(=c
zMz|^%HvJ_rtd>%&>0h`+R}(wZ-Pf2F>Lpjd`A$d)z_KX6sKeb%WD>4l2S4Y2Gq|`N
zc`0;5FR5K))l#1HO~ns8IWaz0vR%Sz+1ssLgNEbHx?Z>tq5@OZhn+Vs`OpKKqxW<#
zS)N5VWsLUAhGjmT6<)5yz5$X8q`D*RaM(s?y1fsA&3lLSF)jBhsY*7Byo&YTy+Fk%
z`r!3~ocT>CIfBT>US#l25f1xUqPK#@JnxU`4|QM?+Pho&LpiaMH7)=G(XZ!=K%N2@
zy!d3kYwd}Sgsk)EDz=SlQZTS0ZoYrE0H&P)3u=<ogb?lqV(%@0kuIiIx#s?|46{lx
z8<mfjE~2Fsd)tEbhmwiceZ1b==vem46%<Khh0<g+`aR6{lWA^%hUA(RpAgqG?h%VO
z=5UfUn4Y#aXUyM$jlO>!xXF2?h?K?=#SX(_eQD3lxgW{~+PCL(3glqI`_c%_=l)th
z<HQzAhJpxe7)-8%og&AqNGUoq?NY`z6G?G8Cb_uG-PpoA2T^$3kuT_%r5HcAPMyvc
z!rNUD*(gQKqi=*bUh!T#Zlhhq1>61h!oNY%O{za0y>u#VQ+j;yk+_r~NX|<-ko7l*
zyD_VPWH8G4LRFA|bdnlZa`AM4nJRiR%Ag7G^p^x`r+9%F!h+Isk)JLqh}SyU4P*bC
z8CR79X>!Sx0%M`U*pky&k1V942A5xwFi`9C^T6S4bN%D6=p54cCh7eqDi9vy4qgQp
zq)1ODIc7-2^$p_Ji?`O9-VDM9&58>}Z#f}(uBzhC5Q6M#%;Ej1W|Bnt-*=@Ob36A|
za7b=48spflOclD}BG*Ls4n5|Dra$<rC1bedg8LZg!QgXUX4Ga7T1c&6jjPMO{^Y6W
z5M$?1@M4Te*WSmznM6@(PKhFmg95mgV%q>EI-Ik22}CD4SKAFJaHn)-<B(SO+`y(Y
zs;!q=hFRCqud?VpCYiHV^FJ-6)J1Y|K%Y6$-YOyjlXYwNWnWzsCuw$mC><m;M~<eT
z2=|}?+sBH5Y}larDy9_?Q_;RZ$?|tEbx?l*5BT;yt>MwXpN#T))RI_d)ouVL%Oejt
zQfUU((qoB;@je(J3osd+p7G)lzhmPtW`O)inkPK=N=866S81`60I|8^C4_7kOxD8V
z!og%bQ?qw1ceKN<d9v~$2fu{_Trq5p>QMcIV`uapoe@hvvz2|JuBXb)$ZfP!7fg@M
zh;`NsQ;!|`<~)ZvEVE2j(A@fXpHA(1Cv7IFo3+<;umsBxOWL=^3m$s#5euAgnX7_w
z4-GH2qniaXykxo!1>?o8TgNo%Y8c-zYcjexBnMGd^EN=5Y({X8(0D&DorU3!vuSs^
zjF@68MeKKatz)P0*LLm&(P5bKo61Oa5oGC?tZ&{t(D)acTQ>SD>aqJ;BOwIJk+*hb
zV1XY*mu5>PIYw(brr+@<e^&{ttQiRpzGwLID^Mp0lpoF%h@qVY6%*1}ZR*a&N4=@!
z-;$daef$fT?rR3BS9^zS5+x8!0<w>Ix9<i;fbDE+^hp^pszOLTFPz}ALWEa#{Es$G
z1@Hq&$pIe03kW86AdB_fFDg-UTdVdiZ)f8--lT5ES(20WYtIYkWWOo<d(~u)P(oot
zg61+g80)y>eRb~7!vf%wrhlR7eI?*nbP6~5|IFl-aY8~Vxaed3{_9@>005WgONV{O
z-@}I=uz!#8MWl~*zw7n5-R6re9vLk)!Rf1s!uTZ{TR0fBWE@<f7dH$y7t);yPyLyK
znY1bdB=1=1<V(EWV9w7U&xMLk5+Fz)Hg&Dvfx>aN>z7{dI!4D8bH*rV6cF6#s?)q#
zwlxqS1825IZto{)LsS-Wz%rIU8Fa7MWO&LDVkmk#$@}t2SMFvJKAt6I#u7zo657#+
zZp^YIqJwifnw^|<)gy49Det!t?3Y|a)hDrW%Ar4Nhn0V-fUgCwPShKF35glN)QR(V
zGfMDl+mNi_{Of1nYMH&Z31UAk2zyC8PHvTDkH=%<iA?wb<Ffr^5msp)wR9&xis^>h
z_C^tF;1QC~3&OlHH?B()P$QLQ*PUh(AJ0-Iu>yEWQ=roidlHuD*iNlo%t#~(s3yww
zw@?-3K#=^w$dgAa?)I}pr5P*U<eiBRGSH`EwG}VB=5edp5|_|3U1;u&SI%rh!hz&H
zZ`h9yd^(&ZSjQD~ZB*(F^B01w6;KG;&9?hN;tXxr)z@(h*_^ArjuzfSzkr4AR}rl~
zCGL1zZz`RwOCWh*TsrPw?a3|4SPl55g)MRIJRaYc)dqTdQqoIXCKoL&s!1EdMK@XN
z$=jXpNc`z|FDY|Iy5%S8ln7_i{rJ08pIt9ImJx8&T$2-WgxoN{Zpglk;qG&|=IB?%
z*2vaG(fL~(St>t=Kg<^$pn{O~O0*wyG)<2aTa2P6Kjy4ieq6i{niJ#lEtPCAzf*Ts
zRMbZ-TAIJwD)us$WV7pd<1Z=?+5zg?X>_c*mIliE8?vt%vDgDK9OYjjg2qF<T6BDa
zh|HFE)`$ddE|`X&n%YaM&1(R&kh46_+L4d{uh1?0%sS_rN4>1L5<)j(6Bv;1(bTpN
zd#rRPE|?2)X(KjB*45x9^*X?hh!1+@z#XuleIKLWwhh>W)Rbjh>X~{(i{u_h#S>vU
zeD*>LdhfosUnZWiuT62JTWQOzl{pB(D=`uuxI3trtcx4{tnvA<v8X|@t?KMUyom@Y
zgvrIj=*eu}I>4C;a4(I^ZKE{x+*ZK6L<W3zft+teN?~GloXi|D4t=z42_cJEY43Ng
zR-m>14mjvYDKWwT>by{nK?Pffj_&bdaMTy8n9`bEdKpGBttI0v%aU#2KJp0)&T9>3
zzy_&$2)HmL;m~KQy%@sqqp?j?`VqwFtO|}rXnnuB8mE<_zSaJSA}u0RTen9Gy{a&G
zpiHwtBW9g%mrPq_-&%)hTwX_EElPfVC=i|$9t`2!t_f);3r%C`-bd0j`p%2+x0RCJ
zlk<Q!!Q0pr6jE*G=iyo1E{p>H2$Kdbb#~69X<B~?ob)H^`*GH)Of#W;o#1vc_(r#B
z1}SsK&>Ej~p?seg$a$YTtu`M=3On05B{<jgJm5pi^Bj8Jv%zoJ0T5Gt)sh;)Xp+J1
zCq>Gti!%?13#}h5h7{U7UyBgik)G=rR9yuZZA80(>|Hsw$EG{(i2;`9aE_8h&<~Vx
zZo^8fxmlrJ(H`{HvaEb-jh{{*E1|a5aGQxc31#Dd-`N<1{f*R=dT4hkR9!hev**d5
zuOA7GRON!h%LMGSOd^qFue#u6=X)R%Fi9NvW$#BM|MXKcFRX0keqJD;-V!>TsM5@#
z0_jGjR5pEZb#)7*#-KJr8Fx)S003XP)VC}qH|3KUikX~FX*AvzneoOU@4@j!YO#og
zkXr;s2ZOznU;}aIVtt$i$k7?DFdGX|ZXoY^j14?5Vvh|+sBnWh8(!F*MAa&Gv{f^=
z7MEl}B+BwFyK2g_wCb^Y9@eJXjWe%ERtc@}xg3JV%#3R$ye%bT6T3^@S>&Zcp(x<Z
zr|N^@lUiyZP9`jxMBK5CQqk=i)+>ccC4;sX&^i~YMvuYS3n4{D@_}T=$T|t=dbM*=
z{Nn=KF^vr@*)Gd}eINTKNZw7@?yVEnubVeS7a#2|5};8`d3u5SnvEDfk@~^x1}YSC
zj0p5TvoVQN4*hi)x-3875ezebxCt7So@)u1Knnbur9B)9SY2N{E+@g0;BMB2cQ4dr
zb|AW6qq9~CWn#qxW>oqkk%R&Hdxg^eJ6O*P#DZQdh%s|<R2HMU%AaO4(`G1q)~@(2
z94kUyQ^vOjwViA2K9(w=C)OG-ul>`gd}u-bSRgeh`>Xs)Jf2uPc$xz}^k=bDWeBe6
zjgH(APYHhXo_z6@8Oj9BcWY;jp?Z!MoVkif8aF8sWfU$pYn{EiV3+M)Ok4zu`pP>;
z*xa8@0YRQ-3AcRPDxGpuBE_R@FKM3xT-GsYHQgEc+I9lqSEXiM#rxlDlk!!2<`7iJ
zNdkWTkH>Sa5&>zsnj&<9hZGrV<;LVf<gcR-uL+h>Q$hIp4|W+P!3N-uwd;d#+@KPE
z85HZj5ZtOk_IH!)E7I3b8{5>`Wqc7Xn`nr3T3pU~`mDw1PyH49Dq{>7tx`SO6+ji&
z@LrUu850%II+DCukQClt^ca6IbtSwr!H@2o;uu$Ndmr^?SEC#8SsXV?;*60nl$Cez
zcC1$V`}^9P5{|*2LmhQR{N}RFf(K<dok)~0s_UC-<>IUyafAf!K`J6^gVtL#V38?S
zhBAeeP2jN#pZ1AKEAD8;I_F9Pgyeihsab93rx0(@<fcyyWgTmi3wO4p(H(0CpQsy-
z*x%SB*v)m@S0RKTS*5h!MjM-m?n$(J2Sqmq)eo&-D@wC_Yh|71{^C=0o|kq0vgb2f
zJ@8p3T*92kwzE6{08+!5P4H<(Z`iH*Daqb5;ay`QO|i4t*^K=)6S*(^P=|EDJ<YYI
zlzRT${Sc$qa?*vmx_;G-sLF&1JNgQF4#_^bfh2~V9lh`yfi_>#i1VJ##RIx}*<5s%
z7@gL<3fdYhZ#MU#fB>z`m&kR;r8AFz9TB2?>d~02L1$fugEQhO$e1Z3FeIg03UOh>
zseRA3=#VNdQF<|#ZFohCzeg*Pr83y*UJ^DDx`*#eLF@GVg_9i>Lr2DArn#^v?gc>D
z41F%lU?e)HfvO|u{@H|l=dn&od~~8?@!Ab36ALJuPSM%&x)j58>~Y#S>rhJe{-bjZ
zH@Puf?+ta4TST(YzPeh5!bVmFALVsez+~dFNP2mjQqK7u-KdKnZt}4x!K6vDN)v3x
zV%wH~KaDzfeF36TCY0533-R-obSi{;hEs0B24Y+~_QDHV=f)qf5Q2?dkYYF(6~bNN
zEk(DF4XZ=5>#W?03ZghoQJlMvRdTJbdJVw`C~B)pNo5+nSw1_k$=}W6`l@vnSc)rI
z6~o{D0>^dg6~@OO9fCFTFD9dGY~<sL4uR3bge#~Xgch<UNk)As;as(F=x0yS&%!1Q
z)rF#}oeTF9jUj0}%vg-RwYeAhDgHo{Ih#F&49HKN7ToK#|E-FlF(Lu$5{+3VAZxDA
zf0I8`%(zKqIS)g&3$7=GvID?K!{Ql$<P6K;5u$KqiFCNGNgi0TKPfm)IVw6N(x|><
zS}Rx;H_8Yan_vomapD)wg6-le8#6m?8EC1T^yQo#lO;yVswaGwQsJ9VrraO%P()jT
z#reY$Dv-25hDOjU;%Y#tL+&#nk%*U(;o$g!Zl@;vr?2aSrEjme!F#rlwNJ&K_8AbE
zy?*t9+NTbcyB()fKu_)aVyM*4x(~<*Wa#>uD@eH`gA)}#-;6k`eedr|FSZ2T6M{9@
z7Jh*Ou(iU_eeZW1rFHF$GRmEMJ}&%}g7OK9Tm7Qg!4gF)K&0!N6>~KVt1e}k#qOS@
z>_L5$*Iil#F20uu90??opbBx744<QC=bZ2R(EyISB5wd1W&y%E;!lKT84m93-}S<_
zQ7kazlFF<KHrSq9q8qHD6I4ebn6Xw25sJ05E^H?Ad5N#j;P0ELzIVb;@@GOIoYINR
z*CWs^?+>BO5`uQ!a?OL`B$a0%lUb(_Qo+^h4tATxcUUVT)JbE6?wPQs;aXp5ZvdWJ
z#uUF~q)Nh*$T0_VOR_j-fGvhR@F^3ewAzGfNK}ww^adWVai&el1VC4oQ8>2ftnHMD
zA-zB{K8w{&XjuJ%>^H!pcVL_At{%0+JDz61573{kB5`2hE8;I`&4y~w$_Kt{IW1|q
zKj9+)!2vj0a)Rg~a0$s^3tR=&3-ifK`;~ZjBnT<|3pc&(hmx9?5n8)$H<nZ7y|-Ve
zP1jpRnxY$PDbA}4df3v|Y~oxkkO-PpOuw7H>T3E|kXd3AH-=56R+C?%>^J>sL$x_7
zRfFV}2H;gU$@nZWoPaOS^`I8HX{*>IcU?5%wy#<k2XdN20`$PdqM1-r$MAjlIoBXC
zK-o^yUKd^rEb>O<EiDE7kML;q2)a!*SM;MOa&L28gI+asi_xS<-b}nkzapaxeeD)*
z*#oxD51N%*Y1$TC=Ze-?9c+Zz=TV<jk{1F!O8EOdb>?5H*dYHMm(-7nRLa`QJw<L$
zyz<L8L&qrZ)9<=&y1m&a9j?B-KgJ2y9^OlE4bCCknyv%d0%4>Eiq@rUDt`MN8h>vC
z)yIIlnPo-v%hEJ?$1zLmI;dIHb3CqjZasP(+q6WU4HKi~-CoJodII-0xQf2}|Avpb
z(s|CFHIR7~Id&19<>=?S+1+W?ONmLrZ@b55q=_^Pp8fg4P=mq3P(`e-O@47`5O}-n
zb1I`!a}ozbfd)o_4UT4c6u$CXML~+JE+Zx-{)Mu#9{}qMZU<q&BK8m|(WA(Xm(UJP
zVK%^i_G<kb=`$wyj!iB7N{VMQ0iocQRe`a6i}M%z31E=ute77!Sg?p)TwJ9jh0TjO
z0*&ADwhiqt8eu<(dPf-6_K<CT+MwB=4Oy<{0qeeP>f?I<ge8|;NQr{g<;yt8SesNh
zWH7253P7A&zHrC+XI^G18c!^O>A;7T>&$woCYU$h;x35T%cJ+-FCxx{+vvl!a$^om
zH}#je@VKY$%N%_IdmZ<<NY}pDg(!B^S=K~z<<dNn>>{~YAMmWApRGObp|n~`x5=0!
zK5-R*{mP+1emMEVi-3Ma2O!Dn0CnOmDZGJ#9Ep6FQ3zOGh_Wtket_n0#z%D;B;gGu
zHctIk%a`<L!mMmvKXD~yrrfI5K2wQtX}QysH~k<l5(T%ulI33p=2*<r6ucuNJZ^Fk
zGv6V%`NFB#|C%LRGQaemVj*C2RPim}NoF9*fmN4z->O8Z-{{aAf-~-rnk@iiRypr>
zX9MzUOJmCjD(ihX?SkW%&i`0Y7jt8$`SLO?p?C6F`=SCX0GH^67puGyguvS8s7tEJ
z_vkuTFJgP#NrCQjSeRA|;e>2nT7+0}8+)fMfkoASTw(nsnDW-ok-m;PSHDq9qQqWs
zyIQB&+%Zmi|C^*Lh})|o>{a<~EAE;Ne#$f1)k-tqKG$oPhoPKq%6aL!G}A~t|GclR
zBF$T2pOv83Oi;(Q@v{qDK@X(C2Jn)|3WLys%yFc~KowTH*{<$$E5&`VSHMVjoJmy)
z5CF1YY1yBlxJy&)!0;<Z>5cZnA`v2vJa_|A9q~fu%0yNL42y+u7CM#+*M#A-09Z^<
zevK?(A@_Z3@f0+Jeqgv!Vb5l2Y4j~Jh=v_H(|_jR!1RC;3l{N5GHzFf&?o5dWX0BH
z!Tx*gevjV^Eti^-{7mFZg8+j9>Huajn?FBZu{HP>LuL#)V^kS?wz?S@g3jAU`(1?n
zVVRXPD~atc!nyPs*tR!%7mm3oY@!VHSPph&sTE}j*JP3C{73vXx`+sv#bm5AfkAMB
zu(eRvqOdg{Hk)ssF)F5@!)}7qp4YZ2l%kMZMYAEUYN<BR<c1u!&29KIXhfSU15<qg
z{9j=N0O094tTAgQJlDX$`J`*Tla|l_3dmzKS%!#U2_-uS=V`}=tlRfC_c>ij7pk=`
z6f7um(@01=N3jRJE3BVBA0jG7S@QAb@xc;5XzzSv-*biyq`e0dct29_dAUP04NVd+
zQ9#3AdfU}lTF$|CTwN~bATziHUSW|I%r%}NLT=T8sUR3$2?)T(4`Anx;*6p`QV(C(
z=q>yHm9s>xv$&*(n?3I_^iYL6nYdxOjAEQn<s)#I)(CwMt!v}!+J~Grf1zfRp3Hhv
z(+m3Q;GDO1c<LpM;<Y;Zo)Ne=nL6NA%V#HRTsevQKKvt~Sm<Q^KJ)k|!FsqAkHsl{
z{u^i~e=UUmW6U%sv|Yb_2jnZvw-HRtf68w>XH*lm{D#qL*sv&UG<As-)W$gw;bQzn
z{|0wA&dHBN+UQ-UT<L}5F~n$L^2ldiL^!6uE>Zep_+p(-X5rVJOI*t-{x|>5c-g0G
zR$6PQG<ytqtIt-_8qIj1h6T=gpABzi5H1=~kH^d+tO5!4I|5r?h=Nn&9KFdrRBSa;
z*{zE^uitA$1ApSO^5cv978Vd&XEo%ti1&Ohk7mT)@jV^&^M@h18Vl)TZw@93x>okK
z7+~zXr5@5QkA#zDobV!-ZDtv}!CZZCQsmG<pr0SHNagh!hk!Odp7GK$+>aLOQ}$IB
zpD91LJABGOSyzzzcsw1`{*P0ocBlVUSeXd|EuhfC{pSJn(9MytUF<<oN*e3eo5IGo
z6Xk&JX2R;LiSY$4RKLH?HEA!o<ClW&w6EY?&#o+_J(RZY;a=oMNYu^C$39HFBJQ#Q
z0R}HEBukt+Rnw?GS{)ATp9e+-o{#h{@8sBkZu?2>y*RG|Jy86Z$KAWwk%0DGx%S}Q
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%0D;Bf^yz0FjcL5D|&0l;_xtvZV
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

literal 0
HcmV?d00001

diff --git a/base/static/img/undraw_posting_photo.svg b/base/static/img/undraw_posting_photo.svg
deleted file mode 100755
index fc0d549c1..000000000
--- a/base/static/img/undraw_posting_photo.svg
+++ /dev/null
@@ -1 +0,0 @@
-<svg id="fe93ff64-a18b-49f4-bb52-e425cf20d0d6" data-name="Layer 1" xmlns="http://www.w3.org/2000/svg" width="1050" height="594.02" viewBox="0 0 1050 594.02"><title>posting photo</title><ellipse cx="525" cy="561.02" rx="525" ry="33" fill="#4e73df" opacity="0.1"/><polygon points="497.09 549.99 318.9 547.71 319.43 543.14 328.04 467.75 484.53 467.75 496.04 543.14 496.92 548.85 497.09 549.99" fill="#d0d2d5"/><polygon points="496.92 548.85 408 548.85 318.9 547.71 319.43 543.14 496.04 543.14 496.92 548.85" opacity="0.1"/><rect x="289.2" y="544.28" width="236.45" height="5.71" fill="#d0d2d5"/><path d="M826.24,167.93A14.87,14.87,0,0,0,811.44,153H151.12a14.87,14.87,0,0,0-14.8,14.94V568.2H826.24Z" transform="translate(-75 -152.99)" fill="#3f3d56"/><path d="M136.32,564.2v46.88a14.8,14.8,0,0,0,14.8,14.8H811.44a14.8,14.8,0,0,0,14.8-14.8V564.2Z" transform="translate(-75 -152.99)" fill="#d0d2d5"/><rect x="89.88" y="25.13" width="636.23" height="359.81" fill="#fff"/><path d="M484.71,608.09a15.43,15.43,0,0,0,12.13-5.88v0a16.06,16.06,0,0,0,1.2-1.76L489.57,599l9.15.07a15.44,15.44,0,0,0,.29-12.22l-12.27,6.36,11.32-8.32a15.42,15.42,0,1,0-25.47,17.26v0A15.43,15.43,0,0,0,484.71,608.09Z" transform="translate(-75 -152.99)" fill="#4e73df"/><polygon points="425.13 472.89 496.22 544.28 485.31 472.89 425.13 472.89" opacity="0.1"/><path d="M709.94,364.1a1.48,1.48,0,0,0,0-.21,55.29,55.29,0,0,0-2.66-14.57c-.09-.27-.17-.54-.27-.8a55.77,55.77,0,0,0-21.32-28,55.47,55.47,0,0,0-72.69,9A78.52,78.52,0,0,0,608.57,314a248.45,248.45,0,0,1-44,1.64,177.65,177.65,0,0,0,27.91,10.14l-.34,1.27a178.73,178.73,0,0,1-31.19-11.67l-3-1.46,3.36.22a249.73,249.73,0,0,0,46.82-1.35,79.17,79.17,0,0,0-13.8-21.9c-25.18-2.54-50.17-7.82-73.48-18.3l.54-1.19c22.7,10.2,47,15.45,71.61,18a78.63,78.63,0,0,0-125,13.28A108.05,108.05,0,0,0,441.16,242a251.7,251.7,0,0,1-41.45,12.56,250.58,250.58,0,0,1-64.81,5.14,177.9,177.9,0,0,0,27.9,10.14l-.34,1.26a179,179,0,0,1-31.19-11.66l-3-1.47,3.35.22A248.9,248.9,0,0,0,440.24,241c-1.29-1.42-2.63-2.81-4-4.17-43.06.87-89.95.45-132.4-15A108.28,108.28,0,0,0,252.44,314c0,20.32,5.58,48.27,15.3,76.31A325.56,325.56,0,0,0,283,427.06c3,6,6.12,11.9,9.44,17.52h0a198.58,198.58,0,0,0,13.16,19.71c.86,1.13,1.73,2.24,2.6,3.32a120.36,120.36,0,0,0,16.42,17h0q1.82,1.52,3.67,2.9A69.49,69.49,0,0,0,338.82,494a48.34,48.34,0,0,0,19.81,5.38c.55,0,1.09,0,1.64,0v.23h294v-.23h.22a14.74,14.74,0,0,0,5-.88c10.4-3.69,20-18.5,27.93-37.21,1.76-4.15,3.44-8.49,5-12.95,1.41-3.93,2.75-8,4-12a371.64,371.64,0,0,0,9.25-36.12c2.8-13.88,4.35-26,4.35-33.68C710,365.76,710,364.93,709.94,364.1Z" transform="translate(-75 -152.99)" fill="#4e73df" opacity="0.1"/><path d="M434.91,235.5a107.89,107.89,0,0,0-129.62-14.61C346.83,235.77,392.68,236.32,434.91,235.5Z" transform="translate(-75 -152.99)" fill="#4e73df" opacity="0.1"/><path d="M675.72,477.05l-45.37-78.59a1.45,1.45,0,0,0-2.51,0l-45.37,78.59a1.45,1.45,0,0,0,1.25,2.17h13.54a1.46,1.46,0,0,1,1.45,1.44v16.79a1.44,1.44,0,0,0,1.44,1.45h17.66a1.45,1.45,0,0,0,1.45-1.45v-8.1a1.44,1.44,0,0,1,1.44-1.45h16.79a1.45,1.45,0,0,1,1.45,1.45v8.1a1.45,1.45,0,0,0,1.45,1.45H658a1.44,1.44,0,0,0,1.37-1,1.34,1.34,0,0,0,.08-.46V480.66a1.45,1.45,0,0,1,1.45-1.44h13.53A1.45,1.45,0,0,0,675.72,477.05Zm-63.26,8.69a1.4,1.4,0,0,1-1,.43h-6.37a1.45,1.45,0,0,1-1.45-1.45,1.47,1.47,0,0,1,1.45-1.45h6.37a1.45,1.45,0,0,1,1.45,1.45A1.4,1.4,0,0,1,612.46,485.74Zm41.68,0a1.4,1.4,0,0,1-1,.43h-6.37a1.45,1.45,0,0,1-1-2.47,1.4,1.4,0,0,1,1-.43h6.37a1.45,1.45,0,0,1,1.45,1.45A1.4,1.4,0,0,1,654.14,485.74Z" transform="translate(-75 -152.99)" fill="#4e73df" opacity="0.1"/><path d="M395.28,477.74l-45.37-78.59a1.45,1.45,0,0,0-2.5,0L308.21,467A119.89,119.89,0,0,0,324.63,484H331a1.45,1.45,0,0,1,1.45,1.45,1.47,1.47,0,0,1-1.45,1.45h-2.69a70.22,70.22,0,0,0,10.51,6.53V490a1.44,1.44,0,0,1,1.45-1.44h16.79A1.44,1.44,0,0,1,358.5,490v8.1a1.51,1.51,0,0,0,.13.61,1.44,1.44,0,0,0,1.32.84h17.66a1.41,1.41,0,0,0,1.15-.58,1.44,1.44,0,0,0,.29-.87V481.36a1.45,1.45,0,0,1,1.45-1.45H394A1.44,1.44,0,0,0,395.28,477.74Zm-30,6.65a1.43,1.43,0,0,1,1-.43h6.36a1.45,1.45,0,0,1,1.45,1.45,1.45,1.45,0,0,1-1.45,1.45h-6.36a1.45,1.45,0,0,1-1.45-1.45A1.44,1.44,0,0,1,365.29,484.39Zm-28.5-29.08a1.44,1.44,0,0,1-1.44-1.45v-11a1.44,1.44,0,0,1,1.44-1.45h23.74a1.45,1.45,0,0,1,1.44,1.45v11a1.45,1.45,0,0,1-1.44,1.45Z" transform="translate(-75 -152.99)" fill="#4e73df" opacity="0.1"/><path d="M574.63,336.57H518.48V324.42a2.9,2.9,0,0,0-2.9-2.9H499.09V308.58a1.82,1.82,0,0,0-1.83-1.82H476a1.83,1.83,0,0,0-1.83,1.82v12.94H454.81a2.9,2.9,0,0,0-2.9,2.9v12.14H398.37a.58.58,0,0,0-.59.59v161.2a.58.58,0,0,0,.59.59H434a.58.58,0,0,0,.59-.59V476.68a.6.6,0,0,1,.59-.6h15a.6.6,0,0,1,.59.6v21.68a.58.58,0,0,0,.59.59h70.32a.59.59,0,0,0,.59-.59V476.68a.59.59,0,0,1,.58-.6h15a.59.59,0,0,1,.59.6v21.68a.59.59,0,0,0,.59.59h35.59a.59.59,0,0,0,.59-.59V337.16A.59.59,0,0,0,574.63,336.57Zm-146.46,132a.58.58,0,0,1-.59.59h-22a.58.58,0,0,1-.59-.59v-7.5a.59.59,0,0,1,.59-.6h22a.59.59,0,0,1,.59.6Zm0-19.39a.59.59,0,0,1-.59.59h-22a.59.59,0,0,1-.59-.59v-7.51a.59.59,0,0,1,.59-.59h22a.59.59,0,0,1,.59.59Zm0-19.4a.58.58,0,0,1-.59.59h-22a.58.58,0,0,1-.59-.59v-7.5a.58.58,0,0,1,.59-.59h22a.58.58,0,0,1,.59.59Zm0-19.39a.58.58,0,0,1-.59.59h-22a.58.58,0,0,1-.59-.59v-7.5a.58.58,0,0,1,.59-.59h22a.58.58,0,0,1,.59.59Zm0-19.39a.59.59,0,0,1-.59.59h-22A.59.59,0,0,1,405,391v-7.51a.59.59,0,0,1,.59-.59h22a.59.59,0,0,1,.59.59Zm0-19.4a.58.58,0,0,1-.59.59h-22a.58.58,0,0,1-.59-.59v-7.5a.58.58,0,0,1,.59-.59h22a.58.58,0,0,1,.59.59Zm0-19.39a.58.58,0,0,1-.59.59h-22a.58.58,0,0,1-.59-.59v-7.5a.58.58,0,0,1,.59-.59h22a.58.58,0,0,1,.59.59Zm52.1,116.36a.58.58,0,0,1-.59.59h-22a.58.58,0,0,1-.59-.59v-7.5a.59.59,0,0,1,.59-.6h22a.59.59,0,0,1,.59.6Zm0-19.39a.59.59,0,0,1-.59.59h-22a.59.59,0,0,1-.59-.59v-7.51a.59.59,0,0,1,.59-.59h22a.59.59,0,0,1,.59.59Zm0-19.4a.58.58,0,0,1-.59.59h-22a.58.58,0,0,1-.59-.59v-7.5a.58.58,0,0,1,.59-.59h22a.58.58,0,0,1,.59.59Zm0-19.39a.58.58,0,0,1-.59.59h-22a.58.58,0,0,1-.59-.59v-7.5a.58.58,0,0,1,.59-.59h22a.58.58,0,0,1,.59.59Zm0-19.39a.59.59,0,0,1-.59.59h-22a.59.59,0,0,1-.59-.59v-7.51a.59.59,0,0,1,.59-.59h22a.59.59,0,0,1,.59.59Zm0-19.4a.58.58,0,0,1-.59.59h-22a.58.58,0,0,1-.59-.59v-7.5a.58.58,0,0,1,.59-.59h22a.58.58,0,0,1,.59.59Zm0-19.39a.58.58,0,0,1-.59.59h-22a.58.58,0,0,1-.59-.59v-7.5a.58.58,0,0,1,.59-.59h22a.58.58,0,0,1,.59.59Zm35.61,116.36a.59.59,0,0,1-.59.59h-22a.59.59,0,0,1-.59-.59v-7.5a.6.6,0,0,1,.59-.6h22a.6.6,0,0,1,.59.6Zm0-19.39a.6.6,0,0,1-.59.59h-22a.6.6,0,0,1-.59-.59v-7.51a.6.6,0,0,1,.59-.59h22a.6.6,0,0,1,.59.59Zm0-19.4a.59.59,0,0,1-.59.59h-22a.59.59,0,0,1-.59-.59v-7.5a.59.59,0,0,1,.59-.59h22a.59.59,0,0,1,.59.59Zm0-19.39a.59.59,0,0,1-.59.59h-22a.59.59,0,0,1-.59-.59v-7.5a.59.59,0,0,1,.59-.59h22a.59.59,0,0,1,.59.59Zm0-19.39a.6.6,0,0,1-.59.59h-22a.6.6,0,0,1-.59-.59v-7.51a.6.6,0,0,1,.59-.59h22a.6.6,0,0,1,.59.59Zm0-19.4a.59.59,0,0,1-.59.59h-22a.59.59,0,0,1-.59-.59v-7.5a.59.59,0,0,1,.59-.59h22a.59.59,0,0,1,.59.59Zm0-19.39a.59.59,0,0,1-.59.59h-22a.59.59,0,0,1-.59-.59v-7.5a.59.59,0,0,1,.59-.59h22a.59.59,0,0,1,.59.59ZM568,468.55a.59.59,0,0,1-.59.59h-22a.58.58,0,0,1-.59-.59v-7.5a.59.59,0,0,1,.59-.6h22a.6.6,0,0,1,.59.6Zm0-19.39a.6.6,0,0,1-.59.59h-22a.59.59,0,0,1-.59-.59v-7.51a.59.59,0,0,1,.59-.59h22a.6.6,0,0,1,.59.59Zm0-19.4a.59.59,0,0,1-.59.59h-22a.58.58,0,0,1-.59-.59v-7.5a.58.58,0,0,1,.59-.59h22a.59.59,0,0,1,.59.59Zm0-19.39a.59.59,0,0,1-.59.59h-22a.58.58,0,0,1-.59-.59v-7.5a.58.58,0,0,1,.59-.59h22a.59.59,0,0,1,.59.59ZM568,391a.6.6,0,0,1-.59.59h-22a.59.59,0,0,1-.59-.59v-7.51a.59.59,0,0,1,.59-.59h22a.6.6,0,0,1,.59.59Zm0-19.4a.59.59,0,0,1-.59.59h-22a.58.58,0,0,1-.59-.59v-7.5a.58.58,0,0,1,.59-.59h22a.59.59,0,0,1,.59.59Zm0-19.39a.59.59,0,0,1-.59.59h-22a.58.58,0,0,1-.59-.59v-7.5a.58.58,0,0,1,.59-.59h22a.59.59,0,0,1,.59.59Z" transform="translate(-75 -152.99)" fill="#4e73df" opacity="0.1"/><path d="M414.7,292.87a12.6,12.6,0,0,0-7.33.8,10.79,10.79,0,0,1-8.81,0,12.37,12.37,0,0,0-10.36.2,6.33,6.33,0,0,1-3,.75c-4.2,0-7.7-4.23-8.42-9.81a8.11,8.11,0,0,0,2.09-2.27c2.47-4,6.28-6.51,10.56-6.51s8.06,2.51,10.52,6.44a8.1,8.1,0,0,0,7,3.83h.11C410.4,286.28,413.3,289,414.7,292.87Z" transform="translate(-75 -152.99)" fill="#4e73df" opacity="0.1"/><path d="M427.5,275.35l-6.79,4.31,4.12-7.5a6.73,6.73,0,0,0-4.1-1.46h-.11a8.22,8.22,0,0,1-1.41-.1l-2.3,1.45,1-1.79a8.19,8.19,0,0,1-4-3.05l-4.12,2.61,2.6-4.73a12.05,12.05,0,0,0-9.22-4.67c-4.29,0-8.1,2.55-10.57,6.52a7.87,7.87,0,0,1-7,3.76h-.23c-4.72,0-8.56,5.36-8.56,12s3.84,12,8.56,12a6.48,6.48,0,0,0,3-.74,12.3,12.3,0,0,1,10.36-.2,10.9,10.9,0,0,0,8.81,0,12.35,12.35,0,0,1,10.27.19,6.31,6.31,0,0,0,3,.73c4.72,0,8.56-5.36,8.56-12A15.22,15.22,0,0,0,427.5,275.35Z" transform="translate(-75 -152.99)" fill="#4e73df" opacity="0.1"/><rect x="505.46" y="102.97" width="371.54" height="447.42" rx="19.8" fill="#3f3d56"/><rect x="522" y="148.11" width="336" height="357.15" fill="#fff"/><circle cx="691.23" cy="528.8" r="13.08" fill="#fff"/><path d="M766.23,288.17a6,6,0,1,1,6-6A6,6,0,0,1,766.23,288.17Z" transform="translate(-75 -152.99)" fill="#fff"/><path d="M766.23,276.58a5.55,5.55,0,1,1-5.54,5.55,5.55,5.55,0,0,1,5.54-5.55m0-1a6.55,6.55,0,1,0,6.54,6.55,6.54,6.54,0,0,0-6.54-6.55Z" transform="translate(-75 -152.99)" fill="#fff"/><path d="M899.2,486.3s0-.08,0-.12a32.12,32.12,0,0,0-1.55-8.47l-.15-.46A32.51,32.51,0,0,0,885.09,461a32.23,32.23,0,0,0-42.25,5.22,47.14,47.14,0,0,0-2.57-9,144.23,144.23,0,0,1-25.59,1A102.72,102.72,0,0,0,830.9,464l-.2.74A103.56,103.56,0,0,1,812.57,458l-1.76-.85,2,.13a144.61,144.61,0,0,0,27.22-.78,46.08,46.08,0,0,0-8-12.73c-14.64-1.48-29.17-4.55-42.72-10.64l.31-.7c13.2,5.94,27.35,9,41.63,10.49a45.71,45.71,0,0,0-72.66,7.72A62.74,62.74,0,0,0,743,415.31a147.66,147.66,0,0,1-24.1,7.3,145.91,145.91,0,0,1-37.68,3,102.72,102.72,0,0,0,16.22,5.89l-.2.73a102.73,102.73,0,0,1-18.13-6.78l-1.76-.85,2,.13a144.71,144.71,0,0,0,63.16-10c-.75-.83-1.53-1.63-2.33-2.42-25,.5-52.29.26-77-8.73a62.93,62.93,0,0,0-29.89,53.62c0,11.81,3.25,28.06,8.9,44.36A187.93,187.93,0,0,0,651,522.91c1.72,3.51,3.55,6.92,5.48,10.18h0a117,117,0,0,0,7.65,11.46c.5.65,1,1.3,1.52,1.93a69.63,69.63,0,0,0,9.54,9.87h0c.71.59,1.42,1.15,2.14,1.68a40.31,40.31,0,0,0,6.11,3.81A28,28,0,0,0,695,565c.31,0,.63,0,.95,0v.13H866.81V565h.12a8.76,8.76,0,0,0,2.89-.51c6-2.15,11.61-10.76,16.23-21.64,1-2.41,2-4.93,2.94-7.52.82-2.29,1.59-4.63,2.33-7a215.07,215.07,0,0,0,5.38-21,110.27,110.27,0,0,0,2.53-19.58C899.23,487.27,899.22,486.79,899.2,486.3Z" transform="translate(-75 -152.99)" fill="#4e73df" opacity="0.1"/><path d="M739.31,411.54A62.72,62.72,0,0,0,664,403.05C688.11,411.7,714.76,412,739.31,411.54Z" transform="translate(-75 -152.99)" fill="#4e73df" opacity="0.1"/><path d="M879.3,552l-26.37-45.69a.84.84,0,0,0-1.46,0L825.09,552a.84.84,0,0,0,.73,1.26h7.87a.85.85,0,0,1,.84.84v9.76a.85.85,0,0,0,.84.84h10.27a.85.85,0,0,0,.84-.84v-4.71a.83.83,0,0,1,.84-.84h9.76a.84.84,0,0,1,.84.84v4.71a.85.85,0,0,0,.84.84H869a.84.84,0,0,0,.8-.57.86.86,0,0,0,0-.27v-9.76a.84.84,0,0,1,.84-.84h7.87A.84.84,0,0,0,879.3,552Zm-36.77,5a.86.86,0,0,1-.6.25h-3.7a.85.85,0,0,1-.84-.84.81.81,0,0,1,.25-.6.84.84,0,0,1,.59-.25h3.7a.85.85,0,0,1,.85.85A.84.84,0,0,1,842.53,557Zm24.23,0a.86.86,0,0,1-.6.25h-3.7a.85.85,0,0,1,0-1.69h3.7a.85.85,0,0,1,.85.85A.84.84,0,0,1,866.76,557Z" transform="translate(-75 -152.99)" fill="#4e73df" opacity="0.1"/><path d="M716.27,552.37,689.9,506.68a.84.84,0,0,0-1.46,0l-22.78,39.46A69.45,69.45,0,0,0,675.2,556h3.7a.84.84,0,0,1,.6,1.43.81.81,0,0,1-.6.25h-1.56a41,41,0,0,0,6.11,3.8v-2a.84.84,0,0,1,.84-.84h9.76a.85.85,0,0,1,.84.84v4.71a.78.78,0,0,0,.08.35.83.83,0,0,0,.76.49H706a.84.84,0,0,0,.67-.34.86.86,0,0,0,.17-.5v-9.76a.84.84,0,0,1,.84-.84h7.87A.84.84,0,0,0,716.27,552.37Zm-17.43,3.86a.83.83,0,0,1,.59-.24h3.71a.83.83,0,0,1,.59,1.43.8.8,0,0,1-.59.25h-3.71a.85.85,0,0,1-.84-.84A.86.86,0,0,1,698.84,556.23Zm-16.57-16.9a.84.84,0,0,1-.84-.85v-6.39a.84.84,0,0,1,.84-.84h13.8a.85.85,0,0,1,.84.84v6.39a.85.85,0,0,1-.84.85Z" transform="translate(-75 -152.99)" fill="#4e73df" opacity="0.1"/><path d="M820.53,470.3H787.89v-7.05a1.69,1.69,0,0,0-1.69-1.69h-9.58V454a1.06,1.06,0,0,0-1.06-1.06H763.21a1.05,1.05,0,0,0-1.06,1.06v7.52H750.88a1.69,1.69,0,0,0-1.69,1.69v7.05H718.07a.35.35,0,0,0-.35.34v93.72a.35.35,0,0,0,.35.34h20.68a.34.34,0,0,0,.34-.34V551.75a.35.35,0,0,1,.35-.34h8.73a.35.35,0,0,1,.35.34v12.61a.34.34,0,0,0,.34.34h40.88a.34.34,0,0,0,.34-.34V551.75a.34.34,0,0,1,.34-.34h8.74a.34.34,0,0,1,.34.34v12.61a.35.35,0,0,0,.35.34h20.68a.34.34,0,0,0,.34-.34V470.64A.34.34,0,0,0,820.53,470.3ZM735.39,547a.34.34,0,0,1-.34.34H722.27a.34.34,0,0,1-.34-.34v-4.37a.34.34,0,0,1,.34-.34h12.78a.34.34,0,0,1,.34.34Zm0-11.28a.34.34,0,0,1-.34.34H722.27a.34.34,0,0,1-.34-.34v-4.36a.34.34,0,0,1,.34-.34h12.78a.34.34,0,0,1,.34.34Zm0-11.27a.34.34,0,0,1-.34.34H722.27a.34.34,0,0,1-.34-.34v-4.37a.34.34,0,0,1,.34-.34h12.78a.34.34,0,0,1,.34.34Zm0-11.28a.35.35,0,0,1-.34.35H722.27a.35.35,0,0,1-.34-.35v-4.36a.34.34,0,0,1,.34-.34h12.78a.34.34,0,0,1,.34.34Zm0-11.27a.34.34,0,0,1-.34.34H722.27a.34.34,0,0,1-.34-.34v-4.37a.34.34,0,0,1,.34-.34h12.78a.34.34,0,0,1,.34.34Zm0-11.27a.34.34,0,0,1-.34.34H722.27a.34.34,0,0,1-.34-.34v-4.37a.34.34,0,0,1,.34-.34h12.78a.34.34,0,0,1,.34.34Zm0-11.28a.34.34,0,0,1-.34.34H722.27a.34.34,0,0,1-.34-.34V475a.34.34,0,0,1,.34-.34h12.78a.34.34,0,0,1,.34.34ZM765.68,547a.34.34,0,0,1-.34.34H752.56a.34.34,0,0,1-.34-.34v-4.37a.34.34,0,0,1,.34-.34h12.78a.34.34,0,0,1,.34.34Zm0-11.28a.34.34,0,0,1-.34.34H752.56a.34.34,0,0,1-.34-.34v-4.36a.34.34,0,0,1,.34-.34h12.78a.34.34,0,0,1,.34.34Zm0-11.27a.34.34,0,0,1-.34.34H752.56a.34.34,0,0,1-.34-.34v-4.37a.34.34,0,0,1,.34-.34h12.78a.34.34,0,0,1,.34.34Zm0-11.28a.35.35,0,0,1-.34.35H752.56a.35.35,0,0,1-.34-.35v-4.36a.34.34,0,0,1,.34-.34h12.78a.34.34,0,0,1,.34.34Zm0-11.27a.34.34,0,0,1-.34.34H752.56a.34.34,0,0,1-.34-.34v-4.37a.34.34,0,0,1,.34-.34h12.78a.34.34,0,0,1,.34.34Zm0-11.27a.34.34,0,0,1-.34.34H752.56a.34.34,0,0,1-.34-.34v-4.37a.34.34,0,0,1,.34-.34h12.78a.34.34,0,0,1,.34.34Zm0-11.28a.34.34,0,0,1-.34.34H752.56a.34.34,0,0,1-.34-.34V475a.34.34,0,0,1,.34-.34h12.78a.34.34,0,0,1,.34.34ZM786.38,547a.34.34,0,0,1-.34.34H773.26a.34.34,0,0,1-.34-.34v-4.37a.34.34,0,0,1,.34-.34H786a.34.34,0,0,1,.34.34Zm0-11.28a.34.34,0,0,1-.34.34H773.26a.34.34,0,0,1-.34-.34v-4.36a.34.34,0,0,1,.34-.34H786a.34.34,0,0,1,.34.34Zm0-11.27a.34.34,0,0,1-.34.34H773.26a.34.34,0,0,1-.34-.34v-4.37a.34.34,0,0,1,.34-.34H786a.34.34,0,0,1,.34.34Zm0-11.28a.35.35,0,0,1-.34.35H773.26a.35.35,0,0,1-.34-.35v-4.36a.34.34,0,0,1,.34-.34H786a.34.34,0,0,1,.34.34Zm0-11.27a.34.34,0,0,1-.34.34H773.26a.34.34,0,0,1-.34-.34v-4.37a.34.34,0,0,1,.34-.34H786a.34.34,0,0,1,.34.34Zm0-11.27a.34.34,0,0,1-.34.34H773.26a.34.34,0,0,1-.34-.34v-4.37a.34.34,0,0,1,.34-.34H786a.34.34,0,0,1,.34.34Zm0-11.28a.34.34,0,0,1-.34.34H773.26a.34.34,0,0,1-.34-.34V475a.34.34,0,0,1,.34-.34H786a.34.34,0,0,1,.34.34ZM816.67,547a.35.35,0,0,1-.34.34H803.55a.34.34,0,0,1-.34-.34v-4.37a.34.34,0,0,1,.34-.34h12.78a.34.34,0,0,1,.34.34Zm0-11.28a.34.34,0,0,1-.34.34H803.55a.34.34,0,0,1-.34-.34v-4.36a.34.34,0,0,1,.34-.34h12.78a.34.34,0,0,1,.34.34Zm0-11.27a.34.34,0,0,1-.34.34H803.55a.34.34,0,0,1-.34-.34v-4.37a.34.34,0,0,1,.34-.34h12.78a.35.35,0,0,1,.34.34Zm0-11.28a.35.35,0,0,1-.34.35H803.55a.35.35,0,0,1-.34-.35v-4.36a.34.34,0,0,1,.34-.34h12.78a.34.34,0,0,1,.34.34Zm0-11.27a.34.34,0,0,1-.34.34H803.55a.34.34,0,0,1-.34-.34v-4.37a.34.34,0,0,1,.34-.34h12.78a.35.35,0,0,1,.34.34Zm0-11.27a.35.35,0,0,1-.34.34H803.55a.34.34,0,0,1-.34-.34v-4.37a.34.34,0,0,1,.34-.34h12.78a.34.34,0,0,1,.34.34Zm0-11.28a.34.34,0,0,1-.34.34H803.55a.34.34,0,0,1-.34-.34V475a.34.34,0,0,1,.34-.34h12.78a.34.34,0,0,1,.34.34Z" transform="translate(-75 -152.99)" fill="#4e73df" opacity="0.1"/><path d="M727.56,444.9a7.39,7.39,0,0,0-4.26.46,6.34,6.34,0,0,1-2.55.54,6.24,6.24,0,0,1-2.57-.55,7.18,7.18,0,0,0-6,.12,3.72,3.72,0,0,1-1.73.43c-2.44,0-4.47-2.46-4.89-5.7a4.82,4.82,0,0,0,1.22-1.32,6.86,6.86,0,0,1,12.25,0,4.68,4.68,0,0,0,4,2.23h.07C725.06,441.07,726.74,442.62,727.56,444.9Z" transform="translate(-75 -152.99)" fill="#4e73df" opacity="0.1"/><path d="M735,434.71l-4,2.51,2.4-4.36a3.92,3.92,0,0,0-2.39-.85H731a5.55,5.55,0,0,1-.82-.06l-1.34.84.58-1a4.72,4.72,0,0,1-2.34-1.77l-2.4,1.51,1.52-2.75a7,7,0,0,0-5.37-2.71,7.35,7.35,0,0,0-6.14,3.79,4.6,4.6,0,0,1-4.06,2.19h-.13c-2.75,0-5,3.11-5,7s2.23,7,5,7a3.73,3.73,0,0,0,1.73-.44,7.18,7.18,0,0,1,6-.11,6.41,6.41,0,0,0,2.57.55,6.34,6.34,0,0,0,2.55-.54,7.19,7.19,0,0,1,6,.11,3.64,3.64,0,0,0,1.71.43c2.75,0,5-3.12,5-7A8.86,8.86,0,0,0,735,434.71Z" transform="translate(-75 -152.99)" fill="#4e73df" opacity="0.1"/><rect x="988.64" y="269.17" width="5.36" height="44.17" rx="2.29" fill="#3f3d56"/><rect x="810.55" y="234.57" width="3.01" height="14.54" rx="1.5" fill="#3f3d56"/><rect x="810.44" y="261.19" width="3.39" height="25.31" rx="1.69" fill="#3f3d56"/><rect x="810.49" y="295.35" width="3.23" height="25.53" rx="1.61" fill="#3f3d56"/><rect x="812.25" y="186.51" width="179.29" height="364.37" rx="18.54" fill="#3f3d56"/><rect x="884.6" y="197.39" width="25.04" height="5.08" rx="2.54" fill="#e6e8ec"/><circle cx="916.3" cy="199.94" r="2.88" fill="#e6e8ec"/><path d="M1041.22,349H1020.7v2.47A11.73,11.73,0,0,1,1009,363.19H943.54a11.73,11.73,0,0,1-11.73-11.73V349H912.56a14.25,14.25,0,0,0-14.24,14.24V680.14a14.24,14.24,0,0,0,14.24,14.24h128.66a14.23,14.23,0,0,0,14.24-14.24V363.23A14.24,14.24,0,0,0,1041.22,349Z" transform="translate(-75 -152.99)" fill="#fff"/><path d="M1037.2,524.68v0a14.33,14.33,0,0,0-.7-3.83,1.72,1.72,0,0,0-.07-.21,14.56,14.56,0,0,0-24.65-5,20.46,20.46,0,0,0-1.16-4.07,65.66,65.66,0,0,1-11.55.43,47.79,47.79,0,0,0,7.32,2.66l-.09.33a46.82,46.82,0,0,1-8.18-3.06l-.79-.39.88.06a65.38,65.38,0,0,0,12.28-.35,20.79,20.79,0,0,0-3.62-5.75,61.91,61.91,0,0,1-19.27-4.79l.14-.32a60.89,60.89,0,0,0,18.78,4.73,20.63,20.63,0,0,0-32.78,3.49,28.35,28.35,0,0,0-7-15.94,66.32,66.32,0,0,1-27.87,4.64,46.76,46.76,0,0,0,7.32,2.66l-.09.33a46.82,46.82,0,0,1-8.18-3.06l-.79-.38.88.06a65.26,65.26,0,0,0,28.49-4.52c-.34-.37-.69-.73-1.05-1.09-11.29.23-23.59.12-34.72-3.94a28.4,28.4,0,0,0-13.48,24.19c0,5.33,1.46,12.66,4,20a83.69,83.69,0,0,0,4,9.64q1.17,2.38,2.47,4.6h0a54,54,0,0,0,3.45,5.17l.69.87a32,32,0,0,0,4.3,4.45h0c.32.27.64.52,1,.76a18.94,18.94,0,0,0,2.75,1.72,12.92,12.92,0,0,0,5.2,1.41h.43v.05h77.09v-.05h.06a3.92,3.92,0,0,0,1.3-.23c2.73-1,5.24-4.85,7.32-9.76.47-1.09.91-2.23,1.33-3.4s.72-2.08,1.05-3.15c1-3.2,1.82-6.49,2.43-9.47a50.32,50.32,0,0,0,1.14-8.83C1037.22,525.12,1037.21,524.9,1037.2,524.68Z" transform="translate(-75 -152.99)" fill="#4e73df" opacity="0.1"/><path d="M965.07,491a28.3,28.3,0,0,0-34-3.83C942,491,954,491.17,965.07,491Z" transform="translate(-75 -152.99)" fill="#4e73df" opacity="0.1"/><path d="M1028.23,554.3l-11.9-20.61a.38.38,0,0,0-.66,0l-11.9,20.61a.38.38,0,0,0,.33.57h3.55a.38.38,0,0,1,.38.38v4.4a.38.38,0,0,0,.38.38H1013a.38.38,0,0,0,.38-.38v-2.12a.38.38,0,0,1,.38-.38h4.4a.38.38,0,0,1,.38.38v2.12a.38.38,0,0,0,.38.38h4.63a.38.38,0,0,0,.36-.26.37.37,0,0,0,0-.12v-4.4a.38.38,0,0,1,.38-.38h3.55A.38.38,0,0,0,1028.23,554.3Zm-16.59,2.28a.39.39,0,0,1-.27.11h-1.67a.38.38,0,0,1-.38-.38.35.35,0,0,1,.11-.26.4.4,0,0,1,.27-.12h1.67a.38.38,0,0,1,.38.38A.37.37,0,0,1,1011.64,556.58Zm10.93,0a.37.37,0,0,1-.27.11h-1.67a.38.38,0,0,1-.38-.38.35.35,0,0,1,.11-.26.4.4,0,0,1,.27-.12h1.67a.38.38,0,0,1,.38.38A.37.37,0,0,1,1022.57,556.58Z" transform="translate(-75 -152.99)" fill="#4e73df" opacity="0.1"/><path d="M954.68,554.48l-11.9-20.61a.38.38,0,0,0-.66,0l-10.27,17.8a32,32,0,0,0,4.3,4.45h1.67a.38.38,0,1,1,0,.75h-.7a18.94,18.94,0,0,0,2.75,1.72v-.88a.38.38,0,0,1,.38-.38h4.41a.38.38,0,0,1,.37.38v2.12a.39.39,0,0,0,.38.38h4.64a.38.38,0,0,0,.3-.15.35.35,0,0,0,.07-.23v-4.4a.38.38,0,0,1,.38-.38h3.55A.38.38,0,0,0,954.68,554.48Zm-7.86,1.75a.35.35,0,0,1,.26-.11h1.67a.38.38,0,1,1,0,.75h-1.67a.38.38,0,0,1-.38-.38A.37.37,0,0,1,946.82,556.23Zm-7.48-7.63a.38.38,0,0,1-.38-.38v-2.88a.38.38,0,0,1,.38-.38h6.23a.38.38,0,0,1,.38.38v2.88a.38.38,0,0,1-.38.38Z" transform="translate(-75 -152.99)" fill="#4e73df" opacity="0.1"/><path d="M1001.72,517.46H987v-3.19a.76.76,0,0,0-.76-.76H981.9v-3.39a.48.48,0,0,0-.47-.48h-5.57a.48.48,0,0,0-.48.48v3.39h-5.09a.76.76,0,0,0-.76.76v3.19h-14a.15.15,0,0,0-.15.15v42.28a.16.16,0,0,0,.15.16h9.33a.16.16,0,0,0,.16-.16V554.2a.15.15,0,0,1,.15-.15h3.94a.16.16,0,0,1,.16.15v5.69a.16.16,0,0,0,.15.16h18.44a.16.16,0,0,0,.16-.16V554.2a.15.15,0,0,1,.15-.15h3.94a.16.16,0,0,1,.16.15v5.69a.16.16,0,0,0,.15.16h9.34a.16.16,0,0,0,.15-.16V517.61A.15.15,0,0,0,1001.72,517.46Zm-38.41,34.61a.16.16,0,0,1-.16.16h-5.76a.16.16,0,0,1-.16-.16v-2a.16.16,0,0,1,.16-.15h5.76a.16.16,0,0,1,.16.15Zm0-5.08a.16.16,0,0,1-.16.15h-5.76a.16.16,0,0,1-.16-.15v-2a.16.16,0,0,1,.16-.16h5.76a.16.16,0,0,1,.16.16Zm0-5.09a.16.16,0,0,1-.16.16h-5.76a.16.16,0,0,1-.16-.16v-2a.16.16,0,0,1,.16-.15h5.76a.16.16,0,0,1,.16.15Zm0-5.09a.16.16,0,0,1-.16.16h-5.76a.16.16,0,0,1-.16-.16v-2a.16.16,0,0,1,.16-.16h5.76a.16.16,0,0,1,.16.16Zm0-5.08a.16.16,0,0,1-.16.15h-5.76a.16.16,0,0,1-.16-.15v-2a.16.16,0,0,1,.16-.15h5.76a.16.16,0,0,1,.16.15Zm0-5.09a.16.16,0,0,1-.16.16h-5.76a.16.16,0,0,1-.16-.16v-2a.16.16,0,0,1,.16-.15h5.76a.16.16,0,0,1,.16.15Zm0-5.08a.16.16,0,0,1-.16.15h-5.76a.16.16,0,0,1-.16-.15v-2a.16.16,0,0,1,.16-.16h5.76a.16.16,0,0,1,.16.16ZM977,552.07a.16.16,0,0,1-.15.16h-5.77a.16.16,0,0,1-.15-.16v-2a.15.15,0,0,1,.15-.15h5.77a.15.15,0,0,1,.15.15Zm0-5.08a.15.15,0,0,1-.15.15h-5.77a.15.15,0,0,1-.15-.15v-2a.16.16,0,0,1,.15-.16h5.77a.16.16,0,0,1,.15.16Zm0-5.09a.16.16,0,0,1-.15.16h-5.77a.16.16,0,0,1-.15-.16v-2a.15.15,0,0,1,.15-.15h5.77a.15.15,0,0,1,.15.15Zm0-5.09a.16.16,0,0,1-.15.16h-5.77a.16.16,0,0,1-.15-.16v-2a.16.16,0,0,1,.15-.16h5.77a.16.16,0,0,1,.15.16Zm0-5.08a.15.15,0,0,1-.15.15h-5.77a.15.15,0,0,1-.15-.15v-2a.15.15,0,0,1,.15-.15h5.77a.15.15,0,0,1,.15.15Zm0-5.09a.16.16,0,0,1-.15.16h-5.77a.16.16,0,0,1-.15-.16v-2a.15.15,0,0,1,.15-.15h5.77a.15.15,0,0,1,.15.15Zm0-5.08a.15.15,0,0,1-.15.15h-5.77a.15.15,0,0,1-.15-.15v-2a.16.16,0,0,1,.15-.16h5.77a.16.16,0,0,1,.15.16Zm9.34,30.51a.16.16,0,0,1-.16.16h-5.76a.16.16,0,0,1-.16-.16v-2a.16.16,0,0,1,.16-.15h5.76a.16.16,0,0,1,.16.15Zm0-5.08a.16.16,0,0,1-.16.15h-5.76a.16.16,0,0,1-.16-.15v-2a.16.16,0,0,1,.16-.16h5.76a.16.16,0,0,1,.16.16Zm0-5.09a.16.16,0,0,1-.16.16h-5.76a.16.16,0,0,1-.16-.16v-2a.16.16,0,0,1,.16-.15h5.76a.16.16,0,0,1,.16.15Zm0-5.09a.16.16,0,0,1-.16.16h-5.76a.16.16,0,0,1-.16-.16v-2a.16.16,0,0,1,.16-.16h5.76a.16.16,0,0,1,.16.16Zm0-5.08a.16.16,0,0,1-.16.15h-5.76a.16.16,0,0,1-.16-.15v-2a.16.16,0,0,1,.16-.15h5.76a.16.16,0,0,1,.16.15Zm0-5.09a.16.16,0,0,1-.16.16h-5.76a.16.16,0,0,1-.16-.16v-2a.16.16,0,0,1,.16-.15h5.76a.16.16,0,0,1,.16.15Zm0-5.08a.16.16,0,0,1-.16.15h-5.76a.16.16,0,0,1-.16-.15v-2a.16.16,0,0,1,.16-.16h5.76a.16.16,0,0,1,.16.16ZM1000,552.07a.16.16,0,0,1-.15.16h-5.77a.16.16,0,0,1-.15-.16v-2a.15.15,0,0,1,.15-.15h5.77a.15.15,0,0,1,.15.15Zm0-5.08a.15.15,0,0,1-.15.15h-5.77a.15.15,0,0,1-.15-.15v-2a.16.16,0,0,1,.15-.16h5.77a.16.16,0,0,1,.15.16Zm0-5.09a.16.16,0,0,1-.15.16h-5.77a.16.16,0,0,1-.15-.16v-2a.15.15,0,0,1,.15-.15h5.77a.15.15,0,0,1,.15.15Zm0-5.09a.16.16,0,0,1-.15.16h-5.77a.16.16,0,0,1-.15-.16v-2a.16.16,0,0,1,.15-.16h5.77a.16.16,0,0,1,.15.16Zm0-5.08a.15.15,0,0,1-.15.15h-5.77a.15.15,0,0,1-.15-.15v-2a.15.15,0,0,1,.15-.15h5.77a.15.15,0,0,1,.15.15Zm0-5.09a.16.16,0,0,1-.15.16h-5.77a.16.16,0,0,1-.15-.16v-2a.15.15,0,0,1,.15-.15h5.77a.15.15,0,0,1,.15.15Zm0-5.08a.15.15,0,0,1-.15.15h-5.77a.15.15,0,0,1-.15-.15v-2a.16.16,0,0,1,.15-.16h5.77a.16.16,0,0,1,.15.16Z" transform="translate(-75 -152.99)" fill="#4e73df" opacity="0.1"/><path d="M959.77,506a3.33,3.33,0,0,0-1.92.21,2.82,2.82,0,0,1-1.15.24,2.72,2.72,0,0,1-1.16-.25,3.27,3.27,0,0,0-2.72.06,1.73,1.73,0,0,1-.78.19c-1.1,0-2-1.11-2.21-2.57a2.06,2.06,0,0,0,.55-.59,3.1,3.1,0,0,1,5.53,0,2.11,2.11,0,0,0,1.83,1h0A2.28,2.28,0,0,1,959.77,506Z" transform="translate(-75 -152.99)" fill="#4e73df" opacity="0.1"/><path d="M963.13,501.41l-1.78,1.12,1.08-2a1.75,1.75,0,0,0-1.08-.39h0a1.51,1.51,0,0,1-.37,0l-.61.38.26-.47a2.19,2.19,0,0,1-1.05-.8l-1.08.68.68-1.24a3.16,3.16,0,0,0-2.42-1.22A3.3,3.3,0,0,0,954,499.2a2.09,2.09,0,0,1-1.83,1h-.06c-1.24,0-2.25,1.41-2.25,3.14s1,3.14,2.25,3.14a1.64,1.64,0,0,0,.78-.19,3.23,3.23,0,0,1,2.72,0,2.9,2.9,0,0,0,2.31,0,3.24,3.24,0,0,1,2.69,0,1.6,1.6,0,0,0,.77.19c1.24,0,2.25-1.4,2.25-3.14A4,4,0,0,0,963.13,501.41Z" transform="translate(-75 -152.99)" fill="#4e73df" opacity="0.1"/><path d="M174.65,693.59a37,37,0,0,1-.8,7.76c-.1.48-.21.95-.32,1.41-2.84,11.39-10.85,19.72-20.41,20.25-.32,0-.64,0-1,0-10.11,0-18.66-8.72-21.48-20.73-.08-.32-.15-.64-.22-1a37,37,0,0,1-.8-7.76c0-16.27,10.07-29.45,22.5-29.45S174.65,677.32,174.65,693.59Z" transform="translate(-75 -152.99)" fill="#3f3d56"/><path d="M174.65,693.59a37,37,0,0,1-.8,7.76c-.1.48-.21.95-.32,1.41-.34,0-.67,0-1,0a45.76,45.76,0,0,1-7.36-1,44.92,44.92,0,0,1-6.56,1.5,45.87,45.87,0,0,1-5.14.48l-1.74,0a46.41,46.41,0,0,1-6.16-.41,45.17,45.17,0,0,1-9.67-2.4,45.56,45.56,0,0,1-5.22,1.4c-.08-.32-.15-.64-.22-1a37,37,0,0,1-.8-7.76c0-16.27,10.07-29.45,22.5-29.45S174.65,677.32,174.65,693.59Z" transform="translate(-75 -152.99)" opacity="0.1"/><path d="M222.65,638.72a45.6,45.6,0,0,0-4.9-20.61l-26.46,8.23,23.23-13.65a45.71,45.71,0,0,0-34.36-19.59,45.65,45.65,0,0,0-3.57-4.72l-38,11.83,31.17-18.33a45.73,45.73,0,0,0-72,24.39l32.55,37.47L95,618.2a45.74,45.74,0,0,0,40.93,80.7,45.92,45.92,0,0,0,29.28.81,45.74,45.74,0,0,0,55.62-44.66c0-1,0-2-.1-3A45.74,45.74,0,0,0,222.65,638.72Z" transform="translate(-75 -152.99)" fill="#4e73df"/><path d="M221.86,647.2a122.14,122.14,0,0,0-42.34-.54c-15.89,2.63-32.13,8.42-47.67,4.19-9.12-2.48-17-8.22-25.91-11.41a49.18,49.18,0,0,0-26.75-1.6,45.76,45.76,0,0,0,56.69,61.06,45.92,45.92,0,0,0,29.28.81,45.74,45.74,0,0,0,55.62-44.66c0-1,0-2-.1-3A46,46,0,0,0,221.86,647.2Z" transform="translate(-75 -152.99)" opacity="0.1"/><path d="M568.71,359.13l-19-.84c-4.35-.19-9.31-.13-12.21,3.11-3.09,3.45-2.28,8.87-.46,13.14s4.48,8.36,4.62,13c.21,7.3-5.78,13.08-11.21,18s-11.23,11-10.44,18.27c.62,5.67,5.14,10.05,9.6,13.59a128.25,128.25,0,0,0,21.85,14c4.43,2.24,9.15,4.26,14.12,4.31,4.36.05,8.58-1.42,12.68-2.9,7.13-2.56,14.45-5.33,19.86-10.62a39.92,39.92,0,0,0,6.9-9.54c9.35-17,11.84-38.26,4.24-56.13a31.55,31.55,0,0,0-7-10.66c-8.1-7.67-20.46-8-31.62-7.91a12.39,12.39,0,0,0-5.92,1.05c-1.77,1-3,3.23-2.18,5.08" transform="translate(-75 -152.99)" fill="#393859"/><path d="M544.39,594.37a411.28,411.28,0,0,0,2.24,60.27c.26,2.29.53,4.58,1,6.84,1.28,7,3.9,13.71,5.95,20.54s3.57,14,2.56,21.07q6.6-.69,13.22-1.13l.06-3.4c.12-6.52-2.44-12.88-1.79-19.37.62-6.14,2.6-12.14,2.51-18.31-.09-5.83-2-11.45-2.91-17.21a97.73,97.73,0,0,1-.82-11.6,146.49,146.49,0,0,1,.1-16c.84-10.82,4.06-21.6,2.57-32.35C560.92,587.48,552.5,590.65,544.39,594.37Z" transform="translate(-75 -152.99)" fill="#a0616a"/><path d="M564.36,726.39a3,3,0,0,0,1.47-.24A3.2,3.2,0,0,0,567,724a26.23,26.23,0,0,1,3.36-7.55c1.13-1.73,2.51-3.49,2.53-5.55,0-3.33-3.48-5.66-4.21-8.91a14.38,14.38,0,0,0-.62-3.08c-.82-1.75-3-2.35-4.88-2.74-2.56-.54-5.87-.76-7.14,1.52-1.08,1.94.12,4.3.28,6.51.2,3-1.58,5.76-3.5,8.07-2.25,2.72-8.16,9.23-4.56,13,1.35,1.42,4.29.94,6,1Z" transform="translate(-75 -152.99)" fill="#3f3d56"/><path d="M603,594.37a409.91,409.91,0,0,1-2.25,60.27c-.25,2.29-.52,4.58-.94,6.84-1.28,7-3.9,13.71-6,20.54s-3.56,14-2.55,21.07q-6.6-.69-13.22-1.13l-.06-3.4c-.12-6.52,2.43-12.88,1.78-19.37-.61-6.14-2.59-12.14-2.5-18.31.09-5.83,2-11.45,2.9-17.21a95.67,95.67,0,0,0,.83-11.6,146.49,146.49,0,0,0-.1-16c-.84-10.82-4.07-21.6-2.57-32.35C586.51,587.48,594.92,590.65,603,594.37Z" transform="translate(-75 -152.99)" fill="#a0616a"/><path d="M583.06,726.39a3,3,0,0,1-1.46-.24,3.2,3.2,0,0,1-1.21-2.15,26.23,26.23,0,0,0-3.36-7.55c-1.13-1.73-2.52-3.49-2.53-5.55,0-3.33,3.48-5.66,4.2-8.91a14.39,14.39,0,0,1,.63-3.08c.82-1.75,3-2.35,4.88-2.74,2.56-.54,5.86-.76,7.14,1.52,1.08,1.94-.13,4.3-.28,6.51-.21,3,1.58,5.76,3.5,8.07,2.25,2.72,8.16,9.23,4.56,13-1.35,1.42-4.29.94-6,1Z" transform="translate(-75 -152.99)" fill="#3f3d56"/><circle cx="492.31" cy="243.59" r="20.49" fill="#a0616a"/><path d="M555.7,415.05A7,7,0,0,1,556,418a5.74,5.74,0,0,1-1.72,2.66,30.58,30.58,0,0,1-10.15,6.77c-.4,1.29.35,2.62,1.08,3.74,2.46,3.79,5.06,7.47,7.67,11.16a74.72,74.72,0,0,0,17.43,18.77l6-7.54a48.75,48.75,0,0,0,3.48-4.73,47.18,47.18,0,0,0,3.12-6.39l7.33-17c-4.41.89-8.89-1.14-12.66-3.61a4.94,4.94,0,0,1-1.84-1.76,5,5,0,0,1-.4-2.18q-.18-5.3-.15-10.59a136.14,136.14,0,0,0-16-1.25c-2.08,0-3.48-.44-4,1.76S555.25,412.92,555.7,415.05Z" transform="translate(-75 -152.99)" fill="#a0616a"/><path d="M564.8,453.61a78.77,78.77,0,0,0-12-16,10.8,10.8,0,0,1-2.51-3.29,10,10,0,0,1-.56-3.18l-.36-5.29a1.23,1.23,0,0,0-.27-.82,1.19,1.19,0,0,0-.81-.23,6.77,6.77,0,0,0-3.71.54,10.4,10.4,0,0,0-2,1.84c-2.29,2.35-5.51,3.46-8.53,4.73a68.63,68.63,0,0,0-6.58,3.17c-1.69.93-3.43,2-4.19,3.8a9.39,9.39,0,0,0-.54,3.58L522,485a2.25,2.25,0,0,1-1.68,2.51,6.1,6.1,0,0,0-2.32,1.77,2.4,2.4,0,0,0-.09,2.75c.3.39.76.63,1.07,1,1,1.19.13,2.91-.54,4.29a9.32,9.32,0,0,0-1,5.81,5,5,0,0,0,3.92,4c.79-2.55-1-5.44,0-7.91a5.67,5.67,0,0,1,3.42-2.85,12.29,12.29,0,0,1,6.24-.68l1.2,4.37c4.31,15.74,1.32,32.65-2.61,48.49-.91,3.7-2.06,7.34-2.74,11.09-1,5.63-1,11.38-1,17.1l0,15.64c0,1.9.12,4.05,1.57,5.28s4.12,1.14,5.21,2.84c.63,1,.51,2.29,1.08,3.31a4.38,4.38,0,0,0,1.7,1.55,11.44,11.44,0,0,0,14.91-3.66c1.08-1.71,1.73-3.78,3.33-5,1.83-1.43,4.37-1.39,6.68-1.28l13.62.65a28.19,28.19,0,0,1,6.92.91,53.46,53.46,0,0,1,5.88,2.54,30.29,30.29,0,0,0,13.77,2.5,8,8,0,0,0,3.72-.9c1.3-.78,2.2-2.2,3.63-2.73,1.61-.6,3.68,0,4.93-1.17a4.47,4.47,0,0,0,1-3.17l.57-13.37c.6-13.79,1.13-28-3.42-41-1.11-3.17-2.51-6.24-3.36-9.49A93.86,93.86,0,0,1,606,520c-1.41-9.51-4.62-18.87-4-28.46,0-.73.64-.9,1.36-1,2.54-.25,5.31.22,7.12,2,1.61,1.6,2.18,4,2.36,6.23a7,7,0,0,1-.86,4.68l3.76-2.76c1.2-.88,2.54-2.09,2.3-3.56-.71-4.37-.47-9.26-1-13.65a199.36,199.36,0,0,0-3.59-22.16A58.25,58.25,0,0,1,612,455c-.36-2.92-.16-5.87-.35-8.81a33.18,33.18,0,0,0-3.14-12,12.26,12.26,0,0,0-2-3.18,13.94,13.94,0,0,0-3.88-2.68A79.93,79.93,0,0,0,583,421.2c-1.35-.29-2.9-.51-4,.33-1.4,1.08-1.24,3.25-.62,4.91s1.57,3.33,1.3,5.08-1.76,3.13-3,4.52c-3.17,3.71-4.61,8.71-8,12.25C567.23,449.92,565.13,451.37,564.8,453.61Z" transform="translate(-75 -152.99)" fill="#ff6f61"/><path d="M552.07,386.46c1.73,1.44,3.18,3.44,5.38,3.91,5.3,1.12,9.44-7.45,14.54-5.62,1.86.67,3,2.52,4.43,3.82a8.77,8.77,0,0,0,12-.87c2.68-3.13,2.71-7.65,2.61-11.77a8.85,8.85,0,0,0-.89-4.42,7.12,7.12,0,0,0-1.77-1.86c-6.05-4.73-14.22-5.41-21.88-5.9a16,16,0,0,0-5,.21c-2.28.58-4.16,2.12-6,3.62-3.44,2.86-11.81,8.3-12.86,12.91S548.67,383.64,552.07,386.46Z" transform="translate(-75 -152.99)" fill="#393859"/><rect x="453.12" y="295.07" width="74.28" height="80.43" rx="2.61" fill="#4e73df"/><rect x="459.52" y="302.01" width="61.48" height="48.65" rx="2.61" fill="#fff"/><path d="M588,480.46v0a5.8,5.8,0,0,0-.27-1.46l0-.07a5.53,5.53,0,0,0-9.36-1.9,7.35,7.35,0,0,0-.44-1.54,24.69,24.69,0,0,1-4.38.16,16.21,16.21,0,0,0,2.78,1l0,.13a18.07,18.07,0,0,1-3.1-1.16l-.3-.15.33,0a24.17,24.17,0,0,0,4.66-.13,7.72,7.72,0,0,0-1.37-2.18,23.49,23.49,0,0,1-7.32-1.82l.06-.12a23.14,23.14,0,0,0,7.13,1.79,7.83,7.83,0,0,0-12.45,1.33,10.74,10.74,0,0,0-2.67-6.05,25.14,25.14,0,0,1-10.58,1.76,18.48,18.48,0,0,0,2.78,1l0,.12a18.07,18.07,0,0,1-3.1-1.16l-.3-.14.33,0a24.79,24.79,0,0,0,10.82-1.72c-.13-.14-.26-.28-.4-.41-4.29.09-8.95,0-13.18-1.5a10.8,10.8,0,0,0-5.12,9.19,25.33,25.33,0,0,0,1.52,7.6,32.44,32.44,0,0,0,1.52,3.66c.3.6.61,1.18.94,1.74h0a20.87,20.87,0,0,0,1.31,2l.26.33a11.48,11.48,0,0,0,1.64,1.69h0a4.57,4.57,0,0,0,.36.29,7.58,7.58,0,0,0,1.05.66,4.87,4.87,0,0,0,2,.53h.17v0h29.27v0h0a1.62,1.62,0,0,0,.49-.08c1-.37,2-1.85,2.79-3.71.17-.41.34-.84.5-1.29s.27-.79.4-1.19c.38-1.22.69-2.47.92-3.6a18.77,18.77,0,0,0,.43-3.35Z" transform="translate(-75 -152.99)" fill="#4e73df" opacity="0.3"/><path d="M560.65,467.65a10.72,10.72,0,0,0-12.91-1.45C551.88,467.68,556.44,467.73,560.65,467.65Z" transform="translate(-75 -152.99)" fill="#4e73df" opacity="0.3"/><path d="M584.63,491.7l-4.52-7.82a.14.14,0,0,0-.25,0l-4.52,7.82a.15.15,0,0,0,.13.22h1.35a.14.14,0,0,1,.14.14v1.68a.14.14,0,0,0,.14.14h1.76a.15.15,0,0,0,.15-.14v-.81a.15.15,0,0,1,.14-.15h1.67a.15.15,0,0,1,.15.15v.81a.14.14,0,0,0,.14.14h1.76a.13.13,0,0,0,.13-.1.06.06,0,0,0,0,0v-1.68a.15.15,0,0,1,.15-.14h1.34A.15.15,0,0,0,584.63,491.7Zm-6.3.87a.13.13,0,0,1-.1,0h-.64a.14.14,0,0,1-.14-.14.15.15,0,0,1,0-.1.14.14,0,0,1,.1-.05h.64a.15.15,0,0,1,.14.15A.13.13,0,0,1,578.33,492.57Zm4.15,0a.13.13,0,0,1-.1,0h-.64a.14.14,0,0,1-.14-.14.15.15,0,0,1,0-.1.14.14,0,0,1,.1-.05h.64a.15.15,0,0,1,.14.15A.13.13,0,0,1,582.48,492.57Z" transform="translate(-75 -152.99)" fill="#4e73df" opacity="0.3"/><path d="M556.7,491.77,552.19,484a.14.14,0,0,0-.25,0L548,490.71a11.91,11.91,0,0,0,1.64,1.68h.63a.15.15,0,0,1,.15.15.14.14,0,0,1-.05.1.15.15,0,0,1-.1,0H550a8.55,8.55,0,0,0,1.05.65V493a.15.15,0,0,1,.14-.15h1.68a.15.15,0,0,1,.14.15v.8a.35.35,0,0,0,0,.06.17.17,0,0,0,.13.09h1.76a.14.14,0,0,0,.12-.06.12.12,0,0,0,0-.09v-1.67a.14.14,0,0,1,.14-.14h1.35A.14.14,0,0,0,556.7,491.77Zm-3,.66a.15.15,0,0,1,.1,0h.63a.15.15,0,0,1,.15.15.14.14,0,0,1-.05.1.15.15,0,0,1-.1,0h-.63a.15.15,0,0,1-.15-.14A.16.16,0,0,1,553.72,492.43Zm-2.84-2.89a.15.15,0,0,1-.15-.15V488.3a.15.15,0,0,1,.15-.14h2.36a.15.15,0,0,1,.15.14v1.09a.15.15,0,0,1-.15.15Z" transform="translate(-75 -152.99)" fill="#4e73df" opacity="0.3"/><path d="M574.56,477.71H569v-1.2a.29.29,0,0,0-.29-.29H567v-1.29a.18.18,0,0,0-.18-.18h-2.12a.18.18,0,0,0-.18.18v1.29h-1.93a.29.29,0,0,0-.29.29v1.2H557a.06.06,0,0,0-.06.06v16.06a.06.06,0,0,0,.06.05h3.54s.06,0,.06-.05v-2.16a.06.06,0,0,1,.06-.06h1.5a.06.06,0,0,1,.06.06v2.16s0,.05.06.05h7a.06.06,0,0,0,.06-.05v-2.16s0-.06,0-.06h1.5a.06.06,0,0,1,.06.06v2.16a.06.06,0,0,0,.06.05h3.54a.06.06,0,0,0,.06-.05V477.77A.06.06,0,0,0,574.56,477.71ZM560,490.86a.06.06,0,0,1-.06.06h-2.19a.06.06,0,0,1-.06-.06v-.75a.06.06,0,0,1,.06-.06h2.19a.06.06,0,0,1,.06.06Zm0-1.93a.06.06,0,0,1-.06.06h-2.19a.06.06,0,0,1-.06-.06v-.75a.06.06,0,0,1,.06-.06h2.19a.06.06,0,0,1,.06.06Zm0-1.93a.06.06,0,0,1-.06.05h-2.19a.06.06,0,0,1-.06-.05v-.75a.06.06,0,0,1,.06-.06h2.19a.06.06,0,0,1,.06.06Zm0-1.94a.06.06,0,0,1-.06.06h-2.19a.06.06,0,0,1-.06-.06v-.74a.06.06,0,0,1,.06-.06h2.19a.06.06,0,0,1,.06.06Zm0-1.93a.06.06,0,0,1-.06.06h-2.19a.06.06,0,0,1-.06-.06v-.74a.06.06,0,0,1,.06-.06h2.19a.06.06,0,0,1,.06.06Zm0-1.93a.06.06,0,0,1-.06.06h-2.19a.06.06,0,0,1-.06-.06v-.75a.06.06,0,0,1,.06-.05h2.19a.06.06,0,0,1,.06.05Zm0-1.93a.06.06,0,0,1-.06.06h-2.19a.06.06,0,0,1-.06-.06v-.75a.06.06,0,0,1,.06-.06h2.19a.06.06,0,0,1,.06.06Zm5.19,11.59a.06.06,0,0,1-.06.06h-2.19a.06.06,0,0,1-.06-.06v-.75a.06.06,0,0,1,.06-.06h2.19a.06.06,0,0,1,.06.06Zm0-1.93a.06.06,0,0,1-.06.06h-2.19a.06.06,0,0,1-.06-.06v-.75a.06.06,0,0,1,.06-.06h2.19a.06.06,0,0,1,.06.06Zm0-1.93a.06.06,0,0,1-.06.05h-2.19a.06.06,0,0,1-.06-.05v-.75a.06.06,0,0,1,.06-.06h2.19a.06.06,0,0,1,.06.06Zm0-1.94a.06.06,0,0,1-.06.06h-2.19a.06.06,0,0,1-.06-.06v-.74a.06.06,0,0,1,.06-.06h2.19a.06.06,0,0,1,.06.06Zm0-1.93a.06.06,0,0,1-.06.06h-2.19a.06.06,0,0,1-.06-.06v-.74a.06.06,0,0,1,.06-.06h2.19a.06.06,0,0,1,.06.06Zm0-1.93a.06.06,0,0,1-.06.06h-2.19a.06.06,0,0,1-.06-.06v-.75a.06.06,0,0,1,.06-.05h2.19a.06.06,0,0,1,.06.05Zm0-1.93a.06.06,0,0,1-.06.06h-2.19a.06.06,0,0,1-.06-.06v-.75a.06.06,0,0,1,.06-.06h2.19a.06.06,0,0,1,.06.06Zm3.54,11.59a.06.06,0,0,1-.06.06h-2.19a.06.06,0,0,1-.05-.06v-.75a.06.06,0,0,1,.05-.06h2.19a.06.06,0,0,1,.06.06Zm0-1.93a.06.06,0,0,1-.06.06h-2.19a.06.06,0,0,1-.05-.06v-.75a.06.06,0,0,1,.05-.06h2.19a.06.06,0,0,1,.06.06Zm0-1.93s0,.05-.06.05h-2.19a0,0,0,0,1-.05-.05v-.75a.06.06,0,0,1,.05-.06h2.19a.06.06,0,0,1,.06.06Zm0-1.94a.05.05,0,0,1-.06.06h-2.19s-.05,0-.05-.06v-.74s0-.06.05-.06h2.19a.05.05,0,0,1,.06.06Zm0-1.93a.05.05,0,0,1-.06.06h-2.19s-.05,0-.05-.06v-.74s0-.06.05-.06h2.19a.05.05,0,0,1,.06.06Zm0-1.93a.06.06,0,0,1-.06.06h-2.19a.06.06,0,0,1-.05-.06v-.75a0,0,0,0,1,.05-.05h2.19s.06,0,.06.05Zm0-1.93a.06.06,0,0,1-.06.06h-2.19a.06.06,0,0,1-.05-.06v-.75a.06.06,0,0,1,.05-.06h2.19a.06.06,0,0,1,.06.06Zm5.19,11.59a.06.06,0,0,1-.06.06h-2.19a.06.06,0,0,1-.06-.06v-.75a.06.06,0,0,1,.06-.06h2.19a.06.06,0,0,1,.06.06Zm0-1.93a.06.06,0,0,1-.06.06h-2.19a.06.06,0,0,1-.06-.06v-.75a.06.06,0,0,1,.06-.06h2.19a.06.06,0,0,1,.06.06Zm0-1.93a.06.06,0,0,1-.06.05h-2.19a.06.06,0,0,1-.06-.05v-.75a.06.06,0,0,1,.06-.06h2.19a.06.06,0,0,1,.06.06Zm0-1.94a.06.06,0,0,1-.06.06h-2.19a.06.06,0,0,1-.06-.06v-.74a.06.06,0,0,1,.06-.06h2.19a.06.06,0,0,1,.06.06Zm0-1.93a.06.06,0,0,1-.06.06h-2.19a.06.06,0,0,1-.06-.06v-.74a.06.06,0,0,1,.06-.06h2.19a.06.06,0,0,1,.06.06Zm0-1.93a.06.06,0,0,1-.06.06h-2.19a.06.06,0,0,1-.06-.06v-.75a.06.06,0,0,1,.06-.05h2.19a.06.06,0,0,1,.06.05Zm0-1.93a.06.06,0,0,1-.06.06h-2.19a.06.06,0,0,1-.06-.06v-.75a.06.06,0,0,1,.06-.06h2.19a.06.06,0,0,1,.06.06Z" transform="translate(-75 -152.99)" fill="#4e73df" opacity="0.3"/><path d="M558.64,473.36a1.38,1.38,0,0,0-.73.08,1,1,0,0,1-.88,0,1.23,1.23,0,0,0-1,0,.61.61,0,0,1-.3.08c-.42,0-.77-.43-.84-1a.77.77,0,0,0,.21-.23,1.28,1.28,0,0,1,1-.65,1.27,1.27,0,0,1,1,.65.81.81,0,0,0,.69.38h0A.87.87,0,0,1,558.64,473.36Z" transform="translate(-75 -152.99)" fill="#4e73df" opacity="0.1"/><path d="M559.91,471.62l-.67.43.41-.75a.7.7,0,0,0-.41-.14h-.15l-.23.14.09-.18a.79.79,0,0,1-.4-.3l-.41.26.26-.47a1.2,1.2,0,0,0-.92-.47,1.28,1.28,0,0,0-1.05.65.79.79,0,0,1-.69.38h0c-.47,0-.85.53-.85,1.19s.38,1.19.85,1.19a.73.73,0,0,0,.3-.07,1.2,1.2,0,0,1,1,0,1.12,1.12,0,0,0,.44.09,1.08,1.08,0,0,0,.44-.09,1.21,1.21,0,0,1,1,0,.73.73,0,0,0,.3.07c.47,0,.85-.53.85-1.19A1.52,1.52,0,0,0,559.91,471.62Z" transform="translate(-75 -152.99)" fill="#4e73df" opacity="0.1"/><ellipse cx="450.81" cy="350.66" rx="6.15" ry="10.25" fill="#a0616a"/><ellipse cx="531.76" cy="345.53" rx="6.15" ry="10.25" fill="#a0616a"/></svg>
\ No newline at end of file
diff --git a/base/static/img/undraw_profile.svg b/base/static/img/undraw_profile.svg
deleted file mode 100755
index 980234178..000000000
--- a/base/static/img/undraw_profile.svg
+++ /dev/null
@@ -1,38 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<!-- Generator: Adobe Illustrator 25.0.0, SVG Export Plug-In . SVG Version: 6.00 Build 0)  -->
-<svg version="1.1" id="Layer_1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px"
-	 viewBox="0 0 108.3 108.3" style="enable-background:new 0 0 108.3 108.3;" xml:space="preserve">
-<style type="text/css">
-	.st0{fill:#E6E6E6;}
-	.st1{fill:#FFB8B8;}
-	.st2{fill:#575A89;}
-	.st3{fill:#2F2E41;}
-</style>
-<g id="Group_45" transform="translate(-191 -152.079)">
-	<g id="Group_30" transform="translate(282.246 224.353)">
-		<path id="Path_944" class="st0" d="M17.1-18.1c0,10.5-3,20.8-8.8,29.6c-1.2,1.9-2.5,3.6-4,5.3c-3.4,4-7.3,7.4-11.6,10.3
-			c-1.2,0.8-2.4,1.5-3.6,2.2c-6.5,3.6-13.7,5.8-21,6.5c-1.7,0.2-3.4,0.2-5.1,0.2c-4.7,0-9.4-0.6-14-1.8c-2.6-0.7-5.1-1.6-7.6-2.6
-			c-1.3-0.5-2.5-1.1-3.7-1.8c-2.9-1.5-5.6-3.3-8.2-5.3c-1.2-0.9-2.3-1.9-3.4-2.9C-95.8,1.3-97.1-33-76.8-54.9s54.6-23.3,76.5-2.9
-			C10.8-47.6,17.1-33.2,17.1-18.1L17.1-18.1z"/>
-		<path id="Path_945" class="st1" d="M-50.2-13.2c0,0,4.9,13.7,1.1,21.4s6,16.4,6,16.4s25.8-13.1,22.5-19.7s-8.8-15.3-7.7-20.8
-			L-50.2-13.2z"/>
-		<ellipse id="Ellipse_185" class="st1" cx="-40.6" cy="-25.5" rx="17.5" ry="17.5"/>
-		<path id="Path_946" class="st2" d="M-51.1,34.2c-2.6-0.7-5.1-1.6-7.6-2.6l0.5-13.3l4.9-11c1.1,0.9,2.3,1.6,3.5,2.3
-			c0.3,0.2,0.6,0.3,0.9,0.5c4.6,2.2,12.2,4.2,19.5-1.3c2.7-2.1,5-4.7,6.7-7.6L-8.8,9l0.7,8.4l0.8,9.8c-1.2,0.8-2.4,1.5-3.6,2.2
-			c-6.5,3.6-13.7,5.8-21,6.5c-1.7,0.2-3.4,0.2-5.1,0.2C-41.8,36.1-46.5,35.4-51.1,34.2z"/>
-		<path id="Path_947" class="st2" d="M-47.7-0.9L-47.7-0.9l-0.7,7.2l-0.4,3.8l-0.5,5.6l-1.8,18.5c-2.6-0.7-5.1-1.6-7.6-2.6
-			c-1.3-0.5-2.5-1.1-3.7-1.8c-2.9-1.5-5.6-3.3-8.2-5.3l-1.9-9l0.1-0.1L-47.7-0.9z"/>
-		<path id="Path_948" class="st2" d="M-10.9,29.3c-6.5,3.6-13.7,5.8-21,6.5c0.4-6.7,1-13.1,1.6-18.8c0.3-2.9,0.7-5.7,1.1-8.2
-			c1.2-8,2.5-13.5,3.4-14.2l6.1,4L4.9,7.3l-0.5,9.5c-3.4,4-7.3,7.4-11.6,10.3C-8.5,27.9-9.7,28.7-10.9,29.3z"/>
-		<path id="Path_949" class="st2" d="M-70.5,24.6c-1.2-0.9-2.3-1.9-3.4-2.9l0.9-6.1l0.7-0.1l3.1-0.4l6.8,14.8
-			C-65.2,28.3-67.9,26.6-70.5,24.6L-70.5,24.6z"/>
-		<path id="Path_950" class="st2" d="M8.3,11.5c-1.2,1.9-2.5,3.6-4,5.3c-3.4,4-7.3,7.4-11.6,10.3c-1.2,0.8-2.4,1.5-3.6,2.2l-0.6-2.8
-			l3.5-9.1l4.2-11.1l8.8,1.1C6.1,8.7,7.2,10.1,8.3,11.5z"/>
-		<path id="Path_951" class="st3" d="M-23.9-41.4c-2.7-4.3-6.8-7.5-11.6-8.9l-3.6,2.9l1.4-3.3c-1.2-0.2-2.3-0.2-3.5-0.2l-3.2,4.1
-			l1.3-4c-5.6,0.7-10.7,3.7-14,8.3c-4.1,5.9-4.8,14.1-0.8,20c1.1-3.4,2.4-6.6,3.5-9.9c0.9,0.1,1.7,0.1,2.6,0l1.3-3.1l0.4,3
-			c4.2-0.4,10.3-1.2,14.3-1.9l-0.4-2.3l2.3,1.9c1.2-0.3,1.9-0.5,1.9-0.7c2.9,4.7,5.8,7.7,8.8,12.5C-22.1-29.8-20.2-35.3-23.9-41.4z"
-			/>
-		<ellipse id="Ellipse_186" class="st1" cx="-24.9" cy="-26.1" rx="1.2" ry="2.4"/>
-	</g>
-</g>
-</svg>
diff --git a/base/static/img/undraw_profile_1.svg b/base/static/img/undraw_profile_1.svg
deleted file mode 100755
index fcc91c706..000000000
--- a/base/static/img/undraw_profile_1.svg
+++ /dev/null
@@ -1,38 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<!-- Generator: Adobe Illustrator 25.0.0, SVG Export Plug-In . SVG Version: 6.00 Build 0)  -->
-<svg version="1.1" id="_x38_8ce59e9-c4b8-4d1d-9d7a-ce0190159aa8"
-	 xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px" viewBox="0 0 231.8 231.8"
-	 style="enable-background:new 0 0 231.8 231.8;" xml:space="preserve">
-<style type="text/css">
-	.st0{opacity:0.5;}
-	.st1{fill:url(#SVGID_1_);}
-	.st2{fill:#F5F5F5;}
-	.st3{fill:#333333;}
-	.st4{fill:#4E73DF;}
-	.st5{opacity:0.1;enable-background:new    ;}
-	.st6{fill:#BE7C5E;}
-</style>
-<g class="st0">
-	
-		<linearGradient id="SVGID_1_" gradientUnits="userSpaceOnUse" x1="115.89" y1="525.2" x2="115.89" y2="756.98" gradientTransform="matrix(1 0 0 -1 0 756.98)">
-		<stop  offset="0" style="stop-color:#808080;stop-opacity:0.25"/>
-		<stop  offset="0.54" style="stop-color:#808080;stop-opacity:0.12"/>
-		<stop  offset="1" style="stop-color:#808080;stop-opacity:0.1"/>
-	</linearGradient>
-	<circle class="st1" cx="115.9" cy="115.9" r="115.9"/>
-</g>
-<circle class="st2" cx="115.9" cy="115.3" r="113.4"/>
-<path class="st3" d="M71.6,116.3c0,0-12.9,63.4-19.9,59.8c0,0,67.7,58.5,127.5,0c0,0-10.5-44.6-25.7-59.8H71.6z"/>
-<path class="st4" d="M116.2,229c22.2,0,43.9-6.5,62.4-18.7c-4.2-22.8-20.1-24.1-20.1-24.1H70.8c0,0-15,1.2-19.7,22.2
-	C70.1,221.9,92.9,229.1,116.2,229z"/>
-<circle class="st3" cx="115" cy="112.8" r="50.3"/>
-<path class="st5" d="M97.3,158.4h35.1l0,0v28.1c0,9.7-7.8,17.5-17.5,17.5l0,0c-9.7,0-17.5-7.9-17.5-17.5L97.3,158.4L97.3,158.4z"/>
-<path class="st6" d="M100.7,157.1h28.4c1.9,0,3.4,1.5,3.4,3.3v0v24.7c0,9.7-7.8,17.5-17.5,17.5l0,0c-9.7,0-17.5-7.9-17.5-17.5v0
-	v-24.7C97.4,158.6,98.9,157.1,100.7,157.1z"/>
-<path class="st5" d="M97.4,171.6c11.3,4.2,23.8,4.3,35.1,0.1v-4.3H97.4V171.6z"/>
-<circle class="st6" cx="115" cy="123.7" r="50.3"/>
-<path class="st3" d="M66.9,104.6h95.9c0,0-8.2-38.7-44.4-36.2S66.9,104.6,66.9,104.6z"/>
-<ellipse class="st6" cx="65.8" cy="121.5" rx="4.7" ry="8.8"/>
-<ellipse class="st6" cx="164" cy="121.5" rx="4.7" ry="8.8"/>
-<path class="st5" d="M66.9,105.9h95.9c0,0-8.2-38.7-44.4-36.2S66.9,105.9,66.9,105.9z"/>
-</svg>
diff --git a/base/static/img/undraw_profile_2.svg b/base/static/img/undraw_profile_2.svg
deleted file mode 100755
index 488d1bd67..000000000
--- a/base/static/img/undraw_profile_2.svg
+++ /dev/null
@@ -1,44 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<!-- Generator: Adobe Illustrator 25.0.0, SVG Export Plug-In . SVG Version: 6.00 Build 0)  -->
-<svg version="1.1" id="_x38_8ce59e9-c4b8-4d1d-9d7a-ce0190159aa8"
-	 xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px" viewBox="0 0 231.8 231.8"
-	 style="enable-background:new 0 0 231.8 231.8;" xml:space="preserve">
-<style type="text/css">
-	.st0{opacity:0.5;}
-	.st1{fill:url(#SVGID_1_);}
-	.st2{fill:#F5F5F5;}
-	.st3{fill:#4E73DF;}
-	.st4{fill:#72351C;}
-	.st5{opacity:0.1;enable-background:new    ;}
-	.st6{fill:#FDA57D;}
-</style>
-<g class="st0">
-	
-		<linearGradient id="SVGID_1_" gradientUnits="userSpaceOnUse" x1="115.89" y1="526.22" x2="115.89" y2="758" gradientTransform="matrix(1 0 0 -1 0 758)">
-		<stop  offset="0" style="stop-color:#808080;stop-opacity:0.25"/>
-		<stop  offset="0.54" style="stop-color:#808080;stop-opacity:0.12"/>
-		<stop  offset="1" style="stop-color:#808080;stop-opacity:0.1"/>
-	</linearGradient>
-	<circle class="st1" cx="115.9" cy="115.9" r="115.9"/>
-</g>
-<circle class="st2" cx="116.1" cy="115.1" r="113.4"/>
-<path class="st3" d="M116.2,229c22.2,0,43.9-6.5,62.4-18.7c-4.2-22.9-20.1-24.2-20.1-24.2H70.8c0,0-15,1.2-19.7,22.2
-	C70.1,221.9,92.9,229.1,116.2,229z"/>
-<circle class="st4" cx="115" cy="112.8" r="54.8"/>
-<path class="st5" d="M97.3,158.4h35.1l0,0v28.1c0,9.7-7.8,17.6-17.5,17.6c0,0,0,0,0,0l0,0c-9.7,0-17.5-7.9-17.5-17.5L97.3,158.4
-	L97.3,158.4z"/>
-<path class="st6" d="M100.7,157.1h28.4c1.9,0,3.3,1.5,3.3,3.4v24.7c0,9.7-7.9,17.5-17.5,17.5l0,0c-9.7,0-17.5-7.9-17.5-17.5v-24.7
-	C97.3,158.6,98.8,157.1,100.7,157.1L100.7,157.1z"/>
-<path class="st5" d="M97.4,171.6c11.3,4.2,23.8,4.3,35.1,0.1v-4.3H97.4V171.6z"/>
-<circle class="st6" cx="115" cy="123.7" r="50.3"/>
-<path class="st5" d="M79.2,77.9c0,0,21.2,43,81,18l-13.9-21.8l-24.7-8.9L79.2,77.9z"/>
-<path class="st4" d="M79.2,77.3c0,0,21.2,43,81,18l-13.9-21.8l-24.7-8.9L79.2,77.3z"/>
-<path class="st4" d="M79,74.4c1.4-4.4,3.9-8.4,7.2-11.7c9.9-9.8,26.1-11.8,34.4-23c1.8,3.1,0.7,7.1-2.4,8.9
-	c-0.2,0.1-0.4,0.2-0.6,0.3c8-0.1,17.2-0.8,21.7-7.3c2.3,5.3,1.3,11.4-2.5,15.7c7.1,0.3,14.6,5.1,15.1,12.2c0.3,4.7-2.6,9.1-6.5,11.9
-	s-8.5,3.9-13.1,4.9C118.8,89.2,70.3,101.6,79,74.4z"/>
-<path class="st4" d="M165.3,124.1H164L138,147.2c-25-11.7-43.3,0-43.3,0l-27.2-22.1l-2.7,0.3c0.8,27.8,23.9,49.6,51.7,48.9
-	C143.6,173.5,165.3,151.3,165.3,124.1L165.3,124.1z M115,156.1c-9.8,0-17.7-2-17.7-4.4s7.9-4.4,17.7-4.4s17.7,2,17.7,4.4
-	S124.7,156.1,115,156.1L115,156.1z"/>
-<ellipse class="st6" cx="64.7" cy="123.6" rx="4.7" ry="8.8"/>
-<ellipse class="st6" cx="165.3" cy="123.6" rx="4.7" ry="8.8"/>
-</svg>
diff --git a/base/static/img/undraw_profile_3.svg b/base/static/img/undraw_profile_3.svg
deleted file mode 100755
index eecb335ba..000000000
--- a/base/static/img/undraw_profile_3.svg
+++ /dev/null
@@ -1,47 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<!-- Generator: Adobe Illustrator 25.0.0, SVG Export Plug-In . SVG Version: 6.00 Build 0)  -->
-<svg version="1.1" id="_x38_8ce59e9-c4b8-4d1d-9d7a-ce0190159aa8"
-	 xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px" viewBox="0 0 231.8 231.8"
-	 style="enable-background:new 0 0 231.8 231.8;" xml:space="preserve">
-<style type="text/css">
-	.st0{opacity:0.5;}
-	.st1{fill:url(#SVGID_1_);}
-	.st2{fill:#F5F5F5;}
-	.st3{fill:#4E73DF;}
-	.st4{fill:#F55F44;}
-	.st5{opacity:0.1;enable-background:new    ;}
-	.st6{fill:#FDA57D;}
-	.st7{fill:#333333;}
-</style>
-<g class="st0">
-	
-		<linearGradient id="SVGID_1_" gradientUnits="userSpaceOnUse" x1="115.89" y1="9.36" x2="115.89" y2="241.14" gradientTransform="matrix(1 0 0 -1 0 241.14)">
-		<stop  offset="0" style="stop-color:#808080;stop-opacity:0.25"/>
-		<stop  offset="0.54" style="stop-color:#808080;stop-opacity:0.12"/>
-		<stop  offset="1" style="stop-color:#808080;stop-opacity:0.1"/>
-	</linearGradient>
-	<circle class="st1" cx="115.9" cy="115.9" r="115.9"/>
-</g>
-<circle class="st2" cx="116.1" cy="115.1" r="113.4"/>
-<path class="st3" d="M116.2,229c22.2,0,43.8-6.5,62.3-18.7c-4.2-22.8-20.1-24.2-20.1-24.2H70.8c0,0-15,1.2-19.7,22.2
-	C70.1,221.9,92.9,229.1,116.2,229z"/>
-<circle class="st4" cx="115" cy="112.8" r="54.8"/>
-<path class="st5" d="M97.3,158.4h35.1l0,0v28.1c0,9.7-7.9,17.5-17.5,17.5l0,0l0,0c-9.7,0-17.5-7.9-17.5-17.5l0,0L97.3,158.4
-	L97.3,158.4z"/>
-<path class="st6" d="M100.7,157.1h28.4c1.9,0,3.4,1.5,3.4,3.4l0,0v24.7c0,9.7-7.9,17.5-17.5,17.5l0,0l0,0c-9.7,0-17.5-7.9-17.5-17.5
-	l0,0v-24.7C97.4,158.6,98.8,157.1,100.7,157.1L100.7,157.1L100.7,157.1z"/>
-<path class="st5" d="M97.4,171.6c11.3,4.2,23.8,4.3,35.1,0.1v-4.3H97.4V171.6z"/>
-<circle class="st6" cx="115" cy="123.7" r="50.3"/>
-<circle class="st4" cx="114.9" cy="57.1" r="20.2"/>
-<circle class="st4" cx="114.9" cy="37.1" r="13.3"/>
-<path class="st4" d="M106.2,68.2c-9.9-4.4-14.5-15.8-10.5-25.9c-0.1,0.3-0.3,0.6-0.4,0.9c-4.6,10.2,0,22.2,10.2,26.8
-	s22.2,0,26.8-10.2c0.1-0.3,0.2-0.6,0.4-0.9C127.6,68.5,116,72.6,106.2,68.2z"/>
-<path class="st5" d="M79.2,77.9c0,0,21.2,43,81,18l-13.9-21.8l-24.7-8.9L79.2,77.9z"/>
-<path class="st4" d="M79.2,77.3c0,0,21.2,43,81,18l-13.9-21.8l-24.7-8.9L79.2,77.3z"/>
-<path class="st7" d="M95.5,61.6c13-1,26.1-1,39.2,0C134.7,61.6,105.8,64.3,95.5,61.6z"/>
-<path class="st4" d="M118,23c-1,0-2,0-3,0.2h0.8c7.3,0.2,13.1,6.4,12.8,13.7c-0.2,6.2-4.7,11.5-10.8,12.6
-	c7.3,0.1,13.3-5.8,13.4-13.2C131.2,29.1,125.3,23.1,118,23L118,23z"/>
-<ellipse class="st6" cx="64.7" cy="123.6" rx="4.7" ry="8.8"/>
-<ellipse class="st6" cx="165.3" cy="123.6" rx="4.7" ry="8.8"/>
-<polygon class="st4" points="76,78.6 85.8,73.5 88,81.6 82,85.7 "/>
-</svg>
diff --git a/base/static/img/undraw_rocket.svg b/base/static/img/undraw_rocket.svg
deleted file mode 100755
index 45426141b..000000000
--- a/base/static/img/undraw_rocket.svg
+++ /dev/null
@@ -1,39 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<!-- Generator: Adobe Illustrator 25.0.0, SVG Export Plug-In . SVG Version: 6.00 Build 0)  -->
-<svg version="1.1" id="b759170a-51c3-4e2f-999d-77dec9fd6d11"
-	 xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px" viewBox="0 0 650.9 610.5"
-	 style="enable-background:new 0 0 650.9 610.5;" xml:space="preserve">
-<style type="text/css">
-	.st0{fill:#AFC0E0;}
-	.st1{opacity:0.2;fill:#FFFFFF;enable-background:new    ;}
-	.st2{opacity:0.1;enable-background:new    ;}
-	.st3{fill:#E3E8F4;}
-	.st4{fill:#4E73DF;}
-</style>
-<path class="st0" d="M174,321c-2-1.6-4.2-3-6.6-4.2c-51.8-26.2-157,67.8-157,67.8L0,372.7c0,0,42.1-43.8,92.4-117.3
-	c45.2-66.1,150.7-51.8,171.4-48.3c2.3,0.4,3.6,0.7,3.6,0.7C298.7,288.3,174,321,174,321z"/>
-<path class="st1" d="M269.4,213.9c-0.6-2-1.3-4-2-6c0,0-1.2-0.2-3.6-0.7c-20.7-3.5-126.2-17.8-171.4,48.3C42.1,329,0,372.7,0,372.7
-	l5.9,6.7c0,0,42.1-43.8,92.4-117.3C143.3,196.3,248,210.2,269.4,213.9z"/>
-<path class="st0" d="M337.7,533.4c-79.2,40.8-127.8,77.1-127.8,77.1l-10.5-11.9c0,0,111.1-96.8,85.3-150.9c-0.5-1.2-1.2-2.3-1.9-3.4
-	c0,0,47.9-119.6,123.9-78.5c0,0,0.1,1,0.2,2.9C407.8,387.8,409.7,496.3,337.7,533.4z"/>
-<path class="st2" d="M174,321c-2-1.6-4.2-3-6.6-4.2c29.3-38.9,61.5-75.5,96.3-109.7c2.3,0.4,3.6,0.7,3.6,0.7
-	C298.7,288.3,174,321,174,321z"/>
-<path class="st2" d="M406.9,368.6c-38.6,29.6-79.4,56.1-122.3,79.1c-0.5-1.2-1.2-2.3-1.9-3.4c0,0,47.9-119.6,123.9-78.5
-	C406.7,365.7,406.8,366.7,406.9,368.6z"/>
-<path class="st3" d="M263.6,455.5c-20.3,10.4-41.6,20.5-64,30.2c-33.6,14.6-51.5-2.2-80.7-91.5c0,0,12.5-22.5,37.2-57
-	c54.3-75.8,167.5-209.1,336.1-286.7C542.7,27.1,596.1,10.1,650.9,0c0,0-9.1,68.8-62,160.1S439.1,365.3,263.6,455.5z"/>
-<circle class="st0" cx="435.6" cy="199.7" r="71.6"/>
-<path class="st4" d="M469.2,237.9c-21,18.6-53.1,16.6-71.7-4.5c-7.8-8.8-12.2-20-12.7-31.8c-0.2-4.7,0.3-9.4,1.4-14
-	c0.5-2,1.1-4.1,1.9-6c2.9-7.7,7.7-14.5,13.8-19.9c0.3-0.3,0.6-0.5,0.9-0.8c17.1-14.4,41.5-15.9,60.3-3.8c3.5,2.3,6.7,4.9,9.5,7.9
-	l1,1.1C492.2,187.2,490.2,219.3,469.2,237.9C469.2,237.8,469.2,237.9,469.2,237.9z"/>
-<path class="st0" d="M588.9,160.1c-83-35.2-96.8-109.6-96.8-109.6C542.7,27,596.1,10.1,650.9,0C650.9,0,641.8,68.8,588.9,160.1z"/>
-<path class="st0" d="M263.6,455.5c-13.7,7.1-27.9,13.9-42.6,20.7c-7,3.2-14.1,6.4-21.4,9.5c-10.9,4.7-51.5-2.2-80.7-91.5
-	c0,0,4.1-7.3,12.1-20c6.1-9.6,14.5-22.2,25.1-37c0,0,11,33.2,41.1,67.3C215.8,425.7,238.4,443,263.6,455.5z"/>
-<path class="st3" d="M221,476.2c-7,3.2-14.1,6.4-21.4,9.5c-10.9,4.7-51.5-2.2-80.7-91.5c0,0,4.1-7.3,12.1-20
-	C131,374.2,170.2,456.9,221,476.2z"/>
-<path class="st1" d="M463.2,157l-0.1,0l-60.1,3.9c-0.3,0.3-0.6,0.5-0.9,0.8c-6.2,5.4-10.9,12.3-13.8,19.9l84.5-16.6L463.2,157z"/>
-<path class="st1" d="M438.8,194.3l-53.9,7.3c-0.2-4.7,0.3-9.4,1.4-14l52.8,1.4L438.8,194.3z"/>
-<path class="st1" d="M131.7,408.7c0,0,12.5-22.5,37.2-57C223.2,276,336.4,142.7,504.9,65c45.6-21.1,93.3-36.9,142.5-47.3
-	C650.1,6.4,650.9,0,650.9,0c-54.8,10.1-108.2,27-158.7,50.5c-168.6,77.7-281.8,211-336.1,286.7c-24.7,34.4-37.2,57-37.2,57
-	c11.5,35.3,26.6,57,40.5,70.3C149.4,451.4,139.7,433.3,131.7,408.7z"/>
-</svg>
diff --git a/base/static/js/click_reset.js b/base/static/js/click_reset.js
deleted file mode 100755
index d46a1afca..000000000
--- a/base/static/js/click_reset.js
+++ /dev/null
@@ -1,29 +0,0 @@
-$(document).ready(function () {
-    //Highlight clicked row
-    document.getElementById('reset_div').addEventListener('click', function () {
-        // on click reset the graph
-        // if reset button exists, hide it
-        var csrftoken = jQuery("[name=csrfmiddlewaretoken]").val();
-        $("#run_counterfactual_loader").show()
-        $("#reset").remove()
-        $.ajax({
-            method: 'POST',
-            url: '',
-            headers: { 'X-CSRFToken': csrftoken },
-            data: {'action': "reset_graph" },
-            success: function (ret) {
-                $("#run_counterfactual_loader").hide()
-                if ($("#og_cf_row") && $("#og_cf_headers")) {
-                    $("#og_cf_row").hide()
-                    $("#og_cf_headers").hide()
-                }
-                ret = JSON.parse(ret)
-                fig = ret["fig"]
-                document.getElementById("tsne").innerHTML = "";
-                $("#tsne").append(fig)
-            },
-            error: function (ret) {
-            }
-        });
-    });
-});
diff --git a/base/static/js/counterfactuals.js b/base/static/js/counterfactuals.js
index 21a372534..e940a73df 100755
--- a/base/static/js/counterfactuals.js
+++ b/base/static/js/counterfactuals.js
@@ -308,6 +308,7 @@ $(document).ready(function () {
                 });
                 data_to_pass = { 'action': "cf", "features_to_vary": JSON.stringify(features_to_vary), "model_name": model_name }
             }
+            
             // hide button and original point row
             // replace with loader
             $("#cfbtn_loader").show()
diff --git a/base/static/js/home.js b/base/static/js/home.js
new file mode 100755
index 000000000..01b18224b
--- /dev/null
+++ b/base/static/js/home.js
@@ -0,0 +1,613 @@
+import { create_dataframe, create_selection, create_uploaded_file_radio, showSuccessMessage, showLoader, clearPreviousContent, resetContainers } from './methods.js';
+
+$(document).ready(function () {
+
+    // Add visibility to fade-in elements on scroll
+    const fadeElements = document.querySelectorAll('.fade-in');
+
+    const elementInView = (el, percentageScroll = 100) => {
+        const elementTop = el.getBoundingClientRect().top;
+        return elementTop <= (window.innerHeight || document.documentElement.clientHeight) * (percentageScroll / 100);
+    };
+
+    const displayFadeElement = (element) => {
+        element.classList.add('visible');
+    };
+
+    const handleFadeAnimation = () => {
+        fadeElements.forEach((el) => {
+            if (elementInView(el)) {
+                displayFadeElement(el);
+            }
+        });
+    };
+
+    window.addEventListener('scroll', () => {
+        handleFadeAnimation();
+    });
+
+    // Initial check for elements already in view
+    handleFadeAnimation();
+
+    function fetchDatasetData(df_name) {
+        const csrftoken = jQuery("[name=csrfmiddlewaretoken]").val();
+        showLoader(true);
+
+        $.ajax({
+            method: 'POST',
+            url: '',
+            headers: { 'X-CSRFToken': csrftoken },
+            data: { 'action': "dataset", 'df_name': df_name },
+            success: function (values) {
+                showLoader(false);
+                handleSuccessResponse(values);
+                $("#new_or_load").show();
+            },
+            error: function (ret) {
+                console.error("Failed to fetch dataset:", ret);
+            }
+        });
+    }
+
+    function handleSuccessResponse(values) {
+        if (!values) return;
+
+        clearPreviousContent();
+        const ret = JSON.parse(values);
+        const datasetType = ret["dataset_type"];
+
+        if (datasetType === "tabular") {
+            setupTabularDataset(ret);
+        } else if (datasetType === "timeseries") {
+            setupTimeseriesDataset(ret);
+        }
+    }
+
+    function setupTabularDataset(ret) {
+        const { data_to_display: df, fig, features, feature1, feature2, labels, curlabel } = ret;
+
+        const selection1 = create_selection(features, "feature1", null, feature1);
+        const selection2 = create_selection(features, "feature2", null, feature2);
+        const selection3 = create_selection(labels, "label", null, curlabel);
+
+        const tb = create_dataframe(df, "df_container");
+
+        $("#model_container, #df, #df_stats").fadeIn(200);
+        $("#df_div").append(tb);
+        $("#selection").append(selection1, selection2, selection3);
+
+        const figDiv = $("<div>", { id: 'stats_container', class: "plotly_fig" }).html(fig);
+        $("#stats_div").append(figDiv);
+    }
+
+    function setupTimeseriesDataset(ret) {
+        const { fig, fig1 } = ret;
+
+        const figDiv = $("<div>", { id: 'ts_confidence_container', class: "plotly_fig" }).html(fig);
+        const figDiv1 = $("<div>", { id: 'ts_stats_container', class: "plotly_fig" }).html(fig1);
+
+        $("#ts_stats, #ts_confidence").fadeIn(200);
+        $("#ts_stats_div").append(figDiv);
+        $("#ts_confidence_div").append(figDiv1);
+    }
+
+    $('.btn-dataset').click(function (e) {
+        const df_name = $(this).is('#upload') ? "upload" : $(this).attr('id');
+        $("#new_or_load_cached").hide();
+        resetContainers();
+        $("#upload_col").toggle(df_name === "upload");
+        $("#timeseries-datasets").toggle(df_name === "timeseries");
+
+        $(this).toggleClass("active").siblings().removeClass("active");
+        $(this).addClass("active");
+
+        const timeseries_dataset = df_name === "timeseries" ? $("input:radio[name=timeseries_dataset]:checked").val() : "";
+        if (timeseries_dataset || (df_name !== "timeseries")) {
+            fetchDatasetData(timeseries_dataset || df_name);
+        }
+    });
+});
+
+document.getElementById("viewModelsButton").addEventListener("click", function () {
+    // Prompt or redirect the user to the pre-trained models section
+    window.location.href = "/charts.html"; // Replace with the actual URL
+});
+
+$(document).ready(function () {
+    $('#timeseries-datasets').change(function () {
+        if ($("input[name=timeseries_dataset]:checked").length > 0) {
+
+            var timeseries_dataset = $("input:radio[name=timeseries_dataset]:checked").val();
+
+            $("#df_container").hide();
+            $("#stats_container").hide();
+            $("#figs").hide();
+
+            $("#ts_confidence_cached").hide()
+            $("#ts_stats_cached").hide()
+
+            $("#ts_confidence").hide()
+            $("#ts_stats").hide()
+            var csrftoken = jQuery("[name=csrfmiddlewaretoken]").val();
+
+            $("#loader_ds").show();
+            $("#loader_stats").show();
+
+            $("#new_or_load").hide();
+            $("#new_or_load_cached").hide();
+
+            $.ajax({
+                method: 'POST',
+                url: '',
+                headers: { 'X-CSRFToken': csrftoken, },
+                data: { 'action': "timeseries-dataset", 'timeseries_dataset': timeseries_dataset },
+                success: function (values) {
+                    $("#loader_ds").hide();
+                    $("#loader_stats").hide();
+                    // fetch data
+                    // remove data if already displayed
+                    if (document.getElementById("df_container")) {
+                        $("#pretrained_radio").remove();
+                        $("#df_container").remove();
+                        $("#stats_container").remove();
+                        $("#feature1").remove();
+                        $("#feature2").remove();
+                        $("#label").remove();
+                    }
+
+                    $("#new_or_load").show();
+
+                    if (document.getElementById("ts_confidence_container")) {
+                        $("#ts_confidence_container").remove();
+                        $("#ts_stats_container").remove();
+                    }
+
+                    var ret = JSON.parse(values)
+                    var dataset_type = ret["dataset_type"]
+
+                    if (values) {
+                        // timeseries
+                        // var feature = ret["feature"]
+                        var fig = ret["fig"]
+                        var fig1 = ret["fig1"]
+
+                        var iDiv = document.createElement('div');
+                        iDiv.id = 'ts_confidence_container';
+                        iDiv.innerHTML = fig;
+                        iDiv.setAttribute("class", "plotly_fig")
+
+                        var iDiv1 = document.createElement('div');
+                        iDiv1.id = 'ts_stats_container';
+                        iDiv1.innerHTML = fig1;
+                        iDiv1.setAttribute("class", "plotly_fig")
+
+                        $("#ts_stats").show();
+                        $("#ts_confidence").show();
+
+                        $("#ts_stats_div").append(iDiv);
+                        $("#ts_confidence_div").append(iDiv1);
+                    }
+                },
+                error: function (ret) {
+                    console.log("All bad")
+                }
+
+            });
+        }
+    })
+});
+
+// $(document).ready(function () {
+//     $('#radio_buttons').change(function () {
+//         if ($("input[name=uploaded_file]:checked").length > 0) {
+//             var uploaded_dataset = $("input:radio[name=uploaded_file]:checked").val();
+
+//             if (document.getElementById("df_container")) {
+//                 $("#df").hide();
+//                 $("#df_stats").hide();
+//             }
+
+//             if (document.getElementById("df_cached")) {
+//                 $("#df_cached").hide()
+//                 $("#df_stats_cached").hide()
+//             }
+
+//             if (document.getElementById("ts_confidence")) {
+//                 $("#ts_confidence").hide()
+//                 $("#ts_stats").hide()
+//             }
+
+//             if (document.getElementById("ts_confidence_cached")) {
+//                 $("#ts_confidence_cached").hide()
+//                 $("#ts_stats_cached").hide()
+//             }
+
+//             $("#new_or_load").hide()
+//             var csrftoken = jQuery("[name=csrfmiddlewaretoken]").val();
+
+//             $("#loader_ds").show();
+//             $("#loader_stats").show();
+
+//             $.ajax({
+//                 method: 'POST',
+//                 url: '',
+//                 headers: { 'X-CSRFToken': csrftoken, },
+//                 data: { 'action': "uploaded_datasets", 'df_name': uploaded_dataset },
+//                 success: function (values) {
+//                     $("#loader_ds").hide();
+//                     $("#loader_stats").hide();
+//                     $("#new_or_load").show()
+//                     // fetch data
+//                     // remove data if already displayed
+//                     if (document.getElementById("df_container")) {
+//                         $("#pretrained_radio").remove();
+//                         $("#df_container").remove();
+//                         $("#stats_container").remove();
+//                         $("#feature1").remove();
+//                         $("#feature2").remove();
+//                         $("#label").remove();
+//                     }
+
+//                     if (document.getElementById("df_cached")) {
+//                         $("#df_cached").remove()
+//                         $("#df_stats_cached").remove()
+//                         $("#ts_confidence_cached").remove()
+//                         $("#ts_stats_cached").remove()
+//                     }
+
+//                     if (document.getElementById("ts_confidence_container")) {
+//                         $("#ts_confidence_container").remove();
+//                         $("#ts_stats_container").remove();
+//                     }
+
+//                     var ret = JSON.parse(values)
+//                     var dataset_type = ret["dataset_type"]
+
+//                     if (values) {
+//                         if (dataset_type == "tabular") {
+//                             var df = ret["data_to_display"]
+//                             var fig = ret["fig"]
+//                             var features = ret["features"]
+//                             var feature1 = ret["feature1"]
+//                             var feature2 = ret["feature2"]
+
+//                             // cur labels
+//                             var labels = ret["labels"]
+//                             var curlabel = ret["curlabel"]
+
+//                             var selection1 = create_selection(features, "feature1", null, feature1)
+//                             var selection2 = create_selection(features, "feature2", null, feature2)
+//                             var selection3 = create_selection(labels, "label", null, curlabel)
+
+//                             // create table
+//                             var tb = create_dataframe(df, "df_container")
+
+//                             $("#model_container").show()
+//                             $("#df").show();
+//                             $("#df_stats").show();
+
+//                             // append new data
+//                             $("#df_div").append(tb);
+//                             $("#selection").append(selection1);
+//                             $("#selection").append(selection2);
+//                             $("#selection").append(selection3);
+
+//                             // append fig
+//                             var iDiv = document.createElement('div');
+//                             iDiv.id = 'stats_container';
+//                             iDiv.innerHTML = fig;
+//                             iDiv.setAttribute("class", "plotly_fig")
+
+//                             $("#stats_div").append(iDiv);
+//                         } else if (dataset_type == "timeseries") {
+
+//                             // timeseries
+//                             // var feature = ret["feature"]
+//                             var fig = ret["fig"]
+//                             var fig1 = ret["fig1"]
+
+//                             var iDiv = document.createElement('div');
+//                             iDiv.id = 'ts_confidence_container';
+//                             iDiv.innerHTML = fig;
+//                             iDiv.setAttribute("class", "plotly_fig")
+
+//                             var iDiv1 = document.createElement('div');
+//                             iDiv1.id = 'ts_stats_container';
+//                             iDiv1.innerHTML = fig1;
+//                             iDiv1.setAttribute("class", "plotly_fig")
+
+//                             $("#ts_stats").show();
+//                             $("#ts_confidence").show();
+
+//                             $("#ts_stats_div").append(iDiv);
+//                             $("#ts_confidence_div").append(iDiv1);
+
+//                         }
+//                     }
+//                 },
+//                 error: function (ret) {
+//                 }
+//             });
+//         }
+//     })
+// });
+
+// $('#upload_btn').click(function (event) {
+//     event.preventDefault(); // Prevent default form submission
+
+//     var datasetType = $('input[name="dataset_type"]:checked').val();
+//     var fileInput = $('#doc')[0].files[0];
+//     var csrfToken = $('input[name="csrfmiddlewaretoken"]').val();
+
+//     if (!datasetType || !fileInput) {
+//         alert('Please select a dataset type and choose a file to upload.');
+//         return;
+//     }
+
+//     // Use FormData to handle file upload
+//     var formData = new FormData();
+//     formData.append('action', 'upload_dataset');
+//     formData.append('dataset_type', datasetType);
+//     formData.append('excel_file', fileInput);
+//     formData.append('csrfmiddlewaretoken', csrfToken);
+
+//     $("#cfbtn_loader").show();
+
+//     $.ajax({
+//         url: '', // Replace with your Django view URL for uploading
+//         type: 'POST',
+//         data: formData,
+//         processData: false, // Prevent jQuery from processing data
+//         contentType: false, // Prevent jQuery from setting content type
+//         success: function (response) {
+//             try {
+//                 var ret = JSON.parse(response);
+//                 var df_name = ret["df_name"];
+//                 var uploaded_files = ret["uploaded_files"];
+//                 var counter = uploaded_files.length - 1;
+
+//                 // Add uploaded file to the list
+//                 alert("here")
+//                 $("#radio_buttons").append(create_uploaded_file_radio(df_name, counter));
+
+//                 // Check if target_labels exist in the response
+//                 if (ret["target_labels"]) {
+//                     populateLabelModal(ret["target_labels"]); // Populate the modal for label selection
+//                 }
+
+//                 showSuccessMessage();
+//             } catch (error) {
+//                 console.error("Error processing response:", error);
+//                 alert("An error occurred while processing the upload response.");
+//             } finally {
+//                 $("#cfbtn_loader").hide();
+//             }
+//         },
+//         error: function (xhr, status, error) {
+//             console.error("Error uploading:", status, error);
+//             alert("An error occurred during upload. Please try again.");
+//             $("#cfbtn_loader").hide();
+//         }
+//     });
+// });
+
+// function populateLabelModal(targetLabels) {
+//     const positiveDropdown = $("#positive-label");
+//     const negativeDropdown = $("#negative-label");
+//     const errorContainer = $("#selection-error");
+
+//     // Populate dropdowns
+//     updateDropdownOptions(positiveDropdown, targetLabels, null);
+//     updateDropdownOptions(negativeDropdown, targetLabels, null);
+
+//     // Reset error message
+//     errorContainer.addClass("d-none").text("");
+
+//     // Open the modal
+//     $("#labelSelectionModal").modal({
+//         backdrop: 'static', // Prevent closing when clicking outside
+//         keyboard: false     // Prevent closing with "Escape"
+//     });
+
+//     let selectedPositive = null;
+//     let selectedNegative = null;
+
+//     // Handle changes in positive dropdown
+//     positiveDropdown.off("change").on("change", function () {
+//         selectedPositive = $(this).val();
+//         updateDropdownOptions(negativeDropdown, targetLabels, selectedPositive, selectedNegative);
+//         validateSelection(selectedPositive, selectedNegative);
+//     });
+
+//     // Handle changes in negative dropdown
+//     negativeDropdown.off("change").on("change", function () {
+//         selectedNegative = $(this).val();
+//         updateDropdownOptions(positiveDropdown, targetLabels, selectedNegative, selectedPositive);
+//         validateSelection(selectedPositive, selectedNegative);
+//     });
+
+//     $("#save-label-choices").click(function (event) {
+//         if (validateSelection(selectedPositive, selectedNegative, true)) {
+//             var csrfToken = $('input[name="csrfmiddlewaretoken"]').val();
+//             var formData = new FormData();
+
+//             formData.append('action', 'select_class_labels_for_uploaded_timeseries');
+//             formData.append('positive_label', selectedPositive);
+//             formData.append('negative_label', selectedNegative);
+//             formData.append('csrfToken', csrfToken);
+//             // Show loader
+//             $("#loader_ds").removeClass("d-none");
+
+//             // Disable the Save button to prevent duplicate submissions
+//             $("#save-label-choices").prop("disabled", true);
+
+//             $.ajax({
+//                 url: '', // Replace with your Django view URL for uploading
+//                 type: 'POST',
+//                 headers: { 'X-CSRFToken': csrfToken, },
+//                 data: formData,
+//                 processData: false, // Prevent jQuery from processing data
+//                 contentType: false, // Prevent jQuery from setting content type
+//                 success: function (response) {
+//                     console.log('Labels saved successfully:', response);
+
+//                     // Hide loader
+//                     $("#loader_ds").addClass("d-none");
+
+//                     // Enable the Save button
+//                     $("#save-label-choices").prop("disabled", false);
+
+//                     // Close the modal
+//                     $("#labelSelectionModal").modal("hide");
+
+//                     // Optionally update the UI with the response
+//                 },
+//                 error: function (xhr) {
+//                     const errorContainer = $("#selection-error");
+//                     const errorMessage = xhr.responseJSON?.message || 'An error occurred while saving labels.';
+//                     errorContainer.html(`<i class="fas fa-exclamation-triangle"></i> ${errorMessage}`)
+//                         .removeClass("d-none");
+
+//                     // Hide loader
+//                     $("#loader_ds").addClass("d-none");
+
+//                     // Enable the Save button
+//                     $("#save-label-choices").prop("disabled", false);
+//                 }
+//             });
+//         }
+//     });
+
+
+//     /**
+//      * Helper function to retrieve CSRF token.
+//      * Assumes the CSRF token is stored in a cookie named 'csrftoken'.
+//      * @returns {string} - CSRF token value.
+//      */
+//     function getCSRFToken() {
+//         const name = 'csrftoken';
+//         const cookies = document.cookie.split(';');
+//         for (let cookie of cookies) {
+//             cookie = cookie.trim();
+//             if (cookie.startsWith(name + '=')) {
+//                 return cookie.substring(name.length + 1);
+//             }
+//         }
+//         return '';
+//     }
+// }
+
+// /**
+//  * Update dropdown options dynamically, excluding the currently selected value in the other dropdown.
+//  * @param {jQuery} dropdown - The dropdown to update.
+//  * @param {Array} options - The list of options to populate.
+//  * @param {string|null} exclude - The value to exclude from the dropdown options.
+//  * @param {string|null} currentValue - The current value of the dropdown being updated.
+//  */
+// function updateDropdownOptions(dropdown, options, exclude, currentValue = null) {
+//     dropdown.empty(); // Clear existing options
+
+//     // Add default placeholder
+//     dropdown.append('<option value="" disabled>Select a label</option>');
+
+//     // Repopulate options, excluding the selected value from the other dropdown
+//     options.forEach(option => {
+//         if (option !== exclude) {
+//             dropdown.append(
+//                 `<option value="${option}" ${option === currentValue ? "selected" : ""}>${option}</option>`
+//             );
+//         }
+//     });
+
+//     // Reset dropdown if the current value is no longer valid
+//     if (exclude === currentValue) {
+//         dropdown.val("");
+//     }
+// }
+
+// /**
+//  * Validate the selected positive and negative labels.
+//  * @param {string|null} positive - The selected positive label.
+//  * @param {string|null} negative - The selected negative label.
+//  * @param {boolean} showError - Whether to show an error message on failure.
+//  * @returns {boolean} - Returns true if the selection is valid, otherwise false.
+//  */
+// function validateSelection(positive, negative, showError = false) {
+//     const errorContainer = $("#selection-error");
+
+//     if (!positive || !negative) {
+//         if (showError) {
+//             errorContainer.text("You must select both a positive and a negative label!").removeClass("d-none");
+//         }
+//         return false;
+//     }
+
+//     if (positive === negative) {
+//         if (showError) {
+//             errorContainer.text("Positive and Negative labels must be different!").removeClass("d-none");
+//         }
+//         return false;
+//     }
+
+//     // Clear error if valid
+//     errorContainer.addClass("d-none").text("");
+//     return true;
+// }
+
+document.getElementById("selection").addEventListener("change", function (e) {
+    var feature1 = document.getElementById("feature1").value
+    var feature2 = document.getElementById("feature2").value
+    var label = document.getElementById("label").value
+    var csrftoken = jQuery("[name=csrfmiddlewaretoken]").val();
+    $("#stats_container").remove()
+    $('#loader_stats').show()
+    $.ajax({
+        method: 'POST',
+        url: '',
+        headers: { 'X-CSRFToken': csrftoken, },
+        data: { 'action': "stat", 'feature1': feature1, 'feature2': feature2, 'label': label },
+        success: function (ret) {
+            $('#loader_stats').hide()
+            var ret = JSON.parse(ret)
+            var fig = ret["fig"]
+            var iDiv = document.createElement('div');
+            iDiv.id = 'stats_container';
+            iDiv.insertAdjacentHTML('beforeend', fig);
+            $("#stats_div").append(iDiv);
+
+        },
+        error: function (ret) {
+        }
+    });
+});
+
+if (document.getElementById("selection_cached")) {
+    document.getElementById("selection_cached").addEventListener("change", function (e) {
+
+        var feature1 = document.getElementById("feature1_cached").value
+        var feature2 = document.getElementById("feature2_cached").value
+        var label = document.getElementById("label_cached").value
+        var csrftoken = jQuery("[name=csrfmiddlewaretoken]").val();
+        $("#stats_container_cached").html("")
+        $('#loader_stats_cached').show()
+        $.ajax({
+            method: 'POST',
+            url: '',
+            headers: { 'X-CSRFToken': csrftoken, },
+            data: { 'action': "stat", 'feature1': feature1, 'feature2': feature2, 'label': label },
+            success: function (ret) {
+                $('#loader_stats_cached').hide()
+                var ret = JSON.parse(ret)
+                var fig = ret["fig"]
+                var iDiv = document.createElement('div');
+                iDiv.id = 'stats_container_cached';
+                iDiv.insertAdjacentHTML('beforeend', fig);
+                $("#stats_container_cached").html(fig)
+                // $("#stats_container_cached").append(iDiv);
+
+            },
+            error: function (ret) {
+            }
+        });
+    });
+}
\ No newline at end of file
diff --git a/base/static/js/import.js b/base/static/js/import.js
deleted file mode 100755
index 100d09d14..000000000
--- a/base/static/js/import.js
+++ /dev/null
@@ -1,21 +0,0 @@
-function enterdata() {
-    //Highlight clicked row
-    document.getElementById('upload_btn').addEventListener('click', function () {
-        var data1 = new FormData()
-        var csrftoken = jQuery("[name=csrfmiddlewaretoken]").val();
-        data1.append('excel_file', $('#doc')[0].files[0])
-        console.log(data1)
-        $.ajax({
-            method: 'POST',
-            url: '',
-            headers: { 'X-CSRFToken': csrftoken, },
-            data: { 'action': "upload_csv", 'data': data1 },
-            success: function (ret) {
-                console.log(ret)
-            },
-            error: function (ret) {
-                
-            }
-        });
-    });
-};
diff --git a/base/static/js/main.js b/base/static/js/main.js
index d943d03a9..248eff38c 100644
--- a/base/static/js/main.js
+++ b/base/static/js/main.js
@@ -73,20 +73,48 @@ document.addEventListener("DOMContentLoaded", function () {
 if (document.getElementById("backToDatasetButton")) {
     document.getElementById("backToDatasetButton").addEventListener("click", function () {
         // Redirect to the dataset selection section
-        window.location.href = "/#dataset_selection"; // Replace with the actual URL
+        window.location.href = "/#dataset_selection";
     });
 }
 
 if (document.getElementById("viewCounterfactualsButton")) {
     document.getElementById("viewCounterfactualsButton").addEventListener("click", function () {
         // Redirect to the counterfactuals view section
-        window.location.href = "/counterfactuals.html"; // Replace with the actual URL
+        window.location.href = "/counterfactuals.html";
     });
 }
 
 if (document.getElementById("viewPreTrainedButton")) {
     document.getElementById("viewPreTrainedButton").addEventListener("click", function () {
-        // Redirect to the counterfactuals view section
-        window.location.href = "/charts.html"; // Replace with the actual URL
+        // Redirect to the pre trained view section
+        window.location.href = "/charts.html"; 
     });
-}
\ No newline at end of file
+}
+
+// JavaScript to handle delete functionality
+document.addEventListener("DOMContentLoaded", function () {
+
+    document.getElementById("radio_buttons").addEventListener("click", function (event) {        
+        // Identify if the click originated from the button or its child span
+        let targetButton = event.target.closest(".delete-file-icon");
+        console.log(targetButton)
+        // Only proceed if a delete-file-icon button was clicked
+        if (targetButton) {
+            // Get the filename from the data-file attribute
+            const fileName = targetButton.getAttribute("data-file");
+
+            const fileNameValue = targetButton.getAttribute("data-file-value");
+
+            // Set the file name in the modal for display
+            document.getElementById("fileToDeleteName").innerText = fileName;
+
+            // Set the filename in the confirm button for reference during deletion
+            document.getElementById("confirmDeleteButton").setAttribute("data-file", fileName);
+
+            document.getElementById("confirmDeleteButton").setAttribute("data-file-value", fileNameValue);
+
+            // Show the delete confirmation modal
+            $('#deleteFileModal').modal('show');
+        }
+    });
+});
\ No newline at end of file
diff --git a/base/static/js/methods.js b/base/static/js/methods.js
index ec8db56cc..557bc1c16 100755
--- a/base/static/js/methods.js
+++ b/base/static/js/methods.js
@@ -81,10 +81,10 @@ function transpose_table(tableHtml) {
         for (let colIndex = 0; colIndex < colNames.length; colIndex++) {
             transposedHtml += `<tr><td>${colNames[colIndex]}</td>`;
             transposedHtml += `<td>${rows[colIndex]}</td>`;
-            transposedHtml += `<td>${rows[colIndex + colNames.length ]}</td>`;
+            transposedHtml += `<td>${rows[colIndex + colNames.length]}</td>`;
             transposedHtml += '</tr>';
         }
-    }else{
+    } else {
         for (let colIndex = 0; colIndex < colNames.length; colIndex++) {
             transposedHtml += `<tr><td>${colNames[colIndex]}</td>`;
             transposedHtml += `<td>${rows[colIndex]}</td>`;
@@ -98,6 +98,108 @@ function transpose_table(tableHtml) {
     return transposedHtml;
 }
 
+function create_uploaded_file_radio(name, counter) {
+    var formCheckDiv = document.createElement("div");
+    formCheckDiv.className = "form-check mb-1 d-flex align-items-center";
+
+    // Create the radio input element
+    var radioInput = document.createElement("input");
+    radioInput.className = "form-check-input mr-2";
+    radioInput.type = "radio";
+    radioInput.name = "uploaded_file";
+    radioInput.id = "file_" + counter;
+    radioInput.value = name;
+    radioInput.required = true;
+
+    // Create the label element
+    var label = document.createElement("label");
+    label.className = "form-check-label mr-auto";
+    label.htmlFor = "file_" + counter;
+    label.innerText = name;
+
+    // Create the delete button
+    var deleteButton = document.createElement("button");
+    deleteButton.className = "delete-file-icon p-0 ml-2 text-muted close";
+    deleteButton.type = "button";
+    deleteButton.dataset.file = name;
+    deleteButton.setAttribute("aria-label", "Delete " + name);
+
+    // Create the '×' span inside the delete button
+    var deleteIcon = document.createElement("span");
+    deleteIcon.setAttribute("aria-hidden", "true");
+    deleteIcon.innerHTML = "&times;";
+
+    // Append the delete icon to the delete button
+    deleteButton.appendChild(deleteIcon);
+
+    // Append the radio input, label, and delete button to the container div
+    formCheckDiv.appendChild(radioInput);
+    formCheckDiv.appendChild(label);
+    formCheckDiv.appendChild(deleteButton);
+
+    return formCheckDiv
+}
+
+
+function showSuccessMessage() {
+    const successMessage = document.getElementById("success-message");
+    successMessage.classList.remove("d-none");
+
+    // Add a slight delay to trigger the transition
+    setTimeout(() => successMessage.classList.add("show"), 10);
+
+    // Automatically hide the message after a few seconds
+    setTimeout(() => hideSuccessMessage(), 3000);
+}
+
+function hideSuccessMessage() {
+    const successMessage = document.getElementById("success-message");
+    successMessage.classList.remove("show");
+
+    // Delay hiding the element fully until after the transition
+    setTimeout(() => successMessage.classList.add("d-none"), 400);
+}
+
+function showLoader(show, ids = ["#loader_ds", "#loader_stats"]) {
+    ids.forEach(id => {
+        $(id).toggle(show);
+    });
+}
+function resetContainers(ids = [
+    "#df_container",
+    "#stats_container",
+    "#figs",
+    "#df",
+    "#df_stats",
+    "#df_cached",
+    "#df_stats_cached",
+    "#ts_confidence_cached",
+    "#ts_stats_cached",
+    "#ts_confidence",
+    "#ts_stats"
+]) {
+    ids.forEach(id => {
+        $(id).hide();
+    });
+}
+
+function clearPreviousContent(ids = [
+    "#df_container",
+    "#stats_container",
+    "#pretrained_radio",
+    "#feature1",
+    "#feature2",
+    "#label",
+    "#ts_confidence_container",
+    "#ts_stats_container"
+]) {
+    ids.forEach(id => {
+        const element = document.querySelector(id);
+        if (element) element.remove();
+    });
+}
+
+
 export {
-    create_selection, create_dataframe, create_div, transpose_table
+    create_selection, create_dataframe, create_div, transpose_table, create_uploaded_file_radio, showSuccessMessage, hideSuccessMessage, showLoader, clearPreviousContent, resetContainers
 }
\ No newline at end of file
diff --git a/base/static/js/radio_dataset.js b/base/static/js/radio_dataset.js
deleted file mode 100755
index a197456e0..000000000
--- a/base/static/js/radio_dataset.js
+++ /dev/null
@@ -1,98 +0,0 @@
-import { create_dataframe, create_selection } from './methods.js';
-
-$(document).ready(function () {
-
-    function showLoader(show) {
-        $("#loader, #loader_stats").toggle(show);
-    }
-
-    function resetContainers() {
-        $("#df_container, #stats_container, #figs, #df, #df_stats, #df_cached, #df_stats_cached, #ts_confidence_cached, #ts_stats_cached, #ts_confidence, #ts_stats").hide();
-    }
-
-    function clearPreviousContent() {
-        ["#df_container", "#stats_container", "#pretrained_radio", "#feature1", "#feature2", "#label", "#ts_confidence_container", "#ts_stats_container"].forEach(id => {
-            if ($(id).length) $(id).remove();
-        });
-    }
-
-    function fetchDatasetData(df_name) {
-        const csrftoken = jQuery("[name=csrfmiddlewaretoken]").val();
-        showLoader(true);
-
-        $.ajax({
-            method: 'POST',
-            url: '',
-            headers: { 'X-CSRFToken': csrftoken },
-            data: { 'action': "dataset", 'df_name': df_name },
-            success: function (values) {
-                showLoader(false);
-                handleSuccessResponse(values);
-            },
-            error: function (ret) {
-                console.error("Failed to fetch dataset:", ret);
-            }
-        });
-    }
-
-    function handleSuccessResponse(values) {
-        if (!values) return;
-        
-        clearPreviousContent();
-        const ret = JSON.parse(values);
-        const datasetType = ret["dataset_type"];
-        
-        if (datasetType === "tabular") {
-            setupTabularDataset(ret);
-        } else if (datasetType === "timeseries") {
-            setupTimeseriesDataset(ret);
-        }
-    }
-
-    function setupTabularDataset(ret) {
-        const { data_to_display: df, fig, features, feature1, feature2, labels, curlabel } = ret;
-
-        const selection1 = create_selection(features, "feature1", null, feature1);
-        const selection2 = create_selection(features, "feature2", null, feature2);
-        const selection3 = create_selection(labels, "label", null, curlabel);
-
-        const tb = create_dataframe(df, "df_container");
-        
-        $("#model_container, #df, #df_stats").fadeIn(200);
-        $("#df_div").append(tb);
-        $("#selection").append(selection1, selection2, selection3);
-
-        const figDiv = $("<div>", { id: 'stats_container', class: "plotly_fig" }).html(fig);
-        $("#stats_div").append(figDiv);
-    }
-
-    function setupTimeseriesDataset(ret) {
-        const { fig, fig1 } = ret;
-
-        const figDiv = $("<div>", { id: 'ts_confidence_container', class: "plotly_fig" }).html(fig);
-        const figDiv1 = $("<div>", { id: 'ts_stats_container', class: "plotly_fig" }).html(fig1);
-
-        $("#ts_stats, #ts_confidence").fadeIn(200);
-        $("#ts_stats_div").append(figDiv);
-        $("#ts_confidence_div").append(figDiv1);
-    }
-
-    $('.btn-dataset').click(function (e) {
-        const df_name = $(this).is('#upload') ? "upload" : $(this).attr('id');
-        resetContainers();
-        $("#upload_col").toggle(df_name === "upload");
-        $("#timeseries-datasets").toggle(df_name === "timeseries");
-
-        $(this).toggleClass("active").siblings().removeClass("active");
-        $(this).addClass("active");
-        const timeseries_dataset = df_name === "timeseries" ? $("input:radio[name=timeseries_dataset]:checked").val() : "";
-        if (timeseries_dataset || df_name !== "timeseries") {
-            fetchDatasetData(timeseries_dataset || df_name);
-        }
-    });
-});
-
-document.getElementById("viewModelsButton").addEventListener("click", function () {
-    // Prompt or redirect the user to the pre-trained models section
-    window.location.href = "/charts.html"; // Replace with the actual URL
-});
\ No newline at end of file
diff --git a/base/static/js/radio_model.js b/base/static/js/radio_model.js
index 6fb99c6e3..3306b7427 100755
--- a/base/static/js/radio_model.js
+++ b/base/static/js/radio_model.js
@@ -1,10 +1,7 @@
-import { create_dataframe, create_div, transpose_table } from './methods.js'
-
-// pretrained model selection and
-// train new model selection (not execution)
+import { create_dataframe, create_div } from './methods.js'
 
 $(document).ready(function () {
-    $('#pre_trained_models').change(function () {
+    $('#radio_buttons').change(function () {
         if ($("input[name=modeling_options]:checked").length > 0) {
 
             // pre trained model selected
@@ -18,8 +15,6 @@ $(document).ready(function () {
             var url = ""
 
             if (currentUrl.includes('charts.html')) {
-                $("#figs").hide();
-                $("#figs_2").hide();
 
                 // if they already exist, remove them and update them
                 if (document.getElementById("principle_component_analysis")) {
@@ -118,4 +113,77 @@ $(document).ready(function () {
             });
         }
     });
+
+    document.getElementById('confirmDeleteButton').addEventListener('click', function () {
+        const fileNameValue = this.getAttribute('data-file-value');
+        const fileName = this.getAttribute('data-file');
+        const csrftoken = jQuery("[name=csrfmiddlewaretoken]").val();
+        const uploadedDataset = $("input:radio[name=radio_buttons]:checked").val();
+        // AJAX request to delete file
+        $.ajax({
+            type: 'POST',
+            url: '',  // Add the URL where this request should go
+            data: {
+                action: 'delete_pre_trained',
+                model_name: fileNameValue,
+                csrfmiddlewaretoken: csrftoken  // Django CSRF token
+            },
+            success: function () {
+                // Remove the file entry from the UI
+                const fileElement = $(`[data-file="${fileName}"]`).closest('.form-check');
+                fileElement.remove();
+                
+                // Check if there are any remaining .form-check elements
+                if ($('#radio_buttons .form-check').length === 0) {
+                    // Replace the #radio_buttons content with the fallback message
+                    const radioButtonsContainer = document.querySelector('#radio_buttons');
+                    radioButtonsContainer.innerHTML = `
+                        <p class="text-danger">
+                            There are no available pre-trained models. 
+                            Please <a href="/train.html" class="text-primary">train a model</a>.
+                        </p>
+                    `;
+                }
+            
+                // Attach a success message to the modal
+                const modalBody = document.querySelector('#deleteFileModal .modal-body');
+                modalBody.innerHTML = `
+                    <div class="alert alert-success mb-3" role="alert">
+                        <i class="fas fa-check-circle mr-2"></i>
+                        The file <strong>${fileName}</strong> has been successfully deleted.
+                    </div>
+                `;
+            
+                // Optionally hide the modal after a delay
+                setTimeout(() => {
+                    $('#deleteFileModal').modal('hide');
+                    modalBody.innerHTML = ''; // Clear the message after hiding
+                }, 2000);
+            
+                // Reset containers if the deleted file is the uploaded dataset
+                if (fileName === uploadedDataset) {
+                    resetContainers();
+                }
+            },
+            
+            error: function () {
+                // Attach an error message to the modal
+                const modalBody = document.querySelector('#deleteFileModal .modal-body');
+                modalBody.innerHTML = `
+                    <div class="alert alert-danger mb-3" role="alert">
+                        <i class="fas fa-times-circle mr-2"></i>
+                        An error occurred while deleting the file. Please try again.
+                    </div>
+                `;
+    
+                // Optionally reset the modal content after a delay
+                setTimeout(() => {
+                    modalBody.innerHTML = `
+                        <p class="mb-1">Delete <span id="fileToDeleteName" class="font-weight-bold"></span> pre-trained classifier on <span class="font-weight-bold"> {{ df_name }} </span> dataset?</p>
+                        <small class="text-muted">This action is permanent.</small>
+                    `;
+                }, 3000);
+            }
+        });
+    });    
 });
diff --git a/base/static/js/radio_timeseries_dataset.js b/base/static/js/radio_timeseries_dataset.js
index 23f2bba8b..d74eb8b28 100644
--- a/base/static/js/radio_timeseries_dataset.js
+++ b/base/static/js/radio_timeseries_dataset.js
@@ -1,81 +1,73 @@
-import { create_dataframe, create_selection } from './methods.js'
+import { create_dataframe, create_selection } from './methods.js';
 
 $(document).ready(function () {
-
     $('#timeseries-datasets').change(function () {
-        if ($("input[name=timeseries_dataset]:checked").length > 0) {
+        const selectedDataset = $("input[name=timeseries_dataset]:checked").val();
 
-            var timeseries_dataset = $("input:radio[name=timeseries_dataset]:checked").val();
+        if (selectedDataset) {
+            resetContainers();
+            toggleSkeletons(true);
 
-            $("#df_container").hide();
-            $("#stats_container").hide();
-            $("#figs").hide();
-
-            $("#ts_confidence_cached").hide()
-            $("#ts_stats_cached").hide()
-
-            $("#ts_confidence").hide()
-            $("#ts_stats").hide()
-            var csrftoken = jQuery("[name=csrfmiddlewaretoken]").val();
-            
-            $("#loader").show();
-            $("#loader_stats").show();
+            const csrfToken = $("[name=csrfmiddlewaretoken]").val();
 
+            // AJAX request to fetch the dataset
             $.ajax({
                 method: 'POST',
-                url: '',
-                headers: { 'X-CSRFToken': csrftoken, },
-                data: { 'action': "timeseries-dataset", 'timeseries_dataset': timeseries_dataset },
-                success: function (values) {
-                    $("#loader").hide();
-                    $("#loader_stats").hide();
-                    // fetch data
-                    // remove data if already displayed
-                    if (document.getElementById("df_container")) {
-                        $("#pretrained_radio").remove();
-                        $("#df_container").remove();
-                        $("#stats_container").remove();
-                        $("#feature1").remove();
-                        $("#feature2").remove();
-                        $("#label").remove();
-                    }
-
-                    if (document.getElementById("ts_confidence_container")) {
-                        $("#ts_confidence_container").remove();
-                        $("#ts_stats_container").remove();
-                    }
-
-                    var ret = JSON.parse(values)
-                    var dataset_type = ret["dataset_type"]
-
-                    if (values) {
-                        // timeseries
-                        // var feature = ret["feature"]
-                        var fig = ret["fig"]
-                        var fig1 = ret["fig1"]
-
-                        var iDiv = document.createElement('div');
-                        iDiv.id = 'ts_confidence_container';
-                        iDiv.innerHTML = fig;
-                        iDiv.setAttribute("class", "plotly_fig")
-
-                        var iDiv1 = document.createElement('div');
-                        iDiv1.id = 'ts_stats_container';
-                        iDiv1.innerHTML = fig1;
-                        iDiv1.setAttribute("class", "plotly_fig")
-
-                        $("#ts_stats").show();
-                        $("#ts_confidence").show();
-
-                        $("#ts_stats_div").append(iDiv);
-                        $("#ts_confidence_div").append(iDiv1);
-                    }
+                url: '', // Specify your endpoint here
+                headers: { 'X-CSRFToken': csrfToken },
+                data: { action: "timeseries-dataset", timeseries_dataset: selectedDataset },
+                success: function (response) {
+                    alert("herereererer")
+                    toggleSkeletons(false);
+                    handleTimeseriesResponse(response);
                 },
-                error: function (ret) {
-                    console.log("All bad")
+                error: function (error) {
+                    toggleSkeletons(false);
+                    console.error("An error occurred:", error);
                 }
-
             });
         }
-    })
-});
\ No newline at end of file
+    });
+
+    /**
+     * Reset the containers by hiding any previous data.
+     */
+    function resetContainers() {
+        const elementsToHide = [
+            "#df_div", "#stats_div", "#ts_confidence_div", "#ts_stats_div"
+        ];
+        elementsToHide.forEach(selector => $(selector).empty().hide());
+    }
+
+    /**
+     * Toggle skeleton loaders for a smooth user experience.
+     * @param {boolean} show - Whether to show or hide the skeleton loaders.
+     */
+    function toggleSkeletons(show) {
+        const skeletonSelectors = [
+            "#df_skeleton", "#stats_skeleton", "#ts_confidence_skeleton", "#ts_stats_skeleton"
+        ];
+        skeletonSelectors.forEach(selector => $(selector).toggle(show));
+    }
+
+    /**
+     * Handle the response for timeseries dataset.
+     * @param {Object|string} response - The server response.
+     */
+    function handleTimeseriesResponse(response) {
+        try {
+            const data = JSON.parse(response);
+            if (!data) throw new Error("Invalid response format");
+
+            // Populate data and stats
+            if (data.fig) {
+                $("#ts_confidence_div").html(data.fig).show();
+            }
+            if (data.fig1) {
+                $("#ts_stats_div").html(data.fig1).show();
+            }
+        } catch (error) {
+            console.error("Failed to process response:", error);
+        }
+    }
+});
diff --git a/base/static/js/radio_uploaded_dataset.js b/base/static/js/radio_uploaded_dataset.js
deleted file mode 100644
index b48757961..000000000
--- a/base/static/js/radio_uploaded_dataset.js
+++ /dev/null
@@ -1,118 +0,0 @@
-import { create_dataframe, create_selection } from './methods.js'
-
-$(document).ready(function () {
-
-    $('#uploaded_file').change(function () {
-        if ($("input[name=uploaded_file]:checked").length > 0) {
-
-            var uploaded_dataset = $("input:radio[name=uploaded_file]:checked").val();
-
-            $("#df_container").hide();
-            $("#stats_container").hide();
-            $("#figs").hide();
-
-            $("#ts_confidence_cached").hide()
-            $("#ts_stats_cached").hide()
-
-            $("#ts_confidence").hide()
-            $("#ts_stats").hide()
-            var csrftoken = jQuery("[name=csrfmiddlewaretoken]").val();
-            
-            $("#loader").show();
-            $("#loader_stats").show();
-
-            $.ajax({
-                method: 'POST',
-                url: '',
-                headers: { 'X-CSRFToken': csrftoken, },
-                data: { 'action': "uploaded_datasets", 'df_name': uploaded_dataset },
-                success: function (values) {
-                     $("#loader").hide();
-                     $("#loader_stats").hide();
-                     // fetch data
-                     // remove data if already displayed
-                     if (document.getElementById("df_container")) {
-                          $("#pretrained_radio").remove();
-                          $("#df_container").remove();
-                          $("#stats_container").remove();
-                          $("#feature1").remove();
-                          $("#feature2").remove();
-                          $("#label").remove();
-                     }
-
-                     if (document.getElementById("ts_confidence_container")) {
-                          $("#ts_confidence_container").remove();
-                          $("#ts_stats_container").remove();
-                     }
-
-                     var ret = JSON.parse(values)
-                     var dataset_type = ret["dataset_type"]
-
-                     if (values) {
-                          if (dataset_type == "tabular") {
-                               var df = ret["data_to_display"]
-                               var fig = ret["fig"]
-                               var features = ret["features"]
-                               var feature1 = ret["feature1"]
-                               var feature2 = ret["feature2"]
-
-                               // cur labels
-                               var labels = ret["labels"]
-                               var curlabel = ret["curlabel"]
-
-                               var selection1 = create_selection(features, "feature1", null, feature1)
-                               var selection2 = create_selection(features, "feature2", null, feature2)
-                               var selection3 = create_selection(labels, "label", null, curlabel)
-
-                               // create table
-                               var tb = create_dataframe(df, "df_container")
-
-                               $("#model_container").show()
-                               $("#df").show();
-                               $("#df_stats").show();
-
-                               // append new data
-                               $("#df_div").append(tb);
-                               $("#selection").append(selection1);
-                               $("#selection").append(selection2);
-                               $("#selection").append(selection3);
-
-                               // append fig
-                               var iDiv = document.createElement('div');
-                               iDiv.id = 'stats_container';
-                               iDiv.innerHTML = fig;
-                               iDiv.setAttribute("class", "plotly_fig")
-
-                               $("#stats_div").append(iDiv);
-                          } else if (dataset_type == "timeseries") {
-
-                               // timeseries
-                               // var feature = ret["feature"]
-                               var fig = ret["fig"]
-                               var fig1 = ret["fig1"]
-
-                               var iDiv = document.createElement('div');
-                               iDiv.id = 'ts_confidence_container';
-                               iDiv.innerHTML = fig;
-                               iDiv.setAttribute("class", "plotly_fig")
-
-                               var iDiv1 = document.createElement('div');
-                               iDiv1.id = 'ts_stats_container';
-                               iDiv1.innerHTML = fig1;
-                               iDiv1.setAttribute("class", "plotly_fig")
-
-                               $("#ts_stats").show();
-                               $("#ts_confidence").show();
-
-                               $("#ts_stats_div").append(iDiv);
-                               $("#ts_confidence_div").append(iDiv1);
-
-                          }
-                     }
-                },
-                error: function (ret) {
-                }
-           });
-        }
-    })
-});
\ No newline at end of file
diff --git a/base/static/js/train.js b/base/static/js/train.js
index 1b5561190..9cc8e15ed 100755
--- a/base/static/js/train.js
+++ b/base/static/js/train.js
@@ -1,6 +1,5 @@
 // train a new model 
-import { create_dataframe, create_div, change_nav_text } from './methods.js'
-change_nav_text("train_nav")
+import { create_dataframe, create_div } from './methods.js'
 
 $(document).ready(function () {
 
@@ -26,57 +25,285 @@ $(document).ready(function () {
     });
 
     $('.train_test').click(function () {
-        // get preprocessing variables, model and test set ratio
-        // send ajax request to back end and wait for results
-        var array_preprocessing = []
+        const classifier = document.getElementById("classifier").value;
+        const errorMessage = $("#error_message_new_x_2");
 
-        $("#loader_train").show();
-        var test_set_ratio
-        var classifier = document.getElementById("classifier").value
-        var class_label = ""
-        var autoencoder = ""
-        var data_to_pass = {}
-        if (classifier != "wildboar_knn" && classifier != "wildboar_rsf" && classifier != "glacier") {
-            class_label = document.getElementById("class_label_train").value
-            test_set_ratio = document.getElementById("slider").value
-            document.getElementsByName("boxes").forEach(function (elem) {
-                if (elem.checked == true) {
-                    array_preprocessing.push(elem.value);
-                }
-            });
-            data_to_pass = { 'action': "train", 'model_name': classifier, 'test_set_ratio': test_set_ratio, 'array_preprocessing': JSON.stringify(array_preprocessing), 'class_label': class_label }
-        } else if (classifier == "glacier") {
-            // time series data, no class label
-            autoencoder = document.getElementById("autoencoder").value
-            // TODO: maybe add test set ratio
-            data_to_pass = { 'action': "train", 'model_name': classifier, 'autoencoder': autoencoder }
-        } else if (classifier == "wildboar_knn" || classifier == "wildboar_rsf") {
-            test_set_ratio = document.getElementById("slider").value
-            document.getElementsByName("boxes").forEach(function (elem) {
-                if (elem.checked == true) {
-                    array_preprocessing.push(elem.value);
-                }
-            });
-            data_to_pass = { 'action': "train", 'model_name': classifier, 'test_set_ratio': test_set_ratio, 'array_preprocessing': JSON.stringify(array_preprocessing) }
+        let array_preprocessing = [];
+        let test_set_ratio, class_label, autoencoder;
+        let data_to_pass = {};
+
+        // Helper function to show errors
+        function showError(message) {
+            errorMessage.text(message);
+            errorMessage.show();
         }
-        // ajax request for training
-        var csrftoken = jQuery("[name=csrfmiddlewaretoken]").val();
+
+        // Helper function to get checked values of checkboxes by name
+        function getCheckedValues(name) {
+            return Array.from(document.getElementsByName(name))
+                .filter((elem) => elem.checked)
+                .map((elem) => elem.value);
+        }
+
+        // Check if a classifier is selected
+        if (!classifier) {
+            // Show loader while training
+            showError("Please select a classifier before proceeding.");
+            return;
+        }
+
+        // Check if at least one preprocessing checkbox is checked
+        const anyPreprocessingChecked = getCheckedValues("boxes").length > 0;
+
+        if (!anyPreprocessingChecked && classifier !== "glacier") {
+            showError("Please select at least one preprocessing option.");
+            return;
+        }
+
+        // Hide the error message if validations pass
+        errorMessage.hide();
+
+        $("#train_test_btn").hide()
+
+        // Show loader while training
+        $("#loader_train").removeClass("d-none").show();
+
+        // Set up data to pass based on classifier
+        if (classifier === "glacier") {
+            autoencoder = document.getElementById("autoencoder").value;
+            data_to_pass = {
+                action: "train",
+                model_name: classifier,
+                autoencoder: autoencoder
+            };
+        } else {
+            test_set_ratio = document.getElementById("slider").value;
+            class_label = document.getElementById("class_label_train")?.value || "";
+            array_preprocessing = getCheckedValues("boxes");
+
+            data_to_pass = {
+                action: "train",
+                model_name: classifier,
+                test_set_ratio: test_set_ratio,
+                array_preprocessing: JSON.stringify(array_preprocessing),
+                class_label: class_label
+            };
+        }
+
+        // AJAX request for training
+        const csrftoken = jQuery("[name=csrfmiddlewaretoken]").val();
         $.ajax({
             method: 'POST',
             url: '',
-            headers: { 'X-CSRFToken': csrftoken, },
+            headers: { 'X-CSRFToken': csrftoken },
             data: data_to_pass,
-            processData: true,   // This should be `true` for form data
-            contentType: 'application/x-www-form-urlencoded; charset=UTF-8',  // Standard form content type,
-            success: function (values) {
+            processData: true,
+            contentType: 'application/x-www-form-urlencoded; charset=UTF-8',
+            success: function (ret) {
                 $("#loader_train").hide();
+
+                try {
+                    $("#train_test_btn").show()
+
+                    // if they already exist, remove them and update them
+                    if (document.getElementById("principle_component_analysis")) {
+                        $("#principle_component_analysis").remove();
+                    }
+                    if (document.getElementById("class_report")) {
+                        $("#class_report").remove();
+                    }
+                    if (document.getElementById("feature_importance")) {
+                        $("#feature_importance").remove();
+                    }
+                    if (document.getElementById("classifier_data")) {
+                        $("#classifier_data").remove();
+                    }
+                    if (document.getElementById("tsne_plot")) {
+                        $("#tsne_plot").remove();
+                    }
+
+                    var ret = JSON.parse(ret)
+                    // Parse successful response data
+                    const class_report = ret["class_report"];
+                    const classifier_data = ret["classifier_data"];
+                    const pca = ret["pca"];
+                    const dataset_type = ret["dataset_type"];
+                    $("#tab").show();
+
+                    if (dataset_type == "timeseries") {
+                        // For timeseries datasets
+                        const tsne = ret["tsne"];
+                        $("#tsne-tab-nav").show();
+                        const col_div_tsne = create_div("tsne_plot", "plotly_fig");
+                        col_div_tsne.insertAdjacentHTML('beforeend', tsne);
+                        $("#tsne_container").append(col_div_tsne);
+                    } else {
+                        // For other datasets
+                        $("#feature-tab-nav").show();
+                        const feature_importance = ret["feature_importance"];
+                        const col_div_fi = create_div("feature_importance", "plotly_fig");
+                        col_div_fi.insertAdjacentHTML('beforeend', feature_importance);
+                        $("#fi_container").append(col_div_fi);
+                    }
+
+                    // Create and append dataframes
+                    const tb = create_dataframe(classifier_data, "details_container");
+                    const cr_tb = create_dataframe(class_report, "cr_container");
+
+                    // Create and append plots
+                    const col_div_pca = create_div("principle_component_analysis", "plotly_fig");
+                    col_div_pca.insertAdjacentHTML('beforeend', pca);
+
+                    const col_div_class_report = create_div("class_report", "plotly_fig sticky-top-table");
+                    col_div_class_report.append(cr_tb);
+
+                    const col_div_classifier_data = create_div("classifier_data", "plotly_fig sticky-top-table");
+                    col_div_classifier_data.append(tb);
+
+                    // Append content to modal tabs
+                    $("#classification_report").append(col_div_class_report);
+                    $("#details").append(col_div_classifier_data);
+                    $("#pca_container").append(col_div_pca);
+
+                    // Show modal for analysis
+                    $("#modelAnalysisModal").modal("show");
+
+                } catch (e) {
+                    console.error("Error processing response:", e);
+                    $("#modelAnalysisModal").modal("show");
+                }
             },
             error: function (ret) {
+                $("#loader_train").hide();
+
+                // Prepare error message
+                const errorMessage = $("#error_message_new_x_2");
+                const errorMessageText = $("#error_message_text");
+                let backendErrorMessage = "An error occurred."; // Default message
+
+                try {
+                    if (ret.responseJSON && ret.responseJSON.message) {
+                        backendErrorMessage = ret.responseJSON.message + ret.responseJSON.line;
+                    } else if (ret.responseText) {
+                        const parsedResponse = JSON.parse(ret.responseText);
+                        backendErrorMessage = parsedResponse.message || backendErrorMessage;
+                    }
+                } catch (e) {
+                    console.error("Error parsing error response:", e);
+                    backendErrorMessage = ret.responseText || "Unknown error.";
+                }
+
+                // Display error message and trigger modal
+                errorMessageText.text(backendErrorMessage);
+                errorMessage.show();
             }
         });
+    });
 
+    document.getElementById("discard-model").addEventListener("click", function () {
+        // Append a confirmation message to the modal
+        const modalBody = document.querySelector("#modelAnalysisModal .modal-body");
+        const messageContainer = document.createElement("div");
+        messageContainer.id = "discard-message";
+        messageContainer.className = "alert"; // Bootstrap class for alert styles
+
+        // Add a message to confirm the user's decision
+        messageContainer.classList.add("alert-warning");
+        messageContainer.innerHTML = `
+            <i class="fas fa-exclamation-triangle mr-2"></i>
+            Are you sure you want to discard this model? This action cannot be undone.
+            <div class="mt-3">
+                <button id="confirm-discard" class="btn btn-danger btn-sm">Yes, Discard</button>
+                <button id="cancel-discard" class="btn btn-secondary btn-sm">Cancel</button>
+            </div>
+        `;
+        modalBody.appendChild(messageContainer);
+
+        // Add event listeners for confirm and cancel buttons
+        document.getElementById("confirm-discard").addEventListener("click", function () {
+            // Data to send in the AJAX request
+            const data = { action: "discard_model" };
+
+            // Fetch CSRF token (assuming Django or similar framework)
+            const csrftoken = jQuery("[name=csrfmiddlewaretoken]").val();
+
+            // Send AJAX POST request to the backend
+            $.ajax({
+                method: "POST",
+                url: "", // Replace with your actual backend URL
+                headers: { "X-CSRFToken": csrftoken }, // Include CSRF token
+                data: data,
+                success: function (response) {
+                    // Update the modal with a success message
+                    messageContainer.classList.remove("alert-warning");
+                    messageContainer.classList.add("alert-success");
+                    messageContainer.innerHTML = `
+                        <i class="fas fa-check-circle mr-2"></i>
+                        The model has been successfully discarded.
+                    `;
+
+                    // Optionally close the modal after a delay
+                    setTimeout(() => {
+                        $("#modelAnalysisModal").modal("hide");
+                        // Optionally refresh the page or update UI
+                        // location.reload(); // Uncomment to refresh the page
+                    }, 2000);
+                },
+                error: function (xhr) {
+                    // Update the modal with an error message
+                    messageContainer.classList.remove("alert-warning");
+                    messageContainer.classList.add("alert-danger");
+                    const errorMessage = xhr.responseJSON?.message || "An error occurred while discarding the model.";
+                    messageContainer.innerHTML = `
+                        <i class="fas fa-times-circle mr-2"></i>
+                        Failed to discard the model: ${errorMessage}.
+                    `;
+                },
+            });
+        });
+
+        // Cancel discard operation
+        document.getElementById("cancel-discard").addEventListener("click", function () {
+            // Remove the confirmation message
+            modalBody.removeChild(messageContainer);
+        });
+    });
+
+    document.getElementById("save-model").addEventListener("click", function () {
+        // Get the modal body element
+        const modalBody = document.querySelector("#modelAnalysisModal .modal-body");
+
+        // Create a confirmation message container
+        const confirmationMessage = document.createElement("div");
+        confirmationMessage.className = "alert alert-success mt-3"; // Bootstrap alert styles
+        confirmationMessage.innerHTML = `
+            <i class="fas fa-check-circle mr-2"></i>
+            The model has been successfully saved!
+        `;
+
+        // Clear existing content in the modal body (optional)
+        modalBody.innerHTML = "";
+
+        // Append the confirmation message to the modal body
+        modalBody.appendChild(confirmationMessage);
+
+        // Set a timeout to hide the modal after showing the message
+        setTimeout(() => {
+            $("#modelAnalysisModal").modal("hide");
+
+            // Optionally reset the modal body content after hiding
+            setTimeout(() => {
+                modalBody.innerHTML = `
+                    <div class="alert alert-info">
+                        <i class="fas fa-info-circle mr-2"></i>
+                        After training your model/classifier, you should now decide whether to <strong>keep</strong> it or <strong>discard</strong> it based on its performance metrics and visualizations below.
+                    </div>
+                    <!-- Tabs Navigation and other content here -->
+                `;
+            }, 500); // Small delay to ensure the modal is fully hidden before resetting
+        }, 2000); // Hide the modal after 2 seconds
+    });
 
-    })
 });
 
 
diff --git a/base/templates/base/charts.html b/base/templates/base/charts.html
index fba3223af..157251bd1 100755
--- a/base/templates/base/charts.html
+++ b/base/templates/base/charts.html
@@ -60,11 +60,11 @@
                     <div class="card-body">
                         {% csrf_token %}
                         <p class="text-muted"><strong>Select a pre-trained model below to view its detailed analysis:</strong></p>
-                        <div id="pre_trained_models">
+                        <div id="radio_buttons">
                             {% if not df_name %}
                                 <p class="text-muted">The available pre-trained models will show up here. You first need to <a href="/" class="text-primary">pick or upload a dataset</a>.</p>
                             {% elif not available_pretrained_models_info %}
-                                <p class="text-danger">There are no available pre-trained models for <b>{{df_name}}</b>. Please <a href="/train.html" class="text-primary">train a model</a>.</p>
+                                <p class="text-danger">There are no available pre-trained models. Please <a href="/train.html" class="text-primary">train a model</a>.</p>
                             {% else %}
                                 {% for value, text in available_pretrained_models_info %}
                                     <div class="form-check py-1">
@@ -78,6 +78,7 @@
                 </div>
             </div>
         </div>
+        
         <!-- Figures Section: Classification, PCA, Feature Importance -->
         <div class="row" id="tab" style="display:none;">
             <div class="col-lg-12">
@@ -147,6 +148,28 @@
             </div>
         </div>
 
+        <!-- Minimal Delete Confirmation Modal -->
+        <div class="modal fade" id="deleteFileModal" tabindex="-1" role="dialog" aria-labelledby="deleteFileModalLabel" aria-hidden="true">
+            <div class="modal-dialog modal-dialog-centered" role="document">
+                <div class="modal-content border-0 shadow-sm">
+                    <div class="modal-header border-0">
+                        <h6 class="modal-title text-danger" id="deleteFileModalLabel">Confirm Deletion</h6>
+                        <button type="button" class="close text-muted" data-dismiss="modal" aria-label="Close" style="font-size: 1.2rem;">
+                            &times;
+                        </button>
+                    </div>
+                    <div class="modal-body text-center py-3">
+                        <p class="mb-1">Delete <span id="fileToDeleteName" class="font-weight-bold"></span> pre trained classifier on <span class="font-weight-bold"> {{ df_name }} </span> dataset?</p>
+                        <small class="text-muted">This action is permanent.</small>
+                    </div>
+                    <div class="modal-footer justify-content-center border-0">
+                        <button type="button" class="custom-btn-secondary" data-dismiss="modal">Cancel</button>
+                        <button type="button" class="custom-btn-danger" id="confirmDeleteButton">Delete</button>
+                    </div>
+                </div>
+            </div>
+        </div>
+
         <div class="row mt-3" id="new_or_load">
             <div class="col d-flex justify-content-center">
                 <div class="text-center mt-4 d-flex justify-content-center">
diff --git a/base/templates/base/counterfactuals.html b/base/templates/base/counterfactuals.html
index 2b528afac..d90f6eb4f 100755
--- a/base/templates/base/counterfactuals.html
+++ b/base/templates/base/counterfactuals.html
@@ -134,7 +134,7 @@
                             <i class="fas fa-info-circle"></i>
                         </button>
                     </div>
-                    <div class="card-body">
+                    <div class="card-body" id="radio_buttons">
                         {% csrf_token %}
                         {% if not df_name %}
                             <p class="text-muted">
@@ -195,13 +195,13 @@
                                     </div>
                                 {% endfor %}
                             {% else %}
-                                <div class="alert alert-warning text-center mb-0">No pre-computed experiments available.</div>
+                                <div class="alert alert-warning text-center mb-0" id="no-pre-computed">No pre-computed experiments available.</div>
                             {% endif %}
-                        </div>
+                        </div> 
                     </div>
                 </div>
             </div>
-        </div>        
+        </div>
         
         <!-- Modal for Glacier Overview -->
         <div class="modal fade" id="glacierInfoModal" tabindex="-1" role="dialog" aria-labelledby="glacierInfoModalLabel" aria-hidden="true">
@@ -278,9 +278,10 @@
                 </div>
             </div>
         </div>
+        
         <!-- Right Column: New Experiment Details -->
-        <div class="row" id="new_experiment_details" style="display:none;">
-            <div class="col-xl-4 col-lg-4 mb-4" >
+        <!-- <div class="row" id="new_experiment_details" style="display:none;" style="padding-top: 50px;">
+            <div class="col-xl-4 col-lg-4 mb-4">
                 <div class="card border-0 shadow-sm h-100">
                     <div class="card-header bg-light text-dark py-3 d-flex justify-content-between align-items-center">
                         <h6 class="m-0 font-weight-bold">New Experiment Details</h6>
@@ -299,7 +300,6 @@
                         <input name="w_value" id="slider" type="range" min="0" max="1" step="0.1" class="w-100 mb-2">
                         <output id="value" class="d-block text-center font-weight-bold"></output>
 
-                        <!-- Run Experiment Button -->
                         <div class="d-flex justify-content-center mt-4">
                             <div id="error_message_new_x" class="alert alert-danger text-center" style="display: none; width: 100%; max-width: 400px;" role="alert">
                                 <i class="fas fa-exclamation-triangle"></i> Please correct errors before proceeding.
@@ -310,8 +310,75 @@
                     </div>
                 </div>
             </div>
-        </div>
+        </div> -->
 
+        <!-- Modal Structure -->
+        <div class="modal fade" id="newExperimentModal" tabindex="-1" role="dialog" aria-labelledby="newExperimentModalLabel" aria-hidden="true">
+            <div class="modal-dialog modal-lg" role="document">
+                <div class="modal-content shadow-lg">
+                    <!-- Modal Header -->
+                    <div class="modal-header bg-primary text-white">
+                        <h5 class="modal-title" id="newExperimentModalLabel">New Experiment Details</h5>
+                        <button type="button" class="close text-white" data-dismiss="modal" aria-label="Close">
+                            <span aria-hidden="true">&times;</span>
+                        </button>
+                    </div>
+                    <!-- Modal Body -->
+                    <div class="modal-body p-4">
+                        <!-- Constraint Selection -->
+                        <div class="form-group mb-4">
+                            <label for="constraint" class="font-weight-bold text-muted">Constraint</label>
+                            <select required id="constraint" class="form-control" aria-describedby="constraintHelp">
+                                <option value="" disabled selected hidden>Select constraints for counterfactuals</option>
+                                <option value="unconstrained">Unconstrained</option>
+                                <option value="local">Local</option>
+                                <option value="global">Global</option>
+                                <option value="uniform">Uniform</option>
+                            </select>
+                            <small id="constraintHelp" class="form-text text-muted">Choose the type of constraint for the experiment.</small>
+                        </div>
+        
+                        <!-- Predicted Margin Weight -->
+                        <div class="form-group mb-4">
+                            <label for="slider" class="font-weight-bold text-muted">Predicted Margin Weight</label>
+                            <input name="w_value" id="slider" type="range" min="0" max="1" step="0.1" class="form-control-range">
+                            <output id="value" class="d-block text-center font-weight-bold mt-2">0.5</output>
+                        </div>
+        
+                        <!-- Error Message -->
+                        <div id="error_message_new_x" class="alert d-none" role="alert"></div>
+        
+                        <!-- Success Message -->
+                        <div id="success_message" class="alert alert-success d-none" role="alert"></div>
+        
+                        <!-- Run Experiment Button -->
+                        <div class="d-flex justify-content-center mt-4">
+                            <button class="btn btn-primary btn-lg compute_counterfactual d-flex align-items-center" id="cfbtn_2" role="button" name="cf">
+                                <i class="fas fa-play-circle mr-2"></i> Run New Experiment!
+                            </button>
+                        </div>
+                        <div class="row justify-content-center align-items-center my-4">
+                            <div id="cfbtn_loader_2" class="col-auto" style="display:none;">
+                                <div class="d-flex align-items-center text-muted">
+                                    <div class="spinner-border spinner-border-sm text-primary mr-2" role="status"></div>
+                                    <span>Processing...</span>
+                                </div>
+                            </div>
+                        </div>
+                    </div>
+                </div>
+            </div>
+        </div>
+        
+
+<script>
+    // Update slider output dynamically
+    const slider = document.getElementById("slider");
+    const output = document.getElementById("value");
+    slider.addEventListener("input", () => {
+        output.textContent = slider.value;
+    });
+</script>
         <!-- Optional Column: Class Label -->
         {% if dataset_type == "timeseries" %}
             <div class="row" id="class_label_container" style="display: none; padding-top: 70px;">
@@ -374,8 +441,12 @@
         {% endif %}
          
         <div class="d-flex justify-content-center mt-4">
-            <div id="error_message_new_x_2" class="alert alert-danger text-center" style="display: none; width: 100%; max-width: 400px;" role="alert">
-                <i class="fas fa-exclamation-triangle"></i> Please correct errors before proceeding.
+            <div id="error_message_new_x_2" class="alert alert-danger alert-dismissible text-center" style="display: none; width: 100%; max-width: 400px;" role="alert">
+                <i class="fas fa-exclamation-triangle"></i> 
+                <span>Please correct errors before proceeding.</span>
+                <button type="button" class="close" aria-label="Close" onclick="$('#error_message_new_x_2').hide();">
+                    <span aria-hidden="true">&times;</span>
+                </button>
             </div>
         </div>
         
diff --git a/base/templates/base/home.html b/base/templates/base/home.html
index cd0e9d22f..06a35dffb 100755
--- a/base/templates/base/home.html
+++ b/base/templates/base/home.html
@@ -6,128 +6,288 @@
 <!-- Main Content -->
 <div id="content">
 
-    <!-- Introduction Section with Collapsible Content -->
-    <div id="home_intro" class="intro-section py-5 bg-light text-center">
-        <div class="container">
-            <h1 class="h3 text-dark mb-3">
-                Welcome to <a href="https://datascience.dsv.su.se/projects/extremum.html" target="_blank" class="text-primary">Extremum Dashboard</a>
+ <!-- Intro Section -->
+ <div id="home_intro" class="intro-section py-5 text-center position-relative">
+    <div class="container">
+        <!-- Animated Background Graphics -->
+        <div class="background-shape shape-1"></div>
+        <div class="background-shape shape-2"></div>
+
+        <!-- Main Heading -->
+        <div class="intro-content position-relative">
+            <div class="logos d-flex justify-content-center align-items-center mb-4 fade-in">
+                <img src="{% static 'img/su_logo.png' %}" alt="Stockholm University Logo" class="logo su-logo mx-3">
+                <img src="{% static 'img/digital_features.png' %}" alt="Digital Features Logo" class="logo df-logo mx-3">
+            </div>
+            <h1 class="display-4 text-dark mb-4 fade-in">
+                Welcome to the <a href="https://datascience.dsv.su.se/projects/extremum.html" target="_blank" class="text-primary">Extremum Dashboard</a>
             </h1>
-            <p class="lead text-muted">An efficient way to explore health informatics and time-series datasets with ease.</p>
+            <p class="lead text-muted fade-in mx-auto" style="max-width: 800px;">
+                Your gateway to exploring health informatics and time-series datasets with ease.
+            </p>
+        </div>
+    </div>
+</div>
 
-            <!-- Learn More Button with Expand/Collapse Functionality -->
-            <button class="btn btn-outline-secondary mb-3" type="button" data-toggle="collapse" data-target="#introContent" aria-expanded="false" aria-controls="introContent" id="toggleIntro">
-                <span class="mr-1">Read More</span>
-                <i class="fas fa-chevron-down ml-2"></i>
-            </button>
 
-            <!-- Collapsible Content for "Learn More" -->
-            <div class="collapse" id="introContent">
-                <p class="text-muted">
-                    The Extremum Dashboard supports researchers and data enthusiasts by providing tools for dataset selection, advanced visualization, and statistical analysis.
+<div class="about-project-section py-5 position-relative">
+    <div class="container" style="padding-top:250px;">
+        <!-- Main Section with Split Layout -->
+        <div class="about-project-section py-5 position-relative fade-in">
+            <div class="container">
+                <div class="row align-items-center">
+                    <!-- Content Section -->
+                    <div class="col-lg-7">
+                        <h2 class="h4 text-dark mb-3 fade-in">About the Extremum Dashboard</h2>
+                        <p class="text-muted fade-in">
+                            The <strong>Extremum Dashboard</strong>, developed by <strong>Stockholm University</strong>, is part of the 
+                            <a href="https://datascience.dsv.su.se/projects/extremum.html" target="_blank" class="text-primary">EXTREMUM project</a>. It combines advanced AI with ethical practices to improve healthcare outcomes.
+                        </p>
+                        <ul class="list-unstyled mt-4 fade-in">
+                            <li class="mb-3">
+                                <i class="fas fa-layer-group text-primary mr-2"></i>
+                                <strong>Unified Data Representation:</strong> Seamlessly integrate complex medical datasets.
+                            </li>
+                            <li class="mb-3">
+                                <i class="fas fa-brain text-success mr-2"></i>
+                                <strong>Explainable Predictive Models:</strong> Build AI solutions that are interpretable and reliable.
+                            </li>
+                            <li class="mb-3">
+                                <i class="fas fa-balance-scale text-warning mr-2"></i>
+                                <strong>Ethical Compliance:</strong> Ensure AI aligns with ethical and legal standards.
+                            </li>
+                        </ul>
+                        <button class="btn btn-primary rounded-pill px-4 mt-4 fade-in" type="button" data-toggle="collapse" data-target="#extremumDetails" aria-expanded="false" aria-controls="extremumDetails">
+                            Learn More <i class="fas fa-chevron-down ml-2"></i>
+                        </button>
+                    </div>
+        
+                    <!-- Image Section -->
+                    <div class="col-lg-5 text-center">
+                        <img src="https://datascience.dsv.su.se/img/logo/dsgroup.png" 
+                             alt="EXTREMUM Visualization" 
+                             class="img-fluid rounded shadow-lg fade-in" 
+                             loading="lazy" 
+                             style="max-height: 250px;">
+                    </div>
+                </div>
+            </div>
+        </div>
+        
+
+        <div class="collapse mt-4 fade-in" id="extremumDetails">
+            <div class="text-muted mx-auto" style="max-width: 700px;">
+                <h4 class="h5 text-dark text-center mb-3">About the EXTREMUM Project</h4>
+                <p>
+                    The <strong>EXTREMUM Project</strong> focuses on developing an explainable machine learning platform to analyze complex medical data. It addresses two key healthcare areas:
                 </p>
-                <ul class="list-unstyled text-left mx-auto" style="max-width: 600px;">
-                    <li><i class="fas fa-database text-primary mr-2"></i><strong>Dataset Selection:</strong> Choose from preloaded datasets or upload your own for tailored analysis.</li>
-                    <li><i class="fas fa-chart-line text-success mr-2"></i><strong>Timeseries Analysis:</strong> Explore timeseries datasets with customizable parameters and statistical insights.</li>
-                    <li><i class="fas fa-eye text-info mr-2"></i><strong>Interactive Visualization:</strong> View tabular data and statistical insights with interactive graphs.</li>
+                <ul class="list-unstyled text-center my-4">
+                    <li class="mb-3">
+                        <i class="fas fa-heartbeat text-danger"></i>
+                        <span class="ml-2">Adverse Drug Event Detection</span>
+                    </li>
+                    <li>
+                        <i class="fas fa-stethoscope text-info"></i>
+                        <span class="ml-2">Cardiovascular Disease Detection</span>
+                    </li>
                 </ul>
-                <p class="text-muted">This platform turns data into actionable insights effortlessly!</p>
+                <p>
+                    This project integrates medical data sources, builds interpretable predictive models, and ensures ethical integrity in machine learning.
+                </p>
+                <p class="text-center">
+                    <a href="https://datascience.dsv.su.se/projects/extremum.html" target="_blank" class="btn btn-outline-primary rounded-pill">
+                        Learn More
+                    </a>
+                </p>
+            </div>
+        </div>
+        
+
+        <!-- Feature Carousel Section -->
+        <div class="feature-carousel py-5 bg-light mt-5 fade-in">
+            <div class="container">
+                <h3 class="h4 text-dark text-center mb-4">Key Innovations in EXTREMUM</h3>
+                <p class="text-muted text-center mx-auto mb-5" style="max-width: 700px;">
+                    Discover the powerful tools and methodologies developed under the EXTREMUM project, designed to revolutionize explainable AI for healthcare applications.
+                </p>
+                <div id="carouselFeatures" class="carousel slide" data-ride="carousel" data-interval="5000" data-pause="hover">
+                    <ol class="carousel-indicators">
+                        <li data-target="#carouselFeatures" data-slide-to="0" class="active" tabindex="0" aria-label="Feature 1"></li>
+                        <li data-target="#carouselFeatures" data-slide-to="1" tabindex="0" aria-label="Feature 2"></li>
+                    </ol>
+
+                    <div class="carousel-inner">
+                        <div class="carousel-item active">
+                            <div class="feature-card p-5 shadow rounded text-center">
+                                <i class="fas fa-wave-square text-info fa-3x mb-4"></i>
+                                <h5 class="text-dark">Wildboar</h5>
+                                <p class="text-muted">
+                                    Created by <strong>Isak Samsten</strong>, Wildboar is a Python library for temporal machine learning, offering tools for classification, regression, and explainability.
+                                </p>
+                                <a href="https://github.com/wildboar-foundation/wildboar" target="_blank" class="btn btn-primary rounded-pill px-4 py-2 mt-3">
+                                    Learn More <i class="fas fa-external-link-alt ml-2"></i>
+                                </a>
+                            </div>
+                        </div>
+
+                        <div class="carousel-item">
+                            <div class="feature-card p-5 shadow rounded text-center">
+                                <i class="fas fa-snowflake text-primary fa-3x mb-4"></i>
+                                <h5 class="text-dark">Glacier</h5>
+                                <p class="text-muted">
+                                    Developed by <strong>Zhendong Wang</strong>, Glacier generates counterfactual explanations for time series classification, ensuring realistic and interpretable results.
+                                </p>
+                                <a href="https://github.com/zhendong3wang/learning-time-series-counterfactuals" target="_blank" class="btn btn-primary rounded-pill px-4 py-2 mt-3">
+                                    Learn More <i class="fas fa-external-link-alt ml-2"></i>
+                                </a>
+                            </div>
+                        </div>
+                    </div>
+
+                    <a class="carousel-control-prev" href="#carouselFeatures" role="button" data-slide="prev">
+                        <span class="carousel-control-prev-icon bg-dark rounded-circle p-2" aria-hidden="true"></span>
+                        <span class="sr-only">Previous</span>
+                    </a>
+                    <a class="carousel-control-next" href="#carouselFeatures" role="button" data-slide="next">
+                        <span class="carousel-control-next-icon bg-dark rounded-circle p-2" aria-hidden="true"></span>
+                        <span class="sr-only">Next</span>
+                    </a>
+                </div>
             </div>
         </div>
     </div>
+</div>
 
-    <!-- New Key Features or Benefits Section -->
-    <div class="key-features-section py-5 text-center bg-white">
+
+<div>
+    <!-- Call to Action Section -->
+    <div class="separator-section py-5 text-center bg-light">
         <div class="container">
-            <h2 class="h4 text-gray-800 mb-4">Why Use Extremum Dashboard?</h2>
-            <div class="row">
-                <div class="col-md-4 mb-4">
-                    <div class="feature-card border-0 p-3 shadow-sm animate-card">
-                        <i class="fas fa-bolt text-primary fa-2x mb-3"></i>
-                        <h5 class="text-dark">Fast & Efficient</h5>
-                        <p class="text-muted">Quickly analyze large datasets with optimized performance and get insights in seconds.</p>
-                    </div>
-                </div>
-                <div class="col-md-4 mb-4">
-                    <div class="feature-card border-0 p-3 shadow-sm animate-card">
-                        <i class="fas fa-chart-pie text-success fa-2x mb-3"></i>
-                        <h5 class="text-dark">Comprehensive Visualizations</h5>
-                        <p class="text-muted">Access a wide range of visualizations to understand your data better.</p>
-                    </div>
-                </div>
-                <div class="col-md-4 mb-4">
-                    <div class="feature-card border-0 p-3 shadow-sm animate-card">
-                        <i class="fas fa-lock text-info fa-2x mb-3"></i>
-                        <h5 class="text-dark">Secure & Reliable</h5>
-                        <p class="text-muted">Your data is safe with us, with top-notch security measures in place.</p>
-                    </div>
-                </div>
-            </div>
+            <h3 class="h5 text-dark mb-4 fade-in">Ready to start your journey?</h3>
+            <button class="btn btn-outline-primary fade-in" onclick="document.getElementById('dataset_selection').scrollIntoView({behavior: 'smooth'})">
+                Explore Datasets <i class="fas fa-arrow-down ml-2"></i>
+            </button>
         </div>
     </div>
-
-    <!-- Separator Section with Interactive Scroll Button -->
-    <div class="separator-section py-4 text-center">
-        <hr class="w-50 mx-auto mb-4">
-        <button class="btn btn-primary btn-lg" onclick="document.getElementById('dataset_selection').scrollIntoView({behavior: 'smooth'})">
-            Start Exploring Datasets
-            <i class="fas fa-arrow-down ml-2"></i>
-        </button>
-    </div>
-    <div class="cool-separator my-5">
-        <hr>
-    </div>
-    
 </div>
 <!-- Page Heading -->
-<!-- Combined Heading and Button Group for Dataset Selection -->
-<div class="text-center mb-5" style="padding-top:250px;">
-    <h2 id="dataset_selection" class="h4 mb-4 text-dark">Choose a Dataset</h2>
 
-    <!-- Dataset Selection Button Group -->
-    <div class="row justify-content-center">
+<!-- Combined Heading and Button Group for Dataset Selection -->
+<style>
+    /* Section Styling */
+    .dataset-section {
+        padding: 100px 20px;
+        background-color: #f8f9fa;
+        text-align: center;
+    }
+
+    .dataset-section h2 {
+        font-size: 1.5rem;
+        font-weight: 600;
+        color: #333;
+        margin-bottom: 1rem;
+    }
+
+    .dataset-section p {
+        font-size: 0.95rem;
+        color: #666;
+        margin-bottom: 2rem;
+        max-width: 600px;
+        margin: 0 auto;
+        line-height: 1.5;
+    }
+
+    /* Button Styling */
+    .btn-dataset {
+        font-size: 1rem;
+        font-weight: 500;
+        border: 1px solid #ccc;
+        color: #333;
+        background-color: white;
+        border-radius: 5px;
+        padding: 12px 20px;
+        margin: 10px;
+        transition: all 0.2s ease;
+        width: 200px;
+    }
+
+    .btn-dataset:hover {
+        border-color: #007bff;
+        color: #007bff;
+    }
+
+    .btn-dataset.active {
+        background-color: #007bff;
+        color: white;
+        border-color: #007bff;
+    }
+
+    /* Responsive Alignment */
+    .dataset-section .row {
+        justify-content: center;
+        gap: 1rem;
+    }
+
+    @media (max-width: 768px) {
+        .btn-dataset {
+            width: 180px;
+            padding: 10px 15px;
+        }
+    }
+</style>
+
+<div class="dataset-section" style="padding-top:300px;">
+    <!-- Title -->
+    <h2 id="dataset_selection">Choose Your Dataset</h2>
+    <p>
+        Select a dataset to visualize its graphs and perform advanced operations like using pre-trained models 
+        or computing counterfactuals. Your choice will be used throughout the session.
+    </p>
+
+    <!-- Dataset Selection Buttons -->
+    <div class="row">
         {% csrf_token %}
-        
+
         <!-- Breast Cancer Dataset -->
-        <div class="col-auto">
-            <button type="button" class="btn btn-dataset px-4 py-2 mb-2 {% if df_name == 'breast-cancer' %}active{% endif %}" id="breast-cancer">
-                <i class="fas fa-dna"></i> Breast Cancer
-            </button>
-        </div>
+        <button type="button" class="btn btn-dataset {% if df_name == 'breast-cancer' %}active{% endif %}" id="breast-cancer">
+            Breast Cancer
+        </button>
 
         <!-- Stroke Dataset -->
-        <div class="col-auto">
-            <button type="button" class="btn btn-dataset px-4 py-2 mb-2 {% if df_name == 'stroke' %}active{% endif %}" id="stroke">
-                <i class="fas fa-heartbeat"></i> Stroke
-            </button>
-        </div>
+        <button type="button" class="btn btn-dataset {% if df_name == 'stroke' %}active{% endif %}" id="stroke">
+            Stroke
+        </button>
 
         <!-- Timeseries Dataset -->
-        <div class="col-auto">
-            <button type="button" class="btn btn-dataset px-4 py-2 mb-2 {% if dataset_type == 'timeseries' %}active{% endif %}" id="timeseries">
-                <i class="fas fa-chart-line"></i> Timeseries
-            </button>
-        </div>
+        <button type="button" class="btn btn-dataset {% if dataset_type == 'timeseries' %}active{% endif %}" id="timeseries">
+            Timeseries
+        </button>
 
-        <!-- Upload Dataset -->
-        <div class="col-auto">
-            <button type="button" class="btn btn-dataset px-4 py-2 mb-2 {% if upload %}active{% endif %}" id="upload">
-                <i class="fas fa-upload"></i> Upload
-            </button>
-        </div>
+        <!-- Upload Dataset (Optional) -->
+        <!-- Uncomment if needed
+        <button type="button" class="btn btn-dataset {% if upload == 1 %}active{% endif %}" id="upload">
+            Upload Dataset
+        </button>
+        -->
     </div>
 </div>
 
+
 <!-- Upload Form Section -->
-<div class="row justify-content-center">
-    <div class="col-xl-5 col-lg-5" id="upload_col" {% if upload %} style="display: block;" {% else %} style="display: none;" {% endif %}>
-        <div class="card shadow-sm mb-4 border-0 animate-card">
-            <div class="card-body">
+<!-- <div class="row justify-content-center">
+    <div class="col-xl-5 col-lg-6" id="upload_col" {% if upload %} style="display: block;" {% else %} style="display: none;" {% endif %}>
+        <div class="card shadow-sm border-0 animate-card">
+            <div class="card-header bg-primary text-muted d-flex align-items-center">
+                <h6 class="mb-0">Upload Dataset</h6>
+                <i class="fas fa-upload ml-auto"></i>
+            </div>
+            <div class="card-body bg-light">
                 <div class="row">
-                    <!-- Left Column: Form Section -->
-                    <div class="col-md-6">
+                    <div class="col-md-7 mb-4">
                         <form id="csv_form" method="POST" enctype="multipart/form-data">
                             {% csrf_token %}
-                            <fieldset class="form-group mb-3">
+                            
+                            <fieldset class="form-group mb-4">
                                 <legend class="col-form-label small text-secondary font-weight-semibold">Data Type</legend>
                                 <div class="form-check">
                                     <input class="form-check-input" type="radio" name="dataset_type" id="tabular" value="tabular" required>
@@ -138,43 +298,81 @@
                                     <label class="form-check-label" for="timeseries">Timeseries</label>
                                 </div>
                             </fieldset>
-
-                            <div class="form-group">
-                                <label class="small text-secondary font-weight-semibold" for="doc">Upload File</label>
+                
+                            <div class="form-group mb-4">
+                                <label class="small text-secondary font-weight-semibold" for="doc">Select File</label>
                                 <input class="form-control-file" type="file" id="doc" name="excel_file" required>
+                                <small class="text-muted d-block mt-1">Supported format: CSV</small>
                             </div>
-
-                            <div class="form-group">
-                                <input class="btn btn-primary btn-sm mt-2" type="submit" value="Upload" id="upload_btn">
+                
+                            <div class="form-group d-flex align-items-center w-100">
+                                <input class="btn btn-primary btn-sm mr-3" type="submit" value="Upload" id="upload_btn">
+                                
+                                <div class="loader" id="cfbtn_loader" style="display: none; margin-left: 5px;">
+                                    <i class="fas fa-spinner fa-spin"></i>
+                                </div>
+                                
+                                <div id="success-message" class="alert alert-success custom-alert d-none ml-3 mb-0" role="alert">
+                                    <i class="fas fa-check-circle"></i>
+                                    <span class="ml-2">File uploaded successfully.</span>
+                                    <button type="button" class="close ml-auto p-0" aria-label="Close" onclick="hideSuccessMessage();">
+                                        <span aria-hidden="true">&times;</span>
+                                    </button>
+                                </div>
                             </div>
                         </form>
                     </div>
-
-                    <!-- Right Column: Uploaded Files Section -->
-                    <div class="col-md-6" id="uploaded_file">
-                        <fieldset class="form-group mb-3">
+                
+                    <div class="col-md-5 mb-5">
+                        <fieldset class="form-group mb-4">
                             <legend class="col-form-label small text-secondary font-weight-semibold">Uploaded Files</legend>
                             {% if uploaded_files %}
-                                <fieldset class="form-group">
+                                <fieldset class="form-group" id="radio_buttons">
                                     {% for uploaded_file in uploaded_files %}
-                                        <div class="form-check mb-1">
-                                            <input class="form-check-input" type="radio" name="uploaded_file" id="uploaded_file_{{ forloop.counter }}" value="{{ uploaded_file }}" required>
-                                            <label class="form-check-label" for="uploaded_file_{{ forloop.counter }}">{{ uploaded_file }}</label>
+                                        <div class="form-check mb-2 d-flex align-items-center">
+                                            <input class="form-check-input mr-2" type="radio" {% if df_name == uploaded_file %} checked {% endif %} name="uploaded_file" id="element_{{ forloop.counter }}" value="{{ uploaded_file }}" required>
+                                            <label class="form-check-label mr-auto" for="element_{{ forloop.counter }}">{{ uploaded_file }}</label>
+                                            <button type="button" class="delete-file-icon p-0 ml-2 text-muted close" data-file="{{ uploaded_file }}" data-file-value="{{uploaded_file}}" aria-label="Delete {{ uploaded_file }}">
+                                                <span aria-hidden="true">&times;</span>
+                                            </button>
                                         </div>
                                     {% endfor %}
                                 </fieldset>
                             {% else %}
-                                <p class="small text-muted">No files uploaded.</p>
+                                <p class="small text-muted">No files uploaded yet. Please upload a dataset to select it here.</p>
                             {% endif %}
                         </fieldset>
                     </div>
                 </div>
             </div>
+            <div class="card-footer bg-white text-center">
+                <small class="text-muted">Manage your datasets effectively. Ensure data is accurate and up-to-date.</small>
+            </div>
+        </div>
+    </div>
+</div> -->
+
+<!-- Minimal Delete Confirmation Modal -->
+<div class="modal fade" id="deleteFileModal" tabindex="-1" role="dialog" aria-labelledby="deleteFileModalLabel" aria-hidden="true">
+    <div class="modal-dialog modal-dialog-centered" role="document">
+        <div class="modal-content border-0 shadow-sm">
+            <div class="modal-header border-0">
+                <h6 class="modal-title text-danger" id="deleteFileModalLabel">Confirm Deletion</h6>
+                <button type="button" class="close text-muted" data-dismiss="modal" aria-label="Close" style="font-size: 1.2rem;">
+                    &times;
+                </button>
+            </div>
+            <div class="modal-body text-center py-3">
+                <p class="mb-1">Delete <span id="fileToDeleteName" class="font-weight-bold"></span>?</p>
+                <small class="text-muted">This action is permanent.</small>
+            </div>
+            <div class="modal-footer justify-content-center border-0">
+                <button type="button" class="custom-btn-secondary" data-dismiss="modal">Cancel</button>
+                <button type="button" class="custom-btn-danger" id="confirmDeleteButton">Delete</button>
+            </div>
         </div>
     </div>
 </div>
-
-
 <!-- Timeseries Dataset Selection -->
 <div class="row justify-content-center">
     <div class="col-lg-5" {% if dataset_type != "timeseries" %} style="display:none;" {% endif %} id="timeseries-datasets">
@@ -269,7 +467,58 @@
     </div>
 </div>
 
+<!-- Modal Window -->
+<div class="modal fade" id="labelSelectionModal" tabindex="-1" aria-labelledby="labelSelectionModalLabel" aria-hidden="true" data-backdrop="static" data-keyboard="false">
+    <div class="modal-dialog modal-dialog-centered">
+        <div class="modal-content">
+            <!-- Modal Header -->
+            <div class="modal-header">
+                <h5 class="modal-title" id="labelSelectionModalLabel">Assign Positive and Negative Labels</h5>
+            </div>
+            <!-- Modal Body -->
+                <div class="modal-body">
+                    {% csrf_token %}
+                    <p class="text-muted">Please assign one label as <strong>Positive</strong> and another as <strong>Negative</strong>.</p>
+                    <!-- Positive Label Dropdown -->
+                    <div class="form-group">
+                        <label for="positive-label" class="font-weight-semibold">Positive Label</label>
+                        <select id="positive-label" class="form-control">
+                            <option value="" disabled selected>Select a positive label</option>
+                            <!-- Options populated dynamically -->
+                        </select>
+                    </div>
+                    <!-- Negative Label Dropdown -->
+                    <div class="form-group mt-3">
+                        <label for="negative-label" class="font-weight-semibold">Negative Label</label>
+                        <select id="negative-label" class="form-control">
+                            <option value="" disabled selected>Select a negative label</option>
+                            <!-- Options populated dynamically -->
+                        </select>
+                    </div>
+                    <!-- Error Message -->
+                    <div id="selection-error" class="alert alert-danger d-none mt-3">
+                        <i class="fas fa-exclamation-triangle"></i> Labels must be different. Please select one positive and one negative label.
+                    </div>
+                    <!-- Loader -->
+                    <div id="loader" class="d-none text-center mt-3">
+                        <div class="spinner-border text-primary" role="status">
+                            <span class="sr-only">Loading...</span>
+                        </div>
+                        <p>Saving your choices...</p>
+                    </div>
+                </div>
+
+            <!-- Modal Footer -->
+            <div class="modal-footer">
+                <button type="button" class="btn btn-primary" id="save-label-choices">Save Choices</button>
+            </div>
+        </div>
+    </div>
+</div>
+
+
 {% if dataset_type == "tabular" and df_name and data_to_display %}
+
     <div class="row mb-4">
         <!-- Data Card with Original ID -->
         <div class="col-lg-6" id="df_cached">
@@ -317,7 +566,20 @@
             </div>
         </div>
     </div>
+
+    <div class="row mt-3" id="new_or_load_cached">
+        <div class="col d-flex justify-content-center">
+            <div class="text-center mt-4">
+                <button id="viewModelsButton" class="btn btn-view-models">
+                    View Pre-trained Models
+                    <i class="fas fa-arrow-right ml-2"></i> <!-- Font Awesome icon for added appeal -->
+                </button>
+            </div>
+        </div>
+    </div>
+
 {% elif dataset_type == "timeseries" %}
+
     <div class="row mb-4">
         <!-- Confidence Interval Card with Original ID -->
         <div class="col-lg-6" id="ts_confidence_cached">
@@ -343,20 +605,27 @@
             </div>
         </div>
     </div>
-{% endif %}
 
-
-<!-- Loader -->
-<div class="row">
-    <div class="col d-flex justify-content-center">
-        <span class="loader" id="loader" style="display: none;"></span>
+    <div class="row mt-3" id="new_or_load_cached">
+        <div class="col d-flex justify-content-center">
+            <div class="text-center mt-4">
+                <button id="viewPreTrainedButton" class="btn btn-view-models">
+                    View Pre-trained Models
+                    <i class="fas fa-arrow-right ml-2"></i> <!-- Font Awesome icon for added appeal -->
+                </button>
+            </div>
+        </div>
     </div>
-</div>
 
-<div class="row mt-3" id="new_or_load">
+{% endif %}
+<!-- Loader -->
+<div class="d-flex justify-content-center">
+    <span class="loader" id="loader_ds" style="display: none;"></span>
+</div>
+<div class="row mt-3" id="new_or_load" style="display:none;">
     <div class="col d-flex justify-content-center">
         <div class="text-center mt-4">
-            <button id="viewModelsButton" class="btn btn-view-models">
+            <button id="viewPreTrainedButton" class="btn btn-view-models">
                 View Pre-trained Models
                 <i class="fas fa-arrow-right ml-2"></i> <!-- Font Awesome icon for added appeal -->
             </button>
@@ -365,9 +634,6 @@
 </div>
 
 <!-- JavaScript -->
-<script type="module" src="{% static 'js/radio_dataset.js' %}"></script>
-<script type="module" src="{% static 'js/selection_change.js' %}"></script>
-<script type="module" src="{% static 'js/radio_timeseries_dataset.js' %}"></script>
-<script type="module" src="{% static 'js/radio_uploaded_dataset.js' %}"></script>
+<script type="module" src="{% static 'js/home.js' %}"></script>
 
 {% endblock content%}
diff --git a/base/templates/base/train.html b/base/templates/base/train.html
index f3f2d90cf..60b936371 100755
--- a/base/templates/base/train.html
+++ b/base/templates/base/train.html
@@ -21,7 +21,7 @@
         
         <div class="row">
             {% if df_name %}
-                <div class="col-xl-10 col-lg-10">
+                <div class="col-xl-12 col-lg-12">
                     <div class="card shadow-sm mb-4 border-0  animate-card">
                         <div class="card-header bg-light text-dark py-3 d-flex flex-row align-items-center justify-content-between"> <!-- Softer background and font color -->
                             <h6 class="m-0">DataFrame Summary Information</h6> <!-- Reduced emphasis -->
@@ -33,7 +33,6 @@
                         
                         <div class="card-body">
                             <div class="row">
-                                
                                 <div class="col-xl-3 col-lg-3">
                                     <div class="py-3 d-flex flex-row align-items-center justify-content-between">
                                         <h6 class="m-0 text-muted">Classifier</h6> <!-- Text-muted for subtlety -->
@@ -63,7 +62,7 @@
 
                             <!-- Test set ratio slider -->
                             <div class="row" style="padding-top:20px;">
-                                <div class="col-xl-6 col-lg-6" id="ratio" {% if dataset_type == "timeseries" %} style="display:none;" {% endif %}>
+                                <div class="col-xl-4 col-lg-4" id="ratio" {% if dataset_type == "timeseries" %} style="display:none;" {% endif %}>
                                     <div class="py-3 d-flex flex-row align-items-center justify-content-between">
                                         <h6 class="m-0 text-muted">Test Set Ratio</h6>
                                     </div>
@@ -71,7 +70,7 @@
                                     <output id="value"></output>
                                 </div>
                                 {% if dataset_type == "tabular" %}
-                                    <div class="col-xl-4 col-lg-4" id="class_label" style="display:none;">
+                                    <div class="col-xl-4 col-lg-4" id="class_label">
                                         <div class="py-3 d-flex flex-row align-items-center justify-content-between">
                                             <h6 class="m-0 text-muted">Class Label</h6>
                                         </div>
@@ -94,17 +93,7 @@
                                     </div>
                                 {% endif %}
                             </div>
-
                             <!-- Action Button Section -->
-                            <div class="row justify-content-md-center" style="padding-top:30px;"> 
-                                {% csrf_token %}
-                                <button class="btn btn-outline-primary train_test" role="button" disabled>Go!</button> <!-- Outlined button for minimalistic style -->
-                                <div id="loader_train" style="display: none;">
-                                    <div class="col-sm d-flex justify-content-center">
-                                        <span class="loader"></span>
-                                    </div>
-                                </div>
-                            </div>
                         </div>
                     </div>
                 </div>
@@ -121,6 +110,142 @@
                 </div>
             {% endif %}
         </div>
+        <div class="d-flex justify-content-center mt-4">
+            <div id="error_message_new_x_2" class="alert alert-danger alert-dismissible text-center" style="display: none; width: 100%; max-width: 400px;" role="alert">
+                <i class="fas fa-exclamation-triangle"></i> 
+                <span id="error_message_text">Please correct errors before proceeding.</span>
+                <button type="button" class="close" aria-label="Close" onclick="$('#error_message_new_x_2').hide();">
+                    <span aria-hidden="true">&times;</span>
+                </button>
+            </div>
+        </div>
+
+        <!-- Modal Window -->
+        <div class="modal fade" id="modelAnalysisModal" tabindex="-1" aria-labelledby="modelAnalysisModalLabel" aria-hidden="true" data-backdrop="static" data-keyboard="false">
+            <div class="modal-dialog modal-dialog-centered modal-lg">
+                <div class="modal-content">
+                    <!-- Modal Header -->
+                    <div class="modal-header bg-light text-dark">
+                        <h5 class="modal-title" id="modelAnalysisModalLabel">Model Analysis and Decision</h5>
+                    </div>
+                    <!-- Modal Body -->
+                    <div class="modal-body">
+                        <!-- Prompt Message -->
+                        <div class="alert alert-info">
+                            <i class="fas fa-info-circle mr-2"></i>
+                            After training your model/classifier, you should now decide whether to <strong>keep</strong> it or <strong>discard</strong> it based on its performance metrics and visualizations below.
+                        </div>
+                        
+                        <!-- Tabs Navigation -->
+                        <ul class="nav nav-tabs" id="analysisTabs" role="tablist">
+                            <li class="nav-item">
+                                <a class="nav-link" id="classification-tab" data-toggle="tab" href="#classification" role="tab" aria-controls="classification" aria-selected="false">
+                                    <i class="fas fa-chart-line mr-2"></i>Classification Report
+                                </a>
+                            </li>
+                            <li class="nav-item">
+                                <a class="nav-link" id="details-tab" data-toggle="tab" href="#details" role="tab" aria-controls="details" aria-selected="false">
+                                    <i class="fas fa-info-circle mr-2"></i>Classifier Details
+                                </a>
+                            </li>
+                            <li class="nav-item">
+                                <a class="nav-link active" id="pca-tab" data-toggle="tab" href="#pca" role="tab" aria-controls="pca" aria-selected="true">
+                                    <i class="fas fa-project-diagram mr-2"></i>PCA
+                                </a>
+                            </li>
+                            <li class="nav-item" id="feature-tab-nav" style="display: none;">
+                                <a class="nav-link" id="fi-tab" data-toggle="tab" href="#feature" role="tab" aria-controls="feature" aria-selected="false">
+                                    <i class="fas fa-th mr-2"></i>Feature Importance
+                                </a>
+                            </li>
+                            <li class="nav-item" id="tsne-tab-nav" style="display: none;">
+                                <a class="nav-link" id="tsne-tab" data-toggle="tab" href="#tsne" role="tab" aria-controls="tsne" aria-selected="true">
+                                    <i class="fas fa-clone mr-2"></i>TSNE
+                                </a>
+                            </li>
+                        </ul>
+                        
+                        <!-- Tabs Content -->
+                        <div class="tab-content mt-3" id="analysisTabsContent">
+                            <!-- Classification Report Tab -->
+                            <div class="tab-pane fade" id="classification" role="tabpanel" aria-labelledby="classification-tab">
+                                <div id="classification_report" class="p-3"></div>
+                            </div>
+                            
+                            <!-- Classifier Details Tab -->
+                            <div class="tab-pane fade" id="details" role="tabpanel" aria-labelledby="details-tab">
+                                <div id="details_content" class="p-3 overflow-auto"></div>
+                            </div>
+                            
+                            <!-- PCA Tab -->
+                            <div class="tab-pane fade show active" id="pca" role="tabpanel" aria-labelledby="pca-tab">
+                                <div id="pca_container" class="p-3"></div>
+                            </div>
+                            
+                            <!-- Feature Importance Tab -->
+                            <div class="tab-pane fade" id="feature" role="tabpanel" aria-labelledby="fi-tab">
+                                <div id="fi_container" class="p-3"></div>
+                            </div>
+                            
+                            <!-- TSNE Tab -->
+                            <div class="tab-pane fade" id="tsne" role="tabpanel" aria-labelledby="tsne-tab">
+                                <div id="tsne_container" class="p-3"></div>
+                            </div>
+                        </div>
+                    </div>
+        
+                    {% csrf_token %}
+                    
+                    <!-- Modal Footer -->
+                    <div class="modal-footer">
+                        <button type="button" class="btn btn-success" id="save-model">
+                            <i class="fas fa-save mr-2"></i>Save Model
+                        </button>
+                        <button type="button" class="btn btn-danger" id="discard-model">
+                            <i class="fas fa-trash-alt mr-2"></i>Discard Model
+                        </button>
+                    </div>
+                </div>
+            </div>
+        </div>        
+
+        <div class="row justify-content-center align-items-center my-4">
+            <!-- CSRF Token -->
+            {% csrf_token %}
+        
+            <!-- Button -->
+            <div class="col-auto" id="train_test_btn">
+                <button class="btn btn-primary train_test align-items-center px-4 py-2 shadow-sm">
+                    <i class="fas fa-play mr-2"></i>
+                    Start Training
+                </button>
+            </div>
+        
+            <!-- Loader -->
+            <div id="loader_train" class="col-auto d-none">
+                <div class="d-flex align-items-center text-muted">
+                    <div class="spinner-border spinner-border-sm text-primary mr-2" role="status"></div>
+                    <span>Processing...</span>
+                </div>
+            </div>
+        </div>
+
+        <div class="row mt-3" id="new_or_load">
+            <div class="col d-flex justify-content-center">
+                <div class="text-center mt-4 d-flex justify-content-center">
+                    <!-- Back to Dataset Selection Button -->
+                    <button id="backToDatasetButton" class="btn btn-view-models mr-3">
+                        <i class="fas fa-arrow-left mr-2"></i> Back to Dataset Selection
+                    </button>
+                    
+                    <!-- View Counterfactuals Button -->
+                    <button id="viewPreTrainedButton" class="btn btn-view-models">
+                        View Pre-Trained Models <i class="fas fa-arrow-right ml-2"></i>
+                    </button>
+                </div>
+            </div>
+        </div>
+
     </div>
 </div>
 <script src="{% static 'js/slider.js' %}"></script>
diff --git a/base/views.py b/base/views.py
index 39cb317c4..19ac3e02a 100755
--- a/base/views.py
+++ b/base/views.py
@@ -1,177 +1,41 @@
-from django.shortcuts import render, HttpResponse, HttpResponseRedirect
-from django.shortcuts import redirect, render
+from django.shortcuts import render
+from django.shortcuts import render
 import base.pipeline as pipeline
-import pickle, os
-import pandas as pd
-import json
-from sklearn.preprocessing import LabelEncoder
-import joblib
 from dict_and_html import *
-from django.conf import settings
 from . import methods
 from .methods import PIPELINE_PATH
-import math
-import numpy as np
-from django.core.files.storage import FileSystemStorage
 import random
-from collections import defaultdict
-from .glacier.src.glacier_compute_counterfactuals import gc_compute_counterfactuals
 import base.pipeline as pipeline
-import concurrent.futures
+import os
+from . handlers import home_handler, counterfactuals_handler, charts_handler, train_handler
 
 
 def home(request):
     # ajax request condition
     if request.headers.get("X-Requested-With") == "XMLHttpRequest":
-        return ajax_requests(request.POST.get("action"), request)
+        return home_handler(request.POST.get("action"), request)
 
-    if request.method == "POST" and request.FILES["excel_file"]:
-        uploaded_file = request.FILES["excel_file"]  # Get the file from request.FILES
-        dataset_type = request.POST.get("dataset_type")
+    if "upload" in request.session:
+        upload = request.session.get("upload")
+    else:
+        upload = 0
 
-        # action to add dataset when from radio button click
-        # add name of used dataframe in session for future use
-        request.session["df_name"] = "upload"
-        name = uploaded_file.name
-
-        # Split the name and extension
-        base_name, extension = os.path.splitext(name)
-        request.session["df_name_upload_base_name"] = base_name
-        request.session["df_name_upload_extension"] = extension
-
-        df_name = base_name
-
-        df_name_path = os.path.join(
-            PIPELINE_PATH + f"{base_name}",
-        )
-
-        if not os.path.exists(df_name_path):
-            os.makedirs(df_name_path)
-
-        fs = FileSystemStorage()  # FileSystemStorage to save the file
-
-        # Save the file with the new filename
-        fs = FileSystemStorage(location=df_name_path)
-        filename = fs.save(uploaded_file.name, uploaded_file)  # Save file
-
-        request.session["excel_file_name"] = df_name_path
-
-        excel_file_name_path = os.path.join(PIPELINE_PATH + f"{base_name}" + "/" + name)
-
-        df = methods.get_dataframe(excel_file_name_path)
-
-        ## update the datasets_types json file
-        datasets_types_pipeline_json_path = os.path.join(
-            PIPELINE_PATH + "/dataset_types_pipeline.json"
-        )
-        jsonFile = pipeline.pipeline_json(datasets_types_pipeline_json_path)
-
-        # with open(datasets_types_pipeline_json_path, "r") as jsonFile:
-        #     datasets_types_pipeline_json = pipeline.load(
-        #         jsonFile
-        #     )  # data becomes a dictionary
-
-        jsonFile.append_pipeline_json({df_name: [dataset_type, "uploaded"]})
-        dataset_type = jsonFile.read_pipline_json([df_name])[0]
-        uploaded_files = jsonFile.get_keys_with_specific_value("uploaded")
-
-        # datasets_types_pipeline_json[df_name] = dataset_type
-        # with open(datasets_types_pipeline_json_path, "w") as file:
-        #     pipeline.dump(
-        #         datasets_types_pipeline_json, file, indent=4
-        #     )  # Write with pretty print (indent=4)
-
-        if df.columns.str.contains(" ").any():
-            df.columns = df.columns.str.replace(" ", "_")
-            # if columns contain space
-            os.remove(excel_file_name_path)
-            df.to_csv(excel_file_name_path, index=None)
-            df = methods.get_dataframe(excel_file_name_path)
-
-        if "id" in df.columns:
-            df.drop(["id"], axis=1, inplace=True)
-            df.to_csv(excel_file_name_path, index=False)
-
-        if dataset_type == "tabular":
-            # tabular datasets
-            features = df.columns
-            feature1 = df.columns[3]
-            feature2 = df.columns[2]
-
-            labels = list(df.select_dtypes(include=["object", "category"]).columns)
-            # Find binary columns (columns with only two unique values, including numerics)
-            binary_columns = [col for col in df.columns if df[col].nunique() == 2]
-
-            # Combine categorical and binary columns into one list
-            labels = list(set(labels + binary_columns))
-
-            label = random.choice(labels)
-            fig = methods.stats(
-                excel_file_name_path,
-                dataset_type,
-                None,
-                None,
-                feature1,
-                feature2,
-                label,
-                df_name,
-            )
-
-            # tabular dataset
-            request.session["data_to_display"] = df[:10].to_html()
-            request.session["features"] = list(features)
-            request.session["feature1"] = feature1
-            request.session["feature2"] = feature2
-            request.session["labels"] = list(labels)
-            request.session["curlabel"] = label
-            request.session["fig"] = fig
-
-            context = {
-                "dataset_type": dataset_type,
-                "data_to_display": df[:10].to_html(),
-                "fig": fig,
-                "features": list(features),  # error if not a list
-                "feature1": feature1,
-                "feature2": feature2,
-                "labels": list(labels),
-                "curlabel": label,
-                "df_name": request.session["df_name"],
-            }
-        elif dataset_type == "timeseries":
-            fig, fig1 = methods.stats(excel_file_name_path, dataset_type)
-            request.session["fig"] = fig
-            request.session["fig1"] = fig1
-            context = {
-                "dataset_type": dataset_type,
-                "df_name": df_name,
-                "fig": fig,
-                "fig1": fig1,
-            }
-
-        print("Uploaded files: ", uploaded_files)
-        context.update({"uploaded_files": uploaded_files})
-        request.session["context"] = context
-
-        return render(request, "base/home.html", context)
-
-    upload = 0
     ## get the type of the active dataset
-    datasets_types_pipeline_json_path = os.path.join(
-        PIPELINE_PATH + "/dataset_types_pipeline.json"
+    datasets_types_PipelineJSON_path = os.path.join(
+        PIPELINE_PATH + "dataset_types_pipeline.json"
     )
-    datasets_types_pipeline_json = pipeline.pipeline_json(
-        datasets_types_pipeline_json_path
+    datasets_types_PipelineJSON = pipeline.PipelineJSON(
+        datasets_types_PipelineJSON_path
     )
-    uploaded_files = datasets_types_pipeline_json.get_keys_with_specific_value(
+
+    uploaded_files = datasets_types_PipelineJSON.get_keys_with_value(
         "uploaded"
     )
-
-    if "df_name" in request.session:
+    
+    if "df_name" in request.session and request.session["df_name"] != "upload":
         df_name = request.session.get("df_name")
-        if df_name == "upload":
-            upload = 1
-            df_name = request.session.get("df_name_upload_base_name")
-        dataset_type = datasets_types_pipeline_json.read_pipline_json([df_name])
+
+        dataset_type = datasets_types_PipelineJSON.read_from_json([df_name])
 
         if type(dataset_type) is list:
             dataset_type = dataset_type[0]
@@ -200,13 +64,14 @@ def home(request):
                 }
         elif dataset_type == "timeseries":
             context = {
+                "upload": upload,
                 "df_name": df_name,
                 "dataset_type": dataset_type,
                 "fig": request.session.get("fig"),
                 "fig1": request.session.get("fig1"),
             }
-        # else:
-        #     context = {}
+        else:
+            context = {}
     else:
         context = {}
 
@@ -217,7 +82,7 @@ def home(request):
 def counterfactuals(request):
     # ajax request condition
     if request.headers.get("X-Requested-With") == "XMLHttpRequest":
-        return ajax_requests(request.POST.get("action", None), request)
+        return counterfactuals_handler(request.POST.get("action", None), request)
     available_pretrained_models_info = []
     if "df_name" in request.session:
         df_name = request.session.get("df_name")
@@ -239,16 +104,16 @@ def counterfactuals(request):
             # if it does not exist, obviously there are no pre trained
             # models
             available_pretrained_models = []
-            jsonFile = pipeline.pipeline_json(json_path)
-            if not jsonFile.check_key_pipeline_json("classifier"):
+            jsonFile = pipeline.PipelineJSON(json_path)
+            if not jsonFile.key_exists("classifier"):
                 # pre trained models do not exist
                 available_pretrained_models = []
             else:
                 # if it exists
                 # check the section of "classifiers"
                 # folder path
-                if jsonFile.check_key_pipeline_json("classifier"):
-                    available_pretrained_models = jsonFile.read_pipline_json(
+                if jsonFile.key_exists("classifier"):
+                    available_pretrained_models = jsonFile.read_from_json(
                         ["classifier"]
                     ).keys()
                     available_pretrained_models_info = (
@@ -258,21 +123,21 @@ def counterfactuals(request):
                     )
 
             ## get the type of the active dataset
-            datasets_types_pipeline_json_path = os.path.join(
+            datasets_types_PipelineJSON_path = os.path.join(
                 PIPELINE_PATH + "/dataset_types_pipeline.json"
             )
-            datasets_types_pipeline_json = pipeline.pipeline_json(
-                datasets_types_pipeline_json_path
+            datasets_types_PipelineJSON = pipeline.PipelineJSON(
+                datasets_types_PipelineJSON_path
             )
-            dataset_type = datasets_types_pipeline_json.read_pipline_json([df_name])
+            dataset_type = datasets_types_PipelineJSON.read_from_json([df_name])
             if type(dataset_type) is list:
                 dataset_type = dataset_type[0]
-            
+
             # model_name_path = os.path.join(
             #     PIPELINE_PATH + f"{df_name}" + "/trained_models/" + pre_trained_model_name
             # )
             # tsne = joblib.load(model_name_path + "/tsne.sav")
-        
+
             if dataset_type == "tabular":
 
                 context = {
@@ -297,12 +162,12 @@ def counterfactuals(request):
                 target_label_info = zip(target_label_value, target_label_text)
 
                 available_pre_computed_counterfactuals = []
-                if jsonFile.check_key_pipeline_json("classifier"):
-                    if jsonFile.check_key_pipeline_json("glacier"):
-                        if jsonFile.check_key_pipeline_json("experiments"):
+                if jsonFile.key_exists("classifier"):
+                    if jsonFile.key_exists("glacier"):
+                        if jsonFile.key_exists("experiments"):
                             # applies only to glacier
                             # there are pre computed counterfactuals
-                            experiments_dict = jsonFile.read_pipline_json(
+                            experiments_dict = jsonFile.read_from_json(
                                 ["classifier", "glacier", "experiments"]
                             )
                             list_of_experiment_keys = list(experiments_dict.keys())
@@ -314,6 +179,8 @@ def counterfactuals(request):
 
                 else:
                     available_pre_computed_counterfactuals = None
+                
+                print(available_pre_computed_counterfactuals)
 
                 context = {
                     "df_name": df_name,
@@ -331,7 +198,7 @@ def counterfactuals(request):
 def train(request):
     # ajax request condition
     if request.headers.get("X-Requested-With") == "XMLHttpRequest":
-        return ajax_requests(request.POST.get("action"), request)
+        return train_handler(request.POST.get("action"), request)
 
     df_name = request.session.get("df_name")
 
@@ -339,13 +206,13 @@ def train(request):
         df_name = request.session.get("df_name_upload_base_name")
 
     ## get the type of the active dataset
-    datasets_types_pipeline_json_path = os.path.join(
+    datasets_types_PipelineJSON_path = os.path.join(
         PIPELINE_PATH + "/dataset_types_pipeline.json"
     )
-    datasets_types_pipeline_json = pipeline.pipeline_json(
-        datasets_types_pipeline_json_path
+    datasets_types_PipelineJSON = pipeline.PipelineJSON(
+        datasets_types_PipelineJSON_path
     )
-    dataset_type = datasets_types_pipeline_json.read_pipline_json([df_name])
+    dataset_type = datasets_types_PipelineJSON.read_from_json([df_name])
 
     if type(dataset_type) is list:
         dataset_type = dataset_type[0]
@@ -400,6 +267,7 @@ def train(request):
         excel_file_name_path = os.path.join(
             PIPELINE_PATH + f"{df_name}" + "/" + df_name + ".csv"
         )
+
         df = methods.get_dataframe(excel_file_name_path)
         df.columns = df.columns.str.replace(" ", "_")
         preprocessing_value = ["std", "denoise", "imp"]
@@ -408,6 +276,7 @@ def train(request):
             "Denoising",
             "Imputations",
         ]
+
         preprocessing_info = zip(preprocessing_value, preprocessing_text)
         classifiers_value = ["wildboar_knn", "wildboar_rsf", "glacier"]
         classifiers_text = [
@@ -415,6 +284,7 @@ def train(request):
             "Wildboar-Random Shapelet Forest (classifier train)",
             "Glacier 1DCNN",
         ]
+
         classifiers_info = zip(classifiers_value, classifiers_text)
         context = {
             "dataset_type": dataset_type,
@@ -430,10 +300,11 @@ def train(request):
 def charts(request):
     # ajax request condition
     if request.headers.get("X-Requested-With") == "XMLHttpRequest":
-        return ajax_requests(request.POST.get("action"), request)
+        return charts_handler(request.POST.get("action"), request)
 
     if "df_name" in request.session:
-        df_name = request.session.get("df_name")
+        df_name = request.session["df_name"]
+        
         if df_name == "upload":
             df_name = request.session.get("df_name_upload_base_name")
 
@@ -441,11 +312,11 @@ def charts(request):
         json_path = os.path.join(PIPELINE_PATH + f"{df_name}" + "/pipeline.json")
 
         if os.path.exists(json_path):
-            jsonFile = pipeline.pipeline_json(json_path)
+            jsonFile = pipeline.PipelineJSON(json_path)
             # if it does not exist, obviously there are no pre trained
             # models
 
-            if not jsonFile.check_key_pipeline_json("classifier"):
+            if not jsonFile.key_exists("classifier"):
                 # pre trained models do not exist
                 # check if dataset directory exists
                 df_dir = os.path.join(PIPELINE_PATH + f"{df_name}")
@@ -460,7 +331,7 @@ def charts(request):
                 # if it exists
                 # check the section of "classifiers"
                 # folder path
-                available_pretrained_models = jsonFile.read_pipline_json(
+                available_pretrained_models = jsonFile.read_from_json(
                     ["classifier"]
                 ).keys()
 
@@ -479,1283 +350,3 @@ def charts(request):
         context = {}
 
     return render(request, "base/charts.html", context)
-
-
-## AJAX REQUSTS HANDLER
-def ajax_requests(action, request):
-    if action == "click_graph":
-        # get df used name
-        df_name = request.session.get("df_name")
-        df_name = request.session.get("df_name")
-        if df_name == "upload":
-            df_name = request.session.get("df_name_upload_base_name")
-        # get model_name
-        model_name = request.POST.get("model_name")
-
-        # preprocessed_path
-        excel_file_name_preprocessed_path = os.path.join(
-            PIPELINE_PATH + f"{df_name}" + "/" + df_name + "_preprocessed" + ".csv"
-        )
-
-        excel_file_name_path = os.path.join(
-            PIPELINE_PATH + f"{df_name}" + "/" + df_name + ".csv"
-        )
-
-        model_name_path = os.path.join(
-            PIPELINE_PATH + f"{df_name}" + "/trained_models/" + model_name
-        )
-
-        # pipeline path
-        json_path = os.path.join(PIPELINE_PATH, f"{df_name}" + "/pipeline.json")
-
-        # load pipeline data
-        # jsonFile = open(json_path, "r")
-        # pipeline_data = pipeline_json.load(jsonFile)  # data becomes a dictionary
-        # class_label = pipeline_data["classifier"][model_name]["class_label"]
-        jsonFile = pipeline.pipeline_json(json_path)
-        class_label = jsonFile.read_pipline_json(
-            ["classifier", model_name, "class_label"]
-        )
-
-        df = pd.read_csv(excel_file_name_path)
-
-        # Load your saved feature importance from a .sav file
-        feature_importance_df = pd.read_csv(
-            model_name_path + "/feature_importance_df.csv"
-        )
-        # sorted_df = feature_importance_df.sort_values(by="importance", ascending=False)
-
-        # x and y coordinates of the clicked point in tsne
-        x_coord = request.POST["x"]
-        y_coord = request.POST["y"]
-
-        # tsne_projections
-        tsne_projections_path = os.path.join(
-            PIPELINE_PATH
-            + f"{df_name}/"
-            + f"trained_models/{model_name}"
-            + "/tsne_projections.json",
-        )
-
-        # tsne projections of all points (saved during generation of tsne)
-        projections = pd.read_json(tsne_projections_path)
-        projections = projections.values.tolist()
-
-        # projections array is a list of pairs with the (x, y)
-        # [ [], [], [] ... ]
-        # coordinates for a point in tsne. These are actual absolute
-        # coordinates and not SVG.
-        # find the pair of the projection with x and y coordinates matching that of
-        # clicked point coordinates
-        for clicked_id, item in enumerate(projections):
-            if math.isclose(item[0], float(x_coord)) and math.isclose(
-                item[1], float(y_coord)
-            ):
-                break
-
-        # save clicked point projections
-        request.session["clicked_point"] = item
-        # get clicked point row
-        row = df.iloc[[int(clicked_id)]]
-        request.session["cfrow_id"] = clicked_id
-        request.session["cfrow_og"] = row.to_html()
-        context = {
-            "row": row.to_html(index=False),
-            "feature_importance_dict": feature_importance_df.to_dict(orient="records"),
-        }
-
-    elif action == "counterfactual_select":
-
-        # if <select> element is used, and a specific counterfactual
-        # is inquired to be demonstrated:
-        df_name = request.session.get("df_name")
-        df_name = request.session.get("df_name")
-        if df_name == "upload":
-            df_name = request.session.get("df_name_upload_base_name")
-
-        model_name = request.session.get("model_name")
-        model_name_path = os.path.join(
-            PIPELINE_PATH + f"{df_name}" + "/trained_models/" + model_name
-        )
-
-        excel_file_name_path = os.path.join(
-            PIPELINE_PATH + f"{df_name}" + "/" + df_name + ".csv"
-        )
-
-        # pipeline path
-        json_path = os.path.join(PIPELINE_PATH, f"{df_name}" + "/pipeline.json")
-        # load pipeline data
-        jsonFile = pipeline.pipeline_json(json_path)
-
-        class_label = jsonFile.read_pipline_json(
-            ["classifier", model_name, "class_label"]
-        )
-
-        # decode counterfactual to original values
-        preprocessing_list = jsonFile.read_pipline_json(
-            ["classifier", model_name, "preprocessing"]
-        )
-
-        df = pd.read_csv(excel_file_name_path)
-        cf_df = pd.read_csv(model_name_path + "/counterfactuals.csv")
-        cf_id = request.POST["cf_id"]
-        row = cf_df.iloc[[int(cf_id)]]
-
-        if "id" in df.columns:
-            df = df.drop("id", axis=1)
-
-        dec_row = methods.decode_cf(
-            df, row, class_label, model_name_path, preprocessing_list
-        )
-
-        fig = joblib.load(model_name_path + "/tsne_cfs.sav")
-
-        # tsne stores data for each class in different data[]
-        # index.
-        # data[0] is class A
-        # data[1] is class B
-        # ...
-        # data[n-2] is counterfactuals
-        # data[n-1] is clicked point
-
-        fig_data_array_length = len(fig.data)
-        for i in range(fig_data_array_length - 2):
-            fig.data[i].update(
-                opacity=0.3,
-            )
-
-        # last one, data[n-1], contains clicked point
-        l = fig.data[fig_data_array_length - 1]
-        clicked_id = -1
-        for clicked_id, item in enumerate(list(zip(l.x, l.y))):
-            if math.isclose(
-                item[0], request.session.get("clicked_point")[0]
-            ) and math.isclose(item[1], request.session.get("clicked_point")[1]):
-                break
-
-        # data[n-2] contains counterfactuals
-        fig.data[fig_data_array_length - 2].update(
-            selectedpoints=[int(cf_id)],
-            unselected=dict(
-                marker=dict(
-                    opacity=0.3,
-                )
-            ),
-        )
-        fig.data[fig_data_array_length - 1].update(
-            selectedpoints=[clicked_id],
-            unselected=dict(
-                marker=dict(
-                    opacity=0.3,
-                )
-            ),
-        )
-
-        if "id" in df.columns:
-            df = df.drop("id", axis=1)
-
-        # order the columns
-        dec_row = dec_row[df.columns]
-        clicked_point_row_id = request.session.get("cfrow_id")
-
-        # return only the differences
-        dec_row = dec_row.reset_index(drop=True)
-        df2 = df.iloc[[int(clicked_point_row_id)]].reset_index(drop=True)
-        difference = dec_row.loc[
-            :,
-            [
-                methods.compare_values(dec_row[col].iloc[0], df2[col].iloc[0])
-                for col in dec_row.columns
-            ],
-        ]
-
-        merged_df = pd.concat([df2[difference.columns], difference], ignore_index=True)
-        print(merged_df)
-        context = {
-            "row": merged_df.to_html(index=False),
-            "fig": fig.to_html(),
-        }
-
-    elif action == "reset_graph":
-
-        model_name = request.session.get("model_name")
-        # dataframe name
-        excel_file_name = request.session.get("df_name")
-        # save the plots for future use
-        # folder path: pipelines/<dataset name>/trained_models/<model_name>/
-        model_name_path = os.path.join(
-            PIPELINE_PATH + f"{excel_file_name}" + "/trained_models/" + model_name
-        )
-
-        model_name_dir_path = os.path.join(PIPELINE_PATH + f"{df_name}")
-
-        tsne = joblib.load(model_name_dir_path + "/tsne.sav")
-        context = {"fig": tsne.to_html()}
-
-    elif action == "dataset" or action == "uploaded_datasets":
-
-        # action to add dataset when from radio button click
-        name = request.POST.get("df_name")
-        request.session["df_name"] = name
-
-        if name == "upload":
-            name = request.session.get("df_name_upload_base_name")
-
-        if name == "timeseries":
-            name = request.session.get("df_name")
-
-        excel_file_name_path = os.path.join(
-            PIPELINE_PATH + f"{name}" + "/" + name + ".csv",
-        )
-
-        datasets_types_pipeline_json_path = os.path.join(
-            PIPELINE_PATH + "/dataset_types_pipeline.json"
-        )
-        datasets_types_pipeline_json = pipeline.pipeline_json(
-            datasets_types_pipeline_json_path
-        )
-        dataset_type = datasets_types_pipeline_json.read_pipline_json([name])
-        uploaded_files = datasets_types_pipeline_json.get_keys_with_specific_value(
-            "uploaded"
-        )
-
-        if request.POST.get("df_name") == "upload" or action == "uploaded_datasets":
-            if type(dataset_type) is list:
-                dataset_type = dataset_type[0]
-
-        if request.POST.get("df_name") != "upload" or action == "uploaded_datasets":
-            if os.path.exists(excel_file_name_path):
-                df = methods.get_dataframe(excel_file_name_path)
-                df.columns = df.columns.str.replace(" ", "_")
-                request.session["excel_file_name"] = excel_file_name_path
-
-                json_path = os.path.join(PIPELINE_PATH + f"{name}" + "/pipeline.json")
-                if not os.path.exists(json_path):
-                    pipeline_json = pipeline.pipeline_json(json_path)
-                    pipeline_json.append_pipeline_json({"name": name})
-
-                if "tabular" == dataset_type:
-
-                    if "id" in df.columns:
-                        df.drop(["id"], axis=1, inplace=True)
-                        df.to_csv(excel_file_name_path, index=False)
-
-                    # tabular datasets
-                    features = df.columns
-                    feature1 = df.columns[3]
-                    feature2 = df.columns[2]
-                    label = ""
-
-                    labels = list(
-                        df.select_dtypes(include=["object", "category"]).columns
-                    )
-                    # Find binary columns (columns with only two unique values, including numerics)
-                    binary_columns = [
-                        col for col in df.columns if df[col].nunique() == 2
-                    ]
-
-                    # Combine categorical and binary columns into one list
-                    labels = list(set(labels + binary_columns))
-                    label = random.choice(labels)
-                    fig = methods.stats(
-                        excel_file_name_path,
-                        dataset_type,
-                        feature1=feature1,
-                        feature2=feature2,
-                        label=label,
-                    )
-
-                    # tabular dataset
-                    request.session["data_to_display"] = df[:10].to_html()
-                    request.session["features"] = list(features)
-                    request.session["feature1"] = feature1
-                    request.session["feature2"] = feature2
-                    request.session["labels"] = list(labels)
-                    request.session["curlabel"] = label
-                    request.session["fig"] = fig
-
-                    context = {
-                        "dataset_type": dataset_type,
-                        "data_to_display": df[:10].to_html(),
-                        "fig": fig,
-                        "features": list(features),  # error if not a list
-                        "feature1": feature1,
-                        "feature2": feature2,
-                        "labels": list(labels),
-                        "curlabel": label,
-                        "uploaded_files": list(uploaded_files),
-                    }
-                elif dataset_type == "timeseries":
-
-                    fig, fig1 = methods.stats(
-                        excel_file_name_path, dataset_type, name=name
-                    )
-                    # timeseries
-                    request.session["fig"] = fig
-                    request.session["fig1"] = fig1
-                    context = {"fig": fig, "fig1": fig1, "dataset_type": dataset_type}
-
-                request.session["context"] = context
-            else:
-                context = {"uploaded_files": list(uploaded_files)}
-        else:
-            context = {}
-    elif action == "stat":
-
-        name = request.session.get("df_name")
-        datasets_types_pipeline_json_path = os.path.join(
-            PIPELINE_PATH + "/dataset_types_pipeline.json"
-        )
-        jsonFile = pipeline.pipeline_json(datasets_types_pipeline_json_path)
-        dataset_type = jsonFile.read_pipline_json([name])
-
-        if type(dataset_type) is list:
-            dataset_type = dataset_type[0]
-
-        file_path = os.path.join(
-            PIPELINE_PATH + f"{name}" + "/" + name + ".csv",
-        )
-        if dataset_type == "tabular":
-            feature1 = request.POST.get("feature1")
-            feature2 = request.POST.get("feature2")
-            label = request.POST.get("label")
-        else:
-            feature1 = request.POST.get("feature1")
-            feature2 = []
-            label = []
-
-        fig = methods.stats(
-            file_path,
-            dataset_type,
-            None,
-            None,
-            feature1=feature1,
-            feature2=feature2,
-            label=label,
-        )
-        context = {
-            "fig": fig,
-        }
-    elif action == "train":
-
-        # train a new model
-        # parameters sent via ajax
-        model_name = request.POST.get("model_name")
-        df_name = request.session.get("df_name")
-
-        # dataframe name
-
-        if df_name == "upload":
-            df_name = request.session.get("df_name_upload_base_name")
-
-        request.session["model_name"] = model_name
-        test_set_ratio = ""
-        if "test_set_ratio" in request.POST:
-            test_set_ratio = request.POST.get("test_set_ratio")
-
-        datasets_types_pipeline_json_path = os.path.join(
-            PIPELINE_PATH + "/dataset_types_pipeline.json"
-        )
-        jsonFile = pipeline.pipeline_json(datasets_types_pipeline_json_path)
-        dataset_type = jsonFile.read_pipline_json([df_name])
-
-        if type(dataset_type) is list:
-            dataset_type = dataset_type[0]
-
-        if "array_preprocessing" in request.POST:
-            array_preprocessing = request.POST.get("array_preprocessing")
-
-        if dataset_type == "tabular":
-            class_label = request.POST.get("class_label")
-            preprocessing_info = {
-                "preprocessing": array_preprocessing,
-                "test_set_ratio": test_set_ratio,
-                "explainability": {"technique": "dice"},
-                "class_label": class_label,
-            }
-        elif dataset_type == "timeseries":
-            if model_name != "glacier":
-                preprocessing_info = {
-                    "preprocessing": array_preprocessing,
-                    "test_set_ratio": test_set_ratio,
-                    "explainability": {"technique": model_name},
-                }
-            else:
-                # Path to the Bash script
-                autoencoder = request.POST.get("autoencoder")
-                preprocessing_info = {
-                    "autoencoder": autoencoder,
-                    "explainability": {"technique": model_name},
-                }
-
-        # absolute excel_file_name_path
-        excel_file_name_path = os.path.join(
-            PIPELINE_PATH + f"{df_name}" + "/" + df_name + ".csv"
-        )
-
-        # load paths
-        # absolute excel_file_preprocessed_path
-        excel_file_name_preprocessed_path = os.path.join(
-            PIPELINE_PATH,
-            f"{df_name}" + "/" + df_name + "_preprocessed" + ".csv",
-        )
-
-        json_path = os.path.join(PIPELINE_PATH + f"{df_name}" + "/pipeline.json")
-        jsonFile = pipeline.pipeline_json(json_path)
-        # save the plots for future use
-        # folder path: pipelines/<dataset name>/trained_models/<model_name>/
-
-        model_name_path = os.path.join(
-            PIPELINE_PATH + f"{df_name}" + "/trained_models/" + model_name
-        )
-
-        model_name_dir_path = os.path.join(PIPELINE_PATH + f"{df_name}")
-
-        # make the dir
-        if not os.path.exists(model_name_path):
-            os.makedirs(model_name_path)
-
-        # if json exists, simply append to it
-        # jsonFile = open(json_path, "r")
-        # pipeline_json = pipeline_json.load(jsonFile)  # data becomes a dictionary
-        # jsonFile.close()  # Close the JSON file
-
-        # if "classifier" in pipeline_json.keys():
-        #     temp_jason = {model_name: preprocessing_info}
-        #     pipeline_json["classifier"].update(temp_jason)
-        # else:
-        #     temp_jason = {
-        #         "preprocessed_name": df_name + "_preprocessed.csv",
-        #         "classifier": {model_name: preprocessing_info},
-        #     }
-        #     pipeline_json.update(temp_jason)
-
-        if jsonFile.check_key_pipeline_json("classifier"):
-            temp_json = {model_name: preprocessing_info}
-            jsonFile.update_pipeline_json(["classifier"], temp_json)
-        else:
-            temp_jason = {
-                "preprocessed_name": df_name + "_preprocessed.csv",
-                "classifier": {model_name: preprocessing_info},
-            }
-            jsonFile.append_pipeline_json(temp_jason)
-
-        if os.path.exists(excel_file_name_preprocessed_path) == True:
-            # if preprocessed_file exists
-            # delete it and do preprocessing again
-            # maybe should optimize it for cases
-            # where the preprocessing is the same with
-            # the one applited on the existing file
-            os.remove(excel_file_name_preprocessed_path)
-
-        # generate filename
-        idx = excel_file_name_path.index(".")
-        excel_file_name_preprocessed = (
-            df_name[:idx] + "_preprocessed" + excel_file_name_path[idx:]
-        )
-
-        # save file for preprocessing
-        preprocess_df = pd.read_csv(excel_file_name_path)
-        request.session["excel_file_name_preprocessed"] = excel_file_name_preprocessed
-
-        if dataset_type == "tabular":
-            le = LabelEncoder()
-            preprocess_df[class_label] = le.fit_transform(preprocess_df[class_label])
-            pickle.dump(le, open(model_name_path + "/label_encoder.sav", "wb"))
-
-            if "array_preprocessing" in request.POST:
-                preprocess_df = methods.preprocess(
-                    preprocess_df,
-                    array_preprocessing,
-                    excel_file_name_path,
-                    dataset_type,
-                    model_name_path,
-                    class_label,
-                )
-        elif dataset_type == "timeseries":
-
-            pos = jsonFile.read_pipline_json(["pos"])
-            neg = jsonFile.read_pipline_json(["neg"])
-            pos_label, neg_label = 1, 0
-
-            if pos != pos_label:
-                preprocess_df.iloc[:, -1] = preprocess_df.iloc[:, -1].apply(
-                    lambda x: pos_label if x == int(pos) else x
-                )
-            if neg != neg_label:
-                preprocess_df.iloc[:, -1] = preprocess_df.iloc[:, -1].apply(
-                    lambda x: neg_label if x == int(neg) else x
-                )
-
-            if "array_preprocessing" in request.POST:
-                preprocess_df = methods.preprocess(
-                    preprocess_df,
-                    array_preprocessing,
-                    excel_file_name_path,
-                    dataset_type,
-                    model_name_path,
-                )
-
-        # PCA
-        pca = methods.generatePCA(preprocess_df)
-        # TSNE
-        if dataset_type == "tabular":
-            tsne, projections = methods.generateTSNE(
-                preprocess_df, dataset_type, class_label
-            )
-        else:
-            tsne, projections = methods.generateTSNE(preprocess_df, dataset_type)
-
-        # save the plots
-        pickle.dump(tsne, open(model_name_path + "/tsne.sav", "wb"))
-        pickle.dump(pca, open(model_name_path + "/pca.sav", "wb"))
-
-        # save projections file for future use
-        with open(model_name_path + "/tsne_projections.json", "w") as f:
-            json.dump(projections.tolist(), f, indent=2)
-
-        if dataset_type == "tabular":
-            # training
-            feature_importance, classification_report, importance_dict = (
-                methods.training(
-                    preprocess_df,
-                    model_name,
-                    float(test_set_ratio),
-                    class_label,
-                    dataset_type,
-                    df_name,
-                    model_name_path,
-                )
-            )
-
-            # save some files
-            pickle.dump(
-                classification_report,
-                open(model_name_path + "/classification_report.sav", "wb"),
-            )
-            pickle.dump(
-                feature_importance,
-                open(model_name_path + "/feature_importance.sav", "wb"),
-            )
-
-            # feature importance on the original categorical columns (if they exist)
-            df = pd.read_csv(excel_file_name_path)
-            df = df.drop(class_label, axis=1)
-
-            # Initialize a dictionary to hold aggregated feature importances
-            categorical_columns = methods.get_categorical_features(df)
-
-            if categorical_columns:
-                aggregated_importance = {}
-                encoded_columns = methods.update_column_list_with_one_hot_columns(
-                    df, preprocess_df, df.columns
-                )
-
-                feature_mapping = defaultdict(list)
-                for col in encoded_columns:
-                    # Check if the column matches a pattern in categorical column names
-                    for original_col in categorical_columns:
-                        if col.startswith(original_col + "_"):
-                            feature_mapping[original_col].append(col)
-                            break
-                    else:
-                        # If no match, it's likely a numerical or non-encoded feature, map it to itself
-                        feature_mapping[col].append(col)
-
-                # Aggregate the feature importances
-                for original_feature, encoded_columns in feature_mapping.items():
-                    if original_feature not in encoded_columns:
-                        aggregated_importance[original_feature] = np.sum(
-                            [importance_dict[col] for col in encoded_columns]
-                        )
-                    else:
-                        aggregated_importance[original_feature] = importance_dict[
-                            original_feature
-                        ]
-
-                importance_df = pd.DataFrame(
-                    {
-                        "feature": list(aggregated_importance.keys()),
-                        "importance": list(aggregated_importance.values()),
-                    }
-                )
-                importance_df.to_csv(
-                    model_name_path + "/feature_importance_df.csv", index=None
-                )
-            else:
-                # if no categorical columns
-
-                # Combine feature names with their respective importance values
-                feature_importance_df = pd.DataFrame(
-                    {
-                        "feature": importance_dict.keys(),
-                        "importance": importance_dict.values(),
-                    }
-                )
-
-                feature_importance_df.to_csv(
-                    model_name_path + "/feature_importance_df.csv", index=None
-                )
-
-            # load pipeline data
-            # jsonFile = open(json_path, "r")
-            # pipeline_data = json.load(jsonFile)  # data becomes a dictionary
-            # classifier_data = pipeline_data["classifier"][model_name]
-            # classifier_data_html = dict_and_html(classifier_data)
-
-            classifier_data = jsonFile.read_pipline_json(["classifier", model_name])
-
-            classifier_data_html = dict_and_html(classifier_data)
-
-            context = {
-                "dataset_type": dataset_type,
-                "tsne": tsne.to_html(),
-                "class_report": classification_report.to_html(),
-                "feature_importance": feature_importance.to_html(),
-                "classifier_data": classifier_data_html,
-            }
-        elif dataset_type == "timeseries":
-
-            # training
-            # if model_name == "glacier":
-            #     path = model_name_path_type_dir
-            # else:
-            path = model_name_path
-            dataset_camel = methods.convert_to_camel_case(df_name)
-            if "Ecg" in dataset_camel:
-                dataset_camel = dataset_camel.replace("Ecg", "ECG")
-
-            experiment = methods.fetch_line_by_dataset(
-                PIPELINE_PATH + "/glacier_experiments.txt",
-                dataset_camel,
-            )
-
-            if experiment is not None:
-                stripped_arguments = methods.extract_arguments_from_line(experiment)
-
-            if model_name == "glacier":
-                classification_report = methods.training(
-                    preprocess_df,
-                    model_name,
-                    float(test_set_ratio) if test_set_ratio != "" else 0,
-                    "",
-                    dataset_type,
-                    df_name,
-                    path,
-                    autoencoder,
-                    stripped_arguments,
-                )
-            else:
-                classification_report = methods.training(
-                    preprocess_df,
-                    model_name,
-                    float(test_set_ratio) if test_set_ratio != "" else 0,
-                    "",
-                    dataset_type,
-                    df_name,
-                    path,
-                )
-
-            pickle.dump(
-                classification_report,
-                open(path + "/classification_report.sav", "wb"),
-            )
-
-            context = {
-                "dataset_type": dataset_type,
-                "pca": pca.to_html(),
-                "tsne": tsne.to_html(),
-                "classification_report": classification_report.to_html(),
-            }
-
-        preprocess_df.to_csv(excel_file_name_preprocessed_path, index=False)
-
-    elif action == "pre_trained":
-        # load pre trained models
-        pre_trained_model_name = request.POST.get("pre_trained")
-        request.session["model_name"] = pre_trained_model_name
-        # dataframe name
-        df_name = request.session.get("df_name")
-
-        if df_name == "upload":
-            df_name = request.session.get("df_name_upload_base_name")
-
-        model_name_path = os.path.join(
-            PIPELINE_PATH + f"{df_name}" + "/trained_models/" + pre_trained_model_name
-        )
-        
-        model_name_dir_path = os.path.join(PIPELINE_PATH + f"{df_name}")
-
-        # get the type of the file
-        datasets_types_pipeline_json_path = os.path.join(
-            PIPELINE_PATH + "/dataset_types_pipeline.json"
-        )
-        datasets_types_pipeline = pipeline.pipeline_json(
-            datasets_types_pipeline_json_path
-        )
-        dataset_type = datasets_types_pipeline.read_pipline_json([df_name])
-
-        if type(dataset_type) is list:
-            dataset_type = dataset_type[0]
-
-        if "url" in request.POST:
-            url = request.POST.get("url")
-            if url == "counterfactuals":
-                # only TSNE
-                tsne = joblib.load(model_name_path + "/tsne.sav")
-                
-                # Assuming you already have your fig object created, you can update it like this:
-                # Improved and modern t-SNE visualization
-                tsne.update_layout(
-                    # Modern Legend Design
-                    legend=dict(
-                        x=0.9,
-                        y=0.95,
-                        xanchor="right",
-                        yanchor="top",
-                        bgcolor="rgba(255,255,255,0.8)",  # Light semi-transparent white background
-                        bordercolor="rgba(0,0,0,0.1)",  # Light border for contrast
-                        borderwidth=1,
-                        font=dict(size=12, color="#444")  # Subtle grey for legend text
-                    ),
-                    # Tight Margins to Focus on the Plot
-                    margin=dict(l=10, r=10, t=30, b=10),  # Very slim margins for a modern look
-                    # Axis Design: Minimalist and Clean
-                    xaxis=dict(
-                        title_text="",  # No axis labels for a clean design
-                        tickfont=dict(size=10, color="#aaa"),  # Light grey for tick labels
-                        showline=True,
-                        linecolor="rgba(0,0,0,0.2)",  # Subtle line color for axis lines
-                        zeroline=False,                # No zero line for a sleek look
-                        showgrid=False,                # Hide grid lines for a minimal appearance
-                        ticks="outside",               # Small ticks outside the axis
-                        ticklen=3                      # Short tick marks for subtlety
-                    ),
-                    yaxis=dict(
-                        title_text="",  # No axis labels
-                        tickfont=dict(size=10, color="#aaa"),
-                        showline=True,
-                        linecolor="rgba(0,0,0,0.2)",
-                        zeroline=False,
-                        showgrid=False,
-                        ticks="outside",
-                        ticklen=3
-                    ),
-                    # Sleek Background
-                    plot_bgcolor="#fafafa",  # Very light grey background for a smooth finish
-                    paper_bgcolor="#ffffff",  # Pure white paper background
-                    # Modern Title with Elegant Style
-                    title=dict(
-                        text="t-SNE Visualization of Data",
-                        font=dict(size=16, color="#222", family="Helvetica, Arial, sans-serif"),  # Classy font style
-                        x=0.5,
-                        xanchor="center",
-                        yanchor="top",
-                        pad=dict(t=15)  # Padding to separate the title from the plot
-                    )
-                )
-
-                # Add hover effects for a smooth user experience
-                tsne.update_traces(hoverinfo="text+name", hoverlabel=dict(bgcolor="white", font_size=12, font_family="Arial"))
-                
-                context = {
-                    "tsne": tsne.to_html(),
-                }
-            else:
-                # load plots
-                pca = joblib.load(model_name_path + "/pca.sav")
-                classification_report = joblib.load(
-                    model_name_path + "/classification_report.sav"
-                )
-                # tsne = joblib.load(model_name_path + "/tsne.sav")
-
-                # pipeline path
-                json_path = os.path.join(PIPELINE_PATH, f"{df_name}" + "/pipeline.json")
-                jsonFile = pipeline.pipeline_json(json_path)
-
-                # load pipeline data
-                # jsonFile = open(json_path, "r")
-                # pipeline_data = json.load(jsonFile)  # data becomes a dictionary
-                # classifier_data = pipeline_data["classifier"][pre_trained_model_name]
-
-                classifier_data = jsonFile.read_pipline_json(
-                    ["classifier", pre_trained_model_name]
-                )
-                classifier_data_flattened = methods.flatten_dict(classifier_data)
-                classifier_data_df = pd.DataFrame([classifier_data_flattened])
-
-                if dataset_type == "tabular":
-                    feature_importance = joblib.load(
-                        model_name_path + "/feature_importance.sav"
-                    )
-                    context = {
-                        "dataset_type": dataset_type,
-                        "pca": pca.to_html(),
-                        "class_report": classification_report.to_html(),
-                        "feature_importance": feature_importance.to_html(),
-                        "classifier_data": classifier_data_df.to_html(),
-                    }
-                elif dataset_type == "timeseries":
-                    tsne = joblib.load(model_name_path + "/tsne.sav")
-                    context = {
-                        "dataset_type": dataset_type,
-                        "pca": pca.to_html(),
-                        "class_report": classification_report.to_html(),
-                        "tsne": tsne.to_html(),
-                        "classifier_data": classifier_data_df.to_html(),
-                    }
-
-    elif action == "cf":
-        # dataframe name
-        df_name = request.session.get("df_name")
-        if df_name == "upload":
-            df_name = request.session.get("df_name_upload_base_name")
-
-        # preprocessed_path
-        excel_file_name_preprocessed_path = os.path.join(
-            PIPELINE_PATH + f"{df_name}" + "/" + df_name + "_preprocessed" + ".csv"
-        )
-
-        excel_file_name_path = os.path.join(
-            PIPELINE_PATH + f"{df_name}" + "/" + df_name + ".csv"
-        )
-        # which model is being used during that session
-        model_name = request.POST.get("model_name")
-        # path of used model
-        model_name_path = os.path.join(
-            PIPELINE_PATH + f"{df_name}/" + "trained_models/" + f"{model_name}/"
-        )
-        model_name_dir_path = os.path.join(PIPELINE_PATH + f"{df_name}")
-
-        # read preprocessed data
-        if os.path.exists(excel_file_name_preprocessed_path):
-            df = pd.read_csv(excel_file_name_preprocessed_path)
-        else:
-            df = pd.read_csv(excel_file_name_path)
-
-        datasets_types_pipeline_json_path = os.path.join(
-            PIPELINE_PATH + "/dataset_types_pipeline.json"
-        )
-        datasets_types_pipeline = pipeline.pipeline_json(
-            datasets_types_pipeline_json_path
-        )
-        dataset_type = datasets_types_pipeline.read_pipline_json([df_name])
-
-        if type(dataset_type) is list:
-            dataset_type = dataset_type[0]
-
-        df_id = request.session.get("cfrow_id")
-        if dataset_type == "tabular":
-
-            # get row
-            features_to_vary = json.loads(request.POST.get("features_to_vary"))
-
-            row = df.iloc[[int(df_id)]]
-
-            # not preprocessed
-            notpre_df = pd.read_csv(excel_file_name_path)
-            notpre_row = notpre_df.iloc[[int(df_id)]]
-
-            # if feature_to_vary has a categorical column then I cannot just
-            # pass that to dice since the trained model does not contain the
-            # categorical column but the one-hot-encoded sub-columns
-            features_to_vary = methods.update_column_list_with_one_hot_columns(
-                notpre_df, df, features_to_vary
-            )
-
-            # pipeline path
-            json_path = os.path.join(PIPELINE_PATH, f"{df_name}" + "/pipeline.json")
-
-            # load pipeline data
-            jsonFile = pipeline.pipeline_json(json_path)
-            class_label = jsonFile.read_pipline_json(
-                ["classifier", model_name, "class_label"]
-            )  # data becomes a dictionary
-
-            # number of counterfactuals
-            # (TBD) input field value as parameter
-            # in ajax
-            num_counterfactuals = 5
-            le = LabelEncoder()
-            notpre_df[class_label] = le.fit_transform(notpre_df[class_label])
-
-            continuous_features = methods.get_continuous_features(df)
-            non_continuous_features = methods.get_non_continuous_features(df)
-
-            # load used classifier
-            clf = joblib.load(model_name_path + model_name + ".sav")
-
-            try:
-                # Set up the executor to run the function in a separate thread
-                with concurrent.futures.ThreadPoolExecutor() as executor:
-                    # Submit the function to the executor
-                    future = executor.submit(
-                        methods.counterfactuals,
-                        row,
-                        clf,
-                        df,
-                        class_label,
-                        continuous_features,
-                        num_counterfactuals,
-                        features_to_vary,
-                    )
-                    # Wait for the result with a timeout of 10 seconds
-                    counterfactuals = future.result(timeout=10)
-                    print("Counterfactuals computed successfully!")
-            except concurrent.futures.TimeoutError:
-                message = (
-                    "It seems like it took more than expected. Refresh and try again..."
-                )
-                print(message)
-                exit(1)
-                
-            if counterfactuals:
-                cf_df = counterfactuals[0].final_cfs_df
-                counterfactuals[0].final_cfs_df.to_csv(
-                    model_name_path + "counterfactuals.csv", index=False
-                )
-
-                # get coordinates of the clicked point (saved during 'click' event)
-                clicked_point = request.session.get("clicked_point")
-                clicked_point_df = pd.DataFrame(
-                    {
-                        "0": clicked_point[0],
-                        "1": clicked_point[1],
-                        f"{class_label}": row[class_label].astype(str),
-                    }
-                )
-
-                # tSNE
-                cf_df = pd.read_csv(model_name_path + "counterfactuals.csv")
-                model_name_dir_path = os.path.join(PIPELINE_PATH + f"{df_name}")
-                tsne_path_to_augment = model_name_path + "tsne.sav"
-                
-                tsne = methods.generateAugmentedTSNE(
-                    df,
-                    cf_df,
-                    num_counterfactuals,
-                    clicked_point_df,
-                    tsne_path_to_augment,
-                    class_label,
-                )
-                
-                tsne.update_layout(
-                    # Modern Legend Design
-                    legend=dict(
-                        x=0.85,
-                        y=0.95,
-                        xanchor="right",
-                        yanchor="top",
-                        bgcolor="rgba(0,0,0,0.05)",  # Transparent black background for a sleek look
-                        bordercolor="rgba(0,0,0,0.1)",  # Soft border for separation
-                        borderwidth=1,
-                        font=dict(size=12, color="#333")  # Modern grey font color for text
-                    ),
-                    # Tight Margins for a Focused Plot Area
-                    margin=dict(l=20, r=20, t=40, b=40),  # Reduced margins for a cleaner look
-                    # Axis Titles and Labels: Minimalist Design
-                    xaxis=dict(
-                        title_font=dict(size=14, color="#555"),  # Medium grey color for axis title
-                        tickfont=dict(size=11, color="#777"),    # Light grey color for tick labels
-                        showline=True,
-                        linecolor="rgba(0,0,0,0.15)",  # Subtle line color for axis lines
-                        zeroline=False,                # Hide the zero line for a cleaner design
-                        showgrid=False                 # No grid lines for a modern look
-                    ),
-                    yaxis=dict(
-                        title_font=dict(size=14, color="#555"),
-                        tickfont=dict(size=11, color="#777"),
-                        showline=True,
-                        linecolor="rgba(0,0,0,0.15)",
-                        zeroline=False,
-                        showgrid=False
-                    ),
-                    # Sleek Background Design
-                    plot_bgcolor="white",  # Crisp white background for a modern touch
-                    paper_bgcolor="white",  # Ensure the entire background is uniform
-                    # Title: Modern Font and Centered
-                    title=dict(
-                        text="t-SNE Visualization of Data",
-                        font=dict(size=18, color="#333", family="Arial, sans-serif"),  # Modern font style
-                        x=0.5,
-                        xanchor="center",
-                        yanchor="top",
-                        pad=dict(t=10)  # Padding to give the title breathing space
-                    )
-                )
-
-                pickle.dump(tsne, open(model_name_path + "tsne_cfs.sav", "wb"))
-
-                context = {
-                    "dataset_type": dataset_type,
-                    "model_name": model_name,
-                    "tsne": tsne.to_html(),
-                    "num_counterfactuals": num_counterfactuals,
-                    "default_counterfactual": "1",
-                    "clicked_point": notpre_row.to_html(),
-                    "counterfactual": cf_df.iloc[[1]].to_html(),
-                }
-
-            else:
-                context = {
-                    "dataset_type": dataset_type,
-                    "model_name": model_name,
-                    "message": "Please try again with different features.",
-                }
-        elif dataset_type == "timeseries":
-            model_name = request.POST["model_name"]
-            model_name_path = os.path.join(
-                PIPELINE_PATH + f"{df_name}/" + "trained_models/" + f"{model_name}/"
-            )
-            path = model_name_path
-            if model_name == "glacier":
-                constraint = request.POST["constraint"]
-                path = os.path.join(
-                    PIPELINE_PATH
-                    + f"{df_name}/"
-                    + "trained_models/"
-                    + f"{model_name}/"
-                    + f"{constraint}/"
-                )
-
-            X_test_path = os.path.join(model_name_path + "X_test.csv")
-            y_test_path = os.path.join(model_name_path + "y_test.npy")
-            y_pred_path = os.path.join(path + "y_pred.npy")
-            X_cf_path = os.path.join(path + "X_cf.npy")
-            cf_pred_path = os.path.join(path + "cf_pred.npy")
-
-            X_test = pd.read_csv(X_test_path)
-            y_test = np.load(y_test_path)
-            y_pred = np.load(y_pred_path)
-            X_cf = np.load(X_cf_path)
-            cf_pred = np.load(cf_pred_path)
-
-            if model_name != "glacier":
-                scaler = joblib.load(model_name_path + "/min_max_scaler.sav")
-                X_test = pd.DataFrame(scaler.inverse_transform(X_test))
-                X_cf = scaler.inverse_transform(X_cf)
-
-            fig = methods.ecg_plot_counterfactuals(
-                int(df_id), X_test, y_test, y_pred, X_cf, cf_pred
-            )
-
-            context = {
-                "df_name": df_name,
-                "fig": fig.to_html(),
-                "dataset_type": dataset_type,
-            }
-    elif action == "compute_cf":
-        model_name = request.POST.get("model_name")
-        if model_name == "glacier":
-            constraint_type = request.POST.get("constraint")
-            w_value = request.POST.get("w_value")
-            df_name = request.session.get("df_name")
-
-            model_name_path = os.path.join(
-                PIPELINE_PATH + f"{df_name}/" + "trained_models/" + f"{model_name}/"
-            )
-            model_name_path_constraint = model_name_path + f"{constraint_type}/"
-            if not os.path.exists(model_name_path_constraint):
-                os.makedirs(model_name_path_constraint)
-
-            # https://github.com/wildboar-foundation/wildboar/blob/master/docs/guide/explain/counterfactuals.rst#id27
-            classifier = joblib.load(model_name_path + "/classifier.sav")
-
-            # pipeline path
-            json_path = os.path.join(PIPELINE_PATH, f"{df_name}" + "/pipeline.json")
-            # load pipeline data
-            jsonFile = pipeline.pipeline_json(json_path)
-            autoencoder = jsonFile.read_pipline_json(
-                ["classifier", model_name, "autoencoder"]
-            )
-
-            experiment_dict = {"constraint": constraint_type, "w_value": w_value}
-
-            # if "experiments" in pipeline_data["classifier"][model_name]:
-            #     # if there exists key with value "experiments"
-            #     keys = pipeline_data["classifier"][model_name]["experiments"].keys()
-            #     last_key_int = int(list(keys)[-1])
-            #     last_key_int_incr_str = str(last_key_int + 1)
-            # else:
-            #     last_key_int_incr_str = "0"
-            #     experiment_key_dict = {"experiments": {last_key_int_incr_str: {}}}
-            #     pipeline_data["classifier"][model_name].update(experiment_key_dict)
-
-            # outter_dict = {last_key_int_incr_str: experiment_dict}
-            # pipeline_data["classifier"][model_name]["experiments"].update(outter_dict)
-
-            if jsonFile.check_key_pipeline_json("experiments"):
-                keys = jsonFile.read_pipline_json(
-                    ["classifier", model_name, "experiments"]
-                ).keys()
-                last_key_int = int(list(keys)[-1])
-                last_key_int_incr_str = str(last_key_int + 1)
-            else:
-                last_key_int_incr_str = "0"
-                experiment_key_dict = {"experiments": {last_key_int_incr_str: {}}}
-                jsonFile.update_pipeline_json(
-                    ["classifier", model_name], experiment_key_dict
-                )
-
-            outter_dict = {last_key_int_incr_str: experiment_dict}
-            jsonFile.update_pipeline_json(
-                ["classifier", model_name, "experiments"], outter_dict
-            )
-
-            if autoencoder == "Yes":
-                autoencoder = joblib.load(model_name_path + "/autoencoder.sav")
-            else:
-                autoencoder = None
-
-            gc_compute_counterfactuals(
-                model_name_path,
-                model_name_path_constraint,
-                constraint_type,
-                [0.0001],
-                float(w_value),
-                0.5,
-                classifier,
-                autoencoder,
-            )
-            path = model_name_path_constraint
-            context = {"experiment_dict": experiment_dict}
-    elif action == "class_label_selection":
-
-        df_name = request.session.get("df_name")
-
-        if df_name == "upload":
-            df_name = request.session["df_name_upload_base_name"]
-
-        datasets_types_pipeline_json_path = os.path.join(
-            PIPELINE_PATH + "/dataset_types_pipeline.json"
-        )
-
-        dataset_type_json = pipeline.pipeline_json(datasets_types_pipeline_json_path)
-
-        dataset_type = dataset_type_json.read_pipline_json([df_name])
-        # preprocessed_path
-        excel_file_name_preprocessed_path = os.path.join(
-            PIPELINE_PATH + f"{df_name}" + "/" + df_name + "_preprocessed" + ".csv"
-        )
-
-        excel_file_name_path = os.path.join(
-            PIPELINE_PATH + f"{df_name}" + "/" + df_name + ".csv"
-        )
-
-        # which model is being used during that session
-        model_name = request.POST.get("model_name")
-
-        model_name_path = os.path.join(
-            PIPELINE_PATH + f"{df_name}" + "/trained_models/" + model_name
-        )
-
-        X_test_path = os.path.join(
-            PIPELINE_PATH
-            + f"{df_name}"
-            + "/trained_models"
-            + f"/{model_name}"
-            + "/X_test.csv"
-        )
-        y_test_path = os.path.join(
-            PIPELINE_PATH
-            + f"{df_name}"
-            + "/trained_models"
-            + f"/{model_name}"
-            + "/y_test.npy"
-        )
-
-        X_test = pd.read_csv(X_test_path)
-        y_test = np.load(y_test_path)
-
-        if model_name != "glacier":
-            scaler = joblib.load(model_name_path + "/min_max_scaler.sav")
-            X_test = pd.DataFrame(scaler.inverse_transform(X_test))
-
-        if dataset_type == "timeseries":
-            class_label = request.POST.get("class_label")
-            cfrow_id = request.POST.get("cfrow_id")
-
-            class_label = (
-                int(class_label)
-                if class_label.isdigit()
-                else (
-                    float(class_label)
-                    if class_label.replace(".", "", 1).isdigit()
-                    else class_label
-                )
-            )
-
-            fig, index = methods.get_ecg_entry(
-                X_test, y_test, int(cfrow_id), class_label
-            )
-            request.session["cfrow_id"] = index
-            request.session["class_label"] = class_label
-            context = {"fig": fig.to_html(), "dataset_type": dataset_type}
-    elif action == "dataset_charts":
-        df_name = request.POST.get("df_name")
-        request.session["df_name"] = df_name
-        context = {}
-    elif action == "timeseries-dataset":
-
-        # action to add dataset when from radio button click
-        name = request.POST.get("timeseries_dataset")
-
-        # add name of used dataframe in session for future use
-        request.session["df_name"] = name
-        excel_file_name_path = os.path.join(
-            PIPELINE_PATH + f"{name}" + "/" + name + ".csv",
-        )
-        datasets_types_pipeline_json_path = os.path.join(
-            PIPELINE_PATH + "/dataset_types_pipeline.json"
-        )
-        datasets_types_pipeline_json = pipeline.pipeline_json(
-            datasets_types_pipeline_json_path
-        )
-        if os.path.exists(excel_file_name_path):
-
-            dataset_type = datasets_types_pipeline_json.read_pipline_json([name])
-
-            df = methods.get_dataframe(excel_file_name_path)
-            df.columns = df.columns.str.replace(" ", "_")
-            request.session["excel_file_name"] = excel_file_name_path
-
-            # find the available pre trained datasets
-            # check the pipeline file
-            json_path = os.path.join(PIPELINE_PATH, f"{name}" + "/pipeline.json")
-            jsonFile = pipeline.pipeline_json(json_path)
-
-            preprocessing_info = {"name": name}
-            dataset_camel = methods.convert_to_camel_case(name)
-            if "Ecg" in dataset_camel:
-                dataset_camel = dataset_camel.replace("Ecg", "ECG")
-            experiment = methods.fetch_line_by_dataset(
-                PIPELINE_PATH + "/glacier_experiments.txt",
-                dataset_camel,
-            )
-            if experiment is not None:
-                stripped_arguments = methods.extract_arguments_from_line(experiment)
-            indices_to_keys = {
-                1: "pos",
-                2: "neg",
-            }
-
-            # Create a dictionary by fetching items from the list at the specified indices
-            inner_dict = {
-                key: stripped_arguments[index] for index, key in indices_to_keys.items()
-            }
-            preprocessing_info.update(inner_dict)
-            jsonFile.append_pipeline_json(preprocessing_info)
-
-            pos = inner_dict["pos"]
-            neg = inner_dict["neg"]
-            fig, fig1 = methods.stats(
-                excel_file_name_path, dataset_type, int(pos), int(neg), name=name
-            )
-            # timeseries
-            request.session["fig"] = fig
-            request.session["fig1"] = fig1
-            context = {"fig": fig, "fig1": fig1, "dataset_type": dataset_type}
-        else:
-            context = {}
-
-    return HttpResponse(json.dumps(context))