Team Ai
Apppublic

hetvi22/commit_message_quality

sourceHugging Faceupdated 1y agoView on Hugging Face
0likes
implementation.ipynb1311 linesDownload Raw Back to root
1{2  "nbformat": 4,3  "nbformat_minor": 0,4  "metadata": {5    "colab": {6      "provenance": []7    },8    "kernelspec": {9      "name": "python3",10      "display_name": "Python 3"11    },12    "language_info": {13      "name": "python"14    }15  },16  "cells": [17    {18      "cell_type": "markdown",19      "source": [20        "# **COMMIT MESSAGE QUALITY ANALYZER**\n",21        "## **Domain: Machine Learning and Software Engineering**\n",22        "\n",23        "**Year - 3rd** **|** **Div - A**  **|**  **Batch - A1**\n",24        "\n",25        "**Group Members:**   \n",26        "**230090107043 - Hetvi Doshi**   \n",27        "**230090107241 - Shreya Wani**     \n",28        "                   **240093107004 - Bhavini Badgujar**     \n",29        "                   **230090107081 - Himanshu Mali**   \n",30        "                   **230090107175 - Prakhar Sinha**   \n",31        "                   **230090107111 - Devansh Parekh**"32      ],33      "metadata": {34        "id": "a8t7OKyDuvUO"35      }36    },37    {38      "cell_type": "markdown",39      "source": [40        "## **IMPORTING LIBRARIES**"41      ],42      "metadata": {43        "id": "eH7yqekqK41q"44      }45    },46    {47      "cell_type": "code",48      "execution_count": 1,49      "metadata": {50        "colab": {51          "base_uri": "https://localhost:8080/"52        },53        "id": "FLQrDqkPuqws",54        "outputId": "6dc9a17f-e649-42ec-b80d-255067fba9d5"55      },56      "outputs": [57        {58          "output_type": "execute_result",59          "data": {60            "text/plain": [61              "0"62            ]63          },64          "metadata": {},65          "execution_count": 166        }67      ],68      "source": [69        "import re\n",70        "import pandas as pd\n",71        "from sklearn.model_selection import train_test_split\n",72        "from sklearn.feature_extraction.text import TfidfVectorizer\n",73        "from sklearn.naive_bayes import MultinomialNB\n",74        "from sklearn.pipeline import Pipeline\n",75        "from sklearn.metrics import classification_report, confusion_matrix, accuracy_score\n",76        "import matplotlib.pyplot as plt\n",77        "import seaborn as sns\n",78        "\n",79        "import random\n",80        "random.seed(42)\n",81        "\n",82        "import gc\n",83        "gc.collect()"84      ]85    },86    {87      "cell_type": "markdown",88      "source": [89        "## **DATA COLLECTION**"90      ],91      "metadata": {92        "id": "CnQ8vFEfK_qG"93      }94    },95    {96      "cell_type": "code",97      "source": [98        "data = [\n",99        "    (\"Refactor user authentication module for better maintainability\", \"high\"),\n",100        "    (\"Fix memory leak in image processing pipeline\", \"high\"),\n",101        "    (\"Improve API response time by implementing caching\", \"high\"),\n",102        "    (\"Add unit tests for payment gateway integration\", \"high\"),\n",103        "    (\"Optimize database queries to reduce page load time\", \"high\"),\n",104        "    (\"Implement role-based access control for admin panel\", \"high\"),\n",105        "    (\"Fix critical security vulnerability in login endpoint\", \"high\"),\n",106        "    (\"Improve error handling in file upload service\", \"high\"),\n",107        "    (\"Add logging for debugging production issues\", \"high\"),\n",108        "    (\"Refactor legacy code in dashboard module\", \"high\"),\n",109        "    (\"Implement rate limiting to prevent abuse\", \"high\"),\n",110        "    (\"Add input validation for user registration form\", \"high\"),\n",111        "    (\"Fix race condition in async task queue\", \"high\"),\n",112        "    (\"Improve documentation for API endpoints\", \"high\"),\n",113        "    (\"Add support for multi-language UI\", \"high\"),\n",114        "    (\"Fix broken link in footer navigation\", \"high\"),\n",115        "    (\"Improve accessibility for screen readers\", \"high\"),\n",116        "    (\"Add dark mode toggle in user settings\", \"high\"),\n",117        "    (\"Fix timezone handling in event scheduler\", \"high\"),\n",118        "    (\"Refactor email notification system\", \"high\"),\n",119        "    (\"Add analytics tracking for user engagement\", \"high\"),\n",120        "    (\"Fix CORS policy for frontend-backend communication\", \"high\"),\n",121        "    (\"Improve password strength requirements\", \"high\"),\n",122        "    (\"Add backup system for user data\", \"high\"),\n",123        "    (\"Fix alignment issue in mobile view\", \"high\"),\n",124        "    (\"Implement lazy loading for images\", \"high\"),\n",125        "    (\"Add search functionality to user dashboard\", \"high\"),\n",126        "    (\"Fix broken API endpoint for user profile\", \"high\"),\n",127        "    (\"Improve SEO meta tags for marketing pages\", \"high\"),\n",128        "    (\"Add social media sharing buttons\", \"high\"),\n",129        "    (\"Fix broken form validation on checkout page\", \"high\"),\n",130        "    (\"Improve performance of search algorithm\", \"high\"),\n",131        "    (\"Add pagination to user list view\", \"high\"),\n",132        "    (\"Fix broken redirect after login\", \"high\"),\n",133        "    (\"Improve UX for password reset flow\", \"high\"),\n",134        "    (\"Add tooltips for complex UI elements\", \"high\"),\n",135        "    (\"Fix broken image paths in documentation\", \"high\"),\n",136        "    (\"Improve loading spinner visibility\", \"high\"),\n",137        "    (\"Add confirmation dialog before delete action\", \"high\"),\n",138        "    (\"Fix broken sorting in data table\", \"high\"),\n",139        "    (\"Improve contrast for better readability\", \"high\"),\n",140        "    (\"Add keyboard shortcuts for power users\", \"high\"),\n",141        "    (\"Fix broken export to CSV feature\", \"high\"),\n",142        "    (\"Improve onboarding tutorial for new users\", \"high\"),\n",143        "    (\"Add support for RTL languages\", \"high\"),\n",144        "    (\"Fix broken drag-and-drop functionality\", \"high\"),\n",145        "    (\"Improve error messages for form validation\", \"high\"),\n",146        "    (\"Add auto-save feature for draft content\", \"high\"),\n",147        "    (\"Fix broken print stylesheet\", \"high\"),\n",148        "    (\"Update user profile page styles\", \"high\"),\n",149        "    (\"Fix login bug for edge case\", \"high\"),\n",150        "    (\"Refactor config loader for scalability\", \"high\"),\n",151        "    (\"Add health check endpoint for monitoring\", \"high\"),\n",152        "    (\"Improve test coverage for core module\", \"high\"),\n",153        "    (\"Fix data race in concurrent requests\", \"high\"),\n",154        "    (\"Add retry logic for flaky external API\", \"high\"),\n",155        "    (\"Improve startup time of application\", \"high\"),\n",156        "    (\"Fix edge case in date parsing logic\", \"high\"),\n",157        "    (\"Add audit log for sensitive operations\", \"high\"),\n",158        "    (\"Refactor state management for clarity\", \"high\"),\n",159        "    (\"Fix memory leak in WebSocket handler\", \"high\"),\n",160        "    (\"Improve handling of malformed input\", \"high\"),\n",161        "    (\"Add rate limit headers to responses\", \"high\"),\n",162        "    (\"Fix bug in CSV export formatting\", \"high\"),\n",163        "    (\"Improve resilience to network failures\", \"high\"),\n",164        "    (\"Add support for custom themes\", \"high\"),\n",165        "    (\"Fix bug in notification delivery\", \"high\"),\n",166        "    (\"Refactor API client for better error handling\", \"high\"),\n",167        "    (\"Improve performance of dashboard rendering\", \"high\"),\n",168        "    (\"Add validation for file uploads\", \"high\"),\n",169        "    (\"Fix bug in user role assignment\", \"high\"),\n",170        "    (\"Improve handling of large datasets\", \"high\"),\n",171        "    (\"Add support for custom domains\", \"high\"),\n",172        "    (\"Fix bug in session timeout logic\", \"high\"),\n",173        "    (\"Refactor logging system for structured output\", \"high\"),\n",174        "    (\"Improve reliability of background jobs\", \"high\"),\n",175        "    (\"Add support for OAuth2 providers\", \"high\"),\n",176        "    (\"Fix bug in password reset token generation\", \"high\"),\n",177        "    (\"Improve scalability of message queue\", \"high\"),\n",178        "    (\"fix bug\", \"low\"),\n",179        "    (\"update code\", \"low\"),\n",180        "    (\"change stuff\", \"low\"),\n",181        "    (\"work on it\", \"low\"),\n",182        "    (\"fix\", \"low\"),\n",183        "    (\"update\", \"low\"),\n",184        "    (\"changed things\", \"low\"),\n",185        "    (\"did stuff\", \"low\"),\n",186        "    (\"fix issue\", \"low\"),\n",187        "    (\"tweak\", \"low\"),\n",188        "    (\"adjust\", \"low\"),\n",189        "    (\"minor change\", \"low\"),\n",190        "    (\"small fix\", \"low\"),\n",191        "    (\"update file\", \"low\"),\n",192        "    (\"change code\", \"low\"),\n",193        "    (\"fix typo\", \"low\"),\n",194        "    (\"update config\", \"low\"),\n",195        "    (\"change settings\", \"low\"),\n",196        "    (\"work\", \"low\"),\n",197        "    (\"stuff\", \"low\"),\n",198        "    (\"whatever\", \"low\"),\n",199        "    (\"idk\", \"low\"),\n",200        "    (\"test\", \"low\"),\n",201        "    (\"try\", \"low\"),\n",202        "    (\"oops\", \"low\"),\n",203        "    (\"again\", \"low\"),\n",204        "    (\"help\", \"low\"),\n",205        "    (\"broken\", \"low\"),\n",206        "    (\"not working\", \"low\"),\n",207        "    (\"why\", \"low\"),\n",208        "    (\"debug\", \"low\"),\n",209        "    (\"temp\", \"low\"),\n",210        "    (\"quick fix\", \"low\"),\n",211        "    (\"hack\", \"low\"),\n",212        "    (\"patch\", \"low\"),\n",213        "    (\"dirty fix\", \"low\"),\n",214        "    (\"ugly code\", \"low\"),\n",215        "    (\"sorry\", \"low\"),\n",216        "    (\"later\", \"low\"),\n",217        "    (\"todo\", \"low\"),\n",218        "    (\"wip\", \"low\"),\n",219        "    (\"experimental\", \"low\"),\n",220        "    (\"prototype\", \"low\"),\n",221        "    (\"draft\", \"low\"),\n",222        "    (\"backup\", \"low\"),\n",223        "    (\"old\", \"low\"),\n",224        "    (\"new\", \"low\"),\n",225        "    (\"version\", \"low\"),\n",226        "    (\"fixed\", \"low\"),\n",227        "    (\"updated\", \"low\"),\n",228        "    (\"changes\", \"low\"),\n",229        "    (\"did it\", \"low\"),\n",230        "    (\"made it work\", \"low\"),\n",231        "    (\"sort of works\", \"low\"),\n",232        "    (\"kinda fixed\", \"low\"),\n",233        "    (\"not sure\", \"low\"),\n",234        "    (\"might be broken\", \"low\"),\n",235        "    (\"works on my machine\", \"low\")\n",236        "]\n",237        "\n",238        "df = pd.DataFrame(data, columns=['commit_message', 'quality_label'])\n",239        "print(\"Dataset created with\", len(df), \"samples\")\n",240        "df.head(10)"241      ],242      "metadata": {243        "colab": {244          "base_uri": "https://localhost:8080/",245          "height": 380246        },247        "id": "WxcueMgVgRMB",248        "outputId": "e21916c2-dc29-4edb-a254-c6867a5a42e4"249      },250      "execution_count": 2,251      "outputs": [252        {253          "output_type": "stream",254          "name": "stdout",255          "text": [256            "Dataset created with 137 samples\n"257          ]258        },259        {260          "output_type": "execute_result",261          "data": {262            "text/plain": [263              "                                      commit_message quality_label\n",264              "0  Refactor user authentication module for better...          high\n",265              "1       Fix memory leak in image processing pipeline          high\n",266              "2  Improve API response time by implementing caching          high\n",267              "3     Add unit tests for payment gateway integration          high\n",268              "4  Optimize database queries to reduce page load ...          high\n",269              "5  Implement role-based access control for admin ...          high\n",270              "6  Fix critical security vulnerability in login e...          high\n",271              "7      Improve error handling in file upload service          high\n",272              "8        Add logging for debugging production issues          high\n",273              "9           Refactor legacy code in dashboard module          high"274            ],275            "text/html": [276              "\n",277              "  <div id=\"df-a2ccfbbf-42c6-47d8-b541-d6b7716eb81f\" class=\"colab-df-container\">\n",278              "    <div>\n",279              "<style scoped>\n",280              "    .dataframe tbody tr th:only-of-type {\n",281              "        vertical-align: middle;\n",282              "    }\n",283              "\n",284              "    .dataframe tbody tr th {\n",285              "        vertical-align: top;\n",286              "    }\n",287              "\n",288              "    .dataframe thead th {\n",289              "        text-align: right;\n",290              "    }\n",291              "</style>\n",292              "<table border=\"1\" class=\"dataframe\">\n",293              "  <thead>\n",294              "    <tr style=\"text-align: right;\">\n",295              "      <th></th>\n",296              "      <th>commit_message</th>\n",297              "      <th>quality_label</th>\n",298              "    </tr>\n",299              "  </thead>\n",300              "  <tbody>\n",301              "    <tr>\n",302              "      <th>0</th>\n",303              "      <td>Refactor user authentication module for better...</td>\n",304              "      <td>high</td>\n",305              "    </tr>\n",306              "    <tr>\n",307              "      <th>1</th>\n",308              "      <td>Fix memory leak in image processing pipeline</td>\n",309              "      <td>high</td>\n",310              "    </tr>\n",311              "    <tr>\n",312              "      <th>2</th>\n",313              "      <td>Improve API response time by implementing caching</td>\n",314              "      <td>high</td>\n",315              "    </tr>\n",316              "    <tr>\n",317              "      <th>3</th>\n",318              "      <td>Add unit tests for payment gateway integration</td>\n",319              "      <td>high</td>\n",320              "    </tr>\n",321              "    <tr>\n",322              "      <th>4</th>\n",323              "      <td>Optimize database queries to reduce page load ...</td>\n",324              "      <td>high</td>\n",325              "    </tr>\n",326              "    <tr>\n",327              "      <th>5</th>\n",328              "      <td>Implement role-based access control for admin ...</td>\n",329              "      <td>high</td>\n",330              "    </tr>\n",331              "    <tr>\n",332              "      <th>6</th>\n",333              "      <td>Fix critical security vulnerability in login e...</td>\n",334              "      <td>high</td>\n",335              "    </tr>\n",336              "    <tr>\n",337              "      <th>7</th>\n",338              "      <td>Improve error handling in file upload service</td>\n",339              "      <td>high</td>\n",340              "    </tr>\n",341              "    <tr>\n",342              "      <th>8</th>\n",343              "      <td>Add logging for debugging production issues</td>\n",344              "      <td>high</td>\n",345              "    </tr>\n",346              "    <tr>\n",347              "      <th>9</th>\n",348              "      <td>Refactor legacy code in dashboard module</td>\n",349              "      <td>high</td>\n",350              "    </tr>\n",351              "  </tbody>\n",352              "</table>\n",353              "</div>\n",354              "    <div class=\"colab-df-buttons\">\n",355              "\n",356              "  <div class=\"colab-df-container\">\n",357              "    <button class=\"colab-df-convert\" onclick=\"convertToInteractive('df-a2ccfbbf-42c6-47d8-b541-d6b7716eb81f')\"\n",358              "            title=\"Convert this dataframe to an interactive table.\"\n",359              "            style=\"display:none;\">\n",360              "\n",361              "  <svg xmlns=\"http://www.w3.org/2000/svg\" height=\"24px\" viewBox=\"0 -960 960 960\">\n",362              "    <path d=\"M120-120v-720h720v720H120Zm60-500h600v-160H180v160Zm220 220h160v-160H400v160Zm0 220h160v-160H400v160ZM180-400h160v-160H180v160Zm440 0h160v-160H620v160ZM180-180h160v-160H180v160Zm440 0h160v-160H620v160Z\"/>\n",363              "  </svg>\n",364              "    </button>\n",365              "\n",366              "  <style>\n",367              "    .colab-df-container {\n",368              "      display:flex;\n",369              "      gap: 12px;\n",370              "    }\n",371              "\n",372              "    .colab-df-convert {\n",373              "      background-color: #E8F0FE;\n",374              "      border: none;\n",375              "      border-radius: 50%;\n",376              "      cursor: pointer;\n",377              "      display: none;\n",378              "      fill: #1967D2;\n",379              "      height: 32px;\n",380              "      padding: 0 0 0 0;\n",381              "      width: 32px;\n",382              "    }\n",383              "\n",384              "    .colab-df-convert:hover {\n",385              "      background-color: #E2EBFA;\n",386              "      box-shadow: 0px 1px 2px rgba(60, 64, 67, 0.3), 0px 1px 3px 1px rgba(60, 64, 67, 0.15);\n",387              "      fill: #174EA6;\n",388              "    }\n",389              "\n",390              "    .colab-df-buttons div {\n",391              "      margin-bottom: 4px;\n",392              "    }\n",393              "\n",394              "    [theme=dark] .colab-df-convert {\n",395              "      background-color: #3B4455;\n",396              "      fill: #D2E3FC;\n",397              "    }\n",398              "\n",399              "    [theme=dark] .colab-df-convert:hover {\n",400              "      background-color: #434B5C;\n",401              "      box-shadow: 0px 1px 3px 1px rgba(0, 0, 0, 0.15);\n",402              "      filter: drop-shadow(0px 1px 2px rgba(0, 0, 0, 0.3));\n",403              "      fill: #FFFFFF;\n",404              "    }\n",405              "  </style>\n",406              "\n",407              "    <script>\n",408              "      const buttonEl =\n",409              "        document.querySelector('#df-a2ccfbbf-42c6-47d8-b541-d6b7716eb81f button.colab-df-convert');\n",410              "      buttonEl.style.display =\n",411              "        google.colab.kernel.accessAllowed ? 'block' : 'none';\n",412              "\n",413              "      async function convertToInteractive(key) {\n",414              "        const element = document.querySelector('#df-a2ccfbbf-42c6-47d8-b541-d6b7716eb81f');\n",415              "        const dataTable =\n",416              "          await google.colab.kernel.invokeFunction('convertToInteractive',\n",417              "                                                    [key], {});\n",418              "        if (!dataTable) return;\n",419              "\n",420              "        const docLinkHtml = 'Like what you see? Visit the ' +\n",421              "          '<a target=\"_blank\" href=https://colab.research.google.com/notebooks/data_table.ipynb>data table notebook</a>'\n",422              "          + ' to learn more about interactive tables.';\n",423              "        element.innerHTML = '';\n",424              "        dataTable['output_type'] = 'display_data';\n",425              "        await google.colab.output.renderOutput(dataTable, element);\n",426              "        const docLink = document.createElement('div');\n",427              "        docLink.innerHTML = docLinkHtml;\n",428              "        element.appendChild(docLink);\n",429              "      }\n",430              "    </script>\n",431              "  </div>\n",432              "\n",433              "\n",434              "    <div id=\"df-f311969b-713e-4580-bfd5-d6d05bebca53\">\n",435              "      <button class=\"colab-df-quickchart\" onclick=\"quickchart('df-f311969b-713e-4580-bfd5-d6d05bebca53')\"\n",436              "                title=\"Suggest charts\"\n",437              "                style=\"display:none;\">\n",438              "\n",439              "<svg xmlns=\"http://www.w3.org/2000/svg\" height=\"24px\"viewBox=\"0 0 24 24\"\n",440              "     width=\"24px\">\n",441              "    <g>\n",442              "        <path d=\"M19 3H5c-1.1 0-2 .9-2 2v14c0 1.1.9 2 2 2h14c1.1 0 2-.9 2-2V5c0-1.1-.9-2-2-2zM9 17H7v-7h2v7zm4 0h-2V7h2v10zm4 0h-2v-4h2v4z\"/>\n",443              "    </g>\n",444              "</svg>\n",445              "      </button>\n",446              "\n",447              "<style>\n",448              "  .colab-df-quickchart {\n",449              "      --bg-color: #E8F0FE;\n",450              "      --fill-color: #1967D2;\n",451              "      --hover-bg-color: #E2EBFA;\n",452              "      --hover-fill-color: #174EA6;\n",453              "      --disabled-fill-color: #AAA;\n",454              "      --disabled-bg-color: #DDD;\n",455              "  }\n",456              "\n",457              "  [theme=dark] .colab-df-quickchart {\n",458              "      --bg-color: #3B4455;\n",459              "      --fill-color: #D2E3FC;\n",460              "      --hover-bg-color: #434B5C;\n",461              "      --hover-fill-color: #FFFFFF;\n",462              "      --disabled-bg-color: #3B4455;\n",463              "      --disabled-fill-color: #666;\n",464              "  }\n",465              "\n",466              "  .colab-df-quickchart {\n",467              "    background-color: var(--bg-color);\n",468              "    border: none;\n",469              "    border-radius: 50%;\n",470              "    cursor: pointer;\n",471              "    display: none;\n",472              "    fill: var(--fill-color);\n",473              "    height: 32px;\n",474              "    padding: 0;\n",475              "    width: 32px;\n",476              "  }\n",477              "\n",478              "  .colab-df-quickchart:hover {\n",479              "    background-color: var(--hover-bg-color);\n",480              "    box-shadow: 0 1px 2px rgba(60, 64, 67, 0.3), 0 1px 3px 1px rgba(60, 64, 67, 0.15);\n",481              "    fill: var(--button-hover-fill-color);\n",482              "  }\n",483              "\n",484              "  .colab-df-quickchart-complete:disabled,\n",485              "  .colab-df-quickchart-complete:disabled:hover {\n",486              "    background-color: var(--disabled-bg-color);\n",487              "    fill: var(--disabled-fill-color);\n",488              "    box-shadow: none;\n",489              "  }\n",490              "\n",491              "  .colab-df-spinner {\n",492              "    border: 2px solid var(--fill-color);\n",493              "    border-color: transparent;\n",494              "    border-bottom-color: var(--fill-color);\n",495              "    animation:\n",496              "      spin 1s steps(1) infinite;\n",497              "  }\n",498              "\n",499              "  @keyframes spin {\n",500              "    0% {\n",501              "      border-color: transparent;\n",502              "      border-bottom-color: var(--fill-color);\n",503              "      border-left-color: var(--fill-color);\n",504              "    }\n",505              "    20% {\n",506              "      border-color: transparent;\n",507              "      border-left-color: var(--fill-color);\n",508              "      border-top-color: var(--fill-color);\n",509              "    }\n",510              "    30% {\n",511              "      border-color: transparent;\n",512              "      border-left-color: var(--fill-color);\n",513              "      border-top-color: var(--fill-color);\n",514              "      border-right-color: var(--fill-color);\n",515              "    }\n",516              "    40% {\n",517              "      border-color: transparent;\n",518              "      border-right-color: var(--fill-color);\n",519              "      border-top-color: var(--fill-color);\n",520              "    }\n",521              "    60% {\n",522              "      border-color: transparent;\n",523              "      border-right-color: var(--fill-color);\n",524              "    }\n",525              "    80% {\n",526              "      border-color: transparent;\n",527              "      border-right-color: var(--fill-color);\n",528              "      border-bottom-color: var(--fill-color);\n",529              "    }\n",530              "    90% {\n",531              "      border-color: transparent;\n",532              "      border-bottom-color: var(--fill-color);\n",533              "    }\n",534              "  }\n",535              "</style>\n",536              "\n",537              "      <script>\n",538              "        async function quickchart(key) {\n",539              "          const quickchartButtonEl =\n",540              "            document.querySelector('#' + key + ' button');\n",541              "          quickchartButtonEl.disabled = true;  // To prevent multiple clicks.\n",542              "          quickchartButtonEl.classList.add('colab-df-spinner');\n",543              "          try {\n",544              "            const charts = await google.colab.kernel.invokeFunction(\n",545              "                'suggestCharts', [key], {});\n",546              "          } catch (error) {\n",547              "            console.error('Error during call to suggestCharts:', error);\n",548              "          }\n",549              "          quickchartButtonEl.classList.remove('colab-df-spinner');\n",550              "          quickchartButtonEl.classList.add('colab-df-quickchart-complete');\n",551              "        }\n",552              "        (() => {\n",553              "          let quickchartButtonEl =\n",554              "            document.querySelector('#df-f311969b-713e-4580-bfd5-d6d05bebca53 button');\n",555              "          quickchartButtonEl.style.display =\n",556              "            google.colab.kernel.accessAllowed ? 'block' : 'none';\n",557              "        })();\n",558              "      </script>\n",559              "    </div>\n",560              "\n",561              "    </div>\n",562              "  </div>\n"563            ],564            "application/vnd.google.colaboratory.intrinsic+json": {565              "type": "dataframe",566              "variable_name": "df",567              "summary": "{\n  \"name\": \"df\",\n  \"rows\": 137,\n  \"fields\": [\n    {\n      \"column\": \"commit_message\",\n      \"properties\": {\n        \"dtype\": \"string\",\n        \"num_unique_values\": 137,\n        \"samples\": [\n          \"help\",\n          \"again\",\n          \"Fix race condition in async task queue\"\n        ],\n        \"semantic_type\": \"\",\n        \"description\": \"\"\n      }\n    },\n    {\n      \"column\": \"quality_label\",\n      \"properties\": {\n        \"dtype\": \"category\",\n        \"num_unique_values\": 2,\n        \"samples\": [\n          \"low\",\n          \"high\"\n        ],\n        \"semantic_type\": \"\",\n        \"description\": \"\"\n      }\n    }\n  ]\n}"568            }569          },570          "metadata": {},571          "execution_count": 2572        }573      ]574    },575    {576      "cell_type": "markdown",577      "source": [578        "## **DATA PREPROCESSING AND VISUALIZATION**"579      ],580      "metadata": {581        "id": "KmLqSuHILOnC"582      }583    },584    {585      "cell_type": "code",586      "source": [587        "print(\"Label Distribution:\")\n",588        "df['quality_label'].value_counts()\n",589        "\n",590        "plt.figure(figsize=(6,4))\n",591        "sns.countplot(data=df, x='quality_label',hue='quality_label', palette='Set2')\n",592        "plt.title(\"Distribution of Commit Message Quality Labels\")\n",593        "plt.xlabel(\"Quality Label\")\n",594        "plt.ylabel(\"Count\")\n",595        "plt.show()"596      ],597      "metadata": {598        "colab": {599          "base_uri": "https://localhost:8080/",600          "height": 427601        },602        "id": "I1T9jb0dKVs-",603        "outputId": "afe0f2e9-401e-433c-8034-02445a9bc928"604      },605      "execution_count": 3,606      "outputs": [607        {608          "output_type": "stream",609          "name": "stdout",610          "text": [611            "Label Distribution:\n"612          ]613        },614        {615          "output_type": "display_data",616          "data": {617            "text/plain": [618              "<Figure size 600x400 with 1 Axes>"619            ],620            "image/png": "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RowYUeo2v//+O7p37w4PDw9ERERAqVTi8uXLOHr0KADAzc0NERERmD59OkaOHIl27doBAFq3bi31cefOHQQEBKBfv3547733YGNj88y65s6dC4VCgSlTpuDWrVtYsmQJ/Pz8kJycLI2glEd5anuaEALvvPMODh48iGHDhsHT0xN79uzBhx9+iOvXr5f4y/7IkSP47rvv8P7778PMzAzLli1DUFAQUlNTYWVlVWZdjx8/ho+PDy5fvoyxY8fCxcUFMTExCA4ORmZmJiZMmAA3Nzd89dVXCAsLg729PSZNmgQAsLa2LrXP3bt348mTJ8+dU1Hk999/R7t27WBubo7JkydDX18fa9asgY+PD+Lj4zX+CgWAcePGQa1WY9asWUhMTMTatWthYWGBY8eOwdHREZ9++il++uknfP7553jttdcwePBgjftv2bIFeXl5GDduHO7evYsFCxagT58+8PX1xaFDhzBlyhRcvnwZy5cvxwcffIAvv/yy1Lor+po+zdnZGd7e3vj6668REBAgPW9ZWVno168fli1bVuI+o0aNwoYNGxASEoLx48fjypUrWLFiBU6fPo2jR49CX18ft27dQpcuXWBtbY2PPvoIFhYWuHr1Kr777jupn3379qF///7o1KkTPvvsMwDA+fPncfToUUyYMAEA8Oeff2L79u3o3bs3XFxckJGRgTVr1qBDhw44d+4c7OzsAAAPHz6Er68vbt68iQkTJkCtViM6OhoHDx4sUf+BAwcQEBAALy8vzJgxAzo6OoiKioKvry9+/vln/Otf/yrz+dq1axcAlHgti6hUKvTo0QMbN27EH3/8gYYNGz73NXhaTEwMHj16hNGjR8PKygq//PILli9fjr/++gsxMTHl7qd9+/YYP348li1bho8//hhubm4A/nmvDBo0CJs2bcKePXs05sOkp6fjwIED5Tp8+DwnTpzAsWPH0K9fP9jb2+Pq1atYtWoVfHx8cO7cORgbG2tsP3bsWFhYWGDmzJlISUnBqlWrcO3aNWkCOgB89dVXGDJkCPz9/fHZZ5/h0aNHWLVqFdq2bYvTp0+XeSjned/XtZq208yr7HkjE0IIoVKpRPPmzaXbxZPu4sWLBQBx+/btMvs4ceJEmX8ddujQQQAQq1evLnVdaSMT9evXF9nZ2VL7t99+KwCIpUuXSm3lGZl4Xm3FRya2b98uAIg5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mZkIDg4GAKSnp8PAwAAWFhYa29nY2CA9Pb3MfubNmweVSiUtDg4O1Vg1ERER1ZgwsX79egQEBMDOzk5WP+Hh4cjKypKWtLS0KqqQiIiISqPVORNFrl27hv379+O7776T2tRqNfLy8pCZmakxOpGRkQG1Wl1mX0qlEkqlsjrLJSIioqfUiJGJqKgo1KtXD926dZPavLy8oK+vj7i4OKktJSUFqamp8Pb21kaZREREVAqtj0wUFhYiKioKQ4YMgZ7e/y9HpVJh2LBhmDhxIiwtLWFubo5x48bB29ubZ3IQERHVIFoPE/v370dqaiqGDh1aYt3ixYuho6ODoKAg5Obmwt/fHytXrtRClURERFQWrYeJLl26QAhR6jpDQ0NERkYiMjLyBVdFRERE5VUj5kwQERFR7cUwQURERLIwTBAREZEsDBNEREQkC8MEERERycIwQURERLIwTBAREZEsDBNEREQkC8MEERERycIwQURERLIwTBAREZEsDBNEREQkC8MEERERycIwQURERLIwTBAREZEsDBNEREQkC8MEERERycIwQURERLIwTBAREZEsDBNEREQkC8MEERERycIwQURERLIwTBAREZEsDBNEREQkC8MEERERycIwQURERLJoPUxcv34d7733HqysrGBkZITXX38dJ0+elNYLITB9+nTY2trCyMgIfn5+uHTpkhYrJiIioqdpNUzcu3cPbdq0gb6+Pnbv3o1z585h4cKFqFOnjrTNggULsGzZMqxevRrHjx+HiYkJ/P39kZOTo8XKiYiIqIieNnf+2WefwcHBAVFRUVKbi4uL9G8hBJYsWYJPPvkEPXr0AABs2rQJNjY22L59O/r16/fCayYiIiJNWh2Z2LlzJ1q0aIHevXujXr16aN68OdatWyetv3LlCtLT0+Hn5ye1qVQqtGzZEgkJCaX2mZubi+zsbI2FiIiIqo9Ww8Sff/6JVatWwdXVFXv27MHo0aMxfvx4bNy4EQCQnp4OALCxsdG4n42NjbSuuHnz5kGlUkmLg4ND9T4IIiKiV5xWw0RhYSHefPNNfPrpp2jevDlGjhyJESNGYPXq1ZXuMzw8HFlZWdKSlpZWhRUTERFRcVoNE7a2tnB3d9doc3NzQ2pqKgBArVYDADIyMjS2ycjIkNYVp1QqYW5urrEQERFR9dFqmGjTpg1SUlI02i5evAgnJycA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\n"621          },622          "metadata": {}623        }624      ]625    },626    {627      "cell_type": "markdown",628      "source": [629        "## **RULE BASED APPROACH**"630      ],631      "metadata": {632        "id": "GkBGg9fPVx0w"633      }634    },635    {636      "cell_type": "code",637      "source": [638        "def rule_based_classifier(message):\n",639        "    \"\"\"\n",640        "    Simple, robust rule-based classifier from your original notebook.\n",641        "    Handles ANY input โ€” even gibberish.\n",642        "    \"\"\"\n",643        "    # Handle None or non-string input\n",644        "    if not message or not isinstance(message, str):\n",645        "        return 'low'\n",646        "\n",647        "    message_lower = message.lower().strip()\n",648        "\n",649        "    # Rule 1: Too short (less than 3 words)\n",650        "    if len(message_lower.split()) < 3:\n",651        "        return 'low'\n",652        "\n",653        "    # Rule 2: Contains vague keywords\n",654        "    vague_keywords = ['fix', 'stuff', 'update', 'change', 'work', 'tweak', 'adjust', 'whatever', 'did', 'made']\n",655        "    for kw in vague_keywords:\n",656        "        if kw in message_lower:\n",657        "            return 'low'\n",658        "\n",659        "    # Rule 3: Too generic phrases\n",660        "    if re.search(r'\\b(fix|update|change)\\s+(bug|code|stuff|things?)\\b', message_lower):\n",661        "        return 'low'\n",662        "\n",663        "    # Default: if none of the above, assume it's decent โ†’ high\n",664        "    return 'high'\n",665        "    # Apply to dataset\n",666        "df['rule_based_pred'] = df['commit_message'].apply(rule_based_classifier)\n",667        "# Evaluate\n",668        "rule_accuracy = accuracy_score(df['quality_label'], df['rule_based_pred'])\n",669        "print(f\"FIXED Rule-Based Accuracy: {rule_accuracy:.2f}\")\n",670        "print(\"\\nClassification Report:\")\n",671        "print(classification_report(df['quality_label'], df['rule_based_pred'], zero_division=0))"672      ],673      "metadata": {674        "colab": {675          "base_uri": "https://localhost:8080/"676        },677        "id": "DAlAbVqTMB7X",678        "outputId": "7f755d54-6341-4677-ac3e-cb928ad62a8f"679      },680      "execution_count": 4,681      "outputs": [682        {683          "output_type": "stream",684          "name": "stdout",685          "text": [686            "FIXED Rule-Based Accuracy: 0.80\n",687            "\n",688            "Classification Report:\n",689            "              precision    recall  f1-score   support\n",690            "\n",691            "        high       0.98      0.67      0.80        79\n",692            "         low       0.69      0.98      0.81        58\n",693            "\n",694            "    accuracy                           0.80       137\n",695            "   macro avg       0.83      0.83      0.80       137\n",696            "weighted avg       0.86      0.80      0.80       137\n",697            "\n"698          ]699        }700      ]701    },702    {703      "cell_type": "markdown",704      "source": [705        "## **MACHINE LEARNING APPROACH**"706      ],707      "metadata": {708        "id": "iq-eul--WI4F"709      }710    },711    {712      "cell_type": "code",713      "source": [714        "# Prepare data (same as before)\n",715        "df_ml = df[df['quality_label'] != 'neutral'].copy()\n",716        "X = df_ml['commit_message']\n",717        "y = df_ml['quality_label']\n",718        "\n",719        "X_train, X_test, y_train, y_test = train_test_split(\n",720        "    X, y, test_size=0.3, random_state=42, stratify=y\n",721        ")\n",722        "\n",723        "# FIXED ML MODEL โ€” Better parameters\n",724        "ml_model = Pipeline([\n",725        "    ('tfidf', TfidfVectorizer(\n",726        "        stop_words='english',\n",727        "        max_features=1000,      # More features\n",728        "        ngram_range=(1, 2),     # Use word pairs\n",729        "        lowercase=True\n",730        "    )),\n",731        "    ('classifier', MultinomialNB(alpha=0.1))  # Smoother probability\n",732        "])\n",733        "\n",734        "# Train\n",735        "ml_model.fit(X_train, y_train)\n",736        "\n",737        "# Predict on TEST SET (not full dataset!)\n",738        "y_pred_ml = ml_model.predict(X_test)\n",739        "\n",740        "# Evaluate on TEST SET\n",741        "ml_accuracy = accuracy_score(y_test, y_pred_ml)\n",742        "print(f\"FIXED ML Model Accuracy (Test Set): {ml_accuracy:.2f}\")\n",743        "print(\"\\nClassification Report (Test Set):\")\n",744        "print(classification_report(y_test, y_pred_ml))\n",745        "\n",746        "# Confusion Matrix\n",747        "cm = confusion_matrix(y_test, y_pred_ml)\n",748        "plt.figure(figsize=(5,4))\n",749        "sns.heatmap(cm, annot=True, fmt='d', cmap='Blues', xticklabels=['high','low'], yticklabels=['high','low'])\n",750        "plt.title('Confusion Matrix (ML Model)')\n",751        "plt.ylabel('Actual')\n",752        "plt.xlabel('Predicted')\n",753        "plt.show()"754      ],755      "metadata": {756        "colab": {757          "base_uri": "https://localhost:8080/",758          "height": 618759        },760        "id": "YSgmKAy5Q1E2",761        "outputId": "b0aa7706-0b6e-4233-8732-0fd36855c5e7"762      },763      "execution_count": 5,764      "outputs": [765        {766          "output_type": "stream",767          "name": "stdout",768          "text": [769            "FIXED ML Model Accuracy (Test Set): 0.64\n",770            "\n",771            "Classification Report (Test Set):\n",772            "              precision    recall  f1-score   support\n",773            "\n",774            "        high       0.65      0.83      0.73        24\n",775            "         low       0.64      0.39      0.48        18\n",776            "\n",777            "    accuracy                           0.64        42\n",778            "   macro avg       0.64      0.61      0.61        42\n",779            "weighted avg       0.64      0.64      0.62        42\n",780            "\n"781          ]782        },783        {784          "output_type": "display_data",785          "data": {786            "text/plain": [787              "<Figure size 500x400 with 2 Axes>"788            ],789            "image/png": "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\n"790          },791          "metadata": {}792        }793      ]794    },795    {796      "cell_type": "markdown",797      "source": [798        "## **COMPARATIVE EVALUATION OF APPROACHES**"799      ],800      "metadata": {801        "id": "kVDaCbA1XM-k"802      }803    },804    {805      "cell_type": "code",806      "source": [807        "# CORRECT COMPARISON โ€” Both models on TEST SET only\n",808        "X_test_list = X_test.tolist()\n",809        "\n",810        "# Rule-Based on Test Set\n",811        "rule_pred_test = [rule_based_classifier(msg) for msg in X_test_list]\n",812        "\n",813        "# ML on Test Set (already predicted)\n",814        "ml_pred_test = y_pred_ml\n",815        "\n",816        "# Calculate accuracy on same test set\n",817        "rule_acc_test = accuracy_score(y_test, rule_pred_test)\n",818        "ml_acc_test = accuracy_score(y_test, ml_pred_test)\n",819        "\n",820        "print(\"=== FIXED MODEL COMPARISON (Test Set Only) ===\")\n",821        "print(f\"Rule-Based Accuracy: {rule_acc_test:.2f}\")\n",822        "print(f\"ML Model Accuracy:    {ml_acc_test:.2f}\")\n",823        "\n",824        "# Table\n",825        "pd.DataFrame({\n",826        "    'Model': ['Rule-Based', 'ML Model'],\n",827        "    'Accuracy': [rule_acc_test, ml_acc_test]\n",828        "})"829      ],830      "metadata": {831        "colab": {832          "base_uri": "https://localhost:8080/",833          "height": 164834        },835        "id": "tg8J1cYtQ67Q",836        "outputId": "e2a6a38e-efc6-4dd2-9f0f-3071e3701762"837      },838      "execution_count": 6,839      "outputs": [840        {841          "output_type": "stream",842          "name": "stdout",843          "text": [844            "=== FIXED MODEL COMPARISON (Test Set Only) ===\n",845            "Rule-Based Accuracy: 0.83\n",846            "ML Model Accuracy:    0.64\n"847          ]848        },849        {850          "output_type": "execute_result",851          "data": {852            "text/plain": [853              "        Model  Accuracy\n",854              "0  Rule-Based  0.833333\n",855              "1    ML Model  0.642857"856            ],857            "text/html": [858              "\n",859              "  <div id=\"df-b6e79223-e76e-4a23-a0f2-8577e5e273f2\" class=\"colab-df-container\">\n",860              "    <div>\n",861              "<style scoped>\n",862              "    .dataframe tbody tr th:only-of-type {\n",863              "        vertical-align: middle;\n",864              "    }\n",865              "\n",866              "    .dataframe tbody tr th {\n",867              "        vertical-align: top;\n",868              "    }\n",869              "\n",870              "    .dataframe thead th {\n",871              "        text-align: right;\n",872              "    }\n",873              "</style>\n",874              "<table border=\"1\" class=\"dataframe\">\n",875              "  <thead>\n",876              "    <tr style=\"text-align: right;\">\n",877              "      <th></th>\n",878              "      <th>Model</th>\n",879              "      <th>Accuracy</th>\n",880              "    </tr>\n",881              "  </thead>\n",882              "  <tbody>\n",883              "    <tr>\n",884              "      <th>0</th>\n",885              "      <td>Rule-Based</td>\n",886              "      <td>0.833333</td>\n",887              "    </tr>\n",888              "    <tr>\n",889              "      <th>1</th>\n",890              "      <td>ML Model</td>\n",891              "      <td>0.642857</td>\n",892              "    </tr>\n",893              "  </tbody>\n",894              "</table>\n",895              "</div>\n",896              "    <div class=\"colab-df-buttons\">\n",897              "\n",898              "  <div class=\"colab-df-container\">\n",899              "    <button class=\"colab-df-convert\" onclick=\"convertToInteractive('df-b6e79223-e76e-4a23-a0f2-8577e5e273f2')\"\n",900              "            title=\"Convert this dataframe to an interactive table.\"\n",901              "            style=\"display:none;\">\n",902              "\n",903              "  <svg xmlns=\"http://www.w3.org/2000/svg\" height=\"24px\" viewBox=\"0 -960 960 960\">\n",904              "    <path d=\"M120-120v-720h720v720H120Zm60-500h600v-160H180v160Zm220 220h160v-160H400v160Zm0 220h160v-160H400v160ZM180-400h160v-160H180v160Zm440 0h160v-160H620v160ZM180-180h160v-160H180v160Zm440 0h160v-160H620v160Z\"/>\n",905              "  </svg>\n",906              "    </button>\n",907              "\n",908              "  <style>\n",909              "    .colab-df-container {\n",910              "      display:flex;\n",911              "      gap: 12px;\n",912              "    }\n",913              "\n",914              "    .colab-df-convert {\n",915              "      background-color: #E8F0FE;\n",916              "      border: none;\n",917              "      border-radius: 50%;\n",918              "      cursor: pointer;\n",919              "      display: none;\n",920              "      fill: #1967D2;\n",921              "      height: 32px;\n",922              "      padding: 0 0 0 0;\n",923              "      width: 32px;\n",924              "    }\n",925              "\n",926              "    .colab-df-convert:hover {\n",927              "      background-color: #E2EBFA;\n",928              "      box-shadow: 0px 1px 2px rgba(60, 64, 67, 0.3), 0px 1px 3px 1px rgba(60, 64, 67, 0.15);\n",929              "      fill: #174EA6;\n",930              "    }\n",931              "\n",932              "    .colab-df-buttons div {\n",933              "      margin-bottom: 4px;\n",934              "    }\n",935              "\n",936              "    [theme=dark] .colab-df-convert {\n",937              "      background-color: #3B4455;\n",938              "      fill: #D2E3FC;\n",939              "    }\n",940              "\n",941              "    [theme=dark] .colab-df-convert:hover {\n",942              "      background-color: #434B5C;\n",943              "      box-shadow: 0px 1px 3px 1px rgba(0, 0, 0, 0.15);\n",944              "      filter: drop-shadow(0px 1px 2px rgba(0, 0, 0, 0.3));\n",945              "      fill: #FFFFFF;\n",946              "    }\n",947              "  </style>\n",948              "\n",949              "    <script>\n",950              "      const buttonEl =\n",951              "        document.querySelector('#df-b6e79223-e76e-4a23-a0f2-8577e5e273f2 button.colab-df-convert');\n",952              "      buttonEl.style.display =\n",953              "        google.colab.kernel.accessAllowed ? 'block' : 'none';\n",954              "\n",955              "      async function convertToInteractive(key) {\n",956              "        const element = document.querySelector('#df-b6e79223-e76e-4a23-a0f2-8577e5e273f2');\n",957              "        const dataTable =\n",958              "          await google.colab.kernel.invokeFunction('convertToInteractive',\n",959              "                                                    [key], {});\n",960              "        if (!dataTable) return;\n",961              "\n",962              "        const docLinkHtml = 'Like what you see? Visit the ' +\n",963              "          '<a target=\"_blank\" href=https://colab.research.google.com/notebooks/data_table.ipynb>data table notebook</a>'\n",964              "          + ' to learn more about interactive tables.';\n",965              "        element.innerHTML = '';\n",966              "        dataTable['output_type'] = 'display_data';\n",967              "        await google.colab.output.renderOutput(dataTable, element);\n",968              "        const docLink = document.createElement('div');\n",969              "        docLink.innerHTML = docLinkHtml;\n",970              "        element.appendChild(docLink);\n",971              "      }\n",972              "    </script>\n",973              "  </div>\n",974              "\n",975              "\n",976              "    <div id=\"df-e39e47e5-b9e3-4636-b16a-43b46922c1e6\">\n",977              "      <button class=\"colab-df-quickchart\" onclick=\"quickchart('df-e39e47e5-b9e3-4636-b16a-43b46922c1e6')\"\n",978              "                title=\"Suggest charts\"\n",979              "                style=\"display:none;\">\n",980              "\n",981              "<svg xmlns=\"http://www.w3.org/2000/svg\" height=\"24px\"viewBox=\"0 0 24 24\"\n",982              "     width=\"24px\">\n",983              "    <g>\n",984              "        <path d=\"M19 3H5c-1.1 0-2 .9-2 2v14c0 1.1.9 2 2 2h14c1.1 0 2-.9 2-2V5c0-1.1-.9-2-2-2zM9 17H7v-7h2v7zm4 0h-2V7h2v10zm4 0h-2v-4h2v4z\"/>\n",985              "    </g>\n",986              "</svg>\n",987              "      </button>\n",988              "\n",989              "<style>\n",990              "  .colab-df-quickchart {\n",991              "      --bg-color: #E8F0FE;\n",992              "      --fill-color: #1967D2;\n",993              "      --hover-bg-color: #E2EBFA;\n",994              "      --hover-fill-color: #174EA6;\n",995              "      --disabled-fill-color: #AAA;\n",996              "      --disabled-bg-color: #DDD;\n",997              "  }\n",998              "\n",999              "  [theme=dark] .colab-df-quickchart {\n",1000              "      --bg-color: #3B4455;\n",1001              "      --fill-color: #D2E3FC;\n",1002              "      --hover-bg-color: #434B5C;\n",1003              "      --hover-fill-color: #FFFFFF;\n",1004              "      --disabled-bg-color: #3B4455;\n",1005              "      --disabled-fill-color: #666;\n",1006              "  }\n",1007              "\n",1008              "  .colab-df-quickchart {\n",1009              "    background-color: var(--bg-color);\n",1010              "    border: none;\n",1011              "    border-radius: 50%;\n",1012              "    cursor: pointer;\n",1013              "    display: none;\n",1014              "    fill: var(--fill-color);\n",1015              "    height: 32px;\n",1016              "    padding: 0;\n",1017              "    width: 32px;\n",1018              "  }\n",1019              "\n",1020              "  .colab-df-quickchart:hover {\n",1021              "    background-color: var(--hover-bg-color);\n",1022              "    box-shadow: 0 1px 2px rgba(60, 64, 67, 0.3), 0 1px 3px 1px rgba(60, 64, 67, 0.15);\n",1023              "    fill: var(--button-hover-fill-color);\n",1024              "  }\n",1025              "\n",1026              "  .colab-df-quickchart-complete:disabled,\n",1027              "  .colab-df-quickchart-complete:disabled:hover {\n",1028              "    background-color: var(--disabled-bg-color);\n",1029              "    fill: var(--disabled-fill-color);\n",1030              "    box-shadow: none;\n",1031              "  }\n",1032              "\n",1033              "  .colab-df-spinner {\n",1034              "    border: 2px solid var(--fill-color);\n",1035              "    border-color: transparent;\n",1036              "    border-bottom-color: var(--fill-color);\n",1037              "    animation:\n",1038              "      spin 1s steps(1) infinite;\n",1039              "  }\n",1040              "\n",1041              "  @keyframes spin {\n",1042              "    0% {\n",1043              "      border-color: transparent;\n",1044              "      border-bottom-color: var(--fill-color);\n",1045              "      border-left-color: var(--fill-color);\n",1046              "    }\n",1047              "    20% {\n",1048              "      border-color: transparent;\n",1049              "      border-left-color: var(--fill-color);\n",1050              "      border-top-color: var(--fill-color);\n",1051              "    }\n",1052              "    30% {\n",1053              "      border-color: transparent;\n",1054              "      border-left-color: var(--fill-color);\n",1055              "      border-top-color: var(--fill-color);\n",1056              "      border-right-color: var(--fill-color);\n",1057              "    }\n",1058              "    40% {\n",1059              "      border-color: transparent;\n",1060              "      border-right-color: var(--fill-color);\n",1061              "      border-top-color: var(--fill-color);\n",1062              "    }\n",1063              "    60% {\n",1064              "      border-color: transparent;\n",1065              "      border-right-color: var(--fill-color);\n",1066              "    }\n",1067              "    80% {\n",1068              "      border-color: transparent;\n",1069              "      border-right-color: var(--fill-color);\n",1070              "      border-bottom-color: var(--fill-color);\n",1071              "    }\n",1072              "    90% {\n",1073              "      border-color: transparent;\n",1074              "      border-bottom-color: var(--fill-color);\n",1075              "    }\n",1076              "  }\n",1077              "</style>\n",1078              "\n",1079              "      <script>\n",1080              "        async function quickchart(key) {\n",1081              "          const quickchartButtonEl =\n",1082              "            document.querySelector('#' + key + ' button');\n",1083              "          quickchartButtonEl.disabled = true;  // To prevent multiple clicks.\n",1084              "          quickchartButtonEl.classList.add('colab-df-spinner');\n",1085              "          try {\n",1086              "            const charts = await google.colab.kernel.invokeFunction(\n",1087              "                'suggestCharts', [key], {});\n",1088              "          } catch (error) {\n",1089              "            console.error('Error during call to suggestCharts:', error);\n",1090              "          }\n",1091              "          quickchartButtonEl.classList.remove('colab-df-spinner');\n",1092              "          quickchartButtonEl.classList.add('colab-df-quickchart-complete');\n",1093              "        }\n",1094              "        (() => {\n",1095              "          let quickchartButtonEl =\n",1096              "            document.querySelector('#df-e39e47e5-b9e3-4636-b16a-43b46922c1e6 button');\n",1097              "          quickchartButtonEl.style.display =\n",1098              "            google.colab.kernel.accessAllowed ? 'block' : 'none';\n",1099              "        })();\n",1100              "      </script>\n",1101              "    </div>\n",1102              "\n",1103              "    </div>\n",1104              "  </div>\n"1105            ],1106            "application/vnd.google.colaboratory.intrinsic+json": {1107              "type": "dataframe",1108              "summary": "{\n  \"name\": \"})\",\n  \"rows\": 2,\n  \"fields\": [\n    {\n      \"column\": \"Model\",\n      \"properties\": {\n        \"dtype\": \"string\",\n        \"num_unique_values\": 2,\n        \"samples\": [\n          \"ML Model\",\n          \"Rule-Based\"\n        ],\n        \"semantic_type\": \"\",\n        \"description\": \"\"\n      }\n    },\n    {\n      \"column\": \"Accuracy\",\n      \"properties\": {\n        \"dtype\": \"number\",\n        \"std\": 0.13468700594029476,\n        \"min\": 0.6428571428571429,\n        \"max\": 0.8333333333333334,\n        \"num_unique_values\": 2,\n        \"samples\": [\n          0.6428571428571429,\n          0.8333333333333334\n        ],\n        \"semantic_type\": \"\",\n        \"description\": \"\"\n      }\n    }\n  ]\n}"1109            }1110          },1111          "metadata": {},1112          "execution_count": 61113        }1114      ]1115    },1116    {1117      "cell_type": "code",1118      "source": [1119        "import gradio as gr\n",1120        "# Define some common software-related keywords\n",1121        "tech_keywords = [\n",1122        "    \"fix\", \"bug\", \"error\", \"issue\", \"feature\", \"update\", \"refactor\",\n",1123        "    \"login\", \"signup\", \"user\", \"api\", \"database\", \"module\", \"function\",\n",1124        "    \"class\", \"variable\", \"code\", \"ui\", \"backend\", \"frontend\", \"auth\",\n",1125        "    \"encryption\", \"validation\", \"session\", \"deploy\"\n",1126        "]\n",1127        "\n",1128        "def is_meaningless(msg):\n",1129        "    words = msg.lower().split()\n",1130        "\n",1131        "    # Too short\n",1132        "    if len(words) < 3:\n",1133        "        return True\n",1134        "\n",1135        "    # If no technical keywords present\n",1136        "    if not any(kw in msg.lower() for kw in tech_keywords):\n",1137        "        return True\n",1138        "\n",1139        "    return False\n",1140        "\n",1141        "def predict_commit_quality(commit_message):\n",1142        "    msg = commit_message.strip()\n",1143        "\n",1144        "    # ๐Ÿšจ If meaningless/unrelated โ†’ directly LOW\n",1145        "    if is_meaningless(msg):\n",1146        "        return \"LOW\", \"LOW\", \"\"\"\n",1147        "        <div style='\n",1148        "            text-align: center;\n",1149        "            padding: 15px;\n",1150        "            background-color: #e74c3c;\n",1151        "            color: white;\n",1152        "            border-radius: 10px;\n",1153        "            font-weight: bold;\n",1154        "            font-size: 18px;\n",1155        "            margin-top: 10px;\n",1156        "        '>LOW QUALITY โ€” Not a Valid/Meaningful Commit Message</div>\n",1157        "        \"\"\"\n",1158        "\n",1159        "    # Rule-based prediction\n",1160        "    rule_pred = rule_based_classifier(msg)\n",1161        "\n",1162        "    # ML prediction (confidence not shown in UI)\n",1163        "    ml_pred = ml_model.predict([msg])[0]\n",1164        "\n",1165        "    # Final verdict: rule-based dominates (since in your project rules were more accurate)\n",1166        "    if rule_pred == 'low' or ml_pred == 'low':\n",1167        "        verdict_html = \"\"\"\n",1168        "        <div style='\n",1169        "            text-align: center;\n",1170        "            padding: 15px;\n",1171        "            background-color: #e74c3c;\n",1172        "            color: white;\n",1173        "            border-radius: 10px;\n",1174        "            font-weight: bold;\n",1175        "            font-size: 18px;\n",1176        "            margin-top: 10px;\n",1177        "        '>LOW QUALITY โ€” Needs Improvement</div>\n",1178        "        \"\"\"\n",1179        "    else:\n",1180        "        verdict_html = \"\"\"\n",1181        "        <div style='\n",1182        "            text-align: center;\n",1183        "            padding: 15px;\n",1184        "            background-color: #27ae60;\n",1185        "            color: white;\n",1186        "            border-radius: 10px;\n",1187        "            font-weight: bold;\n",1188        "            font-size: 18px;\n",1189        "            margin-top: 10px;\n",1190        "        '>GOOD QUALITY COMMIT</div>\n",1191        "        \"\"\"\n",1192        "\n",1193        "    return rule_pred.upper(), ml_pred.upper(), verdict_html\n",1194        "\n",1195        "\n",1196        "\n",1197        "# --- Gradio UI ---\n",1198        "with gr.Blocks(theme=\"soft\", css=\"\"\"\n",1199        "    footer { display: none !important; }\n",1200        "    .app-footer {\n",

Showing the first 1,200 of 1311 lines. Download the file for the rest.